# 재생 중 데이터 폴더 교체 시 "media could not be loaded" 수정

## 증상
재생 중에 다른 데이터 폴더를 드래그&드롭하면 지오 데이터(측점/POI/스테이션바)는 정상 로드되는데
**영상만** 상단에 "The media could not be loaded …" 에러가 뜨고 검은 화면.

## 원인 — objectURL 조기 해제 race
[useVideoPlayer.loadLocalFile](../../client/src/hooks/useVideoPlayer.ts#L72)이 blob URL 해제를 `player.one('emptied', …)` 이벤트에 의존.
소스 교체 시:
1. 첫 로드 → `.one('emptied', revoke url1)` 등록
2. 드롭 → `createObjectURL`로 **url2** 생성 → `player.src(url2)` (이때 `'emptied'`가 **비동기 예약**) → 직후 `.one('emptied', revoke url2)` 등록
3. 예약된 `'emptied'` 발화 → url1·url2 핸들러가 **동시 실행** → 방금 만든 **url2까지 revoke** → 소스 무효 → 로드 실패

첫 로드는 이전 'emptied'가 없어 정상, **교체 시에만** 재현.

## 수정 — ref 기반 결정적 해제
- `objectUrlRef`로 현재 blob URL 추적, `'emptied'` 핸들러 제거
- `loadLocalFile`: 새 `src` 설정 후 **이전 URL만** revoke (새 URL은 보존)
- `loadServerStream`: 로컬→서버 전환 시 이전 blob URL revoke
- 언마운트(dispose) cleanup: 남은 blob URL revoke
- 부가: 교체 직전 재생 중이었으면(=드롭 교체) 새 영상도 `player.play()`로 이어서 재생
  (drop은 사용자 제스처라 자동재생 정책 통과. 최초 로드는 `prevUrl` 없음 → 기존처럼 자동재생 안 함)

## 파일
- [client/src/hooks/useVideoPlayer.ts](../../client/src/hooks/useVideoPlayer.ts)

## 검증
- `tsc --noEmit`: 통과 / `npm run build`: 성공 (node v20.20.2)
- 재현/회귀: 재생 중 폴더 드롭 → 새 영상 로드+재생, 콘솔 에러 없음(코드 경로상). 실브라우저 확인은 하드 새로고침 후 폴더 재드롭 필요.

## 반영 방법
- client만 변경 → **하드 새로고침(Ctrl+Shift+R)** 후 폴더 드롭으로 확인. PM2 재시작 불필요.

---

**소요 시간**: 12분
**Context 사용량**: input 198k / output 26k tokens
