Optimizing Performance with Cache Control

cacheperformancewebpack

2019-02-17


개인적인 곡뢀 λ…ΈνŠΈλ‘œ, 였λ₯˜κ°€ μžˆμ„ 수 μžˆμŠ΅λ‹ˆλ‹€.

1. What is web cache?

μΊμ‹œμ˜ 어원은 ν”„λž‘μŠ€μ–΄λ‘œ "hiding place for stores"λΌλŠ” μ˜λ―Έμ΄λ‹€. (좜처)

μΊμ‹œλŠ” λ™μΌν•œ request(λ™μΌν•œ μ΄λ¦„μ˜ λ¦¬μ†ŒμŠ€)에 λŒ€ν•˜μ—¬ λΈŒλΌμš°μ €κ°€(λ˜λŠ” λ„€νŠΈμ›Œν¬ λ‹¨μ—μ„œ) κ°–κ³ μžˆλŠ” response 의 볡사본이닀. λΈŒλΌμš°μ €λŠ” μ΄μ „μ˜ 응닡을 κΈ°μ–΅ν•˜κ³  μžˆλ‹€κ°€ λ™μΌν•œ request κ°€ 올 λ•Œ μ„œλ²„μ— λ‹€μ‹œ μš”μ²­ν•˜μ§€ μ•Šκ³  볡사본을 λ°˜ν™˜ν•œλ‹€. μ„œλ²„λ₯Ό κ±°μΉ˜μ§€ μ•ŠκΈ° λ•Œλ¬Έμ— λΉ λ₯΄κ³ , λΆ€ν•˜λ„ 적닀. μ†ŒμŠ€κ°€ λ°”λ€” λ•ŒκΉŒμ§€ μΊμ‹œλœ 볡사본을 λ°˜ν™˜ν•˜λ„λ‘ ν•  수 있기 λ•Œλ¬Έμ— 적절히 ν™œμš©ν•˜λ©΄ μ‚¬μš©μžκ°€ 응닡을 λ°›λŠ” 속도λ₯Ό ν˜„μ €νžˆ 쀄일 수 μžˆλ‹€.


2. Caching with webpack

// webpack.config.js
module.exports = {
  ...
  output: {
    filename: "static/js/main.[hash:8].js",
  },
  ...
}
  • μ›ΉνŒ©μ—μ„œλŠ” μœ„μ²˜λŸΌ λΉŒλ“œλœ js νŒŒμΌμ— hash λ₯Ό 뢙일 수 μžˆλ‹€.
  • μƒˆλ‘œ λΉŒλ“œκ°€ 될 λ•Œλ§ˆλ‹€ ν•΄μ‹œκ°’μ΄ λ°”λ€ŒκΈ° λ•Œλ¬Έμ— μ†ŒμŠ€κ°€ λ°”λ€Œμ§€ μ•ŠμœΌλ©΄ λΈŒλΌμš°μ €λŠ” 이λ₯Ό 같은 파일둜 μΈμ‹ν•˜κ³  μΊμ‹±ν•œλ‹€.
  • μ†ŒμŠ€κ°€ λ°”λ€Œλ©΄ js 파일의 이름도 λ°”λ€ŒκΈ° λ•Œλ¬Έμ— μΊμ‹±ν•˜μ§€ μ•Šκ³  μ—…λ°μ΄νŠΈλœ νŒŒμΌμ„ λ°˜ν™˜ν•˜κ²Œ λœλ‹€.
  • 이미지 λ¦¬μ†ŒμŠ€μ— λŒ€ν•΄μ„œλ„ file-loaderμ—μ„œ μ•„λž˜μ™€ 같이 ν•΄μ‹œκ°’μ„ 뢙일 수 μžˆλ‹€.
module: {
  rules: [
    {
      test: [/\.jpeg?g$/, /\.png$/],
      use: [
        {
          loader: "file-loader",
          options: {
            name: "[name].[hash:8].[ext]",
            outputPath: "img/",
            publicPath: "img/"
          }
        }
      ]
    }
    ...
  ];
}

3. Cache-control

html, css, js λ“± λ¦¬μ†ŒμŠ€μ— λŒ€ν•˜μ—¬ cache-control HTTP header λ₯Ό μ§€μ •ν•˜λ©΄ λ”μš± 곡격적으둜 캐싱을 ν•  수 μžˆλ‹€. cache-control에 λ“€μ–΄κ°€λŠ” 값은 ,둜 κ΅¬λΆ„λœ λ¬Έμžμ—΄μ΄λ‹€.

$ tree .
dist
β”œβ”€β”€ favicon.ico
β”œβ”€β”€ index.html
└── static
    β”œβ”€β”€ css
    β”‚ └── main.[hash:8].css
    β”œβ”€β”€ js
    β”‚ └── main.[hash:8].js
    └── media
        └── image.png

예λ₯Ό λ“€μ–΄ μœ„μ™€ 같은 디렉토리 ꡬ쑰둜 Single Page Application 을 κ°œλ°œν•  경우, 각각의 λ¦¬μ†ŒμŠ€μ— λŒ€ν•˜μ—¬ λ‹€μŒκ³Ό 같이 cache-control 을 μ„€μ •ν•  수 μžˆλ‹€.

  1. index.html - "no-cache"

    • no-cache : 맀 μš”μ²­λ§ˆλ‹€ μ½˜ν…μΈ κ°€ λ°”λ€Œμ—ˆλŠ”μ§€ μ„œλ²„μ—μ„œ κ²€μ¦ν•˜λŠ” round-trip 을 ν•œλ²ˆ ν•œλ‹€. λ¦¬μ†ŒμŠ€κ°€ λ°”λ€Œμ§€ μ•Šμ•˜κ³  μΊμ‹œκ°€ μžˆμ„ 경우, λ¦¬μ†ŒμŠ€λ₯Ό μš”μ²­ν•˜μ§€ μ•Šκ³  μΊμ‹œμ—μ„œ κ°€μ Έμ˜¨λ‹€.
    • λŒ€λΆ€λΆ„μ˜ SPA λŠ” index.html μ•ˆμ—μ„œ ν•΄μ‹œ 값이 뢙은 js νŒŒμΌμ„ λ‘œλ“œν•˜κΈ° λ•Œλ¬Έμ— html νŒŒμΌμ€ μΊμ‹±ν•˜μ§€ μ•ŠλŠ”λ‹€. js, css 의 경둜(λ˜λŠ” 파일λͺ…)κ°€ λ°”λ€Œμ—ˆλŠ”μ§€ μ—¬λΆ€λ₯Ό νŒλ‹¨ν•΄μ•Όν•˜κΈ° λ•Œλ¬Έμ΄λ‹€.
  2. main.[hash:8].js - "private, max-age=31536000"

    • private : js νŒŒμΌμ—λŠ” μ€‘μš”ν•œ μ‚¬μš©μž 정보가 μžˆμ„ 수 있기 λ•Œλ¬Έμ— 곡용 cache λ₯Ό μ‚¬μš©ν•˜μ§€ μ•Šκ³  private cache (ν΄λΌμ΄μ–ΈνŠΈμ˜ λΈŒλΌμš°μ €)λ₯Ό μ‚¬μš©ν•œλ‹€.
    • max-age : 초(second) 값을 λ°›μœΌλ©° λͺ…μ‹œλœ μ‹œκ°„λ™μ•ˆ μΊμ‹œλ₯Ό μ‚¬μš©ν•˜λΌλŠ” μ˜λ―Έμ΄λ‹€. js 파일의 μ†ŒμŠ€κ°€ λ³€κ²½λ˜μ–΄ μƒˆλ‘œ λΉŒλ“œλ˜μ—ˆμ„ 경우, url 의 hash 값이 λ°”λ€ŒκΈ° λ•Œλ¬Έμ— 캐싱이 λ˜μ§€ μ•ŠλŠ”λ‹€. max-age=31536000λŠ” λ°”λ€Œμ§€ μ•ŠλŠ” λ¦¬μ†ŒμŠ€μ— λŒ€ν•˜μ—¬ 1 λ…„κ°„ 캐싱함을 μ˜λ―Έν•œλ‹€.
  3. main.css - "max-age=31536000"

    • max-age=31536000 : js 파일과 λ§ˆμ°¬κ°€μ§€λ‘œ hash κ°€ λΆ™κΈ° λ•Œλ¬Έμ— λ°”λ€Œμ§€ μ•Šμ€ νŒŒμΌμ— λŒ€ν•˜μ—¬ 1 λ…„κ°„ μΊμ‹±ν•œλ‹€.
  4. 이미지 - "max-age=86400"

    • max-age : url 이 λ°”λ€Œμ§€ μ•Šμ„ 경우 1 일, hash λ₯Ό 뢙일 경우(μ›ΉνŒ©μ—μ„œ require()λ₯Ό μ‚¬μš©ν•΄ λΉŒλ“œν•˜λŠ” 경우)μ—λŠ” 1 λ…„μœΌλ‘œ ν•  수 μžˆλ‹€.

4. How to set cache-control

s3 λ₯Ό μ΄μš©ν•˜μ—¬ 정적 νŒŒμΌμ„ ν˜ΈμŠ€νŒ…ν•  경우, Metadata 섀정을 ν†΅ν•΄μ„œ cache-control 을 지정할 수 μžˆλ‹€. AWS SDK for JavaScript λ₯Ό μ‚¬μš©ν•˜μ—¬ 정적 νŒŒμΌμ„ s3 에 μ—…λ‘œλ“œ/배포할 경우, μ•„λž˜μ™€ 같이 cache-control을 μ„€μ •ν•  μˆ˜λ„ μžˆλ‹€.

s3.upload(
  {
    Bucket: bucket, // S3 bucket name
    Key: key, // file name
    Body: file,
    ACL: "public-read",
    ContentType: "application/javascript",
    CacheControl: "private, max-age=86400"
  },
  function(err, data) {
    ...
  }
);

Cloudfront λ₯Ό μ‚¬μš©ν•  경우, cache invalidation 을 톡해 μ†ŒμŠ€κ°€ λ°”λ€Œμ—ˆμ§€λ§Œ 이름은 λ°”λ€Œμ§€ μ•Šμ€ λ¦¬μ†ŒμŠ€μ— λŒ€ν•˜μ—¬ μž„μ˜λ‘œ cache λ₯Ό μ§€μ›Œμ€„ μˆ˜λ„ μžˆλ‹€.


더 μ•Œμ•„λ³΄κΈ°

etag - https://developer.mozilla.org/ko/docs/Web/HTTP/Headers/ETag

Sources: