URLの自動リンク

URLの自動リンク

[8] 色々なソフトウェア平文利用者の入力文、 あるいは HTMLメール地の文などから、 URL らしき部分を自動的に検出し、これをリンクとして表示する機能が備わっています。

[9] 中には URL の、あるいは HTTP(S) URL など一部の URL の構文を機械的に正規表現に変換しただけのような雑な実装もありますが、 実用上十分良好な利用者体験を提供するためには、 細かな調整が必要となります。

[12] 実装の中には、 HTML文字参照への変換と URL自動リンクの処理順序が不適切であるなど、 他の処理との兼ね合いで異常な動作をしたり、セキュリティー上の問題をはらんでいたりするものもあります。

実装戦略

境界の処理

[2] 「This is great: https://example.com/great.html. Thanks!」 の最後の「.」は URL の一部ではなく英文の一部と解釈する必要があります。

[3] とすると「See www.example.com.」も www.example.com. を表すのではなさそうです。

[4] 「See https://example.com/great.html, please.」 の「,」は URL の一部ではなく英文の一部と解釈する必要があります。

[5] 「https://example.com/pageU+3000です」は、 U+3000 の前までを URL と解釈する必要があります。

[6] GitHub はこれを正しく扱えません。

[7] 「... (https://test.test/foo)、...」 で GitHub) のあともずっと URL の一部とみなします。

[13] はてなブックマークブックマークコメントでは、 URL の後に「>」 があると、「>」まで URL の一部とみなします。

[14] 掲示板の自動リンクで、 #! のような !URL の一部と見なされず、その直前までが URL とみなされることがあります。

[15] W3Cメーリングリストのアーカイブ: Re: Breaking the `opener` relationship. (Mike West著, ) <https://lists.w3.org/Archives/Public/public-webappsec/2017Apr/0078.html> は、なぜか

`WindowProxy`'s `GetOwnProperty` uses https://html.spec.whatwg.org/#isplatformobjectsameorigin-(-o-): I'd just stick with that as a determinant of the properties listed in https://html.spec.whatwg.org/#crossoriginproperties-(-o-).

`WindowProxy`'s `GetOwnProperty` uses <https://html.spec.whatwg.org/#isplatformobjectsameorigin-(-o>-): I'd just stick with that as a determinant of the properties listed in <https://html.spec.whatwg.org/#crossoriginproperties-(-o>-).

と解釈します。

[19] みのさんのツイート: "https://t.co/927QpBK32e!" () <https://twitter.com/mino90h/status/873210646183026689>

[20] ! で終わる URLTwitter! の直前まで URL と認識。

[21] GitHubhref="https://example.com/">Example Web Page</a> の「https:」から「Example」 までを1つの URL とみなします。

[1] Latest topics > Text LinkとLinkification - outsider reflex (YUKI "Piro" Hiroshi 著, 版) <http://piro.sakura.ne.jp/latest/blosxom/mozilla/extension/2006-03-10_textlink.htm>

「http://www.<em>mozilla</em>.org/」みたいに複数のテキストノードに分割されたURIも認識できる。

某新聞社のサイトのように「http://piro.sakura.ne.jp/」ってな全角文字で書かれたURIも認識できる。

2chでよくある「ttp://」で始まるURIも認識できる。ていうか最初はこれが目的だったんだよね……

非ASCII文字

[27] かつては URL には非ASCII文字は認められていなかったので、 日本語などの非ASCII文字主体の文章では URL とその周りの区切りは比較的明確でした。

[28] ところが URL非ASCII文字一般が認められるようになってから、 URL の直後に文章が続いているものと URL非ASCII文字が含まれるものの区別が難しくなりました。

[31] 素片識別子非ASCII文字を含む語が書かれている場合や、 パス見出し語が入る WikipediaURL の場合のように、 非ASCII文字が含まれる URL が書かれることは少なくないため、 何らかの対応は必須といえます。

リンク回避

[22] 自動リンク機能のある掲示板などの利用者は、 自動リンクを敢えて回避することを好む場合があります。

[23] そのため http:h を省略した ttp: のような URL が用いられることもあります。

ttp: 参照。

[24] しかしそうした自動リンクを回避した URL を敢えて自動リンクリンクをたどる利用者の便を図る実装もあります。

URL scheme の省略

[32] ドメイン名のみを書いたり、 ドメイン名から始まる不完全な URL を書いたりして省略して HTTP(S) URL を表すこともあります。 自動リンクの実装の中には、そうした不完全なものも抽出しようと試みるものがあります。

対応する URL scheme

[10] 任意の URL を自動リンク化すると、 : さえ入っていればほとんどどんな文章でも一部が URL ということになってしまいます。

[35] 一般的な実装は特定の URL scheme のみに対応しています。 HTTP(S) URL のみに対応する最低限のものから、 それ以外の色々な URL に対応するものまであります。

[36] よく対応されている URL scheme

[11] javascript: など、危険な動作を誘引する URL scheme もあります。無邪気な実装はセキュリティーホールとなりかねません。

区切り文字

[25] 古い URLRFC では、自然言語文に URL を混ぜる場合は区切りとして <> で括るのが好ましいという記述がありました。 そのため URL の前後に <> を書くことをよしとする人もいます。 しかしこの慣習は一般には普及しませんでしたし、 Web 技術に詳しい人の中でもそこまで有名ではありません。

[26] <> は通常の URL には含まれないものですから、 自動リンクの実装は特に考慮しなくてもこの区切り文字を意図通りに解釈すると期待されます。 しかし文字参照の扱いが杜撰な自動リンクの実装に誤解釈されることもあるようです (例えば >>13)。

[18] RFC 7322 - rfc Style Guide () <https://tools.ietf.org/html/rfc7322#section-3.3>

Angle brackets are strongly recommended around URIs [STD66], e.g., <http://example.com/>

自動リンク機能付きマーク付け言語

[33] Wiki構文などテキスト系のマーク付け言語は、 自動リンク機能を言語の一部として組み込んでいることがよくあります。

[34] はてな記法

[17] GitHub Flavored Markdown Spec () <https://github.github.com/gfm/#autolinks-extension->

文脈

[37] 次のような分野で使われています。

[38] 自動リンクする場面

関連

[39] その他にメールアドレス電話番号 (x-ms-format-detection も参照)、 アプリケーション依存の識別子などの自動抽出・リンク化が実装されていることがあります。

[40] smart tag も参照。

メモ

[16] OPMLファイルやHTML、テキストファイルからの一括登録機能の追加 - はてなアンテナ日記 - 機能変更、お知らせなど () <https://hatena.g.hatena.ne.jp/hatenaantenna/20060905/1157428635>

はてなアンテナで、複数のページを一括で登録する機能を追加しました。OPMLファイルやHTML、またテキストファイルに対応しています。(テキストファイルからはURLと判別できる文字列を抽出します。)