Skip to content

Commit 1338a2c

Browse files
authored
Merge pull request #66 from degville/snapcraft-go
Snapcraft: Import Go applications how-to
2 parents fe08059 + 4d2e45c commit 1338a2c

File tree

1 file changed

+252
-0
lines changed

1 file changed

+252
-0
lines changed
Lines changed: 252 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,252 @@
1+
Snapcraft can be used to package and distribute Go applications in a way that
2+
enables convenient installation by users.
3+
4+
The process of creating a snap for a Go application builds on standard
5+
Go packaging tools, making it possible to adapt or integrate an
6+
application's existing packaging into the snap building process.
7+
8+
## Getting started
9+
10+
Snaps are defined in a single `snapcraft.yaml` file placed in a
11+
`snap` folder at the root of your project. This YAML file describes
12+
the application, its dependencies and how it should be built.
13+
14+
The following example shows the entire `snapcraft.yaml` file for an existing project, [Woke](https://github.com/degville/woke-snap):
15+
16+
```yaml
17+
name: woke
18+
summary: Detect non-inclusive language in your source code
19+
description: |
20+
Creating an inclusive work environment is imperative to a healthy,
21+
supportive, and productive culture, and an environment where everyone
22+
feels welcome and included. woke is a text file analysis tool that finds
23+
places within your source code that contain non-inclusive language and
24+
suggests replacing them with more inclusive alternatives.
25+
version: git
26+
grade: stable
27+
base: core20
28+
29+
confinement: devmode
30+
31+
apps:
32+
woke:
33+
command: bin/woke
34+
plugs:
35+
- home
36+
parts:
37+
woke:
38+
plugin: go
39+
source-type: git
40+
source: https://github.com/get-woke/woke
41+
```
42+
43+
We'll break this file down into its components in the following sections.
44+
45+
### Metadata
46+
47+
The `snapcraft.yaml` file starts with a small amount of
48+
human-readable metadata, which is often already available in the project's
49+
own packaging metadata or `README.md` file. This data is used in the
50+
presentation of the application in the Snap Store.
51+
52+
```yaml
53+
name: woke
54+
summary: Detect non-inclusive language in your source code
55+
description: |
56+
Creating an inclusive work environment is imperative to a healthy,
57+
supportive, and productive culture, and an environment where everyone
58+
feels welcome and included. woke is a text file analysis tool that finds
59+
places within your source code that contain non-inclusive language and
60+
suggests replacing them with more inclusive alternatives.
61+
version: git
62+
```
63+
64+
The `name` must be unique in the Snap Store. Valid snap names consist of lower-case alphanumeric characters and hyphens. They cannot be all numbers and they also cannot start or end with a hyphen.
65+
66+
By specifying `git` for the version, the current git tag or commit will be used as the version string. Versions carry no semantic meaning in snaps.
67+
68+
The `summary` can not exceed 79 characters. You can use a chevron '>' in the `description` key to declare a multi-line description.
69+
70+
### Base
71+
72+
The base keyword declares which :term:`base snap` to use with the project.
73+
A base snap is a special kind of snap that provides a run-time environment
74+
alongside a minimal set of libraries that are common to most applications.
75+
76+
```yaml
77+
base: core20
78+
```
79+
80+
In this example, [core20](https://snapcraft.io/core20) is used as the base for snap building, and is based
81+
on [Ubuntu 20.04 LTS](http://releases.ubuntu.com/20.04/). See [Base snaps](/t/11198) for more details.
82+
83+
### Security model
84+
85+
Snaps are containerised to ensure more predictable application behaviour and
86+
greater security. The general level of access a snap has to the user's system
87+
depends on its level of confinement.
88+
89+
The next section of the `snapcraft.yaml` file describes the level of
90+
:term:`confinement` applied to the running application:
91+
92+
```yaml
93+
confinement: devmode
94+
```
95+
96+
It is best to start creating a snap with a confinement level that provides
97+
warnings for confinement issues instead of strictly applying confinement.
98+
This is done by specifying the `devmode` (developer mode) confinement value.
99+
When a snap is in devmode, runtime confinement violations will be allowed but
100+
reported. These can be reviewed by running `journalctl -xe`.
101+
102+
Because devmode is only intended for development, snaps must be set to strict
103+
confinement before they can be published as "stable" in the Snap Store.
104+
Once an application is working well in devmode, you can review confinement
105+
violations, add appropriate interfaces, and switch to strict confinement.
106+
107+
The above example will also work if you change the confinement from `devmode`
108+
to `strict`, as you would before a release.
109+
110+
### Parts
111+
112+
Parts define what sources are needed to build your application. Parts can be
113+
anything: programs, libraries, or other needed assets, but for this example,
114+
we only need to use one part for the *woke* source code:
115+
116+
```yaml
117+
parts:
118+
woke:
119+
plugin: go
120+
source-type: git
121+
source: https://github.com/get-woke/woke
122+
```
123+
124+
The `plugin` keyword is used to select a language or technology-specific
125+
plugin that knows how to perform the build steps for the project.
126+
In this example, the [go plugin](/t/7818) is used to
127+
automate the build of this project using the version of Go on the host system.
128+
129+
The `source` keyword points to the source code of the project, which
130+
can be a local directory or remote Git repository. In this case, it refers to
131+
the main project repository.
132+
133+
### Apps
134+
135+
Apps are the commands and services that the snap provides to users. Each key
136+
under `apps` is the name of a command or service that should be made
137+
available on users' systems.
138+
139+
```yaml
140+
apps:
141+
woke:
142+
command: bin/woke
143+
plugs:
144+
- home
145+
```
146+
147+
The `command` specifies the path to the binary to be run. This is resolved
148+
relative to the root of the snap contents.
149+
150+
If the command name matches the name of the snap specified in the top-level
151+
`name` keyword (see **Metadata** above), the binary file will be given the
152+
same name as the snap, as in this example.
153+
If the names differ, the binary file name will be prefixed with the snap name
154+
to avoid naming conflicts between installed snaps. An example of this would be
155+
`woke.some-command`.
156+
157+
The confinement of the snap, which was defined in the **Security model** section
158+
above, can be changed through a set of :term:`interfaces`. In this example,
159+
the `plugs` keyword is used to specify the interfaces that the snap needs
160+
to access.
161+
162+
### Building the snap
163+
164+
You can download the example repository with the following command:
165+
166+
```bash
167+
$ git clone https://github.com/degville/woke-snap
168+
```
169+
170+
After you have created the `snapcraft.yaml` file (which already exists
171+
in the above repository), you can build the snap by simply executing the
172+
`snapcraft` command in the project directory:
173+
174+
```bash
175+
$ snapcraft
176+
Launching a container.
177+
Waiting for container to be ready
178+
[...]
179+
Pulling woke
180+
+ snapcraftctl pull
181+
Cloning into '/root/parts/woke/src'...
182+
remote: Enumerating objects: 2723, done.
183+
remote: Counting objects: 100% (939/939), done.
184+
remote: Compressing objects: 100% (401/401), done.
185+
remote: Total 2723 (delta 697), reused 635 (delta 522), pack-reused 1784
186+
Receiving objects: 100% (2723/2723), 22.33 MiB | 2.88 MiB/s, done.
187+
Resolving deltas: 100% (1574/1574), done.
188+
Building woke
189+
+ snapcraftctl build
190+
+ go mod download
191+
+ go install -p 8 -ldflags -linkmode=external ./...
192+
Staging woke
193+
+ snapcraftctl stage
194+
Priming woke
195+
+ snapcraftctl prime
196+
Determining the version from the project repo (version: git).
197+
The version has been set to '0+git.f23bb0a-dirty'
198+
Snapping |
199+
Snapped woke_0+git.f23bb0a-dirty_multi.snap
200+
```
201+
202+
The resulting snap can be installed locally. This requires the `--dangerous` flag because the snap is not signed by the Snap Store. The `--devmode` flag acknowledges that you are installing an unconfined application:
203+
204+
```bash
205+
$ sudo snap install woke_*.snap --devmode --dangerous
206+
```
207+
208+
You can then try it out:
209+
210+
```bash
211+
$ woke -h
212+
```
213+
214+
Removing the snap is simple too:
215+
216+
```bash
217+
$ sudo snap remove woke
218+
```
219+
220+
## Publishing your snap
221+
222+
To share your snaps you need to publish them in the Snap Store. First, create an account on [the dashboard](https://dashboard.snapcraft.io/dev/account/). Here you can customise how your snaps are presented, review your uploads and control publishing.
223+
224+
You’ll need to choose a unique “developer namespace” as part of the account creation process. This name will be visible by users and associated with your published snaps.
225+
226+
Make sure the `snapcraft` command is authenticated using the email address attached to your Snap Store account:
227+
228+
```
229+
$ snapcraft login
230+
```
231+
232+
### Reserve a name for your snap
233+
234+
You can publish your own version of a snap, provided you do so under a name you have rights to. You can register a name on [dashboard.snapcraft.io](https://dashboard.snapcraft.io/register-snap/), or by running the following command:
235+
236+
```
237+
$ snapcraft register mygosnap
238+
```
239+
240+
Be sure to update the `name:` in your `snapcraft.yaml` to match this registered name, then run `snapcraft` again.
241+
242+
### Upload your snap
243+
244+
Use snapcraft to push the snap to the Snap Store.
245+
246+
```
247+
$ snapcraft upload --release=edge mygosnap_*.snap
248+
```
249+
250+
If you’re happy with the result, you can commit the snapcraft.yaml to your GitHub repo and [turn on automatic builds](https://build.snapcraft.io) so any further commits automatically get released to edge, without requiring you to manually build locally.
251+
252+
Congratulations! You've just built and published your first Go snap. For a more in-depth overview of the snap building process, see [Creating a snap](/t/creating-a-snap/6799).

0 commit comments

Comments
 (0)