ppl 1.25.0 → 2.0.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.
Files changed (34) hide show
  1. checksums.yaml +4 -4
  2. data/features/email.feature +10 -0
  3. data/features/ls.feature +15 -0
  4. data/features/post.feature +24 -0
  5. data/features/step_definitions/ppl_steps.rb +17 -0
  6. data/lib/ppl/adapter/vcard/greencard.rb +49 -19
  7. data/lib/ppl/application/bootstrap.rb +13 -3
  8. data/lib/ppl/application/shell.rb +2 -0
  9. data/lib/ppl/command/post.rb +60 -16
  10. data/lib/ppl/entity/contact.rb +10 -4
  11. data/lib/ppl/entity/postal_address.rb +6 -0
  12. data/lib/ppl/error/postal_address_not_found.rb +4 -0
  13. data/lib/ppl/format/address_book/postal_addresses.rb +5 -18
  14. data/lib/ppl/format/contact/full.rb +5 -6
  15. data/lib/ppl/format/contact/postal_addresses.rb +26 -0
  16. data/lib/ppl/format/custom/contact.rb +8 -12
  17. data/lib/ppl/format/postal_address/multi_line.rb +16 -0
  18. data/lib/ppl/format/postal_address/one_line.rb +21 -9
  19. data/lib/ppl/service/postal_address.rb +65 -0
  20. data/lib/ppl.rb +5 -1
  21. data/ppl.gemspec +4 -4
  22. data/spec/ppl/adapter/vcard/greencard_spec.rb +151 -98
  23. data/spec/ppl/application/bootstrap_spec.rb +14 -2
  24. data/spec/ppl/application/shell_spec.rb +8 -0
  25. data/spec/ppl/command/post_spec.rb +83 -61
  26. data/spec/ppl/entity/contact_spec.rb +40 -10
  27. data/spec/ppl/entity/postal_address_spec.rb +6 -0
  28. data/spec/ppl/format/address_book/postal_addresses_spec.rb +6 -14
  29. data/spec/ppl/format/contact/full_spec.rb +1 -1
  30. data/spec/ppl/format/contact/postal_addresses_spec.rb +36 -0
  31. data/spec/ppl/format/postal_address/multi_line_spec.rb +57 -0
  32. data/spec/ppl/format/postal_address/one_line_spec.rb +32 -18
  33. data/spec/ppl/service/postal_address_spec.rb +152 -0
  34. metadata +13 -4
@@ -0,0 +1,65 @@
1
+
2
+ class Ppl::Service::PostalAddress
3
+
4
+ def add(contact, address_id, options)
5
+ address = Ppl::Entity::PostalAddress.new
6
+ address.id = address_id
7
+ update_postal_address(contact, address, options)
8
+ contact.postal_addresses << address
9
+ end
10
+
11
+ def update(contact, address_id, options)
12
+ address = contact.postal_addresses.find { |p| p.id == address_id }
13
+ update_postal_address(contact, address, options)
14
+ if options[:new_id]
15
+ move(contact, address_id, options[:new_id])
16
+ end
17
+ end
18
+
19
+ def remove(contact, address_id)
20
+ require_address(contact, address_id)
21
+ contact.postal_addresses.reject! { |pa| pa.id == address_id }
22
+ end
23
+
24
+ def move(contact, address_id, new_address_id)
25
+ address = require_address(contact, address_id)
26
+ id_okay = contact.postal_addresses.select { |pa| pa.id == new_address_id }.empty?
27
+ if id_okay
28
+ address.id = new_address_id
29
+ else
30
+ raise "Address '#{new_address_id}' is already in use"
31
+ end
32
+ end
33
+
34
+ private
35
+
36
+ def require_address(contact, address_id)
37
+ address = contact.postal_addresses.find { |p| p.id == address_id }
38
+ if address.nil?
39
+ raise Ppl::Error::PostalAddressNotFound, address_id
40
+ end
41
+ address
42
+ end
43
+
44
+ def update_postal_address(contact, address, options)
45
+ [
46
+ :country,
47
+ :locality,
48
+ :po_box,
49
+ :postal_code,
50
+ :region,
51
+ :street,
52
+ ].each do |property|
53
+ unless options[property].nil?
54
+ address.send("#{property.to_s}=", options[property])
55
+ end
56
+ end
57
+ if options[:preferred] == true
58
+ contact.postal_addresses.each { |pa| pa.preferred = (pa.id == address.id) }
59
+ elsif options[:preferred] == false
60
+ address.preferred = false
61
+ end
62
+ end
63
+
64
+ end
65
+
data/lib/ppl.rb CHANGED
@@ -1,7 +1,7 @@
1
1
 
2
2
  module Ppl
3
3
 
4
- Version = "1.25.0"
4
+ Version = "2.0.0"
5
5
 
6
6
  module Adapter
7
7
  end
@@ -80,6 +80,7 @@ require "ppl/entity/postal_address"
80
80
  require "ppl/error/completion_not_found"
81
81
  require "ppl/error/contact_not_found"
82
82
  require "ppl/error/incorrect_usage"
83
+ require "ppl/error/postal_address_not_found"
83
84
 
84
85
  require "ppl/format/address_book"
85
86
  require "ppl/format/address_book/ages"
@@ -103,17 +104,20 @@ require "ppl/format/contact/nicknames"
103
104
  require "ppl/format/contact/organization"
104
105
  require "ppl/format/contact/phone_number"
105
106
  require "ppl/format/contact/postal_address"
107
+ require "ppl/format/contact/postal_addresses"
106
108
  require "ppl/format/contact/urls"
107
109
  require "ppl/format/custom"
108
110
  require "ppl/format/custom/contact"
109
111
  require "ppl/format/custom/email_address"
110
112
  require "ppl/format/custom/phone_number"
111
113
  require "ppl/format/postal_address"
114
+ require "ppl/format/postal_address/multi_line"
112
115
  require "ppl/format/postal_address/one_line"
113
116
  require "ppl/format/table"
114
117
 
115
118
  require "ppl/service/email_address"
116
119
  require "ppl/service/phone_number"
120
+ require "ppl/service/postal_address"
117
121
 
118
122
  class String
119
123
  alias_method :each, :each_line
data/ppl.gemspec CHANGED
@@ -2,13 +2,13 @@
2
2
  Gem::Specification.new do |spec|
3
3
 
4
4
  spec.name = "ppl"
5
- spec.version = "1.25.0"
6
- spec.date = "2013-04-24"
5
+ spec.version = "2.0.0"
6
+ spec.date = "2013-05-09"
7
7
 
8
8
  spec.required_ruby_version = ">= 1.9.3"
9
9
 
10
- spec.summary = "CLI Address Book"
11
- spec.description = "CLI Address Book"
10
+ spec.summary = "The command line address book"
11
+ spec.description = "ppl is a command-line address book using vCard & git for storage and synchronisation"
12
12
  spec.license = "GPL-2"
13
13
 
14
14
  spec.add_dependency("colored", "1.2")
@@ -51,40 +51,53 @@ describe Ppl::Adapter::Vcard::GreenCard, "#encode" do
51
51
  @adapter.encode(@contact).should include("ORG:Example Ltd")
52
52
  end
53
53
 
54
- it "should encode the contact's street address" do
55
- @contact.postal_address = Ppl::Entity::PostalAddress.new
56
- @contact.postal_address.street = "1 Testing Road"
57
- @adapter.encode(@contact).should include("ADR:;;1 Testing Road;;;;")
58
- end
54
+ describe "postal address encoding" do
59
55
 
60
- it "should encode the contact's postal code" do
61
- @contact.postal_address = Ppl::Entity::PostalAddress.new
62
- @contact.postal_address.postal_code = "L7 8AA"
63
- @adapter.encode(@contact).should include("ADR:;;;;;L7 8AA;")
64
- end
56
+ before(:each) do
57
+ @address = Ppl::Entity::PostalAddress.new
58
+ @contact.postal_addresses << @address
59
+ end
65
60
 
66
- it "should encode the contact's po box" do
67
- @contact.postal_address = Ppl::Entity::PostalAddress.new
68
- @contact.postal_address.po_box = "123456"
69
- @adapter.encode(@contact).should include("ADR:123456;;;;;;")
70
- end
61
+ it "should encode the address id" do
62
+ @contact.postal_addresses[0].id = "home"
63
+ @adapter.encode(@contact).should include("ADR;TYPE=home:;;;;;;")
64
+ end
71
65
 
72
- it "should encode the contact's locality" do
73
- @contact.postal_address = Ppl::Entity::PostalAddress.new
74
- @contact.postal_address.locality = "Liverpool"
75
- @adapter.encode(@contact).should include("ADR:;;;Liverpool;;;")
76
- end
66
+ it "should encode the preferred status of the address" do
67
+ @contact.postal_addresses[0].preferred = true
68
+ @adapter.encode(@contact).should include("ADR;TYPE=pref:;;;;;;")
69
+ end
77
70
 
78
- it "should encode the contact's country" do
79
- @contact.postal_address = Ppl::Entity::PostalAddress.new
80
- @contact.postal_address.country = "UK"
81
- @adapter.encode(@contact).should include("ADR:;;;;;;UK")
82
- end
71
+ it "should encode the contact's street address" do
72
+ @contact.postal_addresses[0].street = "1 Testing Road"
73
+ @adapter.encode(@contact).should include("ADR:;;1 Testing Road;;;;")
74
+ end
75
+
76
+ it "should encode the contact's postal code" do
77
+ @contact.postal_addresses[0].postal_code = "L7 8AA"
78
+ @adapter.encode(@contact).should include("ADR:;;;;;L7 8AA;")
79
+ end
80
+
81
+ it "should encode the contact's po box" do
82
+ @contact.postal_addresses[0].po_box = "123456"
83
+ @adapter.encode(@contact).should include("ADR:123456;;;;;;")
84
+ end
85
+
86
+ it "should encode the contact's locality" do
87
+ @contact.postal_addresses[0].locality = "Liverpool"
88
+ @adapter.encode(@contact).should include("ADR:;;;Liverpool;;;")
89
+ end
90
+
91
+ it "should encode the contact's country" do
92
+ @contact.postal_addresses[0].country = "UK"
93
+ @adapter.encode(@contact).should include("ADR:;;;;;;UK")
94
+ end
95
+
96
+ it "should encode the contact's region" do
97
+ @contact.postal_addresses[0].region = "South West"
98
+ @adapter.encode(@contact).should include("ADR:;;;;South West;;")
99
+ end
83
100
 
84
- it "should encode the contact's region" do
85
- @contact.postal_address = Ppl::Entity::PostalAddress.new
86
- @contact.postal_address.region = "South West"
87
- @adapter.encode(@contact).should include("ADR:;;;;South West;;")
88
101
  end
89
102
 
90
103
  it "should encode the contact's URL" do
@@ -229,76 +242,116 @@ describe Ppl::Adapter::Vcard::GreenCard, "#decode" do
229
242
  contact.organizations.first.should eq "Example Ltd"
230
243
  end
231
244
 
232
- it "should decode the contact's street address" do
233
- vcard = [
234
- "BEGIN:VCARD",
235
- "N:,test",
236
- "VERSION:3.0",
237
- "ADR:;;1 Testing Road;;;;",
238
- "END:VCARD",
239
- ].join("\n")
240
- contact = @adapter.decode(vcard)
241
- contact.postal_address.street.should eq "1 Testing Road"
242
- end
245
+ describe "postal address decoding" do
246
+
247
+ it "should decode the postal address' ID" do
248
+ vcard = [
249
+ "BEGIN:VCARD",
250
+ "N:,test",
251
+ "VERSION:3.0",
252
+ "ADR;TYPE=home:;;1 Testing Road;;;;",
253
+ "END:VCARD",
254
+ ].join("\n")
255
+ contact = @adapter.decode(vcard)
256
+ contact.postal_addresses[0].id.should eq "home"
257
+ end
258
+
259
+ it "should decode the postal address' ID even if it's a nonstandard type" do
260
+ vcard = [
261
+ "BEGIN:VCARD",
262
+ "N:,test",
263
+ "VERSION:3.0",
264
+ "ADR;TYPE=nasa:;;1 Testing Road;;;;",
265
+ "END:VCARD",
266
+ ].join("\n")
267
+ contact = @adapter.decode(vcard)
268
+ contact.postal_addresses[0].id.should eq "nasa"
269
+ end
270
+
271
+ it "should assign the postal address a fallback ID if necessary" do
272
+ vcard = [
273
+ "BEGIN:VCARD",
274
+ "N:,test",
275
+ "VERSION:3.0",
276
+ "ADR:;;1 Testing Road;;;;",
277
+ "END:VCARD",
278
+ ].join("\n")
279
+ contact = @adapter.decode(vcard)
280
+ contact.postal_addresses[0].id.should eq "910c67f"
281
+ end
282
+
283
+ it "should decode the contact's street address" do
284
+ vcard = [
285
+ "BEGIN:VCARD",
286
+ "N:,test",
287
+ "VERSION:3.0",
288
+ "ADR:;;1 Testing Road;;;;",
289
+ "END:VCARD",
290
+ ].join("\n")
291
+ contact = @adapter.decode(vcard)
292
+ contact.postal_addresses[0].street.should eq "1 Testing Road"
293
+ end
294
+
295
+ it "should decode the contact's postal code" do
296
+ vcard = [
297
+ "BEGIN:VCARD",
298
+ "N:,test",
299
+ "VERSION:3.0",
300
+ "ADR:;;;;;L7 8AA;",
301
+ "END:VCARD",
302
+ ].join("\n")
303
+ contact = @adapter.decode(vcard)
304
+ contact.postal_addresses[0].postal_code.should eq "L7 8AA"
305
+ end
306
+
307
+ it "should decode the contact's po box" do
308
+ vcard = [
309
+ "BEGIN:VCARD",
310
+ "N:,test",
311
+ "VERSION:3.0",
312
+ "ADR:123456;;;;;;",
313
+ "END:VCARD",
314
+ ].join("\n")
315
+ contact = @adapter.decode(vcard)
316
+ contact.postal_addresses[0].po_box.should eq "123456"
317
+ end
318
+
319
+ it "should decode the contact's locality" do
320
+ vcard = [
321
+ "BEGIN:VCARD",
322
+ "N:,test",
323
+ "VERSION:3.0",
324
+ "ADR:;;;Liverpool;;;",
325
+ "END:VCARD",
326
+ ].join("\n")
327
+ contact = @adapter.decode(vcard)
328
+ contact.postal_addresses[0].locality.should eq "Liverpool"
329
+ end
330
+
331
+ it "should decode the contact's region" do
332
+ vcard = [
333
+ "BEGIN:VCARD",
334
+ "N:,test",
335
+ "VERSION:3.0",
336
+ "ADR:;;;;South West;;",
337
+ "END:VCARD",
338
+ ].join("\n")
339
+ contact = @adapter.decode(vcard)
340
+ contact.postal_addresses[0].region.should eq "South West"
341
+ end
342
+
343
+ it "should decode the contact's country" do
344
+ vcard = [
345
+ "BEGIN:VCARD",
346
+ "N:,test",
347
+ "VERSION:3.0",
348
+ "ADR:;;;;;;UK",
349
+ "END:VCARD",
350
+ ].join("\n")
351
+ contact = @adapter.decode(vcard)
352
+ contact.postal_addresses[0].country.should eq "UK"
353
+ end
243
354
 
244
- it "should decode the contact's postal code" do
245
- vcard = [
246
- "BEGIN:VCARD",
247
- "N:,test",
248
- "VERSION:3.0",
249
- "ADR:;;;;;L7 8AA;",
250
- "END:VCARD",
251
- ].join("\n")
252
- contact = @adapter.decode(vcard)
253
- contact.postal_address.postal_code.should eq "L7 8AA"
254
- end
255
-
256
- it "should decode the contact's po box" do
257
- vcard = [
258
- "BEGIN:VCARD",
259
- "N:,test",
260
- "VERSION:3.0",
261
- "ADR:123456;;;;;;",
262
- "END:VCARD",
263
- ].join("\n")
264
- contact = @adapter.decode(vcard)
265
- contact.postal_address.po_box.should eq "123456"
266
- end
267
-
268
- it "should decode the contact's locality" do
269
- vcard = [
270
- "BEGIN:VCARD",
271
- "N:,test",
272
- "VERSION:3.0",
273
- "ADR:;;;Liverpool;;;",
274
- "END:VCARD",
275
- ].join("\n")
276
- contact = @adapter.decode(vcard)
277
- contact.postal_address.locality.should eq "Liverpool"
278
- end
279
-
280
- it "should decode the contact's region" do
281
- vcard = [
282
- "BEGIN:VCARD",
283
- "N:,test",
284
- "VERSION:3.0",
285
- "ADR:;;;;South West;;",
286
- "END:VCARD",
287
- ].join("\n")
288
- contact = @adapter.decode(vcard)
289
- contact.postal_address.region.should eq "South West"
290
- end
291
-
292
- it "should decode the contact's country" do
293
- vcard = [
294
- "BEGIN:VCARD",
295
- "N:,test",
296
- "VERSION:3.0",
297
- "ADR:;;;;;;UK",
298
- "END:VCARD",
299
- ].join("\n")
300
- contact = @adapter.decode(vcard)
301
- contact.postal_address.country.should eq "UK"
302
355
  end
303
356
 
304
357
  it "should decode the contact's URL" do
@@ -389,8 +389,8 @@ describe Ppl::Application::Bootstrap do
389
389
  end
390
390
 
391
391
  describe "#format_contact_postal_addresses" do
392
- it "should return a Ppl::Format::Contact::PostalAddress" do
393
- @bootstrap.format_contact_postal_addresses.should be_a(Ppl::Format::Contact::PostalAddress)
392
+ it "should return a Ppl::Format::Contact::PostalAddresses" do
393
+ @bootstrap.format_contact_postal_addresses.should be_a(Ppl::Format::Contact::PostalAddresses)
394
394
  end
395
395
  end
396
396
 
@@ -407,6 +407,12 @@ describe Ppl::Application::Bootstrap do
407
407
  end
408
408
  end
409
409
 
410
+ describe "#format_postal_address_multi_line" do
411
+ it "should return a Ppl::Format::PostalAddress::MultiLine" do
412
+ @bootstrap.format_postal_address_multi_line.should be_a(Ppl::Format::PostalAddress::MultiLine)
413
+ end
414
+ end
415
+
410
416
  describe "#command_suite" do
411
417
 
412
418
  before(:each) do
@@ -553,5 +559,11 @@ describe Ppl::Application::Bootstrap do
553
559
  end
554
560
  end
555
561
 
562
+ describe "#postal_address_service" do
563
+ it "should return a Ppl::Service::PostalAddress" do
564
+ @bootstrap.postal_address_service.should be_a(Ppl::Service::PostalAddress)
565
+ end
566
+ end
567
+
556
568
  end
557
569
 
@@ -99,6 +99,14 @@ describe Ppl::Application::Shell do
99
99
  @shell.run(@input, @output)
100
100
  end
101
101
 
102
+ it "should handle PostalAddressNotFound errors nicely" do
103
+ @command.stub(:options)
104
+ @command.should_receive(:execute) { raise Ppl::Error::PostalAddressNotFound, "example" }
105
+ @router.should_receive(:route).and_return(@command)
106
+ @output.should_receive(:error).with("ppl: Postal address 'example' not found")
107
+ @shell.run(@input, @output)
108
+ end
109
+
102
110
  end
103
111
 
104
112
  end
@@ -7,14 +7,22 @@ describe Ppl::Command::Post do
7
7
  @contact = Ppl::Entity::Contact.new
8
8
  @command = Ppl::Command::Post.new
9
9
  @storage = double(Ppl::Adapter::Storage)
10
+ @service = double(Ppl::Service::PostalAddress)
10
11
 
11
- @list_format = double(Ppl::Format::Contact)
12
- @show_format = double(Ppl::Format::Contact)
12
+ @address_book_format = double(Ppl::Format::AddressBook)
13
+ @contact_format = double(Ppl::Format::Contact)
14
+ @postal_address_format = double(Ppl::Format::PostalAddress)
13
15
 
16
+ @command.address_service = @service
14
17
  @command.storage = @storage
15
- @command.show_format = @show_format
16
- @command.list_format = @list_format
18
+ @command.contact_format = @contact_format
19
+ @command.address_book_format = @address_book_format
20
+ @command.postal_address_format = @postal_address_format
17
21
  @contact.id = "jim"
22
+
23
+ @address = Ppl::Entity::PostalAddress.new
24
+ @address.id = "home"
25
+ @contact.postal_addresses << @address
18
26
  end
19
27
 
20
28
  describe "#name" do
@@ -25,84 +33,98 @@ describe Ppl::Command::Post do
25
33
 
26
34
  describe "#execute" do
27
35
 
28
- it "should list all postal addresses if no contact ID is given" do
29
- @storage.should_receive(:load_address_book).and_return(@address_book)
30
- @list_format.should_receive(:process).and_return("all the postal addresses")
31
- @output.should_receive(:line).with("all the postal addresses")
32
- @input.arguments = []
33
- @command.execute(@input, @output)
34
- end
36
+ context "show address book" do
35
37
 
36
- it "should show the current address if no new address is given" do
37
- @storage.should_receive(:require_contact).and_return(@contact)
38
- @show_format.should_receive(:process).and_return("1 Test Road")
39
- @output.should_receive(:line).with("1 Test Road")
40
- @input.arguments = ["jim"]
41
- @command.execute(@input, @output).should eq true
42
- end
38
+ before { @input.arguments = [] }
43
39
 
44
- it "should not output anything if there's nothing to show" do
45
- @storage.should_receive(:require_contact).and_return(@contact)
46
- @show_format.should_receive(:process).and_return("")
47
- @input.arguments = ["jim"]
48
- @command.execute(@input, @output).should eq false
40
+ it "displays postal address information for the whole address book" do
41
+ @storage.should_receive(:load_address_book).and_return(@address_book)
42
+ @address_book_format.should_receive(:process).and_return("all the postal addresses")
43
+ @output.should_receive(:line).with("all the postal addresses")
44
+ @input.arguments = []
45
+ @command.execute(@input, @output)
46
+ end
49
47
  end
50
48
 
51
- end
49
+ context "show contact" do
52
50
 
53
- describe "#execute" do
54
-
55
- before(:each) do
56
- @input.arguments = ["jim"]
57
- @storage.should_receive(:require_contact).and_return(@contact)
58
- end
51
+ before { @input.arguments = ["jim"] }
59
52
 
60
- it "should change the contact's street address if it's given" do
61
- @input.options = {:street => "1 Test Road"}
62
- @storage.should_receive(:save_contact) do |contact|
63
- contact.postal_address.street.should eq "1 Test Road"
53
+ it "shows all of a contact's postal addresses" do
54
+ @storage.should_receive(:require_contact).and_return(@contact)
55
+ @contact_format.should_receive(:process).and_return("1 Test Road")
56
+ @output.should_receive(:line).with("1 Test Road")
57
+ @command.execute(@input, @output).should eq true
64
58
  end
65
- @command.execute(@input, @output)
66
- end
67
59
 
68
- it "should change the contact's postal code if it's given" do
69
- @input.options = {:postal_code => "L7 8AA"}
70
- @storage.should_receive(:save_contact) do |contact|
71
- contact.postal_address.postal_code.should eq "L7 8AA"
60
+ it "outputs nothing if the contact has no addresses" do
61
+ @storage.should_receive(:require_contact).and_return(@contact)
62
+ @contact_format.should_receive(:process).and_return("")
63
+ @command.execute(@input, @output).should eq false
72
64
  end
73
- @command.execute(@input, @output)
65
+
74
66
  end
75
67
 
76
- it "should change the contact's po box if it's given" do
77
- @input.options = {:po_box => "124578"}
78
- @storage.should_receive(:save_contact) do |contact|
79
- contact.postal_address.po_box.should eq "124578"
68
+ context "show postal address" do
69
+
70
+ before { @input.arguments = ["jim", "home"] }
71
+
72
+ it "shows a single postal address" do
73
+ @storage.should_receive(:require_contact).and_return(@contact)
74
+ @postal_address_format.should_receive(:process).with(@address).and_return("1 Test Road")
75
+ @output.should_receive(:line).with("1 Test Road")
76
+ @command.execute(@input, @output).should eq true
77
+ end
78
+
79
+ it "raises an error if there's no such address" do
80
+ @input.arguments[1] = "other"
81
+ @storage.should_receive(:require_contact).and_return(@contact)
82
+ expect{@command.execute(@input, @output).should eq true}.to raise_error(Ppl::Error::PostalAddressNotFound)
80
83
  end
81
- @command.execute(@input, @output)
84
+
82
85
  end
83
86
 
84
- it "should change the contact's country if it's given" do
85
- @input.options = {:country => "UK"}
86
- @storage.should_receive(:save_contact) do |contact|
87
- contact.postal_address.country.should eq "UK"
87
+ context "delete postal address" do
88
+
89
+ before { @input.arguments = ["jim", "home"] }
90
+ before { @input.options = { :delete => true }}
91
+
92
+ it "deletes the postal address" do
93
+ @storage.should_receive(:require_contact).and_return(@contact)
94
+ @service.should_receive(:remove).with(@contact, "home")
95
+ @storage.should_receive(:save_contact)
96
+ @command.execute(@input, @output).should eq true
88
97
  end
89
- @command.execute(@input, @output)
98
+
90
99
  end
91
100
 
92
- it "should change the contact's locality if it's given" do
93
- @input.options = {:locality => "Liverpool"}
94
- @storage.should_receive(:save_contact) do |contact|
95
- contact.postal_address.locality.should eq "Liverpool"
101
+ context "update postal address" do
102
+
103
+ before { @input.arguments = ["jim", "home"] }
104
+ before { @input.options = { :country => "New Country" }}
105
+
106
+ it "updates the postal address" do
107
+ @storage.should_receive(:require_contact).and_return(@contact)
108
+ @service.should_receive(:update).with(@contact, "home", {:country => "New Country"})
109
+ @storage.should_receive(:save_contact)
110
+ @command.execute(@input, @output).should eq true
96
111
  end
97
- @command.execute(@input, @output)
112
+
98
113
  end
99
114
 
100
- it "should change the contact's region if it's given" do
101
- @input.options = {:region => "North West"}
102
- @storage.should_receive(:save_contact) do |contact|
103
- contact.postal_address.region.should eq "North West"
115
+
116
+ context "add postal address" do
117
+
118
+ before { @input.arguments = ["jim", "newaddress"] }
119
+ before { @input.options = { :street => "123 Swim St" }}
120
+
121
+ it "adds the postal address" do
122
+ @storage.should_receive(:require_contact).and_return(@contact)
123
+ @service.should_receive(:add).with(@contact, "newaddress", {:street => "123 Swim St"})
124
+ @storage.should_receive(:save_contact)
125
+ @command.execute(@input, @output).should eq true
104
126
  end
105
- @command.execute(@input, @output)
127
+
106
128
  end
107
129
 
108
130
  end