Вопрос по ruby-on-rails, safari, apache – Почему некоторые запросы страниц зависают при извлечении ресурсов Javascript / изображений с использованием Safari и Apache 2.2.3?

5

Некоторые пользователи нашего приложения Ruby on Rails жаловались на то, что запросы страниц иногда зависают на неопределенное время в Safari (пара заметила это в Firefox, но это в подавляющем большинстве случаев пользователи Safari). После некоторого исследования кажется, что эти запросы правильно обрабатываются нашим приложением Rails, и зависание происходит при получении ресурсов изображения (которые размещены на том же сервере), на которые есть ссылки в HTML.

Мы настроили Apache для непосредственного обслуживания графических ресурсов и обхода приложения Rails для повышения производительности. Мы также включили сжатие gzip для ресурсов text / javascript / css. Ниже приведены соответствующие настройки из нашей конфигурации виртуального хоста Apache - возможно, мы настроили это таким образом, чтобы объяснить эти произвольные запросы зависания?

RewriteEngine On

# Correct behaviour of IE under SSL
SetEnvIf User-Agent ".*MSIE.*" \
    nokeepalive ssl-unclean-shutdown \
    downgrade-1.0 force-response-1.0

SSLEngine On
SSLCertificateFile /etc/httpd/conf/ssl/_.mycert.com.crt
SSLCertificateKeyFile /etc/httpd/conf/ssl/_. mycert.com.key
SSLCertificateChainFile /etc/httpd/conf/ssl/gd_bundle.crt

RequestHeader set X_ORIGINAL_PROTOCOL 'https'
RequestHeader set X_FORWARDED_PROTO 'https'

# Rewrite index to check for static
RewriteRule ^/$ /index.html [QSA] 
RewriteRule "^/(images|stylesheets|javascripts|system)/?(.*)" "$0" [L]

# Rewrite to check for Rails cached page
RewriteRule ^([^.]+)$ $1.html [QSA]

# Deflate
AddOutputFilterByType DEFLATE text/html text/plain text/xml text/css text/javascript application/x-javascript
BrowserMatch ^Mozilla/4 gzip-only-text/html
BrowserMatch ^Mozilla/4\.0[678] no-gzip
BrowserMatch \bMSIE !no-gzip !gzip-only-text/html

ExpiresActive On
<FilesMatch "\.(ico|gif|jpe?g|png|js|css)$">
  ExpiresDefault "access plus 1 year"
  Header append Cache-Control "public"
</FilesMatch>

Кто-нибудь сталкивался с подобной проблемой раньше?

Наше веб-приложение Ruby on Rails работает с использованием mod_rails и Apache 2.2.3 в RedHat Enterprise Linux 5.

Update: Теперь я попытался удалить следующий блок, и проблема все еще сохраняется, так что похоже, что мы можем исключить заголовок expires из проблемы:

ExpiresActive On
<FilesMatch "\.(ico|gif|jpe?g|png|js|css)$">
  ExpiresDefault "access plus 1 year"
  Header append Cache-Control "public"
</FilesMatch>

Ваш Ответ

5   ответов
3

отлаживая подобную проблему на нашем сайте сегодня. Пользователи Safari - но, похоже, только пользователи Mac - будут жаловаться на то, что наш сайт "зависнет". случайно при загрузке страницы. Обычно это зависало на изображении - выполнено 2 из 3 элементов и т. Д., Но затем я отключил кэш в Safari, JavaScript и CSS, и угадайте, что? Страница все еще висела.

Во-первых, заметка о кэшировании в Safari. Даже если у вас есть «Отключить кэширование» выбрано в разделе "Разработка" меню и выбрали «Очистить кэш» от "Safari" меню, у вас все еще есть кэш на основе ОЗУ. Это означает, что если вы ДЕЙСТВИТЕЛЬНО хотите смоделировать пустой кеш, вы должны выходить из Safari с каждым запросом или удерживать нажатой кнопку «Перезагрузить», нажимая клавиши «Option» + «Shift» + «Молитва к божеству выбора». Мне потребовалось некоторое время, чтобы понять, и пока я не понял это, мне было трудно постоянно воспроизводить проблему.

Так! Что у вас осталось без JavaScript, CSS или изображений? Не так много, кроме реального HTML. Это то, что заставило меня задуматься о том, что, вероятно, связано со сжатием. И, конечно же, отключение сжатия в IIS 6.0 привело к мгновенной загрузке страницы. Поскольку в IIS 6.0 нет удобного способа отключения сжатия на основе пользовательского агента, я использовалIIRF (фильтр ISAPI, который переписывает URL), чтобы переписатьAccept-Encoding Заголовок, когда он прибывает из Safari:

# Safari doesn't handle gzip compression properly; we turn it off by setting 
# the q value to zero for all agents identifying themselves as Safari
RewriteCond %{HTTP_USER_AGENT} Safari
RewriteHeader Accept-Encoding: .* *;q=0

Кажется, проблема в том, что если Safari получает статический сжатый контент (то есть сервер отправляетContent-Length заголовок), то Safari прекрасно с этим справляется. Но если Safari получает динамическое сжатое содержимое (то есть сервер обслуживает ответ, отображаемый ASP.NET, и длина содержимого неизвестна до тех пор, пока это не будет сделано, поэтому сервер отправляетTransfer-Encoding: chunked) затем Safari переходит в режим Flaky Sir-Hangs-A-Lot.

Зачем? Я понятия не имею. Но так я работаю.

1

что это старая тема, но я хотел поделиться решением для Safari, которое может сэкономить другим время. Следующая строка действительно решила все проблемы:

BrowserMatch "^(?=.*Safari)(?=.*Macintosh)(?!.*Chrom).*" nokeepalive gzip-only-text/html

Регулярное выражение гарантирует, что на Mac обнаружен только Safari, а не Mobile Safari, Chrome (ium) и тому подобное. Safari для Windows также не подходит, но проблема keepalive, похоже, заключается только в комбинации Mac-Safari. Кроме того, некоторые версии Safari плохо справляются с gzipped css / js.

Все наши симптомы сбоя нашего сайта или неполной загрузки CSS в разных версиях Safari, из-за которых я чуть не вырвался (Safari - это новый IE), были решены для нас с помощью этого хака конфигурации Apache.

1

ndows.

Проблема исчезнет, если согласование keepalive отключено для браузера Safari (httpd.conf):

BrowserMatch "Safari" nokeepalive

Я не уверен, в чем реальная проблема, или если предыдущие решения являются лучшими, но эта конфигурация устраняет проблему.

2

Это может или не может быть связано, но браузеры имеют ограничение в 2 (по умолчанию) одновременных подключений, которые они могут установить. Если существуют соединения, которые остаются открытыми для общения, и вы также получаете изображения, вызов к изображению может не состояться, пока браузер не освободит одно из предусмотренных соединений. Зависание во время выборки изображения может фактически быть вызвано некоторыми другими соединениями с сервером, которые не завершаются или остаются открытыми сервером и браузером. Так что вы можете охотиться не в том месте.

Если вы можете воспроизвести ошибку, попробуйте переключиться на HTTP 1.0 на вашем dev-сервере и посмотреть, исправит ли она проблему. Также попробуйте переместить некоторые ресурсы в другой домен / поддомен и получить их оттуда.

Надеюсь, что это дает вам другой угол.

С Уважением, Нараян

Из всех существующих браузеров только IE6 и IE7 имеют такой низкий предел. Увидетьstackoverflow.com/questions/985431/… для чисел (без цитирования, к сожалению). Ваша точка зрения остается, конечно, но предел выше, чем 2.
Всем привет. Мы используем виртуальные серверы ресурсов для обслуживания изображений, JavaScript и CSS, поэтому я не уверен, что это ответ. В нашем случае у нас есть 12 JS и CSS-включений (и многих других изображений), которые обслуживаются с assets0.mydomain.com, assets1.mydomain.com, assets2.mydomain.com, assets3.mydomain.com - это делает Rails для меня. Olly
Это моя непосредственная догадка, тоже. Я считаю, что для большинства браузеров обычное число - четыре соединения на домен. Если вы используете Comet или другие долгоживущие HTTP-соединения, это может привести к истощению других запросов. Вы можете обойти это, создав поддомен для некоторых своих ресурсов, например, создать & quot; static.myapp.com & quot; для статических изображений. Таким образом, статические и динамические ресурсы не будут учитываться друг против друга.
0

Use asset hosts, they are extremely easy to setup: http://api.rubyonrails.org/classes/ActionView/Helpers/AssetTagHelper.html Make sure that Javascript is loaded near the bottom of the page, when possible. Make sure that Apache/Nginx/whatever correctly sets the Expires-In HTTP header. Run Google Speed Page under Firefox, this will provide lots of good info.
Использование asset_packer - интересный вариант, но я хотел бы знать,why это происходит. Я только что видел другой случай, когда все активы были обслужены, кроме одного, который вызвал зависание. Этот запрос - к файлу Javascript по адресуassets3.mydomain.com - вообще не отображается в журнале mod_rewrite, поэтому похоже, что браузер вообще не запрашивал этот ресурс у Apache? Может ли быть проблема с SSL? Olly
Благодарю. 1. Мы уже используем хосты активов. 2. Javascript включен в заголовок & lt; HEAD & gt; раздел каждой страницы 3. Когда вы говорите "правильно", задает заголовок истечения срока действия ". что вы имеете в виду? Мы установили это на 1 год, но чтобы попытаться отладить это, я фактически полностью отключил настройку заголовка expires, и проблема все еще сохраняется. 4. Не объясняет, почему мы наблюдаем периодические зависания только для некоторых пользователей, к сожалению Olly
По нашему опыту, когда браузер загружает файлы Javascript, он не загружает другие статические ресурсы. Не знаю, будет ли это проявляться как проблема, о которой вы сообщаете в Safari, когда пользователь загружает страницу с холодным кэшем ... (т.е. он не будет загружать изображения). Ссылка здесь:developer.yahoo.net/blog/archives/2007/07/…  Может быть, с помощью плагина, как asset_packager (github.com/sbecker/asset_packager/tree/master) будет полезен, так как весь ваш Javascript будет упакован в один большой файл, что снижает накладные расходы из-за загрузки большого количества файлов.

Похожие вопросы