なぜ今さら `:link` と `:visited` なのか?—— CSSの「古き良き」仕様に潜む罠と真実
フロントエンドの世界に足を踏み入れて数年、「CSSなんてセレクタを書いてプロパティを当てるだけだろ?」と高を括っている中堅エンジニアほど、実はこの `:link` と `:visited` の深淵に足を取られます。
正直に言おう。現代のモダンな開発現場において、これらを意識して使い分けているエンジニアは驚くほど少ない。しかし、ブラウザの挙動を深く理解し、堅牢なUIを構築したいのであれば、この古典的な擬似クラスこそ避けて通れない「基礎の地層」なのです。
今回は、ブラウザが裏側で何を考えているのか、そして「なぜプライバシー保護の観点から制限が厳しいのか」という現場のリアルを紐解いていきましょう。
—
ブラウザの裏側で起きていること:なぜ `:visited` は「色」しか変えられないのか?
まず、大前提として知っておくべき仕様があります。CSSの仕様書には「`:visited` 擬似クラスで変更できるプロパティは、色に関するものに限定される」という非常に厳しい制約が記されています。
具体的には `color`, `background-color`, `border-color`, `outline-color` 程度です。`font-size` や `display`、あるいは `transform` を変えようとしても、ブラウザは鼻で笑って無視します。
「なぜそんな制限があるんだ?」
これは、悪意のあるWebサイトが「ユーザーの履歴を盗み見ること」を防ぐためです。もし `:visited` で要素の大きさを変えたり、`background-image` で外部リソースを読み込める仕様だったら、サイト側は「このユーザーは銀行のログインページにアクセスしたことがあるか?」を、CSSの読み込み判定だけで特定できてしまいます。
ブラウザ開発者たちは、セキュリティと表現の自由の境界線で、長年この「プライバシーの要塞」を守り続けているわけです。
—
実践:メンテナンス性を損なわない記述術
現場でよくあるミスは、`:link` と `:visited` を別々の場所でバラバラに定義してしまい、後からスタイルを追うのが困難になるパターンです。これらを論理的にグループ化し、かつ保守性を高める書き方を推奨します。
/
- リンクの状態管理(LVHAの順序を守るのが鉄則)
- Link -> Visited -> Hover -> Active
/
.nav-link {
/ ベースのスタイル:ここを一番いじりやすくしておく /
color: #007bff;
text-decoration: none;
transition: color 0.2s ease;
}
/ 未訪問リンクの明示的定義 /
.nav-link:link {
color: #007bff;
}
/ 訪問済みリンクの定義:セキュリティ制限のため色のみ /
.nav-link:visited {
color: #6610f2; / 紫系にして「既読」であることが分かるように /
}
/ ホバー時の挙動:ここは自由度が高い /
.nav-link:hover {
color: #0056b3;
text-decoration: underline;
}
ここがプロのこだわりポイント
1. LVHAの順序: `:link` と `:visited` は必ず `:hover` や `:active` より前に書くこと。これはCSSの「詳細度(Specificity)」の問題ではなく、カスケードの仕様です。後から書いたものが勝つという単純なルールを忘れると、ホバーしても色が変わらないという「デバッグ地獄」に陥ります。
2. デフォルトの継承: `:link` は `href` 属性を持つ `` タグにのみマッチします。`` タグでも `href` がない場合はマッチしない。この「仕様の厳密さ」を逆手に取ると、装飾用のダミーリンクと機能するリンクをCSSだけでクリーンに管理できます。
—
チームへの提言:デザインシステムにおける扱い
最近のコンポーネント指向開発(React/Vue/Next.jsなど)では、`` タグを直接使う機会は減り、ラッパーコンポーネントを通すことが多いはずです。
その際、`:visited` を無理に全ページで実装する必要はありません。むしろ「ユーザーの閲覧履歴という情報をWebサイト側が過剰に保持しない(あるいは表現しない)」というUXデザインの判断もアリです。しかし、ブログ記事や文書アーカイブのような「読み物系サイト」では、`:visited` の有無がUXを劇的に向上させます。
「どこまで読んだか分からない」というユーザーのストレスを、CSSの数行で解消する。
これこそが、フロントエンド・エンジニアの矜持というものです。
まとめ
- `:visited` はセキュリティ上の制限で「色」しか変えられない。
- `:link` と `:visited` は、常に他の擬似クラスより前に書く(LVHAの原則)。
- 「CSSは簡単」と油断せず、ブラウザのセキュリティ仕様まで読み解くことで、一段上のエンジニアへと成長できる。
次回のコードレビューで、「あ、この `visited` はあえて制限を意識して色だけに留めてるんだな」と周りに一目置かれるような、そんな深い実装を期待しています。何か詰まったら、またいつでも相談してください。現場からは以上です。

コメント