Filename | /Users/ether/.perlbrew/libs/36.0@std/lib/perl5/JSON/Schema/Modern/Vocabulary/OpenAPI.pm |
Statements | Executed 2053 statements in 5.41ms |
Calls | P | F | Exclusive Time |
Inclusive Time |
Subroutine |
---|---|---|---|---|---|
2018 | 1 | 1 | 2.46ms | 2.46ms | keywords | JSON::Schema::Modern::Vocabulary::OpenAPI::
1 | 1 | 1 | 47µs | 51µs | BEGIN@1.320 | Module::Runtime::
1 | 1 | 1 | 45µs | 72µs | BEGIN@13 | JSON::Schema::Modern::Vocabulary::OpenAPI::
1 | 1 | 1 | 33µs | 370µs | BEGIN@10 | JSON::Schema::Modern::Vocabulary::OpenAPI::
1 | 1 | 1 | 16µs | 16µs | BEGIN@9 | JSON::Schema::Modern::Vocabulary::OpenAPI::
1 | 1 | 1 | 14µs | 908µs | BEGIN@11 | JSON::Schema::Modern::Vocabulary::OpenAPI::
1 | 1 | 1 | 10µs | 56µs | BEGIN@17 | JSON::Schema::Modern::Vocabulary::OpenAPI::
1 | 1 | 1 | 9µs | 24µs | BEGIN@14 | JSON::Schema::Modern::Vocabulary::OpenAPI::
1 | 1 | 1 | 9µs | 49µs | BEGIN@2.321 | Module::Runtime::
1 | 1 | 1 | 8µs | 111µs | BEGIN@12 | JSON::Schema::Modern::Vocabulary::OpenAPI::
1 | 1 | 1 | 8µs | 16µs | BEGIN@15 | JSON::Schema::Modern::Vocabulary::OpenAPI::
1 | 1 | 1 | 8µs | 15µs | BEGIN@16 | JSON::Schema::Modern::Vocabulary::OpenAPI::
1 | 1 | 1 | 6µs | 321µs | BEGIN@18 | JSON::Schema::Modern::Vocabulary::OpenAPI::
5 | 1 | 1 | 5µs | 5µs | _traverse_keyword_externalDocs | JSON::Schema::Modern::Vocabulary::OpenAPI::
0 | 0 | 0 | 0s | 0s | _eval_keyword_discriminator | JSON::Schema::Modern::Vocabulary::OpenAPI::
0 | 0 | 0 | 0s | 0s | _eval_keyword_example | JSON::Schema::Modern::Vocabulary::OpenAPI::
0 | 0 | 0 | 0s | 0s | _eval_keyword_externalDocs | JSON::Schema::Modern::Vocabulary::OpenAPI::
0 | 0 | 0 | 0s | 0s | _eval_keyword_xml | JSON::Schema::Modern::Vocabulary::OpenAPI::
0 | 0 | 0 | 0s | 0s | _traverse_keyword_discriminator | JSON::Schema::Modern::Vocabulary::OpenAPI::
0 | 0 | 0 | 0s | 0s | _traverse_keyword_example | JSON::Schema::Modern::Vocabulary::OpenAPI::
0 | 0 | 0 | 0s | 0s | _traverse_keyword_xml | JSON::Schema::Modern::Vocabulary::OpenAPI::
1 | 1 | 1 | 0s | 0s | vocabulary | JSON::Schema::Modern::Vocabulary::OpenAPI::
Line | State ments |
Time on line |
Calls | Time in subs |
Code |
---|---|---|---|---|---|
1 | 2 | 38µs | 2 | 55µs | # spent 51µs (47+4) within Module::Runtime::BEGIN@1.320 which was called:
# once (47µs+4µs) by Module::Runtime::require_module at line 1 # spent 51µs making 1 call to Module::Runtime::BEGIN@1.320
# spent 4µs making 1 call to strict::import |
2 | 2 | 88µs | 2 | 89µs | # spent 49µs (9+40) within Module::Runtime::BEGIN@2.321 which was called:
# once (9µs+40µs) by Module::Runtime::require_module at line 2 # spent 49µs making 1 call to Module::Runtime::BEGIN@2.321
# spent 40µs making 1 call to warnings::import |
3 | package JSON::Schema::Modern::Vocabulary::OpenAPI; | ||||
4 | # vim: set ts=8 sts=2 sw=2 tw=100 et : | ||||
5 | # ABSTRACT: Implementation of the JSON Schema OpenAPI vocabulary | ||||
6 | |||||
7 | 1 | 0s | our $VERSION = '0.031'; | ||
8 | |||||
9 | 2 | 74µs | 1 | 16µs | # spent 16µs within JSON::Schema::Modern::Vocabulary::OpenAPI::BEGIN@9 which was called:
# once (16µs+0s) by Module::Runtime::require_module at line 9 # spent 16µs making 1 call to JSON::Schema::Modern::Vocabulary::OpenAPI::BEGIN@9 |
10 | 2 | 27µs | 2 | 707µs | # spent 370µs (33+337) within JSON::Schema::Modern::Vocabulary::OpenAPI::BEGIN@10 which was called:
# once (33µs+337µs) by Module::Runtime::require_module at line 10 # spent 370µs making 1 call to JSON::Schema::Modern::Vocabulary::OpenAPI::BEGIN@10
# spent 337µs making 1 call to Moo::import |
11 | 3 | 79µs | 3 | 1.80ms | # spent 908µs (14+894) within JSON::Schema::Modern::Vocabulary::OpenAPI::BEGIN@11 which was called:
# once (14µs+894µs) by Module::Runtime::require_module at line 11 # spent 908µs making 1 call to JSON::Schema::Modern::Vocabulary::OpenAPI::BEGIN@11
# spent 875µs making 1 call to strictures::import
# spent 19µs making 1 call to strictures::VERSION |
12 | 2 | 72µs | 2 | 214µs | # spent 111µs (8+103) within JSON::Schema::Modern::Vocabulary::OpenAPI::BEGIN@12 which was called:
# once (8µs+103µs) by Module::Runtime::require_module at line 12 # spent 111µs making 1 call to JSON::Schema::Modern::Vocabulary::OpenAPI::BEGIN@12
# spent 103µs making 1 call to experimental::import |
13 | 2 | 26µs | 2 | 76µs | # spent 72µs (45+27) within JSON::Schema::Modern::Vocabulary::OpenAPI::BEGIN@13 which was called:
# once (45µs+27µs) by Module::Runtime::require_module at line 13 # spent 72µs making 1 call to JSON::Schema::Modern::Vocabulary::OpenAPI::BEGIN@13
# spent 4µs making 1 call to if::import |
14 | 2 | 19µs | 2 | 25µs | # spent 24µs (9+15) within JSON::Schema::Modern::Vocabulary::OpenAPI::BEGIN@14 which was called:
# once (9µs+15µs) by Module::Runtime::require_module at line 14 # spent 24µs making 1 call to JSON::Schema::Modern::Vocabulary::OpenAPI::BEGIN@14
# spent 1µs making 1 call to if::unimport |
15 | 2 | 58µs | 2 | 16µs | # spent 16µs (8+8) within JSON::Schema::Modern::Vocabulary::OpenAPI::BEGIN@15 which was called:
# once (8µs+8µs) by Module::Runtime::require_module at line 15 # spent 16µs making 1 call to JSON::Schema::Modern::Vocabulary::OpenAPI::BEGIN@15
# spent 0s making 1 call to if::unimport |
16 | 2 | 19µs | 2 | 15µs | # spent 15µs (8+7) within JSON::Schema::Modern::Vocabulary::OpenAPI::BEGIN@16 which was called:
# once (8µs+7µs) by Module::Runtime::require_module at line 16 # spent 15µs making 1 call to JSON::Schema::Modern::Vocabulary::OpenAPI::BEGIN@16
# spent 0s making 1 call to if::unimport |
17 | 3 | 60µs | 3 | 102µs | # spent 56µs (10+46) within JSON::Schema::Modern::Vocabulary::OpenAPI::BEGIN@17 which was called:
# once (10µs+46µs) by Module::Runtime::require_module at line 17 # spent 56µs making 1 call to JSON::Schema::Modern::Vocabulary::OpenAPI::BEGIN@17
# spent 39µs making 1 call to Exporter::import
# spent 7µs making 1 call to UNIVERSAL::VERSION |
18 | 2 | 830µs | 2 | 636µs | # spent 321µs (6+315) within JSON::Schema::Modern::Vocabulary::OpenAPI::BEGIN@18 which was called:
# once (6µs+315µs) by Module::Runtime::require_module at line 18 # spent 321µs making 1 call to JSON::Schema::Modern::Vocabulary::OpenAPI::BEGIN@18
# spent 315µs making 1 call to namespace::clean::import |
19 | |||||
20 | 1 | 2µs | 1 | 486µs | with 'JSON::Schema::Modern::Vocabulary'; # spent 486µs making 1 call to Moo::with |
21 | |||||
22 | # spent 0s within JSON::Schema::Modern::Vocabulary::OpenAPI::vocabulary which was called:
# once (0s+0s) by JSON::Schema::Modern::add_vocabulary at line 679 of JSON/Schema/Modern.pm | ||||
23 | 1 | 2µs | 'https://spec.openapis.org/oas/3.1/vocab/base' => 'draft2020-12', | ||
24 | } | ||||
25 | |||||
26 | # spent 2.46ms within JSON::Schema::Modern::Vocabulary::OpenAPI::keywords which was called 2018 times, avg 1µs/call:
# 2018 times (2.46ms+0s) by JSON::Schema::Modern::_traverse_subschema at line 447 of JSON/Schema/Modern.pm, avg 1µs/call | ||||
27 | 2018 | 3.94ms | qw(discriminator example externalDocs xml); | ||
28 | } | ||||
29 | |||||
30 | sub _traverse_keyword_discriminator ($self, $schema, $state) { | ||||
31 | return if not assert_keyword_type($state, $schema, 'object'); | ||||
32 | |||||
33 | # "the discriminator field MUST be a required field" | ||||
34 | return E($state, 'missing required field propertyName') | ||||
35 | if not exists $schema->{discriminator}{propertyName}; | ||||
36 | return E({ %$state, _schema_path_suffix => 'propertyName' }, 'discriminator propertyName is not a string') | ||||
37 | if not is_type('string', $schema->{discriminator}{propertyName}); | ||||
38 | |||||
39 | my $valid = 1; | ||||
40 | if (exists $schema->{discriminator}{mapping}) { | ||||
41 | return if not assert_keyword_type({ %$state, _schema_path_suffix => 'mapping' }, $schema, 'object'); | ||||
42 | return E({ %$state, _schema_path_suffix => 'mapping' }, 'discriminator mapping is not an object ') | ||||
43 | if not is_type('object', $schema->{discriminator}{mapping}); | ||||
44 | foreach my $mapping_key (sort keys $schema->{discriminator}{mapping}->%*) { | ||||
45 | my $uri = $schema->{discriminator}{mapping}{$mapping_key}; | ||||
46 | $valid = E({ %$state, _schema_path_suffix => [ 'mapping', $mapping_key ] }, 'discriminator mapping value for "%s" is not a string', $mapping_key), next if not is_type('string', $uri); | ||||
47 | } | ||||
48 | } | ||||
49 | |||||
50 | $valid = E($state, 'missing sibling keyword: one of oneOf, anyOf, allOf') | ||||
51 | if not grep exists $schema->{$_}, qw(oneOf anyOf allOf); | ||||
52 | |||||
53 | return 1; | ||||
54 | } | ||||
55 | |||||
56 | sub _eval_keyword_discriminator ($self, $data, $schema, $state) { | ||||
57 | # Note: the spec is unclear of the expected behaviour when the data instance is not an object | ||||
58 | return 1 if not is_type('object', $data); | ||||
59 | |||||
60 | my $discriminator_key = $schema->{discriminator}{propertyName}; | ||||
61 | |||||
62 | # property with name <propertyName> MUST be present in the data payload | ||||
63 | return E($state, 'missing required discriminator field "%s"', $discriminator_key) | ||||
64 | if not exists $data->{$discriminator_key}; | ||||
65 | |||||
66 | my $discriminator_value = $data->{$discriminator_key}; | ||||
67 | |||||
68 | # if /components/$discriminator_value exists, that schema must validate | ||||
69 | my $uri = Mojo::URL->new->fragment(jsonp('', qw(components schemas), $discriminator_value)) | ||||
70 | ->to_abs($state->{initial_schema_uri}); | ||||
71 | if (my $component_schema_info = $state->{evaluator}->_fetch_from_uri($uri)) { | ||||
72 | $state = { %$state, _schema_path_suffix => 'propertyName' }; | ||||
73 | } | ||||
74 | elsif (exists $schema->{discriminator}{mapping} and exists $schema->{discriminator}{mapping}{$discriminator_value}) { | ||||
75 | # use 'mapping' to determine which schema to use. | ||||
76 | $uri = Mojo::URL->new($schema->{discriminator}{mapping}{$discriminator_value}); | ||||
77 | $state = { %$state, _schema_path_suffix => [ 'mapping', $discriminator_value ] }; | ||||
78 | } | ||||
79 | else { | ||||
80 | # If the discriminator value does not match an implicit or explicit mapping, no schema can be | ||||
81 | # determined and validation SHOULD fail. | ||||
82 | return E($state, 'invalid %s: "%s"', $discriminator_key, $discriminator_value); | ||||
83 | } | ||||
84 | |||||
85 | return E($state, 'subschema for %s: %s is invalid', $discriminator_key, $discriminator_value) | ||||
86 | if not $self->eval_subschema_at_uri($data, $schema, $state, $uri); | ||||
87 | return 1; | ||||
88 | } | ||||
89 | |||||
90 | sub _traverse_keyword_example { 1 } | ||||
91 | |||||
92 | sub _eval_keyword_example ($self, $data, $schema, $state) { | ||||
93 | annotate_self($state, $schema); | ||||
94 | } | ||||
95 | |||||
96 | # until we do something with these values, we do not bother checking the structure | ||||
97 | 5 | 16µs | # spent 5µs within JSON::Schema::Modern::Vocabulary::OpenAPI::_traverse_keyword_externalDocs which was called 5 times, avg 1µs/call:
# 5 times (5µs+0s) by JSON::Schema::Modern::_traverse_subschema at line 457 of JSON/Schema/Modern.pm, avg 1µs/call | ||
98 | |||||
99 | sub _eval_keyword_externalDocs { goto \&_eval_keyword_example } | ||||
100 | |||||
101 | # until we do something with these values, we do not bother checking the structure | ||||
102 | sub _traverse_keyword_xml { 1 } | ||||
103 | |||||
104 | sub _eval_keyword_xml { goto \&_eval_keyword_example } | ||||
105 | |||||
106 | 1 | 8µs | 1; | ||
107 | |||||
108 | 1 | 50µs | 1 | 360µs | __END__ # spent 360µs making 1 call to B::Hooks::EndOfScope::XS::__ANON__[B/Hooks/EndOfScope/XS.pm:26] |