らいふうっどの閑話休題

興味のあることをゆる~く書いていく

Angular: Supercharging The Router の翻訳

mediumAngular: Supercharging The Router の翻訳です ルーターがルーティング以上のことをする場合

f:id:ic_lifewood:20200104224653j:plain
Photo by Shahadat Rahman on Unsplash

アプリに「お問い合わせ」リンクがあり、専用ページにルーティングする代わりに、問い合わせフォームをポップアップ表示したいとします。

「お問い合わせ」ボタンをハードコーディングしても、クリックしたときとは異なる操作をすることは問題ありませんが、ルーターに「何か違う」ことを指示する方法があると便利ではないでしょうか。

これの最大の利点は、ツールバーまたはメニュー上のすべてのリンクを処理するユニークな方法を持つことです。実際にナビゲーションをトリガーするか、必要な他の操作を実行するかは関係ありません。

これを達成する方法を見てみましょう。

ActionLink Observer

基本的な考え方は、 CanActivate 保護メカニズムを利用してルーティング要求をインターセプトすることです。

gist.github.com

上記のコードは、ルーティングガードとして使用される ActionLinkObserver という名前のサービスを実装しています。

gist.github.com

上記の例では、 ActionLinkObserver を使用して「popup」というパスを保護しているため、アプリケーションがそこをナビゲートするたびに、オブザーバーはリクエストをインターセプトし、実際のナビゲーションが行われないようにします。

代わりに、他のユーザーが次のセクションで説明するようにコンテンツをさらに処理できるように、ルートは observer$ subject に沿ってプッシュされます。

お気づきかもしれませんが、ルートはコンポーネントプロパティとして NotFoundComponent を使用します。 これは、ルーターがルートの一貫性を確認しているときにエラーをスローするのを避けるために必要であるため、コンポーネントを定義する必要があります。

ところで、これは静的ルートを定義する場合にのみ必要であるため、遅延ロードモジュールで ActionLinkObserver を使用するときはいつでも、コンポーネントプロパティを未定義のままにすることができます。

Observer の登録

ルーティングガードとして機能することに加えて、サービスは任意のコンポーネントまたはディレクティブに挿入できるため、後者は必要に応じてリンクのアクティブ化に基づいて機能します。

gist.github.com

register() メソッドを呼び出すことにより、サービスは Observable を返します。この Observable は、指定されたリンクがアクティブになると発行されます。

フィルタリングメカニズムは、関数の呼び出しに沿って渡されるアクションコードを、ルート構成で定義されているルートパス値と比較することで実現されます。

最終的にルート内でエンコードされるすべてのクエリパラメーターは、プロパティとして単一のオブジェクトにパックされ、サブスクライバーに渡されるため、結果のアクションの動作をさらにカスタマイズできます。

ActionLink Directive

汎用ディレクティブでもまったく同じロジックを実装できます。

gist.github.com

この実装では、 wmActionLink 入力が動作するリンクパスを取得し、それに応じて ActionLinkObserver サービスに登録して、結果を activate 出力に出力します。

すべてまとめる

すべてのピースを配置したら、ポップアップダイアログを表示できます。

gist.github.com

ここでは、 MatDialog の declarative version を使用しています。

このダイアログは、wmActionLink ディレクティブを使用して app.component.html テンプレートで宣言され、アクティブ化されると開きます。

自分で試してみてください

ここで説明するコードは、Github でホストされるオープンソースプロジェクトである wizdm.io の一部です。 質問や好奇心については、 hello@wizdm.io までお気軽にご連絡ください。

ここで説明するコードの完全に機能するデモは、 StackBlitz でライブで利用できます。

stackblitz.com

medium.com

medium.com