tchellomello / python-arlo

Python Arlo is a library written in Python 2.7/3x that exposes the Netgear Arlo cameras as Python objects.
GNU Lesser General Public License v3.0
100 stars 35 forks source link

Can't get base station mode #43

Open arasium opened 7 years ago

arasium commented 7 years ago

Hi,

I can get the base station mode (I see the update in my mobile App) but base.mode (like in the sample) return an empty result even if I set it just before.

I'm on a raspberry with raspbian jessie lite with Python 2.7.9

rccoleman commented 7 years ago

It's working for me. If you do "arlo.base_stations", does it list only one base station? Some Netgear routers can act as Arlo base stations, and the "base = arlo.base_stations[0]" line will only work properly if the first one is the one you want.

arasium commented 7 years ago

I've done the test. I've only one base station listed. It seems that I don't receive the callback. I will do more tests.

arasium commented 7 years ago

After some tests, it seems to be a thread issue. When the action is sent to arlo server, the code is waiting thrue two loops. During this wait, the thread watching the event queue isn't running so no event is dispatched. Once the waiting loop is finished, i can see the thread getting events and the 'modes' result event.

Tested multiple times on another raspberry 3 but with Jessy desktop: pi@raspberrypi:~ /python-arlo $ sudo python demo.py disarmed pi@raspberrypi:~ /python-arlo $ sudo python demo.py disarmed pi@raspberrypi:~ /python-arlo $ sudo python demo.py None pi@raspberrypi:~ /python-arlo $ sudo python demo.py None pi@raspberrypi:~ /python-arlo $ sudo python demo.py disarmed

tchellomello commented 7 years ago

@arasium can you test it again on the latest version to check if the issue is still happening?

DkYSwe commented 7 years ago

Hi @tchellomello,

I checked it out yesterday (running on RPI) and get the "None" result on each execution. Only one base station identified. Let me know if I can assist with info. :)

chaddotson commented 6 years ago

Is this active with the latest release? I just did some work to modes.

Berjler commented 6 years ago

hi all. Before I did the Update today to pyArlo 0.1.3 the command base.available_modes show ['armed', 'disarmed', 'schedule', 'custom'] And i was able to switch the modes by i.e. base.mode = 'armed'

Now, after the Update there is only ['schedule'] shown. And I could not swich the modes.

The Version I used before was from July2017

Is there any chance to get the modes back?

Cheers mi.ke

chaddotson commented 6 years ago

I encountered this a few times while trying to figure out how to make schedule work correctly. In previous versions, I believe empty list was the result.

What actually happened is the other modes were not retrieved from the arlo api. 'schedule' is special and not returned from the server. Probably need to add some robustness around some of the api calls to better indicate failures such as this.

Is it doing it all the time for you? If it is, out of curiosity, what happens if you call basestation->update() before retrieving modes?

Berjler commented 6 years ago

Yes, I have tried several times and the result is unfortunately always "schedule". base.update () does not help either. The strange thing is that I have been using the API for half a year to automatically switch between modes. There was always perfect. Until update yesterday.

chaddotson commented 6 years ago

Ok I just remembered something I encountered that had this same result.

Try this:

Berjler commented 6 years ago

ok, I logged in via website, than logout. After that, I run the test-script, same result, only ['schedule']

The test-script:

from pyarlo import PyArlo
arlo  = PyArlo('user', 'xxxxx')
base = arlo.base_stations[0]
base.update()
print(base.available_modes)
chaddotson commented 6 years ago

You shouldn't have had to call update, it was just something to try.

I ran the following with pyarlo 0.1.2:

from pyarlo import PyArlo
arlo = PyArlo(username, password)
base = arlo.base_stations[0]
print(base.available_modes)

And got: ['schedule', 'disarmed', 'armed', 'day', 'test']

Berjler commented 6 years ago

well, I added the update command only on the basis of your advice :-)

Now I downgrade pyArlo from 0.1.3 to 0.1.2 but still the same failure.

Maybe there is any other reason . . . Basestation or firmware?! Can we compare a few points? my device is: basestation hardware is VMB3010r2 firmware 1.9.4.0_15548

or do you have any other ideas, what I can try out to get my mode switching back?

chaddotson commented 6 years ago

Same firmware here, but my hardware is the 4000 model. I'm not sure that would have anything to do with it since they would standardize their api away from different model numbers at this level (at least I would think).

Might try increased logging to see if anything falls out. Note: DON'T POST the output as it will contain your username and password.

try:

from logging import basicConfig, DEBUG
from pyarlo import PyArlo

basicConfig(level=DEBUG, format='%(asctime)s - %(levelname)s - %(name)s - %(message)s')
arlo = PyArlo(username, password)
base = arlo.base_stations[0]
print(base.available_modes)

The last couple of lines should be something like:

2018-01-22 21:17:40,387 - DEBUG - pyarlo - Querying https://arlo.netgear.com/hmsweb/client/unsubscribe on attempt: 0/3
2018-01-22 21:17:41,388 - DEBUG - urllib3.connectionpool - https://arlo.netgear.com:443 "GET /hmsweb/client/unsubscribe HTTP/1.1" 200 16
2018-01-22 21:17:41,389 - DEBUG - pyarlo - Required raw object.
['schedule', 'disarmed', 'armed', 'day', 'test']

Note that 200 response from the GET. Does yours have that?

Berjler commented 6 years ago

yes, the response is everytime ok (200) This are the last 4 lines

2018-01-23 08:35:53,369 - DEBUG - pyarlo - Querying https://arlo.netgear.com/hmsweb/client/unsubscribe on attempt: 0/3
2018-01-23 08:35:53,773 - DEBUG - sseclient - Dispatching message event, 383 bytes...
2018-01-23 08:35:53,777 - DEBUG - urllib3.connectionpool - "GET /hmsweb/client/unsubscribe HTTP/1.1" 200 16
2018-01-23 08:35:53,782 - DEBUG - pyarlo - Required raw object.
['schedule']
chaddotson commented 6 years ago

I'll look at this closer this evening. I want to make sure those log lines are representative of what I thought they were last night.

chaddotson commented 6 years ago

Didn't get an opportunity to look in depth but I do believe I had the wrong lines in mind. I'll try to look tomorrow evening. In the mean time could you revert to the version you previously had working and make sure it retrieves the modes properly for you?

chaddotson commented 6 years ago

Please still validate the previous version you had still works.

I was referencing the wrong lines. You'll have to search up into the output some with the debug logging enabled.

Search for the area containing (these are incomplete lines):

pyarlo.base_station - Action body: {'action': 'get', 'from': 'some_guid_web', 'properties': None, 'publishResponse': False, 'resource': 'modes',

^ This line indicates that the code is about to query the api for the list of modes. ..... 4 or so lines later ..... urllib3.connectionpool - https://arlo.netgear.com:443 "POST /hmsweb/users/devices/notify/"

Check to make sure that post return code is 200.

Berjler commented 6 years ago

2018-01-25 09:28:32,276 - DEBUG - urllib3.connectionpool - "POST /hmsweb/users/devices/notify/BASESTATION_ID HTTP/1.1" **200** 16

Then I searched for "HTTP/1.1" in the log
Everytime the respose is "200"

Unfortunately, I do not know how to install an older version. I download the Zip-File (tag.0.0.9) and unzip it. But how can I install it over the curent version without using PIP? (sorry about my unskilled questions and my worse english)

Berjler commented 6 years ago

Now I got it: sudo python setup.py install

Here is the result: I ran the following with pyarlo various versions:

from pyarlo import PyArlo
arlo = PyArlo(username, password)
base = arlo.base_stations[0]
print(base.available_modes)

what did I expect? ['schedule', 'armed', 'disarmed', 'nurEingang'', 'test']

with pyArlo 0.0.6 I got: ['schedule', 'armed', 'disarmed', 'custom'] Incidentally, here it is only possible to switch between armed, disarmed and custom.

with pyArlo 0.0.7 I got:

Traceback (most recent call last):
  File "ArloTest.py", line 4, in <module>
    print(base.available_modes)
  File "build/bdist.linux-armv7l/egg/pyarlo/base_station.py", line 237, in available_modes
  File "build/bdist.linux-armv7l/egg/pyarlo/base_station.py", line 244, in available_modes_with_ids
TypeError: 'NoneType' object is not iterable

with pyArlo 0.0.8 I got:

Exception in thread Thread-1:
Traceback (most recent call last):
  File "/usr/lib/python2.7/threading.py", line 810, in __bootstrap_inner
    self.run()
  File "/usr/lib/python2.7/threading.py", line 763, in run
    self.__target(*self.__args, **self.__kwargs)
  File "build/bdist.linux-armv7l/egg/pyarlo/base_station.py", line 54, in thread_function
    for event in (self.__sseclient).events():
  File "/usr/local/lib/python2.7/dist-packages/sseclient/__init__.py", line 58, in events
    for chunk in self._read():
  File "/usr/local/lib/python2.7/dist-packages/sseclient/__init__.py", line 48, in _read
    for chunk in self._event_source:
  File "/usr/lib/python2.7/dist-packages/requests/models.py", line 656, in generate
    raise ChunkedEncodingError(e)
ChunkedEncodingError: ('Connection broken: IncompleteRead(46 bytes read)', IncompleteRead(46 bytes read))

['schedule']

with pyArlo 0.0.9 I got: ['schedule']

with pyArlo 0.1.0 I got: ['schedule']

with pyArlo 0.1.1 I got: ['schedule']

with pyArlo 0.1.2 I got: ['schedule']

with pyArlo 0.1.3 I got: ['schedule']

I am now back with the productive system to 0.0.6, so that my cameras automatically switch again when I come to home, or the patio door is opened. Unfortunately, the new features are gone.

Incidentally, I got a 4000 basestation in the meantime. No difference to the 3000 (concerning this topic)

Is there anything that I can do to help?

chaddotson commented 6 years ago

This is great information. I'll have a look at it tonight if I can.

edit: No longer tied to my earlier PR

chaddotson commented 6 years ago

I have more info now that I've looked at the code. It looks like it really wasn't doing anything in v0.0.6, those modes: ['schedule', 'armed', 'disarmed', 'custom'] are all hard-coded in that version.

chaddotson commented 6 years ago

With the latest version, what does this result in? print(base.get_available_modes()) should be a list of dictionaries containing the modes and rules for each mode.

from logging import basicConfig, DEBUG, INFO, getLogger
from pyarlo import PyArlo

basicConfig(level=INFO, format='%(asctime)s - %(levelname)s - %(name)s - %(message)s')
arlo = PyArlo(username, password)
base = arlo.base_stations[0]
print(base.available_modes)
print(base.get_available_modes())
Berjler commented 6 years ago

Tried with pyarlo 0.1.2 The output is:

2018-01-27 17:08:54,224 - INFO - urllib3.connectionpool - Starting new HTTPS connection (1): arlo.netgear.com
2018-01-27 17:08:56,207 - INFO - urllib3.connectionpool - Starting new HTTPS connection (2): arlo.netgear.com
['schedule']
None
Berjler commented 6 years ago

I wasn't sure if I understood correctly. So here is additionally the output from pyArlo 0.0.6:

2018-01-27 20:26:57,610 - INFO - urllib3.connectionpool - Starting new HTTPS connection (1): arlo.netgear.com
['schedule', 'armed', 'disarmed', 'custom']
Traceback (most recent call last):
File "ArloTest2.py", line 8, in <module>
print(base.get_available_modes())
AttributeError: 'ArloBaseStation' object has no attribute 'get_available_modes'
chaddotson commented 6 years ago

I was wondering about the 0.1.2. It looks like for some reason it isn't retrieving modes within the specified wait. Currently it will wait 5 seconds for the response before continuing and silently failing.

Try the following with v0.1.2 and post the result.

from logging import basicConfig, DEBUG, INFO, getLogger
from pyarlo import PyArlo
from timeit import timeit

basicConfig(level=INFO, format='%(asctime)s - %(levelname)s - %(name)s - %(message)s')
arlo = PyArlo(username, password)
base = arlo.base_stations[0]
print(timeit(base.get_available_modes, number=1))
Berjler commented 6 years ago

with pyArlo 0.1.2:

2018-01-27 21:26:58,909 - INFO - urllib3.connectionpool - Starting new HTTPS connection (1): arlo.netgear.com
2018-01-27 21:27:00,876 - INFO - urllib3.connectionpool - Starting new HTTPS connection (2): arlo.netgear.com
10.6914310455
chaddotson commented 6 years ago

Ok, its definitely not getting responses when expected. Out of curiosity can you successfully get/set modes or other properties?

Berjler commented 6 years ago

Yes, with the 0.1.2 I can switch from any mode to the 'Schedule' mode. With the 0.0.6 I can switch from anyone mode to another.

What do you think of making the waiting time more dynamic? So wait until the answer, but max e.g. 15 seconds?

Berjler commented 6 years ago

I found a little solution for me by using the old pyArlo 0.0.6

In the file "const.py" I change the following lines:

# define action modes
ACTION_MODES = {
    'armed': 'mode1',
    'disarmed': 'mode0',
    'custom': 'mode2',
    'schedule': 'true',
}

with

# define action modes
ACTION_MODES = {
     'AllesDeaktiviert': 'mode0',    
     'AllesAktiviert': 'mode1',
     'nurInnenbereich': 'mode2',
     'nurAussenbereich': 'mode3',
     'nurGarten': 'mode4',
     'nurGarage': 'mode5',
     'schedule': 'true',
}

The names of the mode assignment correspond exactly to what is entered in the arloAPP. Now I'm able to address each mode specifically by script.

This works without delay and I do not need a scheduler anymore, because my smarthome knows exactly whether I'm at home or not, whether I have barbecue in the garden or if my motorcycle is in the garage etc.

chaddotson commented 6 years ago

Ok, sorry I haven't gotten a chance to look at the master branch in a few days. Hopefully we can resolve this.

tchellomello commented 6 years ago

@Berjler are you still hitting this problem with the latest version?