-
Notifications
You must be signed in to change notification settings - Fork 16
Expand file tree
/
Copy pathjavascript.sh
More file actions
executable file
·147 lines (125 loc) · 5.95 KB
/
Copy pathjavascript.sh
File metadata and controls
executable file
·147 lines (125 loc) · 5.95 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
#!/bin/bash
# Keeps the shipped JS bundles in sync with their CoffeeScript sources.
#
# The committed files BirchOutline/BirchOutline.swift/Dependencies/birchoutline.js and
# BirchEditor/BirchEditor.swift/Dependencies/bircheditor.js are the canonical build
# inputs — a fresh clone builds the app from them with no JS toolchain installed.
# Next to each bundle lives a committed .sha256 manifest recording (a) a hash of the
# bundle's inputs (src/**, gulp/webpack config, package.json, package-lock.json) and
# (b) a hash of the bundle itself.
#
# When manifests match, this script is a no-op (no Node required). When sources have
# changed, it rebuilds with gulp (Node v11.15.0 — the gulp 3 toolchain does not run on
# newer Node), refreshes the bundles and manifests, and tells you to commit them
# together with the source changes. If a rebuild is needed but impossible or fails,
# the Xcode build fails loudly instead of silently shipping stale bundles.
set -euo pipefail
# Hashes depend on `sort` order, which is locale-dependent — pin it.
export LC_ALL=C
ROOT="$(cd "$(dirname "$0")" && pwd)"
OUTLINE_PKG="$ROOT/BirchOutline/birch-outline.js"
EDITOR_PKG="$ROOT/BirchEditor/birch-editor.js"
OUTLINE_DEP="$ROOT/BirchOutline/BirchOutline.swift/Dependencies/birchoutline.js"
EDITOR_DEP="$ROOT/BirchEditor/BirchEditor.swift/Dependencies/bircheditor.js"
OUTLINE_MANIFEST="$OUTLINE_DEP.sha256"
EDITOR_MANIFEST="$EDITOR_DEP.sha256"
REBUILD_HINT="rebuild with: nvm use v11.15.0 && ./javascript.sh, then commit the updated Dependencies/*.js and *.sha256 files"
fail() {
echo "error: $1" >&2
exit 1
}
file_hash() {
shasum -a 256 "$1" | cut -d' ' -f1
}
# Hash of everything that determines a package's bundle bytes.
inputs_hash() {
(
cd "$1"
{
find src -type f ! -name .DS_Store | sort
echo gulpfile.coffee
echo webpack.config.coffee
echo package.json
echo package-lock.json
} | xargs shasum -a 256 | shasum -a 256 | cut -d' ' -f1
)
}
manifest_matches() {
local manifest="$1" inputs="$2" bundle="$3"
[ -f "$manifest" ] && [ -f "$bundle" ] || return 1
[ "$(sed -n 's/^inputs //p' "$manifest")" = "$inputs" ] || return 1
[ "$(sed -n 's/^bundle //p' "$manifest")" = "$(file_hash "$bundle")" ] || return 1
}
write_manifest() {
local manifest="$1" inputs="$2" bundle="$3"
printf 'inputs %s\nbundle %s\n' "$inputs" "$(file_hash "$bundle")" > "$manifest"
}
# True when min/<bundle> exists and no input is newer (e.g. `npm run start` gulp-watch
# already rebuilt it) — then we can skip gulp and just copy.
min_is_fresh() {
local pkg="$1" out="$2"
shift 2
[ -f "$pkg/min/$out" ] || return 1
[ -z "$(cd "$pkg" && find src gulpfile.coffee webpack.config.coffee package.json package-lock.json "$@" -newer "min/$out" -print -quit)" ]
}
ensure_toolchain() {
local nvm_bin="$HOME/.nvm/versions/node/v11.15.0/bin"
if [ -x "$nvm_bin/node" ]; then
export PATH="$nvm_bin:$PATH"
fi
case "$(node -v 2>/dev/null || true)" in
v11.*) ;;
*) fail "JS sources changed but Node v11.15.0 was not found (the gulp 3 toolchain requires it). Install with: nvm install v11.15.0 — then $REBUILD_HINT" ;;
esac
for pkg in "$OUTLINE_PKG" "$EDITOR_PKG"; do
[ -f "$pkg/node_modules/gulp/bin/gulp.js" ] || fail "JS sources changed but $pkg/node_modules is missing. Run: cd $pkg && npm install (with Node v11.15.0), then $REBUILD_HINT"
done
}
STAMP="$(mktemp)"
trap 'rm -f "$STAMP"' EXIT
gulp_prepublish() {
echo "Rebuilding JS bundle in $1 ..."
ensure_toolchain
(cd "$1" && ./node_modules/gulp/bin/gulp.js prepublish) || fail "gulp prepublish failed in $1 — fix the JS build, then $REBUILD_HINT"
}
# gulp 3 swallows CoffeeScript compile errors and doesn't await webpack, so verify the
# output actually got (re)written rather than trusting gulp's exit status.
verify_min() {
local f="$1"
[ -f "$f" ] || fail "$f was not produced by gulp prepublish — fix the JS build, then $REBUILD_HINT"
[ "$(stat -f %z "$f")" -gt 100000 ] || fail "$f is suspiciously small — the JS build likely failed; fix it, then $REBUILD_HINT"
[ "$f" -nt "$STAMP" ] || fail "$f was not regenerated by gulp prepublish (a CoffeeScript error may have been swallowed) — fix the JS build, then $REBUILD_HINT"
}
update_bundle() {
local min="$1" dep="$2" manifest="$3" inputs="$4"
cp "$min" "$dep"
write_manifest "$manifest" "$inputs" "$dep"
echo "Updated $dep — commit it (and its .sha256 manifest) together with the JS source changes."
}
OUTLINE_INPUTS="$(inputs_hash "$OUTLINE_PKG")"
# The editor bundle embeds birch-outline (npm file: link), so its inputs include the outline's.
EDITOR_INPUTS="$(printf '%s\n%s\n' "$(inputs_hash "$EDITOR_PKG")" "$OUTLINE_INPUTS" | shasum -a 256 | cut -d' ' -f1)"
outline_ok=0; manifest_matches "$OUTLINE_MANIFEST" "$OUTLINE_INPUTS" "$OUTLINE_DEP" || outline_ok=1
editor_ok=0; manifest_matches "$EDITOR_MANIFEST" "$EDITOR_INPUTS" "$EDITOR_DEP" || editor_ok=1
if [ "$outline_ok" -eq 0 ] && [ "$editor_ok" -eq 0 ]; then
exit 0
fi
if [ "$outline_ok" -ne 0 ]; then
if ! min_is_fresh "$OUTLINE_PKG" birchoutline.js; then
gulp_prepublish "$OUTLINE_PKG"
verify_min "$OUTLINE_PKG/min/birchoutline.js"
fi
update_bundle "$OUTLINE_PKG/min/birchoutline.js" "$OUTLINE_DEP" "$OUTLINE_MANIFEST" "$OUTLINE_INPUTS"
fi
if [ "$editor_ok" -ne 0 ]; then
# The editor's webpack resolves birch-outline through its gitignored lib/ output,
# which must exist and be current before the editor bundle can build.
if [ ! -f "$OUTLINE_PKG/lib/index.js" ] || ! min_is_fresh "$OUTLINE_PKG" birchoutline.js; then
gulp_prepublish "$OUTLINE_PKG"
fi
if ! min_is_fresh "$EDITOR_PKG" bircheditor.js "$OUTLINE_PKG/src"; then
gulp_prepublish "$EDITOR_PKG"
verify_min "$EDITOR_PKG/min/bircheditor.js"
fi
update_bundle "$EDITOR_PKG/min/bircheditor.js" "$EDITOR_DEP" "$EDITOR_MANIFEST" "$EDITOR_INPUTS"
fi