(Zastrzeżenie: Nie mam rozwiązanie, ja zbadałem co czyni wyjątek obsługi specjalnych w odniesieniu do drukowania emotikonom, z narzędziami mam na systemie Windows 10 - Przy odrobinie szczęścia, które mogłyby poświęcić trochę światła na ten temat i być może ktoś coś rozpozna i zaproponuje rozwiązanie)
Wygląda jak kod raportowania wyjątków Node dla wywołań Windows do innego API Windows, który lepiej obsługuje Unicode.
Zobaczmy z Węzeł 7.10 źródeł:
ReportException → AppendExceptionLine → PrintErrorString
W PrintErrorString
, Windows specyficzny odcinek detects output type (tty/console or not): - Dla non-tty/kontekście konsoli zostanie wydrukowana do stderr
(np. jeśli przekierujesz do pliku) - W konsoli cmd (bez przekierowania), będzie to convert tekst z MultiByteToWideChar()
, a następnie pass do WriteConsoleW()
.
Gdybym uruchomić program za pomocą ConEmu (łatwiejsze niż uzyskanie standardowego cmd
pracować z unicode & emotikonami - tak mam trochę leniwy tutaj), widzę coś podobnego jak to, co widziałeś: console.log
nie zostanie wydrukowana emotikony, ale wiadomość emoji w wyjątku zostanie wydrukowana w porządku (nawet w glifie przewijania).
Jeśli przekieruje wszystkie dane wyjściowe do pliku (node test.js > out.txt 2>&1
, tak, że działa również w systemie Windows cmd), otrzymam "czysty" Unicode w obu przypadkach.
Wygląda na to, że program drukuje do stdout
lub stderr
w konsoli systemu Windows, ale przed ponownym drukowaniem konsola wykonuje pewne (złe) czynności związane z ponownym kodowaniem. Gdy program używa interfejsu API konsoli systemu Windows bezpośrednio (wykonując samą konwersję z MultiByteToWideChar
, a następnie napisz na konsolę z WriteConsoleW()
), konsola pokazuje chwalebny niezmieniony emoji.
Gdy program JS używa funkcji console
API do rejestrowania danych, być może Node może spróbować (w systemie Windows) wykryć konsolę i zrobić to samo, co w przypadku zgłaszania wyjątków. Zobacz @BrianNixon's answer, który wyjaśnia, co faktycznie dzieje się w libuv.
Hmm, masz dużo więcej niż ktokolwiek inny. Znalezienie czcionki obsługującej glify jest niezmiennie główną przeszkodą. Ale to problem kodowania, nie całkiem niezwykły, ponieważ glify przewijania znajdują się w płaszczyznach bitów górnych, a filiżanka kawy nie. Prawdopodobnie powinieneś się skupić na tym, dlaczego jest w porządku, gdy jest renderowany na stderr, tak jak to będzie w "rzucie", ale nie na standardowe wyjście. –
@HansPassant pisząc bezpośrednio do 'stderr' nie robi niczego innego niż pisanie bezpośrednio na' stdout', prawdopodobnie trzeba zajrzeć do tego, jak Node.js obsługuje rzutowanie ... – bdukes
Wydaje się, że problem dotyczy Windows. Działa dobrze na moim macu. – hasen