SPFをワイルドカード(*)で設定するのは悪なのか?!

SPFをワイルドカード(*)で設定するのは悪手なのでしょうか? 便利ないいやり方なのでしょうか。
僕自身、ついさっきまでワイルドカード擁護派だったのですが、よく考えると間違いがあることに気づいたのでまとめておきます。

## はじめに

某所でこんな質問が出てきました。

DMARCレコードを引くとSPFのレコードが返ってくるところがあるんだけど、おかしくね?
```
# dig +short _dmarc.example.com TXT
"v=spf1 ip4:xxx.xxx.xxx.xxx/24 -all"
```

DMARCレコードに間違えてSPFの設定を書くことは考えにくいので、おそらくワイルドカードを使用して

```
*.example.jp.   3600   IN    TXT   "v=spf1 ip4:xxx.xxx.xxx.xxx/24 -all"
```

のように設定されているのでしょう。

さて、これはいいやり方なのでしょうか、悪手なのでしょうか。

## なぜSPFをワイルドカードにしたのか

実際にどのような意図があって設定したのかはこのドメインの設定した人に聞くしかないのですが、そういうわけにもいかないのでここは想像ですが、まず考えられるのは

- **新しいメールホストを追加したときにSPFをわざわざ追加したくない**
- **新しいメールホストを追加したときにSPFを追加し忘れても問題がない**

というあたりでしょうか。

これ、本当に意図したとおりになるのであれば、ホストを管理できてないのが悪だというのはありますが、ま、そんなに悪くはない設定です。

では、そうなのでしょうか。

## DNSのワイルドカードの動き

ここで一旦基本に立ち返って、DNSのワイルドカードの動きについて見てみましょう。

次のようなワイルドなレコードを設定したとします。

```
*.example.com.   3600   IN    A   192.0.2.1
```

いくつかのホスト名でクエリしてみましょう。

```
# dig +short aaa.example.com A
192.0.2.1

# dig +short ohohoho.example.com A
192.0.2.1

# dig +short aaa.bbb.example.com A
192.0.2.1
```

おーー。いい感じです。

では、`aaa.example.com`の`A`レコードを追加したらどうなるでしょうか。

```
*.example.com.   3600   IN    A   192.0.2.1
aaa.example.com. 3600   IN    A   192.0.2.2
```

こんな感じです。これをクエリしてみると、

```
# dig +short aaa.example.com A
192.0.2.2

# dig +short ohohoho.example.com A
192.0.2.1
```

意図したとおり、追加したものが優先になりました。

では、こんな場合はどうでしょうか。

```
*.example.com.   3600   IN    A      192.0.2.1
aaa.example.com. 3600   IN    AAAA   2001:db8::1
```

`aaa.example.com`に`AAAA`レコードを追加してみました。

```
# dig +short aaa.example.com A

# dig +short aaa.example.com AAAA
2001:db8::1
```

あれ?!
ワイルドカードな`A`レコードが出なくなってしまいました。

ワイルドカードで設定した値は、クエリしたホスト名がzoneの中に存在しない場合のみ適用されるのです。
つまり、この場合、`aaa.example.com`の`AAAA`レコードが存在するので、`A`レコードをクエリした場合でも`*.example.com`の`A`レコードは使用されません。

## SPFのワイルドカードの場合は?

では、ワイルドカードなSPFレコードはどのように機能するか考えてみます。

```
*.example.jp.   3600   IN    TXT   "v=spf1 ip4:192.0.2.0/24 -all"
```

というようなSPFを設定したとしましょう。
これに、新しいメール送信サーバー`sender.example.com`を追加したとします。
簡単のためにメールのドメインも`sender.example.com`とします。

メールの受信はしないので、Null MXを設定しておきます。
メールを受信してもらうには暗黙のルールでAレコードが必要な場合もあるのでこれも追加しておきましょう。

```
*.example.jp.        3600   IN    TXT   "v=spf1 ip4:192.0.2.0/24 -all"
sender.example.com.  3600   IN    MX    0 .
sender.example.com.  3600   IN    A     192.0.2.3
```

さて、この状態で、`sender.example.com`のSPFはどうなるでしょうか。

```
# dig +short sender.example.com TXT

```

あらら。ワイルドカードは参照されていません。
そうです。MXやAレコードが存在するからですね。

ということで、ワイルドカードでSPFを記述しても

- **新しいメールホストを追加したときにSPFをわざわざ追加したくない**
- **新しいメールホストを追加したときにSPFを追加し忘れても問題がない**

の要件は満たせません。

新しいホストを追加するたびに、SPFもちゃんと書く必要があります。

これでは、混乱するだけですね。

ということで、SPFをワイルドカード(*)で設定することは (少なくともこの要件では)
悪なのです。

## Parked DomainでのSPFのワイルドカード

ただし、推奨される例がひとつあります。

Parked DomainでのSPFやDKIMの設定です。

Parked Domain(パークドメイン)とは念のために確保したり、キャンペーンなどが終わって、現在は使用されていないドメインのことをいいます。

M3AAWGのParked Domainに関するベストプラクティスによると、

```
example.com. TXT "v=spf1 -all"
example.com. MX 0 .
*.example.com. TXT “v=spf1 -all”
*.example.com MX 0 .
_dmarc.example.com. TXT "v=DMARC1; p=reject; rua=mailto:rua@example.net”
example.com._report._dmarc.example.net TXT “v=DMARC1”
```

のようにSPFをワイルドカードで書いて、サブドメインからもメールを送信しないことを明示的に示すことが推奨されています。

詳しくは、こちら

https://www.m3aawg.org/sites/default/files/m3aawg_parked_domains_bcp-2022-06.pdf

を参照してみてください。

## 結論

SPFをワイルドカードで書くのは、Parked Domain用に`-all`を設定するとき以外は悪ですよ。

ほかに、もっといい感じなワイルドカードにする理由があればぜひ教えてください。検証してみます。