자바스크립트 객체 JSON 변환, 에러 원인과 해결법

브라우저 콘솔이나 소스코드에서 복사한 자바스크립트 객체 리터럴을 JSON.parse()에 그대로 넣으면 대부분 SyntaxError가 발생합니다. 원인은 JS 객체 리터럴과 표준 JSON이 서로 다른 문법을 쓰기 때문입니다. 이 글은 그 차이를 항목별로 비교하고, 손으로 직접 변환하는 방법과 에러 메시지 읽는 법까지 정리합니다.
요약 ① 표준 JSON은 모든 키와 문자열 값에 큰따옴표만 허용하고, trailing comma와 주석은 금지합니다. ② JS 객체 리터럴은 따옴표 없는 키, 작은따옴표 문자열, trailing comma를 허용해 겉보기엔 비슷해도 문법이 다릅니다. ③ JSON.parse 에러의 position 숫자는 입력 문자열의 몇 번째 글자(0부터 시작)에서 멈췄는지를 가리킵니다.
언제 이 문제를 만나나요
흔히 겪는 상황은 이렇습니다. 브라우저 개발자도구 콘솔에서 console.log(config)를 실행해 객체를 확인한 뒤, 출력된 값을 그대로 복사해 API 테스트 도구의 요청 본문이나 다른 프로그램의 설정 입력창에 붙여넣습니다.
콘솔 출력은 자바스크립트 값이 화면에 표시된 것이라 키에 따옴표가 없고 문자열은 작은따옴표로 감싸져 있습니다. 이 상태로 JSON.parse()에 넣거나 JSON 전용 입력창에 붙여넣으면 파싱이 실패합니다.
소스코드에 정의된 설정 객체를 그대로 JSON 파일로 옮길 때도 같은 문제가 생깁니다. 눈으로 보기엔 비슷한 텍스트인데 파서는 전혀 다른 문법으로 인식합니다.
도구 없이 직접 변환하는 방법
표준 JSON 문법은 인터넷 표준 RFC 8259가 정의합니다. 핵심 규칙은 이렇습니다.
- 객체의 키는 반드시 큰따옴표로 감싸야 합니다.
- 문자열 값도 큰따옴표만 허용됩니다. 작은따옴표는 문법 오류입니다.
- 배열이나 객체의 마지막 요소 뒤에 쉼표(trailing comma)를 붙일 수 없습니다.
- 주석(
//또는/* */)을 쓸 수 없습니다. - undefined, 함수, Symbol 같은 값은 JSON으로 표현할 수 없습니다.
복사한 텍스트가 실제로 유효한 자바스크립트 문법이라면 — 즉 소스코드에서 그대로 복사한 객체 리터럴이라면 — 브라우저 개발자도구 콘솔에서 직접 변환할 수 있습니다. 순서는 이렇습니다.
콘솔에서 직접 변환하는 순서
- 개발자도구를 엽니다 (Chrome·Edge는 F12, Mac은 Cmd+Option+I).
- 콘솔 탭에서 복사한 내용을 변수에 대입하는 형태로 감쌉니다. 예를 들어
const obj = { name: 'kim', age: 20, };처럼 앞에const obj =를 붙이고 끝에 세미콜론을 둡니다. - Enter를 눌러 변수를 만든 뒤, 이어서
JSON.stringify(obj, null, 2)를 실행합니다. - 콘솔에 출력된 문자열이 표준 JSON입니다. 큰따옴표로 감싸진 키와 문자열, trailing comma 없는 결과를 확인할 수 있습니다.
이 방식은 코드를 실제로 실행하는 것과 같아서, 출처가 불분명한 코드를 콘솔에 붙여넣으면 실행 과정에서 보안 위험이 발생할 수 있습니다. 본인이 직접 남긴 로그이거나 신뢰할 수 있는 소스코드에서 나온 값일 때는 이 위험이 낮아집니다.
에러 위치(position) 읽는 법
반대로 이미 텍스트를 JSON이라 여기고 JSON.parse()에 넣었는데 실패했다면, 에러 메시지의 position 숫자로 원인을 좁힐 수 있습니다. position은 입력 문자열의 처음(0번째)부터 몇 번째 글자에서 파싱이 멈췄는지를 가리킵니다.
예를 들어 {name: 'a'}라는 문자열은 0번째 글자가 {, 1번째 글자가 n입니다. 이 지점에서 에러가 난다면 큰따옴표 없는 키(name) 때문이라는 뜻입니다.
에러 메시지의 정확한 문구는 브라우저·Node.js 버전에 따라 조금씩 다르지만, position 뒤 숫자가 가리키는 의미(0부터 센 글자 위치)는 동일합니다. 숫자만큼 문자열 앞에서부터 세어 보면 어느 글자에서 막혔는지 확인할 수 있습니다.
글자 수가 많거나 중첩된 객체라면 큰따옴표를 하나씩 바꾸고 trailing comma를 지우는 작업이 번거롭고 실수하기 쉽습니다. 저희 도구로 확인하기.
따옴표 없는 키와 작은따옴표 문자열이 섞인 JS 객체 리터럴을 표준 JSON으로 즉시 변환합니다. 설치나 가입 없이 브라우저에서 바로 실행됩니다.

헷갈리기 쉬운 부분
| 항목 | 표준 JSON | JS 객체 리터럴에서 흔한 표기 |
|---|---|---|
| 키 표기 | 큰따옴표 필수 ("name") | 따옴표 없는 식별자 (name) |
| 문자열 값 | 큰따옴표만 허용 ("kim") | 작은따옴표도 허용 ('kim') |
| 마지막 요소 뒤 쉼표 | 금지 | 허용 (트레일링 콤마) |
| 주석 | 불가 | //, /* */ 가능 |
| undefined·함수 값 | 표현 불가 | 값으로 사용 가능 |
이미 실행 중인 코드 안에 자바스크립트 객체 변수가 있다면 이 변환 과정 자체가 필요 없습니다. 그때는 JSON.stringify(obj)만 실행하면 됩니다. 변환이 필요한 경우는 객체가 텍스트(콘솔 출력이나 소스코드 조각)로만 존재해서 실행 가능한 변수가 없을 때입니다.
원본 JS 객체에 undefined나 함수 값을 가진 키가 있으면 JSON으로 변환하는 과정에서 그 키는 결과에서 아예 사라집니다. 에러가 아니라 JSON.stringify의 정상 동작입니다. NaN이나 Infinity 값을 가진 키는 에러 없이 null로 바뀝니다.
작은따옴표를 큰따옴표로 단순 치환(찾아바꾸기)만 하는 방법도 위험합니다. 문자열 값 안에 원래 있던 작은따옴표(아포스트로피)까지 함께 바뀌거나 이스케이프가 어긋나면서 오히려 새로운 문법 오류를 만들 수 있습니다.
정리
- 표준 JSON은 큰따옴표 키·문자열, trailing comma 금지, 주석 금지라는 규칙을 지켜야 합니다.
- JS 객체 리터럴은 따옴표 없는 키, 작은따옴표, trailing comma를 허용해 겉보기엔 비슷해도 파서는 다르게 인식합니다.
- 소스코드에서 그대로 복사한 텍스트라면 브라우저 콘솔에서 변수에 대입한 뒤 JSON.stringify()로 직접 변환할 수 있습니다. 이 방식은 코드를 실행하는 것과 같아서, 출처가 분명한 코드일 때 위험이 낮습니다.
- JSON.parse 에러의 position 숫자는 문자열의 0번째부터 센 글자 위치이므로, 그 위치를 세어보면 어떤 표기 때문에 실패했는지 좁힐 수 있습니다.
- 단순 치환 방식은 문자열 안의 따옴표 때문에 오류를 만들 수 있어, 길거나 중첩된 객체는 문법을 해석해 변환하는 방식에서 오류가 더 적게 발생합니다.
따옴표 없는 키와 작은따옴표 문자열이 섞인 JS 객체 리터럴을 표준 JSON으로 즉시 변환합니다. 설치나 가입 없이 브라우저에서 바로 실행됩니다.
자주 묻는 질문
JSON.parse에서 "Unexpected token" 에러가 나는 이유는 무엇인가요?
입력한 문자열이 표준 JSON 문법을 지키지 않기 때문입니다. 가장 흔한 원인은 키에 큰따옴표가 없거나, 문자열 값이 작은따옴표로 감싸져 있거나, 마지막 요소 뒤에 trailing comma가 남아 있는 경우입니다. 에러 메시지의 position 숫자를 세어보면 정확히 어느 글자에서 멈췄는지 확인할 수 있습니다.
작은따옴표를 큰따옴표로 바꾸기만 하면 되나요?
문자열 값 안에 원래 작은따옴표나 큰따옴표가 포함돼 있으면 단순 치환은 결과를 깨뜨릴 수 있습니다. 문자열 안의 따옴표까지 무분별하게 바뀌거나 이스케이프 처리가 어긋날 수 있기 때문입니다. 문법을 실제로 해석해서 변환하는 방식은 이런 문제가 생기지 않습니다.
이미 갖고 있는 JS 객체를 JSON으로 바꾸려면 이 변환이 꼭 필요한가요?
코드 안에서 실행 중인 JS 객체 변수가 있다면 JSON.stringify(obj)만 실행하면 되고, 별도 변환 과정이 필요 없습니다. 이 변환이 필요한 경우는 객체가 텍스트(콘솔 출력이나 소스코드 조각) 형태로만 있어서 실행 가능한 변수가 없을 때입니다.
JSON에는 왜 주석을 쓸 수 없나요?
표준 JSON 문법(RFC 8259)이 주석을 정의하고 있지 않기 때문입니다. JS 객체 리터럴은 자바스크립트 문법을 그대로 따르므로 //나 /* */ 주석을 쓸 수 있지만, 이를 JSON으로 옮기면 주석 부분이 문법 오류를 일으키므로 제거해야 합니다.
