Čeština v JSONu se nezobrazuje korektně
- Milan Obrtlík
- Člen | 50
Jak můžu poslat české znaky přes JSON?
Nyní posílám takto:
<?php
namespace App\Presenters;
use Nette;
class HomepagePresenter extends Nette\Application\UI\Presenter {
public function renderDefault() {
$this->payload->test = "Řáďící číšňík";
$this->sendPayload();
}
}
V prohlížeči (Chrome 48) se mi zobrazí
{"test":"ĹáďĂcĂ ÄŤĂšĹĂk"}
ale v ladících nástrojích se to ukazuje korektně.
- Milan Obrtlík
- Člen | 50
Je to čistá „instalace“ nette/webproject pomocí composeru. Jediné dva
přidané řádky jsou ty s tím $this.
To je všechno co vím.
- Milan Obrtlík
- Člen | 50
$this->sendPayload() ukončí okamžitě presenter a odešle se jenom JSON (žádná šablona se nekreslí). Nevím kde mám nastavit kódování na UTF-8.
Kód
<?php
namespace App\Presenters;
use Nette;
class HomepagePresenter extends Nette\Application\UI\Presenter {
public function renderDefault() {
echo json_encode(["test"=>"Řádící číšňík"]);
$this->terminate();
}
}
vypíše v prohlížeči
{"test":"\u0158\u00e1d\u00edc\u00ed \u010d\u00ed\u0161\u0148\u00edk"}
- Milan Obrtlík
- Člen | 50
@Mysteria tak zkrátit se to vždycky, horší je najít to, aby bylo
co zkracovat
@pata.kusik111 json_encode($data, JSON_UNESCAPED_UNICODE)
funguje taky, ale jak pak korektně ukončíš životní cyklus presenteru?
- pata.kusik111
- Člen | 78
Podědím a přepíši JsonResponse
. To řešení od
@Mysteria je bug, který by neměl fungovat. Stačí se podívat jak je
JsonResponse
napsaný. V nové třídě pak přepíši z JsonResponse
tuhle část
na
echo Nette\Utils\Json::encode($this->payload, JSON_UNESCAPED_UNICODE);
.
Samozřejmě, já jsem na druhou stranu strašný puritán a chápu, že takové řešení není zrovna z těch nejpraktičtějších…
- pata.kusik111
- Člen | 78
Original:
@Mysteria moje chyba. Měl jsem za to, že charset má mít vlastní header. A źe se jen zneužívá řetězení pomocí středníku. Máš to samozřejmě naprosto správně. No jo už je víkend a nemyslí mi to.
Edited:
@Mysteria je to nestandardní chování, které funguje i když by
nemělo. Do konstruktoru by měl přijít je MIME type. Protože:
V JsonResponse::send
se ten content type nastavuje. do
Nette\Http\IResponse::setContentType
. Ale jenom jako první
parametr, ne jako oba parametry. Viz API
dokumentace IHttpResponse. Opravdu to funguje bugem, ale ten bug je tady,
kde to dovoluje nastavit charset jen s pomocí contentType
a
charset = NULL
.
Takže „čisté/správné (jakkoli chcete říkat tomu zbytečně
složitému řešení)“ řešení je přetížit
JsonResponse::send
na:
public function send(Nette\Http\IRequest $httpRequest, Nette\Http\IResponse $httpResponse)
{
$httpResponse->setContentType($this->contentType, 'utf-8');
$httpResponse->setExpiration(FALSE);
echo Nette\Utils\Json::encode($this->payload);
}
Editoval pata.kusik111 (19. 2. 2016 16:58)
- Milan Obrtlík
- Člen | 50
@Mysteria $this->terminate() sice presenter ukončí, ale Tracy se pořád objevuje – to je poněkud nežádoucí pro JSON.
@pata.kusik111 paráda, přetížil jsem
JsonResponse::send
tím ‚UTF-8‘ a už můžu zase používat
$this->sendPayload
! Boží!
Asi si budu trochu odporovat (minulou větou jsem vynášel
$this->sendPayload
do nebes), ale dá se v Nette nastavit aby
se mi automaticky posílal JSON bez toho, abych nemusel pokaždé psát
$this->sendPayload
? Úplně kompletně celá aplikace bude vždy
odpovídat jenom pomocí JSONu.
Editoval Milan Obrtlík (19. 2. 2016 18:43)