私はこのような文字列を持っています:My First - Recipe's
私はこれを読みやすいURLに翻訳したいと思います。アポストロフィとハイフンのURL文字の置き換え
スペースを-
に変更したいのですが、すでに文字列にハイフンがあります。また、アポストロフィがあります。
私はアンダースコアを使用して、私はハイフンを使用したいが、私はすでに1と同様にアポストロフィ
私はこのような文字列を持っています:My First - Recipe's
私はこれを読みやすいURLに翻訳したいと思います。アポストロフィとハイフンのURL文字の置き換え
スペースを-
に変更したいのですが、すでに文字列にハイフンがあります。また、アポストロフィがあります。
私はアンダースコアを使用して、私はハイフンを使用したいが、私はすでに1と同様にアポストロフィ
が存在する場合にハイフンを変更するかを把握することができない理由であるクリーンなURLで悪いことをオンラインで読みますWebページのURLでUnicodeを使用することはできますが、実用性と使いやすさのためには使用できる文字に制限があります。たとえば、人が完全なアドレスを手動で入力できるようにするには、すべてを避けるのが最善です英数字以外の文字、特に句読点を使用し、可能であれば、L
、l
、1
、i
、I
などの視覚的同型図も避けてください。等々。
したがって、内部のタイトルが「Kaajh'Kalbh!」である記事のWebページがある場合は、 URL名をkaajh-kaalbh
にします。
「Kaajh'Kalbh!」からの変換は、 "kaajh-kaalbh
"には情報が失われます。これは "one-way function"です。つまり、特定の出力("kaajh-kaalbh"
)を入力すると、元の入力( "Kaajh'Kalbh!")を判断するのは容易ではありません同じ出力につながる複数の入力がある可能性があるので、元の入力が何であるかを知ることはできません。なぜなら、「Kaajh'Kalbh」だったからです。または "Kaajh Kaalbh"または "Kaajh Kaalbh?" - 等々。
:GetUrlVersionOfTitle
はあなたのSQL関数です
SELECT * FROM Articles WHERE GetUrlVersionOfTitle(Title) = 'kaajh-kaalbh'
ことだろうそのような変換を実行します。あなたのクエリになる意味
GetUrlVersionOfTitle(x) = x.ToLower().Replace(' ', '-').Replace('\'', '-').Replace(etc)...
を... non-Sargable(see also)およびデータベース・システムを実行する必要があるため(ひどい実行時のクエリのパフォーマンスを持っているでしょうあなたのテーブルのすべての行に、毎回機能 - 明らかにそれは良くない)。また、最大でも1行に同じURL名があることを保証するという問題を解決することはできません(1行だけが指定されたURL名の入力と一致することを保証するため)。
溶液は、その後、URL名を事前計算別の列に格納し、また@urlTitle
値事前計算URL-あるパラメータである
CREATE TABLE Articles (
ArticleId int IDENTITY(1,1) NOT NULL PRIMARY KEY,
Title nvarchar(255) NOT NULL,
UrlTitle varchar(255) NOT NULL UNIQUE,
...
)
INSERT INTO Articles(Title, UrlTitle) VALUES (@title, @urlTitle)
(UNIQUE
に対する制約を有することですフレンドリーバージョンTitle
)。
そして、それは指定されたURLに対応する記事に一致するように簡単です:
ASPで。NET MVC:私自身のコードで
[Route("~/articles/{urlTitle}")]
public ActionResult GetArticle(String urlTitle) {
Article article
using(DbContext db = ...) {
article = db.Articles.SingleOrDefault(a => a.UrlTitle == urlTitle);
}
return this.View(new ArticleViewModel(article));
}
、私は最初に、正規化されたUnicode表現にテキストを変換し、その後ストリッピングアウト特殊記号を、またそのように、非数字/文字の文字をドロップすることで、URLに優しいタイトルを生成します。
これはだけは本当にラテン文字のために働くことに注意してください - 私は非ラテンシステムを対象としていたことがありません(例えば、ギリシャ語、キリル文字、アラビア語、ヘブライ語、ペルシア語など)YMMVので、同じ原則が適用されます。
public static String ConvertToUrlName(String title) {
if(title == null) throw new ArgumentNullException(nameof(title));
// Convert to normalized Unicode
// see here: https://stackoverflow.com/a/249126/159145
title = title.Normalize(NormalizationForm.FormD);
StringBuilder sb = new StringBuilder(title.Length);
foreach(Char c in title) {
// If the character is a diacritic or other non-base character, then ignore it
if(CharUnicodeInfo.GetUnicodeCategory(c) != UnicodeCategory.NonSpacingMark) continue;
c = Char.ToLowerInvariant(c); // convert to lower-case
if(Char.IsLetterOrDigit(c)) {
sb.Append(c);
}
else if(Char.IsWhiteSpace(c)) {
sb.Append('-');
}
// and ignore all other character classes, such as punctuation
}
String urlTitle = sb.ToString();
return urlTitle;
}
Ta-da。
代わりに、すべての句読記号を削除してください。 – Dai
@Daiいいえ、私はデータベースレコードでそれを翻訳する必要があるので、動かないでしょう。 – jkushner
バックエンドで処理する場合は、選択したエスケープ文字をハイフンの前に置きます。 – freginold