A Python 2.7/3.x module for Amcrest Cameras using the SDK HTTP API.

Overview

Python Amcrest

https://travis-ci.org/tchellomello/python-amcrest.svg?branch=master

A Python 2.7/3.x module for Amcrest Cameras using the SDK HTTP API. Amcrest and Dahua devices share similar firmwares. Dahua Cameras and NVRs also work with this module.

Documentation: http://python-amcrest.readthedocs.io/

Installation

PyPI

/etc/profile.d/amcrest-cli-autocomplete.sh ">
$ pip install amcrest --upgrade
$ eval "$(register-python-argcomplete amcrest-cli)"

# To enable amcrest-cli autocomplete in the system:
$ echo 'eval "$(register-python-argcomplete amcrest-cli)"' >  /etc/profile.d/amcrest-cli-autocomplete.sh

RPM

$ git clone [email protected]:tchellomello/python-amcrest.git
$ ./autogen.sh
$ make rpm
$ dnf/yum install amcrest-cli-NVR.rpm pythonX-amcrest-NVR.rpm

Usage

#Capture audio camera.audio_stream_capture(httptype="singlepart", channel=1, path_file="/home/user/Desktop/audio.aac") CTRL-C to stop the continuous audio flow or use a timer #Move camera down camera.ptz_control_command(action="start", code="Down", arg1=0, arg2=0, arg3=0) #Record realtime stream into a file camera.realtime_stream(path_file="/home/user/Desktop/myvideo") CTRL-C to stop the continuous video flow or use a timer ">
from amcrest import AmcrestCamera
camera = AmcrestCamera('192.168.0.1', 80, 'admin', 'password').camera

#Check software information
camera.software_information
'version=2.420.AC00.15.R\r\nBuildDate=2016-09-08'

#Capture snapshot
camera.snapshot(0, "/home/user/Desktop/snapshot00.jpeg")
<requests.packages.urllib3.response.HTTPResponse object at 0x7f84945083c8>

#Capture audio
camera.audio_stream_capture(httptype="singlepart", channel=1, path_file="/home/user/Desktop/audio.aac")
CTRL-C to stop the continuous audio flow or use a timer

#Move camera down
camera.ptz_control_command(action="start", code="Down", arg1=0, arg2=0, arg3=0)

#Record realtime stream into a file
camera.realtime_stream(path_file="/home/user/Desktop/myvideo")
CTRL-C to stop the continuous video flow or use a timer

Command Line

$ man amcrest-cli
or
$ amcrest-cli --help

# Saving credentials to file.
$ vim ~/.config/amcrest.conf
[patio]
hostname: 192.168.0.20
username: admin
password: 123456
port: 80

[living_room]
hostname: 192.168.0.21
username: admin
password: secret
port: 80

$ amcrest-cli --camera living_room --version-http-api
version=1.40

Text User Interface (TUI)

Configure amcrest.conf and trigger amcrest-tui, make sure the user triggering amcrest-tui have access to framebuffer device or use sudo.

NOTE: Execute it from console logins, like /dev/ttyX (Non X Window). Pseudo-terminals like xterm, ssh, screen and others WONT WORK.

$ vim ~/.config/amcrest.conf
[patio]
hostname: 192.168.0.20
username: admin
password: 123456
port: 80

[living_room]
hostname: 192.168.0.21
username: admin
password: secret
port: 80

$ amcrest-tui

Supportability Matrix

Cameras

Model Tested Status Results/Issues
IPM-721 Yes working  
IPM-HX1 Yes working  
IP2M-841 Yes working  
IP2M-842 Yes working  
IP3M-941 Yes working  
IP3M-943 Yes working  
IP3M-956 Yes working  
IP3M-956E Yes working  
IP3M-HX2 Yes working  
IP4M-1026B Yes working  
IP4M-1051B Yes working  
IP5M-1176EB Yes working  
IP8M-2496EB Yes working  
IP8M-T2499EW-28M Yes working  

Network Video Recorders (NVR)

Model Tested Status Results/Issues
XVR DAHUA 5104S Yes working  

If you have different model, feel fee to contribute and report your results.

Help

If you need any help, please join our community on the Gitter channels available at Gitter.

Comments
  • AttributeError: module 'socket' has no attribute 'TCP_KEEPIDLE'

    AttributeError: module 'socket' has no attribute 'TCP_KEEPIDLE'

    Getting the following error when I try to run anything, even just getting cam info:

    AttributeError: module 'socket' has no attribute 'TCP_KEEPIDLE'

    Process finished with exit code 1

    opened by rtmg2007 20
  • Introducing Unittest

    Introducing Unittest

    Integration with:

    • Tox

    • Coveralls

    • Unittest framework

    • Fixed some lint issues

    • Removed fbida from requirements since it is not a Python package. This should be only present on a SPEC file

    invalid 
    opened by tchellomello 16
  • snapshot() does not work for some cameras (HASS: Amcrest Cameras fail after update to 0.59.1)

    snapshot() does not work for some cameras (HASS: Amcrest Cameras fail after update to 0.59.1)

    **Description of problem:**After upgrade to 0.59.1 only 1 of my Amcrest cameras output appear in both of my Amcrest cameras displays on the Dashboard.

    I upgrade my RPI 3 running on Raspbian Stretch Desktop to HA version 0.60.0. Still having the same trouble with my Amcrest Cameras. I did see this in the Info tab if this helps!! Retrying (Retry(total=2, connect=None, read=None, redirect=None, status=None)) after connection broken by 'ProtocolError('Connection aborted.', RemoteDisconnected('Remote end closed connection without response',))': /cgi-bin/snapshot.cgi?channel=0 2:18 PM components/camera/amcrest.py (WARNING)

    bug help wanted priority 
    opened by akerrichardt 10
  • sending audio

    sending audio

    first off, this is awesome i figured i was going to end up having to put something like this together myself but it's already done!

    on that note; has anyone had any luck sending audio to their cam? this utility appears to send the audio to the cam just fine. However it always sounds completely messed up when outputting through the cam. Initially i started with just curl with the same result until i stumbled upon this.

    im assuming it's some type of audio encoding issue. I have tried sending in most of the available formats with different bit/sample rates with no luck.

    so far this encoding gets me the closest but it's still FAR from correct

    G.711A as content type ffmpeg -i 4353.mp3 -c:a pcm_alaw -ac 1 -ar 16000 -sample_fmt s16 output.wav

    help wanted question 
    opened by josh-- 10
  • Add event_stream() which returns stream of camera events

    Add event_stream() which returns stream of camera events

    Description

    Currently, determining if motion or other events occur requires polling via event_channels_happened() (or one of the other methods or properties that use it.) This can delay response to events, and can even miss events if the event duration is shorter than the polling period.

    This adds a new method -- event_stream() -- which will return events as they happen. It is a generator and will normally not return, so it should be run in a separate thread or process.

    Example use case

    import re
    import threading
    from amcrest import AmcrestCamera, CommError
    
    _START_STOP = re.compile(r"Code=([^;]+);action=(Start|Stop)", flags=re.S)
    
    def process_events(camera, event_codes):
        event_codes = ",".join(event_codes)
        while True:
            try:
                for event_info in camera.event_stream(event_codes, retries=5):
                    print("Event info:", repr(event_info))
                    for code, action in _START_STOP.findall(event_info):
                        print("--->", code, action)
            except CommError as error:
                print("Error while processing events:", repr(error))
    
    camera = AmcrestCamera(...).camera
    thread = threading.Thread(target=process_events, args=(camera, ["VideoMotion"]))
    thread.daemon = True
    thread.start()
    

    To do

    • [x] Make sure comm errors and camera power cycling are handled properly.
    • [x] Get feedback from other users with other camera models and/or firmware versions.
    • [x] Prototype usage in Home Assistant's amcrest integration.
    • [x] Determine if anything can be done about urllib3 warning:
    WARNING:urllib3.connectionpool:Failed to parse headers (url=http://<host>:<port>/cgi-bin/eventManager.cgi?action=attach&codes=%5BVideoMotion%5D): [StartBoundaryNotFoundDefect(), MultipartInvariantViolationDefect()], unparsed data: ''
    Traceback (most recent call last):
      File "/home/phil/test/amcrest/venv/lib/python3.7/site-packages/urllib3/connectionpool.py", line 441, in _make_request
        assert_header_parsing(httplib_response.msg)
      File "/home/phil/test/amcrest/venv/lib/python3.7/site-packages/urllib3/util/response.py", line 71, in assert_header_parsing
        raise HeaderParsingError(defects=defects, unparsed_data=unparsed_data)
    urllib3.exceptions.HeaderParsingError: [StartBoundaryNotFoundDefect(), MultipartInvariantViolationDefect()], unparsed data: ''
    

    Thanks to @NickWaterton and his groundwork in PR #140!

    opened by pnbruckner 9
  • Add functionality to use additional channels

    Add functionality to use additional channels

    Add additional methods to be able to use specified channels, allowing this to be used with NVRs. Currently, the @property's read from channel 0, change these methods to call into the new functions for the channel it used previously, so these should not change behavior.

    Behavioral changes include:

    • Event.event_channels_happened returns a list of channels where the event has occurred, rather than the request output. This simplifies the is_x_detected methods.
    • The Event.is_x_detected methods return a list of channels where the event occurred, rathen than a bool of if the event occurred or not.
    • Video.video_in_option returns a list of all option configurations for all channels, rather than just returning the first option. All of the properties (eg video_enabled and day_night_color) are unchanged, as they check channel 0.
    • Some of the System properties (eg serial_number) are split with pretty() to give just the value rather than the full message payload.
    opened by flacjacket 6
  • FIX for #75 and #149

    FIX for #75 and #149

    Potential fix for #75 and #149

    I do not have access to the hardware at this time (due to corona virus). So I cannot test this.

    The user using play_wav will now need to know the encoding type for their .wav file.

    The most critical part of this PR is the new optional argument 'encoding'

    It is up to someone who has access to a camera to test out all the encodings and report back to this community their results.

    According to a comment in the same file:

    Supported audio encode type according with documentation: PCM ADPCM G.711A G.711.Mu G.726 G.729 MPEG2 AMR AAC

    G.711A will be the default one as that was the encoding type that was hard coded before.

    Take care, and happy testing!

    opened by AlexKohanim 6
  • Reuse command sessions

    Reuse command sessions

    In command method, don't create a new requests session every time. Rather, keep a session for each value of retries. Also don't try to update default values for retries and timeout for each command because that wasn't thread safe.

    opened by pnbruckner 6
  • Release 1.8.0?

    Release 1.8.0?

    It'd be great to have a new release now that some of the NVR channel related functionality is in. Looking at the commits since 1.7.2, I think this is the set of key changes:

    Breaking changes

    • Python 2 no longer supported, Python 3.6 is the minimum required version
    • PTZ commands (e.g. zoom_in, move_left) require boolean value for start parameter, rather than "start" and "stop" strings for the action parameter

    New features

    • Smart motion detection events added as is_human_detected and is_vehicle_detected properties.
    • Added methods to query separate channels to allow using multiple cameras on NVRs.
    • Type annotations added to allow for type checking.

    I'd say no particular rush to get this out, just curious what sort of things would be needed to get to the point of cutting a release. A couple of the current open PRs seem like they are also close to ready if they can get some minor fixes from authors, so those would probably be good to get in if possible.

    opened by flacjacket 5
  • **Feature Request** Smart Motion Detection

    **Feature Request** Smart Motion Detection

    I recently upgraded a camera to the IPC-HDW5442TM-AS. This has some new events and I was hoping to use the Smart Motion Detection (can detect humans and vehicles). Playing with the API calls I found that the getConfig name is SmartMotionDetect

    The following command:

    http://<IP>/cgi-bin/configManager.cgi?action=getConfig&name=SmartMotionDetect
    

    Returns:

    table.SmartMotionDetect[0].Enable=true
    table.SmartMotionDetect[0].ObjectTypes.Human=true
    table.SmartMotionDetect[0].ObjectTypes.Vehicle=false
    table.SmartMotionDetect[0].Sensitivity=Middle
    

    This shows that the smart detection is enabled, and for humans but not vehicles - and the sensitivity is set to medium (3 options, low/medium/high).

    Using this I expect that the event subscription would be either SmartMotionDetect or SmartVideoMotion based on what is already in this repo. I am a novice, and wasn't sure how to test this. I tried, but was unsuccessful getting a correct response with the existing motion detection (I'm sure I'm doing something wrong though).

    When I tried to test some of the commands in the interpreter I expect I am doing it wrong. I am getting generator objects so I expect it is doing something but I am sending the wrong commands or not telling it how to output... as said earlier, I'm a novice 😄 .

    >>> import amcrest
    >>> camera = amcrest.AmcrestCamera('<IP>',80,'<admin>','<password>').camera
    >>> camera.software_information
    ('version=2.800.0000000.20.R', 'build:2020-09-03\r\n')
    >>> camera.event_stream('All')
    <generator object Event.event_stream at 0x7f307bfe0900>
    >>> camera.event_stream('VideoMotion')
    <generator object Event.event_stream at 0x7f307bfe0820>
    >>> camera.event_actions('All')
    <generator object Event.event_actions at 0x7f307bfe0900>
    

    If this is as simple as adding a new event name, fantastic - but if it needs testing, I would be happy to do it, but might need a little hand holding to start. If I could be told how to test the VideoMotion and get a response correctly, I'm sure I could work from there to get the SmartVideoMotion or SmartMotionDetect whatever they call it figured out.

    Thanks! DeadEnd

    opened by DeadEnded 5
  • Older Firmware Cameras Not Supportive of URL that is Encoded (EventManager)

    Older Firmware Cameras Not Supportive of URL that is Encoded (EventManager)

    On a Dahua 2015 firmware, no upgrade possible (last firmware)

    This URL gets a bad response (400) http://192.168.1.41:80/cgi-bin/eventManager.cgi?action=attach&codes=%5BAll%5D

    This URL works http://192.168.1.41:80/cgi-bin/eventManager.cgi?action=attach&codes=[All]

    A quick fix was detailed here (with Python Amcrest 1.7.0) in HA Reported bug https://github.com/home-assistant/core/issues/33875#issuecomment-615548520

    Which seems to be working for me.

    wontfix 
    opened by jamesarbrown 5
  • Events to trigger HTTP Post to external URL

    Events to trigger HTTP Post to external URL

    I'm still reading through some of the documentation with this camera and the API. I'm hoping that I can set a configuration option that will cause the camera to automatically HTTP Post event data to a server I have running in the cloud. I'm hoping to do this without having to have a listener running actively monitoring those events myself.

    .e.g something like setConfig onMotionDetected POST to https://someexternalsite.com

    I'm not seeing anything like this, but the documentation regarding setting config options is a little tough to grok.

    Regards

    opened by trankin 0
  • Support enabling and disabling the mechanical chime

    Support enabling and disabling the mechanical chime

    One of the biggest reasons I'm dropping my Nest doorbell is because of the lack of API control. The Amcrest AD110 has the required control for me to bring things local, but it's missing one thing: the ability to silence the indoor chime. I have young children and a baby on the way, and we want that doorbell chime SILENCED during nap time.

    It seems it is possible to disable (and likely reenable) the chime using the web api.

    http://<ip address of ad110>/cgi-bin/configManager.cgi?action=setConfig&ExternalDoorBell.Enable=false
    http://<ip address of ad110>/cgi-bin/configManager.cgi?action=setConfig&ExternalDoorBell.Enable=true
    

    You can get the current status like so:

    http://<ip address of ad110>/cgi-bin/configManager.cgi?action=getConfig&name=ExternalDoorBell
    

    Is this something the module can support so it may trickle up the stream and eventually into Home Assistant?

    opened by mririgoyen 1
  • event_actions() causes AttributeError

    event_actions() causes AttributeError

    I am connecting to an Amcrest AD410 Doorbell and utilizing the event_actions() method and after about 100s, I receive the Error: AttributeError: 'NoneType' object has no attribute 'read'.

    More specifically, I am calling: camera.event_actions("All", retries=5, timeout_cmd=(10.00, 3600)) and with DEBUG log level, I get the follow:

    2022-04-30 00:42:29,922 - urllib3.connectionpool [DEBUG] Starting new HTTP connection (1): 192.168.10.20:80
    2022-04-30 00:42:29,970 - urllib3.connectionpool [DEBUG] http://192.168.10.20:80 "GET /cgi-bin/eventManager.cgi?action=attach&codes=%5BAll%5D HTTP/1.1" 401 0
    2022-04-30 00:44:12,784 - urllib3.connectionpool [DEBUG] http://192.168.10.20:80 "GET /cgi-bin/eventManager.cgi?action=attach&codes=%5BAll%5D HTTP/1.1" 200 None
    2022-04-30 00:44:12,785 - amcrest.http [DEBUG] <Doorbell-D66A> Query 9 worked. Exit code: <200>
    2022-04-30 00:44:12,786 - amcrest.event [DEBUG] <Doorbell-D66A> event info: '\r\nCode=VideoMotionInfo;action=State;index=0'
      File "/usr/local/lib/python3.10/site-packages/amcrest/event.py", line 361, in event_actions
        for event_info in self.event_stream(
      File "/usr/local/lib/python3.10/site-packages/amcrest/event.py", line 312, in event_stream
        for line in _event_lines(ret.iter_content(decode_unicode=True)):
      File "/usr/local/lib/python3.10/site-packages/amcrest/event.py", line 39, in _event_lines
        for char in ret:
      File "/usr/local/lib/python3.10/site-packages/requests/utils.py", line 549, in stream_decode_response_unicode
        for chunk in iterator:
      File "/usr/local/lib/python3.10/site-packages/requests/models.py", line 760, in generate
        for chunk in self.raw.stream(chunk_size, decode_content=True):
      File "/usr/local/lib/python3.10/site-packages/urllib3/response.py", line 575, in stream
        for line in self.read_chunked(amt, decode_content=decode_content):
      File "/usr/local/lib/python3.10/site-packages/urllib3/response.py", line 770, in read_chunked
        chunk = self._handle_chunk(amt)
      File "/usr/local/lib/python3.10/site-packages/urllib3/response.py", line 714, in _handle_chunk
        value = self._fp._safe_read(amt)
      File "/usr/local/lib/python3.10/http/client.py", line 630, in _safe_read
        data = self.fp.read(amt)
    AttributeError: 'NoneType' object has no attribute 'read'
    

    What's also odd that I first get a 401 response before eventually getting a 200. Not sure if this is affecting things tho as I see the same behavior with other calls (ie camera.storage_all) and they return fine.

    Environment:

    • OS: Debian GNU/Linux 10 (buster)
    • Python: 3.10
      • amcrest: 1.9.7
    opened by maxirus 0
  • Add github action to automate creating PyPI packages

    Add github action to automate creating PyPI packages

    Add a new github action that will build and upload PyPI packages when new releases are cut. This works by running but not uploading the package when a tag is created, then, when the Github release is published, the build is run and the package is pushed to PyPI.

    To work, this will also require a PyPI API token. I am able to generate a token, but do not have access to add it as a Github Actions secret to this repo.

    opened by flacjacket 0
Releases(1.9.7)
Owner
Marcelo Moreira de Mello
Marcelo Moreira de Mello
python3.5+ hubspot client based on hapipy, but modified to use the newer endpoints and non-legacy python

A python wrapper around HubSpot's APIs, for python 3.5+. Built initially around hapipy, but heavily modified. Check out the documentation here! (thank

Jacobi Petrucciani 140 Dec 21, 2022
A Python wrapper around the OpenWeatherMap web API

PyOWM A Python wrapper around OpenWeatherMap web APIs What is it? PyOWM is a client Python wrapper library for OpenWeatherMap (OWM) web APIs. It allow

Claudio Sparpaglione 740 Dec 18, 2022
Infinity: a Twitter retweet bot that can be used by anyone

INSTAMATE Requires Firefox Instapy Python3 How To Use? Fork the repository Add your credentials in the bot.py file Save commits Clone your fork cd int

unofficialdxnny 3 Jun 23, 2022
A python script fetches all your starred repositories from your GitHub account and clones them to your server so you will never lose important resources

A python script fetches all your starred repositories from your GitHub account and clones them to your server so you will never lose important resources

Ringo Hoffmann 27 Oct 01, 2022
Want to get your driver's license? Can't get a appointment because of COVID? Well I got a solution for you.

NJDMV-appoitment-alert Want to get your driver's license? Can't get a appointment because of COVID? Well I got a solution for you. We'll get you one i

Harris Spahic 3 Feb 04, 2022
A simple Telegram bot that can add caption to any media on your channel

Channel Auto Caption This bot can add a caption for any media/document sent to a channel. Just deploy bot and add bot as admin to a channel. Deploy to

22 Nov 14, 2022
🎄 JustaGrabber - A discord token grabber written in python3

🎄 JustaGrabber - A discord token grabber written in python3 🎇 Made by kldiscord https://github.com/kldiscord 🌟 Please leave a star if you liked Jus

1 Dec 19, 2022
Documentation and Samples for the Official HN API

Hacker News API Overview In partnership with Firebase, we're making the public Hacker News data available in near real time. Firebase enables easy acc

Y Combinator Hacker News 9.6k Jan 03, 2023
A python Discord wrapper made in well, python.

discord.why A python Discord wrapper made in well, python. Made to be used by devs who want something a bit more, general. Basic Examples Sending a me

HellSec 6 Mar 26, 2022
A repo to automate the booking process for vaccinations

OntarioVaccineFormAutomaker A repo to automate the booking process for vaccinations Requirements Allow ALL sights to be able to know your location (on

Rafid Dewan 7 May 31, 2021
Non official, but friendly QvaPay library for the Python language.

Python SDK for the QvaPay API Non official, but friendly QvaPay library for the Python language. Setup You can install this package by using the pip t

Carlos Lugones 17 Nov 25, 2022
The Official Twilio SendGrid Led, Community Driven Python API Library

The default branch name for this repository has been changed to main as of 07/27/2020. This library allows you to quickly and easily use the SendGrid

Twilio SendGrid 1.4k Jan 07, 2023
Telegram Bot to store Posts and Documents and it can Access by Special Links.

File-sharing-Bot Telegram Bot to store Posts and Documents and it can Access by Special Links. I Guess This Will Be Usefull For Many People..... 😇 .

Code X Botz 1.2k Jan 08, 2023
IMDbPY is a Python package useful to retrieve and manage the data of the IMDb movie database about movies, people, characters and companies

IMDbPY is a Python package for retrieving and managing the data of the IMDb movie database about movies, people and companies. Revamp notice Starting

Davide Alberani 1.1k Jan 02, 2023
Photogrammetry Web API

OpenScanCloud Photogrammetry Web API Overview / Outline: The OpenScan Cloud is intended to be a decentralized, open and free photogrammetry web API. T

Thomas 86 Jan 05, 2023
Bender: A Markov Babbler Slack Bot

See the Digital Ocean tutorial for instructions on how to get the basic bot structure in place. Once you have that, set the gunicorn command to run as

Andrew Howard 1 Dec 04, 2021
Discord bot built using Python. through this you can get information about the upcoming matches, scoreboard, live score

IPL-bot This is a Discord bot built using Python. through this you can get information about the upcoming matches, scoreboard, live score, and many mo

0 Dec 23, 2021
Unofficial Python wrapper for official Hacker News API

haxor Unofficial Python wrapper for official Hacker News API. Installation pip install haxor Usage Import and initialization: from hackernews import H

147 Sep 18, 2022
A Python Library to Make Quote Images

Quote2Image A Python Library to Make Quote Images How To Use? Download The Latest Package From Releases Extract The Zip File And Place Every File In I

Secrets 28 Dec 30, 2022
BanAllBot - Telegram Code To Ban All Group Members very fast

BanAllBot Telegram Code To Ban All Group Members very fast FORK AND KANG WITH CR

27 May 13, 2022