هر آنچه باید در مورد پارامترهای انگولار بدانید — از صفر تا صد
در این راهنما با روش دریافت دادهها از URL در یک اپلیکیشن انگولار آشنا خواهیم شد و ترفندهایی برای بهبود عملکرد این کار با بهرهگیری از RxJS را مورد بررسی قرار میدهیم. به این منظور باید با روش تنظیم پارامترهای انگولار آشنا شویم.
ما به طور معمول در اپلیکیشنهای انگولار با دو نوع URL سر و کار داریم:
- الگوی URL به صورت heroes/:limit/ برای نمونه: heroes/20/
- الگوی URL به صورت heroes/ برای نمونه: heroes?limit=20/
فریمورک انگولار تکنیکهای مختلفی برای انتخاب اطلاعات مورد نیاز در این ساختارهای URL جهت فراخوانی API و بارگذاری دادهها برای صفحه و اجرای اقدامات مختلف عرضه کرده است.
استفاده از route.snapshot.paramMap.get در زمان رفتن به صفحه دیگر
ابتدا باید در مورد ماهیت snapshot و paramMap توضیح دهیم. snapshot یک تصویر استاتیک از اطلاعات مسیر است که مدت کمی پس از ایجاد کامپوننت در اختیار ما قرار میگیرد.
paramMap یک دیکشنری از مقادیر پارامترهای مسیر است که از URL استخراج شده است. ماژول مسیریابی نمونه از Angular.io به صورت زیر است:
1import { NgModule } from '@angular/core';
2import { RouterModule, Routes } from '@angular/router';
3
4import { DashboardComponent } from './dashboard/dashboard.component';
5import { HeroesComponent } from './heroes/heroes.component';
6import { HeroDetailComponent } from './hero-detail/hero-detail.component';
7
8const routes: Routes = [
9 { path: '', redirectTo: '/dashboard', pathMatch: 'full' },
10 { path: 'dashboard', component: DashboardComponent },
11 { path: 'detail/:id', component: HeroDetailComponent },
12 { path: 'heroes', component: HeroesComponent }
13];
14
15@NgModule({
16 imports: [ RouterModule.forRoot(routes) ],
17 exports: [ RouterModule ]
18})
19export class AppRoutingModule {}
مثال فوق فهرستی از قهرمانان (heroes) را نمایش میدهد و زمانی که روی نام قهرمان کلیک شود به صفحه توضیح آن قهرمان (hero detail) میرود. ما یک ID قهرمان را از URL دریافت میکنیم و آن را به سرویس hero ارسال میکنیم تا دادهها را از طریق کدی مانند زیر از سرور دریافت کنیم:
این یک روش رسمی برای بازیابی دادهها از URL است. برای کسب اطلاعات بیشتر در این مورد به صفحه مستندات انگولار (+) بروید.
استفاده از اشتراک برای تغییرات URL
شاید از خود بپرسید، «اشتراک» (subscription) چیست؟ اشتراک شیئی است که یک منبع قابل افشا را نمایندگی میکند و به طور معمول نسخه اجرایی یک Observable است. برخی اوقات کاربر میتواند روی یک قهرمان مرتبط یا پیشنهاد یک قهرمان جدید در صفحه جزییات hero details کلیک کند. بدین ترتیب به یک صفحه hero details دیگر هدایت میشود که حاوی اطلاعات آن قهرمان دیگر است.
اینک مشکل در route.snapshot.paramMap.get است، چون دیگر کار نمیکند.
Snapshot رویدادی یک باره است که تنها پس از ایجاد کامپوننت تحریک میشود. بنابراین در صفحه جزییات قهرمان، اگر روی ناحیه پیشنهاد قهرمان کلیک کنیم، کار نمیکند زیرا کامپوننت نمیتواند دوباره مقداردهی شود و ID قهرمان ذخیره شده به صورت مقدار قدیمی است.
به طور معمول Subscription به عنوان راهحل این مشکل روشی عالی برای شناسایی موارد تغییر یافتن پارامتر URL در مسیریابی جاری محسوب میشود. این بدان معنی است که یک لینک یا دکمه وجود دارد که میتوان با URL یکسان با پارامترهای مختلف مانند مثال فوق عمل کند. مثالی از استفاده از اشتراک درون getHero به صورت زیر است:
سپس میتوانیم تفاوت را ملاحظه کنیم:
مدیریت لغو اشتراک با RxJS
استفاده از اشتراک، روشی عالی برای بهروزرسانی مقادیر ID قهرمان در پارامتر URL است. با این حال، اشتراک یک متد مهم به نام «لغو اشتراک» (unsubscribe) دارد. این متد هیچ آرگومانی نمیگیرد و صرفاً منبع نگهداری شده از سوی اشتراک را حذف میکند. هر Subscription اساساً یک تابع ()unsubscribe برای آزادسازی منابع یا لغو اجرای Observable دارد.
نگهداری اشیای اشتراک بیش از حد، نشانهای از روش نادرست مدیریت اشتراکها است و نشان میدهد که از مزیت قدرت RX بهرهگیری نمیشود. این بدان معنی است که متد لغو اشتراک موجب آزادسازی اشتراکی میشود که برای استفاده از سوی اشتراک بعدی زمانی که کاربر روی پیشنهاد قهرمان کلیک میکند ضروری است.
پیشنهاد میشود که همراه با اشتراک از switchMap (+) استفاده شود، زیرا مزیتهای زیادی در مقایسه با دیگر عملگرهای مسطح سازی دارد. این عملگر به یک observable جدید سوئیچ میکند و observable قبلی را لغو میکند. بدین ترتیب کد جدید getHero به صورت زیر درمیآید:
زمانی که نوع hero یک observable باشد، قالب باید یک pipe به نام async اضافه کند تا با observable کار کند.
مزیت این کار آن است که در صفحه جزییات قهرمان یک درخواست HTTP درون اشتراک فراخوانی میشود. در طی اجرای درخواست HTTP پارامتر تغییر مییابد. این بدان معنی است که یک اشتراک جدید با یک درخواست HTTP جدید ایجاد میشود.
در این صورت switchMap به ما کمک میکند که اشتراک و درخواست اخیر را لغو کنیم و سپس یک مورد جدید بسازیم. از این رو عملکرد تا حدود زیادی بهبود خواهد یافت. مزیتهای دیگر به شرح زیر هستند:
- امکان ترکیب کردن کد و خوانایی آن افزایش مییابد.
- به کد کمتری نیاز است و لذا به مدیریت کمتری نیاز دارد.
تست عملکرد حالت فوق به صورت زیر است.
سناریو
اشتراک بدون استفاده از switchMap
اشتراک با استفاده از switchMap
پس از چند کلیک روی UI زمان اجرای اسکریپت با switchMap کمتر از زمان عدم استفاده از switchMap بوده است.
نکته: روشهای زیادی برای پایان دادن یک اشتراک در RxJS وجود دارد که شامل take ،takeUntil ،takeWhile ،first میشود. استفاده از هر کدام از روشهای فوق بستگی به نوع کاربری دارد.
دریافت مقدار با queryParamMap
queryParamMap همان ParamMap است. تنها تفاوت در این است که از آن برای کار کردن با یک URL به شکل /heroes?limit=5 استفاده میکنیم. این پارامترها در مسیریابی یک اپلیکیشن انگولار استفاده نمیشوند. اینک متد getHeroes را بهروزرسانی میکنیم:
صفحه قهرمانان مقدار یک قهرمان را بر اساس پارامتر limit از URL به شکل /heroes?limit=5 نمایش خواهد داد.
سخن پایانی
در این مقاله برخی تکنیکها برای دریافت یک پارامتر از یک URL را معرفی کردیم. کاربرد هر یک از آنها به نوع کاربری وابسته است.
از route.snapshot.paramMap.get زمانی استفاده میشود که از این صفحه به صفحه دیگری میرویم. همچنین روش اشتراک به همراه switchMap زمانی استفاده میشود که پارامتر در آن مسیر تغییر پیدا کند.
برخی اوقات پارامتر در مسیریابی تعریف نمیشود و از این رو به جای paramMap از queryParamMap استفاده میکنیم.
اگر این مطلب برای شما مفید بوده است، آموزشهای زیر نیز به شما پیشنهاد میشوند:
- مجموعه آموزشهای JavaScript (جاوا اسکریپت)
- آموزش مقدماتی AngularJS برای ساخت اپلیکیشنهای تک صفحهای
- مجموعه آموزشهای برنامهنویسی
- کامپوننت کانتینری در انگولار (Angular) — از صفر تا صد
- ساخت داشبورد سازمانی مقیاس پذیر با انگولار — بخش اول
==