mirror of
https://github.com/scottlamb/moonfire-nvr.git
synced 2025-11-20 09:56:07 -05:00
update docs to recommend new Docker setup
and remove the old scripts, to reduce the supported ways of doing things.
This commit is contained in:
243
guide/build.md
Normal file
243
guide/build.md
Normal file
@@ -0,0 +1,243 @@
|
||||
# Building Moonfire NVR
|
||||
|
||||
This document has notes for software developers on building Moonfire NVR from
|
||||
source code for development. If you just want to install precompiled
|
||||
binaries, see the [Docker installation instructions](install.md) instead.
|
||||
|
||||
This document doesn't spell out as many details as the installation
|
||||
instructions. Please ask on Moonfire NVR's [issue
|
||||
tracker](https://github.com/scottlamb/moonfire-nvr/issues) or
|
||||
[mailing list](https://groups.google.com/d/forum/moonfire-nvr-users) when
|
||||
stuck. Please also send pull requests to improve this doc.
|
||||
|
||||
## Downloading
|
||||
|
||||
See the [github page](https://github.com/scottlamb/moonfire-nvr) (in case
|
||||
you're not reading this text there already). You can download the
|
||||
bleeding-edge version from the commandline via git:
|
||||
|
||||
```
|
||||
$ git clone https://github.com/scottlamb/moonfire-nvr.git
|
||||
```
|
||||
|
||||
## Docker builds
|
||||
|
||||
This command should prepare a deployment image for your local machine:
|
||||
|
||||
```
|
||||
$ docker buildx build --load --tag=moonfire-nvr -f docker/Dockerfile .
|
||||
```
|
||||
|
||||
If you want to iterate on code changes, doing a full Docker build from
|
||||
scratch every time will be painfully slow. You will likely find it more
|
||||
helpful to use the `dev` target. This is a self-contained developer environment
|
||||
which you can use from its shell via `docker run` or via something like
|
||||
Visual Studio Code's Docker plugin.
|
||||
|
||||
```
|
||||
$ docker buildx build --load --tag=moonfire-dev --target=dev
|
||||
...
|
||||
$ docker run \
|
||||
--rm --interactive=true --tty \
|
||||
--mount=type=bind,source=$(pwd),destination=/var/lib/moonfire-nvr/src \
|
||||
moonfire-dev
|
||||
```
|
||||
|
||||
The development image overrides cargo's output directory to
|
||||
`/var/lib/moonfire-nvr/target`. (See `~moonfire-nvr/.buildrc`.) This avoids
|
||||
using a bind filesystem for build products, which can be slow on macOS. It
|
||||
also means that if you sometimes compile directly on the host and sometimes
|
||||
within Docker, they don't trip over each other's target directories.
|
||||
directories.
|
||||
|
||||
You can also cross-compile to a different architecture. Adding a
|
||||
`--platform=linux/arm64/v8,linux/arm/v7,linux/amd64` argument will compile
|
||||
Moonfire NVR for all supported platforms. For the `dev` target, this prepares
|
||||
a build which executes on your local architecture and is capable of building
|
||||
a binary for your desired target architecture.
|
||||
|
||||
On the author's macOS machine with Docker desktop 3.0.4, building for
|
||||
multiple platforms at once will initially fail with the following error:
|
||||
|
||||
```
|
||||
$ docker buildx build ... --platform=linux/arm64/v8,linux/arm/v7,linux/amd64
|
||||
[+] Building 0.0s (0/0)
|
||||
error: multiple platforms feature is currently not supported for docker driver. Please switch to a different driver (eg. "docker buildx create --use")
|
||||
```
|
||||
|
||||
Running `docker buildx create --use` once solves this problem, with a couple
|
||||
caveats:
|
||||
|
||||
* you'll need to specify an additional `--load` argument to make builds
|
||||
available to run locally.
|
||||
* the `--load` argument only works for one platform at a time. With multiple
|
||||
platforms, it gives an error like the following:
|
||||
```
|
||||
error: failed to solve: rpc error: code = Unknown desc = docker exporter does not currently support exporting manifest lists
|
||||
```
|
||||
[A comment on docker/buildx issue
|
||||
#59](https://github.com/docker/buildx/issues/59#issuecomment-667548900)
|
||||
suggests a workaround of building all three then using caching to quickly
|
||||
load the one of immediate interest:
|
||||
```
|
||||
$ docker buildx build --platform=linux/arm64/v8,linux/arm/v7,linux/amd64 ...
|
||||
$ docker buildx build --load --platform=arm64/v8 ...
|
||||
```
|
||||
|
||||
Major caveat: something appears to be making `docker buildx build` frequently
|
||||
redo builds rather than reusing cached results. The author is very annoyed by
|
||||
this and would welcome help in understanding this problem...
|
||||
|
||||
## Non-Docker setup
|
||||
|
||||
You may prefer building without Docker on the host. Moonfire NVR should run
|
||||
natively on any Unix-like system. It's been tested on Linux and macOS.
|
||||
(In theory [Windows Subsystem for
|
||||
Linux](https://docs.microsoft.com/en-us/windows/wsl/about) should also work.
|
||||
Please speak up if you try it.)
|
||||
|
||||
On macOS systems native builds may be noticeably faster than using Docker's
|
||||
Linux VM and filesystem overlay.
|
||||
|
||||
To build the server, you will need the following C libraries installed:
|
||||
|
||||
* [ffmpeg](http://ffmpeg.org/) version 2.x or 3.x, including `libavutil`,
|
||||
`libavcodec` (to inspect H.264 frames), and `libavformat` (to connect to RTSP
|
||||
servers and write `.mp4` files).
|
||||
|
||||
Note ffmpeg library versions older than 55.1.101, along with all versions of
|
||||
the competing project [libav](http://libav.org), don't support socket
|
||||
timeouts for RTSP. For reliable reconnections on error, it's strongly
|
||||
recommended to use ffmpeg library versions >= 55.1.101.
|
||||
|
||||
* [SQLite3](https://www.sqlite.org/).
|
||||
|
||||
* [`ncursesw`](https://www.gnu.org/software/ncurses/), the UTF-8 version of
|
||||
the `ncurses` library.
|
||||
|
||||
On recent Ubuntu or Raspbian Linux, the following command will install
|
||||
all non-Rust dependencies:
|
||||
|
||||
```
|
||||
$ sudo apt-get install \
|
||||
build-essential \
|
||||
libavcodec-dev \
|
||||
libavformat-dev \
|
||||
libavutil-dev \
|
||||
libncurses5-dev \
|
||||
libncursesw5-dev \
|
||||
libsqlite3-dev \
|
||||
pkgconf \
|
||||
sqlite3 \
|
||||
tzdata
|
||||
```
|
||||
|
||||
On macOS with [Homebrew](https://brew.sh/) and Xcode installed, try the
|
||||
following command:
|
||||
|
||||
```
|
||||
$ brew install ffmpeg yarn
|
||||
```
|
||||
|
||||
Next, you need Rust 1.45+ and Cargo. The easiest way to install them is by
|
||||
following the instructions at [rustup.rs](https://www.rustup.rs/).
|
||||
|
||||
Finally, building the UI requires [yarn](https://yarnpkg.com/en/). (On macOS,
|
||||
the `brew` command above installs it for you. On Linux, follow yarn's guide.)
|
||||
|
||||
Once prerequisites are installed, you can build the server and find it in
|
||||
`target/release/moonfire-nvr`:
|
||||
|
||||
```
|
||||
$ cargo test
|
||||
$ cargo build --release
|
||||
```
|
||||
|
||||
You can build the UI via `yarn` and find it in the `ui-dist` directory:
|
||||
|
||||
```
|
||||
$ yarn
|
||||
$ yarn build
|
||||
```
|
||||
|
||||
### Running interactively straight from the working copy
|
||||
|
||||
The author finds it convenient for local development to set up symlinks so that
|
||||
the binaries in the working copy will run via just `nvr`:
|
||||
|
||||
```
|
||||
$ sudo mkdir /usr/local/moonfire-nvr
|
||||
$ sudo ln -s `pwd`/ui-dist /usr/local/moonfire-nvr/ui
|
||||
$ sudo mkdir /var/lib/moonfire-nvr
|
||||
$ sudo chown $USER:$USER /var/lib/moonfire-nvr
|
||||
$ ln -s `pwd`/target/release/moonfire-nvr $HOME/bin/moonfire-nvr
|
||||
$ ln -s moonfire-nvr $HOME/bin/nvr
|
||||
$ nvr init
|
||||
$ nvr config
|
||||
$ nvr run
|
||||
```
|
||||
|
||||
(Alternatively, you could symlink to `target/debug/moonfire-nvr` and compile
|
||||
with `cargo build` rather than `cargo build --release`, for a faster build
|
||||
cycle and slower performance.)
|
||||
|
||||
Note this `nvr` is a little different than the `nvr` shell script you create
|
||||
when following the [install instructions](install.md). With that shell wrapper,
|
||||
`nvr run` will create and run a detached Docker container with some extra
|
||||
arguments specified in the script. This `nvr run` will directly run from the
|
||||
terminal, with no extra arguments, until you abort with Ctrl-C. Likewise,
|
||||
some of the shell script's subcommands that wrap Docker (`start`, `stop`, and
|
||||
`logs`) have no parallel with this `nvr`.
|
||||
|
||||
## Running as a `systemd` service
|
||||
|
||||
If you want to deploy a non-Docker build on Linux, you may want to use
|
||||
`systemd`. Create `/etc/systemd/system/moonfire-nvr.service`:
|
||||
|
||||
```
|
||||
[Unit]
|
||||
Description=Moonfire NVR
|
||||
After=network-online.target
|
||||
|
||||
[Service]
|
||||
ExecStart=/usr/local/bin/moonfire-nvr run \
|
||||
--db-dir=/var/lib/moonfire-nvr/db \
|
||||
--http-addr=0.0.0.0:8080 \
|
||||
--allow-unauthenticated-permissions='view_video: true'
|
||||
Environment=TZ=:/etc/localtime
|
||||
Environment=MOONFIRE_FORMAT=google-systemd
|
||||
Environment=MOONFIRE_LOG=info
|
||||
Environment=RUST_BACKTRACE=1
|
||||
Type=simple
|
||||
User=moonfire-nvr
|
||||
Nice=-20
|
||||
Restart=on-failure
|
||||
CPUAccounting=true
|
||||
MemoryAccounting=true
|
||||
BlockIOAccounting=true
|
||||
|
||||
[Install]
|
||||
WantedBy=multi-user.target
|
||||
```
|
||||
|
||||
Note that the arguments used here are insecure. You can change that via
|
||||
replacing the `--allow-unauthenticated-permissions` argument here as
|
||||
described in [Securing Moonfire NVR and exposing it to the
|
||||
Internet](secure.md).
|
||||
|
||||
Some handy commands:
|
||||
|
||||
```
|
||||
$ sudo systemctl daemon-reload # reload configuration files
|
||||
$ sudo systemctl start moonfire-nvr # start the service now
|
||||
$ sudo systemctl stop moonfire-nvr # stop the service now (but don't wait for it finish stopping)
|
||||
$ sudo systemctl status moonfire-nvr # show if the service is running and the last few log lines
|
||||
$ sudo systemctl enable moonfire-nvr # start the service on boot
|
||||
$ sudo systemctl disable moonfire-nvr # don't start the service on boot
|
||||
$ sudo journalctl --unit=moonfire-nvr --since='-5 min' --follow # look at recent logs and await more
|
||||
```
|
||||
|
||||
See the [systemd](http://www.freedesktop.org/wiki/Software/systemd/)
|
||||
documentation for more information. The [manual
|
||||
pages](http://www.freedesktop.org/software/systemd/man/) for `systemd.service`
|
||||
and `systemctl` may be of particular interest.
|
||||
@@ -1,130 +0,0 @@
|
||||
# Building and installing Moonfire NVR manually
|
||||
|
||||
This guide will walk you through building and installing Moonfire NVR manually.
|
||||
You should have already downloaded the source code as mentioned in
|
||||
[install.md](install.md), and after completing these instructions you should go
|
||||
back to that page to complete configuration.
|
||||
|
||||
## Building from source
|
||||
|
||||
There are no binary packages of Moonfire NVR available yet, so it must be built
|
||||
from source.
|
||||
|
||||
Moonfire NVR is written in the [Rust Programming
|
||||
Language](https://www.rust-lang.org/en-US/). In the long term, I expect this
|
||||
will result in a more secure, full-featured, easy-to-install software.
|
||||
|
||||
You will need the following C libraries installed:
|
||||
|
||||
* [ffmpeg](http://ffmpeg.org/) version 2.x or 3.x, including `libavutil`,
|
||||
`libavcodec` (to inspect H.264 frames), and `libavformat` (to connect to RTSP
|
||||
servers and write `.mp4` files).
|
||||
|
||||
Note ffmpeg library versions older than 55.1.101, along with all versions of
|
||||
the competing project [libav](http://libav.org), don't support socket
|
||||
timeouts for RTSP. For reliable reconnections on error, it's strongly
|
||||
recommended to use ffmpeg library versions >= 55.1.101.
|
||||
|
||||
* [SQLite3](https://www.sqlite.org/).
|
||||
|
||||
* [`ncursesw`](https://www.gnu.org/software/ncurses/), the UTF-8 version of
|
||||
the `ncurses` library.
|
||||
|
||||
On recent Ubuntu or Raspbian, the following command will install
|
||||
all non-Rust dependencies:
|
||||
|
||||
```
|
||||
$ sudo apt-get install \
|
||||
build-essential \
|
||||
libavcodec-dev \
|
||||
libavformat-dev \
|
||||
libavutil-dev \
|
||||
libncurses5-dev \
|
||||
libncursesw5-dev \
|
||||
libsqlite3-dev \
|
||||
pkgconf \
|
||||
sqlite3 \
|
||||
tzdata
|
||||
```
|
||||
|
||||
Next, you need Rust 1.45+ and Cargo. The easiest way to install them is by
|
||||
following the instructions at [rustup.rs](https://www.rustup.rs/).
|
||||
|
||||
Finally, building the UI requires [yarn](https://yarnpkg.com/en/).
|
||||
|
||||
Once prerequisites are installed, Moonfire NVR can be built as follows:
|
||||
|
||||
```
|
||||
$ yarn
|
||||
$ yarn build
|
||||
$ cargo test
|
||||
$ cargo build --release
|
||||
$ sudo install -m 755 target/release/moonfire-nvr /usr/local/bin
|
||||
$ sudo mkdir /usr/local/lib/moonfire-nvr
|
||||
$ sudo cp -R ui-dist /usr/local/lib/moonfire-nvr/ui
|
||||
```
|
||||
|
||||
## Creating the user and database
|
||||
|
||||
You can create Moonfire NVR's dedicated user and SQLite database with the
|
||||
following commands:
|
||||
|
||||
```
|
||||
$ sudo useradd --system --user-group --create-home --home /var/lib/moonfire-nvr moonfire-nvr
|
||||
$ sudo -u moonfire-nvr -H sh -c 'cd && mkdir --mode=700 db'
|
||||
$ sudo -u moonfire-nvr moonfire-nvr init
|
||||
```
|
||||
|
||||
## System Service
|
||||
|
||||
Moonfire NVR can be run as a systemd service. Create
|
||||
`/etc/systemd/system/moonfire-nvr.service`:
|
||||
|
||||
```
|
||||
[Unit]
|
||||
Description=Moonfire NVR
|
||||
After=network-online.target
|
||||
|
||||
[Service]
|
||||
ExecStart=/usr/local/bin/moonfire-nvr run \
|
||||
--db-dir=/var/lib/moonfire-nvr/db \
|
||||
--http-addr=0.0.0.0:8080 \
|
||||
--allow-unauthenticated-permissions='view_video: true'
|
||||
Environment=TZ=:/etc/localtime
|
||||
Environment=MOONFIRE_FORMAT=google-systemd
|
||||
Environment=MOONFIRE_LOG=info
|
||||
Environment=RUST_BACKTRACE=1
|
||||
Type=simple
|
||||
User=moonfire-nvr
|
||||
Nice=-20
|
||||
Restart=on-failure
|
||||
CPUAccounting=true
|
||||
MemoryAccounting=true
|
||||
BlockIOAccounting=true
|
||||
|
||||
[Install]
|
||||
WantedBy=multi-user.target
|
||||
```
|
||||
|
||||
Note that the HTTP port currently has no authentication, encryption, or
|
||||
logging; it should not be directly exposed to the Internet.
|
||||
|
||||
Tell `systemd` to look for the new file:
|
||||
|
||||
```
|
||||
$ sudo systemctl daemon-reload
|
||||
```
|
||||
|
||||
See the [systemd](http://www.freedesktop.org/wiki/Software/systemd/)
|
||||
documentation for more information. The [manual
|
||||
pages](http://www.freedesktop.org/software/systemd/man/) for `systemd.service`
|
||||
and `systemctl` may be of particular interest.
|
||||
|
||||
Don't enable or start the service just yet; you'll need to do some more
|
||||
configuration first.
|
||||
|
||||
## Completing installation
|
||||
|
||||
After the steps on this page, go back to [Downloading, installing, and
|
||||
configuring Moonfire NVR](install.md) to set up the sample file directory and
|
||||
configure the system.
|
||||
@@ -1,104 +0,0 @@
|
||||
# Building and installing Moonfire NVR using provided scripts
|
||||
|
||||
This guide will walk you through building and installing Moonfire NVR with the
|
||||
provided scripts. You should have already downloaded the source code as
|
||||
mentioned in [install.md](install.md), and after completing these instructions
|
||||
you should go back to that page to complete configuration.
|
||||
|
||||
There are no binary packages of Moonfire NVR available yet, so it must be built
|
||||
from source. This is made easy using a few scripts that will do the job for you
|
||||
unless you have very a different operating system. The scripts are written and
|
||||
tested under ubuntu and raspbian but should not be hard to modify if necessary.
|
||||
|
||||
## Setting everything up
|
||||
|
||||
Start by executing the setup script:
|
||||
|
||||
$ cd moonfire-nvr
|
||||
$ scripts/setup-ubuntu.sh
|
||||
|
||||
If this is the very first time you run this script, a file named `prep.config`
|
||||
will be created and the script will stop. This file is where you will set
|
||||
or change variables that describe the Moonfire installation you want. The
|
||||
initial execution will put default values in this value, but only for the
|
||||
most commonly changed variables. For a full list of variables, see below.
|
||||
|
||||
Once you modify this file (if desired), you run the setup script again. This
|
||||
time it will use the values in the file and proceed with the setup.
|
||||
The script will download and install any pre-requisites. Watch carefully for
|
||||
error messages. It may be you have conflicting installations. If that is the
|
||||
case you must either resolve those first, or go the manual route.
|
||||
|
||||
The script may be given the `-f` option. If you do, you are telling the script
|
||||
that you do not want any existing installation of ffmpeg to be overwritten with
|
||||
a newer one. This could be important to you. If you do use it, and the version
|
||||
you have installed is not compatible with Moonfire, you will be told through
|
||||
a message. If you have no ffmpeg installed, the option is effectively ignored
|
||||
and the necessary version of ffmpeg will be installed.
|
||||
|
||||
The setup script should only need to be run once (after `prep.config` has been
|
||||
created), although if you do a re-install of Moonfire, in particular a much
|
||||
newer version, it is a good idea to run it again as requirements and pre-requisites
|
||||
may have changed. Running the script multiple times should not have any negative effects.
|
||||
|
||||
*Note:* It is quite possible that during the running of the setup script,
|
||||
in particular during the building of libavutil you will see several compiler
|
||||
warnings. This, while undesirable, is a direct result of the original
|
||||
developers not cleaning up the cause(s) of these warnings. They are, however,
|
||||
just warnings and will not affect correct functioning of Moonfire.
|
||||
|
||||
Once the setup is complete, two steps remain: building and then installing.
|
||||
There is a script for each of these scenarios, but since generally you would
|
||||
want to install after a succesul build, the build script automatically invokes
|
||||
the install script, unless specifically told not to.
|
||||
|
||||
## Building
|
||||
|
||||
The build script is involved like this:
|
||||
|
||||
$ scripts/build.sh
|
||||
|
||||
This script will perform all steps necessary to build a complete Moonfire
|
||||
setup. If there are no build errors, this script will then automatically
|
||||
invoke the install script (see below).
|
||||
|
||||
There are two options you may pass to this script. The first is `-B` which
|
||||
means "build only". In other words, this will stop the automatic invocation
|
||||
of the install script. The other option available is `-t` and causes the
|
||||
script to ignore the results of any tests. In other words, even if tests
|
||||
fail, the build phase will be considered successful. This can occasionally
|
||||
be useful if you are doing development, and have temporarily broken one
|
||||
or more test, but want to proceed anyway.
|
||||
|
||||
## Installing
|
||||
|
||||
The install step is performed by the script that can be manually invoked
|
||||
like this:
|
||||
|
||||
$ scripts/install.sh
|
||||
|
||||
This script will copy various files resulting from the build to the correct
|
||||
locations. It will also create a "service configuration" for systemctl that
|
||||
can be used to control Moonfire. This service configuration can be prevented
|
||||
by using the `-s` option to this script. It will also prevent the automatic
|
||||
start of this configuration.
|
||||
|
||||
## Configuration variables
|
||||
|
||||
Although not all listed in the default `prep.config` file, these are the
|
||||
available configuration variable and their defaults.
|
||||
|
||||
NVR_USER=moonfire-nvr
|
||||
NVR_PORT=8080
|
||||
NVR_HOME_BASE=/var/lib
|
||||
DB_NAME=db
|
||||
DB_DIR=$NVR_HOME/$DB_NAME
|
||||
SERVICE_NAME=moonfire-nvr
|
||||
SERVICE_DESC="Moonfire NVR"
|
||||
SERVICE_BIN=/usr/local/bin/$SERVICE_NAME
|
||||
|
||||
## Completing installation
|
||||
|
||||
After the steps on this page, go back to [Downloading, installing, and
|
||||
configuring Moonfire NVR](install.md) to set up the sample file directory and
|
||||
configure the system.
|
||||
160
guide/install.md
160
guide/install.md
@@ -1,47 +1,109 @@
|
||||
# Downloading, installing, and configuring Moonfire NVR
|
||||
# Downloading, installing, and configuring Moonfire NVR with Docker
|
||||
|
||||
This document describes how to download, install, and configure Moonfire NVR
|
||||
on a Debian-based Linux system (such as Ubuntu or Raspbian).
|
||||
via the prebuilt Docker images available for x86-64, arm64, and arm. If you
|
||||
instead want to build Moonfire NVR yourself, see the [Build
|
||||
instructions](build.md).
|
||||
|
||||
(In principle, Moonfire NVR supports any POSIX-compliant system, and the main
|
||||
author uses macOS for development, but the documentation and scripts are
|
||||
intended for Linux.)
|
||||
|
||||
## Downloading
|
||||
|
||||
See the [github page](https://github.com/scottlamb/moonfire-nvr) (in case
|
||||
you're not reading this text there already). You can download the
|
||||
bleeding-edge version from the commandline via git:
|
||||
First, install [Docker](https://www.docker.com/) if you haven't already,
|
||||
and verify you can run the container.
|
||||
|
||||
```
|
||||
$ git clone https://github.com/scottlamb/moonfire-nvr.git
|
||||
$ docker run --rm -it scottlamb/moonfire-nvr:latest
|
||||
moonfire-nvr 0.6.0
|
||||
security camera network video recorder
|
||||
|
||||
USAGE:
|
||||
moonfire-nvr <SUBCOMMAND>
|
||||
|
||||
...
|
||||
```
|
||||
|
||||
## Building and installing from source
|
||||
|
||||
There are no binary packages of Moonfire NVR available yet, so it must be built
|
||||
from source. To do so, you can follow either of two paths:
|
||||
|
||||
* Scripted: You will run some shell scripts (after preparing one or two files,
|
||||
and will be completely done. This is by far the easiest option, in
|
||||
particular for first time builders/installers. Read more in [Scripted
|
||||
Installation](install-scripted.md).
|
||||
* Manual: see [instructions](install-manual.md).
|
||||
Next, you'll need to set up your filesystem and the Monfire NVR user.
|
||||
|
||||
Moonfire NVR keeps two kinds of state:
|
||||
|
||||
* a SQLite database, typically <1 GiB. It should be stored on flash if
|
||||
available.
|
||||
* the "sample file directories", which hold the actual samples/frames of
|
||||
H.264 video. These should be quite large and are typically stored on hard
|
||||
drives.
|
||||
* a SQLite database, typically <1 GiB. It should be stored on flash if
|
||||
available. In most cases your root filesystem is on flash, so the
|
||||
default location of `/var/lib/moonfire-nvr/db` will be fine.
|
||||
* the "sample file directories", which hold the actual samples/frames of
|
||||
H.264 video. These should be quite large and are typically stored on hard
|
||||
drives. More below.
|
||||
|
||||
(See [schema.md](schema.md) for more information.)
|
||||
|
||||
By now Moonfire NVR's dedicated user and database should have been created for
|
||||
you. Next you need to create a sample file directory.
|
||||
On most Linux systems, you can create the user as follows:
|
||||
|
||||
## Dedicated hard drive seutp
|
||||
```
|
||||
$ sudo useradd --user-group --create-home --home /var/lib/moonfire-nvr moonfire-nvr
|
||||
```
|
||||
|
||||
and create a script called `nvr` to run Moonfire NVR as the intended host user.
|
||||
This script supports running Moonfire NVR's various administrative commands interactively
|
||||
and managing a long-lived Docker container for its web interface.
|
||||
|
||||
As you set up this script, adjust the `tz` variable as appropriate for your
|
||||
time zone.
|
||||
|
||||
```
|
||||
sudo sh -c 'cat > /usr/local/bin/nvr' <<EOF
|
||||
#!/bin/bash -e
|
||||
|
||||
tz=America/Los_Angeles
|
||||
container_name=moonfire-nvr
|
||||
image_name=scottlamb/moonfire-nvr:latest
|
||||
common_docker_run_args=(
|
||||
--mount=type=bind,source=/etc/localtime,destination=/etc/localtime
|
||||
--mount=type=bind,source=/var/lib/moonfire-nvr,destination=/var/lib/moonfire-nvr
|
||||
--user="$(id -u moonfire-nvr):$(id -g moonfire-nvr)"
|
||||
--env=RUST_BACKTRACE=1
|
||||
--env=TZ=:/etc/localtime
|
||||
)
|
||||
|
||||
case "$1" in
|
||||
run)
|
||||
shift
|
||||
exec docker run \
|
||||
--detach=true \
|
||||
--restart=on-failure \
|
||||
"${common_docker_run_args[@]}" \
|
||||
--publish=8080:8080 \
|
||||
--name="${container_name}" \
|
||||
"${image_name}" \
|
||||
run \
|
||||
--allow-unauthenticated-permissions='view_video: true' \
|
||||
"$@"
|
||||
;;
|
||||
start|stop|logs|rm)
|
||||
exec docker "$@" "${container_name}"
|
||||
;;
|
||||
pull)
|
||||
exec docker pull "${image_name}"
|
||||
;;
|
||||
*)
|
||||
exec docker run \
|
||||
--interactive=true \
|
||||
--tty \
|
||||
--rm \
|
||||
"${common_docker_run_args[@]}" \
|
||||
"${image_name}" \
|
||||
"$@"
|
||||
;;
|
||||
esac
|
||||
EOF
|
||||
sudo chmod a+rx /usr/local/bin/nvr
|
||||
```
|
||||
|
||||
then try it out by initializing the database:
|
||||
|
||||
```
|
||||
$ nvr init
|
||||
```
|
||||
|
||||
This will create a directory `/var/lib/moonfire-nvr/db` with a SQLite3 database
|
||||
within it.
|
||||
|
||||
## Dedicated hard drive setup
|
||||
|
||||
If a dedicated hard drive is available, set up the mount point:
|
||||
|
||||
@@ -67,38 +129,32 @@ $ ls -l /dev/disk/by-uuid
|
||||
|
||||
If you use the `nofail` attribute in `/etc/fstab` as described above, your
|
||||
system will boot successfully even when the hard drive is unavailable (such as
|
||||
when your external USB storage is unmounted). This is convenient, but you
|
||||
likely want to ensure the `moonfire-nvr` service only starts when the mounting
|
||||
is successful. Edit the systemd configuration to do so:
|
||||
when your external USB storage is unmounted). This can be helpful when
|
||||
recovering from problems.
|
||||
|
||||
Add a new `--mount` line to your Docker wrapper script `/usr/local/bin/nvr`
|
||||
to expose this new volume to the Docker container, directly below the other
|
||||
mount lines. It will look similar to this:
|
||||
|
||||
```
|
||||
$ sudo vim /etc/systemd/system/moonfire-nvr.service
|
||||
$ sudo systemctl daemon-reload
|
||||
```
|
||||
|
||||
You'll want to add a line similar to the following to the `[Unit]` section of
|
||||
the file:
|
||||
|
||||
```
|
||||
RequiresMountsFor=/media/nvr
|
||||
--mount=type=bind,source=/media/nvr/sample,destination=/media/nvr/sample
|
||||
```
|
||||
|
||||
## Completing configuration through the UI
|
||||
|
||||
Once your system is set up, it's time to initialize an empty database,
|
||||
and add the cameras and sample directories to moonfire. You can do this
|
||||
Once your system is set up, it's time to initialize an empty database
|
||||
and add the cameras and sample directories. You can do this
|
||||
by using the `moonfire-nvr` binary's text-based configuration tool.
|
||||
|
||||
```
|
||||
$ sudo -u moonfire-nvr moonfire-nvr init # Initialize empty db
|
||||
$ sudo -u moonfire-nvr moonfire-nvr config 2>debug-log # Configure cameras and storage
|
||||
$ nvr config 2>debug-log
|
||||
```
|
||||
|
||||
In the user interface,
|
||||
|
||||
1. add your sample file dir(s) under "Directories and retention".
|
||||
If you used a dedicated hard drive, use the directory you precreated
|
||||
(`/media/surveillance/sample`). Otherwise, try
|
||||
(eg `/media/nvr/sample`). Otherwise, try
|
||||
`/var/lib/moonfire-nvr/sample`. Moonfire NVR will create the directory as
|
||||
long as it has the required permissions on the parent directory.
|
||||
|
||||
@@ -154,14 +210,16 @@ out, particularly if the machine it's running on is behind a home router's
|
||||
firewall. You might not; in that case read through [secure the
|
||||
system](secure.md) first.
|
||||
|
||||
The following commands will start Moonfire NVR and enable it for following
|
||||
boots, respectively:
|
||||
This command will start a detached Docker container for the web interface.
|
||||
It will automatically restart when your system does.
|
||||
|
||||
```
|
||||
$ sudo systemctl start moonfire-nvr
|
||||
$ sudo systemctl enable moonfire-nvr
|
||||
$ nvr run
|
||||
```
|
||||
|
||||
You can temporarily disable the service via `nvr stop` and restart it later via
|
||||
`nvr start`.
|
||||
|
||||
The HTTP interface is accessible on port 8080; if your web browser is running
|
||||
on the same machine, you can access it at
|
||||
[http://localhost:8080/](http://localhost:8080/).
|
||||
|
||||
@@ -53,16 +53,10 @@ SQLite database:
|
||||
no longer in the dangerous mode.
|
||||
|
||||
Next ensure Moonfire NVR is not running and does not automatically restart if
|
||||
the system is rebooted during the upgrade. If you are using systemd with the
|
||||
service name `moonfire-nvr`, you can do this as follows:
|
||||
the system is rebooted during the upgrade. If you followed the Docker
|
||||
instructions, you can do this as follows:
|
||||
|
||||
$ sudo systemctl stop moonfire-nvr
|
||||
$ sudo systemctl disable moonfire-nvr
|
||||
|
||||
The service takes a moment to shut down; wait until the following command
|
||||
reports that it is not running:
|
||||
|
||||
$ sudo systemctl status moonfire-nvr
|
||||
$ nvr stop
|
||||
|
||||
Then back up your SQLite database. If you are using the default path, you can
|
||||
do so as follows:
|
||||
@@ -83,27 +77,34 @@ manual for write-ahead logging](https://www.sqlite.org/wal.html):
|
||||
> 3.11.0 (2016-02-15), WAL mode works as efficiently with large transactions
|
||||
> as does rollback mode.
|
||||
|
||||
Run the upgrade procedure using the new software binary (here referred to as
|
||||
`new-moonfire-nvr`; if you are installing from source, you may find it as
|
||||
`target/release/moonfire-nvr`).
|
||||
Run the upgrade procedure using the new software binary.
|
||||
|
||||
$ sudo -u moonfire-nvr new-moonfire-nvr upgrade
|
||||
```
|
||||
$ nvr pull # updates the docker image to the latest binary
|
||||
$ nvr upgrade # runs the upgrade
|
||||
```
|
||||
|
||||
Then run the system in read-only mode to verify correct operation:
|
||||
You can run the system in read-only mode, although you'll find this only
|
||||
works in the "insecure" setup. (Authorization requires writing the database.)
|
||||
|
||||
$ sudo -u moonfire-nvr new-moonfire-nvr run --read-only
|
||||
```
|
||||
$ nvr rm
|
||||
$ nvr run --read-only
|
||||
```
|
||||
|
||||
Go to the web interface and ensure the system is operating correctly. If
|
||||
you detect a problem now, you can copy the old database back over the new one.
|
||||
If you detect a problem after enabling read-write operation, a restore will be
|
||||
you detect a problem now, you can copy the old database back over the new one
|
||||
and edit your `nvr` script to use the corresponding older Docker image. If
|
||||
you detect a problem after enabling read-write operation, a restore will be
|
||||
more complicated.
|
||||
|
||||
Then install the new software to the path expected by your systemd
|
||||
configuration and start it up:
|
||||
Once you're satisfied, restart the system in read-write mode:
|
||||
|
||||
$ sudo install -m 755 new-moonfire-nvr /usr/local/bin/moonfire-nvr
|
||||
$ sudo systemctl enable moonfire-nvr
|
||||
$ sudo systemctl start moonfire-nvr
|
||||
```
|
||||
$ nvr stop
|
||||
$ nvr rm
|
||||
$ nvr run
|
||||
```
|
||||
|
||||
Hopefully your system is functioning correctly. If not, there are two options
|
||||
for restore; neither are easy:
|
||||
@@ -120,9 +121,7 @@ for restore; neither are easy:
|
||||
* undo the changes by hand. There's no documentation on this; you'll need
|
||||
to read the code and come up with a reverse transformation.
|
||||
|
||||
Once you're confident of correct operation, delete the unneeded backup:
|
||||
|
||||
$ sudo systemctl rm /var/lib/moonfire-nvr/db/db.pre-upgrade
|
||||
The `nvr check` command will show you what problems exist on your system.
|
||||
|
||||
### Unversioned to version 0
|
||||
|
||||
|
||||
@@ -149,16 +149,20 @@ your browser. See [How to secure Nginx with Let's Encrypt on Ubuntu
|
||||
|
||||
## 6. Reconfigure Moonfire NVR
|
||||
|
||||
In your `/etc/systemd/system/moonfire-nvr.service` file, look for these lines:
|
||||
If you follow the recommended Docker setup, your `/usr/local/bin/nvr` script
|
||||
will contain this line:
|
||||
|
||||
```
|
||||
ExecStart=/usr/local/bin/moonfire-nvr run \
|
||||
--db-dir=/var/lib/moonfire-nvr/db \
|
||||
--http-addr=0.0.0.0:8080 \
|
||||
--allow-unauthenticated-permissions='view_video: true'
|
||||
--allow-unauthenticated-permissions='view_video: true'
|
||||
```
|
||||
|
||||
Replace the last line with `--trust-forward-hdrs`. This change has two effects:
|
||||
Replace it with the following:
|
||||
|
||||
```
|
||||
--trust-forward-hdrs
|
||||
```
|
||||
|
||||
This change has two effects:
|
||||
|
||||
* No `--allow-unauthenticated-permissions` means that web users must
|
||||
authenticate.
|
||||
@@ -167,15 +171,17 @@ Replace the last line with `--trust-forward-hdrs`. This change has two effects:
|
||||
in the next section.
|
||||
|
||||
If the webserver is running on the same machine as Moonfire NVR, you might
|
||||
also change `0.0.0.0:8080` to `127.0.0.1:8080`, which prevents other machines
|
||||
on the network from impersonating the proxy, effectively allowing them to lie
|
||||
about the client's IP and protocol.
|
||||
also change `--publish=8080:8080` to `--publish=127.0.0.1:8080:8080`, which
|
||||
prevents other machines on the network from impersonating the proxy,
|
||||
effectively allowing them to lie about the client's IP and protocol.
|
||||
|
||||
Run these commands to make the configuration take effect:
|
||||
To make this take effect, you'll need to stop the running Docker container,
|
||||
delete it, and create/run a new one:
|
||||
|
||||
```
|
||||
$ sudo systemctl daemon-reload
|
||||
$ sudo systemctl restart moonfire-nvr
|
||||
$ nvr stop
|
||||
$ nvr rm
|
||||
$ nvr run
|
||||
```
|
||||
|
||||
## 7. Configure the webserver
|
||||
|
||||
@@ -4,9 +4,12 @@
|
||||
|
||||
While Moonfire NVR is running, logs will be written to stderr.
|
||||
|
||||
* When running `moonfire-nvr config`, you typically should redirect stderr
|
||||
* When running the configuration UI, you typically should redirect stderr
|
||||
to a text file to avoid poor interaction between the interactive stdout
|
||||
output and the logging.
|
||||
output and the logging. If you use the recommended
|
||||
`nvr config 2>debug-log` command, output will be in the `debug-log` file.
|
||||
* When running detached through Docker, Docker saves the logs for you.
|
||||
Try `nvr logs` or `docker logs moonfire-nvr`.
|
||||
* When running through systemd, stderr will be redirected to the journal.
|
||||
Try `sudo journalctl --unit moonfire-nvr` to view the logs. You also
|
||||
likely want to set `MOONFIRE_FORMAT=google-systemd` to format logs as
|
||||
@@ -25,6 +28,8 @@ Logging options are controlled by environmental variables:
|
||||
[glog](https://github.com/google/glog) package) and `google-systemd` (a
|
||||
variation for better systemd compatibility).
|
||||
|
||||
If you use Docker, set these via Docker's `--env` argument.
|
||||
|
||||
## Problems
|
||||
|
||||
### `Error: pts not monotonically increasing; got 26615520 then 26539470`
|
||||
@@ -39,11 +44,5 @@ to disable B frames in the meantime.
|
||||
### `moonfire-nvr config` displays garbage
|
||||
|
||||
This happens if your machine is configured to a non-UTF-8 locale, due to
|
||||
gyscos/Cursive#13. As a workaround, type `export LC_ALL=en_US.UTF-8` prior to
|
||||
running `moonfire-nvr config`.
|
||||
|
||||
### Logging in is very very slow
|
||||
|
||||
Ensure you're using a build compiled with the `--release` flag. See
|
||||
[libpasta/libpasta#9](https://github.com/libpasta/libpasta/issues/9) for more
|
||||
background.
|
||||
gyscos/Cursive#13. As a workaround, try setting the environment variable
|
||||
`LC_ALL=C.UTF-8`. This should automatically be set with the Docker container.
|
||||
|
||||
Reference in New Issue
Block a user