avro_turf 1.9.0 → 1.10.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 3cb36f9b1395a1a6210d1178ca0823636f30ad194caf57663e8fb5cc13273d68
4
- data.tar.gz: 2fb489fe330b39b88ed585d6b622936e573b525c1f4c5c4fe50704b16b11fd39
3
+ metadata.gz: c0907531d40226b59cd545baf7341f3e41613565d50de98684b266b6b33a081f
4
+ data.tar.gz: e472794d6e7ecbd4a32b1a08f4cc0eb6b0ae810d849483d86ab16a7da929a9fb
5
5
  SHA512:
6
- metadata.gz: be796c4b42daf30a79dd699d23842e61c61e8f8c70b1645f269ec25e4a4f4fb1e87148b0ffd69a68b24382e9abc01048cb3ba082bd3a3dd2162be714ecdcd57b
7
- data.tar.gz: 332486d45cd611da3906247f4fb55386c7e1617043070dd44fff06b05c50c44237af6dad62f1fd087ca9c67580aadd53fc342f76509b69b67375532b60637bf9
6
+ metadata.gz: ac1324149cb3299c3e67ffbd287879da88a09c338b967e2098fed63836c9fba5f775623ee6d6ae2ac0ac5e6f6a4ad28ea4c7bb7ece2d1e5979cee2eb379ac43a
7
+ data.tar.gz: 84709d06f4b3d97a23c1f0a1b94f4757c8b7024d17354ec65c7068be8cca52cdeed832096d7ea43f646d3f52d09ebd0f2286375456503d9da14cf6cb7a37772b
data/CHANGELOG.md CHANGED
@@ -2,6 +2,11 @@
2
2
 
3
3
  ## Unreleased
4
4
 
5
+ ## v1.10.0
6
+
7
+ - Add `schema_subject_versions` to `ConfluentSchemaRegistry` to retrieve all subject versions for a schema id. (#189)
8
+ - `FakeConfluentSchemaRegistryServer` now returns same id if identical schema is created for a different subject (#188)
9
+
5
10
  ## v1.9.0
6
11
 
7
12
  - Send Accept and User-Agent headers on every request (#184)
@@ -17,7 +17,7 @@ class AvroTurf::CachedConfluentSchemaRegistry
17
17
  end
18
18
 
19
19
  # Delegate the following methods to the upstream
20
- %i(subjects subject_versions check compatible?
20
+ %i(subjects subject_versions schema_subject_versions check compatible?
21
21
  global_config update_global_config subject_config update_subject_config).each do |name|
22
22
  define_method(name) do |*args|
23
23
  instance_variable_get(:@upstream).send(name, *args)
@@ -68,6 +68,11 @@ class AvroTurf::ConfluentSchemaRegistry
68
68
  get("/subjects/#{subject}/versions/#{version}")
69
69
  end
70
70
 
71
+ # Get the subject and version for a schema id
72
+ def schema_subject_versions(schema_id)
73
+ get("/schemas/ids/#{schema_id}/versions")
74
+ end
75
+
71
76
  # Check if a schema exists. Returns nil if not found.
72
77
  def check(subject, schema)
73
78
  data = post("/subjects/#{subject}",
@@ -22,7 +22,7 @@ class AvroTurf::SchemaStore
22
22
  # Still need to check is the schema already loaded
23
23
  return @schemas[fullname] if @schemas.key?(fullname)
24
24
 
25
- load_schema!(fullname)
25
+ load_schema!(fullname, @schemas.dup)
26
26
  end
27
27
  end
28
28
 
@@ -35,23 +35,35 @@ class FakeConfluentSchemaRegistryServer < Sinatra::Base
35
35
 
36
36
  post "/subjects/:subject/versions" do
37
37
  schema = parse_schema
38
- ids_for_subject = SUBJECTS[params[:subject]]
39
-
40
- schemas_for_subject =
41
- SCHEMAS.select
42
- .with_index { |_, i| ids_for_subject.include?(i) }
43
-
44
- if schemas_for_subject.include?(schema)
45
- schema_id = SCHEMAS.index(schema)
46
- else
38
+ schema_id = SCHEMAS.index(schema)
39
+ if schema_id.nil?
47
40
  SCHEMAS << schema
48
41
  schema_id = SCHEMAS.size - 1
49
- SUBJECTS[params[:subject]] = SUBJECTS[params[:subject]] << schema_id
42
+ end
43
+
44
+ subject = params[:subject]
45
+ unless SUBJECTS[subject].include?(schema_id)
46
+ SUBJECTS[subject] = SUBJECTS[subject] << schema_id
50
47
  end
51
48
 
52
49
  { id: schema_id }.to_json
53
50
  end
54
51
 
52
+ get "/schemas/ids/:schema_id/versions" do
53
+ schema_id = params[:schema_id].to_i
54
+ schema = SCHEMAS.at(schema_id)
55
+ halt(404, SCHEMA_NOT_FOUND) unless schema
56
+
57
+ related_subjects = SUBJECTS.select {|_, vs| vs.include? schema_id }
58
+
59
+ related_subjects.map do |subject, versions|
60
+ {
61
+ subject: subject,
62
+ version: versions.find_index(schema_id) + 1
63
+ }
64
+ end.to_json
65
+ end
66
+
55
67
  get "/schemas/ids/:schema_id" do
56
68
  schema = SCHEMAS.at(params[:schema_id].to_i)
57
69
  halt(404, SCHEMA_NOT_FOUND) unless schema
@@ -1,3 +1,3 @@
1
1
  class AvroTurf
2
- VERSION = "1.9.0"
2
+ VERSION = "1.10.0"
3
3
  end
@@ -109,7 +109,7 @@ describe AvroTurf::Messaging do
109
109
  end
110
110
 
111
111
  it 'encodes and decodes messages' do
112
- data = avro.encode(message, schema_id: 1)
112
+ data = avro.encode(message, schema_id: 0)
113
113
  expect(avro.decode(data)).to eq message
114
114
  end
115
115
 
@@ -118,7 +118,7 @@ describe AvroTurf::Messaging do
118
118
  end
119
119
 
120
120
  it 'caches parsed schemas for decoding' do
121
- data = avro.encode(message, schema_id: 1)
121
+ data = avro.encode(message, schema_id: 0)
122
122
  avro.decode(data)
123
123
  allow(Avro::Schema).to receive(:parse).and_call_original
124
124
  expect(avro.decode(data)).to eq message
@@ -361,6 +361,49 @@ describe AvroTurf::SchemaStore do
361
361
  end
362
362
 
363
363
  describe "#load_schemas!" do
364
+ it "do not try to reload known schemas" do
365
+ define_schema "first.avsc", <<-AVSC
366
+ {
367
+ "name": "first",
368
+ "type": "record",
369
+ "fields": [
370
+ {
371
+ "type": "string",
372
+ "name": "a_value"
373
+ }
374
+ ]
375
+ }
376
+ AVSC
377
+
378
+ define_schema "second.avsc", <<-AVSC
379
+ {
380
+ "name": "second",
381
+ "type": "record",
382
+ "fields": [
383
+ {
384
+ "type": "first",
385
+ "name": "full_name"
386
+ }
387
+ ]
388
+ }
389
+ AVSC
390
+
391
+ define_schema "third.avsc", <<-AVSC
392
+ {
393
+ "name": "third",
394
+ "type": "record",
395
+ "fields": [
396
+ {
397
+ "type": "second",
398
+ "name": "embedded_first"
399
+ }
400
+ ]
401
+ }
402
+ AVSC
403
+
404
+ expect { store.load_schemas! }.not_to raise_error
405
+ end
406
+
364
407
  it "loads schemas defined in the `schemas_path` directory" do
365
408
  define_schema "person.avsc", <<-AVSC
366
409
  {
data/spec/spec_helper.rb CHANGED
@@ -1,6 +1,7 @@
1
1
  require 'bundler/setup'
2
2
  require 'logger'
3
3
  require 'json_spec'
4
+ require 'pp' # Require pp before fakefs to fix TypeError: superclass mismatch for class File
4
5
  require 'fakefs/spec_helpers'
5
6
  require 'avro_turf'
6
7
 
@@ -77,6 +77,33 @@ shared_examples_for "a confluent schema registry client" do
77
77
  end
78
78
  end
79
79
 
80
+ describe "#schema_subject_versions" do
81
+ it "returns subject and version for a schema id" do
82
+ schema_id1 = registry.register(subject_name, { type: :record, name: "r1", fields: [] }.to_json)
83
+ registry.register(subject_name, { type: :record, name: "r2", fields: [] }.to_json)
84
+ schema_id2 = registry.register("other#{subject_name}", { type: :record, name: "r2", fields: [] }.to_json)
85
+ expect(registry.schema_subject_versions(schema_id1)).to eq([
86
+ 'subject' => subject_name,
87
+ 'version' => 1
88
+ ])
89
+ expect(registry.schema_subject_versions(schema_id2)).to include({
90
+ 'subject' => subject_name,
91
+ 'version' => 2
92
+ },{
93
+ 'subject' => "other#{subject_name}",
94
+ 'version' => 1
95
+ } )
96
+ end
97
+
98
+ context "when the schema does not exist" do
99
+ it "raises an error" do
100
+ expect do
101
+ registry.schema_subject_versions(-1)
102
+ end.to raise_error(Excon::Errors::NotFound)
103
+ end
104
+ end
105
+ end
106
+
80
107
  describe "#subject_versions" do
81
108
  it "lists all the versions for the subject" do
82
109
  2.times do |n|
@@ -27,14 +27,75 @@ describe FakeConfluentSchemaRegistryServer do
27
27
  expect(JSON.parse(last_response.body).fetch('id')).to eq expected_id
28
28
  end
29
29
 
30
- it 'returns a different schema ID when invoked with same schema and different subject' do
30
+ it 'returns the same schema ID when invoked with same schema and different subject' do
31
31
  post '/subjects/person/versions', { schema: schema }.to_json, 'CONTENT_TYPE' => 'application/vnd.schemaregistry+json'
32
32
 
33
33
  original_id = JSON.parse(last_response.body).fetch('id')
34
34
 
35
35
  post '/subjects/happy-person/versions', { schema: schema }.to_json, 'CONTENT_TYPE' => 'application/vnd.schemaregistry+json'
36
36
 
37
- expect(JSON.parse(last_response.body).fetch('id')).not_to eq original_id
37
+ expect(JSON.parse(last_response.body).fetch('id')).to eq original_id
38
+ end
39
+
40
+ it 'returns a different schema ID when invoked with a different schema' do
41
+ post '/subjects/person/versions', { schema: schema }.to_json, 'CONTENT_TYPE' => 'application/vnd.schemaregistry+json'
42
+
43
+ original_id = JSON.parse(last_response.body).fetch('id')
44
+
45
+ other_schema = {
46
+ type: "record",
47
+ name: "other",
48
+ fields: [
49
+ { name: "name", type: "string" }
50
+ ]
51
+ }.to_json
52
+
53
+ post '/subjects/person/versions', { schema: other_schema }.to_json, 'CONTENT_TYPE' => 'application/vnd.schemaregistry+json'
54
+
55
+ expect(JSON.parse(last_response.body).fetch('id')).to_not eq original_id
56
+ end
57
+ end
58
+
59
+ describe 'GET /schemas/ids/:id/versions' do
60
+ def schema(name:)
61
+ {
62
+ type: "record",
63
+ name: name,
64
+ fields: [
65
+ { name: "name", type: "string" },
66
+ ]
67
+ }.to_json
68
+ end
69
+
70
+ it "returns array containing subjects and versions for given schema id" do
71
+ schema1 = schema(name: "name1")
72
+ schema2 = schema(name: "name2")
73
+
74
+ post "/subjects/cats/versions", { schema: schema1 }.to_json, 'CONTENT_TYPE' => 'application/vnd.schemaregistry+json'
75
+ schema1_id = JSON.parse(last_response.body).fetch('id') # Original cats schema
76
+
77
+ post "/subjects/dogs/versions", { schema: schema2 }.to_json, 'CONTENT_TYPE' => 'application/vnd.schemaregistry+json'
78
+ post "/subjects/cats/versions", { schema: schema2 }.to_json, 'CONTENT_TYPE' => 'application/vnd.schemaregistry+json'
79
+ schema2_id = JSON.parse(last_response.body).fetch('id') # Changed cats schema == Original Dogs schema
80
+
81
+ get "/schemas/ids/#{schema1_id}/versions"
82
+ result = JSON.parse(last_response.body)
83
+
84
+ expect(result).to eq [{
85
+ 'subject' => 'cats',
86
+ 'version' => 1
87
+ }]
88
+
89
+ get "/schemas/ids/#{schema2_id}/versions"
90
+ result = JSON.parse(last_response.body)
91
+
92
+ expect(result).to include( {
93
+ 'subject' => 'cats',
94
+ 'version' => 2
95
+ }, {
96
+ 'subject' => 'dogs',
97
+ 'version' => 1
98
+ })
38
99
  end
39
100
  end
40
101
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: avro_turf
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.9.0
4
+ version: 1.10.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Daniel Schierbeck
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2023-06-06 00:00:00.000000000 Z
11
+ date: 2023-08-25 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: avro