diff --git a/src/app/core/end-user-agreement/end-user-agreement-current-user.guard.spec.ts b/src/app/core/end-user-agreement/end-user-agreement-current-user.guard.spec.ts index 01835a62ef7..a291c86e3b0 100644 --- a/src/app/core/end-user-agreement/end-user-agreement-current-user.guard.spec.ts +++ b/src/app/core/end-user-agreement/end-user-agreement-current-user.guard.spec.ts @@ -22,7 +22,7 @@ describe('endUserAgreementGuard', () => { beforeEach(() => { endUserAgreementService = jasmine.createSpyObj('endUserAgreementService', { - hasCurrentUserAcceptedAgreement: of(true), + hasCurrentUserOrCookieAcceptedAgreement: of(true), }); router = jasmine.createSpyObj('router', { @@ -61,7 +61,7 @@ describe('endUserAgreementGuard', () => { describe('when the user hasn\'t accepted the agreement', () => { beforeEach(() => { - (endUserAgreementService.hasCurrentUserAcceptedAgreement as jasmine.Spy).and.returnValue(of(false)); + (endUserAgreementService.hasCurrentUserOrCookieAcceptedAgreement as jasmine.Spy).and.returnValue(of(false)); }); it('should return a UrlTree', (done) => { diff --git a/src/app/core/end-user-agreement/end-user-agreement-current-user.guard.ts b/src/app/core/end-user-agreement/end-user-agreement-current-user.guard.ts index e99ab32f27c..fffe9a5baf3 100644 --- a/src/app/core/end-user-agreement/end-user-agreement-current-user.guard.ts +++ b/src/app/core/end-user-agreement/end-user-agreement-current-user.guard.ts @@ -2,6 +2,7 @@ import { inject } from '@angular/core'; import { CanActivateFn } from '@angular/router'; import { APP_CONFIG } from '@dspace/config/app-config.interface'; import { of } from 'rxjs'; +import { take } from 'rxjs/operators'; import { endUserAgreementGuard } from './end-user-agreement.guard'; import { EndUserAgreementService } from './end-user-agreement.service'; @@ -20,6 +21,10 @@ export const endUserAgreementCurrentUserGuard: CanActivateFn = return of(true); } - return endUserAgreementService.hasCurrentUserAcceptedAgreement(true); + // Use hasCurrentUserOrCookieAcceptedAgreement to leverage synchronous cookie check + // This prevents guard hangs after PATCH operations when store cache may be stale + return endUserAgreementService.hasCurrentUserOrCookieAcceptedAgreement(true).pipe( + take(1), + ); }, ); diff --git a/src/app/core/end-user-agreement/end-user-agreement.service.ts b/src/app/core/end-user-agreement/end-user-agreement.service.ts index a7f92b244f8..573d3c1481c 100644 --- a/src/app/core/end-user-agreement/end-user-agreement.service.ts +++ b/src/app/core/end-user-agreement/end-user-agreement.service.ts @@ -52,6 +52,7 @@ export class EndUserAgreementService { switchMap((authenticated) => { if (authenticated) { return this.authService.getAuthenticatedUserFromStore().pipe( + take(1), map((user) => hasValue(user) && user.hasMetadata(END_USER_AGREEMENT_METADATA_FIELD) && user.firstMetadata(END_USER_AGREEMENT_METADATA_FIELD).value === 'true'), ); } else { @@ -84,7 +85,14 @@ export class EndUserAgreementService { return this.ePersonService.patch(user, [operation]); }), getFirstCompletedRemoteData(), - map((response) => response.hasSucceeded), + map((response) => { + const success = response.hasSucceeded; + // Set cookie as synchronous fallback to prevent guard hangs after PATCH + if (success) { + this.setCookieAccepted(accepted); + } + return success; + }), ); } else { this.setCookieAccepted(accepted); diff --git a/src/app/info/end-user-agreement/end-user-agreement.component.ts b/src/app/info/end-user-agreement/end-user-agreement.component.ts index 3e6585a8667..06ac15aca4e 100644 --- a/src/app/info/end-user-agreement/end-user-agreement.component.ts +++ b/src/app/info/end-user-agreement/end-user-agreement.component.ts @@ -69,7 +69,9 @@ export class EndUserAgreementComponent implements OnInit { * Initialize the "accepted" property of this component by checking if the current user has accepted it before */ initAccepted() { - this.endUserAgreementService.hasCurrentUserOrCookieAcceptedAgreement(false).subscribe((accepted) => { + this.endUserAgreementService.hasCurrentUserOrCookieAcceptedAgreement(false).pipe( + take(1), + ).subscribe((accepted) => { this.accepted = accepted; }); }