273

Here is my string

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

Here the message contains single quotation mark, which is same as the quotation used in JSON. What I do is fill up a string from user inputs such as message. So, I need to escape those kind of special scenarios which breaks the code. But other than string replace, is there any way to make them escape but still allow HTML to process them back to the correct message?

WEFX
  • 8,298
  • 8
  • 66
  • 102
dinesh707
  • 12,106
  • 22
  • 84
  • 134
  • 67
    JSON uses only double quotes, not single quotes, see http://www.json.org/ – Niels Bom Dec 13 '13 at 12:36
  • 5
    RFC 4627 states that parsers must be able to parse conformant JSON (paragraph 4), and may support additional non-JSON extensions. However, paragraph 5 emphatically states that all producers (generators) MUST produce ONLY 100% compliant JSON. Producing JSON with frame characters that do not need escaping is an especially bad idea. Please consider replacing your apostrophes with quotes. https://www.ietf.org/rfc/rfc4627.txt – Luv2code Jul 07 '15 at 04:25
  • 3
    @Luv2code While the points you're making remain true, note that you're citing an obsolete spec. When reading RFCs, always use the https://tools.ietf.org/html version, not the text version. The HTML versions are easier to read and link to subsections of, and most importantly, at the top of the HTML versions is a list of all subsequent RFCs that update or obsolete the one you're reading. If you'd gone to https://tools.ietf.org/html/rfc4627 you'd have seen that RFC 4627 is obsolete and has been replaced by [RFC 7159](https://tools.ietf.org/html/rfc7159). – Mark Amery Jul 10 '15 at 11:46
  • 7
    For people reading this in the future, RFC 7159 has in turn been obsoleted by https://tools.ietf.org/html/rfc8259 – Joram van den Boezem Mar 13 '18 at 13:15
  • Related post - [Do the JSON keys have to be surrounded by quotes?](https://stackoverflow.com/q/949449/465053) – RBT Jun 18 '19 at 11:57
  • The relevant part of the specification in 8259 (as of dec 2020) is Section 7, which simply says "A string begins and ends with quotation marks." It does not say "may", "shall", or "must" -- this is hopefully something they will address in the next revision. Section 7 also addresses escaping characters in strings. Any character "may" be escaped, but the quotation, backslash ("reverse solidus"), and the control characters (U+0000 through U+001F) "MUST" be escaped. – Jeremy Dec 25 '20 at 04:07

11 Answers11

496

I'm appalled by the presence of highly-upvoted misinformation on such a highly-viewed question about a basic topic.

JSON strings cannot be quoted with single quotes. The various versions of the spec (the original by Douglas Crockford, the ECMA version, and the IETF version) all state that strings must be quoted with double quotes. This is not a theoretical issue, nor a matter of opinion as the accepted answer currently suggests; any JSON parser in the real world will error out if you try to have it parse a single-quoted string.

Crockford's and ECMA's version even display the definition of a string using a pretty picture, which should make the point unambiguously clear:

Image showing the definition of a string from the JSON spec

The pretty picture also lists all of the legitimate escape sequences within a JSON string:

  • \"
  • \\
  • \/
  • \b
  • \f
  • \n
  • \r
  • \t
  • \u followed by four-hex-digits

Note that, contrary to the nonsense in some other answers here, \' is never a valid escape sequence in a JSON string. It doesn't need to be, because JSON strings are always double-quoted.

Finally, you shouldn't normally have to think about escaping characters yourself when programatically generating JSON (though of course you will when manually editing, say, a JSON-based config file). Instead, form the data structure you want to encode using whatever native map, array, string, number, boolean, and null types your language has, and then encode it to JSON with a JSON-encoding function. Such a function is probably built into whatever language you're using, like JavaScript's JSON.stringify, PHP's json_encode, or Python's json.dumps. If you're using a language that doesn't have such functionality built in, you can probably find a JSON parsing and encoding library to use. If you simply use language or library functions to convert things to and from JSON, you'll never even need to know JSON's escaping rules. This is what the misguided question asker here ought to have done.

Community
  • 1
  • 1
Mark Amery
  • 143,130
  • 81
  • 406
  • 459
348

A JSON string must be double-quoted, according to the specs, so you don't need to escape '.
If you have to use special character in your JSON string, you can escape it using \ character.

See this list of special character used in JSON :

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


However, even if it is totally contrary to the spec, the author could use \'.

This is bad because :

  • It IS contrary to the specs
  • It is no-longer JSON valid string

But it works, as you want it or not.

For new readers, always use a double quotes for your json strings.

Andrew
  • 18,680
  • 13
  • 103
  • 118
AlexB
  • 7,302
  • 12
  • 56
  • 74
  • 37
    *"single quoted json strings"*? This is nonsense; strings in JSON can only ever be double-quoted. Try `JSON.parse("'foo'")` in your browser console, for example, and observe the `SyntaxError: Unexpected token '`. The JSON spec is [really simple and clear](http://json.org/string.gif) about this. There is no escape sequence in JSON for single quotes, and a JSON string cannot be single-quoted. – Mark Amery Dec 17 '14 at 01:12
  • 1
    false information is given here, you should at least correct it. – Gary Drocella Jan 06 '15 at 00:44
  • 21
    Even the supposedly clarifying update to this answer is bad. While technically true, it is misleading to say that you *"don't need"* to escape `'`, in much the same way that it is technically true but misleading to say that legally you *don't need* to murder children. More correct would be to say that you *cannot* escape `'`. `\'` is an illegal escape sequence, and if you use it then your JSON is *not valid JSON* and any JSON parser will choke on it. (Certainly JavaScript's `JSON.parse` and Python's `json.loads` do.) – Mark Amery Jan 31 '15 at 16:26
  • 1
    It's an improvement, certainly. But why don't you at least delete the bits that are wrong? You still suggest using `\'` (twice), and you still have a confusing and irrelevant link to a page about javascript. – David Knipe Feb 18 '15 at 08:45
  • 3
    This answer remains utter nonsense after many edits. You claim, wrongly, that using single-quoted strings in JSON and using the `\'` escape sequence *"works, as you want it or not"*. This is false. I challenge you to exhibit *any* JSON parser in popular use that will not choke on single-quoted strings or on the `\'` sequence. I have already pointed out that `JSON.parse("'foo'")` and `JSON.parse('"\\\'"')` (in JavaScript) and `json.loads("'foo'")` and `json.loads('"\\\'"')` (in Python) both throw exceptions. *What on earth is your basis* for the claim that using these constructs "works"? – Mark Amery Apr 19 '15 at 14:08
  • @MarkAmery I agree with your sentiments, but I think you are incorrect about \' being an illegal character. RFC 4627 "2.5 Strings" states, "Any character may be escaped." That said, it doesn't mean it's a good idea. Just like with regex, you see escaped period, dollar, etc. within character class, or escaped closing brace. It works, but it's ambiguous and confusing. As with the extraneous escaping in regex, I'd suggest "don't escape JSON where you don't need to" because someday it may be a new meta-sequence that does have special meaning, then your doc is non-conformant. – Luv2code Jul 07 '15 at 04:46
  • 11
    @Luv2code interesting quote. You're misinterpreting it slightly; it *doesn't* mean that any character can be escaped simply by putting a backslash in front of it. A fuller quote is "Any character may be escaped. If the character is in the Basic Multilingual Plane (U+0000 through U+FFFF), then it may be represented as a ***six-character sequence***. ... Alternatively, there are two-character sequence escape representations of ***some popular characters.***" (emphasis mine). It's saying you can escape `'` as `\u0027`, *not* that you can escape it as `\'`. – Mark Amery Jul 07 '15 at 07:05
  • 2
    @Luv2code still, it does mean that my upvoted comment stating that "you cannot escape `'`" (and comparing such an act to the murder of children!) is technically wrong; more accurate is to say that you can escape it, just not as `\'`. I hadn't realised that the RFC version of the spec referred to sequences like `\u0027` as a way of 'escaping' the characters they represent. The key point that `\'` is illegal, though, is still true and important. – Mark Amery Jul 07 '15 at 07:10
  • @MarkAmery Yes sir, you are correct. I misunderstood "escape" to be the backslash escape sequence. I did understand \uXXXX notation, but just hadn't grasped that it was referred to as "escaped." In my code, I've "escaped" any 0x00-0x1F that is not one of the two-byte \C sequences, using \uXXXX notation. (Even if it's known to have a common backslash representation such as \0 null, \a alert [aka bell], \v vertical tab, etc.) So should I delete my erroneous comment so as not to confuse anyone? Or would you rather I didn't do that, and leave your comments "dangling"? – Luv2code Jul 09 '15 at 05:45
  • 1
    @Luv2code let it be - it's useful as there is a genuine error in one of my earlier comments. In an ideal world there'd be some means for us to tidy up this comment thread without destroying information, but there isn't, so screw it. – Mark Amery Jul 09 '15 at 13:23
  • @MarkAmery, I'm confused about your comment `JSON.parse("'foo'")` do you mean `JSON.parse("foo")` without single quotes is a valid json object? I always thought two vertical line at start of diagram means expanded partial information. isn't a valid json object should contain in `[]` or `{}`? – AaA Oct 03 '18 at 06:29
  • @AaA So, if we're being precise about terminology, `"foo"` is not a valid JSON *object*, because a JSON object is a mapping of keys to values contained in braces, like `{"foo":"bar", "qux":7}`. But JSON parsers aren't limited to parsing encoded *objects*; rather they parse a [JSON *text*](https://tools.ietf.org/html/rfc7159.html#section-2) which contains any serialised JSON *value*, where a value can be an object, an array, a number, a string, true, false, or null. `"foo"` is a valid JSON string, and thus also a valid JSON text. – Mark Amery Oct 04 '18 at 09:28
  • @AaA This wasn't always the case; as alluded to in the linked spec, previous versions of the spec dictated that the top-level value in a JSON text had to be an object or an array. So a conformant implementation of a JSON parser implementing an *older* version of the spec ought to happily parse the text `{}` but raise an error if you ask it to just parse `"foo"`. This was inconvenient, though, since it just arbitrarily limited the set of values you could serialise and forced you to wrap stuff in objects or arrays - hence implementations often violated that rule, and the latest spec removes it. – Mark Amery Oct 04 '18 at 09:31
  • @AaA Of course, `JSON.parse("foo")` should still fail, because there you're not trying to parse the JSON text `"foo"` but rather the JSON text `foo`, which is not a valid JSON text. The double quotes in `JSON.parse("foo")` just denote the start and end of the 3-character *JavaScript* string storing the invalid JSON text. But the 5-character JavaScript string `'"foo"'` is a valid 5-character JSON text whose value is a 3-character string, and `JSON.parse` will correctly parse it and return the JavaScript string `'foo'`. – Mark Amery Oct 04 '18 at 09:33
  • @AaA Returning to the point of my comment that you replied to: it was that, *unlike* the valid 5-character JSON text `"foo"`, the 5-character text `'foo'` is *not* a valid JSON text, and so the 5-character JavaScript string `"'foo'"` does not represent a valid JSON text, and so `JSON.parse("'foo'")` fails, which is correct, spec-compliant behaviour. This is because the JSON grammar does not permit strings to be quoted with single quotes. – Mark Amery Oct 04 '18 at 09:37
  • @AaA Simple expressions to paste into your browser's JavaScript console to help confirm and understand all the above: `JSON.parse('"foo"')` , `JSON.parse('"foo"') == 'foo'`, and `JSON.parse("'foo'")` . – Mark Amery Oct 04 '18 at 09:40
  • @MarkAmery, No argument about `'` not being a string qualifier in JSON definition, Your second comment answered my question which a json object need to be `{}` or `[]` at top level, even though `.parse` can parse a string to a javascript object (string in this case) – AaA Oct 08 '18 at 06:53
49

Everyone is talking about how to escape ' in a '-quoted string literal. There's a much bigger issue here: single-quoted string literals aren't valid JSON. JSON is based on JavaScript, but it's not the same thing. If you're writing an object literal inside JavaScript code, fine; if you actually need JSON, you need to use ".

With double-quoted strings, you won't need to escape the '. (And if you did want a literal " in the string, you'd use \".)

informatik01
  • 16,038
  • 10
  • 74
  • 104
David Knipe
  • 3,417
  • 1
  • 19
  • 19
  • 1
    Hi, you said with double-quoted strings, you won't need to escape the `'`. Foe example if my string value is `"Member's_id" : 4` , are you saying it doesn't need escaping? Apparently I am having a problem where its giving an error of wrong encoding: UTF-8 and it is being read as `Member�s`. Its a manually generated json file. – Shubham Jul 28 '19 at 16:06
  • 3
    `'` in a JSON string literal must not be escaped. Did you copy-paste it from somewhere? Maybe it's really a `\u2019`, not an apostrophe. My guess: someone typed it into MS Word, which turned it into a quotation mark because it thinks it knows best. Grammatically, the good old ASCII character apostrophe (`'`, a.k.a. `\x27`, which we've been calling "single quote" up until now) is the one you want. But it would still be nice to fix your character encoding issue, in case there are other similar problems. So pick a character encoding, and use it for both reads and writes. Or escape using `\u`. – David Knipe Aug 01 '19 at 21:30
7

Most of these answers either does not answer the question or is unnecessarily long in the explanation.

OK so JSON only uses double quotation marks, we get that!

I was trying to use JQuery AJAX to post JSON data to server and then later return that same information. The best solution to the posted question I found was to use:

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

This will escape the characters for you.

This was also suggested by Mark Amery, Great answer BTW

Hope this helps someone.

Kickass
  • 1,114
  • 9
  • 16
1

May be i am too late to the party but this will parse/escape single quote (don't want to get into a battle on parse vs escape)..

JSON.parse("\"'\"")
YankTHEcode
  • 634
  • 4
  • 8
0

I was struggling with this for complicated mixtures of strings, lists and dictionarys wrapped in JSON.

The simple answer is, don't do anything! Use:

 json.dumps( item, indent=4 )

where item is for instance a dictionary of dictionary of strings and lists and it will escape everything for you itself. This will also result in pretty print output that is human readable.

Example of a part of a dictionary of dictionaries containing lists with special forward slash character:

        {
            "MEASUREMENT": [
                "1\u20444 cup"
            ],
            "DESCRIPTION": [
                "dried"
            ],
            "INGREDIENT": [
                "cranberries"
            ]
        },

It does the right thing for \n replacing it with \\n and so forth. You don't want to escape strings that don't need escaping so let dumps do it for you.

Eamonn Kenny
  • 1,926
  • 18
  • 20
-1

The answer the direct question:
To be safe, replace the required character with \u+4-digit-hex-value

Example: If you want to escape the apostrophe ' replace with \u0027
D'Amico becomes D\u0027Amico

NICE REFERENCE: http://es5.github.io/x7.html#x7.8.4

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

Luigi D'Amico
  • 665
  • 7
  • 11
  • -1 for the references. The question is about JSON, but your linked references are about JavaScript, and list escape sequences that aren't valid in JavaScript like `\'`. – Mark Amery Sep 29 '18 at 15:35
  • 2
    Thanks Mark - I really just wanted to give an alternative angle - depending on who arrives here may find this useful. But I take your point about JSON & Javascript - Thanks for being a Ninja on the forums. – Luigi D'Amico Oct 06 '18 at 09:19
-2

Using template literals...

var json = `{"1440167924916":{"id":1440167924916,"type":"text","content":"It's a test!"}}`;
Ruben
  • 1,065
  • 5
  • 18
  • 44
  • This does not parse or decode the string in any way. The string also contains no `\\` characters in it. – i336_ Mar 13 '21 at 11:41
-4

Use encodeURIComponent() to encode the string.

Eg.:

var product_list = encodeURIComponent(JSON.stringify(product_list));

You don't need to decode it since the web server automatically do the same.

Yuri
  • 4,254
  • 1
  • 29
  • 46
Sanju Kaniyamattam
  • 501
  • 1
  • 4
  • 14
  • 1
    The question is about encoding strings containing quote marks in JSON, not about encoding JSON for passing in a URL. – Quentin Feb 05 '21 at 11:00
-7

To allow single quotes within doubule quoted string for the purpose of json, you double the single quote. {"X": "What's the question"} ==> {"X": "What''s the question"}

https://codereview.stackexchange.com/questions/69266/json-conversion-to-single-quotes

The \' sequence is invalid.

4T2G
  • 53
  • 5
-16

regarding AlexB's post:

 \'  Apostrophe or single quote
 \"  Double quote

escaping single quotes is only valid in single quoted json strings
escaping double quotes is only valid in double quoted json strings

example:

'Bart\'s car'       -> valid
'Bart says \"Hi\"'  -> invalid
Bart
  • 187
  • 2
  • 5
  • 17
    Single quoted strings are not legal in JSON. JSON is not javascript. JSON does not allow escaping the single quote. See http://json.org/ for the very simple document of JSON syntax. – srm Oct 16 '14 at 18:55
  • 4
    downvote - because single quotes jsons are not valid! – DominikAngerer Apr 19 '15 at 14:56
  • Single quotes are invalid in json. Please show a working sample if this is possible – Rohith Feb 03 '20 at 16:06