]> Cypherpunks.ru repositories - gocheese.git/blob - gocheese.texi
Split pretty huge gocheese.go
[gocheese.git] / gocheese.texi
1 \input texinfo
2 @documentencoding UTF-8
3 @settitle GoCheese
4
5 @node Top
6 @top
7
8 GoCheese is Python private package repository and caching proxy.
9
10 It serves two purposes:
11
12 @itemize
13 @item proxying and caching of missing packages from upstream
14     @url{https://pypi.org/, PyPI}, conforming to
15     @url{https://www.python.org/dev/peps/pep-0503/, PEP-0503}
16     (Simple Repository API)
17 @item hosting of private locally uploaded packages, conforming to
18     @url{https://warehouse.pypa.io/api-reference/legacy/, Warehouse Legacy API}
19 @end itemize
20
21 Initially it was created as a fork of
22 @url{https://github.com/c4s4/cheeseshop, cheeseshop},
23 but nearly all the code was rewritten. It has huge differences:
24
25 @itemize
26 @item proxying and caching of missing packages, including GPG signatures
27 @item @url{https://pythonwheels.com/, Wheel} uploading support
28 @item integrity check of proxied packages: MD5, SHA256, SHA512, BLAKE2b-256
29 @item SHA256 checksums for stored packages
30 @item verifying of SHA256 checksum for uploaded packages
31 @item storing of uploaded GPG signatures
32 @item no YAML configuration, just command-line arguments
33 @item no package overwriting ability (as PyPI does too)
34 @item atomic packages store on filesystem
35 @item graceful HTTP-server shutdown
36 @end itemize
37
38 Also it contains @file{pyshop2packages.sh} migration script for
39 converting @url{https://pypi.org/project/pyshop/, Pyshop} database into
40 GoCheese one, including private packages.
41
42 GoCheese is free software, licenced under
43 @url{https://www.gnu.org/licenses/gpl-3.0.html, GNU GPLv3}:
44 see the file COPYING for copying conditions.
45
46 @menu
47 * Usage::
48 * Password authentication: Passwords.
49 * TLS support: TLS.
50 * Storage format: Storage.
51 @end menu
52
53 @node Usage
54 @unnumbered Usage
55
56 To use it for download purposes, just configure your @file{pip.conf}:
57
58 @verbatim
59 [install]
60 index-url = http://gocheese.host:8080/simple/
61 @end verbatim
62
63 @option{-refresh} URL (@code{/simple/} by default) automatically
64 refreshes metainformation (available versions and their checksums)
65 from the upstream, when queried for package directory listing.
66 @option{-norefresh} prevents upstream queries.
67
68 @option{-gpgupdate} is useful mainly for migrated for Pyshop migrated
69 repositories. It forces GPG signature files downloading for all existing
70 package files.
71
72 You can upload packages to it with @url{https://pypi.org/project/twine/, twine}:
73
74 @verbatim
75 twine upload
76     --repository-url http://gocheese.host:8080/simple/ \
77     --username spam \
78     --password foo dist/tarball.tar.gz
79 @end verbatim
80
81 Or you can store it permanently in @file{.pypirc}:
82
83 @verbatim
84 [pypi]
85 repository: https://gocheese.host/simple/
86 username: spam
87 password: foo
88 @end verbatim
89
90 If @command{twine} sends SHA256 checksum in the request, then uploaded
91 file is checked against it.
92
93 Pay attention that you have to manually create corresponding private
94 package directory! You are not allowed to upload anything explicitly
95 flagged as internal package.
96
97 @node Passwords
98 @unnumbered Password authentication
99
100 Password authentication is required for packages uploading.
101 You have to store your authentication data in @option{-passwd} file in
102 following format:
103
104 @verbatim
105 username:hashed-password
106 @end verbatim
107
108 Empty lines and having @verb{|#|} at the beginning are skipped.
109
110 Supported hashing algorithms are:
111
112 @table @asis
113
114 @item @url{https://www.argon2i.com/, Argon2i} (recommended one!)
115     To get Argon2i hashed-password you can use any of following tools:
116     @itemize
117     @item @url{https://github.com/balakhonova/argon2i,
118         go get github.com/balakhonova/argon2i} (Go)
119     @item @url{https://github.com/p-h-c/phc-winner-argon2} (C)
120     @end itemize
121     Example user @code{foo} with password @code{bar} can have the
122     following password file entry:
123
124 @verbatim
125 foo:$argon2i$v=19$m=32768,t=3,p=4$OGU5MTM3YjVlYzQwZjhkZA$rVn53v6Ckpf7WH0676ZQLr9Hbm6VH3YnL6I9ONJcIIU
126 @end verbatim
127
128 @item SHA256
129     You can use your operating system tools:
130
131 @verbatim
132 # BSD-based systems:
133 $ echo -n "password" | sha256
134
135 # GNU/Linux-based systems
136 $ echo -n "password" | sha256sum
137 @end verbatim
138     Example user @code{foo} with password @code{bar} will have the
139     following password file entry:
140
141 @verbatim
142 foo:$sha256$fcde2b2edba56bf408601fb721fe9b5c338d10ee429ea04fae5511b68fbf8fb9
143 @end verbatim
144
145 @end table
146
147 You can refresh passwords by sending @code{SIGHUP} signal to the working daemon:
148
149 @verbatim
150 $ pkill -HUP gocheese
151 $ kill -HUP `pidof gocheese`
152 @end verbatim
153
154 Before refreshing it's recommended to check @option{-passwd} file with
155 @option{-passwd-check} option to prevent daemon failure.
156
157 @node TLS
158 @unnumbered TLS support
159
160 You can enable TLS support by specifying PEM-encoded X.509 certificate
161 and private key files. Go's TLS implementation supports TLS 1.3, HTTP/2
162 negotiation, Keep-Alives, modern ciphersuites and ECC.
163
164 For example generate some self-signed certificate using GnuTLS toolset:
165
166 @verbatim
167 $ certtool --generate-privkey --ecc --outfile prv.pem
168 $ cert_template=`mktemp`
169 $ echo cn=gocheese.host > $cert_template
170 $ certtool \
171     --generate-self-signed \
172     --load-privkey=prv.pem \
173     --template $cert_template \
174     --outfile=cert.pem
175 $ rm $cert_template
176 $ gocheese -tls-cert cert.pem -tls-key prv.pem [...]
177 @end verbatim
178
179 @node Storage
180 @unnumbered Storage format
181
182 Root directory has the following hierarchy:
183
184 @verbatim
185 root
186   +-- public-package
187   |     +- public-package-0.1.tar.gz.md5
188   |     +- public-package-0.1.tar.gz.blake2_256
189   |     +- public-package-0.1.1.tar.gz.blake2_256
190   |     +- public-package-0.2.tar.gz
191   |     +- public-package-0.2.tar.gz.asc
192   |     +- public-package-0.2.tar.gz.sha256
193   +-- private-package
194   |     +- .internal
195   |     +- private-package-0.1.tar.gz
196   |     +- private-package-0.1.tar.gz.asc
197   |     +- private-package-0.1.tar.gz.sha256
198   |...
199 @end verbatim
200
201 Each directory is a normalized package name. When you try to list non
202 existent directory contents (you are downloading package you have not
203 seen before), then GoCheese will download information about package's
204 versions with checksums and write them in corresponding
205 @file{.sha256}, @file{.blake2_256}, @file{.sha512}, @file{.md5} files.
206 However no package package tarball is downloaded.
207
208 When you request for particular package version, then its tarball is
209 downloaded and verified against the stored checksum. But SHA256 is
210 forced to be stored and used later.
211
212 For example @file{public-package} has @code{0.1} version, downloaded a
213 long time ago with MD5 checksum. @code{0.1.1} version is downloaded more
214 recently with BLAKE2b-256 checksum, also storing that checksum for
215 @code{0.1}. @code{0.2} version is downloaded tarball, having forced
216 SHA256 recalculated checksum. Also upstream has corresponding
217 @file{.asc} signature file.
218
219 @file{private-package} is private package, because it contains
220 @file{.internal} file. It can be uploaded and queries to it are not
221 proxied to upstream PyPI. You have to create it manually. If you upload
222 GPG signature, then it will be also stored.
223
224 @bye