Невозможно проанализировать объект JSON (который не является вложенным JSON), поступающий из сокета в python - PullRequest
0 голосов
/ 13 марта 2019

Новое в python, я читаю объект JSON с сервера, размер объекта JSON не является фиксированным.Я получаю данные с сервера согласно размеру буфера, указанному в socket.recv (1024).Как проверить, что объект JSON из полученного сокета сервера заполнен / завершен, потому что при анализе этого JSON я получаю сообщение об ошибке.Обратите внимание, что мой объект JSON не является вложенным.

**** Пример кода ****

def get_data():
    s = socket.socket()
    host = 'IP_Address'
    port = 'Port_Number'

    # connection to hostname on the port.
    s.connect((host, port))
    msg=''
    while(True):        
        msg = s.recv(1024)
        print(msg.decode('ascii'))   
        jsonObject=json.loads(msg.decode('ascii'))     

    s.close()    

Ниже приведена ошибка

Traceback (most recent call last):

  File "d:/xxxxxxxxxxxxx/Python_Test.py", line 26, in <module>
    get_data()

  File "d:/xxxxxxxxxxxxx/Python_Test.py", line 20, in get_data
    temp=json.loads(msg.decode('ascii'))

  File "xxxxxxxxxxxxx\Python\Python37\lib\json\__init__.py", line 348, in loads
    return _default_decoder.decode(s)

  File "xxxxxxxxxxxxx\Python\Python37\lib\json\decoder.py", line 340, in decode
    raise JSONDecodeError("Extra data", s, end)

json.decoder.JSONDecodeError: Extra data: line 2 column 1 (char 777)

Ответы [ 2 ]

1 голос
/ 13 марта 2019

Вы получаете 1024 байта в каждом цикле, и если ваш объект json больше, чем этот, вы должны обработать незавершенную строку json.
Также у вас может быть два объекта json размером 1024 байта или даже больше. Вы можете изменить свой код на код ниже

def get_data():
    s = socket.socket()
    host = 'IP_Address'
    port = 'Port_Number'
    s.connect((host, port))
    msg=''
    while True:        
        r = s.recv(1024)
        msg += r.decode('ascii')
        while True:
            start = msg.find("{")
            end = msg.find("}") 
            if start==-1 or end==-1:   # if can not find both { and } in string  
                break
            jsonObject=json.loads(msg[start:end+1])  # only read { ... } and not another uncompleted data
            #  do whatever you want with jsonObject here
            msg = msg[end+1:]
    s.close()  

ПРИМЕЧАНИЕ: этот код работает правильно, только если в ваших данных нет вложенных json (например: {"device_id": {"another_json": "something"}})

0 голосов
/ 13 марта 2019

Вам нужно подождать, пока будет получен полный json, а затем проанализировать его, что-то вроде этого должно работать:

msg = ''
while(True):        
    response = s.recv(1024)
    if not response:
        break
    msg += response
jsonObject=json.loads(msg.decode('ascii'))     
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...