# </> Htmx – The Fetch()ening

> Clean Markdown view of GeekNews topic #24132. Use the original source for factual precision when an external source URL is present.

## Metadata

- GeekNews HTML: [https://news.hada.io/topic?id=24132](https://news.hada.io/topic?id=24132)
- GeekNews Markdown: [https://news.hada.io/topic/24132.md](https://news.hada.io/topic/24132.md)
- Type: GN+
- Author: [neo](https://news.hada.io/@neo)
- Published: 2025-11-04T13:32:59+09:00
- Updated: 2025-11-04T13:32:59+09:00
- Original source: [htmx.org](https://htmx.org/essays/the-fetchening/)
- Points: 2
- Comments: 1

## Topic Body

- **htmx 4.0**은 기존 `XMLHttpRequest` 기반 구조를 **`fetch()` 중심 비동기 구조**로 전면 교체하는 대규모 리빌드 버전  
- **속성 상속 방식**이 암시적에서 **`:inherited` 명시적 선언**으로 변경되어 코드 명확성과 유지보수성 향상  
- **히스토리 캐시**는 로컬 스냅샷 저장 대신 **네트워크 요청 기반 복원 방식**으로 단순화되어 안정성 강화  
- **스트리밍 응답, SSE, DOM morphing, &lt;partial&gt; 태그, View Transition 큐** 등 다양한 신규 기능이 코어에 통합  
- 장기적으로 **코드베이스 단순화와 확장성 개선**, 기존 2.0 사용자도 지속 지원 예정  

---

### htmx 4.0 개요
- htmx 4.0은 기존 구조를 전면 재작성하며, **fixi.js 개발 경험**과 **5년간의 유지보수 교훈**을 반영  
- 주요 변화는 `fetch()` 전환, 속성 상속 명시화, 히스토리 캐시 단순화의 **3가지 핵심 변경점**으로 요약  

### The fetch()ening
- `XMLHttpRequest`를 **`fetch()`** 로 교체하여 Ajax 인프라를 현대화  
  - 대부분의 사용 사례에는 큰 영향이 없지만, **이벤트 모델**은 `fetch()`의 비동기 특성에 따라 변경  
- 이 전환은 코드 단순화와 향후 기능 확장을 위한 기반 제공  

### 명시적 속성 상속
- 기존 암시적 상속 대신 **`:inherited` 수정자**를 사용해 명시적으로 선언  
  - 예시:  
    ```html
    &lt;div hx-target:inherited="#output"&gt;
        &lt;button hx-post="/up"&gt;Like&lt;/button&gt;
        &lt;button hx-post="/down"&gt;Dislike&lt;/button&gt;
    &lt;/div&gt;
    ```
  - `hx-target`이 명시되지 않으면 하위 요소는 상속되지 않음  
- 대부분의 사용자에게 **가장 큰 업그레이드 변경점**  

### 히스토리 캐시 단순화
- htmx 2.0의 **로컬 DOM 스냅샷 캐시**는 서드파티 수정, 숨겨진 상태 등으로 인해 불안정  
- 4.0에서는 **네트워크 요청을 통한 복원 방식**으로 변경  
  - 캐시 확장은 선택적(opt-in)으로 제공  
- 코드베이스 단순화 및 **기본 동작의 신뢰성 향상**  

### 유지되는 요소
- `hx-get`, `hx-post`, `hx-target`, `hx-boost`, `hx-swap`, `hx-trigger` 등 **핵심 API는 동일**  
- `:inherited` 추가 외 대부분의 프로젝트는 **기존 코드 그대로 작동 가능**  
- 장기 유지보수성과 안정성 강화  

### 업그레이드 정책
- 2.0 사용자는 **업그레이드 프로젝트 필요**, 그러나 2.0은 **영구 지원**  
- 4.0은 **2.x와 병행 배포**, `latest` 전환은 **2027년 초 예상**  
- 2.0 동작을 복원하는 **확장(extension)** 제공 예정  

### 신규 기능 요약

#### 스트리밍 응답 및 SSE 통합
- `fetch()`의 **Readable Streams** 지원을 활용해 **부분적 DOM 교체** 가능  
- SSE(Server Sent Events)가 **핵심 기능으로 재통합**, 점진적 콘텐츠 갱신 지원  

#### Morphing Swap
- **Idiomorph 알고리듬**을 기반으로 DOM 병합 시 **노드 보존·삭제 판단 개선**  
- `morphInner`, `morphOuter` 스왑이 코어에 포함  

#### `&lt;partial&gt;` 태그 지원
- 기존 **Out-of-band swap**의 복잡한 문법을 단순화  
- `&lt;partial&gt;`은 템플릿 요소로, `hx-target`, `hx-swap` 등 표준 속성 사용 가능  
- Out-of-band swap은 **id 기반 단순 교체**로 회귀  

#### View Transition 개선
- **전환 큐(queue)** 도입으로 시각적 충돌 방지  
- CSS 전환은 기존 방식 유지, **비동기 런타임으로 단순화**  
- 기본 활성화 여부는 미정  

#### 이벤트 순서 안정화
- `fetch()` 기반 비동기 구조로 **이벤트 순서 보장 용이**  
- 새로운 이벤트 명명 규칙 도입:  
  `htmx:&lt;phase&gt;:&lt;system&gt;[:&lt;optional-sub-action&gt;]`  
  - 예: `htmx:before:request`  

#### 확장성 강화
- `async` 기반으로 **사전 요청(preload)** 및 **낙관적 업데이트(optimistic update)** 확장 제공  
- 요청/응답/스왑 사이클을 **확장 개발자에게 개방**, `fetch()` 구현 교체 가능  
- **핵(hack)** 없이 원하는 동작 구현 가능  

#### `hx-on` 개선
- 표준화된 구문 `hx-on:&lt;event name&gt;` 채택  
- 비동기 API 지원으로 **간단한 DOM 스크립팅 가능**  
  ```html
  <button hx-post="/like"
          hx-on:htmx:after:swap="await timeout('3s'); ctx.newContent[0].remove()">
      Get A Response Then Remove It 3 Seconds Later
  &lt;/button&gt;
  ```
- `eval()` 비활성화 환경에서도 동작하나 일부 기능 제한  

### 전체 방향
- htmx 4.0은 **2.0과 유사한 사용감**을 유지하면서 **버그 감소와 기능 향상**을 목표  
- 코드 단순화, 명시적 구조, 비동기 기반 확장성으로 **보다 안정적이고 현대적인 htmx 제공**  

### 개발 일정
- **알파 버전(`htmx@4.0.0-alpha1`)** 현재 공개  
- **정식 4.0.0 릴리스**는 2026년 초~중반 예정  
- **2027년 초**에 `latest`로 전환 예정  
- 개발 진행 상황은 GitHub `four` 브랜치 및 [four.htmx.org](https://four.htmx.org)에서 확인 가능  

---

## Comments



### Comment 45854

- Author: neo
- Created: 2025-11-04T13:33:00+09:00
- Points: 1

###### [Hacker News 의견](https://news.ycombinator.com/item?id=45803358) 
- 결국 마음을 바꿔서 **htmx의 새로운 메이저 버전**을 내기로 했음  
  단, “3.0은 없을 것”이라는 약속을 지키기 위해 다음 버전은 **htmx 4.0**으로 명명함  
  기술적으로는 맞는 표현이라며 농담 섞인 반응을 보임
  - 재밌는 해결책이지만, 예전에 사라진 **PHP 6**처럼 사용자 혼란을 줄 수도 있음  
    차라리 솔직히 3.0으로 내는 게 낫지 않았을까 생각함
  - 그냥 바로 **htmx 4.1**로 가서 “xhtmx 1.0”을 만들자는 농담을 던짐
  - [Leisure Suit Larry 4: The Missing Floppies](https://en.wikipedia.org/wiki/Leisure_Suit_Larry#Leisure_Suit_Larry_4:_The_Missing_Floppies) 같은 느낌이 난다고 함
  - “3번째 버전은 없다”고 말하지 않은 게 다행이라며 표현의 여지를 언급함

- **htmx 2.0**은 영구적으로 지원될 예정이라, 업그레이드 압박이 전혀 없다고 함  
  요즘처럼 **API 변경이 잦은 시대**에 이런 접근은 칭찬할 만함

- 안정성을 추구하는 사람들이 종종 잘못된 교훈을 얻는다고 느낌  
  Python 3.0처럼 한 번에 큰 변화를 몰아넣기보다, **점진적 릴리스 전략**이 낫다고 주장함  
  예를 들어 2.1, 4.0, 5.0 등으로 나누어 변경을 도입하면 관리가 훨씬 쉬움  
  Django처럼 여러 버전에 걸쳐 **호환 단계를 유지하는 방식**을 추천함

- `hx-target` 속성의 설명이 헷갈린다고 느낌  
  “inherited”보다는 “**inheritable**” 혹은 “inherit”이 더 자연스러워 보임
  - 자신은 “자식이 상속받는다”는 의미로 읽었다며, “pass-down” 같은 표현이 더 명확할 수도 있다고 제안함
  - “inherited”는 잘못된 단어라며 “inherit”이 짧고 좋다고 함  
    농담으로 “bequeath”도 가능하다고 덧붙임
  - 여러 표현을 고민 중이라며 의견을 수용할 의향이 있다고 함
  - “heritable”이나 “cascade” 같은 대안도 제시됨

- HTMX의 아이디어와 **Hypermedia 철학**은 멋지다고 생각함  
  SPA 환경에서 벗어나 Datastar를 선택했는데, 학습 투자 대비 **확장성**이 더 크다고 느낌  
  서버에서 브라우저로 **신호를 직접 푸시**하면서 폴링 코드를 제거했고, 복잡도가 크게 줄었음  
  Alpine.js 의존성도 없애서 코드가 단순해졌고, **스트리밍 기반 전체 뷰 갱신**도 압축 덕분에 효율적으로 작동함  
  SPA에서 왔다면 Datastar와 HTMX 둘 다 시도해보길 권함

- `fetch()`로 전환해 **Readable Stream**을 활용하는 부분이 흥미로움  
  HTMX를 많이 써봤지만, Datastar의 **SSE 기반 스트리밍**이 더 매력적이라 요즘은 그쪽을 선호함

- HTMX의 발전이 반갑다고 하면서도, Datastar가 더 **표준 친화적이고 유연한 API**를 제공한다고 느낌  
  작은 패키지에 Fetch, SSE, declarative signals, DOM morphing 등 다양한 기능이 들어있다고 함  
  그래서 “왜 HTMX를 써야 하지?”라는 의문을 던짐
  - Datastar Pro는 **오픈소스가 아니기 때문에** 신뢰성 리스크가 있다고 지적함
  - Datastar 제작자가 예전에 HTMX에 이런 기능을 넣으려 했다는 **아이러니**를 언급함
  - HTMX는 **요청/응답 패러다임**에 최적화된 단순한 인터페이스가 강점이라고 설명함  
    Datastar는 이벤트 스트림 중심이라 실시간 대시보드나 게임에는 적합하지만, 대부분의 웹앱은 HTMX의 단순함이 더 유리함  
    관련 참고: [Datastar 에세이](https://data-star.dev/essays/v1_and_beyond), [Less HTMX is More](https://unplannedobsolescence.com/blog/less-htmx-is-more/)
  - HTMX는 브라우저의 **URL 히스토리 관리**를 쉽게 지원하지만, Datastar는 이 기능을 유료(Pro)로 제한했다고 함

- “완벽해서 더 이상 메이저 버전이 없다”던 말에서 결국 **진화의 필요성**을 인정한 점을 꼬집음  
  “이제 이벤트 네이밍 표준을 바꾼다”는 부분을 인용하며, 자바스크립트를 피하려는 시도로 풍자함
  - “결국 자바스크립트를 안 쓰려다 **커스텀 문법**을 JS로 해석하게 됐다”며 비꼼  
    그래도 HTML로 의도를 표현할 수 있다는 점은 인정함
  - “이번이 진짜 마지막 버전일 것”이라는 농담을 던짐
  - “그래도 자바스크립트 직접 쓰는 것보단 낫다”고 긍정적으로 받아들임
  - “저자의 생각이 바뀐 게 뭐가 문제냐”며 비판적인 어조를 지적함

- 글이 매우 명확하고 **API 설계 철학**을 잘 배울 수 있었다고 함

- `fetch`와 HTMX를 함께 쓰기 위해 **xhr-fetch-proxy**를 만들었는데,  
  이번 변경으로 더 많은 가능성이 열릴 것 같다고 함  
  [프로젝트 링크](https://github.com/logankeenan/xhr-fetch-proxy)
  - 4.0에서는 요청 사이클이 완전히 열려 있어서, 요청마다 **fetch 구현을 교체**할 수 있다고 함  
    이 아이디어는 fixi.js에서 배웠다고 덧붙임
