Extract and install:
Extract the downloaded archive (if applicable) and move the pvr executable to a directory in your system's PATH, such as /usr/local/bin or ~/bin.
Example (for a Linux 64-bit system, assuming the downloaded file is pvr-linux-amd64.tar.gz):
tar -xzf pvr-linux-amd64.tar.gz
sudo mv pvr /usr/local/bin/
Example (for a Windows 64-bit system, assuming the downloaded file is pvr-windows-amd64.zip):
For a quick and automated installation, you can use the install.sh script (or install.ps1 on Windows). This script will automatically detect your operating system and architecture, find the latest stable version of pvr from the GitLab package registry, download it, and install it to ~/.local/bin (or $HOME\.local\bin on Windows).
pvr is about transforming a directory structure that contains files as well as json files into
a single managable, diffable and mergeable json file that unambiguously defines directory state.
To leverage the features of json diff/merge etc. all json files found in a directory tree will
get inlined while all other objects will get a sha reference entry with the files themselves
getting stored in a flat objects directory.
When adding applications from Docker images or other sources, pvr uses a powerful template system to automatically generate Pantavisor manifests (run.json) and container configurations (lxc.container.conf).
You can customize this process using args.json (for Pantavisor-specific settings) and config.json (to override Docker manifest values like Entrypoint or Env).
For a detailed guide on available variables and how the template system works, see:
Being happy with what you see, you can checkpoint your working state using the
commit command:
$ pvr commit
Committing some.json
Committing working.txt
Adding newfile.txt
Removing deleted.txt
This will atomically update the json file in your repo after ensuring all the
right objects have been synched into the objects store of that pvr repo.
After committing your changes you might want to store your current repository
state for reuse or archiving purpose. You can do so using the push command:
$ pvr push /tmp/myrepo
You can always get a birds view on things in your repo by dumping the complete
current json:
$ pvr json
{...}
You can also push your repository to a pvr compliant REST backend. In this
case to a device trails (replace device id with your device)
$ pvr post https://api.pantahub.com/trails/<DEVICEID>
You can later clone that very repo to use it as a starting point or get
its content to update another repo.
Every PVR Repo is backed by an object repository which has for each
file a hashed file in it. These will be used on device as hardlink or on a checkout as a source to copy the files referenced from the state json file above.
By default the objects are kept centrally so you they get reused across potentially many projects you might checkout as a developer, but on device or in special cases you can use the --objects-dir parameter to use a different location.
Observe how the repo json got created in a subdirectory:
$ cat .pvr/json
{
"#spec": "pantavisor-multi-platform@1"
}
You would now continue editing this directory as it pleases you and you can refer to any file you put here in your configs just using the path as key (e.g. systemc.json": {} would create a systemc.json file on checkout).
prv add will put a file that exists in working directory under management of pvr. This means that the file will be honored on future pvr diff and pvr commit operations.
Example: If you bring in a basic platform to your system you simply copy them into the working dir and put them under pvr management:
By default pvr inlines any .json file in the main system state and does not save it
as an object. This implies that the exact formatting and order of elements in that .json
might get lost and for large .json files this might artifically grow the state json.
For those cases one might decide to hint at pvr that a .json file shall be added
as a raw object instead. For that oe uses the pvr add --raw command flag.
You can use that for new files but also to mark an already committed file for
conversion to a raw object on next commit.
When developing a device that has a pvr compatible cgi local
frontend (such as provided by pvr-sdk by default) installed
you can use pvr clone IP directly.
In that pvr clone 1.2.3.4 is equivalent to pvr clone http://1.2.3.4:12368/cgi-bin/pvr.
You can copy device state or subelements from one device to another without
downloading the bits to your local machine.
This only works for source devices that the user has access to. Right now
thats the case for Public devices as well as for devices owned by the
user itself.
To fastcopy a complete device experience you would simply use:
pvr fastcopy -m "your commit message to remember" \
NOTE: this will delete app apps and bsp/ entries before replacing them. If you dont want that you have to use fragment encoded in the URL to select specific source elements to copy and replace.
To fastcopy a specific folder of your source device and replace the matching folder you coudl simply use:
PVR Devices commands provide convenience for developers and individuals
that operate their very own pantavisor enabled solutions.
These commands are designed for developers that want to interface with devices
in their own local network, but not does not replace a fleet management
solution.
pvr device set <DEVICE_NICK|ID> = [KEY2]=[VALUE2]...[KEY-N]=[VALUE-N]
pvr device set : Set or Update device user-meta & device-meta fields (Note:If you are logged in as USER then you can update user-meta field but if you are logged in as DEVICE then you can update device-meta field)
example1$ pvr device set 5df243ff0be81900099855e6 a=1 b=2
{
"a": "1",
"b": "2"
}
user-meta field Updated Successfully
example2$ pvr device set 5df243ff0be81900099855e6 a=1 b=2
2020-01-06T12:54:10Z 5e0f4ede:pantavisor.log:INFO My log line 1 to remember from device:5d555d5e80123b31faa3cff2
2020-01-06T12:54:10Z 5e0f4ede:pantavisor.log:INFO My log line 1 to remember from device:5d555d5e80123b31faa3cff5
2020-01-06T12:54:10Z 5e0f4ede:pantavisor.log:INFO My log line 2 to remember from device:5d555d5e80123b31faa3cff2
2020-01-07T12:55:15Z 5e0f4ede:pantavisor.log:INFO My log line 2 to remember from device:5d555d5e80123b31faa3cff5
2020-01-07T12:55:15Z 5e0f4ede:pantavisor2.log:INFO2 My log line 3 to remember from device:5d555d5e80123b31faa3cff2
2020-01-07T12:55:20Z 5e0f4ede:pantavisor2.log:INFO2 My log line 3 to remember from device:5d555d5e80123b31faa3cff5
2020-01-07T12:55:20Z 5e0f4ede:pantavisor2.log:INFO2 My log line 4 to remember from device:5d555d5e80123b31faa3cff2
2020-01-06T12:56:20Z 5e0f4ede:pantavisor2.log:INFO2 My log line 4 to remember from device:5d555d5e80123b31faa3cff5
pvr device logs --from=2020-01-06T12:54:10+05:30 --to=2020-01-06T12:54:20+05:30 list the logs within a given date time range having timezone: +05:30(IST) ,Note:Timezone is optional
pvr import : import repo tarball (like the one produced by 'pvr export') into pvr in current working dir.It can import files with.gz or .tgz extension as well as plain .tar. Will not do pvr checkout, so working directory stays untouched.
Since version 006 PVR also provides convenience commands for interacting with pantahub
regardless beyond publishing pvr repositories to pantahub trails.
The --platform argument is used to select the desired platform from the package. You can also specify a version by appending @<version> to the URL.
If the --platform argument is not provided, pvr will look for a _hostconfig/pvr/docker.json file in the local repository and use the platforms defined there.
{
"platforms":[
"linux/arm",
"linux/arm/v6"
]
}
# Get from a GitLab package for a specific platform
$ pvr get --platform=linux/arm64 https://gitlab.com/my-group/my-project
An example of the output:
# get latest from remembered repository
example1$ $ pvr get
33aefd8dbf46f05 [OK]
686a026cd606613 [OK]
ff2a85a62cd09f1 [OK]
76d1d085d44fd3f [OK]
b30e6b64d3e1ecb [OK]
66ae7cac57d6d05 [OK]
e8305714eaadc57 [OK]
989647b3d5b7fde [OK]
612408620229de6 [OK]
f1b441cb2721355 [OK]
d49d56059ba219c [OK]
3f4889e5eed2252 [OK]
b56390fbeb5e46f [OK]
70075ca4496451e [OK]
You would usually introspect retrieved changes first using pvr status and then replace working copy with pristine state using pvr checkout.
The --platform argument is used to select the desired platform from the package. You can also specify a version by appending @<version> to the URL.
If the --platform argument is not provided, pvr will look for a _hostconfig/pvr/docker.json file in the local repository and use the platforms defined there.
pvr checkout|reset : checkout/reset working directory to match the repo stat.reset/checkout also forgets about added files; pvr status and diff will yield empty
pvr app add creates a new application and generates files by pulling layers from a given docker image in either remote or local docker repo's.
By default it will first look in remote repo. when not found it will pull from local docker repo,the priority can be changed using the --source flag(default:remote,local).
We now can create an app, install an app, and update an app using as source a root filesystem, that filesystem could be as a tar in local for the computer is running the PVR, could be a plain folder with the filesystem inside, or could be an URL where the tar is to be downloaded.
Add application that extends from another application
PVR and pantavisor support application that uses another application rootfs system as base and just create a diff squashfs for the files that are different in the added application.
That will allow to have smaller applications that share libraries or tools between several applications.
In this case for this to work the base system should be created as a data application
src.json is an input document used to store information about a Pantavisor container to be consumed by the pvr app install and pvr app update commands. It contains key-value pairs that define various aspects of the platform configuration.
PV_GROUP: Group to which the container belongs. Possible values: "data", "root", "platform" "app" or any additional group.
PV_RESTART_POLICY: Restart policy for the container. Possible values: "system" or "container".
PV_ROLES: Roles assigned to the platform. Possible values: "mgmt" or empty.
PV_SECURITY_WITH_STORAGE: Enable/disable security with storage. Possible values: "yes" or "no".
PV_STATUS_GOAL: Desired status goal for the platform. Possible values: "MOUNTED", "STARTED", or "READY".
PV_LXC_EXTRA_CONF: Extra LXC configuration to be appended to lxc.container.conf.
PV_LXC_CAP_KEEP: Specify the capabilities to be kept in the container.
PV_LXC_CAP_DROP: Specify the capabilities to be kept in the container (note: use either keep or drop, but not both).
PV_LXC_NAMESPACE_KEEP: Specify the namespaces to be inherited from Pantavisor.
PVR_LXC_CGROUP_DEVICES_WHITE: Allow list of devices for the container. See the device indexes to be used here.
PV_VOLUME_IMPORTS: Import a volume or a subpath within a volume; syntax: :[@]:[:ro]
PV_VOLUME_MOUNTS: Mount volume owned by the container itself to aditional places; syntax: :
PV_IMPORT_CONFIGVOLUMES: Mount configvolumes to a target path. configvolumes are volumes that can have configs for multiple containers inside. the top level directory of such volume would be the container name. Syntax: : (e.g for a container named 'foo' the directory /foo inside the '' volume would be mounted to ''
PV_DISABLE_AUTODEV: disable lxc.autodev feature. Do this if you know what you are doing only.
PV_SECURITY_FULLDEV: mount host /dev to dev/ inside container. IMPORTANT: usually you dont want this. Only do this if you know what you are doing.
PV_SECURITY_WITH_HOST: mount host / partition to host/ directory inside container. Usually this is not a good idea.
PV_SECURITY_WITH_HOSTPROC: mount /proc of host to host/proc mountpoint. Treat carefully.
PV_SECURITY_WITH_STORAGE: make the pantavisor /storage partition (e.g. pvroot) available inside the container at /storage.
PV_RUN_TMPFS_DISABLE: disable mounting a tmpfs to /run folder. You usually do not want to disable this.
PV_RESOLV_CONF_DISABLE: do not mount the central host /etc/resolv.conf inside the container.
With pvr deploy you can deploy one to many source repos to a deployment directory such as the
one you find on the pantavisor device for each revision.
This command can be used to modify a rootfs and change/replace/update apps.
Example, will deploy the 'os' container from a local repository, the 'bsp' container from a pvr
export to a factory revision (trails/0) in a pantavisor enabled rootfs.
PVR sig commands offers support for maintaining pvs signatures inside your tree.
For details see README.pvs.md
Commands currently supported are:
Review all object and file usage cases to ensure tall are validated before they are installed/used.
pvr sig add - adds a new signature to the _pvs/ hierarchy of the state
pvr sig update - updates a committed signature from the _pvs/ hierarchy to be validate against committed state
pvr sig ls - list files covered by signatures in _sigs/ hieararchy; by default sig ls will show signature info while considering all signatures in the system state
To allow easier integration in higher level tools, like external signing tools
pvr sig offers a few options to make their live easier.
The idea of making an external signing tool is to keep the logic that interprets
the PVS headers and create the protected header and the payload of the jose token
inside pvr itself, but allow for easy export of the complete jose token including
payload which then external tools can inspect and sign.
The first avenue is to produce a signature during signing that includes the full
payload. This can be achieved through the --with-payload option for pvr sig add
and pvr sig update. Example:
$ pvr clone pantahub-ci/rock64_initial_stable example
$ cd example
$ pvr sig --with-payload add --part awconnect
This will produce a jose signature file in _sigs/awconnect.json that
includes the full payload and hence can be send to a service that resigns
it in infrastructure.
To make this more conveniebnt, the --output=- option allows to print that
signature to stdout:
The second approach that might be viable is to take a package that was
already signed by a developer or CI system, inspect it and resign it with
a production key.
For that the pvr sig ls command offers some convenience to include the
jose serialization found in the result summary with the --with-sig option.
Combined with the --with-payload option this gives the user the ability
to again a produce a complete jose token that an external system can
resign without further business logic. Example:
$ pvr sig --with-payload ls --with-sig _sigs/awconnect.json
pvr device mapper support for container volumes allows for an easy way to
postprocess the squashfs volumes produced by pvr app add etc. in a way that
the pantavisor device mapper addon can mount volumes using device-mapper.
For now dm-verity type device mapper entries are supported by pantavisor
client and hence pvr supports that mode first and foremost for now.
... and also the hash_device in os/root.squashfs.hash.
Also it will convert the volume reference in run.json to "dm:<volume", e.g.
dm:rootfs.squashfs. This syntax will ensure that pantavisor will not try to
mount the squash himself, but rather delegate that to a device-mapper
volume handler.
You can then pvr commit this and post it to a pantavisor device-mapper
enabled device