medium の Angular: Supercharging The Router の翻訳です ルーターがルーティング以上のことをする場合
アプリに「お問い合わせ」リンクがあり、専用ページにルーティングする代わりに、問い合わせフォームをポップアップ表示したいとします。
「お問い合わせ」ボタンをハードコーディングしても、クリックしたときとは異なる操作をすることは問題ありませんが、ルーターに「何か違う」ことを指示する方法があると便利ではないでしょうか。
これの最大の利点は、ツールバーまたはメニュー上のすべてのリンクを処理するユニークな方法を持つことです。実際にナビゲーションをトリガーするか、必要な他の操作を実行するかは関係ありません。
これを達成する方法を見てみましょう。
ActionLink Observer
基本的な考え方は、 CanActivate 保護メカニズムを利用してルーティング要求をインターセプトすることです。
上記のコードは、ルーティングガードとして使用される ActionLinkObserver という名前のサービスを実装しています。
上記の例では、 ActionLinkObserver を使用して「popup」というパスを保護しているため、アプリケーションがそこをナビゲートするたびに、オブザーバーはリクエストをインターセプトし、実際のナビゲーションが行われないようにします。
代わりに、他のユーザーが次のセクションで説明するようにコンテンツをさらに処理できるように、ルートは observer$
subject に沿ってプッシュされます。
お気づきかもしれませんが、ルートはコンポーネントプロパティとして NotFoundComponent を使用します。 これは、ルーターがルートの一貫性を確認しているときにエラーをスローするのを避けるために必要であるため、コンポーネントを定義する必要があります。
ところで、これは静的ルートを定義する場合にのみ必要であるため、遅延ロードモジュールで ActionLinkObserver を使用するときはいつでも、コンポーネントプロパティを未定義のままにすることができます。
Observer の登録
ルーティングガードとして機能することに加えて、サービスは任意のコンポーネントまたはディレクティブに挿入できるため、後者は必要に応じてリンクのアクティブ化に基づいて機能します。
register()
メソッドを呼び出すことにより、サービスは Observable を返します。この Observable は、指定されたリンクがアクティブになると発行されます。
フィルタリングメカニズムは、関数の呼び出しに沿って渡されるアクションコードを、ルート構成で定義されているルートパス値と比較することで実現されます。
最終的にルート内でエンコードされるすべてのクエリパラメーターは、プロパティとして単一のオブジェクトにパックされ、サブスクライバーに渡されるため、結果のアクションの動作をさらにカスタマイズできます。
ActionLink Directive
汎用ディレクティブでもまったく同じロジックを実装できます。
この実装では、 wmActionLink
入力が動作するリンクパスを取得し、それに応じて ActionLinkObserver サービスに登録して、結果を activate
出力に出力します。
すべてまとめる
すべてのピースを配置したら、ポップアップダイアログを表示できます。
ここでは、 MatDialog の declarative version を使用しています。
このダイアログは、wmActionLink ディレクティブを使用して app.component.html テンプレートで宣言され、アクティブ化されると開きます。
自分で試してみてください
ここで説明するコードは、Github でホストされるオープンソースプロジェクトである wizdm.io の一部です。 質問や好奇心については、 hello@wizdm.io までお気軽にご連絡ください。
ここで説明するコードの完全に機能するデモは、 StackBlitz でライブで利用できます。