Rails
Osushi

Osushiで見つかったユーザーid問題を対策する

Osushiというサービスがリリースされました。

投げ銭がお寿司でできるというサービスです。「お寿司」ということもあり(?)、リリース直後からエンジニア界隈で少し話題になっていましたが、どうやら法律上の問題や実装上のバグが多くあるようでエンジニア界隈を騒がせていました。

エンジニアとして気が引き締まる思いがありつつも、実装上のバグに関しては対策ができそうだと思ったので簡単にまとめてみます。

どうやらユーザーid関連のバグの発見が発端なようです。

他にも問題があったようですが、今回はその発端となったユーザーid関連のみ取り上げます。

問題:ユーザーidが他の人と同じにできてしまう

OsushiはTwitterログインを利用してログインするサービスで、TwitterでのユーザーidがOsushiでのユーザーidになります。

そして、サービスリリース時、ユーザーページでそのユーザーidを変更できる仕様になっていました。(Twitterログインなら変更できなくても...)

※ すでにユーザーidは変更できない仕様に変わっています。

変更できない仕様になる前は、ユーザーidを他の人のユーザーidに変更できたりしてしまいました。

対策:DBにユニーク制約をつける

DBの対象カラムにユニーク制約をつけるようにします。ユニーク制約をつけることによって同じデータを登録できないようにできます。

対策:バリデーションをかける

モデルのバリデーションでもユニークかどうかチェックした方がいいです。

問題:ユーザーidが他のルーティングと被ってしまう

ユーザーidを他のルーティング(settingsやlogin)に変えてしまうことができました。

そういったユーザーid(仮にパラメーターのキーは:usernameとします)に変更できてしまうことで、ユーザーページにアクセスできなくなってしまうことがありました。

対策:他のルーティングをあらかじめバリデーションではじく

裏側で他のルーティングを取得するライブラリを用意するか、自分で一覧を定義するかして、予約されているルーティングをバリデーションではじくようにします。

対策:/:usernameではなく/users/:usernameにする

/:usernameにすることで考慮しなければいけないことがふえているので/users/:usernameとすることで対策することもできます。

/users/settingsなどのパスがある場合があったら別ですが、、、笑

対策:/:usernameではなく/@:usernameにする

上と似ていますがこっちのほうがより他のパスとかぶる心配がなくいいかなと思います。

少しURLがかっこ悪くなってしまうのでそれでもよければという感じです。

対策:/:usernameではなく/users/:idにする

最終手段です。

対策:おまけ

ちなみに以前、Railsですが、この手の記事を書いたことがあるので参考にしてみてください。
/:usernameなroutingにするときに考えるべきこと

問題:特殊記号もユーザーidに登録できてしまう

対策:特殊記号をバリデーションではじく

これもバリデーションではじくことが必要です。

最後に

細かい部分まで最低限のバリデーションをかけることで対策できることがほとんどなので、きちんとかけましょう。