Estou aprendendo Perl. Consegui iterar com sucesso em uma coleção JSON quando os objetos estavam contidos em uma matriz. No entanto, não consigo entender como trabalhar com dados JSON onde os objetos não estão em uma matriz e possuem identificadores aleatórios (por exemplo, 0y7vfr1234
) que não são conhecidos antecipadamente . Aqui estão alguns dados de exemplo com a estrutura que estou tentando ler, atualizar e salvar em um arquivo.
{
"0y7vfr1234": {
"username": "[email protected]",
"password": "some-random-password123",
"uri": "ww1.example.com",
"index": 14
},
"v2rbz1568": {
"username": "[email protected]",
"password": "some-random-password125",
"uri": "ww3.example.com",
"index": 29
},
"0zjk1156": {
"username": "[email protected]",
"password": "some-random-password124",
"uri": "ww2.example.com",
"index": 38
}
}
Se esses objetos estivessem todos dentro de um array, eu faria assim:
#!/usr/bin/perl
use lib qw(..);
use JSON;
binmode STDOUT, ":utf8";
use utf8;
use strict;
use warnings;
my $filename1 = 'input.json';
my $filename2 = 'serverlist.txt';
my $json_text = do {
open(my $json_fh, "<:encoding(UTF-8)", $filename1)
or die("Can't open \$filename1\": $!\n");
local $/;
<$json_fh>
};
open my $server_list, '<', $filename2 or die "Can't open $filename2: $!";
my @server_list = <$server_list>;
close $server_list or die "Can't close $server_list: $!";
my $json = JSON->new;
my $data = $json->decode($json_text);
my $aref = $data->{the_array_name};
for my $setting (@$aref) {
if (length $setting->{uri}) { #no warnings
$setting->{uri} =~ m/^ww(\d+)\.example.com/;
my $server_number = $1;
print "checking $server_number ... \n";
if (grep{/$setting->{uri}/} @server_list) {
print "server number is: $server_number\n";
} else {
# 1. iterate through the sorted list
foreach (@server_list)
{
$_ =~ m/^ww(\d+)\.example.com/;
my $new_num = $1;
# 2. find the next match in order
if ( $new_num > $server_number ) {
print "Found it: new server number $new_num is greater than $server_number\n";
# TODO 3. check that it does not exist in $data->{the_array_name};
# 4. replace $setting->{uri} with new value
my $new_server = $_;
$new_server =~ s/\s+$//;
$setting->{uri} = $new_server;
last;
}
}
}
}
}
# 5. save JSON as a file to disk.
my $filename3 = 'output.json';
open my $proxy_settings, '>', $filename3 or die "Can't open $filename3: $!";
print $proxy_settings encode_json($data);
close $proxy_settings or die "Can't close $proxy_settings: $!";
Esse é o primeiro Perl que eu já escrevi. Eu não entendo cada linha dele 100% ainda. (Exemplo: binmode STDOUT, ":utf8";
). Tenho certeza de que está longe de ser o ideal e continuarei trabalhando nisso. Minha pergunta é, como ele pode ser modificado para funcionar com a estrutura JSON mostrada acima?
Estou usando perl 5, versão 30 no Linux.
Assim :
Resultado