Creating a pkg with pkg-create

I'm trying to create a package, from a tree of files, by following the instructions in pkg-create(8)(). I'm perplexed:

* the package manifests created by pkg create -o /tmp foo don't seem to match what's described in the manpage
* if I follow the instructions in the manpage, I get... weird errors

The +MANIFEST files created by pkg create (acting a currently installed package) include a files: { "filename": "hash", ...} key which isn't mentioned in the manpage. Also, the hashes all start 1$..., which is also un-mentioned in the manpage, which simply refers to sha256-hash. Oddness number 1.

Oddness 2: If I follow the manpage and create a manifest file freebsd/manifest which contains lots of lines like

Code:
...
file 5c6a0998512f902de57525713ef1b3ab1144c2f41b4c6861e3be6aa494080dcc usr/local/motherhen/lib/plt/motherhen/exts/ert/r6/default-web-root/htdocs/servlets/examples/clear.rkt
file 9685f028ac25a1f24244ce6bd13878a135137102611bdffe42f8a9742ef5a248 usr/local/motherhen/lib/plt/motherhen/exts/ert/r6/default-web-root/htdocs/servlets/examples/response.rktd
file ea1f1c890625bdf3547a1bea6542456c20f78a62285f163e4c6f2c176019d991 usr/local/motherhen/lib/plt/motherhen/exts/ert/r6/default-web-root/htdocs/servlets/examples/info.rkt
file 7860e83116a92fec0d2564d727aabb308a425302a1736692d8840b809b8b2322 usr/local/motherhen/lib/plt/motherhen/exts/ert/r6/default-web-root/htdocs/servlets/examples/digest.rkt
file b9b0517e79cfce3d765affed339ddd5d89c6dbd9444993481ac60b4b948574b2 usr/local/motherhen/lib/plt/motherhen/exts/ert/r6/default-web-root/htdocs/servlets/examples/add-ssd.rkt
file 487295da908e00ebe70ea2424d83efebdd57e2cd717db5aa8a08e169629b8913 usr/local/motherhen/lib/plt/motherhen/exts/ert/r6/default-web-root/htdocs/servlets/examples/fupload.rkt
...

that looks like it matches the file sha256-hash path described in the manpage. But when I run pkg create -M freebsd/manifest -r dist (the above files are rooted below the directory dist/), I consistently get an error

Code:
pkg: manifest parsing error: error while parsing <unknown>: line: 77, column: 5 - 'numeric value out of range', character: '7'

Line 77 is the one file 7860e8311..., and I get an error reported on this line even when move it elsewhere, or change the hash in another line to start with '7'. It's not clear just what links this error message to external reality!

So I generate an alternative manifest with lines like

Code:
files {
 "usr/local/motherhen/man/man8/motherhen.8":"1$0f12ec2037765ce9ef20b32b5a28d95b04bc3486f8027ec6718d9d5d1f23f71e",
 ...
}

and now pkg create -r freebsd/manifest -r dist produces errors like

Code:
pkg: fstat() failed for(dist//usr/home/norman/checkouts/motherhen/usr/local/motherhen/man/man8/motherhenctl.8): No such file or directory

which I similarly can't relate to the documentation of the pkg-create -r option. Using instead -r $PWD/dist just produces a differently unexpected generated path.

I feel like I'm reading the wrong manpage! What am I misunderstanding?

Norman
 
Thanks, Pat!

I've now managed to get something that appears to have worked, by a process of trial-and-error, with files

Code:
$PWD/dist/usr/local/etc/...
plus manifest lines like

Code:
files {
    "/usr/local/etc/...": "abc123hash...",
    ...
}

(ie, the file path has a leading slash) and pkg create -M freebsd/manifest -r dist (the -r freebsd/manifest in the previous post was a typo).

But the manifest file you've illustrated, Pat (and thanks for the reassurance...), has lines like
Code:
name: pkg-create-example
(ie, the keyword has a trailing colon), which appears to be a third possible format, none of which is actually documented by pkg-create(). I have seen a mention of the files being in ‘UCL’ format, but libucl() doesn't describe the format, either.

Am I missing something glaring, or is this just really badly underdocumented? (grumble, grumble...)

Norman
 
Yeah it's just badly underdocument, and I can't say I have any idea how well-used pkg-create(8) is. I went through a similar process as you. I also won't claim that my way is the right way - only that it's been working well so far. Generally speaking, I feel like ports are the "blessed path" for packaging software. But, you can certainly make this approach work. There are just way fewer examples out there.

Manifest can either be in UCL or JSON, maybe also YML. I used UCL, your examples were JSON. Either one works. UCL is more human-editable, JSON more machine-editable.

The best documentation for pkg is the github repo, e.g. manifest documentation.

Keep in mind the relationship between the -r rootdir flag and pkg-plist (or the files stanza in manifest if you use that instead). e.g. in my example the generated pkg-plist has a line /usr/local/share/pkg-create-example/foo, and the makefile produces stage/usr/local/share/pkg-create-example/foo so when I pass -r stage it looks in the stage for that file to include in the pkg, which it then installs to the correct location.
 
and I can't say I have any idea how well-used pkg-create(8) is.
Well, it's used by make package and all the package build tools use it to create packages. It's rarely used 'stand-alone' though, its intended use is to create a package from a built port.

In this case it might be better (maybe even simpler) to create a custom port for your own application. If you set up the port correctly the package will automatically be good too.
 
Indeed, it would be better to create a custom port. This will assure a correct installation and a correct registration into the package database.

A port will use scripts under /usr/ports/Mk/Scripts from the ports framework, inclusive /usr/ports/Mk/Scripts/create-manifest.sh
 
Righto – thanks for this; I'll study the porter's handbook appropriately.

The application (which is not one I plan to distribute other than locally) has a slightly complicated makefile already, so I'm slightly nervous of making it more complicated, but... make will cope.

Thanks all!

Norman
 
The application (which is not one I plan to distribute other than locally) has a slightly complicated makefile already, so I'm slightly nervous of making it more complicated, but... make will cope.
Leave that as is. Treat the 'port' as a wrapper around your source code and Makefile. That's what all other ports are in essence too.
 
Well, it's used by make package and all the package build tools use it to create packages. It's rarely used 'stand-alone' though, its intended use is to create a package from a built port.

In this case it might be better (maybe even simpler) to create a custom port for your own application. If you set up the port correctly the package will automatically be good too.

Ah! That makes way more sense.

This is the only article I've ever found on making packages with pkg-create. Some of the things I've done with it (particularly scripts and manifests) just end up being simpler when done via ports.

Good to know - thanks :)
 
Back
Top