From 46eab3f23427ab1151a7b4187b365bf1e211ec12 Mon Sep 17 00:00:00 2001 From: Charles McGarvey Date: Sun, 22 Mar 2020 01:58:09 -0600 Subject: [PATCH] fix encoding issues --- lib/GraphQL/Client/CLI.pm | 20 ++++++++++++++------ lib/GraphQL/Client/http.pm | 2 +- t/http.t | 2 +- 3 files changed, 16 insertions(+), 8 deletions(-) diff --git a/lib/GraphQL/Client/CLI.pm b/lib/GraphQL/Client/CLI.pm index 81fb47a..66b391c 100644 --- a/lib/GraphQL/Client/CLI.pm +++ b/lib/GraphQL/Client/CLI.pm @@ -4,14 +4,17 @@ package GraphQL::Client::CLI; use warnings; use strict; -use Text::ParseWords; +use Encode qw(decode); use Getopt::Long 2.39 qw(GetOptionsFromArray); use GraphQL::Client; -use JSON::MaybeXS qw(encode_json); +use JSON::MaybeXS; +use Text::ParseWords; use namespace::clean; our $VERSION = '999.999'; # VERSION +my $JSON = JSON::MaybeXS->new(canonical => 1); + sub _croak { require Carp; goto &Carp::croak } sub new { @@ -67,6 +70,7 @@ sub main { if ($query eq '-') { print STDERR "Interactive mode engaged! Waiting for a query on ...\n" if -t STDIN; ## no critic (InputOutput::ProhibitInteractiveTest) + binmode(STDIN, 'encoding(UTF-8)'); $query = do { local $/; }; } @@ -80,6 +84,7 @@ sub main { *STDOUT = $out; } + binmode(STDOUT, 'encoding(UTF-8)'); _print_data($data, $format); exit($unpack && $err ? 1 : 0); @@ -91,6 +96,9 @@ sub _get_options { unshift @args, shellwords($ENV{GRAPHQL_CLIENT_OPTIONS} || ''); + # assume UTF-8 args if non-ASCII + @args = map { decode('UTF-8', $_) } @args if grep { /\P{ASCII}/ } @args; + my %options = ( format => 'json:pretty', unpack => 0, @@ -124,7 +132,7 @@ sub _get_options { die "Two or more --variable keys are incompatible.\n" if $@; } elsif ($options{variables}) { - $options{variables} = eval { JSON::MaybeXS->new->decode($options{variables}) }; + $options{variables} = eval { $JSON->decode($options{variables}) }; die "The --variables JSON does not parse.\n" if $@; } @@ -136,9 +144,9 @@ sub _stringify { if (ref($item) eq 'ARRAY') { my $first = @$item && $item->[0]; return join(',', @$item) if !ref($first); - return join(',', map { encode_json($_) } @$item); + return join(',', map { $JSON->encode($_) } @$item); } - return encode_json($item) if ref($item) eq 'HASH'; + return $JSON->encode($item) if ref($item) eq 'HASH'; return $item; } @@ -146,7 +154,7 @@ sub _print_data { my ($data, $format) = @_; $format = lc($format || 'json:pretty'); if ($format eq 'json' || $format eq 'json:pretty') { - my %opts = (allow_nonref => 1, canonical => 1, utf8 => 1); + my %opts = (allow_nonref => 1, canonical => 1); $opts{pretty} = 1 if $format eq 'json:pretty'; print JSON::MaybeXS->new(%opts)->encode($data); } diff --git a/lib/GraphQL/Client/http.pm b/lib/GraphQL/Client/http.pm index 77a089f..795f2e7 100644 --- a/lib/GraphQL/Client/http.pm +++ b/lib/GraphQL/Client/http.pm @@ -42,7 +42,7 @@ sub execute { my $encoded_data = $self->json->encode($data); $options->{content} = $encoded_data; $options->{headers}{'content-length'} = length $encoded_data; - $options->{headers}{'content-type'} = 'application/json'; + $options->{headers}{'content-type'} = 'application/json;charset=UTF-8'; } return $self->_handle_response($self->any_ua->request($method, $url, $options)); diff --git a/t/http.t b/t/http.t index 61a9ccf..cad84fd 100755 --- a/t/http.t +++ b/t/http.t @@ -57,7 +57,7 @@ subtest 'POST request' => sub { is($req->[0], 'POST', 'method is POST'); is($req->[2]{content}, '{"query":"{hello}"}', 'encoded body as JSON'); - is($req->[2]{headers}{'content-type'}, 'application/json', 'set content-type to json'); + is($req->[2]{headers}{'content-type'}, 'application/json;charset=UTF-8', 'set content-type to json'); }; subtest 'GET request' => sub { -- 2.43.0