Uncaught SyntaxError: jeton inattendu avec JSON.parse

192

qu'est-ce qui cause cette erreur sur la troisième ligne?

var products = [{
  "name": "Pizza",
  "price": "10",
  "quantity": "7"
}, {
  "name": "Cerveja",
  "price": "12",
  "quantity": "5"
}, {
  "name": "Hamburguer",
  "price": "10",
  "quantity": "2"
}, {
  "name": "Fraldas",
  "price": "6",
  "quantity": "2"
}];
console.log(products);
var b = JSON.parse(products); //unexpected token o

Ouvrez la console pour afficher l'erreur

coiso
la source
16
Vous n'avez pas de JSON? C'est un littéral tableau / objet.
Bergi

Réponses:

220

productsest un objet. (création à partir d'un objet littéral)

JSON.parse()est utilisé pour convertir une chaîne contenant une notation JSON en un objet Javascript.

Votre code transforme l'objet en une chaîne (en appelant .toString()) afin d'essayer de l'analyser en tant que texte JSON.
La valeur par défaut .toString()renvoie "[object Object]", qui n'est pas un JSON valide; d'où l'erreur.

SLaks
la source
1
n'est-ce pas un tableau? Pourquoi est-ce un objet. Les objets commencent par {et les tableaux commencent par [? ou suis-je faux ici
4
Les tableaux sont des objets; c'est ce qui .toString()revient (selon les spécifications).
SLaks le
1
La solution consiste-t-elle d'abord à stringifier l'objet?
Mohammed Noureldin le
6
@MohammedNoureldin: Non; la solution est de ne rien faire et d'utiliser votre objet.
SLaks
2
Que faire si j'obtiens mes données d'un service distant utilisant Ajax, ce qui me donne une réponse Json? Et je veux que cette réponse soit enregistrée dans l'objet de tableau JavaScript?
Mohammed Noureldin le
125

Disons que vous savez que c'est du JSON valide mais que vous obtenez toujours ceci ...

Dans ce cas, il est probable qu'il y ait des caractères cachés / spéciaux dans la chaîne de n'importe quelle source que vous les obtenez. Lorsque vous les collez dans un validateur, ils sont perdus - mais dans la chaîne, ils sont toujours là. Ces caractères, bien qu'invisibles, se briserontJSON.parse()

S'il ss'agit de votre JSON brut, nettoyez-le avec:

// preserve newlines, etc - use valid JSON
s = s.replace(/\\n/g, "\\n")  
               .replace(/\\'/g, "\\'")
               .replace(/\\"/g, '\\"')
               .replace(/\\&/g, "\\&")
               .replace(/\\r/g, "\\r")
               .replace(/\\t/g, "\\t")
               .replace(/\\b/g, "\\b")
               .replace(/\\f/g, "\\f");
// remove non-printable and other non-valid JSON chars
s = s.replace(/[\u0000-\u0019]+/g,""); 
var o = JSON.parse(s);
EdH
la source
J'obtenais l'erreur et je l'ai retracée jusqu'à un caractère étrange dans une chaîne. J'ai utilisé votre méthode pour supprimer les caractères JSON non valides et cela a fonctionné.
albertski
1
sont venus ici deux fois maintenant. thnx
Benjamin Hoffman
Vous avez un caractère spécial de fin après le décodage Base64, votre méthode m'a beaucoup aidé! Thx
Guillaume
ne faites pas confiance à une source répondant avec un JSON non valide. Informez-les simplement que les données sont corrompues. ils devraient le réparer. si vous essayez de "récupérer" la réponse de cette manière ou de manière similaire, vous maintiendrez une communication instable.
Onur Yıldırım
Doit être à la s = s.replace(/[\u0000-\u001F]+/g,""); place de s = s.replace(/[\u0000-\u0019]+/g,""); , pour remplacer tous les caractères de contrôle. Droite?
HongchaoZhang
64

Il semble que vous vouliez stringifier l'objet. Alors fais ceci:

JSON.stringify(products);

La raison de l'erreur est que JSON.parse()s'attend à une Stringvaleur et productsest un Array.

Remarque: je pense qu'il tente json.parse('[object Array]')ce qui se plaint qu'il ne s'attendait pas à un jeton oaprès [.

Onur Yıldırım
la source
28

J'ai trouvé le même problème avec JSON.parse(inputString).

Dans mon cas, la chaîne d'entrée provient de la page de mon serveur [méthode de retour d'une page] .

J'ai imprimé le typeof(inputString)- c'était une chaîne, l'erreur se produit toujours.

J'ai aussi essayé JSON.stringify(inputString), mais cela n'a pas aidé.

Plus tard, j'ai trouvé que c'était un problème avec l'opérateur de nouvelle ligne [\n], à l'intérieur d'une valeur de champ.

J'ai fait un remplacement [avec un autre caractère, remettre la nouvelle ligne après l'analyse] et tout fonctionne bien.

Derin
la source
2
Le caractère de nouvelle ligne était aussi mon problème. Alors, comment pouvons-nous restaurer de telles données?
kolenda
@kolenda Vous avez un JSON non valide. Vous devez modifier votre serveur pour utiliser un sérialiseur JSON réel qui renvoie un JSON valide.
SLaks
J'ai eu un problème similaire mais au lieu de "\ n", j'avais un "\ e" dans un chemin (j'ai changé le code côté serveur pour utiliser "/" au lieu de "\" et tout fonctionnait à nouveau)
Adam Tal
utiliser un échappement dans lequel \ n serait \\ n
Paul Gregoire
14

JSON.parse attend une chaîne en paramètre. Vous devez stringifier votre objet JSON pour résoudre le problème.

products = [{"name":"Pizza","price":"10","quantity":"7"}, {"name":"Cerveja","price":"12","quantity":"5"}, {"name":"Hamburguer","price":"10","quantity":"2"}, {"name":"Fraldas","price":"6","quantity":"2"}];
console.log(products);
var b = JSON.parse(JSON.stringify(products));  //solves the problem
Térence
la source
12
products = [{"name":"Pizza","price":"10","quantity":"7"}, {"name":"Cerveja","price":"12","quantity":"5"}, {"name":"Hamburguer","price":"10","quantity":"2"}, {"name":"Fraldas","price":"6","quantity":"2"}];

changer en

products = '[{"name":"Pizza","price":"10","quantity":"7"}, {"name":"Cerveja","price":"12","quantity":"5"}, {"name":"Hamburguer","price":"10","quantity":"2"}, {"name":"Fraldas","price":"6","quantity":"2"}]';
pktangyue
la source
2
@SLaks oui, OP peut utiliser des produits directement. mais s'il veut l'utiliser JSON.parse, les arguments doivent être une chaîne.
pktangyue
que dois-je faire dans ASP Classic parce que 'est un commentaire
ashish bhatt
1
@ashishbhatt vous pouvez utiliser ", puis changer tous les autres" en \ "
pktangyue
2
Quelque chose comme çaJSON.parse(products.replace(/'/g, '"'))
Programmeur chimique
11

Vous devez valider votre chaîne JSON ici .

Une chaîne JSON valide doit avoir des guillemets doubles autour des clés:

JSON.parse({"u1":1000,"u2":1100})       // will be ok

S'il n'y a pas de guillemets, cela provoquera une erreur:

JSON.parse({u1:1000,u2:1100})    
// error Uncaught SyntaxError: Unexpected token u in JSON at position 2

L'utilisation de guillemets simples provoquera également une erreur:

JSON.parse({'u1':1000,'u2':1100})    
// error Uncaught SyntaxError: Unexpected token ' in JSON at position 1
hoogw
la source
Dans mon cas, Grails 2.5.6 est rendu render ([key: value])avec des guillemets simples, conduisant à l'erreur JSON parseError à la position 1 dans jquery Ajax. render (groovy.json.JsonOutput.toJson ([key:value]))m'a aidé.
philburns
3
[
  {
    "name": "Pizza",
    "price": "10",
    "quantity": "7"
  },
  {
    "name": "Cerveja",
    "price": "12",
    "quantity": "5"
  },
  {
    "name": "Hamburguer",
    "price": "10",
    "quantity": "2"
  },
  {
    "name": "Fraldas",
    "price": "6",
    "quantity": "2"
  }
]

Voici votre Json parfait que vous pouvez analyser.

San
la source
3

Voici une fonction que j'ai créée sur la base des réponses précédentes: elle fonctionne sur ma machine mais YMMV.

          /**
             * @description Converts a string response to an array of objects.
             * @param {string} string - The string you want to convert.
             * @returns {array} - an array of objects.
            */
            function stringToJson(input) {
              var result = [];

              //replace leading and trailing [], if present
              input = input.replace(/^\[/,'');
              input = input.replace(/\]$/,'');

              //change the delimiter to 
              input = input.replace(/},{/g,'};;;{');

              // preserve newlines, etc - use valid JSON
              ///programming/14432165/uncaught-syntaxerror-unexpected-token-with-json-parse
            input = input.replace(/\\n/g, "\\n")  
            .replace(/\\'/g, "\\'")
            .replace(/\\"/g, '\\"')
            .replace(/\\&/g, "\\&")
            .replace(/\\r/g, "\\r")
            .replace(/\\t/g, "\\t")
            .replace(/\\b/g, "\\b")
            .replace(/\\f/g, "\\f");
            // remove non-printable and other non-valid JSON chars
            input = input.replace(/[\u0000-\u0019]+/g,""); 

              input = input.split(';;;');

              input.forEach(function(element) {
                // console.log(JSON.stringify(element));

                result.push(JSON.parse(element));
              }, this);

              return result;
            }
tmurphree
la source
2

Un autre piège qui peut entraîner une "SyntaxError: Unexpected token"exception lors de l'appel JSON.parse()utilise l'un des éléments suivants dans les valeurs de chaîne:

  1. Caractères de nouvelle ligne.

  2. Onglets (oui, des onglets que vous pouvez produire avec la touche Tab!)

  3. Toute barre oblique autonome \(mais pour une raison quelconque /, du moins pas sur Chrome.)

(Pour une liste complète, voir la section String ici .)

Par exemple, ce qui suit vous obtiendra cette exception:

{
    "msg" : {
        "message": "It cannot
contain a new-line",
        "description": "Some discription with a     tabbed space is also bad",
        "value": "It cannot have 3\4 un-escaped"
    }
}

Il devrait donc être remplacé par:

{
    "msg" : {
        "message": "It cannot\ncontain a new-line",
        "description": "Some discription with a\t\ttabbed space",
        "value": "It cannot have 3\\4 un-escaped"
    }
}

Ce qui, je devrais dire, le rend assez illisible au format JSON uniquement avec une plus grande quantité de texte.

c00000fd
la source
1

Espérons que cela aide quelqu'un d'autre.

Mon problème était que j'avais commenté du HTML dans une fonction de rappel PHP via AJAX qui analysait les commentaires et renvoyait un JSON invalide.

Une fois que j'ai supprimé le HTML commenté, tout allait bien et le JSON a été analysé sans problème.

Chris
la source
0

products est un tableau qui peut être utilisé directement:

var i, j;

for(i=0;i<products.length;i++)
  for(j in products[i])
    console.log("property name: " + j,"value: "+products[i][j]);
ic3b3rg
la source
0

Maintenant , semble - t - \r, \b, \t, \f, etc ne sont pas les caractères seulement problématiques qui peuvent vous donner cette erreur.

Notez que certains navigateurs peuvent avoir des exigences supplémentaires pour la saisie de JSON.parse.

Exécutez ce code de test sur votre navigateur:

var arr = [];
for(var x=0; x < 0xffff; ++x){
    try{
        JSON.parse(String.fromCharCode(0x22, x, 0x22));
    }catch(e){
        arr.push(x);
    }
}
console.log(arr);

En testant sur Chrome, je vois qu'il ne permet pas JSON.parse(String.fromCharCode(0x22, x, 0x22));xest 34, 92 ou entre 0 et 31.

Les caractères 34 et 92 sont respectivement les caractères "et \, et ils sont généralement attendus et correctement échappés. Ce sont les caractères 0 à 31 qui vous poseraient des problèmes.

Pour faciliter le débogage, avant de le faire JSON.parse(input), vérifiez d'abord que l'entrée ne contient pas de caractères problématiques:

function VerifyInput(input){
    for(var x=0; x<input.length; ++x){
        let c = input.charCodeAt(x);
        if(c >= 0 && c <= 31){
            throw 'problematic character found at position ' + x;
        }
    }
}
Pacerier
la source
0

Pourquoi avez-vous besoin de JSON.parse? C'est déjà dans un tableau de format objet.

Mieux vaut utiliser JSON.stringify comme ci-dessous: var b = JSON.stringify(products);

Cela peut vous aider.

abhijit padhy
la source
0

Oh mec, les solutions dans toutes les réponses ci-dessus fournies jusqu'à présent n'ont pas fonctionné pour moi. J'ai eu un problème similaire tout à l'heure. J'ai réussi à le résoudre avec un emballage avec le devis. Voir la capture d'écran. Whoo.

entrez la description de l'image ici

Original:

var products = [{
  "name": "Pizza",
  "price": "10",
  "quantity": "7"
}, {
  "name": "Cerveja",
  "price": "12",
  "quantity": "5"
}, {
  "name": "Hamburguer",
  "price": "10",
  "quantity": "2"
}, {
  "name": "Fraldas",
  "price": "6",
  "quantity": "2"
}];
console.log(products);
var b = JSON.parse(products); //unexpected token o

Eh bien Smith
la source
0

L'erreur que vous obtenez, c'est-à-dire "jeton inattendu o", est due au fait que json est attendu mais que l'objet est obtenu lors de l'analyse. Ce "o" est la première lettre du mot "objet".

Shashank Bodkhe
la source
0

La seule erreur que vous faites est que vous analysez un objet déjà analysé, il génère donc une erreur, utilisez ceci et vous serez prêt à partir.

var products = [{
  "name": "Pizza",
  "price": "10",
  "quantity": "7"
}, {
  "name": "Cerveja",
  "price": "12",
  "quantity": "5"
}, {
  "name": "Hamburguer",
  "price": "10",
  "quantity": "2"
}, {
  "name": "Fraldas",
  "price": "6",
  "quantity": "2"
}];
console.log(products[0].name); //name of item at 0th index

si vous voulez imprimer le json entier, utilisez JSON.stringify ()

Kiran Maniya
la source
0

Cela peut arriver pour de nombreuses raisons, mais probablement pour un caractère invalide, vous pouvez donc l'utiliser JSON.stringify(obj);pour transformer votre objet en JSON, mais rappelez-vous qu'il s'agit d'une expression JQUERY.

Elvis Silva Noleto
la source
0

J'ai cette erreur parce que l'API qui a renvoyé l'objet json donnait UNE ERREUR (dans mon cas, Code Igniter, renvoie un html lorsque le code php échoue) donc CE N'EST PAS UN OBJET JSON.

Vérifiez les phrases SQL et le code PHP, et testez-le avec Postman (ou un autre testeur d'API)

Ari Waisberg
la source
0

L'erreur que je faisais était de passer null(sans le savoir) dans JSON.parse ().

Alors ça a jeté Unexpected token n in JSON at position 0

Aashutosh Rathi
la source
-24

Utilisez eval. Il prend l'expression / code JavaScript sous forme de chaîne et l'évalue / l'exécute.

eval(inputString);
Kasthuri
la source
Chaque appel de eval () crée une nouvelle instance de l'interpréteur JavaScript. Cela peut être un porc de ressources.
Yëco