Python / Json: Çift tırnak içine alınmış özellik adı bekleniyor


125

Python'da JSON nesnelerini yüklemenin iyi bir yolunu bulmaya çalışıyorum. Bu json verilerini gönderiyorum:

{'http://example.org/about': {'http://purl.org/dc/terms/title': [{'type': 'literal', 'value': "Anna's Homepage"}]}}

dize olarak alınacağı arka uca gittikten sonra onu json.loads(data)ayrıştırmak için kullandım.

Ama her seferinde aynı istisnayla karşılaştım:

ValueError: Expecting property name enclosed in double quotes: line 1 column 2 (char 1)

Google'da araştırdım ama json.loads(json.dumps(data))kişisel olarak bana göre o kadar verimli olmayan bu çözümün dışında hiçbir şey işe yaramıyor gibi görünüyor çünkü json formatında olmayanlar bile her türlü veriyi kabul ediyor.

Herhangi bir öneri çok takdir edilecektir.


22
Benim hatam çift tırnak meselesi değildi. Python'da yaptığımız gibi, son anahtar / değer çiftinden sonra virgül ekliyordum. Bunu JSON'da yapmazsınız.
Luv33preet

5
her zamanjson.dumps() sadece python yazmak ve python gösteriminin JavaScript okuyucunuzda çalışacağını ummak yerine kullanın .
vy32

Bu sorunu yaşadım çünkü a sonucunu alıp print(jsonpickle_deserialized_object_string)kullanmaya çalıştım. Bazı nedenlerden dolayı print()olan teklifleri şu şekilde "değiştirir:'
StingyJack

@ Luv33preet, teşekkürler, çözüldü. ancak logger-
msg'nin

Yanıtlar:


169

Bu:

{'http://example.org/about': {'http://purl.org/dc/terms/title': [{'type': 'literal', 'value': "Anna's Homepage"}]}}

JSON değil.
Bu:

{"http://example.org/about": {"http://purl.org/dc/terms/title": [{"type": "literal", "value": "Anna's Homepage"}]}}

JSON'dur.

DÜZENLEME:
Bazı yorumcular yukarıdakilerin yeterli olmadığını öne sürdü.
JSON belirtimi - RFC7159 , bir dizenin tırnak işaretiyle başladığını ve bittiğini belirtir. Yani ".
Tek bir quoute ', JSON'da anlamsal bir anlama sahip değildir ve yalnızca bir dize içinde izin verilir.


5
Thanx :) Buna dikkat etmedim, veriyi gönderirken doğru json formatını kullanıyorum ama arka uçta alındığında çift tırnak yerine tekli tırnaklar geliyor! bu yüzden bu istisnayı aldım.
raeX

45
bu bir çözüm değil. Bir çözüm ona dizeyi geçerli json olarak nasıl değiştireceğini söylerdi.
FistOfFury

2
@FistOfFury Özür dilerim, ancak ifadeniz rastgele geçersiz JSON dizesinin programlı olarak güvenilir bir şekilde geçerli bir dizgeye dönüştürülebileceğine dair yanlış bir varsayıma dayanıyor. Bu soruya verilecek pek çok cevap, sorunu 'ile "vb. Değiştirerek çözmeye çalışmaktadır. Size bu" çözümleri "bozacak basit girdi dizeleri örnekleri vermem gerekiyor mu? Görünüşe göre OP, uğraştığımız şeyin JSON ve devam edebildi - cevabımı kabul etti. İpucu - girdi dizesi daha çok Python dict .__ repr __ () yönteminin çıktısına benziyor.
ElmoVanKielmo

5
@ElmoVanKielmo, cevabınızın sorunun cevabı değil, bir ifade olduğu gerçeğini değiştirmez. Hiçbir bağlam veya açıklama sunmuyorsunuz. Buraya soruyla ilgili bilgi arayanlar hayal kırıklığına uğrayacak. OP'ye yardım etmiş olabilirsiniz, ancak diğerleri o kadar değil.
FistOfFury

Basit ve net bir ifade genellikle çok yardımcı olur. Özellikle, etrafta çok sayıda başka cevap olduğunda.
Ben

58

JSON yalnızca çift tırnaklı dizelere izin verdiğinden, dizeyi şu şekilde değiştirebilirsiniz:

str = str.replace("\'", "\"")

JSON'nuzda çıkış karakterli tek tırnak işareti ( \') varsa, daha kesin olan aşağıdaki kodu kullanmanız gerekir:

import re
p = re.compile('(?<!\\\\)\'')
str = p.sub('\"', str)

Bu, JSON dizesindeki tek tırnak tüm oluşumlarını çift strtırnakla değiştirir ve ikinci durumda çıkış karakterli tek tırnakların yerini almaz.

Daha js-beautifyaz katı olanı da kullanabilirsiniz :

$ pip install jsbeautifier
$ js-beautify file.js

4
İyi bir fikir değil çünkü tüm 'leri yanlış olan "s" ile değiştirebilir: ÖRNEK: "kötü" -> "kötü" -> bozuk dizge
Reihan_amn

@Reihan_amn Çıkış karakterli tek tırnakların kullanıldığı durumlar için daha kesin bir normal ifade alternatifi ekledim.
Elig

@WolfgangFahl şimdi tekrar deneyebilirsiniz.
Elig

thx onun yerine stackoverflow.com/a/63862387/1497139 kullanıyorum
Wolfgang Fahl

Ben bir test durumu testSingleQuoteToDoubleQuoteStackoverflow eklendi github.com/WolfgangFahl/pyLoDStorage/blob/master/tests/... tartışma başına stackoverflow.com/a/63862387/1497139 sonuçlarda farklılık gösterir: { 'şehirler': [{' name ': "Üst Cehennemin Kapısı"}, {' name ': "N'zeto"}] {"şehirler": [{"name": "Üst Cehennem Kapısı"}, {"name": "N'zeto" }] {"şehirler": [{"name": "Üst Cehennemin Kapısı"}, {"name": "N" zeto "}]
Wolfgang Fahl

35

Benim durumumda çift tırnak problemi olmadı.

Son virgül bana aynı hata mesajını verdi.

{'a':{'b':c,}}
           ^

Bu virgülü kaldırmak için basit bir kod yazdım.

import json

with open('a.json','r') as f:
    s = f.read()
    s = s.replace('\t','')
    s = s.replace('\n','')
    s = s.replace(',}','}')
    s = s.replace(',]',']')
    data = json.loads(s)

Ve bu benim için çalıştı.


4
+1 Bunu teyit edebilirim. Sondaki virgül bu hata mesajını oluşturur. Örnek:, echo '{"json":"obj",}' | python -m json.tool kabukta çalıştırıldığında, "Beklenen özellik adı çift tırnak içine alınmış: satır 1 sütun 15 (karakter 14)" verir. Takip eden iletişimler yasal JSON değildir, ancak Python JSON modülü bu durumda ilgili bir hata mesajı verirse iyi olur.
Laryx Desidua

8

Oldukça basit, bu dize geçerli JSON değil. Hatanın dediği gibi, JSON belgelerinin çift tırnak kullanması gerekir.

Verilerin kaynağını düzeltmeniz gerekiyor.


7

JSON verilerinizi kontrol ettim

{'http://example.org/about': {'http://purl.org/dc/terms/title': [{'type': 'literal', 'value': "Anna's Homepage"}]}}

içinde http://jsonlint.com/ ve sonuçları vardı:

Error: Parse error on line 1:
{   'http://example.org/
--^
Expecting 'STRING', '}', got 'undefined'

bunu aşağıdaki dizeye değiştirmek JSON hatasını çözer:

{
    "http://example.org/about": {
        "http://purl.org/dc/terms/title": [{
            "type": "literal",
            "value": "Anna's Homepage"
        }]
    }
}

2
LİNK İÇİN TEŞEKKÜRLER!
WolVes

7

JSON dizeleri çift tırnak kullanmalıdır. JSON python kitaplığı bunu zorlar, böylece dizenizi yükleyemezsiniz. Verilerinizin şöyle görünmesi gerekir:

{"http://example.org/about": {"http://purl.org/dc/terms/title": [{"type": "literal", "value": "Anna's Homepage"}]}}

Bu yapabileceğin bir şey değilse, ast.literal_eval()yerine kullanabilirsinjson.loads()


3
Bu, Python kütüphanesinin bir kısıtlaması değil, JSON formatının kendisidir.
Daniel Roseman

Haklısın. Bununla birlikte, bazı JSON ayrıştırıcıları çift tırnakları zorlamaz. Cevabımı güncelleyeceğim.
alexbclay

bu JSON değil, tek tırnaklı dizgelerde hiçbir zaman çift tırnak bulunmaması koşuluyla, tek yapmanız gereken çağırmadan önce tüm single'ları json.loads()
çiftlere dizmek

2
Kullanım , JSON dizesinin bir boole değerine sahip olmasıyla ast.literal_evalsonuçlanır ValueError: malformed string.
Scratch'N'Purr

4
import ast

inpt = {'http://example.org/about': {'http://purl.org/dc/terms/title':
                                     [{'type': 'literal', 'value': "Anna's Homepage"}]}}

json_data = ast.literal_eval(json.dumps(inpt))

print(json_data)

bu sorunu çözecektir.


3

Yanlışlıkla açıkça ifade edildiği gibi, isimler tek tırnak yerine çift tırnak içine alınmalıdır. Geçtiğiniz dize geçerli bir JSON değil. Gibi görünmeli

{"http://example.org/about": {"http://purl.org/dc/terms/title": [{"type": "literal", "value": "Anna's Homepage"}]}}

2

Bu yöntemi kullandım ve istenen çıktıyı almayı başardım. benim senaryom

x = "{'inner-temperature': 31.73, 'outer-temperature': 28.38, 'keys-value': 0}"

x = x.replace("'", '"')
j = json.loads(x)
print(j['keys-value'])

çıktı

>>> 0

2
with open('input.json','r') as f:
    s = f.read()
    s = s.replace('\'','\"')
    data = json.loads(s)

Bu benim için gayet iyi çalıştı. Teşekkürler.


2
x = x.replace("'", '"')
j = json.loads(x)

Bu doğru çözüm olmasına rağmen, bunun gibi bir JSON varsa oldukça baş ağrısına yol açabilir -

{'status': 'success', 'data': {'equity': {'enabled': True, 'net': 66706.14510000008, 'available': {'adhoc_margin': 0, 'cash': 1277252.56, 'opening_balance': 1277252.56, 'live_balance': 66706.14510000008, 'collateral': 249823.93, 'intraday_payin': 15000}, 'utilised': {'debits': 1475370.3449, 'exposure': 607729.3129, 'm2m_realised': 0, 'm2m_unrealised': -9033, 'option_premium': 0, 'payout': 0, 'span': 858608.032, 'holding_sales': 0, 'turnover': 0, 'liquid_collateral': 0, 'stock_collateral': 249823.93}}, 'commodity': {'enabled': True, 'net': 0, 'available': {'adhoc_margin': 0, 'cash': 0, 'opening_balance': 0, 'live_balance': 0, 'collateral': 0, 'intraday_payin': 0}, 'utilised': {'debits': 0, 'exposure': 0, 'm2m_realised': 0, 'm2m_unrealised': 0, 'option_premium': 0, 'payout': 0, 'span': 0, 'holding_sales': 0, 'turnover': 0, 'liquid_collateral': 0, 'stock_collateral': 0}}}}

"Gerçek" değeri fark ettiniz mi? Boolean için iki kez kontrol yapılmasını sağlamak için bunu kullanın. Bu, bu davaları kapsayacaktır -

x = x.replace("'", '"').replace("True", '"True"').replace("False", '"False"').replace("null", '"null"')
j = json.loads(x)

Ayrıca, yapmadığınızdan emin olun.

x = json.loads(x)

Başka bir değişken olmalı.


1

Benim de benzer bir problemim vardı. Birbiriyle iletişim kuran iki bileşen bir kuyruk kullanıyordu.

İlk bileşen, mesajı sıraya koymadan önce json.dumps yapmıyordu. Dolayısıyla, bileşen tarafından oluşturulan JSON dizesi tek tırnak içindeydi. Bu hataya neden oluyordu

 Expecting property name enclosed in double quotes

Json.dumps eklenmesi, doğru biçimlendirilmiş JSON oluşturmaya başladı ve sorun çözüldü.


0

evalİşlevi kullanın .

Tek ve çift alıntılar arasındaki tutarsızlığı giderir.


Kullanıcı girdisinde veya HTTP isteğiyle gelen veride ASLA eval kullanmayın. Bu çok büyük bir güvenlik sorunudur.
ElmoVanKielmo

0

Diğer cevapların iyi açıkladığı gibi, hata json modülüne geçirilen geçersiz tırnak karakterlerinden kaynaklanmaktadır.

Benim durumumda, dizemde 'ile değiştirdikten sonra bile ValueError'ı almaya devam "ettim. Sonunda anladığım şey, alıntı benzeri unicode sembollerinin dizime girmiş olduğuydu:

 “  ”  ‛  ’  ‘  `  ´  ″  ′ 

Bunların hepsini temizlemek için dizenizi normal bir ifadeden geçirmeniz yeterlidir:

import re

raw_string = '{“key”:“value”}'

parsed_string = re.sub(r"[“|”|‛|’|‘|`|´|″|′|']", '"', my_string)

json_object = json.loads(parsed_string)


-1

JSON elle düzenlendiğinde bu problemle birçok kez karşılaştım. Birisi dosyadan bir şeyi fark etmeden silerse, aynı hatayı verebilir.

Örneğin, JSON son "}" eksikse, aynı hatayı verir.

Bu nedenle, dosyanızı elle düzenlerseniz, JSON kod çözücünün beklediği gibi biçimlendirdiğinizden emin olun, aksi takdirde aynı sorunla karşılaşırsınız.

Bu yardımcı olur umarım!


-2

json.dumps()Yöntemi kullanmak her zaman idealdir . Bu hatadan kurtulmak için aşağıdaki kodu kullandım

json.dumps(YOUR_DICT_STRING).replace("'", '"')
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.