Установка и настройка zoneminder на ubuntu linux. делаем систему видеонаблюдения
Содержание:
Zoneminder Database
Enable and convert MySQL to innodb_file_per_table for Zoneminder
Note: You may wish to convert MyISAM tables to InnoDB tables before you proceed. Upgrading Zoneminder to 1.26 or newer should do this for you.
innodb_file_per_table is by default ON Mysql 5.6.6 and onwards. There is plenty of stuff on Google about pros & cons of innodb_file_per_table.
This post details how to enable innodb_file_per_table on an existing database. Because innodb_file_per_table affects new tables only, created after innodb_file_per_table is enabled, we need to recreate old databases to force innodb_file_per_table on old tables and reclaim some disk space.
Become root
sudo su
Backup First
Create a dir to take backups:
cd ~
Note: I found it helpful to create a file which contained the MySQL user and password. Otherwise you will have to enter the user and password for every operation.
nano .my.cnf
Enter this content
user=root password=mysqlpass
Ctrl+o Enter to save
CTRL+x to exit
Make backup directory
mkdir backup
cd backup
Copy MySQL data files (raw)
(If all goes well, we will not need this)
Stop Zoneminder
service zoneminder stop
If you have other services that use MySQL you will want to stop them and possibly Apache.
service mysql stop && cp -ra /var/lib/mysql mysqldata && service mysql start
Take mysqldump
As soon as above line completes, take a mysqldump of all databases
mysqldump --routines --events --flush-privileges --all-databases > all-db.sql
Drop Databases
Create a sql file to drop all databases EXCEPT mysql database
mysql -e "SELECT DISTINCT CONCAT ('DROP DATABASE ',TABLE_SCHEMA,' ;') FROM INFORMATION_SCHEMA.TABLES WHERE TABLE_SCHEMA <> 'mysql' AND TABLE_SCHEMA <> 'information_schema';" | tail -n+2 > drop.sql
Verify if drop.sql has correct database names and then execute drop.sql queries.
mysql < drop.sql
Verify all InnoDB tables gone
SELECT table_name, table_schema, engine FROM information_schema.tables WHERE engine = 'InnoDB';
Remove InnoDB files
Stop mysql server first
service mysql stop
Then
rm /var/lib/mysql/ibdata1 && rm /var/lib/mysql/ib_logfile0 && rm /var/lib/mysql/ib_logfile1
At this point most likely you will have only /var/lib/mysql/mysql directory only.
Enable innodb_file_per_table
Open my.cnf file
nano /etc/mysql/my.cnf
Add following line after
innodb_file_per_table
Ctrl+o Enter to save
CTRL+x to exit
Time to import from mysqldump
Start mysql server now
service mysql start
Run mysql import
mysql < all-db.sql
Force mysql_upgrade (to generate performance_schema)
mysql_upgrade --force
That’s All!
Restart Zoneminder (and any other services you have stopped)
service zoneminder start
Check for proper operation and that all your events are present.
When you are satisfied that all is worling well remove the backup directory and password filr=e
cd ~
rm -r backup
rm .my.cnf
You are finished!
Adding Permissions to allow Database Upgrade
Versions of Zoneminder up to and including 1.28.1 in Ubuntu would automatically add the zm database to MySQL. Beginning about August
2015 the development version from the iconnor-master PPA omitted this step becoming like the Debian install process. Manually adding the
database to MySQL will be necessary.
To install the zm database (after doing apt-get install zoneminder)
Create Zoneminder database in MySQL (Note: this also creates the default Zoneminder user and permissions in MySQL)
This next step creates a file which contained the MySQL user and password. Otherwise you will have to enter the user and password on the
command line which is not secure!
Go to the root directory
cd ~
Create a hidden password file
nano .my.cnf
Enter this content (but use your MySQL root password!)
user=root password=(mysqlpass)
Ctrl+o Enter to save
CTRL+x to exit
Create database permissions
mysql -e "grant select,insert,update,delete,create,alter,lock tables on zm.* to 'zmuser'@localhost identified by 'zmpass';"
Remove password file
rm .my.cnf
Continue with the Zoneminder installation
Hardening Webserver
Hide Apache Version and Operating System
sudo vi /etc/apache2/conf-enabled/security.conf
ServerTokens Prod ServerSignature Off
sudo systemctl restart apache2
Disable Directory Listing and FollowSymLinks
sudo vi /etc/apache2/apache2.conf
<Directory /var/www/> Options -Indexes -FollowSymLinks AllowOverride None Require all granted </Directory>
sudo systemctl restart apache2
Secure Apache using mod_security and mod_evasive Modules
Mod_security
Acts as a firewall for web servers and applications, providing protection against brute force attacks. Install it and then restart Apache.
sudo apt-get install libapache2-mod-security2 -y
sudo systemctl restart apache2
Disable TRACE HTTP Requestit Request Size
By default, Trace HTTP Request is enabled allowing for Cross Site Tracing. This enables a hacker to easily steal cookie information. Disabling Trace HTTP Request makes the mod_proxy and core server return “405 — Method Not Allowed” error message to clients.
sudo vi /etc/apache2/conf-enabled/security.conf
TraceEnable Off
sudo systemctl restart apache2
Easy Way: Debian Jessie¶
Step 1: Setup Sudo
By default Debian does not come with sudo. Log in as root or use su command.
N.B. The instructions below are for setting up sudo for your current account, you can
do this as root if you prefer.
apt-get update apt-get install sudo usermod -a -G sudo <username> exit
Logout or try to reload user groups
Step 2: Run sudo and update
Now run session using sudo and ensure system is updated.
sudo -i apt-get upgrade
Step 3: Install Apache and MySQL
These are not dependencies for the package as they could
be installed elsewhere.
apt-get install apache2 mysql-server
Step 4: Edit sources.list to add jessie-backports
nano etcaptsources.list
Add the following to the bottom of the file
# Backports repository deb http//archive.debian.orgdebian jessie-backports main contrib non-free
CTRL+o and <Enter> to save
CTRL+x to exit
Run the following
echo 'Acquire::Check-Valid-Until no;' > etcaptapt.conf.d99no-check-valid-until
Step 5: Install ZoneMinder
apt-get update apt-get install zoneminder
Step 6: Read the Readme
The rest of the install process is covered in the README.Debian, so feel free to have
a read.
zcat usrsharedoczoneminderREADME.Debian.gz
Step 7: Setup Database
Install the zm database and setup the user account. Refer to Hints in Ubuntu install
should you choose to change default database user and password.
cat usrsharezoneminderdbzm_create.sql | sudo mysql --defaults-file=/etcmysqldebian.cnf echo 'grant lock tables,alter,create,select,insert,update,delete,index on zm.* to 'zmuser'@localhost identified by "zmpass";' | sudo mysql --defaults-file=/etcmysqldebian.cnf mysql
Step 8: zm.conf Permissions
Adjust permissions to the zm.conf file to allow web account to access it.
chgrp -c www-data etczmzm.conf
Step 9: Setup ZoneMinder service
Step 10: Configure Apache
The following commands will setup the default /zm virtual directory and configure
required apache modules.
a2enconf zoneminder a2enmod cgi a2enmod rewrite
Step 11: Edit Timezone in PHP
nano etcphp5apache2php.ini
Search for (Ctrl + w then type Date and press Enter) and change
date.timezone for your time zone. Don’t forget to remove the ; from in front
of date.timezone
Date ; Defines the default timezone used by the date functions ; http//php.netdate.timezone date.timezone = AmericaNew_York
CTRL+o then to save
CTRL+x to exit
Step 12: Please check the configuration
- Zoneminder 1.32.x
-
-
- Check path of ZM_PATH in ‘/etc/zm/conf.d/zmcustom.conf’ is ZM_PATH_ZMS=/zm/cgi-bin/nph-zms
-
- ::
-
cat /etc/zm/conf.d/zmcustom.conf
-
Check config of /etc/apache2/conf-enabled/zoneminder.conf has the same ScriptAlias /zm/cgi-bin that is configured
in ZM_PATH. The part /nph-zms has to be left out of the ScriptAlias
-
Step 13: Start ZoneMinder
Reload Apache to enable your changes and then start ZoneMinder.
systemctl reload apache2 systemctl start zoneminder
Step 14: Making sure ZoneMinder works
-
Open up a browser and go to — should bring up ZoneMinder Console
-
(Optional API Check)Open up a tab in the same browser and go to
Congratulations Your installation is complete
Configuration Apis¶
The APIs allow you to access all the configuration parameters of ZM that you typically set inside the web console.
This returns the full list of configuration parameters:
curl -XGET http//serverzmapiconfigs.json
Each configuration parameter has an Id, Name, Value and other fields. Chances are you are likely only going to focus on these 3.
The edit function of the Configs API is a little quirky at the moment. Its format deviates from the usual edit flow of other APIs. This will be fixed, eventually. For now, to change the “Value” of ZM_X10_HOUSE_CODE from A to B:
curl -XPUT http//serverzmapiconfigseditZM_X10_HOUSE_CODE.json -d "Config=B"
To validate changes have been made:
sudo service zoneminder stop
NFS Client installieren und konfigurieren
sudo apt-get install nfs-client nfs-common
sudo modprobe nfs
sudo su - echo NFS | tee -a /etc/modules exit
sudo cat /etc/modules
# /etc/modules: kernel modules to load at boot time. # # This file contains the names of kernel modules that should be loaded # at boot time, one per line. Lines beginning with "#" are ignored. NFS
sudo cp /etc/idmapd.conf /etc/idmapd.conf_orig sudo vi /etc/idmapd.conf
Verbosity = 0 Pipefs-Directory = /run/rpc_pipefs # set your own domain here, if it differs from FQDN minus hostname Domain = localdomain Nobody-User = nobody Nobody-Group = nogroup
ZoneMinder event storage
sudo vi /etc/systemd/system/var-cache-zoneminder-events.mount
# systemd NFS mount for ZoneMinder event storage Description=NFS mount for ZoneMinder event storage After=network.target Before=zoneminder What=192.168.1.5:/volume1/ZoneMinder Where=/var/cache/zoneminder/events Type=nfs WantedBy=multi-user.target
sudo systemctl enable var-cache-zoneminder-events.mount sudo systemctl start var-cache-zoneminder-events.mount sudo systemctl status var-cache-zoneminder-events.mount
ZoneMinder cache storage
sudo vi /etc/systemd/system/var-cache-zoneminder-cache.mount
# systemd NFS mount for ZoneMinder cache storage Description=NFS mount for ZoneMinder cache storage After=network.target Before=zoneminder What=192.168.1.5:/volume1/ZoneMinder Where=/var/cache/zoneminder/cache Type=nfs WantedBy=multi-user.target
sudo systemctl enable var-cache-zoneminder-cache.mount sudo systemctl start var-cache-zoneminder-cache.mount sudo systemctl status var-cache-zoneminder-cache.mount
ZoneMinder images storage
sudo vi /etc/systemd/system/var-cache-zoneminder-images.mount
# systemd NFS mount for ZoneMinder images storage Description=NFS mount for ZoneMinder images storage After=network.target Before=zoneminder What=192.168.1.5:/volume1/ZoneMinder Where=/var/cache/zoneminder/images Type=nfs WantedBy=multi-user.target
sudo systemctl enable var-cache-zoneminder-images.mount sudo systemctl start var-cache-zoneminder-images.mount sudo systemctl status var-cache-zoneminder-images.mount
ZoneMinder temp storage
sudo vi /etc/systemd/system/var-cache-zoneminder-temp.mount
# systemd NFS mount for ZoneMinder temp storage Description=NFS mount for ZoneMinder temp storage After=network.target Before=zoneminder What=192.168.1.5:/volume1/ZoneMinder Where=/var/cache/zoneminder/temp Type=nfs WantedBy=multi-user.target
sudo systemctl enable var-cache-zoneminder-temp.mount sudo systemctl start var-cache-zoneminder-temp.mount sudo systemctl status var-cache-zoneminder-temp.mount
sudo init 6
Misc Tab¶
- Event Prefix
- By default events are named ‘Event-<event id>’, however you are free to rename them individually as you wish. This option lets you modify the event prefix, the ‘Event-‘ part, to be a value of your choice so that events are named differently as they are generated. This allows you to name events according to which monitor generated them.
- Section Length
- This specifies the length (in seconds) of any fixed length events produced when the monitor function is ‘Record’ or ‘Mocord’. Otherwise it is ignored. This should not be so long that events are difficult to navigate nor so short that too many events are generated. A length of between 300 and 900 seconds I recommended.
- Frame Skip
- This setting also applies only to the ‘Record’ or ‘Mocord’ functions and specifies how many frames should be skipped in the recorded events. The default setting of zero results in every captured frame being saved. Using a value of one would mean that one frame is skipped between each saved, two means that two frames are skipped between each saved frame etc. An alternate way of thinking is that one in every ‘Frame Skip + 1’ frames is saved. The point of this is to ensure that saved events do not take up too much space unnecessarily whilst still allowing the camera to capture at a fairly high frame rate. The alternate approach is to limit the capture frame rate which will obviously affect the rate at which frames are saved.
- FPS Report Interval
- How often the current performance in terms of Frames Per Second is output to the system log. Not used in any functional way so set it to maybe 1000 for now. If you watch /var/log/messages (normally) you will see this value being emitted at the frequency you specify both for video capture and processing.
- Default Scale
- If your monitor has been defined with a particularly large or small image size then you can choose a default scale here with which to view the monitor so it is easier or more visible from the web interface.
- Web Colour
- Some elements of ZoneMinder now use colours to identify monitors on certain views. You can select which colour is used for each monitor here. Any specification that is valid for HTML colours is valid here, e.g. ‘red’ or ‘#ff0000’. A small swatch next to the input box displays the colour you have chosen.
- Embed EXIF data into image:
-
Embeds EXIF data into each jpeg frame
Todo
what about mp4s?
Zoneminder Multi Server on Ubuntu
10MAY18 — Tested this procedure with Ubuntu Bionic 18.04 with Zoneminder 1.30.4, Mariadb, Apache2 and PHP 7.2 installed per the WIKI instructions with the shell script.
For this procedure my servers were:
Name — u2 IP address 192.168.50.2 This is the storage and database server
Name — u3 IP address 192.168.50.3 This is the remote zoneminder server
It is possible to use a separate database server and a seperate storage server. Your storage server does need to have a Linux file system on it as Zoneminder uses symbolic links and a Windows (NTFS, FAT32) does not know about symbolic links. You can also use Samba to mount the storage drive but this is written to use NFS.
I use Putty from a Windows PC to connect to the servers as I can copy the commands from this web page and paste them into Putty. This is the easy way for me!
Database and Storage Server
Stop the Zoneminder service
service zoneminder stop
Edit the my.conf. Change bind-address to: bind-address = 0.0.0.0
nano /etc/mysql/my.cnf
Ctrl+o Enter to save
CTRL+x to exit
Restart MySQL
systemctl restart mysql
Grant remote user access (Note: for additional remote servers add them using their IP address)
mysql -uroot -p -e "grant all on zm.* to 'zmuser'@192.168.50.2 identified by 'zmpass';"
mysql -uroot -p -e "grant all on zm.* to 'zmuser'@192.168.50.3 identified by 'zmpass';"
Install the NFS server
apt install nfs-kernel-server
Add the export directory
nano /etc/exports
Add to the end of the file (Note: for additional remote servers add additional lines using their IP address)
/var/cache/zoneminder/events 192.168.50.3(rw,sync,no_subtree_check)
Ctrl+o Enter to save
CTRL+x to exit
Restart the NFS server
systemctl restart nfs-kernel-server
Edit the Zoneminder config file
nano /etc/zm/zm.conf
Change these two lines
ZM_DB_HOST=192.168.50.2
ZM_SERVER_HOST=u2
Ctrl+o Enter to save
CTRL+x to exit
Start Zoneminder service
service zoneminder start
Local Zoneminder Server(s)
If you have more than one remote server repeat this procedure on each one adjusting the host name for each.
Stop Zoneminder
service zoneminder stop
Edit the Zoneminder config file
nano /etc/zm/zm.conf
Change these two lines
ZM_DB_HOST=192.168.50.2
ZM_SERVER_HOST=u3
Ctrl+o Enter to save
CTRL+x to exit
Install NFS client
apt install nfs-client
modprobe nfs
echo NFS | tee -a /etc/modules
Create a systemd file for the mount
nano /etc/systemd/system/var-cache-zoneminder-events.mount
Copy and paste everything between the lines into the systemd file
# systemd mount unit for ZoneMinder event storage Description=systemd mount unit for ZoneMinder event storage After=network.target Before=zoneminder What=192.168.50.2:/var/cache/zoneminder/events Where=/var/cache/zoneminder/events Type=nfs WantedBy=multi-user.target
Ctrl+o Enter to save
CTRL+x to exit
Save and start the mount
systemctl enable var-cache-zoneminder-events.mount
systemctl start var-cache-zoneminder-events.mount
Start the Zoneminder service
service zoneminder start
In a web browser open Zoneminder on one of the servers. (Note: you may want to check all your servers to insure Zoneminder is started on each. You may have to reboot each server to get Zoneminder to start)
Click on Options — Servers — Add New Server
In the Name block add a name of one of your servers. In my example the first server name is u2.
In the Hostname block enter the IP address of the first server. In my example it is 192.168.50.2
Click Save
Add the rest of your servers in the same way. Close the Options window when your servers have been added.
Storage and Server APIs¶
ZoneMinder introduced many new options that allowed you to configure multiserver/multistorage configurations. While a part of this was available in previous versions, a lot of rework was done as part of ZM 1.31 and 1.32. As part of that work, a lot of new and useful APIs were added. Some of these are part of ZM 1.32 and others will be part of ZM 1.32.3 (of course, if you build from master, you can access them right away, or wait till a stable release is out.
This returns storage data for my single server install. If you are using multi-storage, you’ll see many such “Storage” entries, one for each storage defined:
curl http//serverzmapistorage.json
Returns:
{ "storage" { "Storage" { "Id" "0", "Path" "\/var\/cache\/zoneminder\/events", "Name" "Default", "Type" "local", "Url" null, "DiskSpace" "364705447651", "Scheme" "Medium", "ServerId" null, "DoDelete" true } } }
“DiskSpace” is the disk used in bytes. While this doesn’t return disk space data as rich as , it is much more efficient.
Similarly,
curl http//serverzmapiservers.json
Returns:
{ "servers" { "Server" { "Id" "1", "Name" "server1", "Hostname" "server1.mydomain.com", "State_Id" null, "Status" "Running", "CpuLoad" "0.9", "TotalMem" "6186237952", "FreeMem" "156102656", "TotalSwap" "536866816", "FreeSwap" "525697024", "zmstats" false, "zmaudit" false, "zmtrigger" false } } }
Streaming Interface¶
Developers working on their application often ask if there is an “API” to receive live streams, or recorded event streams.
It is possible to stream both live and recorded streams. This isn’t strictly an “API” per-se (that is, it is not integrated
into the Cake PHP based API layer discussed here) and also why we’ve used the term “Interface” instead of an “API”.
Live Streams
What you need to know is that if you want to display “live streams”, ZoneMinder sends you streaming JPEG images (MJPEG)
which can easily be rendered in a browser using an tag.
For example:
<img src="https://yourserver/zm/cgi-bin/nph-zms?scale=50&width=640p&height=480px&mode=jpeg&maxfps=5&buffer=1000&&monitor=1&auth=b54a589e09f330498f4ae2203&connkey=36139" />
will display a live feed from monitor id 1, scaled down by 50% in quality and resized to 640x480px.
- This assumes is your CGI_BIN path. Change it to what is correct in your system
- The “auth” token you see above is required if you use ZoneMinder authentication. To understand how to get the auth token, please read the “Login, Logout & API security” section below.
- The “connkey” parameter is essentially a random number which uniquely identifies a stream. If you don’t specify a connkey, ZM will generate its own. It is recommended to generate a connkey because you can then use it to “control” the stream (pause/resume etc.)
- Instead of dealing with the “auth” token, you can also use where “username” and “password” are your ZoneMinder username and password respectively. Note that this is not recommended because you are transmitting them in a URL and even if you use HTTPS, they may show up in web server logs.
PTZ on live streams
PTZ commands are pretty cryptic in ZoneMinder. This is not meant to be an exhaustive guide, but just something to whet your appetite:
Lets assume you have a monitor, with ID=6. Let’s further assume you want to pan it left.
You’d need to send a:
command to with the following data payload in the command (NOT in the URL)
Obviously, if you are using authentication, you need to be logged in for this to work.
Like I said, at this stage, this is only meant to get you started. Explore the ZoneMinder code and use “Inspect source” as you use PTZ commands in the ZoneMinder source code.
control_functions.php is a great place to start.
Pre-recorded (past event) streams
Similar to live playback, if you have chosen to store events in JPEG mode, you can play it back using:
<img src="https://yourserver/zm/cgi-bin/nph-zms?mode=jpeg&frame=1&replay=none&source=event&event=293820&connkey=77493&auth=b54a58f5f4ae2203" />
- This assumes is your CGI_BIN path. Change it to what is correct in your system
- This will playback event 293820, starting from frame 1 as an MJPEG stream
- Like before, you can add more parameters like etc.
- auth and connkey have the same meaning as before, and yes, you can replace auth by as before and the same security concerns cited above apply.
If instead, you have chosen to use the MP4 (Video) storage mode for events, you can directly play back the saved video file:
<video src="https://yourserver/zm/index.php?view=view_video&eid=294690&auth=33f3d558af84cf08" type="video/mp4"></video>
This will play back the video recording for event 294690
Storage and Server APIs¶
ZoneMinder introduced many new options that allowed you to configure multiserver/multistorage configurations. While a part of this was available in previous versions, a lot of rework was done as part of ZM 1.31 and 1.32. As part of that work, a lot of new and useful APIs were added. Some of these are part of ZM 1.32 and others will be part of ZM 1.32.3 (of course, if you build from master, you can access them right away, or wait till a stable release is out.
This returns storage data for my single server install. If you are using multi-storage, you’ll see many such “Storage” entries, one for each storage defined:
curl http//serverzmapistorage.json
Returns:
{ "storage" { "Storage" { "Id" "0", "Path" "\/var\/cache\/zoneminder\/events", "Name" "Default", "Type" "local", "Url" null, "DiskSpace" "364705447651", "Scheme" "Medium", "ServerId" null, "DoDelete" true } } }
“DiskSpace” is the disk used in bytes. While this doesn’t return disk space data as rich as , it is much more efficient.
Similarly,
curl http//serverzmapiservers.json
Returns:
{ "servers" { "Server" { "Id" "1", "Name" "server1", "Hostname" "server1.mydomain.com", "State_Id" null, "Status" "Running", "CpuLoad" "0.9", "TotalMem" "6186237952", "FreeMem" "156102656", "TotalSwap" "536866816", "FreeSwap" "525697024", "zmstats" false, "zmaudit" false, "zmtrigger" false } } }
MySQL installieren
sudo apt-get install mysql-server sudo mysql
mysql> SHOW databases; +--------------------+ | Database | +--------------------+ | information_schema | | mysql | | performance_schema | | sys | +--------------------+ 4 rows in set (0.00 sec) mysql> exit
Standardmäßig hat MySQL nur den Benutzer root. Mit diesem Benutzer kann man sich an der Datenbank anmelden, wenn man als root auf dem Linux Betriebssystem den Befehl mysql ausführt. Eine Passworteingabe ist nicht nötig.
Es ist empfehlenswert einen weiteren Benutzer anzulegen, der sich per Passwort verbinden kann. So kann beispielsweise über ein PHP Skript etc. auf die Datenbank zugegriffen werden. Der Benutzer kann folgendermaßen angelegt werden:
sudo mysql -e "CREATE USER 'mysqluser'@'localhost' IDENTIFIED BY 'mysqlpassword';" sudo mysql -e "GRANT ALL PRIVILEGES ON * . * TO 'mysqluser'@'localhost' WITH GRANT OPTION;" sudo mysql -e "FLUSH PRIVILEGES;" mysql -u mysqluser -p exit
Datenbank Adminbenutzer: mysqluser Kennwort: mysqlpassword
Understanding key security¶
- Version 1.0 uses an MD5 hash to generate the credentials. The hash is computed over your secret key (if available), username, password and some time parameters (along with remote IP if enabled). This is not a secure/recommended hashing mechanism. If your auth hash is compromised, an attacker will be able to use your hash till it expires. To avoid this, you could disable the user in ZoneMinder. Furthermore, enabling remote IP () requires that you issue future requests from the same IP that generated the tokens. While this may be considered an additional layer for security, this can cause issues with mobile devices.
- Version 2.0 uses a different approach. The hash is a simple base64 encoded form of “claims”, but signed with your secret key. Consider for example, the following access key:
eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpc3MiOiJab25lTWluZGVyIiwiaWF0IjoxNTU3OTQwNzUyLCJleHAiOjE1NTc5NDQzNTIsInVzZXIiOiJhZG1pbiIsInR5cGUiOiJhY2Nlc3MifQ.-5VOcpw3cFHiSTN5zfGDSrrPyVya1M8_2Anh5u6eNlI
If you were to use any JWT token verifier it can easily decode that token and will show:
{ "iss" "ZoneMinder", "iat" 1557940752, "exp" 1557944352, "user" "admin", "type" "access" } Invalid Signature
Don’t be surprised. JWT tokens, by default, are not meant to be encrypted. It is just an assertion of a claim. It states that the issuer of this token was ZoneMinder,
It was issued at (iat) Wednesday, 2019-05-15 17:19:12 UTC and will expire on (exp) Wednesday, 2019-05-15 18:19:12 UTC. This token claims to be owned by an admin and is an access token. If your token were to be stolen, this information is available to the person who stole it. Note that there are no sensitive details like passwords in this claim.
However, that person will not have your secret key as part of this token and therefore, will NOT be able to create a new JWT token to get, say, a refresh token. They will however, be able to use your access token to access resources just like the auth hash above, till the access token expires (2 hrs). To revoke this token, you don’t need to disable the user. Go to and tap on “Revoke All Access Tokens”. This will invalidate the token immediately (this option will invalidate all tokens for all users, and new ones will need to be generated).
Over time, we will provide you with more fine grained access to these options.
Summarizing good practices:
- Use HTTPS, not HTTP
- If possible, use free services like LetsEncrypt instead of self-signed certificates (sometimes this is not possible)
- Keep your tokens as private as possible, and use them as recommended above
- If you believe your tokens are compromised, revoke them, but also check if your attacker has compromised more than you think (example, they may also have your username/password or access to your system via other exploits, in which case they can regenerate as many tokens/credentials as they want).