その他
    ホーム 技術発信 DoRuby [rails] Jpmobileを使用する際の注意点 Edit

    [rails] Jpmobileを使用する際の注意点 Edit

    この記事はアピリッツの技術ブログ「DoRuby」から移行した記事です。情報が古い可能性がありますのでご注意ください。

    スマフォでPC表示させているときの条件に注意。

    Jpmobileの概要

    RailsでPCサイトと共にスマフォサイトを作成する場合に便利なGemとして、JpmobileというGemがあります。

    このGemを使うことで、アクセス端末に応じてviewを切り替えることができます。

    すなわち、Jpmobileを使用することで、PCからアクセスされた場合にはPC用のviewを表示させ、スマフォからアクセスされた場合にはスマフォ用のviewを表示させることを、Webサイトの開発者が意識することなく実装できます。

    また、スマフォからのアクセスかどうかを「request.smart_phone?」のように判定することができるようになります。

    ここで、スマフォでアクセスした場合であっても、PC用のviewを表示したいユーザーがいることを考慮して、「PCサイトを表示する」のようなリンクを用意することがあると思います。

    この場合には、「disable_mobile_view!」メソッドをコールすることで、PCサイトを表示させることができます。

    ※恐らく、このようなリンクがクリックされたことを、cookieやsessionに保存し、ページ遷移した後であっても、PCサイトを表示するように実装されるかと思います。

    問題点

    スマフォからのアクセスに対してPCサイトを表示させている状態であっても、request.smart_phone?の結果は「true」になります。

    すなわち、viewが絡む部分(*1)に関して「request.smart_phone?」で条件判定をすると、意図しない動作になる可能性があります。

    (*1) controllerでインスタンス変数に値を設定する場合等も含む。

    例えば、

    • PCの場合 → 12個のレコードをインスタンス変数に設定
    • スマフォの場合 → 8個のレコードをインスタンス変数に設定

    とすべき場合、本来であれば、

    • PCアクセス(PC用の表示) → 12個のレコードがインスタンス変数に設定される
    • SPアクセスでスマフォ用のを表示 → 8個のレコードがインスタンス変数に設定される
    • SPアクセスでPC用の表示 → 12個のレコードがインスタンス変数に設定される

    となって欲しいところです。

    しかしながら、controllerで、

    def index
      count = request.smart_phone? ? 8 : 12
      @records = TestTable.where(...).limit(count)
    end
    

    のように、「request.smart_phone?」を使用してしまうと以下のようになってしまいます。

    • PCアクセス(PC用の表示) → 12個のレコードがインスタンス変数に設定される
    • SPアクセスでスマフォ用のを表示 → 8個のレコードがインスタンス変数に設定される
    • SPアクセスでPC用の表示 → 8個のレコードがインスタンス変数に設定される(←12個になっていない!!)

    ■ 対策

    このため、viewに絡む部分に関しては、

    • 判定1:アクセス端末によって切り替えるのか?
    • 判定2:PC用のviewとスマフォ用のviewのどちらを表示しているかによって切り替えるのか?

    を常に意識しないと思わぬバグに繋ります。

    先程の例では、判定2でやらなければいけません(判定方法は、どちらのviewを表示しているかの情報が保存されたcookieやsessionを参照して判定することになると思われます)。

    なお、判定1が必要になる例としては「SPアクセスでPC用の表示をしているときに、スマフォ用のviewに戻すためのリンクを表示する場合(PCでアクセスして来た人に対してスマフォ用のviewを表示することは通常ない。スマフォのときにのみ有効。但し、この例の場合には、PC用のviewを表示している場合にのみ表示させる必要有り)」が挙げられます。