웹 최적화 방법 - 이미지 파트

임효진·2023년 1월 20일
0

프로젝트 당시, 크롬 라이트하우스 측정을 통한 성능 개선을 시도한 적이 있다.
우리 서비스의 경우, 정보제공형 커뮤니티였기에 유저들이 고화질의 사진 또는 gif를 업로드하고 뿌려주는 것이 UX에 적합하다고 의사결정을 했고, 자연스레 최적화는 필수조건이 되었다. 당시에는 시간관계상 다양한 최적화 방법을 시도하지는 못했고 image compression 라이브러리를 사용해 이미지 압축 후, 백엔드에 송신하였고 백엔드에서는 url를 보내줌으로써 시간복잡도를 낮춘 경험이 있었다.
오늘은 프론트엔드단에서 다양한 웹 최적화 방법에 대해 공부를 해보려한다.

웹 최적화란?

웹 최적화란 최고의 웹 성능을 구현하기 위한 최고의 컨디션을 만드는 다양한 노력을 의미한다. 즉 최고의 퍼포먼스를 만드는 최적화 조건을 갖추는 것을 의미한다.

프론트엔드 최적화

웹 UI/UX적 최적화다. 주로 HTML / JS / CSS / Image 최적화를 진행한다.
최적화가 잘되어 있는 웹사이트는 브라우저에서 콘텐츠를 다운로드, 로딩, 렌더링 할 때 속도가 빨라진다.

브라우징 시간별 콘텐츠를 볼 때 대부분 프런트엔드에서 발생한다.

  • 스트립트를 병합하여 브라우저의 호출 개수를 줄인다.
  • 스크립트 크기를 최소화해 바이트자체를 줄인다
  • 스크립트를 gzip 등으로 압축하여 전달한다.
  • WebP 등으로 브라우저 이미지 형식을 최적화한다
  • 이미지 손실, 무손실 압축한다.
  • Cache-Control 응답헤더를 통해 브라우저 캐시를 충실히 사용한다.
  • 도메인 수를 줄여 DNS조회를 최소화한다.
  • DNS 정보를 미리 읽어 온다.
  • CSS를 HTML상단에, JS를 HTML하단에 위치시킨다.
  • page prefetching한다.
  • 타사 스크립트가 웹 성능을 방해하지 않도록 조정한다.

아래는 공부에 참고한 블로그이다.
출처 : https://oliveyoung.tech/blog/2021-11-22/How-to-Improve-Web-Performance-with-Image-Optimization/

브라우저 사이즈에 맞춰 적절한 이미지 제공

이미지를 다양한 사이즈에 대응할 수 있도록 적절한 브레이크 포인트를 설정하여 사이즈를 조절해준다. 이렇게 하는 이유는 데스크톱의 이미지는 모바일의 이미지보다 상대적으로 용량이 클 수밖에 없다. 그렇게 되면 사용자는 필요 이상의 이미지를 다운받게 되어 리소스가 낭비될 수 있다. 그러므로 브라우저 사이즈에 맞게 브레이크 포인트를 걸어 과도한 리소스를 사용하지 못하게 해주어 보다 빠른 렌더링이 가능하도록 해준다. 이러한 방식의 해결로 미디어쿼리 및 태그의 srcset 속성, 태그 등의 방법이 있다.

미디어 쿼리를 활용하는 방법

미디어 쿼리는 단말기의 유형과 어떤 특성이나 수치에 따라 스타일을 조절할 수 있는 CSS 문법이다. 이 미디어 쿼리를 이용하면, 브라우저의 사이즈, 호버 상태, 사용자 OS의 다크 모드 적용 여부 등 다양한 조건에 따라 다른 스타일 시트를 적용할 수 있다. 사용법은 아래와 같다.

  <div class="image-box"></div>
.image-box {
  max-width: 100%;
  width: 400px;
  height: 400px;
  background-image: url(./small.png);
  background-repeat: no-repeat;
  background-size: contain;
  padding: 10px
}

@media (min-width: 401px) {
	.image-box {
  	width: 700px;
  	height: 700px;
  	background-image: url(./midium.png);
  }
}

@media (min-width: 701px) {
	.image-box {
    width: 1000px;
    height: 1000px;
    background-image: url(./large.png);
  }
}

태그의 srcset 속성 사용하는 방법

태그의 srcset 속성은 이미지 소스의 세트라는 의미로, 같은 비율의 다양한 크기를 가지는 동일 이미지들을 명시하는 속성이다. (단, 주의사항은 이미지의 크기로 px단위가 아닌 w디스크립터 혹은 x디스크립터를 입력해야 하며, 작은 크기 이미지부터 순서대로 입력해야 한다), 또한 sizes는 미디어 조건과 그 조건에 해당하는 이미지의 최적화 출력 크기를 지정한다. 사용법은 아래와 같다. (단, IE는 지원하지 않는다.)

  
  <img 
   srcset="./small.png 400w,
           ./medium.png 700w,
           ./large.png 1000w"
   sizes="(max-width: 401px) 400px,
          (max-width: 700px) 7000px,
          1000px"
   src="./large.png"
/>

####태그를 사용하는 방법
사실 위의 태그는 완벽하지 않다. 브라우저가 사용하는 연산 방식이나 메모리, 혹은 파워가 충분한지에 따라 낮은 해상도가 선택될 수도 있고, 해상도별로 다른 비율의 이미지를 사용하거나 부분만 확대한 이미지를 사용할 때 이미지가 비정상적으로 보이는 이슈가 존재한다. 하지만 태그는 태그의 단점을 보완하는 방법이다. picture는 특정 브라우저에서 특정 이미지를 사용할 수 있도록 강제할 수 있으며, 조건에 맞지 않는 이미지는 다운로드 하지 않는다. 또한 태그는 이미지를 숨겨도 이미지를 다운로드하고 이미지를 줄여도 다른 이미지가 보여지지 않는 태그와는 다르게 해당 문제를 모두 해결할 수 있는 가장 효과적인 방법이다. 하지만 HTML 소스가 길어진다는 점과 IE 및 안드로이드 구버전 브라우저에서는 지원하지 않는다는 점이 단점이다. (다만 pollyfill을 사용하면 어느정도 해결은 가능합니다.)

  <picture>
    <source media="(min-width: 700px)" srcset="/examples/images/people_960.jpg">
    <source media="(min-width: 400px)" srcset="/examples/images/people_575.jpg">
    <img src="/examples/images/people_200.jpg" alt="People">
</picture>

이미지 Lazy Loading

웹사이트의 이미지는 최대한 사용자가 보이는 부분부터 로드되도록 처리하며, 사용자가 보이지 않는 부분은 Lazy Loading을 적용하여 사용자의 사용자 경험 저하를 막을 수 있도록 한다. 사용자가 처음부터 보지 않는 부분을 초기 렌더링 시 로드하게 되면 정작 사용자가 보이는 화면의 로딩 시간이 지연되게 된다. 이러한 화면 밖의 콘텐츠들을 Above the fold라고 하며, 이러한 Above the fold 이미지들은 자바스크립트를 이용하여 레이지 로딩을 적용한다. 방법은 아래와 같다.

<img loading="lazy">

위와 같이 사용하여 태그 자체에서 지원하는 레이지 로딩을 사용하는 방법이 있고

<img src="1px.gif" data-src="book.jpg" onload="loadReal(this)"/>
function loadReal(img) {
	if(img.style.display != "none"){
		img.onload = null;
		img.src = img.getAttribute("data-src")
	}
}

자바스크립트를 활용하여 위와 같이 활용하는 방법이 있다. 위의 자바스크립트를 간단히 설명하자면 태그의 src는 1px짜리의 작고 투명한 파일을 설정해놓고 추후 data-src에 들어가 있는 진짜 이미지를 로드해서 넣어주는 방법이다. 위의 img 태그에서 지원하는 loading의 경우에는 아직 비표준이므로, 자바스크립트를 이용한 방법을 추천한다. 단 이건 간단한 예시이며 실제 운영에서는 지연 로딩을 지원하는 라이브러리를 사용하는 것을 추천한다.

profile
프론트 요정임

0개의 댓글

관련 채용 정보