ezid-client 0.3.0 → 0.4.0

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,203 @@
1
+ module Ezid
2
+ RSpec.describe Identifier do
3
+
4
+ describe ".create" do
5
+ describe "when given an id" do
6
+ let(:id) { "ark:/99999/fk4zzzzzzz" }
7
+ subject { described_class.create(id: id) }
8
+ before do
9
+ allow_any_instance_of(Client).to receive(:create_identifier).with(id, {}) { double(id: id) }
10
+ allow_any_instance_of(Client).to receive(:get_identifier_metadata).with(id) { double(metadata: {}) }
11
+ end
12
+ it "should create an identifier" do
13
+ expect(subject).to be_a(described_class)
14
+ expect(subject.id).to eq(id)
15
+ end
16
+ end
17
+ describe "when given a shoulder (and no id)" do
18
+ let(:id) { "ark:/99999/fk4fn19h88" }
19
+ subject { described_class.create(shoulder: ARK_SHOULDER) }
20
+ before do
21
+ allow_any_instance_of(Client).to receive(:mint_identifier).with(ARK_SHOULDER, {}) { double(id: id) }
22
+ allow_any_instance_of(Client).to receive(:get_identifier_metadata).with(id) { double(metadata: {}) }
23
+ end
24
+ it "should mint an identifier" do
25
+ expect(subject).to be_a(described_class)
26
+ expect(subject.id).to eq(id)
27
+ end
28
+ end
29
+ describe "when given neither an id nor a shoulder" do
30
+ it "should raise an exception" do
31
+ expect { described_class.create }.to raise_error
32
+ end
33
+ end
34
+ describe "with metadata" do
35
+ it "should send the metadata"
36
+ end
37
+ end
38
+
39
+ describe ".find" do
40
+ describe "when the id exists" do
41
+ let(:id) { "ark:/99999/fk4fn19h88" }
42
+ subject { described_class.find(id) }
43
+ before do
44
+ allow_any_instance_of(Client).to receive(:get_identifier_metadata).with(id) { double(id: id, metadata: {}) }
45
+ end
46
+ it "should get the identifier" do
47
+ expect(subject).to be_a(Identifier)
48
+ expect(subject.id).to eq(id)
49
+ end
50
+ end
51
+ describe "when the id does not exist" do
52
+ let(:id) { "ark:/99999/fk4zzzzzzz" }
53
+ before do
54
+ allow_any_instance_of(Client).to receive(:get_identifier_metadata).with(id).and_raise(Error)
55
+ end
56
+ it "should raise an exception" do
57
+ expect { described_class.find(id) }.to raise_error
58
+ end
59
+ end
60
+ end
61
+
62
+ describe "#update" do
63
+ let(:id) { "ark:/99999/fk4fn19h88" }
64
+ let(:metadata) { {"_status" => "unavailable"} }
65
+ subject { described_class.new(id: id) }
66
+ before do
67
+ allow(subject).to receive(:persisted?) { true }
68
+ allow(subject.client).to receive(:modify_identifier).with(id, subject.metadata) do
69
+ double(id: id, metadata: {})
70
+ end
71
+ end
72
+ it "should update the metadata" do
73
+ expect(subject.metadata).to receive(:update).with(metadata)
74
+ subject.update(metadata)
75
+ end
76
+ it "should save the identifier" do
77
+ expect(subject).to receive(:save)
78
+ subject.update(metadata)
79
+ end
80
+ end
81
+
82
+ describe "#reload" do
83
+ let(:id) { "ark:/99999/fk4fn19h88" }
84
+ let(:metadata) { "_created: 1416507086" }
85
+ subject { described_class.new(id: id) }
86
+ before do
87
+ allow(subject.client).to receive(:get_identifier_metadata).with(id) { double(metadata: metadata) }
88
+ end
89
+ it "should update the metadata from EZID" do
90
+ expect(subject.metadata).to receive(:replace).with(metadata)
91
+ subject.reload
92
+ end
93
+ end
94
+
95
+ describe "#reset" do
96
+ it "should clear the local metadata" do
97
+ expect(subject.metadata).to receive(:clear)
98
+ subject.reset
99
+ end
100
+ end
101
+
102
+ describe "#persisted?" do
103
+ it "should be false if id is nil" do
104
+ expect(subject).not_to be_persisted
105
+ end
106
+ context "when `created' is nil" do
107
+ before { allow(subject).to receive(:id) { "ark:/99999/fk4fn19h88" } }
108
+ it "should be false" do
109
+ expect(subject).not_to be_persisted
110
+ end
111
+ end
112
+ context "when id and `created' are present" do
113
+ before do
114
+ allow(subject).to receive(:id) { "ark:/99999/fk4fn19h88" }
115
+ allow(subject.metadata).to receive(:created) { Time.at(1416507086) }
116
+ end
117
+ it "should be true" do
118
+ expect(subject).to be_persisted
119
+ end
120
+ end
121
+ end
122
+
123
+ describe "#delete" do
124
+ let(:id) { "ark:/99999/fk4zzzzzzz" }
125
+ subject { described_class.new(id: id, status: "reserved") }
126
+ before do
127
+ allow_any_instance_of(Client).to receive(:delete_identifier).with(id) { double(id: id) }
128
+ end
129
+ it "should delete the identifier" do
130
+ expect(subject.client).to receive(:delete_identifier).with(id)
131
+ subject.delete
132
+ expect(subject).to be_deleted
133
+ end
134
+ end
135
+
136
+ describe "#save" do
137
+ let(:id) { "ark:/99999/fk4zzzzzzz" }
138
+ before do
139
+ allow(subject.client).to receive(:get_identifier_metadata).with(id) { double(metadata: {}) }
140
+ end
141
+ context "when the identifier is persisted" do
142
+ before do
143
+ allow_any_instance_of(Client).to receive(:modify_identifier).with(id, {}) { double(id: id) }
144
+ allow(subject).to receive(:id) { id }
145
+ allow(subject).to receive(:persisted?) { true }
146
+ end
147
+ it "should modify the identifier" do
148
+ expect(subject.client).to receive(:modify_identifier).with(id, {})
149
+ subject.save
150
+ end
151
+ end
152
+ context "when the identifier is not persisted" do
153
+ before do
154
+ allow(subject).to receive(:persisted?) { false }
155
+ end
156
+ context "and `id' is present" do
157
+ before do
158
+ allow(subject).to receive(:id) { id }
159
+ allow_any_instance_of(Client).to receive(:create_identifier).with(id, {}) { double(id: id) }
160
+ end
161
+ it "should create the identifier" do
162
+ expect(subject.client).to receive(:create_identifier).with(id, {})
163
+ subject.save
164
+ end
165
+ end
166
+ context "and `id' is not present" do
167
+ context "and `shoulder' is present" do
168
+ before do
169
+ allow(subject).to receive(:shoulder) { ARK_SHOULDER }
170
+ allow_any_instance_of(Client).to receive(:mint_identifier).with(ARK_SHOULDER, {}) { double(id: id) }
171
+ end
172
+ it "should mint the identifier" do
173
+ expect(subject.client).to receive(:mint_identifier).with(ARK_SHOULDER, {})
174
+ subject.save
175
+ end
176
+ end
177
+ context "and `shoulder' is not present" do
178
+ it "should raise an exception" do
179
+ expect { subject.save }.to raise_error
180
+ end
181
+ end
182
+ end
183
+ end
184
+ end
185
+
186
+ it "should handle CRUD operations", type: :feature do
187
+ # create (mint)
188
+ identifier = Ezid::Identifier.create(shoulder: ARK_SHOULDER)
189
+ expect(identifier.status).to eq("public")
190
+ # update
191
+ identifier.target = "http://example.com"
192
+ identifier.save
193
+ # retrieve
194
+ identifier = Ezid::Identifier.find(identifier.id)
195
+ expect(identifier.target).to eq("http://example.com")
196
+ # delete
197
+ identifier = Ezid::Identifier.create(shoulder: ARK_SHOULDER, status: "reserved")
198
+ identifier.delete
199
+ expect { Ezid::Identifier.find(identifier.id) }.to raise_error
200
+ end
201
+
202
+ end
203
+ end
@@ -11,31 +11,37 @@ module Ezid
11
11
  "_created" => "1416507086",
12
12
  "_status" => "public" }
13
13
  end
14
- before { subject.instance_variable_set(:@elements, elements) }
15
- describe "#status" do
16
- it "should return the status" do
17
- expect(subject.status).to eq("public")
18
- end
19
- end
20
- describe "#target" do
21
- it "should return the target URL" do
22
- expect(subject.target).to eq("http://ezid.cdlib.org/id/ark:/99999/fk4fn19h87")
23
- end
14
+ subject { described_class.new(elements) }
15
+
16
+ it "should have a non-leading-underscore reader for each reserved element, except '_crossref'" do
17
+ Metadata::RESERVED_ELEMENTS.each do |element|
18
+ next if element == "_crossref"
19
+ expect(subject).to respond_to(element.sub("_", ""))
20
+ end
24
21
  end
25
- describe "#profile" do
26
- it "should return the profile" do
27
- expect(subject.profile).to eq("erc")
22
+
23
+ describe "element reader aliases for datetime elements" do
24
+ it "should return Time values" do
25
+ expect(subject.created).to eq Time.parse("2014-11-20 13:11:26 -0500")
26
+ expect(subject.updated).to eq Time.parse("2014-11-20 13:11:26 -0500")
28
27
  end
29
28
  end
30
- describe "#created" do
31
- it "should return the creation time" do
32
- expect(subject.created).to be_a(Time)
33
- end
29
+
30
+ it "should have a non-leading-underscore writer for each writable reserved element, except '_crossref'" do
31
+ Metadata::RESERVED_READWRITE_ELEMENTS.each do |element|
32
+ next if element == "_crossref"
33
+ expect(subject).to respond_to("#{element.sub('_', '')}=")
34
+ end
35
+ end
36
+
37
+ describe "#update" do
38
+ it "should coerce the data"
39
+ it "should update the delegated hash"
34
40
  end
35
- describe "#updated" do
36
- it "should return the last update time" do
37
- expect(subject.updated).to be_a(Time)
38
- end
41
+
42
+ describe "#replace" do
43
+ it "should coerce the data"
44
+ it "should call `replace' on the delegated hash"
39
45
  end
40
46
 
41
47
  describe "ANVL output" do
@@ -52,11 +58,11 @@ _status: public")
52
58
  end
53
59
  describe "encoding" do
54
60
  before do
55
- subject.each_key { |k| subject[k] = subject[k].force_encoding("US_ASCII") }
61
+ subject.each_key { |k| subject[k] = subject[k].force_encoding(Encoding::US_ASCII) }
62
+ end
63
+ it "should be encoded in UTF-8" do
64
+ expect(subject.to_anvl.encoding).to eq(Encoding::UTF_8)
56
65
  end
57
- end
58
- it "should be encoded in UTF-8" do
59
- expect(subject.to_anvl.encoding).to eq(Encoding::UTF_8)
60
66
  end
61
67
  describe "escaping" do
62
68
  before do
@@ -78,6 +84,12 @@ _status: public")
78
84
 
79
85
  describe "coercion" do
80
86
  subject { described_class.new(data) }
87
+ context "of nil" do
88
+ let(:data) { nil }
89
+ it "should return an empty hash" do
90
+ expect(subject).to eq({})
91
+ end
92
+ end
81
93
  context "of a string" do
82
94
  let(:data) do <<-EOS
83
95
  _updated: 1416507086
@@ -91,14 +103,14 @@ _status: public
91
103
  EOS
92
104
  end
93
105
  it "should coerce the data into a hash" do
94
- expect(subject.elements).to eq({"_updated" => "1416507086",
95
- "_target" => "http://ezid.cdlib.org/id/ark:/99999/fk4fn19h87",
96
- "_profile" => "erc",
97
- "_ownergroup" => "apitest",
98
- "_owner" => "apitest",
99
- "_export" => "yes",
100
- "_created" => "1416507086",
101
- "_status" => "public"})
106
+ expect(subject).to eq({"_updated" => "1416507086",
107
+ "_target" => "http://ezid.cdlib.org/id/ark:/99999/fk4fn19h87",
108
+ "_profile" => "erc",
109
+ "_ownergroup" => "apitest",
110
+ "_owner" => "apitest",
111
+ "_export" => "yes",
112
+ "_created" => "1416507086",
113
+ "_status" => "public"})
102
114
  end
103
115
  end
104
116
  context "of a hash" do
@@ -113,14 +125,161 @@ EOS
113
125
  _status: "public" }
114
126
  end
115
127
  it "should stringify the keys" do
116
- expect(subject.elements).to eq({"_updated" => "1416507086",
117
- "_target" => "http://ezid.cdlib.org/id/ark:/99999/fk4fn19h87",
118
- "_profile" => "erc",
119
- "_ownergroup" => "apitest",
120
- "_owner" => "apitest",
121
- "_export" => "yes",
122
- "_created" => "1416507086",
123
- "_status" => "public"})
128
+ expect(subject).to eq({"_updated" => "1416507086",
129
+ "_target" => "http://ezid.cdlib.org/id/ark:/99999/fk4fn19h87",
130
+ "_profile" => "erc",
131
+ "_ownergroup" => "apitest",
132
+ "_owner" => "apitest",
133
+ "_export" => "yes",
134
+ "_created" => "1416507086",
135
+ "_status" => "public"})
136
+ end
137
+ end
138
+ context "of a Metadata instance" do
139
+ let(:hsh) do
140
+ { "_updated" => "1416507086",
141
+ "_target" => "http://ezid.cdlib.org/id/ark:/99999/fk4fn19h87",
142
+ "_profile" => "erc",
143
+ "_ownergroup" => "apitest",
144
+ "_owner" => "apitest",
145
+ "_export" => "yes",
146
+ "_created" => "1416507086",
147
+ "_status" => "public" }
148
+ end
149
+ let(:data) { Metadata.new(hsh) }
150
+ it "should have the same hash" do
151
+ expect(subject).to eq(hsh)
152
+ end
153
+ end
154
+ end
155
+
156
+ describe "profiles" do
157
+ describe "dc" do
158
+ describe "readers" do
159
+ before do
160
+ subject.update("dc.title" => "Testing Profiles",
161
+ "dc.creator" => "Kermit the Frog",
162
+ "dc.publisher" => "Duke University",
163
+ "dc.date" => "2004",
164
+ "dc.type" => "Text")
165
+ end
166
+ it "should have a reader for each element" do
167
+ expect(subject.dc_title).to eq("Testing Profiles")
168
+ expect(subject.dc_creator).to eq("Kermit the Frog")
169
+ expect(subject.dc_publisher).to eq("Duke University")
170
+ expect(subject.dc_date).to eq("2004")
171
+ expect(subject.dc_type).to eq("Text")
172
+ end
173
+ end
174
+ describe "writers" do
175
+ before do
176
+ subject.dc_title = "Run of the Mill"
177
+ subject.dc_creator = "Jack Bean"
178
+ subject.dc_publisher = "Random Housing"
179
+ subject.dc_date = "1967"
180
+ subject.dc_type = "Physical Object"
181
+ end
182
+ it "should have a writer for each element" do
183
+ expect(subject["dc.title"]).to eq "Run of the Mill"
184
+ expect(subject["dc.creator"]).to eq "Jack Bean"
185
+ expect(subject["dc.publisher"]).to eq "Random Housing"
186
+ expect(subject["dc.date"]).to eq "1967"
187
+ expect(subject["dc.type"]).to eq "Physical Object"
188
+ end
189
+ end
190
+ end
191
+ describe "erc" do
192
+ describe "readers" do
193
+ before do
194
+ subject.update("erc.what" => "Testing Profiles",
195
+ "erc.who" => "Kermit the Frog",
196
+ "erc.when" => "2004")
197
+ end
198
+ it "should have a reader for each element" do
199
+ expect(subject.erc_what).to eq("Testing Profiles")
200
+ expect(subject.erc_who).to eq("Kermit the Frog")
201
+ expect(subject.erc_when).to eq("2004")
202
+ end
203
+ end
204
+ describe "writers" do
205
+ before do
206
+ subject.erc_what = "Run of the Mill"
207
+ subject.erc_who = "Jack Bean"
208
+ subject.erc_when = "1967"
209
+ end
210
+ it "should have a writer for each element" do
211
+ expect(subject["erc.what"]).to eq "Run of the Mill"
212
+ expect(subject["erc.who"]).to eq "Jack Bean"
213
+ expect(subject["erc.when"]).to eq "1967"
214
+ end
215
+ end
216
+ end
217
+ describe "crossref" do
218
+ describe "xml document reader" do
219
+ before do
220
+ subject["crossref"] = "<xml/>"
221
+ end
222
+ it "should return the xml" do
223
+ expect(subject.crossref).to eq "<xml/>"
224
+ end
225
+ end
226
+ describe "xml document writer" do
227
+ before do
228
+ subject.crossref = "<yml/>"
229
+ end
230
+ it "should set the 'crossref' metadata element" do
231
+ expect(subject["crossref"]).to eq "<yml/>"
232
+ end
233
+ end
234
+ end
235
+ describe "datacite" do
236
+ describe "element readers" do
237
+ before do
238
+ subject.update("datacite.title" => "Testing Profiles",
239
+ "datacite.creator" => "Kermit the Frog",
240
+ "datacite.publisher" => "Duke University",
241
+ "datacite.publicationyear" => "2004",
242
+ "datacite.resourcetype" => "Text")
243
+ end
244
+ it "should have a reader for each element" do
245
+ expect(subject.datacite_title).to eq("Testing Profiles")
246
+ expect(subject.datacite_creator).to eq("Kermit the Frog")
247
+ expect(subject.datacite_publisher).to eq("Duke University")
248
+ expect(subject.datacite_publicationyear).to eq("2004")
249
+ expect(subject.datacite_resourcetype).to eq("Text")
250
+ end
251
+ end
252
+ describe "element writers" do
253
+ before do
254
+ subject.datacite_title = "Run of the Mill"
255
+ subject.datacite_creator = "Jack Bean"
256
+ subject.datacite_publisher = "Random Housing"
257
+ subject.datacite_publicationyear = "1967"
258
+ subject.datacite_resourcetype = "Physical Object"
259
+ end
260
+ it "should have a writer for each element" do
261
+ expect(subject["datacite.title"]).to eq "Run of the Mill"
262
+ expect(subject["datacite.creator"]).to eq "Jack Bean"
263
+ expect(subject["datacite.publisher"]).to eq "Random Housing"
264
+ expect(subject["datacite.publicationyear"]).to eq "1967"
265
+ expect(subject["datacite.resourcetype"]).to eq "Physical Object"
266
+ end
267
+ end
268
+ describe "xml document reader" do
269
+ before do
270
+ subject["datacite"] = "<xml/>"
271
+ end
272
+ it "should return the xml" do
273
+ expect(subject.datacite).to eq "<xml/>"
274
+ end
275
+ end
276
+ describe "xml document writer" do
277
+ before do
278
+ subject.datacite = "<yml/>"
279
+ end
280
+ it "should set the 'datacite' metadata element" do
281
+ expect(subject["datacite"]).to eq "<yml/>"
282
+ end
124
283
  end
125
284
  end
126
285
  end