Skip to content

refactor: 화면 정책을 DOM 없이 시험할 수 있는 순수 함수로 분리 #66

Description

@lee-eojin

트랙 B1. 표현 계층. 후속 작업 B2와 B4의 선행이다.

지금 무엇이 문제인가

boardFrame()이 정류장 필터, 차량 필터, 예보 계산을 한 번에 하고 세 개의 원본 배열을
돌려준다.

interface BoardFrame {
  stops: DisplayStop[];
  vehicles: DisplayVehicle[];
  forecastsByVehicle: Map<DisplayVehicle, Map<number, SeatForecast>>;
}

정류장 하나가 화면에서 어떻게 보여야 하는지는 어디에도 안 적혀 있다. renderAxis가 행을
만들면서 그때그때 결정한다. 미정차 지점인지(isNonBoardingStop), 예보가 붙는지, 안 붙으면
과거 확률을 보여줄지, 내 정류장인지를 175줄짜리 함수 안에서 판단한다. renderConclusion
같은 판단을 자기 방식으로 다시 한다.

결과가 두 가지다. 같은 정류장을 두 곳이 다르게 해석할 수 있고, 어느 쪽도 DOM 없이는
시험할 수 없다. 지금 packages/domain에는 시험이 있지만 화면 계층에는 하나도 없다.

무엇을 하나

팀 프론트엔드의 src/pages/verdict-board/displayPolicy.ts(114줄)가 쓰는 방식을 가져온다.
정류장 하나를 화면 모델로 바꾸는 순수 함수를 두고, 렌더는 그 모델만 읽는다.

export type StopView =
  | { kind: 'boarding'; sequence: number; name: string; verdict: ...; arrival: ... }
  | { kind: 'passThrough'; sequence: number; name: string }
  | { kind: 'noForecast'; sequence: number; name: string; probability: ... };

팀 쪽은 세 갈래인데 프로토타입은 여기에 내 정류장 표시, 회차 지점, 대기 범위가 더 붙는다.
갈래를 몇 개로 둘지는 구현하면서 정한다. 규칙은 하나다. 화면 갈래를 정하는 판단이 전부
이 함수 안에 있고 렌더 함수에는 조건문이 안 남는다.

끝났다고 보는 기준

  • 정류장 목록을 화면 모델 배열로 바꾸는 함수가 생긴다
  • renderAxisrenderConclusion이 같은 모델을 읽는다
  • 이 함수의 시험이 DOM 없이 node --test로 돈다
  • 미정차 지점, 회차 지점, 내 정류장, 예보 없음의 네 경우가 시험으로 덮인다

참고

원본은 2026-salmonbus/frontend/src/pages/verdict-board/displayPolicy.ts.

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    enhancementNew feature or request

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions