Repository navigation
Expand file tree
/
Copy pathMakefile
More file actions
162 lines (139 loc) · 6.5 KB
/
Copy pathMakefile
File metadata and controls
162 lines (139 loc) · 6.5 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
# Rustible.
#
# The default target is the gate CI runs; everything else is opt-in. The `vm-`
# targets need Vagrant, which most work does not: see docs/DEVELOPING.md.
CARGO ?= cargo
VAGRANT ?= vagrant
VAGRANT_DIR := dev/vagrant
.PHONY: default check fmt clippy test doc example integration rust-analyzer \
vm-up vm-up-x86 vm-up-arm vm-test vm-halt vm-destroy vm-status \
vm-ssh vm-orphans
default: check
## ---------------------------------------------------------------- the gate
# What CI runs, in the order that fails soonest.
check: fmt clippy test doc example
fmt:
$(CARGO) fmt --all --check
# The second line is every member as a playbook links it: no dev-dependency,
# so the `testing` feature off and the test API compiled out.
clippy:
$(CARGO) clippy --workspace --all-targets -- -D warnings
$(CARGO) clippy --workspace -- -D warnings
# T1, in-process: everything a plain `cargo test` runs with nothing installed,
# chiefly pure functions and ops against the `Fake`. The T2 tests skip
# themselves here, without RUSTIBLE_INTEGRATION=1.
test:
$(CARGO) test --workspace
# `--all-features` documents the test API behind `testing`, as docs.rs does.
doc:
RUSTDOCFLAGS="-D warnings" $(CARGO) doc --workspace --no-deps --lib --all-features
# examples/workspace is outside the cargo workspace on purpose, so
# `cargo test --workspace` never compiles it. This is what catches a public
# API change that breaks the generated layout.
example:
$(CARGO) build --manifest-path examples/workspace/Cargo.toml
# The container tier, T2. Needs docker.
integration:
RUSTIBLE_INTEGRATION=1 $(CARGO) test -p rustible-std --tests
# `template!` as rust-analyzer shows it, against what the build reports, in a
# copy of the example workspace. Needs the rust-analyzer component (`rustup
# component add rust-analyzer`), or RUST_ANALYZER=<path to one>.
rust-analyzer:
RUSTIBLE_RUST_ANALYZER=1 $(CARGO) test -p rustible-macros --test rust_analyzer
## ------------------------------------------- the machine tier, T3: Linux VMs
# T3 is a real machine; here, a Linux VM over a real SSH transport, with a
# real sudo setup, a live /proc/sys and a real boot, none of which the
# container harness gives. Optional day to day; a new operation gets a step
# in vagrant.rs only if it needs a real machine. CI's other T3 machine is the
# macOS runner.
# `vagrant up` with no argument brings up only the machine whose architecture
# matches this host -- x86 on an x86_64 host, arm on Apple silicon -- because
# that is the one the Vagrantfile marks `autostart`. It is the fastest one
# available here, though not necessarily an accelerated one: a host with no
# /dev/kvm interprets its own architecture too. The other machine is always
# emulated, so it is opt-in by name below.
#
# It is also the `primary` machine, which is what lets `make vm-ssh` and
# `vagrant ssh` work without naming a machine.
vm-up:
cd $(VAGRANT_DIR) && $(VAGRANT) up
# By name, whichever host you are on. On a host of the other architecture this
# is the emulated one: minutes of your life, and the point of having it.
vm-up-x86:
cd $(VAGRANT_DIR) && $(VAGRANT) up x86
vm-up-arm:
cd $(VAGRANT_DIR) && $(VAGRANT) up arm
# Destroys and recreates the guests, then runs each playbook twice (vagrant,
# then vagrant_login and vagrant_escalate_user, which log in as and escalate
# to accounts the first creates): the first run must change something
# (otherwise the test is vacuous) and the second must change nothing; each
# run recovers exactly the failures its playbook catches on purpose; each run
# of vagrant must fetch back, byte for byte, the 50 MiB file it copied through
# the escalation helper. Then vagrant_login_escalate, once, whose launch must
# be refused. Pass HOSTS=vagrant-arm to limit it, QUICK=1 to skip the
# recreate while iterating, FRESH=1 when the guests were just brought up (CI
# does, to build while they boot): no recreate, every assertion kept.
vm-test: example
$(CARGO) build --release -p rustible-cli
$(VAGRANT_DIR)/vm-test.sh $(HOSTS)
vm-status:
cd $(VAGRANT_DIR) && $(VAGRANT) status
@echo
@if [ -f $(VAGRANT_DIR)/hosts.vagrant.kdl ]; then \
echo "inventory: $(VAGRANT_DIR)/hosts.vagrant.kdl"; \
grep '^ host ' $(VAGRANT_DIR)/hosts.vagrant.kdl || true; \
else \
echo "no inventory: nothing is up"; \
fi
# A shell in a machine. With one running, `make vm-ssh` is enough; otherwise
# name it, `make vm-ssh M=arm`.
vm-ssh:
cd $(VAGRANT_DIR) && $(VAGRANT) ssh $(M)
# Libvirt domains left behind by a checkout that was deleted before its
# machines were destroyed. Vagrant tracks a domain through
# dev/vagrant/.vagrant/, so removing that directory first orphans the domain:
# it keeps running, holds its disk, and `vagrant destroy` can no longer see it.
#
# "Known" means the provider's `id` file exists, not that the directory does:
# `vagrant destroy` leaves the machine directory behind and removes only `id`,
# so keying on the directory would report a genuinely stranded domain as known.
#
# Domain names are not unique across checkouts -- two clones both call it
# `vagrant_x86` -- so a second checkout's live machine shows up here. That is
# why this prints commands instead of running them.
vm-orphans:
@command -v virsh >/dev/null 2>&1 || { \
echo "virsh not found: this check is for the libvirt provider on Linux."; \
echo "The qemu provider (macOS) keeps each machine's disk in .vagrant/,"; \
echo "so there is no shared daemon to leave a domain behind in."; \
exit 0; \
}; \
doms=$$(virsh -c qemu:///system list --all --name 2>/dev/null | grep '^vagrant_' || true); \
known=$$(for d in $(VAGRANT_DIR)/.vagrant/machines/*/; do \
m=$$(basename "$$d"); \
for p in "$$d"*/id; do [ -f "$$p" ] && echo "vagrant_$$m"; done; \
done 2>/dev/null | sort -u); \
orphans=""; \
for d in $$doms; do \
echo "$$known" | grep -qx "$$d" || orphans="$$orphans $$d"; \
done; \
if [ -z "$$orphans" ]; then \
echo "no orphaned domains"; \
else \
echo "orphaned libvirt domains (not tracked by this checkout):"; \
for d in $$orphans; do echo " $$d"; done; \
echo; \
echo "If no other checkout owns them, remove each with:"; \
for d in $$orphans; do \
echo " sudo virsh -c qemu:///system destroy $$d; \
sudo virsh -c qemu:///system undefine $$d --nvram; \
sudo virsh -c qemu:///system vol-delete $$d.img --pool default"; \
done; \
fi
# Stop the machines, keeping their disks.
vm-halt:
cd $(VAGRANT_DIR) && $(VAGRANT) halt
# Delete them and their disks. The boxes stay in ~/.vagrant.d; remove those
# with `vagrant box prune`.
vm-destroy:
cd $(VAGRANT_DIR) && $(VAGRANT) destroy -f