구현 근거
글마다 공개 저장소와 관련 파일을 연결합니다.
Frontend Note는 김영주의 공개 프로젝트에서 확인할 수 있는 코드, 테스트 자산, 측정 조건을 바탕으로 프론트엔드 구현 과정을 기록합니다.
글마다 공개 저장소와 관련 파일을 연결합니다.
입력 자산, 품질값, 인코더, 측정일을 함께 적습니다.
확인하지 못한 환경과 조건을 결론에서 분리합니다.
파일 업로드 UI에서 MIME 타입, 확장자, 손상 파일, 너무 큰 파일, 이미지 디코딩 실패를 어떻게 나눠 처리해야 하는지 실무 기준으로 정리합니다.
사진, UI 스크린샷, 투명 그래픽에서 JPEG, PNG, WebP 압축 결과가 어떻게 달라지는지 브라우저 도구 구현 관점으로 비교합니다.
Canvas로 이미지를 줄일 때 흐림, 계단 현상, 비율 깨짐, EXIF 방향 문제를 줄이기 위한 실무 체크리스트입니다.
여러 파일을 동시에 처리할 때 전체 진행률, 파일별 상태, 실패 메시지, 다운로드 가능 상태를 어떻게 나눌지 React UI 기준으로 정리합니다.
React 기반 기술 블로그가 검색 봇과 애드센스 심사에서 읽히도록 제목, 설명, canonical, 사이트맵, 내부 링크, 정책 페이지를 점검하는 방법입니다.
React SPA 블로그에서 사전 렌더링, 메타 태그, 구조화 데이터, 사이트맵을 준비해 검색 봇과 애드센스 심사가 본문을 읽을 수 있게 만드는 방법입니다.

서버 업로드 없이 브라우저에서 이미지를 압축하는 방법을 리사이즈, 손실 압축, WebP 변환, 다운로드 단계별로 공개 코드와 측정 자산을 근거로 정리합니다.

브라우저에서 사용자가 선택한 파일을 읽는 FileReader API의 read 메서드 네 가지와 이벤트 처리 방법을, 실제 이미지 처리 코드가 왜 readAsDataURL을 선택했는지와 함께 정리합니다.

서버 없이 브라우저에서 만든 파일을 사용자 PC에 저장시키는 방법을 a 태그의 download 속성, Blob URL, 여러 파일을 연속으로 받을 때 생기는 문제까지 실제 코드로 정리합니다.

FileReader.readAsDataURL과 URL.createObjectURL은 둘 다 파일을 화면에 보여줄 수 있지만 메모리 사용 방식이 다릅니다. img-compressor가 두 방식을 각각 어디에 쓰는지로 차이를 비교합니다.

Canvas로 이미지를 리사이즈하고 WebP로 변환하는 전체 파이프라인과, 품질 옵션의 범위를 넓게 열어두지 않은 이유를 실제 코드와 벤치마크 수치로 정리합니다.

무거운 압축 라이브러리를 필요한 시점에만 불러오는 동적 import와, 압축 중 화면이 멈춘 것처럼 느껴지는 문제를 줄이는 Web Worker 옵션을 함께 정리합니다.

사진, 스크린샷, 투명 그래픽을 WebP·JPEG로 변환했을 때 실제 감소율을 품질값별로 측정하고, 인코더와 측정 조건까지 함께 남긴 벤치마크입니다.

여러 이미지를 순서대로 처리하는 진행 상태, 완료된 파일만 남기는 결과 목록, 원본 이름을 보존하는 다운로드 파일명까지 다중 파일 업로드 UI를 코드로 정리합니다.

파일 읽기 실패, 이미지 디코딩 실패, Canvas 변환 실패까지 브라우저 이미지 도구에서 놓치기 쉬운 에러 처리 흐름을 코드로 정리합니다.

URL.createObjectURL로 만든 미리보기·다운로드 링크를 언제 revokeObjectURL로 해제해야 하는지, 이미지 도구와 영상 도구 두 사례로 정리합니다.

파일 입력, 옵션 영역, 결과 카드가 작은 화면에서 겹치지 않게 만드는 반응형 레이아웃 기준과, 키보드·스크린리더 사용자도 끝까지 쓸 수 있게 만드는 접근성 체크리스트를 함께 정리합니다.

파일 형식, 크기, 실패 케이스, 모바일 화면, 다운로드 흐름까지 브라우저 이미지 도구를 배포하기 전 확인해야 할 테스트 항목을 정리합니다.

WebP 변환율이나 Worker 옵션 효과를 설명하는 글을 읽을 때 저자의 코드 링크와 수치를 어디까지 신뢰해도 되는지 점검하는 기준입니다.
브라우저에서 FFmpeg.wasm으로 영상·음성 구간을 재인코딩 없이 -c copy로 빠르게 잘라내는 방법과 그 트레이드오프를 정리합니다.
img-compressor의 [locale] 세그먼트와 next-intl 미들웨어가 지원하지 않는 언어 경로를 어떻게 걸러내는지, 실제 설정 코드를 기준으로 정리합니다.
img-compressor와 media-crop 두 프로젝트가 각각 next/og의 ImageResponse로 파비콘과 OG 이미지를 어떻게 다르게 구성했는지 비교합니다.
img-compressor의 manifest.ts, robots.ts 파일을 기준으로 Next.js Metadata API가 PWA 매니페스트와 크롤링 규칙을 어떻게 타입 안전하게 관리하는지 정리합니다.
img-compressor의 sitemap.ts가 언어별 URL마다 alternates.languages를 함께 기록하는 방식과 x-default가 필요한 이유를 정리합니다.
img-compressor의 next.config.js가 언어 세그먼트를 포함한 다수의 예전 경로를 소수의 대표 페이지로 영구 리다이렉트하는 방법을 코드로 정리합니다.
media-crop의 next.config.ts가 모든 응답에 Cross-Origin-Opener-Policy와 Cross-Origin-Embedder-Policy 헤더를 붙이는 이유를 SharedArrayBuffer 요구사항을 중심으로 정리합니다.
media-crop의 FileUploader가 드래그앤드롭과 파일 선택 모두에서 MIME 타입과 파일명 확장자를 함께 확인하는 validateAndSelect 함수를 코드로 살펴봅니다.
media-crop이 next/font/google로 폰트를 빌드 시점에 자체 호스팅하는 방식과, 이 사이트(Frontend Note)가 CDN에서 폰트를 직접 불러오는 방식의 트레이드오프를 비교합니다.
media-crop의 lib/utils.ts에 있는 세 줄짜리 cn() 함수가 clsx와 tailwind-merge를 조합해 조건부 Tailwind 클래스 충돌을 어떻게 해결하는지 정리합니다.
img-compressor의 messages/ko.json, en.json이 common, compressor, language, seo 네임스페이스로 문구를 나누는 구조와 그 이유를 정리합니다.
img-compressor의 LanguageSwitcher 컴포넌트가 pathname 문자열 치환만으로 현재 페이지를 유지한 채 언어를 바꾸는 방법과, 이 방식이 성립하는 전제 조건을 정리합니다.
img-compressor와 media-crop의 아이콘·OG 이미지 코드가 왜 모두 edge 런타임과 인라인 flex 스타일만 쓰는지, ImageResponse의 실제 제약을 기준으로 정리합니다.
이 사이트(Frontend Note) 자체가 Vite로 빌드된 SPA임에도 각 글마다 다른 title, description, JSON-LD가 정적 HTML에 들어 있는 이유를 빌드 스크립트 구조로 설명합니다.
이 사이트의 ScrollToTop 컴포넌트가 다섯 줄 안팎의 코드로 라우트 전환 시 스크롤 위치가 이어지는 문제를 해결하는 방법을 정리합니다.
이 사이트의 scripts/prerender.js가 정적 페이지 목록과 posts 배열을 합쳐 sitemap.xml을 빌드마다 새로 만들고, dist와 public 두 곳에 함께 쓰는 이유를 정리합니다.
media-crop의 MediaCropEditor가 구간 슬라이더와 HH:MM:SS 텍스트 입력 두 가지 조작 방식을 같은 range 상태로 동기화하는 방법을 정리합니다.