alexa_remotectl 0.4.1 → 0.4.4
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.
- checksums.yaml +4 -4
- checksums.yaml.gz.sig +4 -2
- data/lib/alexa_remotectl.rb +101 -39
- data.tar.gz.sig +0 -0
- metadata +2 -2
- metadata.gz.sig +0 -0
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: ee085eb3e18299edb7c08f01ca1eac8f90ca30f6cc125b64deb18ff9af848662
|
4
|
+
data.tar.gz: 48225e18ed743504662f52f6abd3ba17bad63fa3035bfb04a29a85b1d176a0a4
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: efbd977b60c72d374cb8b3f7864030dc772fbd1fb6369e3a5ee74f1dc7ba41276c2df2b2640b983deccad8273a8a1cf6ca26237a60b72fc59e61cb489bac5a42
|
7
|
+
data.tar.gz: 2e40d366bb49d53f9808117034cfa87c276d4ddb212ee321320ce9f9dc7ead6a50db66e3f88b341a505ad322e0aee045f6a495162508fd105d79bfd37b4d9b33
|
checksums.yaml.gz.sig
CHANGED
@@ -1,2 +1,4 @@
|
|
1
|
-
|
2
|
-
|
1
|
+
�����$�
|
2
|
+
�������� �" �,���i��&��E��'q>��2�rZ]l�FB(��?_I�퓾N����*��M���|�[��8^����G�d��^j��R�qW�7ܸ�_p�
|
3
|
+
U-3YԤ�57�C��H�S߭
|
4
|
+
�'���.D�Q)Sզ\��<�N���f���4rϼ.՛,���u;<I�\�T�V���F��8�s�F}j��a�u���قU>��co�)��J�pc����������kd̜|)��s9픃4*O�gC��SM���F;<f8�go��L`�}�i=���A&5�L�ӭ������C��)���:4�3?Z���� J�;�!k�!���B���3�1���z�МԪ�##��A�0�2Y
|
data/lib/alexa_remotectl.rb
CHANGED
@@ -13,7 +13,7 @@ require 'json'
|
|
13
13
|
# Use the CodeWizard with the cURL command you've copied using Developer
|
14
14
|
# tools on Alexa's SPA page (within the web browser).
|
15
15
|
#
|
16
|
-
# note: to find the correct url to convert, try
|
16
|
+
# note: to find the correct url to convert, try clicking on pause or play to
|
17
17
|
# invoke an AJAX request
|
18
18
|
|
19
19
|
class CodeWizard
|
@@ -22,14 +22,15 @@ class CodeWizard
|
|
22
22
|
|
23
23
|
return 'no curl command found' unless s =~ /curl/
|
24
24
|
|
25
|
-
cookie, serialno, type = parse(s)
|
25
|
+
cookie, csrf, serialno, type = parse(s)
|
26
26
|
|
27
27
|
@s =<<EOF
|
28
28
|
require 'alexa_remotectl'
|
29
29
|
|
30
30
|
cookie = '#{cookie}'
|
31
|
+
csrf = '#{csrf}'
|
31
32
|
device = {serialno: '#{serialno}', type: '#{type}'}
|
32
|
-
alexa = AlexaRemoteCtl.new(cookie: cookie, device: device)
|
33
|
+
alexa = AlexaRemoteCtl.new(cookie: cookie, csrf: csrf, device: device)
|
33
34
|
alexa.pause
|
34
35
|
#alexa.play
|
35
36
|
EOF
|
@@ -50,18 +51,37 @@ EOF
|
|
50
51
|
serialno = s[/deviceSerialNumber=(\w+)/,1]
|
51
52
|
type = s[/deviceType=(\w+)/,1]
|
52
53
|
cookie = s[/Cookie: ([^']+)/,1]
|
54
|
+
csrf = s[/csrf: ([^']+)/,1]
|
53
55
|
|
54
|
-
[cookie, serialno, type]
|
56
|
+
[cookie, csrf, serialno, type]
|
55
57
|
|
56
58
|
end
|
57
59
|
end
|
58
60
|
|
59
61
|
class AlexaRemoteCtl
|
60
62
|
|
63
|
+
# note: Added the Cross-site request forgery (crsf) variable
|
64
|
+
#
|
61
65
|
def initialize(domain: 'alexa.amazon.co.uk', device: {}, cookie: '',
|
62
|
-
|
66
|
+
customerid: '', csrf: '')
|
63
67
|
|
64
68
|
@domain, @device, @cookie, @customerid = domain, device, cookie, customerid
|
69
|
+
@csrf = csrf
|
70
|
+
|
71
|
+
end
|
72
|
+
|
73
|
+
# Some audio streams can't be paused through the SPA API. Playing a
|
74
|
+
# historical queue, and then pausing it, is the best next option.
|
75
|
+
#
|
76
|
+
def force_pause()
|
77
|
+
|
78
|
+
r = list_hq()
|
79
|
+
queueid = r[:media][0][:queueId]
|
80
|
+
|
81
|
+
play_hq queueid
|
82
|
+
sleep 1
|
83
|
+
|
84
|
+
pause()
|
65
85
|
|
66
86
|
end
|
67
87
|
|
@@ -70,8 +90,15 @@ class AlexaRemoteCtl
|
|
70
90
|
end
|
71
91
|
|
72
92
|
def list_ebooks()
|
73
|
-
get_json '/api/ebooks/library', "mediaOwnerCustomerId=#{@customerid}" +
|
93
|
+
r = get_json '/api/ebooks/library', "mediaOwnerCustomerId=#{@customerid}" +
|
74
94
|
"&nextToken=&size=50"
|
95
|
+
r[:metadataList]
|
96
|
+
end
|
97
|
+
|
98
|
+
# list historical queue (hq)
|
99
|
+
#
|
100
|
+
def list_hq()
|
101
|
+
get_json '/api/media/historical-queue', "size=50&offset=-1"
|
75
102
|
end
|
76
103
|
|
77
104
|
def mute?()
|
@@ -93,7 +120,13 @@ class AlexaRemoteCtl
|
|
93
120
|
pp_cmd('Play')
|
94
121
|
end
|
95
122
|
|
96
|
-
def play_ebook(
|
123
|
+
def play_ebook(obj)
|
124
|
+
|
125
|
+
id = if obj.is_a? Integer then
|
126
|
+
list_ebook()[obj][:asin]
|
127
|
+
else
|
128
|
+
obj
|
129
|
+
end
|
97
130
|
|
98
131
|
serialno = @device[:serialno]
|
99
132
|
type = @device[:type]
|
@@ -111,8 +144,19 @@ class AlexaRemoteCtl
|
|
111
144
|
|
112
145
|
end
|
113
146
|
|
114
|
-
|
115
|
-
|
147
|
+
# play historical queue
|
148
|
+
# note: You can find the queueid from an entry in the list_hq() result
|
149
|
+
#
|
150
|
+
def play_hq(obj)
|
151
|
+
|
152
|
+
queueid = if obj.is_a? Integer then
|
153
|
+
r = list_hq()
|
154
|
+
r[:media][obj][:queueId]
|
155
|
+
else
|
156
|
+
obj
|
157
|
+
end
|
158
|
+
|
159
|
+
device_phq(queueid)
|
116
160
|
end
|
117
161
|
|
118
162
|
def playing?()
|
@@ -150,6 +194,8 @@ class AlexaRemoteCtl
|
|
150
194
|
device_cmd(body)
|
151
195
|
end
|
152
196
|
|
197
|
+
alias setvol vol=
|
198
|
+
|
153
199
|
private
|
154
200
|
|
155
201
|
# play, pause, or next
|
@@ -226,7 +272,7 @@ class AlexaRemoteCtl
|
|
226
272
|
"AppleWebKit/537.36 (KHTML, like Gecko) " +
|
227
273
|
"Chrome/101.0.4951.64 Safari/537.36"
|
228
274
|
request["X-Requested-With"] = "XMLHttpRequest"
|
229
|
-
request["csrf"] =
|
275
|
+
request["csrf"] = @csrf
|
230
276
|
request["dnt"] = "1"
|
231
277
|
request["sec-ch-ua"] = "\" Not A;Brand\";v=\"99\", \"Chromium\";v=\"101\""
|
232
278
|
request["sec-ch-ua-mobile"] = "?0"
|
@@ -288,70 +334,86 @@ class AlexaDevices
|
|
288
334
|
# note: label can be any identifier you choose e.g. kitchen
|
289
335
|
#
|
290
336
|
def initialize(devicesx=[], devices: devicesx,
|
291
|
-
domain: 'alexa.amazon.co.uk', cookie: '', customerid: ''
|
337
|
+
domain: 'alexa.amazon.co.uk', cookie: '', customerid: '',
|
338
|
+
csrf: '', debug: false)
|
292
339
|
|
293
340
|
@devices, @domain, @cookie = devices, domain, cookie
|
294
|
-
@customerid = customerid
|
341
|
+
@customerid, @csrf, @debug = customerid, csrf, debug
|
295
342
|
|
296
343
|
end
|
297
344
|
|
345
|
+
def force_pause(id) invoke(:force_pause, id) end
|
346
|
+
def info(id=nil) invoke(:info, id) end
|
347
|
+
def list_ebooks(id) invoke(:list_ebooks, id) end
|
348
|
+
def list_hq(id=nil) invoke(:list_hq, id) end
|
349
|
+
def mute?(id=nil) invoke2(:mute?, id) end
|
350
|
+
def next(id) invoke2(:next, id) end
|
351
|
+
|
298
352
|
def playing()
|
299
353
|
|
300
|
-
@devices.map do |device, label|
|
354
|
+
devices = @devices.map do |device, label|
|
355
|
+
|
356
|
+
puts 'label: ' + label.inspect if @debug
|
357
|
+
puts 'device: ' + device.inspect if @debug
|
358
|
+
|
301
359
|
alexa = get_alexa device
|
302
360
|
alexa.playing? ? [alexa, label] : nil
|
303
|
-
end.compact
|
304
361
|
|
305
|
-
|
306
|
-
|
307
|
-
def pause(id=nil)
|
362
|
+
end.compact
|
308
363
|
|
309
|
-
|
364
|
+
puts 'devices: ' + devices.inspect if @debug
|
365
|
+
return devices
|
310
366
|
|
311
|
-
|
367
|
+
end
|
312
368
|
|
313
|
-
|
314
|
-
|
369
|
+
def pause(id=nil) invoke2(:pause, id) end
|
370
|
+
def play(id) invoke(:play, id) end
|
371
|
+
def play_ebook(id) invoke(:list_hq, id) end
|
372
|
+
def play_hq(id,qid) invoke(:play_hq, id, qid) end
|
373
|
+
def playing?(id=nil) invoke(:playing, id) end
|
374
|
+
def text1(id=nil) invoke2(:text1, id) end
|
375
|
+
def text2(id=nil) invoke2(:text2, id) end
|
376
|
+
def title(id=nil) invoke2(:title, id) end
|
377
|
+
def vol(id=nil) invoke(:vol, id) end
|
378
|
+
def vol=(id=nil) invoke(:vol=, id) end
|
315
379
|
|
316
|
-
|
380
|
+
private
|
317
381
|
|
318
|
-
|
319
|
-
puts 'Pausing @' + label.inspect
|
320
|
-
alexa.pause
|
321
|
-
end
|
382
|
+
def get_alexa(device)
|
322
383
|
|
323
|
-
|
384
|
+
AlexaRemoteCtl.new(cookie: @cookie, device: device,
|
385
|
+
customerid: @customerid, csrf: @csrf)
|
324
386
|
end
|
325
387
|
|
326
|
-
def
|
327
|
-
|
328
|
-
a = @devices
|
388
|
+
def apply_cmd(a, cmd, id, args)
|
329
389
|
|
330
390
|
if id then
|
331
391
|
|
332
392
|
device, _ = a.find {|_, label| label.to_sym == id.to_sym}
|
333
393
|
alexa = get_alexa device
|
334
|
-
alexa.
|
394
|
+
alexa.method(cmd).call(*args)
|
335
395
|
|
336
396
|
else
|
337
397
|
|
338
|
-
a.
|
398
|
+
a.map do |device, label|
|
339
399
|
|
340
|
-
puts '
|
400
|
+
puts cmd.to_s + ' @' + label.inspect
|
341
401
|
alexa = get_alexa device
|
342
|
-
alexa.
|
402
|
+
alexa.method(cmd).call(*args)
|
343
403
|
|
344
404
|
end
|
345
405
|
|
346
406
|
end
|
347
407
|
end
|
348
408
|
|
349
|
-
|
350
|
-
|
351
|
-
|
409
|
+
def invoke(cmd, id, *args)
|
410
|
+
apply_cmd(@devices, cmd, id, args)
|
411
|
+
end
|
352
412
|
|
353
|
-
|
354
|
-
|
413
|
+
# apply command to an Alexa device which is currently playing
|
414
|
+
#
|
415
|
+
def invoke2(cmd, id, *args)
|
416
|
+
apply_cmd(playing(), cmd, id, args)
|
355
417
|
end
|
356
418
|
|
357
419
|
end
|
data.tar.gz.sig
CHANGED
Binary file
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: alexa_remotectl
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.4.
|
4
|
+
version: 0.4.4
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- James Robertson
|
@@ -35,7 +35,7 @@ cert_chain:
|
|
35
35
|
d/gEwBtUmduwWZNX2NOJehf8s1cnH9OBP7s1ziHjdkZCgkQm3QewRRcdfZeYwFi6
|
36
36
|
4kVEcApgAgd+04ctE6uiRn5o
|
37
37
|
-----END CERTIFICATE-----
|
38
|
-
date: 2022-05-
|
38
|
+
date: 2022-05-23 00:00:00.000000000 Z
|
39
39
|
dependencies:
|
40
40
|
- !ruby/object:Gem::Dependency
|
41
41
|
name: clipboard
|
metadata.gz.sig
CHANGED
Binary file
|