Rails 프로덕션에서 config.assets.compile = true, 왜 그렇지 않습니까?


185

에 의해 기본값은 응용 프로그램 설치 난간 rails newconfig.assets.compile = false생산.

그리고 일반적인 방법은 rake assets:precompile앱을 배포하기 전에 실행 하여 모든 자산 파이프 라인 자산이 컴파일되도록하는 것입니다.

config.assets.compile = true프로덕션 환경에서 설정하면 어떻게됩니까 ?

precompile더 이상 달릴 필요가 없습니다. 내가 믿게 될 것은 자산이 처음 요청되면 컴파일 될 것입니다. 이것은 처음으로 성능 저하가 될 것입니다 (일반적으로 프로덕션 환경에서 js 런타임이 필요하다는 것을 의미합니다). 그러나 이러한 단점 외에도 자산이 느리게 컴파일 된 후 해당 자산에 대한 모든 후속 액세스 에는 성능 저하 가 없을 것이라고 생각 합니다. 이 최초의 첫 번째 적중 게으른 컴파일 후 사전 컴파일 된 자산과 앱의 성능은 정확히 동일 합니다. 이것이 사실입니까?

누락 된 것이 있습니까? config.assets.compile = true프로덕션 환경 에서 설정하지 않는 다른 이유 는 무엇입니까? 프로덕션 환경에서 JS 런타임을 가지고 있고 자산을 처음 액세스 할 때 성능 저하의 균형을 잡을 의향 이 있다면, 실행하지 않아도되는 대가로 precompile이것이 의미가 있습니까?


1
경고, 이전 버전의 스프라켓에는 버그가 포함되어 있으며 config.assets.compile이 true로 구성된 경우 디렉토리 통과 취약점 ( blog.heroku.com/rails-asset-pipeline-vulnerability ) 의 위험이 있습니다
Mauro

이것이 바로 Stackoverflow가 작동하는 방식입니다. 잘 쓰여진 질문과 잘 쓰여진 답변. op와 @ richard-hulse를 모두 사랑합니다.
schmijos

답변:


259

나는 그 안내서를 썼습니다.

프로덕션 환경에서 컴파일하고 싶지는 않습니다.

컴파일하면 다음과 같은 일이 발생합니다.

/ assets의 파일에 대한 모든 요청은 Sprockets로 전달됩니다. 온 첫번째 각각의 모든 자산에 대한 요청이 컴파일 및 캐시 (일반적으로 파일 시스템)에 사용되는 어떤 레일에 캐싱.

후속 요청에서 스프로킷은 요청을 수신하고 핑거 프린팅 된 파일 이름을 찾아야하며 자산을 구성하는 파일 (이미지) 또는 파일 (css 및 js)이 수정되지 않았는지 확인한 다음 캐시 된 버전이있는 경우 해당 파일을 제공합니다.

모든 자산 폴더에 벤더에 / 자산 폴더는 플러그인에 의해 사용.

솔직히 말하면 코드가 속도에 최적화되어 있지 않기 때문에 많은 오버 헤드가 있습니다.

이는 자산이 고객에게 얼마나 빨리 전달되는지에 영향을 미치며 사이트의 페이지로드 시간에 부정적인 영향을 미칩니다.

기본값과 비교하십시오.

자산이 사전 컴파일되고 컴파일이 해제되면 자산이 컴파일되어에 지문이 표시됩니다 public/assets. Sprockets는 일반에서 지문으로 표시된 파일 이름의 매핑 테이블을 Rails에 반환하고 Rails는이를 파일 시스템에 씁니다. 매니페스트 파일 (Rails 3의 YML 또는 Rails 4의 무작위 이름을 가진 JSON)은 시작할 때 Memory by Rails에로드되고 자산 헬퍼 메소드에서 사용하기 위해 캐시됩니다.

이를 통해 올바른 핑거 프린팅 자산을 사용하여 페이지를 매우 빠르게 생성 할 수 있으며 파일 자체는 웹 서버에서 파일 시스템으로 빠르게 제공됩니다. 둘 다 라이브 컴파일보다 훨씬 빠릅니다.

파이프 라인 및 지문의 이점을 최대한 활용하려면 웹 서버에서 원거리 미래 헤더를 설정하고 js 및 css 파일에 gzip 압축을 활성화해야합니다. 스프로킷은 서버가 사용하도록 설정할 수있는 애셋 버전의 애셋을 작성하므로 각 요청마다 그렇게하지 않아도됩니다.

이렇게하면 가능한 빨리 가장 작은 크기로 클라이언트에 자산을 가져 와서 페이지의 클라이언트 쪽 표시 속도를 높이고 (먼 미래의 헤더로) 요청을 줄일 수 있습니다.

따라서 라이브 컴파일하는 경우 다음과 같습니다.

  1. 아주 느린
  2. 압축 부족
  3. 페이지 렌더링 시간에 영향을 미칩니다

  1. 최대한 빨리
  2. 압축
  3. 서버에서 들었던 압축을 제거하십시오 (선택 사항).
  4. 페이지 렌더링 시간을 최소화하십시오.

편집 : (댓글을 달아 답하십시오)

첫 번째 요청에서 파이프 라인 을 사전 컴파일하도록 변경할 있지만이를 수행하기위한 몇 가지 주요 장애물이 있습니다. 첫 번째는 지문이 붙은 이름에 대한 조회 테이블이 있거나 도우미 메서드가 너무 느리다는 것입니다. 주문형 컴파일 시나리오에서는 각각의 새 자산이 컴파일되거나 요청 될 때 조회 테이블에 추가 할 수있는 방법이 필요합니다.

또한 누군가는 모든 자산이 컴파일되고 제자리에 올 때까지 알려지지 않은 기간 동안 느린 자산 배송 가격을 지불해야 할 것입니다.

모든 컴파일 비용이 한 번에 오프라인으로 지불되는 기본값은 공개 방문자에게 영향을 미치지 않으며 모든 것이 작동하기 전에 모든 것이 작동하도록 보장합니다.

거래 차단기는 생산 시스템에 많은 복잡성을 추가한다는 것입니다.

[편집, 2015 년 6 월] 배포하는 동안 느린 컴파일 시간에 대한 솔루션을 찾고 있기 때문에이 내용을 읽고 있다면 자산을 로컬로 사전 컴파일하는 것을 고려할 수 있습니다. 이에 대한 정보는 자산 파이프 라인 안내서에 있습니다. 이를 통해 변경 사항이있을 때만 로컬에서 사전 컴파일하고 커밋 한 다음 사전 컴파일 단계없이 빠르게 배포 할 수 있습니다.


1
감사합니다. 답변을 수락했습니다. 그러나 이제 내 질문은, 지금은 그렇지 않지만, Asset Pipeline 첫 번째 요청에서 느리게 컴파일 수있는 기능을 가지고 있다고 생각할 것입니다. 지문 매니페스트?
jrochkind

위 참조. Capistrano가 작동하지 않기 때문에 이것이 문제입니까?
Richard Hulse

나는 Capistrano를 사용하지 않습니다. 이전에는 필요하지 않았지만 추가 된 복잡성은 가치가 없었습니다. 아마도 자산 파이프 라인은 낙타를 깰 수있는 짚입니다. 귀하의 의견으로는, capistrano 또는 이와 유사한 것 없이 자산 파이프 라인으로 Rails 배포를 관리하는 것은 불가능 합니까? 단순한 설정의 경우 수작업으로 큰 문제가되지 않은 것은 부끄러운 일입니다.
jrochkind

Rails 3.1에는 Capistrano가 정말로 필요합니다. 이전 앱이 계속 실행되는 동안 자산이 새 공용 디렉토리에 컴파일됩니다. 컴파일이 완료되면 새 버전이 심볼릭 링크되고 서버가 자동으로 다시 시작됩니다.
Richard Hulse 2012

"파이프 라인과 핑거 프린팅의 이점을 최대한 활용하려면 웹 서버에서 원거리 미래 헤더를 설정하고 js 및 css 파일에 대해 gzip 압축을 활성화해야합니다."-어떻게해야하는지에 대한 지침이나 링크를 제공해 주시겠습니까? 이?
Isaac Betesh 2016 년

7

사전 컴파일 작업으로 오버 헤드가 줄어 듭니다.

Precompile everything initially with these settings in production.rb
# Precompile *all* assets, except those that start with underscore
config.assets.precompile << /(^[^_\/]|\/[^_])[^\/]*$/

그런 다음 * .html.erb 또는 "/assets/web.png"에서 이미지 및 스타일 시트를 "/assets/stylesheet.css"로 사용할 수 있습니다.


6

Heroku를 사용하는 사람 :

Herkou에 배포하는 경우 컴파일 된 자산이 포함되지 않은 (즉, public/assets커밋되지 않은) 배포되지 않은 경우 config.assets.compile = true또는 사전 컴파일 된 자산을 커밋 할 경우 배포 중에 자동으로 사전 컴파일됩니다.

헤 로쿠의 문서는 여기에 있습니다 . CDN은 다이노 자원의 부하를 제거하는 것이 좋습니다.


1

파일이 파일 시스템에 기록되지 않기 때문에 웹 서버에서 직접 제공 할 수 없으므로 파일이 파일 시스템에 기록되지 않기 때문에 사전 컴파일과 동일하지 않습니다. 캐시 항목을 읽는 경우에도 일부 루비 코드가 항상 관련됩니다.


흠, 나는 precompile=true컴파일 된 자산이 파일 시스템에 쓰여질 것이라고 생각했다 . 확실합니까? 내가 확인하자 ...
jrochkind

1
그들은 파일 시스템에 기록됩니다,하지만처럼 보이는 - 바하, 난 당신이 맞아요 생각 tmp/cache보다는 public/assets, 웹 서버, 그들은 여전히 레일에 의해 제공 될거야 없습니다되는 앱 볼 수 있도록하지 장소를 웹 서버. ㅋㅋ 맞습니까?
jrochkind

옳은. 웹 서버가 올바른 선택을하는 것만 큼 빠르지는 않습니다. 앱 앞에 클라우드 프론트와 같은 CDN을 넣더라도 상관 없습니다.
Frederick Cheung

1

세트 config.asset.compile = false

Gemfile에 추가

group :assets do gem 'turbo-sprockets-rails3' end

번들 설치

운영 rake assets:precompile

그런 다음 서버를 시작하십시오


config.asset.compile = true in production.rb사전 완료 메커니즘이 추가되지 않았으므로 파일 을 설정 한 한 . 서버를 시작할 때마다 페이지를로드하는 데 너무 많은 시간이 걸립니다 (요청이 요청을 처리하고 자산을 컴파일하는 경우). 이제 turbo-sprockets-rails3Gemfile에 포함 시키고 명령을 실행 rake assets:precompile하여 자산을 사전에 컴파일합니다. 이제 config.asset.compile = false in production.rb서버를 설정 하고 시작했는데 지연없이 페이지가로드됩니다. (만 자산 컴파일하지 않고 요청을 처리)
모하메드 살림

2
turbo-sprockets-rails3루비 3에서만 필요하다고 말할 가치가 있습니다.
Andre Figueiredo

0

공식 안내서에서 :

첫 번째 요청에서 자산은 위의 개발에서 설명한대로 컴파일 및 캐시되며 헬퍼에 사용 된 매니페스트 이름이 MD5 해시를 포함하도록 변경됩니다.

Sprockets는 또한 Cache-Control HTTP 헤더를 max-age = 31536000으로 설정합니다. 이는 서버와 클라이언트 브라우저 사이의 모든 캐시에이 컨텐츠 (제공된 파일)를 1 년 동안 캐시 할 수 있음을 나타냅니다. 그 결과 서버에서이 자산에 대한 요청 수가 줄어 듭니다. 자산이 로컬 브라우저 캐시 또는 일부 중간 캐시에있을 가능성이 높습니다.

이 모드는 더 많은 메모리를 사용하고 기본값보다 성능이 저하되므로 권장하지 않습니다.

또한 배포에 Capistrano 를 사용하면 프리 컴파일 단계가 전혀 문제되지 않습니다 . 그것은 당신을 위해 그것을 돌봐. 당신은 그냥 실행

cap deploy

또는 (설정에 따라)

cap production deploy

그리고 당신은 모두 설정되었습니다. 여전히 사용하지 않으면 확인하는 것이 좋습니다.


공식 가이드의 언어가 나와 동의한다고 생각하십니까? 나는 그 가이드를 보았습니다. 위에서 제안하는 것이 의미가 있는지 확실하지 않습니다. 어떻게 생각하십니까? 그게 내 질문입니다.
jrochkind

예, 당신은 기본적으로 같은 것을 말합니다. 라이브 컴파일을 사용하지 않는 것이 좋습니다.
Sergio Tulentsev

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.