Ruby4Skype 0.2.3 → 0.3.1
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.
- data/LICENSE +3 -0
- data/README +14 -0
- data/Rakefile +67 -0
- data/lib/skypeapi.rb +570 -509
- data/lib/skypeapi/application.rb +79 -77
- data/lib/skypeapi/call.rb +243 -230
- data/lib/skypeapi/chat.rb +162 -172
- data/lib/skypeapi/chatmember.rb +26 -28
- data/lib/skypeapi/chatmessage.rb +81 -65
- data/lib/skypeapi/error.rb +8 -0
- data/lib/skypeapi/event.rb +25 -26
- data/lib/skypeapi/filetransfer.rb +47 -28
- data/lib/skypeapi/group.rb +72 -73
- data/lib/skypeapi/menuitem.rb +44 -44
- data/lib/skypeapi/message.rb +39 -41
- data/lib/skypeapi/object.rb +246 -82
- data/lib/skypeapi/os/etc.rb +48 -98
- data/lib/skypeapi/os/mac.rb +92 -4
- data/lib/skypeapi/os/notifier.rb +31 -0
- data/lib/skypeapi/os/window_event_queue.rb +198 -0
- data/lib/skypeapi/os/window_messagehandler.rb +120 -0
- data/lib/skypeapi/os/windows.rb +170 -306
- data/lib/skypeapi/profile.rb +190 -120
- data/lib/skypeapi/sharefunctions.rb +31 -23
- data/lib/skypeapi/sms.rb +87 -67
- data/lib/skypeapi/user.rb +159 -99
- data/lib/skypeapi/version.rb +3 -3
- data/lib/skypeapi/voicemail.rb +59 -52
- data/spec/matcher_be_boolean.rb +10 -0
- data/spec/skypeapi/application_spec.rb +76 -0
- data/spec/skypeapi/chat_spec.rb +356 -0
- data/spec/skypeapi/chatmember_spec.rb +42 -0
- data/spec/skypeapi/chatmessage_spec.rb +89 -0
- data/spec/skypeapi/event_spec.rb +31 -0
- data/spec/skypeapi/filetransfer_spec.rb +67 -0
- data/spec/skypeapi/group_spec.rb +16 -0
- data/spec/skypeapi/menuitem_spec.rb +37 -0
- data/spec/skypeapi/os/windows_spec.rb +305 -0
- data/spec/skypeapi/profile_spec.rb +22 -0
- data/spec/skypeapi/user_spec.rb +25 -0
- data/spec/skypeapi_spec.rb +528 -0
- metadata +32 -12
- data/lib/skypeapi/os/timer.rb +0 -108
data/lib/skypeapi/os/mac.rb
CHANGED
@@ -1,10 +1,98 @@
|
|
1
|
+
require 'osx/cocoa'
|
2
|
+
OSX.require_framework 'Skype'
|
3
|
+
|
1
4
|
module SkypeAPI
|
2
5
|
module OS
|
3
6
|
class Mac
|
4
|
-
|
5
|
-
|
6
|
-
|
7
|
+
class Server < OSX::NSObject
|
8
|
+
def clientApplicationName
|
9
|
+
@client_application_name
|
10
|
+
end
|
11
|
+
|
12
|
+
addRubyMethod_withType 'skypeAttachResponse:', 'v@:i'
|
13
|
+
def skypeAttachResponse status
|
14
|
+
p [:skypeAttachResponse,status]
|
15
|
+
case status
|
16
|
+
when 0 #?
|
17
|
+
when 1 #sccess
|
18
|
+
@upper.attached = true
|
19
|
+
when 2 ####
|
20
|
+
end
|
21
|
+
end
|
22
|
+
|
23
|
+
#addRubyMethod_withType 'skypeBecameAviable:', 'v@:@'
|
24
|
+
def skypeBecameAvilable notification
|
25
|
+
p [:skypeBecameAvilable,notification]
|
26
|
+
end
|
27
|
+
|
28
|
+
#addRubyMethod_withType 'skypeBecameUnavialbe:', 'v@:@'
|
29
|
+
def skypeBecameUnavilable notification
|
30
|
+
p [:skypeBecameUnavilable,notification]
|
31
|
+
end
|
32
|
+
|
33
|
+
#addRubyMethod_withType 'skypeAttachResponse:', 'v@:@'
|
34
|
+
def skypeNotificationReceived notifation_string
|
35
|
+
p [:skypeNotificationReceived,notifation_string]
|
36
|
+
end
|
7
37
|
end
|
38
|
+
|
39
|
+
def initialize client_application_name='ruby4skype'
|
40
|
+
raise Skype::Error::NotImplement
|
41
|
+
|
42
|
+
@server = Server.alloc.init
|
43
|
+
@server.instance_variable_set :@upper, self
|
44
|
+
@server.instance_variable_set :@client_application_name, @client_application_name
|
45
|
+
OSX::SkypeAPI.setSkypeDelegate @server
|
46
|
+
|
47
|
+
@notify = Hash.new
|
48
|
+
@event = Hash.new do |h,k|
|
49
|
+
h[k] = Array.new
|
50
|
+
end
|
51
|
+
|
52
|
+
@attached = false
|
53
|
+
Thread.new do
|
54
|
+
OSX::NSRunLoop.currentRunLoop.run
|
55
|
+
end
|
56
|
+
end
|
57
|
+
|
58
|
+
attr_reader :attached
|
59
|
+
|
60
|
+
def attach
|
61
|
+
OSX::SkypeAPI.connect
|
62
|
+
end
|
63
|
+
|
64
|
+
def attach_wait
|
65
|
+
self.attach
|
66
|
+
loop do
|
67
|
+
break if @attached
|
68
|
+
sleep 0.123
|
69
|
+
end
|
70
|
+
end
|
71
|
+
|
72
|
+
def dettach
|
73
|
+
OSX::SkypeAPI.disconnect
|
74
|
+
end
|
75
|
+
|
76
|
+
def skype_runnging?
|
77
|
+
OSX::SkypeAPI.isSkypeRunnging
|
78
|
+
end
|
79
|
+
|
80
|
+
def invoke_prototype cmd
|
81
|
+
res = OSX::SkypeAPI.sendSkypeCommand(cmd)
|
82
|
+
@queue.push(proc{do_event(:sent, cmd)}) if exist_event? :sent
|
83
|
+
@queue.push(proc{do_event(:received, res)}) if exist_event? :received
|
84
|
+
return res
|
85
|
+
end
|
86
|
+
|
87
|
+
def invoke_callback cmd,cb=Proc.new
|
88
|
+
res = invoke_prototype cmd
|
89
|
+
cb.call res
|
90
|
+
end
|
91
|
+
|
92
|
+
def invoke_block cmd, waitLimit = WAIT_CMD_LIMIT
|
93
|
+
res = invoke_prototype cmd
|
94
|
+
end
|
95
|
+
|
8
96
|
end
|
9
97
|
end
|
10
|
-
end
|
98
|
+
end
|
@@ -0,0 +1,31 @@
|
|
1
|
+
module SkypeAPI
|
2
|
+
module OS
|
3
|
+
class Notifier
|
4
|
+
def notify
|
5
|
+
@notify ||= Hash.new
|
6
|
+
end
|
7
|
+
|
8
|
+
def add reg, block=Proc.new
|
9
|
+
notify[reg] = block
|
10
|
+
end
|
11
|
+
|
12
|
+
def del reg
|
13
|
+
notify.delete reg
|
14
|
+
end
|
15
|
+
|
16
|
+
def fire res
|
17
|
+
objects_notify_fire = false
|
18
|
+
notify.each do |reg, action|
|
19
|
+
if res =~ reg
|
20
|
+
action.call($1)
|
21
|
+
objects_notify_fire = true
|
22
|
+
end
|
23
|
+
end
|
24
|
+
|
25
|
+
unless objects_notify_fire
|
26
|
+
notify[nil].call(res) if notify[nil]
|
27
|
+
end
|
28
|
+
end
|
29
|
+
end
|
30
|
+
end
|
31
|
+
end
|
@@ -0,0 +1,198 @@
|
|
1
|
+
require 'thread'
|
2
|
+
|
3
|
+
class BlockQueue < Queue #:nodoc: all
|
4
|
+
def push_block block=Proc.new
|
5
|
+
push block
|
6
|
+
end
|
7
|
+
end
|
8
|
+
|
9
|
+
module SkypeAPI
|
10
|
+
module OS
|
11
|
+
class WindowsEventQueue
|
12
|
+
def initialize windows
|
13
|
+
@windows = windows
|
14
|
+
@pause_count = 0
|
15
|
+
@pause_mutex = Mutex.new
|
16
|
+
end
|
17
|
+
|
18
|
+
attr_reader :windows
|
19
|
+
|
20
|
+
def queue
|
21
|
+
@queue ||= BlockQueue.new
|
22
|
+
end
|
23
|
+
|
24
|
+
def length
|
25
|
+
@queue.length
|
26
|
+
end
|
27
|
+
|
28
|
+
def received_count
|
29
|
+
@received_count ||= 0
|
30
|
+
end
|
31
|
+
attr_writer :received_count
|
32
|
+
private :received_count=
|
33
|
+
|
34
|
+
def callback
|
35
|
+
@callback ||= Hash.new
|
36
|
+
end
|
37
|
+
|
38
|
+
def set_notify_selector block=Proc.new
|
39
|
+
@notify_selector = block
|
40
|
+
end
|
41
|
+
|
42
|
+
attr_reader :notify_selector
|
43
|
+
|
44
|
+
def hook
|
45
|
+
@hook ||= Hash.new do |h,k|
|
46
|
+
h[k] = Array.new
|
47
|
+
end
|
48
|
+
end
|
49
|
+
|
50
|
+
private :queue, :hook, :windows
|
51
|
+
|
52
|
+
def add_hook sym, block=Proc.new
|
53
|
+
hook[sym].push block
|
54
|
+
end
|
55
|
+
|
56
|
+
def del_hook sym, block=nil
|
57
|
+
unless block
|
58
|
+
hook[sym] = Array.new
|
59
|
+
else
|
60
|
+
hook[sym].delete block
|
61
|
+
end
|
62
|
+
end
|
63
|
+
|
64
|
+
def exist_hook? sym
|
65
|
+
if hook[sym].length > 0
|
66
|
+
return true
|
67
|
+
else
|
68
|
+
return false
|
69
|
+
end
|
70
|
+
end
|
71
|
+
|
72
|
+
def get_hook sym
|
73
|
+
hook[sym] ? true : false
|
74
|
+
end
|
75
|
+
|
76
|
+
def push response
|
77
|
+
self.received_count += 1
|
78
|
+
response = response.chop
|
79
|
+
push_received_hook(response)
|
80
|
+
|
81
|
+
cmd_num, res = response_match(response)
|
82
|
+
if cmd_num
|
83
|
+
@windows.wmHandler.del_send_buffer cmd_num.to_i
|
84
|
+
set_cmd_response(cmd_num, res)
|
85
|
+
else
|
86
|
+
when_detached if response_detached?(res)
|
87
|
+
push_notify res
|
88
|
+
end
|
89
|
+
end
|
90
|
+
|
91
|
+
def push_hook sym, *args
|
92
|
+
queue.push_block{ call_hook(sym, *args) }
|
93
|
+
end
|
94
|
+
|
95
|
+
def push_block block=Proc.new
|
96
|
+
queue.push block
|
97
|
+
end
|
98
|
+
|
99
|
+
def start_messageloop
|
100
|
+
@messageloop_thread = Thread.new{messageloop}
|
101
|
+
end
|
102
|
+
|
103
|
+
def messageloop
|
104
|
+
@messageloop_flag = true
|
105
|
+
while callback = queue.shift
|
106
|
+
sleep 0.001 while paused?
|
107
|
+
break if callback == :exit
|
108
|
+
callback.call
|
109
|
+
end
|
110
|
+
@messageloop_flag = false
|
111
|
+
end
|
112
|
+
|
113
|
+
def messagepolling
|
114
|
+
until queue.empty?
|
115
|
+
sleep 0.001 while paused?
|
116
|
+
callback = queue.shift
|
117
|
+
break if callback == :exit
|
118
|
+
callback.call
|
119
|
+
end
|
120
|
+
end
|
121
|
+
|
122
|
+
def close
|
123
|
+
queue.clear
|
124
|
+
queue.push :exit
|
125
|
+
end
|
126
|
+
|
127
|
+
def paused?
|
128
|
+
@pause_count > 0
|
129
|
+
end
|
130
|
+
|
131
|
+
def pause &block
|
132
|
+
if block
|
133
|
+
_pause
|
134
|
+
block.call
|
135
|
+
play
|
136
|
+
else
|
137
|
+
_pause
|
138
|
+
end
|
139
|
+
end
|
140
|
+
|
141
|
+
def _pause
|
142
|
+
@pause_mutex.synchronized{@pause_count += 1}
|
143
|
+
end
|
144
|
+
|
145
|
+
def paly
|
146
|
+
@pause_mutex.synchronized{@pause_count -=1}
|
147
|
+
end
|
148
|
+
|
149
|
+
def push_detached_hook
|
150
|
+
#windows.attached = false
|
151
|
+
queue.push_block{ call_hook(:detached) }
|
152
|
+
#SkypeAPI.attach
|
153
|
+
end
|
154
|
+
|
155
|
+
private
|
156
|
+
|
157
|
+
def push_received_hook(response)
|
158
|
+
queue.push_block{ call_hook(:received, response) }
|
159
|
+
end
|
160
|
+
|
161
|
+
def response_match(res)
|
162
|
+
res =~ /^(#(\d+?) )?(.+?)$/m
|
163
|
+
return [$2, $3]
|
164
|
+
end
|
165
|
+
|
166
|
+
def when_detached
|
167
|
+
windows.attached = false
|
168
|
+
queue.push_block{ call_hook(:detached) }
|
169
|
+
SkypeAPI.attach
|
170
|
+
end
|
171
|
+
|
172
|
+
def set_cmd_response(cmd_num, res)
|
173
|
+
cmd_num = cmd_num.to_i
|
174
|
+
if callback[cmd_num]
|
175
|
+
cb = callback[cmd_num]
|
176
|
+
callback.delete(cmd_num)
|
177
|
+
#@windows.invoke_callback_mutex.synchronize do
|
178
|
+
cb.call(res)
|
179
|
+
@windows.cv.broadcast
|
180
|
+
#end
|
181
|
+
end
|
182
|
+
end
|
183
|
+
|
184
|
+
def response_detached? res
|
185
|
+
res == 'CONNSTATUS LOGGEDOUT'
|
186
|
+
end
|
187
|
+
|
188
|
+
def push_notify res
|
189
|
+
queue.push_block{notify_selector.call res} if notify_selector
|
190
|
+
end
|
191
|
+
|
192
|
+
def call_hook sym, *args
|
193
|
+
hook[sym].each{ |h| h.call *args }
|
194
|
+
end
|
195
|
+
|
196
|
+
end
|
197
|
+
end
|
198
|
+
end
|
@@ -0,0 +1,120 @@
|
|
1
|
+
module SkypeAPI
|
2
|
+
module OS
|
3
|
+
class MessageHandler < SWin::Window
|
4
|
+
|
5
|
+
def init skypeAPI, queue
|
6
|
+
@skypeAPI = skypeAPI
|
7
|
+
@queue = queue
|
8
|
+
|
9
|
+
@dwDiscoverMsg = RegisterWindowMessage.call("SkypeControlAPIDiscover");
|
10
|
+
raise SkypeAPI::Error::Attach.new("SkypeControlAPIDiscover nothing") unless @dwDiscoverMsg
|
11
|
+
|
12
|
+
@dwAttachMsg = RegisterWindowMessage.call("SkypeControlAPIAttach")
|
13
|
+
raise SkypeAPI::Error::Attach.new("SkypeControlAPIAttach nothing") unless @dwAttachMsg
|
14
|
+
|
15
|
+
addEvent(WM_COPYDATA)
|
16
|
+
addEvent(WM_USER_MSG)
|
17
|
+
addEvent @dwAttachMsg
|
18
|
+
|
19
|
+
create unless alive?
|
20
|
+
end
|
21
|
+
|
22
|
+
def attach
|
23
|
+
unless PostMessage.call(HWND_BROADCAST, @dwDiscoverMsg, hWnd, 0)
|
24
|
+
raise SkypeAPI::Error::Attach.new("SkypeControlAPIDiscover broadcast failure")
|
25
|
+
end
|
26
|
+
return true
|
27
|
+
end
|
28
|
+
|
29
|
+
def send_buffer
|
30
|
+
@send_buffer ||= Hash.new
|
31
|
+
end
|
32
|
+
|
33
|
+
def del_send_buffer num
|
34
|
+
@send_buffer.delete num
|
35
|
+
end
|
36
|
+
|
37
|
+
def invoke num, cmd
|
38
|
+
unless @hSkypeAPIWindowHandle
|
39
|
+
raise SkypeAPI::Error::Attach.new("NullPointerException SendSkype!")
|
40
|
+
return false
|
41
|
+
end
|
42
|
+
|
43
|
+
cmd = '#' + num.to_s + ' ' + cmd + "\0"
|
44
|
+
pCopyData = application.arg2cstructStr("LLS",0,cmd.length+1,cmd)
|
45
|
+
send_buffer[num] = cmd
|
46
|
+
unless PostMessage.call(hWnd, WM_USER_MSG, @hSkypeAPIWindowHandle, pCopyData)
|
47
|
+
@hSkypeAPIWindowHandle = nil
|
48
|
+
raise SkypeAPI::Error::Attach.new("Skype not ready")
|
49
|
+
end
|
50
|
+
@queue.push_hook(:sent, cmd.chop) if @queue.exist_hook? :sent
|
51
|
+
return true
|
52
|
+
end
|
53
|
+
|
54
|
+
def msghandler(sMsg)
|
55
|
+
case sMsg.msg
|
56
|
+
when @dwAttachMsg
|
57
|
+
case sMsg.lParam
|
58
|
+
when SKYPECONTROLAPI_ATTACH_SUCCESS
|
59
|
+
@hSkypeAPIWindowHandle = sMsg.wParam
|
60
|
+
invoke_protocol
|
61
|
+
@queue.push_hook(:attach,:success)
|
62
|
+
|
63
|
+
unless @skypeAPI.attached
|
64
|
+
if @skypeAPI.first_attached
|
65
|
+
@queue.push_hook(:attached)
|
66
|
+
else
|
67
|
+
@queue.push_hook(:reattached)
|
68
|
+
end
|
69
|
+
end
|
70
|
+
|
71
|
+
@skypeAPI.attached = true
|
72
|
+
@skypeAPI.first_attached = false
|
73
|
+
when SKYPECONTROLAPI_ATTACH_PENDING_AUTHORIZATION
|
74
|
+
@queue.push_hook(:attach,:authorize)
|
75
|
+
@queue.push_hook(:authorize)
|
76
|
+
when SKYPECONTROLAPI_ATTACH_REFUSED
|
77
|
+
@queue.push_hook(:attach,:refused)
|
78
|
+
@queue.push_hook(:refused)
|
79
|
+
@skypeAPI.attached = false
|
80
|
+
when SKYPECONTROLAPI_ATTACH_NOT_AVAILABLE
|
81
|
+
@queue.push_hook(:attach, :not_available)
|
82
|
+
@queue.push_hook(:not_available)
|
83
|
+
@skypeAPI.attached = false
|
84
|
+
when SKYPECONTROLAPI_ATTACH_API_AVAILABLE
|
85
|
+
@queue.push_hook(:attach, :available)
|
86
|
+
@queue.push_hook(:available)
|
87
|
+
else
|
88
|
+
@queue.push_hook(:attach,:unkown)
|
89
|
+
@queue.push_hook(:unkown)
|
90
|
+
end
|
91
|
+
sMsg.retval = 1
|
92
|
+
when WM_COPYDATA
|
93
|
+
if sMsg.wParam == @hSkypeAPIWindowHandle
|
94
|
+
retval = application.cstruct2array(sMsg.lParam,"LLL")
|
95
|
+
cmd = application.pointer2string(retval[2],retval[1])
|
96
|
+
@queue.push cmd
|
97
|
+
sMsg.retval = 1
|
98
|
+
end
|
99
|
+
when WM_USER_MSG
|
100
|
+
unless SendMessage.call(sMsg.wParam, WM_COPYDATA, sMsg.hWnd, sMsg.lParam)
|
101
|
+
raise SkypeAPI::Error::Attach.new("Skype not ready")
|
102
|
+
end
|
103
|
+
sMsg.retval = 1
|
104
|
+
else
|
105
|
+
super
|
106
|
+
end
|
107
|
+
end
|
108
|
+
|
109
|
+
def invoke_protocol
|
110
|
+
#@queue.push Proc.new{@skypeAPI.invoke_callback("PROTOCOL 9999"){}}
|
111
|
+
#@queue.push_block{@skypeAPI.invoke_callback("PROTOCOL 9999"){}}
|
112
|
+
@skypeAPI.__send__ :invoke_callback, "PROTOCOL 9999", Proc.new{}
|
113
|
+
#@queue.push_block{@skypeAPI.invoke_block("PROTOCOL 9999")}
|
114
|
+
#@skypeAPI.invoke_block("PROTOCOL 9999")
|
115
|
+
end
|
116
|
+
private :invoke_protocol
|
117
|
+
end
|
118
|
+
|
119
|
+
end
|
120
|
+
end
|