Hello community,

here is the log from the commit of package perl-JSON-Validator for 
openSUSE:Factory checked in at 2020-10-26 16:18:04
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Comparing /work/SRC/openSUSE:Factory/perl-JSON-Validator (Old)
 and      /work/SRC/openSUSE:Factory/.perl-JSON-Validator.new.3463 (New)
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++

Package is "perl-JSON-Validator"

Mon Oct 26 16:18:04 2020 rev:26 rq:841735 version:4.10

Changes:
--------
--- /work/SRC/openSUSE:Factory/perl-JSON-Validator/perl-JSON-Validator.changes  
2020-10-13 15:46:38.373475447 +0200
+++ 
/work/SRC/openSUSE:Factory/.perl-JSON-Validator.new.3463/perl-JSON-Validator.changes
        2020-10-26 16:19:16.419077992 +0100
@@ -1,0 +2,12 @@
+Wed Oct 14 03:11:25 UTC 2020 - Tina Müller <timueller+p...@suse.de>
+
+- updated to 4.10
+   see /usr/share/doc/packages/perl-JSON-Validator/Changes
+
+  4.10 2020-10-13T10:53:11+0900
+   - Add JSON::Validator::Store
+   - Changed JSON::Validator->schema() to also load
+   - JSON::Validator->schema() can handle draft 2019-09 schemas
+   - Documented what is not supported in draft 2019-09
+
+-------------------------------------------------------------------

Old:
----
  JSON-Validator-4.09.tar.gz

New:
----
  JSON-Validator-4.10.tar.gz

++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++

Other differences:
------------------
++++++ perl-JSON-Validator.spec ++++++
--- /var/tmp/diff_new_pack.duymTN/_old  2020-10-26 16:19:17.415078793 +0100
+++ /var/tmp/diff_new_pack.duymTN/_new  2020-10-26 16:19:17.419078796 +0100
@@ -17,7 +17,7 @@
 
 
 Name:           perl-JSON-Validator
-Version:        4.09
+Version:        4.10
 Release:        0
 %define cpan_name JSON-Validator
 Summary:        Validate data against a JSON schema

++++++ JSON-Validator-4.09.tar.gz -> JSON-Validator-4.10.tar.gz ++++++
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/JSON-Validator-4.09/Changes 
new/JSON-Validator-4.10/Changes
--- old/JSON-Validator-4.09/Changes     2020-10-12 04:04:16.000000000 +0200
+++ new/JSON-Validator-4.10/Changes     2020-10-13 03:53:11.000000000 +0200
@@ -1,5 +1,11 @@
 Revision history for perl distribution JSON-Validator
 
+4.10 2020-10-13T10:53:11+0900
+ - Add JSON::Validator::Store
+ - Changed JSON::Validator->schema() to also load
+ - JSON::Validator->schema() can handle draft 2019-09 schemas
+ - Documented what is not supported in draft 2019-09
+
 4.09 2020-10-12T11:04:16+0900
  - Fix handling if "id" and "$id" in subschemas #186
  - Add CONTRIBUTING.md #161
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/JSON-Validator-4.09/MANIFEST 
new/JSON-Validator-4.10/MANIFEST
--- old/JSON-Validator-4.09/MANIFEST    2020-10-12 04:04:17.000000000 +0200
+++ new/JSON-Validator-4.10/MANIFEST    2020-10-13 03:53:12.000000000 +0200
@@ -27,6 +27,7 @@
 lib/JSON/Validator/Schema/Draft4.pm
 lib/JSON/Validator/Schema/Draft6.pm
 lib/JSON/Validator/Schema/Draft7.pm
+lib/JSON/Validator/Store.pm
 lib/JSON/Validator/Util.pm
 Makefile.PL
 MANIFEST                       This list of files
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/JSON-Validator-4.09/META.json 
new/JSON-Validator-4.10/META.json
--- old/JSON-Validator-4.09/META.json   2020-10-12 04:04:17.000000000 +0200
+++ new/JSON-Validator-4.10/META.json   2020-10-13 03:53:12.000000000 +0200
@@ -63,6 +63,6 @@
       },
       "x_IRC" : "irc://irc.freenode.net/#mojo"
    },
-   "version" : "4.09",
+   "version" : "4.10",
    "x_serialization_backend" : "JSON::PP version 4.04"
 }
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/JSON-Validator-4.09/META.yml 
new/JSON-Validator-4.10/META.yml
--- old/JSON-Validator-4.09/META.yml    2020-10-12 04:04:17.000000000 +0200
+++ new/JSON-Validator-4.10/META.yml    2020-10-13 03:53:12.000000000 +0200
@@ -32,5 +32,5 @@
   homepage: https://mojolicious.org
   license: http://www.opensource.org/licenses/artistic-license-2.0
   repository: https://github.com/mojolicious/json-validator.git
-version: '4.09'
+version: '4.10'
 x_serialization_backend: 'CPAN::Meta::YAML version 0.018'
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/JSON-Validator-4.09/lib/JSON/Validator/Schema/Draft201909.pm 
new/JSON-Validator-4.10/lib/JSON/Validator/Schema/Draft201909.pm
--- old/JSON-Validator-4.09/lib/JSON/Validator/Schema/Draft201909.pm    
2020-10-12 03:20:53.000000000 +0200
+++ new/JSON-Validator-4.10/lib/JSON/Validator/Schema/Draft201909.pm    
2020-10-13 02:39:39.000000000 +0200
@@ -35,7 +35,7 @@
       if ($topic->{'$id'} and !ref $topic->{'$id'}) {
         my $id = Mojo::URL->new($topic->{'$id'});
         $id = $id->to_abs($base_url) unless $id->is_abs;
-        $self->_store($id->to_string => $topic);
+        $self->store->add($id->to_string => $topic);
         $base_url = $id;
       }
 
@@ -151,6 +151,36 @@
 This class represents
 
L<https://json-schema.org/specification-links.html#2019-09-formerly-known-as-draft-8>.
 
+Support for parsing the draft is not yet complete. Look at
+L<https://github.com/mojolicious/json-validator/blob/master/t/draft2019-09-acceptance.t>
+for the most recent overview of what is not yet supported.
+
+Currently less than 1% of the official test suite gets skipped. Here is a list 
of known
+limitations:
+
+=over 2
+
+=item * Float and integers are equal up to 64-bit representation limits
+
+This module is unable to say that the 64-bit number "9007199254740992.0" is the
+same as "9007199254740992".
+
+=item * unevaluatedItems
+
+See L</unevaluatedProperties>
+
+=item * unevaluatedProperties
+
+L</unevaluatedItems> and L</unevaluatedProperties> needs to track what has been
+valdated or not using annotations. This is not yet supported.
+
+=item * $recursiveAnchor
+
+Basic support for C<$recursiveRef> is supported, but using it together with
+C<$recursiveAnchor> is not.
+
+=back
+
 =head1 ATTRIBUTES
 
 =head2 specification
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/JSON-Validator-4.09/lib/JSON/Validator/Store.pm 
new/JSON-Validator-4.10/lib/JSON/Validator/Store.pm
--- old/JSON-Validator-4.09/lib/JSON/Validator/Store.pm 1970-01-01 
01:00:00.000000000 +0100
+++ new/JSON-Validator-4.10/lib/JSON/Validator/Store.pm 2020-10-13 
03:35:10.000000000 +0200
@@ -0,0 +1,239 @@
+package JSON::Validator::Store;
+use Mojo::Base -base;
+
+use Mojo::Exception qw(raise);
+use Mojo::File qw(path);
+use Mojo::JSON;
+use Mojo::UserAgent;
+use Mojo::Util qw(url_unescape);
+use JSON::Validator::Schema;
+use JSON::Validator::Util qw(data_section);
+
+use constant BUNDLED_PATH  => path(path(__FILE__)->dirname, 
'cache')->to_string;
+use constant CASE_TOLERANT => File::Spec->case_tolerant;
+
+has cache_paths => sub { [split(/:/, $ENV{JSON_VALIDATOR_CACHE_PATH} || ''), 
BUNDLED_PATH] };
+has schemas     => sub { +{} };
+
+has ua => sub {
+  my $ua = Mojo::UserAgent->new;
+  $ua->proxy->detect;
+  return $ua->max_redirects(3);
+};
+
+sub add {
+  my ($self, $id, $schema) = @_;
+  $id =~ s!(.)#$!$1!;
+  $self->schemas->{$id} = $schema;
+  return $id;
+}
+
+sub exists {
+  my ($self, $id) = @_;
+  return undef unless defined $id;
+  $id =~ s!(.)#$!$1!;
+  return $self->schemas->{$id} && $id;
+}
+
+sub get {
+  my ($self, $id) = @_;
+  return undef unless defined $id;
+  $id =~ s!(.)#$!$1!;
+  return $self->schemas->{$id};
+}
+
+sub load {
+  return
+       $_[0]->_load_from_url($_[1])
+    || $_[0]->_load_from_data($_[1])
+    || $_[0]->_load_from_text($_[1])
+    || $_[0]->_load_from_file($_[1])
+    || $_[0]->_load_from_app($_[1])
+    || $_[0]->get($_[1])
+    || raise 'JSON::Validator::Exception', "Unable to load schema $_[1]";
+}
+
+sub _load_from_app {
+  return undef unless $_[1] =~ m!^/!;
+
+  my ($self, $url, $id) = @_;
+  return $id if $id = $self->exists($url);
+
+  my $tx  = $self->ua->get($url);
+  my $err = $tx->error && $tx->error->{message};
+  raise 'JSON::Validator::Exception', $err if $err;
+  return $self->add($url => _parse($tx->res->body));
+}
+
+sub _load_from_data {
+  return undef unless $_[1] =~ m!^data://([^/]*)/(.*)!;
+
+  my ($self, $url, $id) = @_;
+  return $id if $id = $self->exists($url);
+
+  my ($class, $file) = ($1, $2);    # data://([^/]*)/(.*)
+  my $text = data_section $class, $file, {encoding => 'UTF-8'};
+  raise 'JSON::Validator::Exception', "Could not find $url" unless $text;
+  return $self->add($url => _parse($text));
+}
+
+sub _load_from_file {
+  my ($self, $file) = @_;
+
+  $file =~ s!^file://!!;
+  $file =~ s!#$!!;
+  $file = path(split '/', url_unescape $file);
+  return undef unless -e $file;
+
+  $file = $file->realpath;
+  my $id = Mojo::URL->new->scheme('file')->host('')->path(CASE_TOLERANT ? lc 
$file : "$file");
+  return $self->exists($id) || $self->add($id => _parse($file->slurp));
+}
+
+sub _load_from_text {
+  my ($self, $text) = @_;
+  my $is_scalar_ref = ref $text eq 'SCALAR';
+  return undef unless $is_scalar_ref or $text =~ m!^\s*(?:---|\{)!s;
+
+  my $id = sprintf 'urn:text:%s', Mojo::Util::md5_sum($is_scalar_ref ? $$text 
: $text);
+  return $self->exists($id) || $self->add($id => _parse($is_scalar_ref ? 
$$text : $text));
+}
+
+sub _load_from_url {
+  return undef unless $_[1] =~ m!^https?://!;
+
+  my ($self, $url, $id) = @_;
+  return $id if $id = $self->exists($url);
+
+  $url = Mojo::URL->new($url)->fragment(undef);
+  return $id if $id = $self->exists($url);
+
+  my $cache_path = $self->cache_paths->[0];
+  my $cache_file = Mojo::Util::md5_sum("$url");
+  for (@{$self->cache_paths}) {
+    my $path = path $_, $cache_file;
+    return $self->add($url => _parse($path->slurp)) if -r $path;
+  }
+
+  my $tx  = $self->ua->get($url);
+  my $err = $tx->error && $tx->error->{message};
+  raise 'JSON::Validator::Exception', $err if $err;
+
+  if ($cache_path and $cache_path ne BUNDLED_PATH and -w $cache_path) {
+    $cache_file = path $cache_path, $cache_file;
+    $cache_file->spurt($tx->res->body);
+  }
+
+  return $self->add($url => _parse($tx->res->body));
+}
+
+sub _parse {
+  return Mojo::JSON::decode_json($_[0]) if $_[0] =~ m!^\s*\{!s;
+  return JSON::Validator::Util::_yaml_load($_[0]);
+}
+
+1;
+
+=encoding utf8
+
+=head1 NAME
+
+JSON::Validator::Store - Load and caching JSON schemas
+
+=head1 SYNOPSIS
+
+  use JSON::Validator;
+  my $jv = JSON::Validator->new;
+  $jv->store->add("urn:uuid:ee564b8a-7a87-4125-8c96-e9f123d6766f" => {...});
+  $jv->store->load("http://api.example.com/my/schema.json";);
+
+=head1 DESCRIPTION
+
+L<JSON::Validator::Store> is a class for loading and caching JSON-Schemas.
+
+=head1 ATTRIBUTES
+
+=head2 cache_paths
+
+  my $store     = $store->cache_paths(\@paths);
+  my $array_ref = $store->cache_paths;
+
+A list of directories to where cached specifications are stored. Defaults to
+C<JSON_VALIDATOR_CACHE_PATH> environment variable and the specs that is bundled
+with this distribution.
+
+C<JSON_VALIDATOR_CACHE_PATH> can be a list of directories, each separated by 
":".
+
+See L<JSON::Validator/Bundled specifications> for more details.
+
+=head2 schemas
+
+  my $hash_ref = $store->schemas;
+  my $store = $store->schemas({});
+
+Hold the schemas as data structures. The keys are schema "id".
+
+=head2 ua
+
+  my $ua    = $store->ua;
+  my $store = $store->ua(Mojo::UserAgent->new);
+
+Holds a L<Mojo::UserAgent> object, used by L</schema> to load a JSON schema
+from remote location.
+
+The default L<Mojo::UserAgent> will detect proxy settings and have
+L<Mojo::UserAgent/max_redirects> set to 3.
+
+=head1 METHODS
+
+=head2 add
+
+  my $normalized_id = $store->add($id => \%schema);
+
+Used to add a schema data structure. Note that C<$id> might not be the same as
+C<$normalized_id>.
+
+=head2 exists
+
+  my $normalized_id = $store->exists($id);
+
+Returns a C<$normalized_id> if it is present in the L</schemas>.
+
+=head2 get
+
+  my $schema = $store->get($normalized_id);
+
+Used to retrieve a C<$schema> added by L</add> or L</load>.
+
+=head2 load
+
+  my $normalized_id = $store->load('https://...');
+  my $normalized_id = $store->load('data://main/foo.json');
+  my $normalized_id = $store->load('---\nid: yaml');
+  my $normalized_id = $store->load('{"id":"yaml"}');
+  my $normalized_id = $store->load(\$text);
+  my $normalized_id = $store->load('/path/to/foo.json');
+  my $normalized_id = $store->load('file:///path/to/foo.json');
+  my $normalized_id = $store->load('/load/from/ua-server-app');
+
+Can load a C<$schema> from many different sources. The input can be a string or
+a string-like object, and the L</load> method will try to resolve it in the
+order listed in above.
+
+Loading schemas from C<$text> will generate an C<$normalized_id> in L</schemas>
+looking like "urn:text:$text_checksum". This might change in the future!
+
+Loading files from disk will result in a C<$normalized_id> that always start
+with "file://".
+
+Loading can also be done with relative path, which will then load from:
+
+  $store->ua->server->app;
+
+This method is EXPERIMENTAL, but unlikely to change significantly.
+
+=head1 SEE ALSO
+
+L<JSON::Validator>.
+
+=cut
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/JSON-Validator-4.09/lib/JSON/Validator.pm 
new/JSON-Validator-4.10/lib/JSON/Validator.pm
--- old/JSON-Validator-4.09/lib/JSON/Validator.pm       2020-10-12 
04:04:16.000000000 +0200
+++ new/JSON-Validator-4.10/lib/JSON/Validator.pm       2020-10-13 
03:53:11.000000000 +0200
@@ -2,42 +2,44 @@
 use Mojo::Base -base;
 use Exporter 'import';
 
-use Carp 'confess';
+use Carp qw(confess);
 use JSON::Validator::Formats;
-use JSON::Validator::Joi;
 use JSON::Validator::Ref;
-use JSON::Validator::Schema;
-use JSON::Validator::Util qw(E data_checksum data_section data_type is_type 
json_pointer prefix_errors schema_type);
-use List::Util 'uniq';
-use Mojo::File 'path';
+use JSON::Validator::Store;
+use JSON::Validator::Util qw(E data_checksum data_type is_type json_pointer 
prefix_errors schema_type);
+use List::Util qw(uniq);
+use Mojo::File qw(path);
 use Mojo::JSON qw(false true);
 use Mojo::URL;
-use Mojo::Util qw(url_unescape sha1_sum);
+use Mojo::Util qw(sha1_sum);
 use Scalar::Util qw(blessed refaddr);
 
-use constant CASE_TOLERANT   => File::Spec->case_tolerant;
-use constant DEBUG           => $ENV{JSON_VALIDATOR_DEBUG} || 0;
 use constant RECURSION_LIMIT => $ENV{JSON_VALIDATOR_RECURSION_LIMIT} || 100;
 
-our $VERSION = '4.09';
+our $VERSION = '4.10';
 our @EXPORT_OK = qw(joi validate_json);
 
 our %SCHEMAS = (
-  'http://json-schema.org/draft-04/schema#' => '+Draft4',
-  'http://json-schema.org/draft-06/schema#' => '+Draft6',
-  'http://json-schema.org/draft-07/schema#' => '+Draft7',
+  'http://json-schema.org/draft-04/schema#'      => '+Draft4',
+  'http://json-schema.org/draft-06/schema#'      => '+Draft6',
+  'http://json-schema.org/draft-07/schema#'      => '+Draft7',
+  'https://json-schema.org/draft/2019-09/schema' => '+Draft201909',
 );
 
-my $BUNDLED_CACHE_DIR = path(path(__FILE__)->dirname, qw(Validator cache));
-my $HTTP_SCHEME_RE    = qr{^https?:};
+has formats                   => sub { shift->_build_formats };
+has recursive_data_protection => 1;
 
-has cache_paths => sub {
-  return [split(/:/, $ENV{JSON_VALIDATOR_CACHE_PATH} || ''), 
$BUNDLED_CACHE_DIR];
+has store => sub {
+  my $self = shift;
+  my %attrs;
+  $attrs{$_} = delete $self->{$_} for grep { $self->{$_} } qw(cache_paths ua);
+  return JSON::Validator::Store->new(%attrs);
 };
 
-has formats => sub { shift->_build_formats };
-
-has recursive_data_protection => 1;
+# store proxy attributes
+for my $method (qw(cache_paths ua)) {
+  Mojo::Util::monkey_patch(__PACKAGE__, $method => sub { 
shift->store->$method(@_) });
+}
 
 sub version {
   my $self = shift;
@@ -47,14 +49,6 @@
   $self;
 }
 
-has ua => sub {
-  require Mojo::UserAgent;
-  my $ua = Mojo::UserAgent->new;
-  $ua->proxy->detect;
-  $ua->max_redirects(3);
-  $ua;
-};
-
 sub bundle {
   my ($self, $args) = @_;
   my $cloner;
@@ -145,6 +139,7 @@
 
 sub joi {
   Mojo::Util::deprecated('JSON::Validator::joi() is replaced by 
JSON::Validator::Joi::joi().');
+  require JSON::Validator::Joi;
   return JSON::Validator::Joi->new unless @_;
   my ($data, $joi) = @_;
   return $joi->validate($data, $joi);
@@ -284,7 +279,7 @@
       if ($topic->{$id_key} and !ref $topic->{$id_key}) {
         my $id = Mojo::URL->new($topic->{$id_key});
         $id = $id->to_abs($base_url) unless $id->is_abs;
-        $self->_store($id->to_string => $topic);
+        $self->store->add($id => $topic);
         $base_url = $id;
       }
 
@@ -312,87 +307,22 @@
 
 sub _id_key { ($_[0]->{version} || 4) < 7 ? 'id' : '$id' }
 
-sub _load_schema {
-  my ($self, $url) = @_;
-
-  my $cached;
-  return $cached, $url if $cached = $self->_store($url);
-
-  if ($url =~ m!^https?://!) {
-    warn "[JSON::Validator] Loading schema from URL $url\n" if DEBUG;
-    return 
$self->_load_schema_from_url(Mojo::URL->new($url)->fragment(undef)), "$url";
-  }
-
-  if ($url =~ m!^data://([^/]*)/(.*)!) {
-    my ($class, $file) = ($1, $2);
-    my $text = data_section $class, $file, {confess => 1, encoding => 'UTF-8'};
-    return $self->_load_schema_from_text(\$text), "$url";
-  }
-
-  if ($url =~ m!^\s*[\[\{]!) {
-    warn "[JSON::Validator] Loading schema from string.\n" if DEBUG;
-    return $self->_load_schema_from_text(\$url), '';
-  }
-
-  my $file = $url;
-  $file =~ s!^file://!!;
-  $file =~ s!#$!!;
-  $file = path(split '/', url_unescape $file);
-  if (-e $file) {
-    $file = $file->realpath;
-    warn "[JSON::Validator] Loading schema from file: $file\n" if DEBUG;
-    $url = Mojo::URL->new->scheme('file')->host('')->path(CASE_TOLERANT ? lc 
$file : "$file");
-    return $cached, $url if $cached = $self->_store($url);
-    return $self->_load_schema_from_text(\$file->slurp), $url;
-  }
-  elsif ($url =~ m!^/! and $self->ua->server->app) {
-    warn "[JSON::Validator] Loading schema from URL $url\n" if DEBUG;
-    return 
$self->_load_schema_from_url(Mojo::URL->new($url)->fragment(undef)), "$url";
-  }
-
-  confess "Unable to load schema '$url' ($file)";
-}
-
-sub _load_schema_from_text {
-  my ($self, $text) = @_;
-  return $$text =~ /^\s*\{/s ? Mojo::JSON::decode_json($$text) : 
JSON::Validator::Util::_yaml_load($$text);
-}
-
-sub _load_schema_from_url {
-  my ($self, $url) = @_;
-  my $cache_path = $self->cache_paths->[0];
-  my $cache_file = Mojo::Util::md5_sum("$url");
-
-  for (@{$self->cache_paths}) {
-    my $path = path $_, $cache_file;
-    warn "[JSON::Validator] Looking for cached spec $path ($url)\n" if DEBUG;
-    next unless -r $path;
-    return $self->_load_schema_from_text(\$path->slurp);
-  }
-
-  my $tx  = $self->ua->get($url);
-  my $err = $tx->error && $tx->error->{message};
-  confess "GET $url == $err"               if DEBUG and $err;
-  die "[JSON::Validator] GET $url == $err" if $err;
-
-  if ($cache_path and ($cache_path ne $BUNDLED_CACHE_DIR or 
$ENV{JSON_VALIDATOR_CACHE_ANYWAYS}) and -w $cache_path) {
-    $cache_file = path $cache_path, $cache_file;
-    warn "[JSON::Validator] Caching $url to $cache_file\n" unless 
$ENV{HARNESS_ACTIVE};
-    $cache_file->spurt($tx->res->body);
-  }
-
-  return $self->_load_schema_from_text(\$tx->res->body);
-}
-
 sub _new_schema {
-  my ($self, $schema, %attrs) = @_;
-  return $schema if blessed $schema and $schema->can('specification');
+  my ($self, $source, %attrs) = @_;
+  return $source if blessed $source and $source->can('specification');
 
   # Compat with load_and_validate_schema()
   $attrs{specification} = delete $attrs{schema} if $attrs{schema};
 
-  if (!$attrs{specification} and is_type $schema, 'HASH') {
-    $attrs{specification} = $schema->{'$schema'} if $schema->{'$schema'};
+  my $loadable
+    = (blessed $source && ($source->can('scheme') || 
$source->isa('Mojo::File')))
+    || -f $source
+    || (!ref $source && $source =~ /^\w/);
+
+  my $store  = $self->store;
+  my $schema = $loadable ? $store->get($store->load($source)) : $source;
+  if (!$attrs{specification} and is_type $schema, 'HASH' and 
$schema->{'$schema'}) {
+    $attrs{specification} = $schema->{'$schema'};
   }
   if (!$attrs{specification} and $self->{version}) {
     $attrs{specification} = sprintf 
'http://json-schema.org/draft-%02s/schema#', $self->{version};
@@ -400,11 +330,9 @@
 
   $attrs{formats} ||= $self->{formats} if $self->{formats};
   $attrs{version} ||= $self->{version} if $self->{version};
-  $attrs{schemas} ||= $self->{schemas} ||= {};
-  $attrs{$_} = $self->$_ for qw(cache_paths ua);
+  $attrs{store} = $store;
 
-  my $schema_obj = $self->_schema_class($attrs{specification} || 
$schema)->new($schema, %attrs);
-  return $schema_obj;
+  return $self->_schema_class($attrs{specification} || $schema)->new($source, 
%attrs);
 }
 
 sub _node {
@@ -447,23 +375,24 @@
   my ($self, $schema, $nested) = @_;
   return $schema if is_type $schema, 'BOOL';
 
-  my ($id_key, $id, $resolved) = ($self->_id_key);
+  my ($id_key, $id, $cached_id, $resolved) = ($self->_id_key);
   if (ref $schema eq 'HASH') {
-    $id       = $schema->{$id_key} // '';
-    $resolved = $self->_store($id) // $schema;
+    $id        = $schema->{$id_key} // '';
+    $cached_id = $self->store->exists($id);
+    $resolved  = $cached_id ? $self->store->get($cached_id) : $schema;
   }
   else {
-    ($resolved, $id) = $self->_load_schema($schema);
-    $id = $resolved->{$id_key} if is_type($resolved, 'HASH') and 
$resolved->{$id_key};
+    $cached_id = $self->store->exists($id);
+    $id        = $cached_id // $self->store->load($schema);
+    $resolved  = $self->store->get($id);
+    $id        = $resolved->{$id_key} if is_type($resolved, 'HASH') and 
$resolved->{$id_key};
   }
 
+  $cached_id //= '';
   $id = Mojo::URL->new("$id");
   $self->_register_root_schema($id => $resolved) if !$nested and "$id";
-
-  unless ($self->_store($id)) {
-    $self->_store($id => $resolved) if "$id";
-    $self->_find_and_resolve_refs($id => $resolved);
-  }
+  $self->store->add($id => $resolved)            if "$id"    and "$id" ne 
$cached_id;
+  $self->_find_and_resolve_refs($id => $resolved) unless $cached_id;
 
   return $resolved;
 }
@@ -477,8 +406,8 @@
   my $other;
 
   $fqn = $fqn->to_abs($base_url) if "$base_url";
-  $other //= $self->_store($fqn);
-  $other //= $self->_store($fqn->clone->fragment(undef));
+  $other //= $self->store->get($fqn);
+  $other //= $self->store->get($fqn->clone->fragment(undef));
   $other //= $self->_resolve($fqn->clone->fragment(undef), 1) if $fqn->is_abs 
&& $fqn ne $base_url;
   $other //= $schema;
 
@@ -513,13 +442,6 @@
   return $package;
 }
 
-sub _store {
-  my ($self, $id, $schema) = @_;
-  $id =~ s!(.)#$!$1!;
-  return $self->{schemas}{$id} unless defined $schema;
-  return $self->{schemas}{$id} = $schema;
-}
-
 sub _validate {
   my ($self, $data, $path, $schema) = @_;
   $schema = $self->_ref_to_schema($schema);
@@ -609,7 +531,7 @@
     push @errors, @e;
   }
 
-  # favour a non-type error from one of the rules
+  # favor a non-type error from one of the rules
   if (my @e = grep { $_->details->[1] ne 'type' or $_->path ne ($path || '/') 
} @errors) {
     return @e;
   }
@@ -1134,16 +1056,7 @@
 
 =head2 cache_paths
 
-  my $jv        = $jv->cache_paths(\@paths);
-  my $array_ref = $jv->cache_paths;
-
-A list of directories to where cached specifications are stored. Defaults to
-C<JSON_VALIDATOR_CACHE_PATH> environment variable and the specs that is bundled
-with this distribution.
-
-C<JSON_VALIDATOR_CACHE_PATH> can be a list of directories, each separated by 
":".
-
-See L</Bundled specifications> for more details.
+Proxy attribtue for L<JSON::Validator::Store/cache_paths>.
 
 =head2 formats
 
@@ -1177,14 +1090,7 @@
 
 =head2 ua
 
-  my $ua = $jv->ua;
-  my $jv = $jv->ua(Mojo::UserAgent->new);
-
-Holds a L<Mojo::UserAgent> object, used by L</schema> to load a JSON schema
-from remote location.
-
-The default L<Mojo::UserAgent> will detect proxy settings and have
-L<Mojo::UserAgent/max_redirects> set to 3.
+Proxy attribtue for L<JSON::Validator::Store/ua>.
 
 =head2 version
 
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/JSON-Validator-4.09/t/bundle.t 
new/JSON-Validator-4.10/t/bundle.t
--- old/JSON-Validator-4.09/t/bundle.t  2020-10-09 00:10:54.000000000 +0200
+++ new/JSON-Validator-4.10/t/bundle.t  2020-10-13 01:13:59.000000000 +0200
@@ -8,18 +8,11 @@
 my $jv      = JSON::Validator->new;
 my $bundled;
 
-{
-  note 'bundle files';
-  local $ENV{JSON_VALIDATOR_CACHE_ANYWAYS} = 1;
-  $jv->_load_schema_from_url("http://json-schema.org/draft-04/schema";);
-  $jv->_load_schema_from_url("http://json-schema.org/draft-06/schema";);
-  $jv->_load_schema_from_url("http://json-schema.org/draft-07/schema";);
-}
-
 my $schema
   = JSON::Validator::Schema::Draft7->new({
   definitions => {name => {type => 'string'}}, surname => {'$ref' => 
'#/definitions/name'},
   });
+
 is $schema->bundle({replace => 1})->data->{surname}{type}, 'string', 
"schema->bundle";
 
 note 'Run multiple times to make sure _reset() works';
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/JSON-Validator-4.09/t/draft2019-09.t 
new/JSON-Validator-4.10/t/draft2019-09.t
--- old/JSON-Validator-4.09/t/draft2019-09.t    2020-10-12 00:56:10.000000000 
+0200
+++ new/JSON-Validator-4.10/t/draft2019-09.t    2020-10-13 03:47:15.000000000 
+0200
@@ -20,12 +20,21 @@
 is $schema->data->{type}, 'integer', 'foo anchor type';
 
 note 'recursiveRef, without recursiveAnchor';
-$schema->data('data://main/tree.json')->resolve;
-$schema->data('data://main/recursiveRef.json')->resolve;
-is $schema->data->{type}, 'object', 'recursiveRef type';
-is $schema->data->{properties}{data}, true, 'recursiveRef properties data';
-is $schema->data->{properties}{children}{items}{type}, 'object', 'recursiveRef 
properties data items';
-is 
$schema->data->{properties}{children}{items}{properties}{children}{items}{type},
 'object', 'recursive';
+my $jv = JSON::Validator->new->schema('data://main/tree.json');
+$jv->schema('data://main/recursiveRef.json');
+isa_ok $jv->schema, 'JSON::Validator::Schema::Draft201909';
+is $jv->schema->data->{type}, 'object', 'recursiveRef type';
+is $jv->schema->data->{properties}{data}, true, 'recursiveRef properties data';
+is $jv->schema->data->{properties}{children}{items}{type}, 'object', 
'recursiveRef properties data items';
+is 
$jv->schema->data->{properties}{children}{items}{properties}{children}{items}{type},
 'object', 'recursive';
+is_deeply [sort keys %{$jv->store->schemas}],
+  [qw(data://main/recursiveRef.json data://main/tree.json urn:recursiveRef 
urn:tree)], 'schemas in the store';
+
+{
+  no warnings 'redefine';
+  local *JSON::Validator::_load_from_data = sub { die 'not cached' };
+  ok eval { JSON::Validator->new->schema('data://main/tree.json') }, 'cached' 
or diag $@;
+}
 
 done_testing;
 
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/JSON-Validator-4.09/t/jv-boolean.t 
new/JSON-Validator-4.10/t/jv-boolean.t
--- old/JSON-Validator-4.09/t/jv-boolean.t      2020-10-09 00:20:23.000000000 
+0200
+++ new/JSON-Validator-4.10/t/jv-boolean.t      2020-10-13 02:12:33.000000000 
+0200
@@ -33,7 +33,7 @@
 validate_ok false, $bool_constant_true, E('/', q{Does not match const: true.});
 
 note 'boolean objects';
-my $data = jv->_load_schema_from_text(\"---\nv: true\n");
+my $data = jv->store->get(jv->store->load(\"---\nv: true\n"));
 isa_ok($data->{v}, 'JSON::PP::Boolean');
 validate_ok $data, $schema;
 
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/JSON-Validator-4.09/t/load-data.t 
new/JSON-Validator-4.10/t/load-data.t
--- old/JSON-Validator-4.09/t/load-data.t       2020-10-09 00:22:59.000000000 
+0200
+++ new/JSON-Validator-4.10/t/load-data.t       2020-10-13 00:15:59.000000000 
+0200
@@ -31,7 +31,7 @@
 sub validate { $jv->schema($_[1])->validate($_[2]) }
 
 package main;
-is_deeply [sort keys %{$jv->{schemas}}], [qw(data:///spec.json 
data://main/spec.json)], 'schemas in store';
+is_deeply [sort keys %{$jv->store->schemas}], [qw(data:///spec.json 
data://main/spec.json)], 'schemas in store';
 
 done_testing;
 
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/JSON-Validator-4.09/t/load-file.t 
new/JSON-Validator-4.10/t/load-file.t
--- old/JSON-Validator-4.09/t/load-file.t       2020-10-12 01:05:18.000000000 
+0200
+++ new/JSON-Validator-4.10/t/load-file.t       2020-10-13 00:10:28.000000000 
+0200
@@ -12,10 +12,10 @@
 isa_ok $jv->schema, 'JSON::Validator::Schema';
 is $jv->schema->get('/title'), 'Example Schema', 'got example schema';
 is $jv->schema->id, $id, 'schema id';
-is_deeply [sort keys %{$jv->{schemas}}], [$jv->schema->id], 'schemas in store';
+is_deeply [sort keys %{$jv->store->schemas}], [$jv->schema->id], 'schemas in 
store';
 
 ok eval { $jv->schema($spec->to_string) }, 'loaded from file:// again' or diag 
$@;
 is $jv->schema->id, $id, 'schema id again';
-is_deeply [sort keys %{$jv->{schemas}}], [$jv->schema->id], 'schemas in store 
again';
+is_deeply [sort keys %{$jv->store->schemas}], [$jv->schema->id], 'schemas in 
store again';
 
 done_testing;
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/JSON-Validator-4.09/t/load-from-app.t 
new/JSON-Validator-4.10/t/load-from-app.t
--- old/JSON-Validator-4.09/t/load-from-app.t   2020-10-09 00:22:59.000000000 
+0200
+++ new/JSON-Validator-4.10/t/load-from-app.t   2020-10-13 02:12:33.000000000 
+0200
@@ -7,18 +7,28 @@
 $jv->ua->server->app(Mojolicious->new);
 $jv->ua->server->app->routes->get(
   '/spec' => sub {
-    shift->render(json => {'$ref' => 'http://swagger.io/v2/schema.json'});
+    my $c = shift;
+    die 'not cached' if $c->stash('from_cache');
+    $c->render(json => {'$ref' => 'http://swagger.io/v2/schema.json'});
   }
 );
 
-# Some CPAN testers says: [JSON::Validator] GET http://127.0.0.1:61594/api == 
Service Unavailable at JSON/Validator.pm
+# Some CPAN testers says "Service Unavailable"
 eval { $jv->schema('/spec') };
 plan skip_all => $@ if $@ =~ /\sGET\s/i;
 
+is $jv->store->ua, $jv->ua, 'shared ua';
 is $@, '', 'loaded schema from app';
 is $jv->get('/properties/swagger/enum/0'), '2.0', 'loaded schema structure';
 
-is_deeply [sort keys %{$jv->{schemas}}],
+is_deeply [sort keys %{$jv->store->schemas}],
   ['/spec', 'http://json-schema.org/draft-04/schema', 
'http://swagger.io/v2/schema.json'], 'schemas in store';
 
+$jv->ua->server->app->defaults(from_cache => 1);
+ok $jv->schema('/spec'), 'loaded from cache';
+
+$jv->store->schemas({});
+eval { $jv->schema('/spec') };
+like $@, qr{Internal Server Error}, 'cache cleared';
+
 done_testing;
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/JSON-Validator-4.09/t/load-http.t 
new/JSON-Validator-4.10/t/load-http.t
--- old/JSON-Validator-4.09/t/load-http.t       2020-10-09 00:22:59.000000000 
+0200
+++ new/JSON-Validator-4.10/t/load-http.t       2020-10-13 00:10:28.000000000 
+0200
@@ -12,7 +12,7 @@
 like $jv->schema->get('/title'), qr{swagger}i, 'got swagger spec';
 ok $jv->schema->get('/patternProperties/^x-/description'), 'resolved 
vendorExtension $ref';
 
-is_deeply [sort keys %{$jv->{schemas}}],
+is_deeply [sort keys %{$jv->store->schemas}],
   ['http://json-schema.org/draft-04/schema', 
'http://swagger.io/v2/schema.json'], 'schemas in store';
 
 done_testing;
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/JSON-Validator-4.09/t/load-json.t 
new/JSON-Validator-4.10/t/load-json.t
--- old/JSON-Validator-4.09/t/load-json.t       2020-10-09 00:22:59.000000000 
+0200
+++ new/JSON-Validator-4.10/t/load-json.t       2020-10-13 01:00:34.000000000 
+0200
@@ -22,6 +22,6 @@
 is(eval { JSON::Validator->new->schema('http://swagger.io/v2/schema.json'); 42 
}, 42, 'loaded from cache') or diag $@;
 
 like $jv->schema->id, qr{^file:.*person\.json}, 'schema id';
-is_deeply [sort keys %{$jv->{schemas}}], [$jv->schema->id], 'schemas in store';
+is_deeply [sort keys %{$jv->store->schemas}], [$jv->schema->id], 'schemas in 
store';
 
 done_testing;
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/JSON-Validator-4.09/t/predictable-errors.t 
new/JSON-Validator-4.10/t/predictable-errors.t
--- old/JSON-Validator-4.09/t/predictable-errors.t      2020-10-05 
23:31:23.000000000 +0200
+++ new/JSON-Validator-4.10/t/predictable-errors.t      2020-10-12 
23:33:35.000000000 +0200
@@ -11,15 +11,11 @@
 # so looping around like this will execute the test with all kinds of
 # different internal ordering
 for (1 .. 20) {
-  $jv->schema(my $schema_text
-      = '{ "type": "object", "properties": { "ant": { "type": "string" }, 
"bat": { "type": "array" }, "cat": { "type": "object" }, "dog": { "type": 
"integer" } } }'
-  );
-  my @errors = $jv->validate($broken_data);
-  is_deeply([map { $_->path } @errors], [qw(/ant /bat /cat /dog)], "got errors 
in expected order");
-  if (!$num_errors) {    # only run this test once
-    $num_errors = $jv->validate($broken_data);
-    is($num_errors, 4, "in scalar context got the right number of errors");
-  }
+  my $schema_text
+    = 
'{"type":"object","properties":{"ant":{"type":"string"},"bat":{"type":"array"},"cat":{"type":"object"},"dog":{"type":"integer"}}}';
+  $jv->schema($schema_text);
+  is_deeply [map { $_->path } $jv->validate($broken_data)], [qw(/ant /bat /cat 
/dog)], 'got errors in expected order';
+  is scalar $jv->validate($broken_data), 4, 'in scalar context got the right 
number of errors';
 }
 
 done_testing;


Reply via email to