4

ページのURLをローカライズ/翻訳する必要があるという要件があります。既存のメカニズムは、実際に公開されたURLに依存して、oDataを介してページを取得します。簡単な例で明確にするために、フロントエンドにリクエストURLを受け取るロジックがあります(ファイル拡張子はなく、.html拡張子を追加します。例:

/my-awesome-path/my-awesome-page

今になる

/my-awesome-path/my-awesome-page.html

次に、ロジックはクエリを使用してoDataからページをプルします

/odata.svc/Pages?$filter=url eq '/my-awesome-path/my-awesome-page.html'

このSEO対応のURLを解析し、MVCコントローラーの関数パラメーターやその他の情報を取得するためのロジックは他にもたくさんありますが、ここでは関係ありません。

私たちの要件は、ページをローカライズして翻訳されたURLを提供できないことです。これは、ページ全体を親Webパブリケーションで管理できないことを意味するためです。

ページファイル名に至るまでのローカライズされたパスを取得するには、SGをローカライズするだけです。難しいのはページのファイル名です。ページのメタデータには、ローカライズされたページのファイル名を提供するためのフィールドを持つリンクされた「ローカライズ可能なメタデータ」コンポーネントがあります。

公開/デプロイプロセス中にページのURLプロパティを更新して、このリンクされたメタデータコンポーネントからのローカライズされたページファイル名でページの公開URLを更新します(ローカライズされたファイル名フィールドの値にいつでもアクセスできると想定します)公開の開始から展開のコミットメントまで)。

カスタムリゾルバーを介してこれを実行しようとしましたが、このレベルでは、page.PublishedUrlプロパティはCMによって既に確立されており、オーバーライドできないようです。したがって、page.FileNameプロパティを更新しても、何の役にも立ちません。

また、Broker DBのPAGEテーブルのURL列を別の名前に直接更新しようとしましたが、動的リンクやページの非公開など、すべてが引き続き機能しているようです。明らかに、jdbcを介してDBを直接更新するためにストレージ拡張機能またはデプロイヤー拡張機能を作成することは受け入れられません。

私が考えているオプションは次のとおりです。1)デプロイヤー拡張機能を試し、Tridion APIを使用してurlプロパティを更新します。2)ブローカーで実際にURLを更新せずにURL置換ロジックを実行するカスタムレンダラーを作成してみます。毎回リクエスト時の処理が必要になるので、これは好きではありません。

私の質問は、ページのURLプロパティを更新するための最も適切な方法は何ですか?Tridion APIを使用してカスタムデプロイヤーを作成してURLプロパティを更新すると、Resolverと同じように行き止まりになりますか?

4

2 に答える 2

3

上記のNunoのコメントのポイントに従って、カスタムデプロイヤーを使用しないことにし、イベントシステムの2つのイベントサブスクリプションを使用して問題を解決しました。ページ公開では、最初にページをローカライズし、ローカライズされたリンクされたメタデータコンポーネントからローカライズされたファイル名を取得して、ページを保存します。その後のイベントでは、単にページのローカライズを解除します。これが私の作業コードです:

[TcmExtension("Publish or Unpublish Events")]
public class PublishOrUnpublishEvents : TcmExtension
{
    public PublishOrUnpublishEvents()
    {
        EventSystem.Subscribe<Page, PublishEventArgs>(SetLocalizedPageFileName, EventPhases.Initiated);
        EventSystem.Subscribe<Page, SetPublishStateEventArgs>(UnlocalizePageOncePublished, EventPhases.Initiated);
    }


    public void SetLocalizedPageFileName(Page page, PublishEventArgs args, EventPhases phase)
    {
        string localFilename = GetLocalilizedFileNameFromPageMetadata(page);
        if (!string.IsNullOrEmpty(localFilename))
        {
            page.Localize();
            if (page.TryCheckOut())
            {
                page.FileName = localFilename;
                page.Save(true);
            }
        }
    }

    public void UnlocalizePageOncePublished(Page page, SetPublishStateEventArgs args, EventPhases phase)
    {
        string localFilename = GetLocalilizedFileNameFromPageMetadata(page);
        if (!string.IsNullOrEmpty(localFilename))
            page.UnLocalize();
    }

    private string GetLocalilizedFileNameFromPageMetadata(Page page)
    {
        string localFilename = string.Empty;
        if (page.Metadata != null)
        {
            ItemFields fields = new ItemFields(page.Metadata, page.MetadataSchema);
            if (fields.Contains("LocalizableMeta"))
            {
                ComponentLinkField localMetaField = fields["LocalizableMeta"] as ComponentLinkField;
                Component component = localMetaField.Value;
                ItemFields compFields = new ItemFields(component.Content, component.Schema);
                if (compFields.Contains("LocalizedPageFilename"))
                {
                    SingleLineTextField fileNameTextField = compFields["LocalizedPageFilename"] as SingleLineTextField;
                    localFilename = fileNameTextField.Value;
                }
            }
        }
        return localFilename;
    }
}
于 2013-01-11T04:48:14.990 に答える
1

おそらく別のオプション:

ローカライズされた URL を保存すると、ページの追加のメタデータ フィールドがあり、公開されたページの同じ物理 URL が維持されます。

あなたの要件は、子ページのローカライズを避けることだと思います。Wordpress で、URL がどのように機能するかをグローバルに入力できる方法が気に入っています。次に例を示します。

/マイサイト/ %postname%/

コンテンツのタイトルを抽出してコンテンツの URL で使用できるように、SDL Tridion 内でこれに似たものを構築できれば素晴らしいと思います。

いずれにせよ、'Friendly URL' を取​​得して実際の URL を検索するシステムを作成する必要がある場合、これは非常に簡単だと思います。

于 2013-01-09T08:41:01.823 に答える