Repository navigation
Expand file tree
/
Copy pathMakefile
More file actions
217 lines (178 loc) · 12.9 KB
/
Copy pathMakefile
File metadata and controls
217 lines (178 loc) · 12.9 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
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
# SPDX-License-Identifier: AGPL-3.0-or-later
#
# FoxByte runs inside the Linux dev VM (ZFS + Docker); day-to-day operation is
# via `lima /tmp/fox <command>`. This Makefile just builds/checks the CLI.
.PHONY: integration-f1 integration-f5 integration-f6 license-key license-samples integration-realtime integration-upgrade integration-sdks integration-ui release-key build build-enterprise vet vet-enterprise fmt vm-build test test-enterprise integration web-dev web-build release release-linux wsl-zfs wsl-distro feature-doc integration-v2 integration-update integration-pg-upgrade integration-editions test-vm test-vm-stop test-vm-delete
VERSION ?= 0.1.0
LDFLAGS := -s -w -X github.com/thefoxbyte/foxbyte/internal/version.Version=$(VERSION)
build: ## Build the CLI into ./bin/fox (host)
go build -o bin/fox ./cmd/fox
# The paid edition. `-tags enterprise` is the only difference: it compiles in
# everything under enterprise/, which the Standard binary above does not contain
# at all. That is what keeps ./bin/fox purely AGPL and freely redistributable.
build-enterprise: ## Build the Enterprise CLI into ./bin/fox-enterprise (host)
go build -tags enterprise -o bin/fox-enterprise ./cmd/fox
# The distro image bakes in one binary. Building the other four release
# targets to get it cost several minutes of cross-compilation per run, and
# release.yml already builds and publishes the full set separately.
release-linux: web-build ## Cross-compile just the Linux engine binary (for the distro image)
@mkdir -p dist
CGO_ENABLED=0 GOOS=linux GOARCH=amd64 \
go build -trimpath -tags embedui -ldflags "$(LDFLAGS)" -o dist/fox-linux-amd64 ./cmd/fox
release-key: ## One time: make the release signing key (private key to release-signing.key; public key into fox and install.sh)
go run ./cmd/releasesign generate --write
# Deliberately NOT a CI secret, unlike the release key. Every tag is signed in
# CI, so that key has to live there; this one is used by hand a few times a
# year, and a copy in CI is a copy that mints Enterprise for anyone who reaches
# it -- silently, because nothing calls home.
license-key: ## One time: make the licence signing key (private key to license-signing.key, for your password manager)
go run ./cmd/licensesign generate --write
# Evaluation licences for collaborators: every feature, any machine, three
# months. Site-wide and short-lived on purpose -- see docs/evaluation-licences.md.
COUNT ?= 50
license-samples: ## Mint $(COUNT) evaluation licences into ./eval-licences (needs license-signing.key)
@test -f license-signing.key || { echo "no license-signing.key — run: make license-key"; exit 1; }
@FOX_LICENSE_SIGNING_KEY=$$(cat license-signing.key) go run ./cmd/licensesign issue \
--customer "FoxByte evaluation" --features all --months 3 \
--id FB-EVAL --count $(COUNT) --out ./eval-licences
@echo "$(COUNT) licences in ./eval-licences — give one file to each collaborator"
release: web-build ## Cross-compile release binaries + the Windows image context into ./dist
@mkdir -p dist
@rm -f dist/fox-* dist/foxbyte-docker-context.tar.gz
@for t in darwin/arm64 darwin/amd64 linux/arm64 linux/amd64 windows/amd64; do \
os=$${t%/*}; arch=$${t#*/}; ext=""; [ "$$os" = "windows" ] && ext=".exe"; \
std="-tags embedui"; ent="-tags embedui,enterprise"; \
[ "$$os" = "linux" ] || { std=""; ent="-tags enterprise"; }; \
echo " building fox-$$os-$$arch$$ext"; \
CGO_ENABLED=0 GOOS=$$os GOARCH=$$arch \
go build -trimpath $$std -ldflags "$(LDFLAGS)" -o dist/fox-$$os-$$arch$$ext ./cmd/fox; \
echo " building fox-enterprise-$$os-$$arch$$ext"; \
CGO_ENABLED=0 GOOS=$$os GOARCH=$$arch \
go build -trimpath $$ent -ldflags "$(LDFLAGS)" -o dist/fox-enterprise-$$os-$$arch$$ext ./cmd/fox; \
CGO_ENABLED=0 GOOS=$$os GOARCH=$$arch \
go build -trimpath -ldflags "$(LDFLAGS)" -o dist/fox-verify-$$os-$$arch$$ext ./cmd/fox-verify; \
done
@echo " building foxbyte-docker-context.tar.gz"
@tar -C docker/postgres --exclude='*.go' -czf dist/foxbyte-docker-context.tar.gz .
@echo "release binaries in ./dist (version $(VERSION))"
@echo "note: the Windows installer also needs the ZFS module bundle (see make wsl-zfs / docs/windows-setup.md)"
vet: ## go vet
go vet ./...
# Without the tag, enterprise/ is only its untagged files, so `go vet ./...`
# above never looks at the paid code. Both have to be run.
vet-enterprise: ## go vet, with the enterprise code compiled in
go vet -tags enterprise ./...
fmt: ## list files needing gofmt
gofmt -l cmd internal
vm-build: web-build ## Build the Linux binary (UI embedded) inside the Lima VM to /tmp/fox
lima bash -c 'cd "$(CURDIR)" && go build -tags embedui -o /tmp/fox ./cmd/fox'
test: ## Run unit tests (host, no VM needed)
go test ./...
# Same reason as vet-enterprise: a test under enterprise/ does not run without
# the tag, and internal/edition's own tests assert different things in each
# edition. Both editions have to pass.
test-enterprise: ## Run unit tests with the enterprise code compiled in
go test -tags enterprise ./...
# The integration suites are destructive (they wipe Blackbox history, restore
# main to an earlier point, fail HA over), so they run in a throwaway VM of
# their own — never the VM holding your install. See scripts/test_vm.sh.
TEST_VM ?= fox-test
# A suite in the VM keeps this computer from sleeping while it runs: a VM stops
# when its host sleeps, and on waking every wait in flight has expired at once,
# so a run fails in batches of "timeouts" that say nothing about the code
# (scripts/lib/vm_pause.sh, which also reports it when it happens anyway).
# caffeinate -i holds off idle sleep, and -s system sleep while on power; on
# battery, closing the lid still sleeps a Mac, which nothing here can prevent.
KEEP_AWAKE := $(if $(filter Darwin,$(shell uname -s)),caffeinate -i -s,)
IN_TEST_VM = $(KEEP_AWAKE) env LIMA_INSTANCE=$(TEST_VM) lima
test-vm: ## Create or start the throwaway VM the integration suites run in
FOX_TEST_VM=$(TEST_VM) bash scripts/test_vm.sh
test-vm-stop: ## Stop the test VM (frees its memory; keeps it for next time)
limactl stop $(TEST_VM)
test-vm-delete: ## Delete the test VM and everything in it
limactl delete --force $(TEST_VM)
# The suites test features, and seven of those need a licence now. They run
# against an Enterprise build with a throwaway one (scripts/build_test_fox.sh):
# running them against Standard would test the refusal rather than the feature,
# and the refusals have tests of their own in scripts/test_editions.sh.
integration: test-vm ## Run the full end-to-end integration test in the test VM
$(IN_TEST_VM) bash -c 'cd "$(CURDIR)" && scripts/build_test_fox.sh /tmp/fox && go build -o /tmp/fox-verify ./cmd/fox-verify' && $(IN_TEST_VM) bash "$(CURDIR)/scripts/integration_test.sh"
integration-v2: test-vm ## Run the Blackbox 2.0 checks (behaviour-unchanged + new) in the test VM
$(IN_TEST_VM) bash -c 'cd "$(CURDIR)" && scripts/build_test_fox.sh /tmp/fox && go build -o /tmp/fox-verify ./cmd/fox-verify' && $(IN_TEST_VM) bash "$(CURDIR)/scripts/integration_ledger_v2.sh"
# The update suite hands the stack back to /usr/local/bin/fox when it finishes,
# so the test VM gets the current build installed there first.
#
# Standard, unlike the suites above: this one tests the update mechanism, which
# is free and the same in both editions. Running it on Enterprise would mean
# publishing fox-enterprise-* assets in the fake release too, since `fox update`
# deliberately keeps an install inside its own edition -- a lot of machinery to
# test something that does not differ.
integration-update: test-vm ## Run the `fox update` / new-release notice checks against a fake GitHub in the test VM
$(IN_TEST_VM) bash -c 'cd "$(CURDIR)" && go build -o /tmp/fox ./cmd/fox && sudo install -m 0755 /tmp/fox /usr/local/bin/fox' && $(IN_TEST_VM) bash "$(CURDIR)/scripts/integration_update.sh"
# Builds a PostgreSQL 16 install, exports and restores it, upgrades it to the
# major this fox ships, rolls back, upgrades again and finalizes. It uninstalls
# the stack at both ends, so it runs on its own.
integration-sdks: test-vm ## Run the Python and TypeScript client contract tests in the test VM
$(IN_TEST_VM) bash -c 'cd "$(CURDIR)" && scripts/build_test_fox.sh /tmp/fox' && $(IN_TEST_VM) bash "$(CURDIR)/scripts/integration_sdks.sh"
# The console is only in a binary built with `embedui`, from web/dist — which
# npm builds here on the host, since the repository is read-only in the VM.
integration-ui: web-build test-vm ## Run the web console's Playwright tests in the test VM (first run downloads Chromium)
$(IN_TEST_VM) bash -c 'cd "$(CURDIR)" && scripts/build_test_fox.sh /tmp/fox embedui' && $(IN_TEST_VM) bash "$(CURDIR)/scripts/integration_ui.sh"
# Host-side, no VM: builds both editions and looks inside them.
# The change feed. Built with -tags enterprise and a throwaway licence key the
# script mints itself: the real signing key is deliberately not in the
# repository or in CI, and a suite that needed it could never run here.
integration-realtime: test-vm ## Run the realtime change-feed checks in the test VM
$(IN_TEST_VM) bash "$(CURDIR)/scripts/integration_realtime.sh"
integration-f1: test-vm ## Run the F1 identity prototype's checks in the test VM (a throwaway container; no install touched)
$(IN_TEST_VM) bash "$(CURDIR)/scripts/integration_f1.sh"
integration-f6: test-vm ## Run the F6 audit prototype's checks in the test VM (throwaway containers; no install touched)
$(IN_TEST_VM) bash "$(CURDIR)/scripts/integration_f6.sh"
integration-f5: test-vm ## Run the F5 masking prototype's checks in the test VM (throwaway containers and a ZFS pool of its own; no install touched)
$(IN_TEST_VM) bash "$(CURDIR)/scripts/integration_f5.sh"
integration-editions: ## Check the edition boundary against the built binaries
bash scripts/test_editions.sh
# Non-destructive and needs no stack, so it runs on the host rather than in the
# test VM — but only on Linux, where the engine is the host binary. It builds
# each recent tag from its own source, so it needs the tags present.
integration-upgrade: test-vm ## Check that previously released versions can update to this build, in the test VM
$(IN_TEST_VM) bash "$(CURDIR)/scripts/integration_upgrade.sh"
integration-pg-upgrade: test-vm ## Run the export/restore and `fox pg upgrade` checks (16 -> the shipped major) in the test VM
$(IN_TEST_VM) bash -c 'cd "$(CURDIR)" && go build -o /tmp/fox ./cmd/fox' && $(IN_TEST_VM) bash "$(CURDIR)/scripts/integration_pg_upgrade.sh"
web-dev: ## DEPRECATED: the engine serves the UI at https://localhost:8080 (`fox start`). Hot-reload dev server only.
@echo "note: 'make web-dev' is deprecated — 'fox start' serves the UI at https://localhost:8080."
@echo " This runs a hot-reloading dev server for UI development only."
npm --prefix web install --no-audit --no-fund && npm --prefix web run dev
web-build: ## Build the web UI to web/dist (same-origin; embedded into the engine binary)
npm --prefix web ci && VITE_API_URL= npm --prefix web run build
# Both build scripts are invoked through bash rather than relying on their
# exec bit: this repo is developed on Windows with core.filemode=false, where
# a dropped +x is invisible locally and surfaces only as "Permission denied"
# on the Linux runner.
wsl-zfs: ## Build the OpenZFS modules + userland for the stock WSL2 kernel (Linux builder/CI only)
bash deploy/wsl-zfs/build.sh
wsl-distro: ## Build the prebuilt WSL2 distro image (Linux builder/CI with Docker)
bash deploy/wsl-distro/build.sh
# The living feature document: edit docs/FOX_Feature_Implemented.html with every
# change, then re-render the PDF. Uses headless Chrome/Chromium; set CHROME to a
brand: ## Regenerate everything derived from brand.json (see docs/branding.md)
go run ./cmd/brandgen -root .
brand-check: ## Fail if anything generated from brand.json is out of date
go run ./cmd/brandgen -root . -check
# browser binary if it isn't found automatically.
screenshots: web-build ## Retake docs/screenshots/*.png from a canned control plane
@node scripts/screenshots.mjs
feature-doc: ## Render docs/FOX_Feature_Implemented.pdf and docs/FOX_Checklist.pdf from their HTML sources
@chrome="$${CHROME:-}"; \
for c in "/Applications/Google Chrome.app/Contents/MacOS/Google Chrome" google-chrome chromium chromium-browser; do \
[ -n "$$chrome" ] && break; \
if [ -x "$$c" ] || command -v "$$c" >/dev/null 2>&1; then chrome="$$c"; fi; \
done; \
[ -n "$$chrome" ] || { echo "Chrome/Chromium not found — set CHROME=/path/to/chrome"; exit 1; }; \
bash scripts/test_feature_checklist.sh || exit 1; \
for doc in FOX_Feature_Implemented FOX_Checklist; do \
url="file://$$(printf '%s' "$(CURDIR)" | sed 's/ /%20/g')/docs/$$doc.html"; \
"$$chrome" --headless --disable-gpu --no-pdf-header-footer --print-to-pdf-no-header \
--print-to-pdf="$(CURDIR)/docs/$$doc.pdf" "$$url" 2>/dev/null && \
echo "wrote docs/$$doc.pdf" || exit 1; \
done