Получение JSON по URL

Вопросы программирования и использования среды Lazarus.

Модератор: Модераторы

Ответить
Frig@te
незнакомец
Сообщения: 3
Зарегистрирован: 28.05.2018 14:22:05

Получение JSON по URL

Сообщение Frig@te »

Добрый день. Давно не программил ничего, да и ранее не работал с JSON.
В целом понятно пока все, но появился вопрос.
По различным примерам из инета, я получил данные из URL

Код: Выделить всё

procedure TForm1.Button3Click(Sender: TObject);
var
  url, html : String;
begin
  url := 'http://enduristov.net/work/TestJson/Test.php';
  html := TFPCustomHTTPClient.SimpleGet(url);

  memo1.Text := trim(html);       


И попробовал читать.

Код: Выделить всё

procedure TForm1.Button1Click(Sender: TObject);
var
  J: TJSONData;
  begin
    J:=GetJSON(Memo1.text);  //Место где мы берем данные, в моем случаем это Memo1

    Memo2.Text:=J.FindPath(Edit1.Text).AsString; //Куда копируем результат, и путь до значение которое требуется
    J.Free; //Не забываем освобождать память, иначе будут утечки...
  end;           


Вот вопрос в следующем.
Если в мемо я руками копирую текст JSON , то все работает.
Если я получаю по URL в конце добавляются лишние пробелы, если их убрать в Мемо руками, все работает. Если использовать Trim то ошибка.
Не могу понять в чем дело.
Вывел три Лейбла, синяя просто из урл, красная трим(урл), желая из другого мемо, в которое вставил руками текст. Всю голову уже сломал..
У вас нет необходимых прав для просмотра вложений в этом сообщении.
Аватара пользователя
wofs
постоялец
Сообщения: 379
Зарегистрирован: 05.10.2009 10:16:55
Откуда: Астрахань
Контактная информация:

Сообщение wofs »

Frig@te писал(а):Если использовать Trim то ошибка.

А какая именно ошибка?
Frig@te
незнакомец
Сообщения: 3
Зарегистрирован: 28.05.2018 14:22:05

Сообщение Frig@te »

Вот скрины ошибок
У вас нет необходимых прав для просмотра вложений в этом сообщении.
MysticCoder
постоялец
Сообщения: 154
Зарегистрирован: 14.09.2013 00:20:28

Сообщение MysticCoder »

Кофейная гуща показывает, что у тебя ошибка в 7 строке.
Что именно ты делаешь с этим текстом в мемо дальше? Приведи текст процедуры, на какой именно строке ошибка, и какие именно значения строк передаются при возникновении ошибки и без возникновения.
Frig@te
незнакомец
Сообщения: 3
Зарегистрирован: 28.05.2018 14:22:05

Сообщение Frig@te »

Разобрался вроде. Дело в кодировке. Сервер отдает в UTF-8.
Функция UTF8ToSys отдает строку со знаком вопроса вначале. Сделал пока чтобы сервер отдавал 1251.

Добавлено спустя 1 минуту 8 секунд:
MysticCoder писал(а):Кофейная гуща показывает, что у тебя ошибка в 7 строке.
Что именно ты делаешь с этим текстом в мемо дальше? Приведи текст процедуры, на какой именно строке ошибка, и какие именно значения строк передаются при возникновении ошибки и без возникновения.

Ошибка возникала на строке

Код: Выделить всё

J:=GetJSON(Memo1.text);


Добавлено спустя 55 минут 3 секунды:
Теперь я понял, что JSon неправильно формирует сервер. Сделал как правильно.

Код: Выделить всё

[{
   "_id": "1",
   "author": "Test1",
   "client": "Test2",
   "data": "2805",
   "text": "Yaaaaahooo"
}, {
   "_id": "2",
   "author": "Test2",
   "client": "Test3",
   "data": "29",
   "text": "\u041e\u043f\u0430\u043f\u0430\u043f\u0430\u043f\u0430"
}, {
   "_id": "3",
   "author": "Test2",
   "client": "Test3",
   "data": "2905",
   "text": "\u041e\u043f\u0430\u043f\u0430\u043f\u0430\u043f\u0430"
}]

Но нет примеров, как работать с ним если он в массиве.
Аватара пользователя
Снег Север
долгожитель
Сообщения: 3067
Зарегистрирован: 27.11.2007 15:14:47
Контактная информация:

Сообщение Снег Север »

Frig@te, как-то так:

Код: Выделить всё

uses     
fpjson, jsonparser, jsonscanner; 

...
var 
Parser:TJSONParser;
  jObject, jSubObject  : TJSONObject;
  Arr:TJSONArray;   

...
Parser := TJSONParser.Create(str, [joUTF8]);
try
jObject := Parser.Parse as TJSONObject;   

...jObject.Items[1].FormatJSON
...
Arr := jObject.Get('dirs', TJSONArray(nil));
for i := 0 to Arr.Count - 1 do
        begin
             ...Arr[i].AsString ...
        end;       
Arr.Clear;
finally
        jObject.Free;
        FreeAndNil(Parser);
end;       



это кусочек из моего рабочего кода, под мой конкретный json
Последний раз редактировалось Снег Север 30.05.2018 12:33:00, всего редактировалось 1 раз.
Аватара пользователя
Ichthyander
энтузиаст
Сообщения: 701
Зарегистрирован: 04.04.2007 08:32:43
Откуда: Астрахань
Контактная информация:

Сообщение Ichthyander »

А у Вас сервер на Windows что ли? Это все объясняет. Вам сервер генерирует в PHP не просто строку JSON в UTF8, но еще и добавляет в начало BOM. При ручном копировании, то есть через буфер обмена WIndows BOM само собой благополучно не передается и понимается верно. А вот функция Trim справедливо не обрезает BOM, потому что BOM=EF BB BF байты, больше 32-ух.
Так что можете также генерировать строчку в UTF8 на сервере. Но сделайте так, чтобы никаких BOM в первых трех байтах!

Добавлено спустя 2 минуты 26 секунд:
Да и на скриншотах с ошибкой явственно видно, что сканер JSON не понимает первый символ строчки "п", так как если прочитать BOM в cp1251, то получится такая белиберда: п»ї (обращаем внимание на первый символ)
Аватара пользователя
Снег Север
долгожитель
Сообщения: 3067
Зарегистрирован: 27.11.2007 15:14:47
Контактная информация:

Сообщение Снег Север »

Ichthyander, я в десятке приложений генерировал строку JSON в UTF8 из сервисов на Windows серверах и никогда никакого BOM не добавлялось. Ни в дотнет, ни делфи, ни пхп. Я даже не знаю что такого надо замутить, чтобы этот BOM вставлялся.
Аватара пользователя
Ichthyander
энтузиаст
Сообщения: 701
Зарегистрирован: 04.04.2007 08:32:43
Откуда: Астрахань
Контактная информация:

Сообщение Ichthyander »

Снег Север ну я не говорю о том, как у сервера получилось сгенерировать BOM в начале строки (я действительно на WIndows никогда не делал web), но факт остается фактом:
1) На скриншоте у него показано, что сканер JSON наткнулся в самом начале на неизвестный символ п, то есть тот первый байт в BOM, который именно так виден визуально, если он интерпретируется как CP1251.
2) Этот BOM не обрезается функцией Trim
3) Этот BOM исчезает при ручном копировании.
То есть по всем признакам вывод: JSON сканеру вскармливается строка с BOM в самом начале.
Каким образом BOM попадает в начало строки при выводе PHP скрипта не знаю, я не вижу бэкенда, но он есть. Я предположил, что какой-то самопальный скрипт/сервер на WIndows. Это уже дело десятое. Собака [снова] зарыта в BOM

Добавлено спустя 5 минут 46 секунд:
Снег Север кстати, можно предположить такое. Топикстартер создал JSON строку в блокноте Windows, выбрав кодировку UTF8. Windows "любезно" подставил BOM в начало файла. А PHP скрипт не генерирует этот JSON, а просто напросто подгружает этот файл и отдает пользователя, запросившему этот скрип на вывод. Таким образом мы получим BOM на любой ОС, лишь бы файл был создан и сохранен в блокноте Windows или, случайно, человек сам выбрал UTF8 c BOM...
Vadim
долгожитель
Сообщения: 4112
Зарегистрирован: 05.10.2006 08:52:59
Откуда: Красноярск

Сообщение Vadim »

Ichthyander
Я пробовал понять эту ситуацию у топикстартера. На сервере (в страничке, что выдаёт PHP-скрипт) BOM нету, специально смотрел исходный код этой страницы. А вот при попытке получить страничку программой "wget", BOM в начале чудесным образом появился. Это наводит на мысль, что BOM генерирует веб-сервер. Или сервер генерит страничку в зависимости от названия браузер-клиента, для Firefox BOM не ставится, а, к примеру, незнакомое название интерпретируется как IE и там BOM вставляется. Как вы думаете?
Аватара пользователя
Ichthyander
энтузиаст
Сообщения: 701
Зарегистрирован: 04.04.2007 08:32:43
Откуда: Астрахань
Контактная информация:

Сообщение Ichthyander »

Vadim, а откуда Вам известно, что FireFox/браузер не получает BOM в начале? Я думаю, браузеру нет нужды показывать BOM клиентам, пусть даже в "исходном коде". Видимо при обработке браузере просто удаляют информацию при отображении клиенту в "исходном коде браузера".
P.S. Вот я сейчас даже провел эскперимент на своем сервере. Создал файл test.php с русским текстом в кодировке UTF8 with BOM... "вуаля"... и в браузере FireFox BOM не виден. А wget или, например, при программном закачивании файла BOM никуда не денется
Vadim
долгожитель
Сообщения: 4112
Зарегистрирован: 05.10.2006 08:52:59
Откуда: Красноярск

Сообщение Vadim »

Ichthyander
Беру свои слова назад. :-) Действительно, FF страничку с BOM получает, только BOM не показывает. При сохранении странички BOM присутствует.
Ответить