Серверный редирект на мобильную версию сайта

    image
    Предлагаю вашему вниманию простое и дешевое (по ресурсам) решение для перенаправления пользователей мобильных устройств на легкую версию сайта. Решение ориентировано на highload сайты, оптимизация которых основана на кешировании гостевых запросов.
    Проверка, является ли клиент мобильным устройством, производится веб-сервером nginx и в случае успеха клиент перенаправляется на поддомен или локейшн. Это существенно экономит ресурсы и позволяет добиться большей масштабируемости по сравнение с PHP методами.

    Конфигурация для NGINX

    Вариант №1. Мобильная версия расположена на поддомене
    server{
    < … >
    if ( $http_user_agent ~* (windows\smobile|windows\sce|iphone|ipod|midp|symbian|series\s60|s60|nokia|аndroid| blackberry) ){
    rewrite ^/(.*) m.site.ru$1 permanent;
    }

    location / {
    < … >
    }

    }


    Вариант №2. Мобильная версия открывалась на том же домене
    if ( $http_user_agent ~* (windows\smobile|windows\sce|iphone|ipod|midp|symbian|series\s60|s60|nokia|аndroid| blackberry) ){
    rewrite ^/(.*)$ /liteversion/$1 last;
    }


    Определение мобильного устройства по $http_user_agent позволяет с высокой точностью и с минимальными затратами ресурсов отличать мобильных клиентов от обычных ПК.
    Так работают Google и Yandex. Вы можете поменять user_agent своего браузера и убедится в этом.

    Конечно, я не знаю, как в точности работает алгоритм определения «мобильника» в G и Y. Но я считаю, что он очень похож на элементарное регулярное выражение написанное выше.

    Регулярное выражение содержит список вариаций ключевых слов в строке http_user_agent составленный на основе анализа логов нескольких сайтов. Всего проанализировано около 200 000 запросов за сутки, 5% из которых отправлено с мобильных устройств. Это гарантирует высокую вероятность выхождения в списков всех возможных вариантов user_agent мобильных устройств. Ipad я исключил из-за разрешения экрана в 1024х768px.

    Надеюсь, моя заметка будет для вас полезной.

    Дополнительно

    Переключатель User Agent для Моззилы
    Расширенный список юзер агентов
    Ads
    AdBlock has stolen the banner, but banners are not teeth — they will be back

    More

    Comments 35

      +1
      неплохая шпаргалка, спасибо.
        +5
        Думаю, у Google этим занимается нейронная сеть, натренированная генетикой, в тандеме с SVM-кой)
          +5
          Да нет, ну что вы. Там сидят 100500 очень шустрых индусов-аналитиков, которые принимают решение для каждого хттп-запроса, с какого устройства он пришел.
          +2
          Ещё неплохо бы по наличию хттп-заголовка x-wap-profile, а так же наличию в accept application/vnd.wap.xhtml+xml — это телефоны, поддерживающие wap 2.0 и text/vnd.wap.wml — wap 1.x
            +3
            Скажите, пожалуйста, как при таком варианте сделать возможность пользователю принудительно переключиться на полную версию сайта? Ведь если указать ссылку на полную версию вида www.site.ru, то опять сработает регулярка в nginx. Видимо, нужно делать проверку на куки?
              0
              Ключ site.com/?v=full подойдет? Обходите его регуляркой.
                0
                Это сработает для одной страницы. А если человек пойдет по ссылке дальше, скажем, www.site.ru/catalog/, то ведь опять регулярка сработает? Если же ключ ко всем страницам дописывать, то это уже переделка движка получается.
                  +4
                  можно ставить куку и проверять ее
                +1
                Думаю, можно и без куки:

                1) автоматический редирект только для / (корня)
                2) на каждой странице мобильного сайта (или только на первой) снизу ссылка «Полная версия» на /full
                3) /full на основном сайте — это копия / (корня), в robots.txt прописывается, чтобы не индексировалась
                4) на каждой странице основного сайта (или только на первой) ссылка на «Мобильная версия» (на / мобильного сайта, если для этой страницы нет соответствия на мобильном сайте)
                5) на мобильном сайте автоматического редиректа на основной нет
                0
                А поисковики это за клоакинг не сочтут?
                  0
                  А его тут и нет. Максимум — дублирование контента.
                    0
                    Ну, не скажите. В мобильной же версии наверняка придётся отцеплять всякие картинки из контента, а, по хорошему, переписывать сам контент и менять структуру с учётом того, что юзер не станет читать длинные портянки с мобильного (особенно, если это юзер не смартфона, а обычного телефона с JavaME).

                    В случае поддомена, думаю, проблем не возникнет, а вот если контент по основному домену будет меняться в зависимости от юзер-агента.

                    Но вопрос я свой задал, наверное, слишком провокационно. На самом деле, хочется услышать о чьём-то реальном опыте: не было ли санкций, нормально ли индексируется мобильная версия, сильно ли повысило её наличие долю трафика с мобильных устройств?
                      +3
                      Мобильная версия на поддомене индексируется настолько хорошо, что стала ранжироваться выше основного сайта. Пришлось через роботс исключать из индексации.
                        +2
                        Вполне естественное явление.

                        Как подметил kostin, мобильная версия является облегченной. В глазах робота — меньше вторичного контента(для примера смотрите сайдбар хабра справа).
                        Чем меньше вторичного контента — тем выше будет текстовая релевантность.

                        Санкции за мобильную версию не наложат, если по одному адресу всегда отдается один документ.
                        Если же URL будет один, а контент будет зависить от User-Agent — другое дело.

                        Единственное, что меня смущает в предложенном здесь примере — постоянный редирект. На мой взгляд, временный будет более логичен.
                        Робот же не будет намеренно подставлять User-Agent мобильных устройств. На это у крупных ПС есть отдельные роботы, занимающиеся мобильным контентом.
                        0
                        Дублированный контент чаще всего определяют по шинглам. Вы же не будете для мобильных пользователей писать отдельные статьи :)
                        Вынос мобильной версии на поддомен гарантированно защитит от неприятностей.
                    +2
                    Менять http_user_agent

                    Если серьезно, то есть такое предположение: поскольку перенаправление должно сработать только при первом обращении, можно проверять откуда идет пользователь, если извне (с чужого сайта или из пустоты) — перенаправлять, иначе ничего не трогать.
                      +1
                      Упс, отвечал на это
                        0
                        Да, я тоже об этом подумал. Но пока не понял, как это сделать в конфиге nginx.
                          0
                          К сожалению не знаю тонкостей работы с куками.но примерно вот так.
                            +1
                            Думаю, по рефереру надёжнее, поскольку куки в мобильных браузерах бывают чаще, наверное, выключены, чем в настольных (например, помню, что-то нативное на Нокии N8 постоянно мне предлагало почистить куки, когда я пользовался соответствующим девайсом).
                              0
                              что будете делать, когда реферер пустой? На львиной доле мобильных устройств его вообще нет.
                                +1
                                Отправлять на мобильную версию, если пустой. Так и надо же.

                                А вот о том, что многие мобильные девайсы его не поддерживают — не знал. Не получится их тогда пустить на основую версию сайта.

                                Но тут надо смотреть из кого именно составлена львиная доля: если в неё не входят Андройды, Айфоныи и Опера Мини, то и прекрасно, нечего всякие wap-браузеры на основную версию сайта пускать, они её всё равно нормально не отобразят.
                            +1
                            Ага, было бы хорошо, если б кто-то подсказал, как построить примерно такое правило: если реферер m.site.ru, то пускать на основную версию (на site.ru) даже если юзер-агент мобильный.
                              0
                              Вы читаете мои мысли. ))
                                0
                                Есть модуль ngx_http_referer_module.
                                Если закрыть глаза на прямое назначение $invalid_referer, можно через нее делать.
                                Только надо учитывать не только m.site.ru, но и сам site.ru.
                            +1
                            Спасибо, то что нужно
                              0
                              Можно ставить куку, как только определили user agent. Если кука говорит, что пользователь хочет основной сайт, то редирект не делать.
                                0
                                Определять надо не только и не столько по user_agent, сколько по дополнительным заголовкам. user-agent может меняться из браузера, например.

                                Мы писали для себя что-такое.

                                Транслировать его в nginx конфиг — дело техники )
                                  0
                                    +4
                                    Яндекс.Детектор — это лишний запрос на другой сервер.
                                      +2
                                      стоит ли говорить, что nginx сделает быстрее и ловчее? :)
                                      +10
                                      Вот RegExp'ы для HTTP_USER_AGENT с detectmobilebrowser.com, которыми я пользуюсь.

                                      android|avantgo|blackberry|blazer|compal|elaine|fennec|hiptop|iemobile|ip(hone|od)|iris|kindle|lge\ |maemo|midp|mmp|opera\ m(ob|in)i|palm(\ os)?|phone|p(ixi|re)\/|plucker|pocket|psp|symbian|treo|up\.(browser|link)|vodafone|wap|windows\ (ce|phone)|xda|xiino


                                      OR

                                      ^(1207|6310|6590|3gso|4thp|50[1-6]i|770s|802s|a\ wa|abac|ac(er|oo|s\-)|ai(ko|rn)|al(av|ca|co)|amoi|an(ex|ny|yw)|aptu|ar(ch|go)|as(te|us)|attw|au(di|\-m|r\ |s\ )|avan|be(ck|ll|nq)|bi(lb|rd)|bl(ac|az)|br(e|v)w|bumb|bw\-(n|u)|c55\/|capi|ccwa|cdm\-|cell|chtm|cldc|cmd\-|co(mp|nd)|craw|da(it|ll|ng)|dbte|dc\-s|devi|dica|dmob|do(c|p)o|ds(12|\-d)|el(49|ai)|em(l2|ul)|er(ic|k0)|esl8|ez([4-7]0|os|wa|ze)|fetc|fly(\-|_)|g1\ u|g560|gene|gf\-5|g\-mo|go(\.w|od)|gr(ad|un)|haie|hcit|hd\-(m|p|t)|hei\-|hi(pt|ta)|hp(\ i|ip)|hs\-c|ht(c(\-|\ |_|a|g|p|s|t)|tp)|hu(aw|tc)|i\-(20|go|ma)|i230|iac(\ |\-|\/)|ibro|idea|ig01|ikom|im1k|inno|ipaq|iris|ja(t|v)a|jbro|jemu|jigs|kddi|keji|kgt(\ |\/)|klon|kpt\ |kwc\-|kyo(c|k)|le(no|xi)|lg(\ g|\/(k|l|u)|50|54|e\-|e\/|\-[a-w])|libw|lynx|m1\-w|m3ga|m50\/|ma(te|ui|xo)|mc(01|21|ca)|m\-cr|me(di|rc|ri)|mi(o8|oa|ts)|mmef|mo(01|02|bi|de|do|t(\-|\ |o|v)|zz)|mt(50|p1|v\ )|mwbp|mywa|n10[0-2]|n20[2-3]|n30(0|2)|n50(0|2|5)|n7(0(0|1)|10)|ne((c|m)\-|on|tf|wf|wg|wt)|nok(6|i)|nzph|o2im|op(ti|wv)|oran|owg1|p800|pan(a|d|t)|pdxg|pg(13|\-([1-8]|c))|phil|pire|pl(ay|uc)|pn\-2|po(ck|rt|se)|prox|psio|pt\-g|qa\-a|qc(07|12|21|32|60|\-[2-7]|i\-)|qtek|r380|r600|raks|rim9|ro(ve|zo)|s55\/|sa(ge|ma|mm|ms|ny|va)|sc(01|h\-|oo|p\-)|sdk\/|se(c(\-|0|1)|47|mc|nd|ri)|sgh\-|shar|sie(\-|m)|sk\-0|sl(45|id)|sm(al|ar|b3|it|t5)|so(ft|ny)|sp(01|h\-|v\-|v\ )|sy(01|mb)|t2(18|50)|t6(00|10|18)|ta(gt|lk)|tcl\-|tdg\-|tel(i|m)|tim\-|t\-mo|to(pl|sh)|ts(70|m\-|m3|m5)|tx\-9|up(\.b|g1|si)|utst|v400|v750|veri|vi(rg|te)|vk(40|5[0-3]|\-v)|vm40|voda|vulc|vx(52|53|60|61|70|80|81|83|85|98)|w3c(\-|\ )|webc|whit|wi(g\ |nc|nw)|wmlb|wonu|x700|xda(\-|2|g)|yas\-|your|zeto|zte\-)
                                        +3
                                        Вторая, ну просто пацанская регулярка!
                                          +1
                                          Точно не проще запрос на другой сервер?
                                            0
                                            Не проще. К тому же намного накладнее, и в том числе дольше.
                                            В любом случае, я предложил только наиболее полные из мне известных регулярок для парсинга HTTP_USER_AGENT, а как использовать его, дело ваше.
                                            Можно в nginx, как описано в этой статье (очень шустрый метод). Лично я использую в одном проекте в .htaccess mod_rewrite apache'а (это аналогично, только для другого веб-сервера) и в одном проекте, исходя из специфики, в PHP-коде (что уже немного накладнее, но все равно быстрее запросов куда-либо).

                                        Only users with full accounts can post comments. Log in, please.