CanDeactivate route guards

ה-guard CanDeactivate משמש לשליטה של מי שיכול לצאת מעמוד.

נניח שיש לנו מישהו שממלא טופס ורוצה לצאת באמצע בלי שהוא שמר את הנתונים. עם CanDeactivate אנחנו יכולים לתת לו הודעה לפני שהוא יוצא מהעמוד.

יצירת ה-guard:

ng g guard guards/contact-form

contact-form.gourd.ts

export class ContactFormGuard implements CanDeactivate<unknown> {
  canDeactivate(
    component: unknown,
    currentRoute: ActivatedRouteSnapshot,
    currentState: RouterStateSnapshot,
    nextState?: RouterStateSnapshot): Observable<boolean | UrlTree> | 
        Promise<boolean | UrlTree> | boolean | UrlTree {
    return true;
  }
}

אנחנו רוצים להשתמש בפונקציה deactivate על קומפוננטת contact ולכן נכניס אותה לערגים שהפונקציה מקבלת.

contact-form.gourd.ts

export class ContactFormGuard implements CanDeactivate<ContactComponent>

נכניס את ה-guard ל-route המתאים:

app.module

{ path: 'contact', canDeactivate: [ContactFormGuard], component: ContactComponent },

אם הפונקציה canDeactivate מחזירה false המשתמש לא יכול לצאת מהעמוד.

נקח את הטופס בעמוד צור קשר ונגדיר את פונקצית canExit שמחזירה false אם לא כל השדות מלאים.

contact.comp.ts

firstName: string = '';
lastName: string = '';
message: string = '';
email: string = '';

canExit(){
    if(this.firstName || this.lastName || this.message || this.email){
      return confirm('You have unsaved changes. Do you want to exit.');
    } else {
      return true;
    }
}

בפונקציה canDeactivate נגש לפונקציה canExit ונבדוק מה היא מחזירה. לפי זה נקבע האם המשתמש יכול לצאת מהעמוד.

contact-form.gourd.ts

canDeactivate(
    component: ContactComponent,
    currentRoute: ActivatedRouteSnapshot,
    currentState: RouterStateSnapshot,
    nextState?: RouterStateSnapshot): Observable<boolean | UrlTree> | Promise<boolean | UrlTree> | boolean | UrlTree {

    return component.canExit();
}

canDeactivate גלובלי

נניח שאנחנו רוצים איזה תנאי כללי שחוסם יציאה מעמודים.

ניצור interface כללי שבודק את הערך של פונקציית canExit המקומית של הקומפוננטה.

export interface IDiactivateComponent{
  canExit: () => Observable<boolean | UrlTree> | Promise<boolean | UrlTree> | boolean | UrlTree;
}

עכשיו אנחנו יכולים לקבל את הערך של הפונקציה המקומית לקומפוננטה שאותה אנחנו בודקים.

contact-form.gourd.ts

export class ContactFormGuard implements CanDeactivate<IDiactivateComponent>

הקומפוננטה תצטרך לממש את ה-interface שיצרנו ואת הפונקציה canExit.

contact.comp.ts

export class ContactComponent implements IDiactivateComponent{