punchblock 1.6.1 → 1.7.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 (46) hide show
  1. data/CHANGELOG.md +8 -0
  2. data/Guardfile +1 -1
  3. data/Rakefile +1 -1
  4. data/lib/punchblock/client.rb +5 -8
  5. data/lib/punchblock/client/component_registry.rb +8 -1
  6. data/lib/punchblock/component/component_node.rb +1 -0
  7. data/lib/punchblock/component/output.rb +15 -1
  8. data/lib/punchblock/translator/asterisk.rb +1 -1
  9. data/lib/punchblock/translator/asterisk/call.rb +1 -1
  10. data/lib/punchblock/translator/asterisk/component/output.rb +5 -1
  11. data/lib/punchblock/translator/freeswitch.rb +7 -1
  12. data/lib/punchblock/translator/freeswitch/call.rb +10 -6
  13. data/lib/punchblock/translator/freeswitch/component.rb +1 -1
  14. data/lib/punchblock/version.rb +1 -1
  15. data/punchblock.gemspec +1 -2
  16. data/spec/punchblock/client/component_registry_spec.rb +7 -0
  17. data/spec/punchblock/client_spec.rb +14 -12
  18. data/spec/punchblock/command_node_spec.rb +2 -2
  19. data/spec/punchblock/component/component_node_spec.rb +10 -3
  20. data/spec/punchblock/component/input_spec.rb +1 -1
  21. data/spec/punchblock/component/output_spec.rb +32 -27
  22. data/spec/punchblock/component/record_spec.rb +5 -5
  23. data/spec/punchblock/connection/asterisk_spec.rb +7 -7
  24. data/spec/punchblock/connection/freeswitch_spec.rb +8 -8
  25. data/spec/punchblock/connection/xmpp_spec.rb +9 -9
  26. data/spec/punchblock/translator/asterisk/call_spec.rb +65 -65
  27. data/spec/punchblock/translator/asterisk/component/asterisk/agi_command_spec.rb +17 -20
  28. data/spec/punchblock/translator/asterisk/component/asterisk/ami_action_spec.rb +13 -16
  29. data/spec/punchblock/translator/asterisk/component/input_spec.rb +9 -12
  30. data/spec/punchblock/translator/asterisk/component/output_spec.rb +62 -29
  31. data/spec/punchblock/translator/asterisk/component/record_spec.rb +38 -42
  32. data/spec/punchblock/translator/asterisk/component/stop_by_redirect_spec.rb +2 -2
  33. data/spec/punchblock/translator/asterisk/component_spec.rb +5 -5
  34. data/spec/punchblock/translator/asterisk_spec.rb +55 -55
  35. data/spec/punchblock/translator/freeswitch/call_spec.rb +80 -54
  36. data/spec/punchblock/translator/freeswitch/component/flite_output_spec.rb +7 -10
  37. data/spec/punchblock/translator/freeswitch/component/input_spec.rb +8 -10
  38. data/spec/punchblock/translator/freeswitch/component/output_spec.rb +9 -12
  39. data/spec/punchblock/translator/freeswitch/component/record_spec.rb +31 -34
  40. data/spec/punchblock/translator/freeswitch/component/tts_output_spec.rb +7 -10
  41. data/spec/punchblock/translator/freeswitch/component_spec.rb +6 -6
  42. data/spec/punchblock/translator/freeswitch_spec.rb +27 -27
  43. data/spec/punchblock_spec.rb +5 -6
  44. data/spec/spec_helper.rb +2 -3
  45. data/spec/support/mock_connection_with_event_handler.rb +8 -19
  46. metadata +5 -21
@@ -8,33 +8,30 @@ module Punchblock
8
8
  module Component
9
9
  module Asterisk
10
10
  describe AGICommand do
11
+ include HasMockCallbackConnection
12
+
11
13
  let(:channel) { 'SIP/foo' }
12
- let(:connection) do
13
- mock_connection_with_event_handler do |event|
14
- command.add_event event
15
- end
16
- end
17
14
  let(:translator) { Punchblock::Translator::Asterisk.new mock('AMI'), connection }
18
15
  let(:mock_call) { Punchblock::Translator::Asterisk::Call.new channel, translator }
19
16
  let(:component_id) { Punchblock.new_uuid }
20
17
 
21
18
  before { stub_uuids component_id }
22
19
 
23
- let :command do
20
+ let :original_command do
24
21
  Punchblock::Component::Asterisk::AGI::Command.new :name => 'EXEC ANSWER'
25
22
  end
26
23
 
27
- subject { AGICommand.new command, mock_call }
24
+ subject { AGICommand.new original_command, mock_call }
28
25
 
29
26
  let :expected_action do
30
27
  RubyAMI::Action.new 'AGI', 'Channel' => channel, 'Command' => 'EXEC ANSWER', 'CommandID' => component_id
31
28
  end
32
29
 
33
30
  context 'initial execution' do
34
- before { command.request! }
31
+ before { original_command.request! }
35
32
 
36
33
  it 'should send the appropriate RubyAMI::Action' do
37
- mock_call.expects(:send_ami_action).once.with(expected_action).returns(expected_action)
34
+ mock_call.should_receive(:send_ami_action).once.with(expected_action).and_return(expected_action)
38
35
  subject.execute
39
36
  end
40
37
 
@@ -45,12 +42,12 @@ module Punchblock
45
42
  RubyAMI::Action.new 'AGI', 'Channel' => channel, 'Command' => 'WAIT FOR DIGIT "1000" "foo"', 'CommandID' => component_id
46
43
  end
47
44
 
48
- let :command do
45
+ let :original_command do
49
46
  Punchblock::Component::Asterisk::AGI::Command.new :name => 'WAIT FOR DIGIT', :params => params
50
47
  end
51
48
 
52
49
  it 'should send the appropriate RubyAMI::Action' do
53
- mock_call.expects(:send_ami_action).once.with(expected_action).returns(expected_action)
50
+ mock_call.should_receive(:send_ami_action).once.with(expected_action).and_return(expected_action)
54
51
  subject.execute
55
52
  end
56
53
  end
@@ -58,8 +55,8 @@ module Punchblock
58
55
 
59
56
  context 'when the AMI action completes' do
60
57
  before do
61
- command.request!
62
- command.execute!
58
+ original_command.request!
59
+ original_command.execute!
63
60
  end
64
61
 
65
62
  let :expected_response do
@@ -69,12 +66,12 @@ module Punchblock
69
66
  let :response do
70
67
  RubyAMI::Response.new.tap do |r|
71
68
  r['ActionID'] = "552a9d9f-46d7-45d8-a257-06fe95f48d99"
72
- r['Message'] = 'Added AGI command to queue'
69
+ r['Message'] = 'Added AGI original_command to queue'
73
70
  end
74
71
  end
75
72
 
76
73
  it 'should send the component node a ref with the action ID' do
77
- command.expects(:response=).once.with(expected_response)
74
+ original_command.should_receive(:response=).once.with(expected_response)
78
75
  subject.action << response
79
76
  end
80
77
 
@@ -84,7 +81,7 @@ module Punchblock
84
81
  end
85
82
 
86
83
  it 'should send the component node false' do
87
- command.expects(:response=).once.with false
84
+ original_command.should_receive(:response=).once.with false
88
85
  subject.action << error
89
86
  end
90
87
  end
@@ -92,8 +89,8 @@ module Punchblock
92
89
 
93
90
  describe 'when receiving an AsyncAGI event' do
94
91
  before do
95
- command.request!
96
- command.execute!
92
+ original_command.request!
93
+ original_command.execute!
97
94
  end
98
95
 
99
96
  context 'of type start'
@@ -118,9 +115,9 @@ module Punchblock
118
115
  it 'should send a complete event' do
119
116
  subject.handle_ami_event ami_event
120
117
 
121
- complete_event = command.complete_event 0.5
118
+ complete_event = original_command.complete_event 0.5
122
119
 
123
- command.should be_complete
120
+ original_command.should be_complete
124
121
 
125
122
  complete_event.component_id.should be == component_id.to_s
126
123
  complete_event.reason.should be == expected_complete_reason
@@ -8,18 +8,15 @@ module Punchblock
8
8
  module Component
9
9
  module Asterisk
10
10
  describe AMIAction do
11
- let(:connection) do
12
- mock_connection_with_event_handler do |event|
13
- command.add_event event
14
- end
15
- end
11
+ include HasMockCallbackConnection
12
+
16
13
  let(:mock_translator) { Punchblock::Translator::Asterisk.new mock('AMI'), connection }
17
14
 
18
- let :command do
15
+ let :original_command do
19
16
  Punchblock::Component::Asterisk::AMI::Action.new :name => 'ExtensionStatus', :params => { :context => 'default', :exten => 'idonno' }
20
17
  end
21
18
 
22
- subject { AMIAction.new command, mock_translator }
19
+ subject { AMIAction.new original_command, mock_translator }
23
20
 
24
21
  let :expected_action do
25
22
  RubyAMI::Action.new 'ExtensionStatus', 'Context' => 'default', 'Exten' => 'idonno'
@@ -35,16 +32,16 @@ module Punchblock
35
32
  before { stub_uuids component_id }
36
33
 
37
34
  it 'should send the appropriate RubyAMI::Action and send the component node a ref with the action ID' do
38
- mock_translator.expects(:send_ami_action).once.with(expected_action).returns(expected_action)
39
- command.expects(:response=).once.with(expected_response)
35
+ mock_translator.should_receive(:send_ami_action).once.with(expected_action).and_return(expected_action)
36
+ original_command.should_receive(:response=).once.with(expected_response)
40
37
  subject.execute
41
38
  end
42
39
  end
43
40
 
44
41
  context 'when the AMI action completes' do
45
42
  before do
46
- command.request!
47
- command.execute!
43
+ original_command.request!
44
+ original_command.execute!
48
45
  end
49
46
 
50
47
  let :response do
@@ -64,13 +61,13 @@ module Punchblock
64
61
 
65
62
  context 'for a non-causal action' do
66
63
  it 'should send a complete event to the component node' do
67
- subject.wrapped_object.expects(:send_complete_event).once.with expected_complete_reason
64
+ subject.wrapped_object.should_receive(:send_complete_event).once.with expected_complete_reason
68
65
  subject.handle_response response
69
66
  end
70
67
  end
71
68
 
72
69
  context 'for a causal action' do
73
- let :command do
70
+ let :original_command do
74
71
  Punchblock::Component::Asterisk::AMI::Action.new :name => 'CoreShowChannels'
75
72
  end
76
73
 
@@ -117,7 +114,7 @@ module Punchblock
117
114
 
118
115
  it 'should send events to the component node' do
119
116
  event_node
120
- command.register_handler :internal, Punchblock::Event::Asterisk::AMI::Event do |event|
117
+ original_command.register_handler :internal, Punchblock::Event::Asterisk::AMI::Event do |event|
121
118
  @event = event
122
119
  end
123
120
  action = subject.action
@@ -131,7 +128,7 @@ module Punchblock
131
128
  subject.action << response
132
129
  subject.action << terminating_event
133
130
 
134
- command.complete_event(0.5).reason.should be == expected_complete_reason
131
+ original_command.complete_event(0.5).reason.should be == expected_complete_reason
135
132
  end
136
133
  end
137
134
 
@@ -145,7 +142,7 @@ module Punchblock
145
142
  end
146
143
 
147
144
  it 'should send a complete event to the component node' do
148
- subject.wrapped_object.expects(:send_complete_event).once.with expected_complete_reason
145
+ subject.wrapped_object.should_receive(:send_complete_event).once.with expected_complete_reason
149
146
  subject.handle_response error
150
147
  end
151
148
  end
@@ -7,11 +7,8 @@ module Punchblock
7
7
  class Asterisk
8
8
  module Component
9
9
  describe Input do
10
- let(:connection) do
11
- mock_connection_with_event_handler do |event|
12
- original_command.add_event event
13
- end
14
- end
10
+ include HasMockCallbackConnection
11
+
15
12
  let(:media_engine) { nil }
16
13
  let(:translator) { Punchblock::Translator::Asterisk.new mock('AMI'), connection, media_engine }
17
14
  let(:call) { Punchblock::Translator::Asterisk::Call.new 'foo', translator }
@@ -43,11 +40,11 @@ module Punchblock
43
40
  before { original_command.request! }
44
41
 
45
42
  it "calls send_progress on the call" do
46
- call.expects(:send_progress)
43
+ call.should_receive(:send_progress)
47
44
  subject.execute
48
45
  end
49
46
 
50
- before { call.stubs :send_progress }
47
+ before { call.stub :send_progress }
51
48
 
52
49
  let(:original_command_opts) { {} }
53
50
 
@@ -96,7 +93,7 @@ module Punchblock
96
93
  end
97
94
 
98
95
  it "should not process further dtmf events" do
99
- subject.expects(:process_dtmf!).never
96
+ subject.should_receive(:process_dtmf!).never
100
97
  send_ami_events_for_dtmf 3
101
98
  end
102
99
  end
@@ -191,7 +188,7 @@ module Punchblock
191
188
  let(:original_command_opts) { { :initial_timeout => -1 } }
192
189
 
193
190
  it "should not start a timer" do
194
- subject.wrapped_object.expects(:begin_initial_timer).never
191
+ subject.wrapped_object.should_receive(:begin_initial_timer).never
195
192
  subject.execute
196
193
  end
197
194
  end
@@ -200,7 +197,7 @@ module Punchblock
200
197
  let(:original_command_opts) { { :initial_timeout => nil } }
201
198
 
202
199
  it "should not start a timer" do
203
- subject.wrapped_object.expects(:begin_initial_timer).never
200
+ subject.wrapped_object.should_receive(:begin_initial_timer).never
204
201
  subject.execute
205
202
  end
206
203
  end
@@ -243,7 +240,7 @@ module Punchblock
243
240
  let(:original_command_opts) { { :inter_digit_timeout => -1 } }
244
241
 
245
242
  it "should not start a timer" do
246
- subject.wrapped_object.expects(:begin_inter_digit_timer).never
243
+ subject.wrapped_object.should_receive(:begin_inter_digit_timer).never
247
244
  subject.execute
248
245
  end
249
246
  end
@@ -252,7 +249,7 @@ module Punchblock
252
249
  let(:original_command_opts) { { :inter_digit_timeout => nil } }
253
250
 
254
251
  it "should not start a timer" do
255
- subject.wrapped_object.expects(:begin_inter_digit_timer).never
252
+ subject.wrapped_object.should_receive(:begin_inter_digit_timer).never
256
253
  subject.execute
257
254
  end
258
255
  end
@@ -7,11 +7,8 @@ module Punchblock
7
7
  class Asterisk
8
8
  module Component
9
9
  describe Output do
10
- let(:connection) do
11
- mock_connection_with_event_handler do |event|
12
- original_command.add_event event
13
- end
14
- end
10
+ include HasMockCallbackConnection
11
+
15
12
  let(:media_engine) { nil }
16
13
  let(:translator) { Punchblock::Translator::Asterisk.new mock('AMI'), connection, media_engine }
17
14
  let(:mock_call) { Punchblock::Translator::Asterisk::Call.new 'foo', translator }
@@ -33,14 +30,24 @@ module Punchblock
33
30
  subject { Output.new original_command, mock_call }
34
31
 
35
32
  def expect_answered(value = true)
36
- mock_call.expects(:answered?).returns(value).at_least_once
33
+ mock_call.should_receive(:answered?).at_least(:once).and_return(value)
37
34
  end
38
35
 
39
36
  describe '#execute' do
40
37
  before { original_command.request! }
41
38
 
39
+ context 'with an invalid media engine' do
40
+ let(:media_engine) { 'foobar' }
41
+
42
+ it "should return an error and not execute any actions" do
43
+ subject.execute
44
+ error = ProtocolError.new.setup 'option error', 'The renderer foobar is unsupported.'
45
+ original_command.response(0.1).should be == error
46
+ end
47
+ end
48
+
42
49
  context 'with a media engine of :swift' do
43
- let(:media_engine) { :swift }
50
+ let(:media_engine) { 'swift' }
44
51
 
45
52
  let(:audio_filename) { 'http://foo.com/bar.mp3' }
46
53
 
@@ -63,7 +70,7 @@ module Punchblock
63
70
  end
64
71
 
65
72
  it "should execute Swift" do
66
- mock_call.expects(:send_agi_action!).once.with 'EXEC Swift', ssml_with_options
73
+ mock_call.should_receive(:send_agi_action!).once.with 'EXEC Swift', ssml_with_options
67
74
  subject.execute
68
75
  end
69
76
 
@@ -79,7 +86,7 @@ module Punchblock
79
86
  context "set to nil" do
80
87
  let(:command_opts) { { :interrupt_on => nil } }
81
88
  it "should not add interrupt arguments" do
82
- mock_call.expects(:send_agi_action!).once.with 'EXEC Swift', ssml_with_options
89
+ mock_call.should_receive(:send_agi_action!).once.with 'EXEC Swift', ssml_with_options
83
90
  subject.execute
84
91
  end
85
92
  end
@@ -88,7 +95,7 @@ module Punchblock
88
95
  let(:command_opts) { { :interrupt_on => :any } }
89
96
  it "should add the interrupt options to the argument" do
90
97
  expect_answered
91
- mock_call.expects(:send_agi_action!).once.with 'EXEC Swift', ssml_with_options('', '|1|1')
98
+ mock_call.should_receive(:send_agi_action!).once.with 'EXEC Swift', ssml_with_options('', '|1|1')
92
99
  subject.execute
93
100
  end
94
101
  end
@@ -97,7 +104,7 @@ module Punchblock
97
104
  let(:command_opts) { { :interrupt_on => :dtmf } }
98
105
  it "should add the interrupt options to the argument" do
99
106
  expect_answered
100
- mock_call.expects(:send_agi_action!).once.with 'EXEC Swift', ssml_with_options('', '|1|1')
107
+ mock_call.should_receive(:send_agi_action!).once.with 'EXEC Swift', ssml_with_options('', '|1|1')
101
108
  subject.execute
102
109
  end
103
110
  end
@@ -116,7 +123,7 @@ module Punchblock
116
123
  context "set to nil" do
117
124
  let(:command_opts) { { :voice => nil } }
118
125
  it "should not add a voice at the beginning of the argument" do
119
- mock_call.expects(:send_agi_action!).once.with 'EXEC Swift', ssml_with_options
126
+ mock_call.should_receive(:send_agi_action!).once.with 'EXEC Swift', ssml_with_options
120
127
  subject.execute
121
128
  end
122
129
  end
@@ -124,7 +131,7 @@ module Punchblock
124
131
  context "set to Leonard" do
125
132
  let(:command_opts) { { :voice => "Leonard" } }
126
133
  it "should add a voice at the beginning of the argument" do
127
- mock_call.expects(:send_agi_action!).once.with 'EXEC Swift', ssml_with_options('Leonard^', '')
134
+ mock_call.should_receive(:send_agi_action!).once.with 'EXEC Swift', ssml_with_options('Leonard^', '')
128
135
  subject.execute
129
136
  end
130
137
  end
@@ -151,14 +158,14 @@ module Punchblock
151
158
  end
152
159
 
153
160
  def expect_mrcpsynth_with_options(options)
154
- mock_call.expects(:send_agi_action!).once.with do |*args|
161
+ mock_call.should_receive(:send_agi_action!).once.with do |*args|
155
162
  args[0].should be == 'EXEC MRCPSynth'
156
163
  args[2].should match options
157
164
  end
158
165
  end
159
166
 
160
167
  it "should execute MRCPSynth" do
161
- mock_call.expects(:send_agi_action!).once.with 'EXEC MRCPSynth', ssml_doc.to_s.squish.gsub(/["\\]/) { |m| "\\#{m}" }, ''
168
+ mock_call.should_receive(:send_agi_action!).once.with 'EXEC MRCPSynth', ssml_doc.to_s.squish.gsub(/["\\]/) { |m| "\\#{m}" }, ''
162
169
  subject.execute
163
170
  end
164
171
 
@@ -170,7 +177,7 @@ module Punchblock
170
177
  end
171
178
 
172
179
  it 'should escape TTS strings containing a comma' do
173
- mock_call.expects(:send_agi_action!).once.with do |*args|
180
+ mock_call.should_receive(:send_agi_action!).once.with do |*args|
174
181
  args[0].should be == 'EXEC MRCPSynth'
175
182
  args[1].should match(/this\\, here\\, is a test/)
176
183
  end
@@ -352,11 +359,11 @@ module Punchblock
352
359
  let(:media_engine) { :asterisk }
353
360
 
354
361
  def expect_playback(filename = audio_filename)
355
- mock_call.expects(:send_agi_action!).once.with 'EXEC Playback', filename
362
+ mock_call.should_receive(:send_agi_action!).once.with 'EXEC Playback', filename
356
363
  end
357
364
 
358
365
  def expect_playback_noanswer
359
- mock_call.expects(:send_agi_action!).once.with 'EXEC Playback', audio_filename + ',noanswer'
366
+ mock_call.should_receive(:send_agi_action!).once.with 'EXEC Playback', audio_filename + ',noanswer'
360
367
  end
361
368
 
362
369
  let(:audio_filename) { 'http://foo.com/bar.mp3' }
@@ -440,7 +447,7 @@ module Punchblock
440
447
  it "should play the file with Playback" do
441
448
  expect_answered false
442
449
  expect_playback_noanswer
443
- mock_call.expects(:send_progress)
450
+ mock_call.should_receive(:send_progress)
444
451
  subject.execute
445
452
  end
446
453
 
@@ -501,7 +508,7 @@ module Punchblock
501
508
  block.call Punchblock::Component::Asterisk::AGI::Command::Complete::Success.new(:code => 200, :result => 1)
502
509
  end
503
510
  latch = CountDownLatch.new 1
504
- original_command.expects(:add_event).once.with do |e|
511
+ original_command.should_receive(:add_event).once.with do |e|
505
512
  e.reason.should be_a Punchblock::Component::Output::Complete::Success
506
513
  latch.countdown!
507
514
  end
@@ -676,7 +683,7 @@ module Punchblock
676
683
  it "does not redirect the call" do
677
684
  expect_answered
678
685
  expect_playback
679
- mock_call.expects(:redirect_back!).never
686
+ mock_call.should_receive(:redirect_back!).never
680
687
  subject.execute
681
688
  original_command.response(0.1).should be_a Ref
682
689
  send_ami_events_for_dtmf 1
@@ -693,7 +700,7 @@ module Punchblock
693
700
 
694
701
  context "when a DTMF digit is received" do
695
702
  it "sends the correct complete event" do
696
- mock_call.expects :redirect_back!
703
+ mock_call.should_receive :redirect_back!
697
704
  subject.execute
698
705
  original_command.response(0.1).should be_a Ref
699
706
  original_command.should_not be_complete
@@ -705,7 +712,7 @@ module Punchblock
705
712
  end
706
713
 
707
714
  it "redirects the call back to async AGI" do
708
- mock_call.expects(:redirect_back!).with(nil).once
715
+ mock_call.should_receive(:redirect_back!).once
709
716
  subject.execute
710
717
  original_command.response(0.1).should be_a Ref
711
718
  send_ami_events_for_dtmf 1
@@ -723,7 +730,7 @@ module Punchblock
723
730
 
724
731
  context "when a DTMF digit is received" do
725
732
  it "sends the correct complete event" do
726
- mock_call.expects :redirect_back!
733
+ mock_call.should_receive :redirect_back!
727
734
  subject.execute
728
735
  original_command.response(0.1).should be_a Ref
729
736
  original_command.should_not be_complete
@@ -735,7 +742,7 @@ module Punchblock
735
742
  end
736
743
 
737
744
  it "redirects the call back to async AGI" do
738
- mock_call.expects(:redirect_back!).with(nil).once
745
+ mock_call.should_receive(:redirect_back!).once
739
746
  subject.execute
740
747
  original_command.response(0.1).should be_a Ref
741
748
  send_ami_events_for_dtmf 1
@@ -753,6 +760,32 @@ module Punchblock
753
760
  end
754
761
  end
755
762
  end
763
+
764
+ context "with a media renderer set on itself" do
765
+ let(:media_engine) { :swift }
766
+ let(:audio_filename) { '/foo/bar.wav' }
767
+ let :ssml_doc do
768
+ RubySpeech::SSML.draw do
769
+ audio :src => audio_filename
770
+ end
771
+ end
772
+
773
+ let(:command_opts) { {:renderer => :asterisk} }
774
+
775
+ let :command_options do
776
+ { :ssml => ssml_doc }.merge(command_opts)
777
+ end
778
+
779
+ let :original_command do
780
+ Punchblock::Component::Output.new command_options
781
+ end
782
+
783
+ it "should use the media renderer set and not the platform default" do
784
+ expect_answered
785
+ mock_call.should_receive(:send_agi_action!).once.with 'EXEC Playback', audio_filename
786
+ subject.execute
787
+ end
788
+ end
756
789
  end
757
790
 
758
791
  describe "#execute_command" do
@@ -785,22 +818,22 @@ module Punchblock
785
818
  end
786
819
 
787
820
  it "sets the command response to true" do
788
- mock_call.expects(:redirect_back!)
821
+ mock_call.should_receive(:redirect_back!)
789
822
  subject.execute_command command
790
823
  command.response(0.1).should be == true
791
824
  end
792
825
 
793
826
  it "sends the correct complete event" do
794
- mock_call.expects(:redirect_back!)
827
+ mock_call.should_receive(:redirect_back!)
795
828
  subject.execute_command command
796
829
  original_command.should_not be_complete
797
- mock_call.process_ami_event! ami_event
830
+ mock_call.process_ami_event ami_event
798
831
  reason.should be_a Punchblock::Event::Complete::Stop
799
832
  original_command.should be_complete
800
833
  end
801
834
 
802
835
  it "redirects the call by unjoining it" do
803
- mock_call.expects(:redirect_back!).with(nil)
836
+ mock_call.should_receive(:redirect_back!)
804
837
  subject.execute_command command
805
838
  end
806
839
  end