ziglog

    Search by

    2025년 8월

    August 31, 2025 • ☕️☕️☕️ 15 min read

    💡 Newly Learend


    useEffect vs useLayoutEffect vs useInsertionEffect

    종종 헷갈리는 useEffectuseLayoutEffect의 동작, 거기다 useInsertionEffect까지 나오다니! 😵

    useEffect

    • 주요 특징

      • 브라우저 paint 이후 실행됨.
      • 비동기적으로 실행 → 렌더링 성능에 영향을 주지 않음.
      • 서버 컴포넌트에는 적용되지 않으며, 클라이언트에서만 동작.
    • 용도

      • 데이터 fetching (fetch, axios)
      • 이벤트 리스너 등록/제거
      • 타이머 설정 등 UI 업데이트에 직접 관련 없는 작업
    • 실행 순서

      Copy
      render -> commit -> paint -> useEffect 실행

    useLayoutEffect

    • 주요 특징
      • DOM mutation 후, paint 이전에 동기적으로 실행됨.
      • useEffect보다 빠르게 실행됨 → 레이아웃에 영향을 미칠 수 있는 작업에 적합.
    • 용도
      • DOM 측정 (e.g., getBoundingClientRect())
      • 스크롤 위치 조정
      • 레이아웃 계산 필요 작업
      • 애니메이션 프레임 이전에 동작해야 하는 로직
    • 주의사항
      • 렌더링 차단 → 사용자에게 “깜빡임”이 보일 수 있음
      • 서버 사이드 렌더링 시 경고 발생 (useLayoutEffect는 클라이언트에서만 실행됨)
    • 실행 순서
      Copy
      render -> commit -> useLayoutEffect 실행 -> paint

    useInsertionEffect (React 18 도입)

    • 주요 특징
      • React 렌더링과 DOM 삽입 사이, 가장 먼저 실행됨.
      • CSS-in-JS 라이브러리 (예: Emotion, styled-components)가 스타일을 DOM에 삽입하기 위해 사용.
    • 용도
      • 스타일이 레이아웃 계산 이전에 DOM에 들어가야 하는 경우 (깜빡임 방지)
      • 일반 로직에서는 거의 사용하지 않음 (라이브러리 제작자 전용)
    • 실행 순서
      Copy
      render -> useInsertionEffect 실행 -> commit -> useLayoutEffect -> paint -> useEffect

    실행 순서 요약 (클라이언트 기준)

    Copy
    1. render
    2. useInsertionEffect (가장 빠름)
    3. commit (DOM 반영)
    4. useLayoutEffect (동기)
    5. paint
    6. useEffect (비동기)

    RPC

    RPC는 ‘Remote Procedure Call’의 약자로, 원격 프로시저 호출을 의미한다. 즉, 로컬에서 실행되는 것처럼 다른 컴퓨터나 프로세스에서 함수를 호출할 수 있도록 하는 기술이다.

    RPC를 이용하면 프로그래머는 함수 또는 프로시저가 실행 프로그램이 존재하는 로컬 위치에 있든, 원격 위치에 있든 상관없이 동일한 기능을 수행할 수 있다.

    다만, RPC는 호출의 실행과 반환 시간이 보장되지 않는다. (네트워크 구간을 통하여 RPC 통신을 하는 경우, 치명적 문제가 발생할 수 있다.) 또, 보안이 보장되지 않을 수 있다.

    RPC vs REST

    • 원격 프로시저 호출(RPC)
      • 함수로 호출
      • 클라이언트는 서버에서 원격 함수(메서드 또는 프로시저라고도 함)를 직접적으로 호출한다. 일반적으로 직접 호출 중에 하나 이상의 데이터 값이 서버에 전달된다.
    • REST 클라이언트
      • URL로 호출
      • 서버에 특정 서버 리소스에 대한 작업을 수행할 것을 요청하나다. 작업은 생성, 읽기, 업데이트 및 삭제(CRUD)로만 제한되며 HTTP 동사 또는 HTTP 메서드로 전달된다.

    Refs

    yarn resolutions

    yarn의 resolutions 필드는 프로젝트에서 특정 패키지 버전을 강제로 지정하고 싶을 때 사용하는 기능이다. 주로 의존성 트리 내의 하위 패키지들에서 사용하는 버전을 강제로 고정할 때 사용된다. 특히 여러 라이브러리가 동일한 하위 의존성을 사용하는데 서로 다른 버전을 요구할 때 버전 충돌 문제를 해결하는 데 유용하다.

    🎯 핵심 차이

    항목 dependencies resolutions
    적용 대상 내 프로젝트의 직접 의존성 내 프로젝트의 의존성의 의존성 (transitive dependency)
    선언 위치 package.json > dependencies package.json > resolutions
    목적 내가 직접 사용하는 패키지를 명시함 하위 의존성 버전을 강제로 오버라이드

    Next.js에서 URL query param vs [id] 경로

    Next.js의 PDP(상세 페이지) 링크를 만들 때, /products?id=123과 같은 URL query param을 이용하는 방식과 /products/123과 같은 [id] 경로의 슬러그 방식이 있다. 둘 중에 무엇을 선택해야 할지 고민된다?

    답은, PDP는 [id] 같은 동적 세그먼트 경로를 쓰는 것이 정석이라고 한다. SSR은 [id] 경로에서도 완벽히 동작하기 때문이다. SSR/ISR이 필요해서 굳이 ?id=123과 같은 쿼리 파라미터로 만들 필요는 없습니다.

    쿼리 파라미터는 리소스의 “식별자”가 아니라 “상태”를 표현할 때만 사용하는 것이 좋다. (예: 탭, 정렬, 트래킹 등)

    왜 [id] 경로가 더 적합한가

    • SEO/링크 가독성: 리소스 아이덴티티가 URL path에 드러나 canonical 관리가 용이
    • 캐싱/프리패치: 경로 단위 캐싱, Link 프리패치, 세그먼트별 loading/error 구성에 유리
    • ISR/온디맨드 무효화: revalidate, fetch의 tags로 상품별 캐시 무효화가 직관적
    • 리라이트/미들웨어/i18n: 경로 매칭이 명확

    언제 쿼리 파라미터를 쓰나

    • UI 상태?tab=review&sort=latest 등 리소스 정체성에 영향 없는 상태
    • 필터/트래킹: A/B, 캠페인, 뷰 모드 등

    Canonical 관리

    Canonical 관리란, 여러 URL로 같은(또는 매우 유사한) 콘텐츠가 노출될 때 검색엔진에 “이 페이지의 대표 URL은 이거야”라고 알려 중복 평가·순위 분산을 막는 작업이다.

    동일한 PDP가 ?utm=...?sort=..., 대소문자/슬래시 차이 등으로 여러 URL에 노출되면, 검색 랭킹이 분산되고, 중복 컨텐츠 페널티의 위험성이 있다. 또한 크롤링 예산이 낭비된다.

    이때 Canonical을 지정하면 대표 URL로 신호를 모아 SEO 효율이 좋아집니다.

    Canonical 관리의 원칙은 다음과 같다.

    • 리소스의 정체성(URL path)/products/[id] 같은 깨끗한 경로를 대표로 한다.
    • 상태성(query)?tab=review?utm=...?sort=... 등은 canonical에 포함하지 않는다.
    • PDP는 보통 “자기 자신”을 canonical로, 필터/정렬/트래킹 파라미터가 붙어도 동일 canonical을 유지한다.

    View Transition API

    서로 다른 웹뷰들 간 자연스러운 애니메이션 전환 효과를 제공한다.

    Refs

    yarn workspaces focus

    단일 워크스페이스의 의존성만 설치할 수 있다.

    Ref https://yarnpkg.com/cli/workspaces/focus

    📍 Monthly Pinned


    GSAP

    자바스크립트로 요란한 애니메이션을 만들 수 있다.

    요즘 이런 정신 쏙 빼놓는 애니메이션을 섬세하게 구현하는 애들이 많이 나오는 것 같다.

    근데 자기들도 너무 요란해서 홈페이지 성능조차 느린 게 충격

    Ref https://gsap.com/resources/position-parameter/

    GPT 5 출시!

    가장 스마트하고 빠르고 어쩌구… 에 덧붙여

    그동안 GPT가 활약하지 못했던 코딩 분야에도 힘 좀 썼다는데

    잘 모르겠음.

    일단 무지하게 느려서 도무지 기다릴 수가 없다. (Cursor 에이전트로 사용했을 때)

    Ref https://openai.com/ko-KR/gpt-5/

    프론트엔드 개발자를 위한 5가지 스크롤 복구 시나리오와 실전 코드 팁

    정적인 데이터 뿐 아니라 동적인 데이터에서도 스크롤 위치를 복구하는 법,

    그리고 스켈레톤으로 CLS를 줄이는 법까지 고민한다.

    추가로 react query의 캐시에 스크롤 정보를 저장한다니! 이건 🍯팁

    올리브영 잘 쓰고 있다.

    Ref https://oliveyoung.tech/2025-07-30/scroll-restoration/

    모든 ToDo 앱을 써봤지만 결국 .txt 파일로 돌아왔어요

    Notion, Todoist, Things 3 등 수많은 앱을 거쳤지만 결국 todo.txt라는 단순한 텍스트 파일로 회귀했다.

    앱은 구독료, 동기화 오류, 과도한 기능 관리 등으로 오히려 생산성을 저하시켰다.

    현재는 날짜별로 할 일을 적고, 진행 중 메모를 추가하는 단일 텍스트 파일 시스템을 사용한다.

    생산성의 핵심은 도구가 아니라 기록·확인·실행이라는 단순한 프로세스!

    나도..^^ (Akiflow 구독료 낭비하며 그냥 Microsoft Todo 앱 쓰는 사람)

    Ref https://www.al3rez.com/todo-txt-journey

    Event Tracker

    보안적인 문제만 없다면 많은 서비스에서 참고해볼만 한 툴

    Ref https://github.com/offlegacy/event-tracker

    리액트 리렌더링 문제, FGR(Fine Grained Reactivity)로 해결하기

    리액트의 동작 원리에 대한 깊은 탐구를 바탕으로 코드를 짤 줄 알았더니,

    사실 Legend State라는 (작명 실화…) 상태 관리 라이브러리를 소개하고 있다.

    FGR 객체는 이런 내부 구조를 가지고 있다.

    Copy
    const observable = {
    	_value: "지그",
    	_handlers: [], // 이벤트 핸들러들이 저장되는 배열
    
    	get() {
    		// get할 때: 현재 실행 중인 effect를 핸들러로 등록
    		if (currentTracker) {
    			this._handlers.push(currentTracker);
    		}
    		return this._value;
    	},
    
    	set(newValue) {
    		this._value = newValue;
    		// set할 때: 등록된 이벤트 핸들러들을 호출
    		this._handlers.forEach(handler => handler());
    	}
    }

    프록시 같은 구조. get()을 호출하면 이벤트 핸들러가 등록되고, set()을 호출하면 그 핸들러들이 실행된다.

    Legend State는 use$라는 훅을 사용해서(훅 이름도 실화…) FGR을 리액트와 연결하고, observable 객체의 값이 바뀌면 해당하는 컴포넌트만 리렌더링한다.

    Copy
    import { observable, use$ } from '@legendapp/state';
    
    const user = observable({
    	name: "지그",
    	age: 20,
    });
    
    function UserProfile() {
    	const name = use$(() => user.name.get());
    	const age = use$(() => user.age.get());
    
    	return <div>{name} ({age}세)</div>;
    }

    리액트의 고질적인 문제였던 상태 업데이트와 리렌더링 문제는 어느 정도 해결해주지만, 리액트의 한계 상 완벽하게 줄여줄 순 없다! 😵 (이 정도면 리액트를 쓰는 것 자체가 문제라는 생각도 슬 드는 중)

    Ref https://yozm.wishket.com/magazine/detail/3294/

    답답하지만 착한 동료 vs 성격 나쁘지만 잘하는 동료

    성격 나쁘지만 실력만 좋은 동료는, 함께 하는 회사 생활에서 진정으로 잘하는 것이 아니라는 생각에 공감한다.

    인성도 예의도 지능으로 평가 받는 이 시점, 솔직이라는 이름으로 자신의 무례를 포장하고 있진 않은지?

    소신 발언: ‘래디컬 캔도어’는 잘못됐다.

    Ref https://yozm.wishket.com/magazine/detail/3295/

    토스의 접근성 문서 A11y Fundamentals 공개

    토스가 참 이런 건 잘한다. (남의 회사인 양)

    문서 링크는 요기

    1. 구조 명확하게 만들기
    2. 의미 정확히 전달하기
    3. 예상 가능한 동작 만들기
    4. 시각 정보 보완하기

    당연하지만 그래서 더 중요한 네 가지 꼭지로 A11y를 소개하고 있다.

    Ref https://toss.tech/article/A11y_Fundamentals

    Vibe 코딩은 버스 팩터를 0으로 만든다

    소프트웨어 개발에서 Bus Factor는 특정 지식 보유자가 몇 명이나 있어야 프로젝트 유지가 가능한지를 나타내는 개념으로, 기존에는 최악의 경우 값이 1이었다. 그러나 ChatGPT 공개 이후, 생성형 AI가 대중적으로 채택되면서 많은 이들이 지식을 직접 보존하지 않고 AI에 의존하며, 사실상 버스 팩터 0의 상황이 발생하고 있다.

    점점 더 많은 개발자가 LLM이 생성한 코드와 기능을 그대로 사용하며, 코드베이스를 이해하려는 노력을 포기하고 “바이브 코딩(vibe coding)“으로 전환하고 있다. 이로 인해 버그 수정, 보안 패치, 기능 확장 시, 누구도 코드가 왜 그렇게 작성되었는지 모르는 상황에 직면할 수 있다.

    이는 소프트웨어 신뢰성과 보안에 심각한 위험을 초래하며, AI가 완벽한 코드를 완벽히 생성하는 날이 오기 전까지는 근본적 한계가 존재한다.

    나잖아… 하지만 반성하고 집에서는 코딩 에이전트 안 쓰는 중. 참 고전 좋아하고, 아날로그 좋아한다. 어째서 개발자가 됐을까?

    Ref https://www.mindflash.org/coding/ai/ai-and-the-bus-factor-of-0-1608

    프롬프트 엔지니어링의 진화, 컨텍스트 엔지니어링이란?

    단순히 프롬프트를 잘 작성하는 수준을 넘어서, LLM이 태스크를 수행하는 데 필요한 ‘정보 환경’과 ‘전체적인 시스템의 맥락’을 설계하는 종합적인 접근 방식

    즉, LLM의 성능을 극대화하기 위해 다양한 외부 데이터와 도구를 통합하고 활용하는 것까지 포함하는, 훨씬 더 포괄적인 개념

    Ref https://yozm.wishket.com/magazine/detail/3316/

    “삭제 기한 늘리고, 발신자 감추고” UX 관점에서 본 카카오톡 메시지 삭제 업데이트

    메시지 삭제 기능은 기한을 너무 짧게 설정할 경우, 사용자가 실수를 알아차렸을 때엔 이미 메시지를 삭제할 수 없는 불편함을 초래하거나, 그렇다고 너무 길게 설정하면 대화 기록을 왜곡할 수 있어 대화의 신뢰성이 떨어지는 양날의 검이기 때문입니다. 이런 문제로 인해 해외 주요 메신저 서비스 중 메시지 삭제를 지원하는 일부는 대화의 신뢰성 보호를 위해 삭제 기한을 제한하는 방식을 택하고 있습니다.

    그냥 사용자들이 징징대서 UX 바꿔준 줄 알았는데, 메신저 UX에도 이런 깊은 뜻이 있었다니.

    메시지를 누가 삭제했는지 보이지 않도록 개선한 것은 몰랐는데, 이건 확실히 좋아보인다.

    Ref https://ditoday.com/삭제-기한-늘리고-발신자-감추고-ux-관점에서-본-카/

    웹 메모 - 웹사이트에서 즉시 메모하기

    간단하지만 많은 이들에게 필요할 것 같은 도구!

    Ref https://chromewebstore.google.com/detail/웹-메모-웹사이트에서-즉시-메모하기/eaiojpmgklfngpjddhoalgcpkepgkclh

    AI의 친절은 때로 사람을 병들게 한다?

    AI 챗봇이 사용자의 정신질환을 야기하거나 악화시킬 가능성. 🤕

    나도 이제 가끔 상담을 하는 지경에 이르렀는데, 너무 과하면 안될 것 같긴 해.

    Ref https://pxd.co.kr/ko/insights/pov-ai-bad-ux-sick-person

    웹에서 화면이 전환될 때 벌어지는 일을 아시나요? 🤯

    웹에서 화면이 전환될 때, DOM 생명주기를 가로채서 애니메이션을 부드럽게 만든다.

    요즘 스프링 물리 기반 애니메이션 엔진을 사용하는 도구도 참 많이 보인다. 물리학을 공부할걸 - 늦지 않았을지도?

    Ref https://velog.io/@k-svelte-master/do-you-know-web-view-transition

    🧺 Wrap up


    8월엔 갑작스럽게 너무 많은 일이 있었고

    조금 외롭기도 했고, 그 반대로 정신없이 몰아치기도 했다.

    무더운 날씨 때문도 아닌데 화도 짜증도 많아지다가 갑자기 인생 노잼 시기가 찾아온 것 같지만

    다음 달부터는 정말 전쟁일 수도 있으니 정신 차리기!


    Relative Posts:

    2025년 7월

    August 2, 2025

    zigsong

    지그의 개발 블로그

    RotateLinkImg-iconRotateLinkImg-iconRotateLinkImg-icon