From 9c5b1693cab21218c1ab90ea6e975546e90629c5 Mon Sep 17 00:00:00 2001 From: Woohyuck Jeong Date: Mon, 19 Oct 2026 15:36:44 +0900 Subject: [PATCH] =?UTF-8?q?fix:=20=EC=88=AB=EC=9E=90=EA=B0=80=20=EB=93=A0?= =?UTF-8?q?=20=EC=97=AD=20=EC=9D=B4=EB=A6=84=EC=9D=98=20=EC=A2=8C=ED=91=9C?= =?UTF-8?q?=20=EB=B3=80=ED=99=98=20=EC=8B=A4=ED=8C=A8=20=EC=88=98=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/utils/geocode.ts | 3 ++- tests/utils/geocode-fallback.test.ts | 23 +++++++++++++++++++++++ 2 files changed, 25 insertions(+), 1 deletion(-) diff --git a/src/utils/geocode.ts b/src/utils/geocode.ts index 9dcd2869..968f1d58 100644 --- a/src/utils/geocode.ts +++ b/src/utils/geocode.ts @@ -173,7 +173,8 @@ export async function geocodeLocation( // 대체 공급자도 최초 요청의 남은 시간만 사용합니다. const deadline = Date.now() + (options.timeout ?? options.timeoutMs ?? 10000); const remaining = () => deadline - Date.now(); - const isAddress = /(?:로|길|동|읍|면|리)\s*\d/u.test(keyword); + // '을지로3가역'처럼 숫자가 든 역 이름은 주소가 아니라 장소로 검색합니다. + const isAddress = !keyword.endsWith('역') && /(?:로|길|동|읍|면|리)\s*\d/u.test(keyword); let documents: KakaoDocument[] = []; const kakaoTimeout = remaining(); if (options.kakaoRestApiKey?.trim() && kakaoTimeout > 0) { diff --git a/tests/utils/geocode-fallback.test.ts b/tests/utils/geocode-fallback.test.ts index c4c98639..df17fa54 100644 --- a/tests/utils/geocode-fallback.test.ts +++ b/tests/utils/geocode-fallback.test.ts @@ -166,6 +166,29 @@ describe('정확한 주소 fallback', () => { '/v1/search/local.json', ]); }); + it.each(['을지로3가역', '종로3가역'])('숫자가 든 역 이름은 장소로 검색한다: %s', async (query) => { + const fetchImpl = responses( + json({ + documents: [ + { + place_name: `${query} 1호선`, + address_name: '서울 종로구 예시동 10', + road_address_name: '서울 종로구 예시로 지하 129', + x: '126.99', + y: '37.57', + }, + ], + }), + ); + expect(await geocodeLocation(query, { kakaoRestApiKey: 'test-kakao', fetchImpl })).toEqual({ + latitude: 37.57, + longitude: 126.99, + formattedAddress: '서울 종로구 예시로 지하 129', + }); + expect(new URL(String(fetchImpl.mock.calls[0][0])).pathname).toBe( + '/v2/local/search/keyword.json', + ); + }); it('빈 입력과 환경키 없는 입력은 요청하지 않는다', async () => { expect(await geocodeLocation(' ')).toBeNull(); expect(await geocodeLocation('예시역')).toBeNull();