ezid-client 1.5.0 → 1.9.0.rc1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,34 @@
1
+ require 'ezid/batch'
2
+
3
+ module Ezid
4
+ RSpec.describe Batch do
5
+
6
+ let(:batch_file) { File.expand_path("../../fixtures/anvl_batch.txt", __FILE__) }
7
+
8
+ subject { described_class.new(:anvl, batch_file) }
9
+
10
+ its(:count) { is_expected.to eq 4 }
11
+
12
+ specify {
13
+ subject.each do |id|
14
+ expect(id).to be_a(Identifier)
15
+ end
16
+ }
17
+
18
+ specify {
19
+ batch_array = subject.to_a
20
+ expect(batch_array.length).to eq 4
21
+ }
22
+
23
+ specify {
24
+ ids = subject.map(&:id)
25
+ expect(ids).to eq ["ark:/99999/fk4086hs23", "ark:/99999/fk4086hs23/123", "ark:/99999/fk40p1bb85", "ark:/99999/fk40z7fh7x"]
26
+ }
27
+
28
+ specify {
29
+ id = subject.first
30
+ expect(id.target).to eq "http://example.com"
31
+ }
32
+
33
+ end
34
+ end
@@ -1,7 +1,15 @@
1
1
  module Ezid
2
2
  RSpec.describe Client do
3
3
 
4
+ let(:http_response) { double }
5
+
6
+ before do
7
+ allow(http_response).to receive(:value) { nil }
8
+ allow(http_response).to receive(:code) { '200' }
9
+ end
10
+
4
11
  describe "initialization without a block" do
12
+ let(:http_response) { double }
5
13
  it "should not login" do
6
14
  expect_any_instance_of(described_class).not_to receive(:login)
7
15
  described_class.new
@@ -151,9 +159,33 @@ EOS
151
159
  end
152
160
 
153
161
  describe "error handling" do
154
- let(:http_response) { double(body: "error: bad request - no such identifier") }
155
- it "should raise an exception" do
156
- expect { subject.get_identifier_metadata("invalid") }.to raise_error(Error)
162
+ let(:stub_response) { GetIdentifierMetadataResponse.new(http_response) }
163
+ before do
164
+ allow(GetIdentifierMetadataRequest).to receive(:execute).with(subject, "invalid") { stub_response }
165
+ end
166
+
167
+ describe "HTTP error response" do
168
+ before do
169
+ allow(http_response).to receive(:code) { '500' }
170
+ allow(http_response).to receive(:message) { 'Internal Server Error' }
171
+ end
172
+ it "should raise an exception" do
173
+ expect { subject.get_identifier_metadata("invalid") }.to raise_error(Error)
174
+ end
175
+ end
176
+
177
+ describe "EZID API error response" do
178
+ let(:http_response) { double(body: "error: bad request - no such identifier") }
179
+ it "should raise an exception" do
180
+ expect { subject.get_identifier_metadata("invalid") }.to raise_error(Error)
181
+ end
182
+ end
183
+
184
+ describe "Unexpected response" do
185
+ let(:http_response) { double(body: "<html>\n<head><title>Ouch!</title></head>\n<body>Help!</body>\n</html>") }
186
+ it "should raise an exception" do
187
+ expect { subject.get_identifier_metadata("invalid") }.to raise_error(UnexpectedResponseError)
188
+ end
157
189
  end
158
190
  end
159
191
  end
@@ -1,6 +1,39 @@
1
1
  module Ezid
2
2
  RSpec.describe Identifier do
3
+
3
4
  describe "class methods" do
5
+
6
+ describe ".load" do
7
+ subject { described_class.load("ark:/99999/fk4086hs23", metadata) }
8
+ describe "with ANVL metadata" do
9
+ let(:metadata) do
10
+ <<-EOS
11
+ _updated: 1488227717
12
+ _target: http://example.com
13
+ _profile: erc
14
+ _ownergroup: apitest
15
+ _owner: apitest
16
+ _export: yes
17
+ _created: 1488227717
18
+ _status: public
19
+ EOS
20
+ end
21
+ its(:remote_metadata) {
22
+ is_expected.to eq({"_updated"=>"1488227717",
23
+ "_target"=>"http://example.com",
24
+ "_profile"=>"erc",
25
+ "_ownergroup"=>"apitest",
26
+ "_owner"=>"apitest",
27
+ "_export"=>"yes",
28
+ "_created"=>"1488227717",
29
+ "_status"=>"public"})
30
+ }
31
+ end
32
+ describe "with nil" do
33
+ let(:metadata) { nil }
34
+ its(:remote_metadata) { is_expected.to be_empty }
35
+ end
36
+ end
4
37
  describe ".create" do
5
38
  describe "with id and metadata args" do
6
39
  it "instantiates a new Identifier and saves it" do
@@ -63,6 +96,7 @@ module Ezid
63
96
  end
64
97
 
65
98
  describe "instance methods" do
99
+
66
100
  describe "#initialize" do
67
101
  before {
68
102
  allow(described_class).to receive(:defaults) { defaults }
@@ -129,7 +163,7 @@ module Ezid
129
163
  its(:client) { is_expected.to_not eq(client) }
130
164
  end
131
165
  end
132
- end
166
+ end # initialize
133
167
 
134
168
  describe "#update" do
135
169
  let(:metadata) { {"status" => "unavailable"} }
@@ -172,12 +206,23 @@ module Ezid
172
206
  end
173
207
 
174
208
  describe "#load_metadata" do
209
+ subject { described_class.new("id") }
175
210
  let(:metadata) { "_profile: erc" }
176
- before { allow(subject).to receive(:id) { "id" } }
177
211
  it "replaces the remote metadata with metadata from EZID" do
178
212
  expect(subject.client).to receive(:get_identifier_metadata).with("id") { double(id: "id", metadata: metadata) }
179
- expect(subject.remote_metadata).to receive(:replace).with(metadata)
180
213
  subject.load_metadata
214
+ expect(subject.remote_metadata).to eq({"_profile"=>"erc"})
215
+ expect(subject).to be_persisted
216
+ end
217
+ end
218
+
219
+ describe "#load_metadata!" do
220
+ subject { described_class.new("id") }
221
+ let(:metadata) { "_profile: erc" }
222
+ it "replaces the remote metadata with the provided metadata" do
223
+ subject.load_metadata!(metadata)
224
+ expect(subject.remote_metadata).to eq({"_profile"=>"erc"})
225
+ expect(subject).to be_persisted
181
226
  end
182
227
  end
183
228
 
@@ -323,23 +368,11 @@ module Ezid
323
368
  context "when the status is \"unavailable\"" do
324
369
  let(:status) { "#{Status::UNAVAILABLE} | whatever" }
325
370
  context "and no reason is given" do
326
- it "logs a warning" do
327
- pending "https://github.com/duke-libraries/ezid-client/issues/46"
328
- allow_message_expectations_on_nil
329
- expect(subject.logger).to receive(:warn)
330
- subject.unavailable!
331
- end
332
371
  it "does not change the status" do
333
372
  expect { subject.unavailable! }.not_to change(subject, :status)
334
373
  end
335
374
  end
336
375
  context "and a reason is given" do
337
- it "logs a warning" do
338
- pending "https://github.com/duke-libraries/ezid-client/issues/46"
339
- allow_message_expectations_on_nil
340
- expect(subject.logger).to receive(:warn)
341
- subject.unavailable!("because")
342
- end
343
376
  it "should change the status" do
344
377
  expect { subject.unavailable!("because") }.to change(subject, :status).from(status).to("#{Status::UNAVAILABLE} | because")
345
378
  end
@@ -382,5 +415,11 @@ module Ezid
382
415
  end
383
416
  end
384
417
  end
418
+
419
+ describe "#metadata" do
420
+ it "is frozen" do
421
+ expect { subject.metadata["foo"] = "bar" }.to raise_error(RuntimeError)
422
+ end
423
+ end
385
424
  end
386
425
  end
@@ -1,3 +1,5 @@
1
+ require 'time'
2
+
1
3
  module Ezid
2
4
  RSpec.describe Metadata do
3
5
  describe "initializer" do
@@ -0,0 +1,169 @@
1
+ module Ezid
2
+ RSpec.describe MetadataTransformDatacite do
3
+ describe "#transform" do
4
+ before(:each) do
5
+ described_class.transform(test_hash)
6
+ end
7
+
8
+ context "when there are no datacite fields" do
9
+ let(:test_hash) { {} }
10
+ let(:expected_xml) { File.read("spec/fixtures/datacite_xml/empty.xml") }
11
+
12
+ it "populates a datacite xml field with all required fields as empty" do
13
+ expect(test_hash["datacite"]).to eq(expected_xml)
14
+ end
15
+ end
16
+
17
+ context "when there are datacite fields" do
18
+ let(:test_hash) { {
19
+ "datacite.identifier" => "TestIdentifier",
20
+ "datacite.identifiertype" => "TestIdentifierType",
21
+ "datacite.creator" => "TestCreatorName",
22
+ "datacite.title" => "TestTitle",
23
+ "datacite.publisher" => "TestPublisher",
24
+ "datacite.publicationyear" => "TestPublicationYear",
25
+ "datacite.resourcetype" => "TestResourceType",
26
+ "datacite.resourcetypegeneral" => "TestResourceTypeGeneral",
27
+ "datacite.description" => "TestDescription",
28
+ "some.other.field" => "SomeOtherValue",
29
+ } }
30
+ let(:expected_xml) { File.read("spec/fixtures/datacite_xml/populated.xml") }
31
+
32
+ it "populates a datacite xml field using values from the datacite.* fields" do
33
+ expect(test_hash["datacite"]).to eq(expected_xml)
34
+ end
35
+
36
+ it "removes the datacite.* fields from the hash" do
37
+ expect(test_hash.keys).not_to include(
38
+ "datacite.identifer",
39
+ "datacite.identifiertype",
40
+ "datacite.creator",
41
+ "datacite.title",
42
+ "datacite.publisher",
43
+ "datacite.publicationyear",
44
+ "datacite.resourcetype",
45
+ "datacite.resourcetypegeneral",
46
+ "datacite.description",
47
+ )
48
+ end
49
+
50
+ it "does not remove other fields" do
51
+ expect(test_hash).to include("some.other.field")
52
+ end
53
+ end
54
+ end
55
+
56
+ describe "#inverse" do
57
+ let(:test_hash) { {
58
+ "datacite" => test_xml,
59
+ "some.other.field" => "SomeOtherValue"
60
+ } }
61
+
62
+ before(:each) do
63
+ described_class.inverse(test_hash)
64
+ end
65
+
66
+
67
+ context "when there are no datacite fields" do
68
+ let(:expected_hash) { {
69
+ "datacite.identifier" => "",
70
+ "datacite.identifiertype" => "DOI",
71
+ "datacite.creator" => "",
72
+ "datacite.description" => "",
73
+ "datacite.publicationyear" => "",
74
+ "datacite.publisher" => "",
75
+ "datacite.resourcetype" => "",
76
+ "datacite.resourcetypegeneral" => "",
77
+ "datacite.title" => "",
78
+ } }
79
+ let(:test_xml) { File.read("spec/fixtures/datacite_xml/empty.xml") }
80
+
81
+ it "populates all required fields as empty" do
82
+ expect(test_hash).to include(expected_hash)
83
+ end
84
+ end
85
+
86
+ context "when there are datacite fields" do
87
+ let(:expected_hash) { {
88
+ "datacite.identifier" => "TestIdentifier",
89
+ "datacite.identifiertype" => "TestIdentifierType",
90
+ "datacite.creator" => "TestCreatorName",
91
+ "datacite.title" => "TestTitle",
92
+ "datacite.publisher" => "TestPublisher",
93
+ "datacite.publicationyear" => "TestPublicationYear",
94
+ "datacite.resourcetype" => "TestResourceType",
95
+ "datacite.resourcetypegeneral" => "TestResourceTypeGeneral",
96
+ "datacite.description" => "TestDescription",
97
+ } }
98
+ let(:test_xml) { File.read("spec/fixtures/datacite_xml/populated.xml") }
99
+
100
+ it "populates all fields from the datacite.* fields" do
101
+ expect(test_hash).to include(expected_hash)
102
+ end
103
+
104
+ it "removes the datacite field" do
105
+ expect(test_hash).not_to include("datacite")
106
+ end
107
+
108
+ it "does not remove other fields" do
109
+ expect(test_hash).to include("some.other.field")
110
+ end
111
+ end
112
+ end
113
+
114
+ describe "#transform then #inverse" do
115
+ let(:test_hash) { {
116
+ "datacite.identifier" => "TestIdentifier",
117
+ "datacite.identifiertype" => "TestIdentifierType",
118
+ "datacite.creator" => "TestCreatorName",
119
+ "datacite.title" => "TestTitle",
120
+ "datacite.publisher" => "TestPublisher",
121
+ "datacite.publicationyear" => "TestPublicationYear",
122
+ "datacite.resourcetype" => "TestResourceType",
123
+ "datacite.resourcetypegeneral" => "TestResourceTypeGeneral",
124
+ "datacite.description" => "TestDescription",
125
+ "some.other.field" => "SomeOtherValue",
126
+ } }
127
+
128
+ before(:each) do
129
+ described_class.transform(test_hash)
130
+ described_class.inverse(test_hash)
131
+ end
132
+
133
+ it "is a lossless transformation" do
134
+ expect(test_hash).to eq({
135
+ "datacite.identifier" => "TestIdentifier",
136
+ "datacite.identifiertype" => "TestIdentifierType",
137
+ "datacite.creator" => "TestCreatorName",
138
+ "datacite.title" => "TestTitle",
139
+ "datacite.publisher" => "TestPublisher",
140
+ "datacite.publicationyear" => "TestPublicationYear",
141
+ "datacite.resourcetype" => "TestResourceType",
142
+ "datacite.resourcetypegeneral" => "TestResourceTypeGeneral",
143
+ "datacite.description" => "TestDescription",
144
+ "some.other.field" => "SomeOtherValue",
145
+ })
146
+ end
147
+ end
148
+
149
+ describe "#inverse then #transform" do
150
+ let(:test_xml) { File.read("spec/fixtures/datacite_xml/empty.xml") }
151
+ let(:test_hash) { {
152
+ "datacite" => test_xml,
153
+ "some.other.field" => "SomeOtherValue"
154
+ } }
155
+
156
+ before(:each) do
157
+ described_class.inverse(test_hash)
158
+ described_class.transform(test_hash)
159
+ end
160
+
161
+ it "is a lossless transformation" do
162
+ expect(test_hash).to eq({
163
+ "datacite" => test_xml,
164
+ "some.other.field" => "SomeOtherValue"
165
+ })
166
+ end
167
+ end
168
+ end
169
+ end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: ezid-client
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.5.0
4
+ version: 1.9.0.rc1
5
5
  platform: ruby
6
6
  authors:
7
7
  - David Chandek-Stark
8
- autorequire:
8
+ autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2016-03-24 00:00:00.000000000 Z
11
+ date: 2021-03-23 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: hashie
@@ -30,34 +30,62 @@ dependencies:
30
30
  - - ">="
31
31
  - !ruby/object:Gem::Version
32
32
  version: 3.4.3
33
+ - !ruby/object:Gem::Dependency
34
+ name: nokogiri
35
+ requirement: !ruby/object:Gem::Requirement
36
+ requirements:
37
+ - - ">="
38
+ - !ruby/object:Gem::Version
39
+ version: '0'
40
+ type: :runtime
41
+ prerelease: false
42
+ version_requirements: !ruby/object:Gem::Requirement
43
+ requirements:
44
+ - - ">="
45
+ - !ruby/object:Gem::Version
46
+ version: '0'
33
47
  - !ruby/object:Gem::Dependency
34
48
  name: bundler
35
49
  requirement: !ruby/object:Gem::Requirement
36
50
  requirements:
37
- - - "~>"
51
+ - - ">="
38
52
  - !ruby/object:Gem::Version
39
- version: '1.7'
53
+ version: '0'
40
54
  type: :development
41
55
  prerelease: false
42
56
  version_requirements: !ruby/object:Gem::Requirement
43
57
  requirements:
44
- - - "~>"
58
+ - - ">="
45
59
  - !ruby/object:Gem::Version
46
- version: '1.7'
60
+ version: '0'
61
+ - !ruby/object:Gem::Dependency
62
+ name: byebug
63
+ requirement: !ruby/object:Gem::Requirement
64
+ requirements:
65
+ - - ">="
66
+ - !ruby/object:Gem::Version
67
+ version: '0'
68
+ type: :development
69
+ prerelease: false
70
+ version_requirements: !ruby/object:Gem::Requirement
71
+ requirements:
72
+ - - ">="
73
+ - !ruby/object:Gem::Version
74
+ version: '0'
47
75
  - !ruby/object:Gem::Dependency
48
76
  name: rake
49
77
  requirement: !ruby/object:Gem::Requirement
50
78
  requirements:
51
- - - "~>"
79
+ - - ">="
52
80
  - !ruby/object:Gem::Version
53
- version: '10.5'
81
+ version: '0'
54
82
  type: :development
55
83
  prerelease: false
56
84
  version_requirements: !ruby/object:Gem::Requirement
57
85
  requirements:
58
- - - "~>"
86
+ - - ">="
59
87
  - !ruby/object:Gem::Version
60
- version: '10.5'
88
+ version: '0'
61
89
  - !ruby/object:Gem::Dependency
62
90
  name: rspec
63
91
  requirement: !ruby/object:Gem::Requirement
@@ -93,9 +121,9 @@ executables: []
93
121
  extensions: []
94
122
  extra_rdoc_files: []
95
123
  files:
124
+ - ".github/workflows/ruby.yml"
96
125
  - ".gitignore"
97
126
  - ".rspec"
98
- - ".travis.yml"
99
127
  - Gemfile
100
128
  - LICENSE.txt
101
129
  - README.md
@@ -103,12 +131,14 @@ files:
103
131
  - VERSION
104
132
  - ezid-client.gemspec
105
133
  - lib/ezid-client.rb
134
+ - lib/ezid/batch.rb
106
135
  - lib/ezid/batch_download.rb
107
136
  - lib/ezid/client.rb
108
137
  - lib/ezid/configuration.rb
109
138
  - lib/ezid/error.rb
110
139
  - lib/ezid/identifier.rb
111
140
  - lib/ezid/metadata.rb
141
+ - lib/ezid/metadata_transforms/datacite.rb
112
142
  - lib/ezid/proxy_identifier.rb
113
143
  - lib/ezid/requests/batch_download_request.rb
114
144
  - lib/ezid/requests/create_identifier_request.rb
@@ -137,20 +167,25 @@ files:
137
167
  - lib/ezid/session.rb
138
168
  - lib/ezid/status.rb
139
169
  - lib/ezid/test_helper.rb
170
+ - spec/fixtures/anvl_batch.txt
171
+ - spec/fixtures/datacite_xml/empty.xml
172
+ - spec/fixtures/datacite_xml/populated.xml
173
+ - spec/integration/batch_download_spec.rb
140
174
  - spec/integration/client_spec.rb
141
175
  - spec/integration/identifier_spec.rb
142
176
  - spec/spec_helper.rb
143
177
  - spec/unit/batch_download_request_spec.rb
144
- - spec/unit/batch_download_spec.rb
178
+ - spec/unit/batch_spec.rb
145
179
  - spec/unit/client_spec.rb
146
180
  - spec/unit/identifier_spec.rb
147
181
  - spec/unit/metadata_spec.rb
182
+ - spec/unit/metadata_transform_datacite_spec.rb
148
183
  - spec/unit/proxy_identifier_spec.rb
149
184
  homepage: https://github.com/duke-libraries/ezid-client
150
185
  licenses:
151
186
  - BSD-3-Clause
152
187
  metadata: {}
153
- post_install_message:
188
+ post_install_message:
154
189
  rdoc_options: []
155
190
  require_paths:
156
191
  - lib
@@ -158,25 +193,29 @@ required_ruby_version: !ruby/object:Gem::Requirement
158
193
  requirements:
159
194
  - - "~>"
160
195
  - !ruby/object:Gem::Version
161
- version: '2.0'
196
+ version: '2.1'
162
197
  required_rubygems_version: !ruby/object:Gem::Requirement
163
198
  requirements:
164
- - - ">="
199
+ - - ">"
165
200
  - !ruby/object:Gem::Version
166
- version: '0'
201
+ version: 1.3.1
167
202
  requirements: []
168
- rubyforge_project:
169
- rubygems_version: 2.4.3
170
- signing_key:
203
+ rubygems_version: 3.0.8
204
+ signing_key:
171
205
  specification_version: 4
172
206
  summary: Ruby client for EZID API Version 2
173
207
  test_files:
208
+ - spec/fixtures/anvl_batch.txt
209
+ - spec/fixtures/datacite_xml/empty.xml
210
+ - spec/fixtures/datacite_xml/populated.xml
211
+ - spec/integration/batch_download_spec.rb
174
212
  - spec/integration/client_spec.rb
175
213
  - spec/integration/identifier_spec.rb
176
214
  - spec/spec_helper.rb
177
215
  - spec/unit/batch_download_request_spec.rb
178
- - spec/unit/batch_download_spec.rb
216
+ - spec/unit/batch_spec.rb
179
217
  - spec/unit/client_spec.rb
180
218
  - spec/unit/identifier_spec.rb
181
219
  - spec/unit/metadata_spec.rb
220
+ - spec/unit/metadata_transform_datacite_spec.rb
182
221
  - spec/unit/proxy_identifier_spec.rb