Làm cách nào để thoát các ký tự đặc biệt trong việc xây dựng chuỗi JSON?


200

Đây là chuỗi của tôi

{
    'user': {
        'name': 'abc',
        'fx': {
            'message': {
                'color': 'red'
            },
            'user': {
                'color': 'blue'
            }
        }
    },
    'timestamp': '2013-10-04T08: 10: 41+0100',
    'message': 'I'mABC..',
    'nanotime': '19993363098581330'
}    

Ở đây, thông báo chứa một dấu ngoặc kép, giống như dấu ngoặc kép được sử dụng trong JSON. Những gì tôi làm là điền vào một chuỗi từ đầu vào của người dùng như tin nhắn. Vì vậy, tôi cần phải thoát khỏi những tình huống đặc biệt phá vỡ mã. Nhưng ngoài việc thay thế chuỗi, có cách nào để làm cho chúng thoát nhưng vẫn cho phép HTML xử lý chúng trở lại đúng thông điệp không?


45
JSON chỉ sử dụng dấu ngoặc kép, không phải dấu ngoặc đơn, xem json.org
Niels Bom

4
RFC 4627 tuyên bố rằng các trình phân tích cú pháp phải có khả năng phân tích cú pháp JSON phù hợp (đoạn 4) và có thể hỗ trợ các phần mở rộng không phải JSON. Tuy nhiên, đoạn 5 tuyên bố rõ ràng rằng tất cả các nhà sản xuất (máy phát điện) PHẢI sản xuất JSON tuân thủ CHỈ 100%. Sản xuất JSON với các ký tự khung không cần thoát là một ý tưởng đặc biệt tồi. Vui lòng xem xét thay thế dấu nháy đơn của bạn bằng dấu ngoặc kép. ietf.org/rfc/rfc4627.txt
Luv2code

3
@ Luv2code Mặc dù các điểm bạn đang thực hiện vẫn đúng, lưu ý rằng bạn đang trích dẫn một thông số lỗi thời. Khi đọc RFC, luôn luôn sử dụng phiên bản tools.ietf.org/html , không phải phiên bản văn bản. Các phiên bản HTML dễ đọc và liên kết với các phần phụ hơn và quan trọng nhất, ở đầu các phiên bản HTML là danh sách tất cả các RFC tiếp theo cập nhật hoặc lỗi thời với bản bạn đang đọc. Nếu bạn đã truy cập tools.ietf.org/html/rfc4627 bạn sẽ thấy RFC 4627 đã lỗi thời và đã được thay thế bởi RFC 7159 .
Đánh dấu Amery

3
Đối với những người đọc điều này trong tương lai, RFC 7159 đã lần lượt bị các công cụ lỗi thời.ietf.org/html/rfc8259
Joram van den Boezem 13/03/18

Câu trả lời:


286

Một chuỗi JSON phải được trích dẫn hai lần, theo thông số kỹ thuật , vì vậy bạn không cần phải thoát '.
Nếu bạn phải sử dụng ký tự đặc biệt trong chuỗi JSON của mình, bạn có thể thoát nó bằng \ký tự.

Xem danh sách ký tự đặc biệt này được sử dụng trong JSON:

\b  Backspace (ascii code 08)
\f  Form feed (ascii code 0C)
\n  New line
\r  Carriage return
\t  Tab
\"  Double quote
\\  Backslash character


Tuy nhiên, ngay cả khi nó hoàn toàn trái với thông số kỹ thuật, tác giả có thể sử dụng \'.

Điều này là xấu bởi vì:

  • Nó trái với thông số kỹ thuật
  • Đó là chuỗi hợp lệ JSON không còn

Nhưng nó hoạt động, như bạn muốn hay không.

Đối với người đọc mới, luôn luôn sử dụng dấu ngoặc kép cho chuỗi json của bạn.


30
"chuỗi json trích dẫn duy nhất" ? Thật vô nghĩa; các chuỗi trong JSON chỉ có thể được trích dẫn kép. Hãy thử JSON.parse("'foo'")trong bảng điều khiển trình duyệt của bạn, ví dụ, và quan sát SyntaxError: Unexpected token '. Thông số JSON thực sự đơn giản và rõ ràng về điều này. Không có chuỗi thoát trong JSON cho các trích dẫn đơn và chuỗi JSON có thể được trích dẫn đơn.
Đánh dấu Amery

15
Ngay cả bản cập nhật được cho là làm rõ cho câu trả lời này là xấu. Mặc dù về mặt kỹ thuật, thật sai lầm khi nói rằng bạn "không cần" trốn thoát ', theo cách tương tự như sự thật về mặt kỹ thuật nhưng lại gây hiểu lầm rằng về mặt pháp lý bạn không cần phải giết trẻ em. Chính xác hơn sẽ nói rằng bạn không thể trốn thoát '. \'là một chuỗi thoát bất hợp pháp và nếu bạn sử dụng nó thì JSON của bạn không phảiJSON hợp lệ và bất kỳ trình phân tích cú pháp JSON nào cũng sẽ bị nghẹt thở. (Chắc chắn là của JavaScript JSON.parsevà Python json.loads.)
Mark Amery

2
Câu trả lời này vẫn hoàn toàn vô nghĩa sau nhiều lần chỉnh sửa. Bạn khẳng định, sai, rằng sử dụng các chuỗi trích dẫn đơn trong JSON và sử dụng \'chuỗi thoát "hoạt động, như bạn muốn hay không" . Điều này là sai. Tôi thách bạn thể hiện bất kỳ trình phân tích cú pháp JSON nào trong sử dụng phổ biến mà sẽ không bị nghẹt thở trên các chuỗi trích dẫn đơn hoặc trên \'chuỗi. Tôi đã chỉ ra rằng JSON.parse("'foo'")JSON.parse('"\\\'"') (bằng JavaScript) json.loads("'foo'")json.loads('"\\\'"')(bằng Python) cả hai đều có ngoại lệ. Điều gì trên trái đất là cơ sở của bạn cho tuyên bố rằng sử dụng các "công trình" này?
Mark Amery

10
@ Luv2code trích dẫn thú vị. Bạn đang hiểu sai nó một chút; điều đó không có nghĩa là bất kỳ nhân vật nào cũng có thể thoát được chỉ bằng cách đặt dấu gạch chéo ngược trước nó. Một câu trích dẫn đầy đủ hơn là "Bất kỳ ký tự nào cũng có thể được thoát. Nếu ký tự nằm trong Mặt phẳng đa ngôn ngữ cơ bản (U + 0000 đến U + FFFF), thì nó có thể được biểu diễn dưới dạng một chuỗi sáu ký tự . ... Ngoài ra, có hai ký tự -Sản phẩm thoát chuỗi trình tự của một số nhân vật phổ biến. "(nhấn mạnh của tôi). Nó nói rằng bạn có thể thoát 'như \u0027, không phải là bạn có thể thoát khỏi nó như \'.
Mark Amery

2
@ Luv2code vẫn vậy, điều đó có nghĩa là bình luận được đánh giá cao của tôi nói rằng "bạn không thể trốn thoát '" (và so sánh hành động đó với việc giết trẻ em!) Là sai về mặt kỹ thuật; chính xác hơn là nói rằng bạn có thể thoát khỏi nó, chỉ là không \'. Tôi đã không nhận ra rằng phiên bản RFC của thông số kỹ thuật đề cập đến các chuỗi giống \u0027như một cách 'thoát' các nhân vật mà họ đại diện. Điểm mấu chốt \'là bất hợp pháp, mặc dù, vẫn đúng và quan trọng.
Đánh dấu Amery

362

Tôi kinh hoàng vì sự hiện diện của thông tin sai lệch được đánh giá cao về một câu hỏi được xem nhiều về một chủ đề cơ bản.

Chuỗi JSON không thể được trích dẫn với dấu ngoặc đơn . Các phiên bản khác nhau của thông số kỹ thuật ( bản gốc của Douglas Crockford, phiên bản ECMAphiên bản IETF ) đều nêu rõ các chuỗi phải được trích dẫn bằng dấu ngoặc kép. Đây không phải là một vấn đề lý thuyết, cũng không phải là vấn đề quan điểm như câu trả lời được chấp nhận hiện đang đề xuất; bất kỳ trình phân tích cú pháp JSON nào trong thế giới thực sẽ lỗi nếu bạn cố gắng phân tích cú pháp một chuỗi trích dẫn.

Phiên bản của Crockford và ECMA thậm chí còn hiển thị định nghĩa của một chuỗi bằng một hình ảnh đẹp, điều này sẽ làm cho điểm rõ ràng rõ ràng:

Hình ảnh hiển thị định nghĩa của một chuỗi từ thông số JSON

Bức tranh đẹp cũng liệt kê tất cả các chuỗi thoát hợp pháp trong chuỗi JSON:

  • \"
  • \\
  • \/
  • \b
  • \f
  • \n
  • \r
  • \t
  • \u theo sau là bốn chữ số

Lưu ý rằng, trái với những điều vô nghĩa trong một số câu trả lời khác ở đây, \' không bao giờ là một chuỗi thoát hợp lệ trong chuỗi JSON. Không cần thiết, bởi vì các chuỗi JSON luôn được trích dẫn hai lần.

Cuối cùng, thông thường bạn không cần phải suy nghĩ về việc tự thoát các ký tự khi tạo JSON theo chương trình (mặc dù tất nhiên bạn sẽ làm khi chỉnh sửa thủ công, giả sử, tệp cấu hình dựa trên JSON). Thay vào đó, hình thành cấu trúc dữ liệu mà bạn muốn mã hóa bằng bất kỳ loại bản đồ, mảng, chuỗi, số, boolean và null nào mà ngôn ngữ của bạn có, sau đó mã hóa nó thành JSON bằng hàm mã hóa JSON. Một hàm như vậy có thể được tích hợp vào bất kỳ ngôn ngữ nào bạn đang sử dụng, như của JavaScript JSON.stringify, PHP json_encodehoặc Pythonjson.dumps. Nếu bạn đang sử dụng ngôn ngữ không có chức năng như vậy, bạn có thể tìm thấy thư viện mã hóa và phân tích cú pháp JSON để sử dụng. Nếu bạn chỉ đơn giản sử dụng các chức năng ngôn ngữ hoặc thư viện để chuyển đổi mọi thứ sang và từ JSON, bạn thậm chí sẽ không cần phải biết các quy tắc thoát của JSON. Đây là những gì người hỏi câu hỏi sai lầm ở đây nên đã làm.


4 byte hex hay nibble ?
leetbacoon

36

Mọi người đang nói về làm thế nào để thoát 'trong một 'chuỗi ký tự được trích dẫn. Có một vấn đề lớn hơn nhiều ở đây: chuỗi ký tự đơn trích dẫn không phải là JSON hợp lệ . JSON dựa trên JavaScript, nhưng nó không giống nhau. Nếu bạn đang viết một đối tượng bằng chữ JavaScript, tốt thôi; nếu bạn thực sự cần JSON, bạn cần sử dụng ".

Với các chuỗi trích dẫn kép, bạn sẽ không cần phải thoát '. (Và nếu bạn đã muốn có một chữ "trong chuỗi, bạn sẽ sử dụng \".)


1
Xin chào, bạn đã nói với các chuỗi trích dẫn kép, bạn sẽ không cần phải thoát '. Ví dụ về kẻ thù nếu giá trị chuỗi của tôi là "Member's_id" : 4, bạn có nói rằng nó không cần thoát không? Rõ ràng tôi đang gặp vấn đề trong đó nó đưa ra lỗi mã hóa sai: UTF-8 và nó đang được đọc là Member�s. Đây là một tập tin json được tạo thủ công.
Shubham

1
'trong một chuỗi JSON theo nghĩa đen không được thoát. Bạn đã sao chép-dán nó từ một nơi nào đó? Có lẽ nó thực sự là một \u2019, không phải là một dấu nháy đơn. Tôi đoán: ai đó đã gõ nó vào MS Word, điều này đã biến nó thành dấu ngoặc kép vì nó nghĩ rằng nó biết rõ nhất. Về mặt ngữ pháp, dấu nháy đơn của ký tự ASCII cũ ( 'hay còn gọi là \x27"trích dẫn duy nhất" cho đến bây giờ) là thứ bạn muốn. Nhưng nó vẫn tốt để khắc phục vấn đề mã hóa ký tự của bạn, trong trường hợp có các vấn đề tương tự khác. Vì vậy, chọn một mã hóa ký tự, và sử dụng nó cho cả đọc và viết. Hoặc thoát bằng cách sử dụng \u.
David Knipe

7

Hầu hết các câu trả lời này không trả lời được câu hỏi hoặc không cần thiết trong phần giải thích.

OK để JSON chỉ sử dụng dấu ngoặc kép, chúng tôi hiểu điều đó!

Tôi đã cố gắng sử dụng JQuery AJAX để đăng dữ liệu JSON lên máy chủ và sau đó trả lại thông tin tương tự. Giải pháp tốt nhất cho câu hỏi được đăng mà tôi tìm thấy là sử dụng:

var d = {
    name: 'whatever',
    address: 'whatever',
    DOB: '01/01/2001'
}
$.ajax({
    type: "POST",
    url: 'some/url',
    dataType: 'json',
    data: JSON.stringify(d),
    ...
}

Điều này sẽ thoát khỏi các nhân vật cho bạn.

Điều này cũng được đề xuất bởi Mark Amery, câu trả lời tuyệt vời BTW

Hy vọng điều này sẽ giúp được ai đó.


0

Có thể tôi đến bữa tiệc quá muộn nhưng điều này sẽ phân tích / thoát một trích dẫn duy nhất (không muốn tham gia vào trận chiến phân tích so với trốn thoát) ..

JSON.parse("\"'\"")

0

Câu trả lời cho câu hỏi trực tiếp:
Để an toàn, hãy thay thế ký tự được yêu cầu bằng \ u + 4 chữ số-hex-value

Ví dụ: Nếu bạn muốn thoát dấu nháy đơn 'thay thế bằng \ u0027
D'Amico trở thành D \ u0027Amico

TÀI LIỆU THAM KHẢO: http://es5.github.io/x7.html#x7.8.4

https://mathiasbynens.be/notes/javascript-escapes


-1 cho các tài liệu tham khảo. Câu hỏi là về JSON, nhưng các tham chiếu được liên kết của bạn là về JavaScript và liệt kê các chuỗi thoát không hợp lệ trong JavaScript như thế nào \'.
Đánh dấu Amery

Cảm ơn Mark - Tôi thực sự chỉ muốn đưa ra một góc thay thế - tùy thuộc vào người đến đây có thể thấy điều này hữu ích. Nhưng tôi có quan điểm của bạn về JSON & Javascript - Cảm ơn vì đã trở thành Ninja trên các diễn đàn.
Luigi D'Amico

0

Sử dụng encodeURIComponent () để mã hóa chuỗi.

Ví dụ. var sản phẩm_list = encodeURIComponent (JSON.opesify (sản phẩm_list));

Bạn không cần giải mã nó vì máy chủ web sẽ tự động làm như vậy.


0

Sử dụng mẫu chữ ...

var json = `{"1440167924916":{"id":1440167924916,"type":"text","content":"It's a test!"}}`;

-2

Tôi nghĩ rằng tất cả chúng ta đồng ý trích dẫn jsons duy nhất không phải là jsons thực sự. Dù có thể, chúng ta vẫn cần giải quyết câu hỏi về việc thoát "trong một chuỗi json được trích dẫn kép, trong trường hợp không có thư viện để làm điều đó cho chúng ta.

Việc thay thế từng "bằng một \" là KHÔNG ĐÚNG: Người dùng có thể nhập dữ liệu đầu vào: \ và phân tích lại, thất bại (nghĩ tại sao).

Thay vào đó, trước tiên hãy thay thế mỗi \ bằng \ (dấu gạch chéo kép). Chỉ sau đó, thay thế mỗi "bằng \" (dấu gạch chéo theo sau ").


-2

Để cho phép các trích dẫn đơn trong chuỗi trích dẫn nghi ngờ cho mục đích của json, bạn nhân đôi trích dẫn. {"X": "Câu hỏi là gì"} ==> {"X": "Câu hỏi là gì"}

/codereview/69266/json-conversion-to-single-quotes

Chuỗi \ 'không hợp lệ.


2
Nhân đôi một trích dẫn trong chuỗi JSON không thoát khỏi nó. Nó chỉ có nghĩa là chuỗi của bạn chứa hai dấu ngoặc đơn, thay vì một.
Đánh dấu Amery

-15

liên quan đến bài viết của AlexB:

 \'  Apostrophe or single quote
 \"  Double quote

thoát các dấu ngoặc đơn chỉ có giá trị trong các chuỗi json được trích dẫn
thoát dấu ngoặc kép chỉ có giá trị trong chuỗi json được trích dẫn kép

thí dụ:

'Bart\'s car'       -> valid
'Bart says \"Hi\"'  -> invalid

14
Các chuỗi trích dẫn đơn không hợp pháp trong JSON. JSON không phải là javascript. JSON không cho phép thoát khỏi trích dẫn duy nhất. Xem json.org để biết tài liệu cú pháp JSON rất đơn giản.
srm

3
downvote - vì trích dẫn đơn jsons không hợp lệ!
DominikAngerer

Dấu ngoặc đơn không hợp lệ trong json. Vui lòng hiển thị một mẫu làm việc nếu điều này là có thể
Rohith
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.