احراز هویت کاربران با یک کادر Pop–up در انگولار – از صفر تا صد


در این مقاله با روش طراحی یک کادر محاورهای Pop-up در انگولار برای احراز هویت کاربران آشنا میشویم و بدین ترتیب لزوم ریدایرکت کردن کاربران از میان برداشته میشود.
هر نوع اپلیکیشنی که قصد داشته باشید توسعه دهید، در هر حال باید یکی از روشهای احراز هویت کاربران را پیادهسازی کنید. با این که ممکن است تصور کنید کاربران اهمیت کمی به جزییات پیادهسازی این قابلیتهای اساسی یک اپلیکیشن میدهند، اما مطمئن باشید که این موارد، تأثیر زیادی روی طراحی اپلیکیشن دارند و از این رو باید همه نکات را پیش از کامیت یا پیادهسازی گزینههای خود مورد ارزیابی دقیق قرار دهید.
در این مقاله یک روش احراز هویت کاربران با استفاده از کادر محاورهای modal را بررسی میکنیم. بدین ترتیب اگر کاربر تلاش کند تا عملی اجرا کند یا به یک صفحه مراجعه کند که نیازمند احراز هویت است، این کادر محاورهای باز میشود و از لزوم ریدایرکت کردن کاربر به صفحه دیگر جلوگیری میکند.
آیتمهای مورد نیاز
برای ساختن کادر محاورهای احراز هویت به موارد زیر نیاز داریم:
- Auth: سرویس احراز هویت با استفاده از سرویس AngularFireAuth از AngularFire (+) پیاده سازی میشود.
- AuthGuard: یک سرویس کاربردی به عنوان محافظ مسیریابی استفاده خواهد شد که هر زمان کاربر تلاش کند به صفحههای خصوصی دست یابد، به کاربر هشدار میدهد که باید اطلاعات احراز هویت خود را وارد کند.
- LoginComponent: کامپوننت واقعی که فرم لاگین را تحقق میبخشد و به لطف سرویس MatDialog از Angular Material (+) به صورت یک کادر محاورهای رندر میشود.
همه موارد فوق بخشی از یک دموی زنده هستند که میتوانید در این آدرس (+) ملاحظه کنید و همه کارکردهای توصیفشده را به چشم خود بررسی کنید.
سرویس Auth
ما با پیادهسازی سرویس احراز هویتمان قادر خواهیم بود نیازهای اپلیکیشن خود را به نحو بهتری پاسخگو باشیم و از این رو خواندن و نگهداری کدبیس کلی آسانتر خواهد بود.
فایل auth.service.ts
پیادهسازی فوق اساساً پوششی برای همه کارکردهای ارائه شده از سوی AngularFireAuth است و همزمان شیء User احراز هویت شده را نیز عرضه میکند. بدین ترتیب به لطف ()authenticated که هر زمان شیء کاربر معتبر باشد، مقدار true بازگشت میدهد، میتوانیم وضعیت احراز هویت را در همه جای اپلیکیشن بدون نیاز به اشتراک در یک observable مشاهده کنیم. به طور مشابه ()userId اقدام به بازگرداندن id کاربر احراز هویت شده میکند.
چنان که مشاهده خواهید کرد، هر دو مشخصه کاملاً کارگشا هستند.
نکته: البته Firebase.Auth یک شیء User احراز هویت شده در متغیری به نام currentUser ارائه میکند و ما نیز در نهایت کدبیس خود را به این روش آپدیت کردیم.
محافظ Auth
انگولار از مسیریابی برای ناوبری از یک view به view دیگر بهره میگیرد و در این زمان کاربران وظایفی در اپلیکیشن اجرا میکنند.
میتوان از مسیرها محافظت کرد تا کاربران نتوانند به صفحههایی که اجازه ندارند، دسترسی یابند. این سازوکار یک کادر محاورهای pop-up نمایش میدهد که از کاربر میخواهد هویت خود را احراز کند.
فایل auth-guard.service.ts
AuthGuard که در کد فوق ارائه شده است، اینترفیس canActivate را پیادهسازی میکند تا به مسیریاب اطلاع دهد که در مسیر خود در موارد لزوم از مسیرهای محافظتشده بهره بگیرد. AuthGuard پوششی برای AuthService به عنوان یک متغیر فقط-خواندنی است و از این رو با تزریق AuthGuard در یک کامپوننت همواره دسترسی آسانی به canActivate نیز خواهیم داشت.
تابع ()canActivate تابعی است که یک Promise با مقدار بولی بازگشت میدهد و زمانی که true باشد مسیر فعال میشود و زمانی که false باشد مسیر مسدود خواهد بود. همه کارها در فراخوانی ()authenticate انجام مییابد و تابع اصلی کادر محاورهای را نمایش میدهد و در صورت موفق بودن، شیء User احراز هویت شده بازگشت مییابد.
در مثال زیر از ظرفیت ()canActivate برای کار با اشیای ناهمگام استفاده میکنیم. به طوری که کادر محاورهای pop-up نمایش مییابد و از کاربر میخواهد که احراز هویت کند و بر همین مبنا کار را ادامه میدهد یا ناوبری لغو میشود.
متد احراز هویت
فرض کنید اپلیکیشن شما یک صفحه عمومی دارد که همه کس میتوانند آن را ببینند، اما تنها کاربران احراز هویت شده میتوانند کاری روی آن انجام دهند. ()authenticate برای این نوع از موقعیتها طراحی شده است.
فایل authenticate.ts
این متد یک observable به نام user$ را resolve میکند تا مشخص شود که آیا کاربر جاری قبلاً احراز هویت شده است یا نه. take(1) این observable را درست پس از این که مقدار منفرد مورد نیاز را دریافت کرد تکمیل میکند، سپس در صورت تهی بودن شیء User در ادامه ()switchMap از کاربر میخواهد که احراز هویت کند و در غیر این صورت مستقیماً با شیء User جاری اقدام به resolve میکند.
متد Prompt
متد ()Prompt متدی است که کادر محاورهای احراز هویت را به کمک سرویس MatDialog نمایش میدهد.
فایل prompt.ts
این سرویس به موارد زیر نیاز دارد:
- یک کامپوننت یا قالب برای رندر کردن به عنوان بدنه کادر محاورهای که به وسیله LoginComponent انجام مییابد.
- یک شیء اختیاری DIALOG_DATA که روی سازنده تزریقشده LoginComponent برای وارد کردن اطلاعات در دسترس خواهد بود. ما در این جا از متغیر loginAction برای انتخاب حالت نمایش کادر محاورهای استفاده میکنیم.
- یک شیء User که انتظار داریم از observable به نام ()afterClosed در کادر محاورهای بازگشت یابد.
همه موارد فوق زمانی که متد ()open برای نمایش کار محاورهای فراخوانی میشود، مورد استفاده قرار میگیرند و یک promise بازگشت میدهد که به صورت شیء User احراز هویت شده یا مقدار null خواهد بود.
کامپوننت Login
LoginComponent اساساً یک فرم است که در آن ایمیل و رمز عبور را برای وارد شدن به اکانت وارد میکنیم.
به علاوه این فرم به صورت دینامیک از یک حالت نمایشی به حالت دیگر تغییر مییابد. حالتهای نمایشی ممکن به صورت زیر هستند:
- signIn: جفت فیلدهای ایمیل و رمز عبور را به همراه آیکونهای ارائهدهندههای مختلف سرویسهای احراز هویت (گوگل، فیسبوک و غیره) نمایش میدهد تا به صورت یک کاربر ثبت شده موجود وارد شوید.
- Register: یک نام، ایمیل، و رمز عبور برای ثبت کردن کاربر جدید میپرسد.
- forgotPassword: یک ایمیل میخواهد تا لینک ریست کردن رمز عبور را به آن ارسال کند.
- changePassword: یک رمز عبور جدید میخواهد و عملیات را با دریافت رمز عبور فعلی تأیید میکند.
- changeEmail: یک ایمیل جدید میخواهد و عملیات با رمز عبور فعلی تأیید میشود.
- delete: از کاربر میخواهد که حذف حساب را با رمز عبور فعلی تأیید کند.
ساخت فرم
با توجه به این که کد کامل این پروژه در انتهای این مقاله ارائه شده است، ما در این بخش روی بخشهای کلیدی متمرکز میشویم:
فایل login-constructor.ts
زمانی که کادر محاورهای رندر میشود، سازنده LoginComponent نیز فراخوانی میشود. در این بخش MatDialogRef، یک شیء ارجاع به کادر محاورهای است و متغیر ورودیمان MAT_DIALOG_DATA را تزریق میکنیم که شامل حالت نمایشی است که میخواهیم فرم با آن آغاز به کار کند. فراموش نکنید که LoginComponent را در میان entryComponents ماژولش برای MatDialog لیست کنید تا آن را به طرز صحیحی رندر کند.
از آنجا که فرم بسته به حالت نمایشی، شامل فیلدهای مختلفی است، همه کنترلهای فرم به طور مجزا ایجاد میشوند، در حالی که فرم به عنوان یک گروه خالی ساخته میشود و منتظر متد switchPage() میماند تا کنترلهای مناسبی که باید اضافه شوند را انتخاب کند.
سوئیچ بین صفحات
این متد ابتدا با حذف همه کنترلها از گروه فرم و سپس افزودن موارد مرتبط بسته به آرگومان page، میان حالتهای نمایشی مختلف سوئیچ میکند.
فایل login-switch-page.ts
نمای کامپوننت بر همین اساس رندر میشود، چون قالب از متد ()contains گروه فرم برای تشخیص این که کدام فیلدها باید نمایش پیدا کنند استفاده میکند.
فایل login-template.html
از این رو در کد فوق میتوانید ببینید که mat-input-field شامل "formControlName="name است و از یک دایرکتیو "*ngIf="form.contains('name') برای تصمیمگیری در مورد رندر کردن یا نکردن view بهره میگیرد.
اعتبارسنجی فرم
ما با استفاده از این تکنیک تغییر دادن دینامیک محتوای گروه فرم، میتوانیم همواره طرز کار صحیحی از اعتبارسنجی Reactive Forms انگولار را بر اساس اعتبارسنجهای کنترل فرم ذکر شده شاهد باشیم. در این مثال از Validators.required بری هر کنترل تعیینشده به صورت الزامی و از Validators.email برای کنترلهای ایمیل استفاده کردهایم تا بر اساس ساختار ایمیل مناسب مورد بررسی قرار گیرند.
تحویل فرم
به طور مشابه، زمانی که کاربر فرم را تحویل دهد، کامپوننت ()activate را فراخوانی میکند.
فایل login-activate.ts
این کد به نوبه خود متد خاصی را برای حالت نمایشی فراخوانی میکند. از این رو در ادامه نگاهی به ()signIn به عنوان یک مثال ارزشمند خواهیم داشت:
فایل login-sign-in.ts
متد ()signIn ابتدا متد مرتبط AuthService را فرا میخواند و سپس کادر محاورهای را با استفاده از متد ()close که در MatDialogRef اشاره شده است میبندد و شیء USER احراز هویت شده را در بازگشت ارسال میکند.
سخن پایانی
در این مقاله دیدیم که متد ()authenticate در ابتدا و در طی حفاظت از مسیر از سوی ()canActivate فراخوانی میشود، مسیریاب بر اساس نتیجه این متد میتواند کار خود را ادامه داده یا ناوبری را لغو کند. بدیهی است که متد ()authenticate میتواند در غیر این صورت فراخوانی شود تا از کاربر درخواست ورود به حساب بکند و بدین ترتیب مطمئن میشویم که کاربر پیش از اجرای کاری که نیازمند احراز هویت روی صفحهای عمومی است، احراز هویت شده است.
اگر این مطلب برای شما مفید بوده است، آموزشهای زیر نیز به شما پیشنهاد میشوند:
- مجموعه آموزشهای JavaScript (جاوا اسکریپت)
- آموزش مقدماتی AngularJS برای ساخت اپلیکیشنهای تک صفحهای
- مجموعه آموزشهای برنامهنویسی
- آشنایی با Angular CLI – به زبان ساده
- ساخت کتابخانه انگولار با Angular CLI — از صفر تا صد
==