-
Notifications
You must be signed in to change notification settings - Fork 3
Expand file tree
/
Copy pathMakefile
More file actions
355 lines (313 loc) · 13.2 KB
/
Makefile
File metadata and controls
355 lines (313 loc) · 13.2 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
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
.DEFAULT_GOAL := help
SIMULATOR_DESTINATION := platform=iOS Simulator,name=iPhone 17
.PHONY: help
help: ## Display this help menu
@echo "Usage: make [target]"
@echo ""
@echo "Available targets:"
@grep -E '^[a-zA-Z0-9_-]+:.*?## ' $(MAKEFILE_LIST) | \
awk 'BEGIN {FS = ":.*?## "}; {printf " \033[36m%-25s\033[0m %s\n", $$1, $$2}' | \
sort
@echo ""
define XCODEBUILD_CMD
@set -o pipefail && \
xcodebuild $(1) \
-scheme GutenbergKit \
-sdk iphonesimulator \
-destination '${SIMULATOR_DESTINATION}' \
| xcbeautify
endef
################################################################################
# Utility Targets
################################################################################
.PHONY: npm-dependencies
npm-dependencies: ## Install npm dependencies
# Skip unless...
# - node_modules doesn't exist
# - REFRESH_DEPS is set to true or 1
# - npm-dependencies was invoked directly
@if [ ! -d "node_modules" ] || [ "$(REFRESH_DEPS)" = "true" ] || [ "$(REFRESH_DEPS)" = "1" ] || echo "$(MAKECMDGOALS)" | grep -q "^npm-dependencies$$"; then \
echo "--- :npm: Installing NPM Dependencies"; \
npm ci; \
else \
echo "--- :white_check_mark: Skipping NPM dependencies installation (node_modules already exists). Use REFRESH_DEPS=1 to force refresh."; \
fi
.PHONY: prep-translations
prep-translations: ## Fetch and cache locale string files
# Skip unless...
# - src/translations doesn't exist
# - REFRESH_L10N is set to true or 1
# - prep-translations was invoked directly
@if [ ! -d "src/translations" ] || [ "$(REFRESH_L10N)" = "true" ] || [ "$(REFRESH_L10N)" = "1" ] || echo "$(MAKECMDGOALS)" | grep -q "^prep-translations$$"; then \
echo "--- :npm: Preparing Translations"; \
if ! npm run prep-translations -- --force; then \
if [ "$(STRICT_L10N)" = "true" ] || [ "$(STRICT_L10N)" = "1" ]; then \
echo "--- :x: ERROR: Translation fetching failed and STRICT_L10N is enabled"; \
exit 1; \
else \
echo "--- :warning: WARNING: Translation fetching failed, but continuing anyway. Use STRICT_L10N=1 to make this fatal."; \
fi; \
fi; \
else \
echo "--- :white_check_mark: Skipping translations fetch (src/translations already exists). Use REFRESH_L10N=1 to force refresh."; \
fi
.PHONY: e2e-dependencies
e2e-dependencies: npm-dependencies ## Install E2E test dependencies
@CHROMIUM_PATH=$$(npx playwright install --dry-run chromium 2>&1 | grep "Install location" | head -1 | sed 's/.*: *//'); \
if [ -d "$$CHROMIUM_PATH" ]; then \
echo "--- :white_check_mark: Playwright Chromium is already installed."; \
elif [ -n "$$CI" ]; then \
echo "--- :chromium: Installing Playwright Chromium"; \
npx playwright install chromium; \
else \
echo ""; \
echo "Playwright Chromium browser is not installed."; \
echo "It is required to run E2E tests."; \
echo ""; \
printf "Install it now? [Y/n] "; \
read -r answer; \
if [ "$$answer" != "n" ] && [ "$$answer" != "N" ]; then \
npx playwright install chromium; \
else \
echo "Skipping install. Run 'npx playwright install chromium' manually to install."; \
exit 1; \
fi; \
fi
.PHONY: clean
clean: ## Remove build artifacts and translation string files
npm run clean
################################################################################
# Build Targets
################################################################################
.PHONY: build
build: npm-dependencies prep-translations ## Build the project for all platforms (iOS, Android, web)
# Skip unless...
# - dist doesn't exist
# - REFRESH_JS_BUILD is set to true or 1
# - build was invoked directly
@if [ ! -d "dist" ] || [ "$(REFRESH_JS_BUILD)" = "true" ] || [ "$(REFRESH_JS_BUILD)" = "1" ] || echo "$(MAKECMDGOALS)" | grep -q "^build$$"; then \
echo "--- :node: Building Gutenberg"; \
npm run build; \
echo "--- :open_file_folder: Copying Build Products into place"; \
rm -rf ./ios/Sources/GutenbergKit/Gutenberg/ ./android/Gutenberg/src/main/assets/; \
cp -r ./dist/. ./ios/Sources/GutenbergKit/Gutenberg/; \
cp -r ./dist/. ./android/Gutenberg/src/main/assets; \
else \
echo "--- :white_check_mark: Skipping JS build (dist already exists). Use REFRESH_JS_BUILD=1 to force refresh."; \
fi
.PHONY: build-swift-package
build-swift-package: build ## Build the Swift package for iOS
$(call XCODEBUILD_CMD, build)
.PHONY: local-android-library
local-android-library: build ## Build the Android library to local Maven
@echo "--- :android: Building Library"
./android/gradlew -p ./android :gutenberg:publishToMavenLocal -exclude-task prepareToPublishToS3
################################################################################
# Development Targets
################################################################################
.PHONY: dev-server
dev-server: npm-dependencies ## Start the development server
npm run dev
.PHONY: dev-server-force
dev-server-force: npm-dependencies ## Start the development server, ignore the cache and re-bundle
npm run dev:force
.PHONY: dev-tools
dev-tools: npm-dependencies ## Start the React Developer Tools
npm run dev:tools
.PHONY: preview
preview: npm-dependencies ## Preview the production build locally
npm run preview
################################################################################
# Local WordPress Environment Targets (wp-env)
################################################################################
.PHONY: wp-env-start
wp-env-start: npm-dependencies ## Start the local WordPress environment (RESET=1 to regenerate credentials)
npm run wp-env start -- --runtime=playground
@RESET=$(RESET) bash bin/wp-env-setup.sh
.PHONY: wp-env-stop
wp-env-stop: ## Stop the local WordPress environment
npm run wp-env stop
.PHONY: wp-env-clean
wp-env-clean: ## Stop wp-env and remove all data (fresh start)
npm run wp-env destroy
@rm -f .wp-env.credentials.json
.PHONY: wp-env-android
wp-env-android: ## Remap wp-env site URLs for the Android emulator and restart
@cp wp-env/android-url-override.php wp-env/mu-plugins/gutenbergkit-android-urls.php
@RESET=1 $(MAKE) wp-env-start
.PHONY: wp-env-android-reset
wp-env-android-reset: ## Remove the Android emulator URL remap and restart
@rm -f wp-env/mu-plugins/gutenbergkit-android-urls.php
@RESET=1 $(MAKE) wp-env-start
################################################################################
# Code Quality Targets
################################################################################
.PHONY: format
format: npm-dependencies ## Format code
npm run format
.PHONY: lint-js
lint-js: npm-dependencies ## Lint JavaScript code
npm run lint:js
.PHONY: lint-fix-js
lint-js-fix: npm-dependencies ## Lint and auto-fix JavaScript code
npm run lint:js:fix
.PHONY: lint-swift
lint-swift: ## Lint Swift code
swift package plugin swiftlint
################################################################################
# Testing Targets
################################################################################
.PHONY: test-e2e
test-e2e: e2e-dependencies ## Run end-to-end tests
@if [ ! -d "dist" ]; then \
$(MAKE) build; \
else \
echo "--- :white_check_mark: Using existing build. Use 'make build REFRESH_JS_BUILD=1' to rebuild."; \
fi
npm run test:e2e
.PHONY: test-e2e-ui
test-e2e-ui: e2e-dependencies ## Run end-to-end tests in UI mode
@if [ ! -d "dist" ]; then \
$(MAKE) build; \
else \
echo "--- :white_check_mark: Using existing build. Use 'make build REFRESH_JS_BUILD=1' to rebuild."; \
fi
npm run test:e2e:ui
.PHONY: test-js
test-js: npm-dependencies ## Run JavaScript tests
npm run test:unit
.PHONY: test-js-watch
test-js-watch: npm-dependencies ## Run JavaScript tests in watch mode
npm run test:unit:watch
.PHONY: test-swift-package
test-swift-package: build ## Run Swift package tests
$(call XCODEBUILD_CMD, test)
.PHONY: test-ios-e2e
test-ios-e2e: ## Run iOS E2E tests against the production build
@if [ ! -d "dist" ]; then \
$(MAKE) build; \
else \
echo "--- :white_check_mark: Using existing build. Use 'make build REFRESH_JS_BUILD=1' to rebuild."; \
fi
@echo "--- :open_file_folder: Copying build into iOS bundle"
@rm -rf ./ios/Sources/GutenbergKit/Gutenberg/
@cp -r ./dist/. ./ios/Sources/GutenbergKit/Gutenberg/
@echo "--- :ios: Running iOS E2E Tests (production build)"
@set -o pipefail && \
xcodebuild test \
-project ./ios/Demo-iOS/Gutenberg.xcodeproj \
-scheme GutenbergUITests \
-sdk iphonesimulator \
-destination '${SIMULATOR_DESTINATION}' \
| xcbeautify
.PHONY: test-ios-e2e-dev
test-ios-e2e-dev: ## Run iOS E2E tests against the Vite dev server (must be running)
@if ! curl -sf http://localhost:5173 > /dev/null 2>&1; then \
echo "Error: Dev server is not running at http://localhost:5173"; \
echo "Start it first with: make dev-server"; \
exit 1; \
fi
@echo "--- :ios: Running iOS E2E Tests (dev server)"
@set -o pipefail && \
TEST_RUNNER_GUTENBERG_EDITOR_URL=http://localhost:5173 \
xcodebuild test \
-project ./ios/Demo-iOS/Gutenberg.xcodeproj \
-scheme GutenbergUITests \
-sdk iphonesimulator \
-destination '${SIMULATOR_DESTINATION}' \
| xcbeautify
.PHONY: test-android
test-android: ## Run Android tests
@echo "--- :android: Running Android Tests"
./android/gradlew -p ./android :gutenberg:test
# Ensure an Android device or emulator is available for instrumented tests.
# Checks for any connected device; if none found, boots the first available AVD.
define ENSURE_ANDROID_DEVICE
@if adb devices 2>/dev/null | tail -n +2 | grep -q 'device$$'; then \
echo "--- :white_check_mark: Android device already connected."; \
else \
AVD=$$("$$ANDROID_HOME/emulator/emulator" -list-avds 2>/dev/null | head -n 1); \
if [ -z "$$AVD" ]; then \
echo "Error: No Android device connected and no AVDs found."; \
echo "Connect a device, start an emulator, or create an AVD with Android Studio."; \
exit 1; \
fi; \
echo "--- :rocket: Booting Android emulator ($$AVD)..."; \
"$$ANDROID_HOME/emulator/emulator" -avd "$$AVD" -no-snapshot-load -no-audio -no-window &>/dev/null & \
EMULATOR_PID=$$!; \
echo "--- :hourglass: Waiting for emulator to boot..."; \
adb wait-for-device; \
BOOT_WAIT=0; \
while [ "$$(adb shell getprop sys.boot_completed 2>/dev/null | tr -d '\r')" != "1" ]; do \
BOOT_WAIT=$$((BOOT_WAIT + 1)); \
if [ $$BOOT_WAIT -gt 60 ]; then \
echo "Error: Emulator boot timed out after 120 seconds."; \
kill $$EMULATOR_PID 2>/dev/null; \
exit 1; \
fi; \
sleep 2; \
done; \
echo "--- :white_check_mark: Emulator booted."; \
fi
endef
.PHONY: test-android-e2e
test-android-e2e: ## Run Android E2E tests against the production build
@if [ ! -d "dist" ]; then \
$(MAKE) build; \
else \
echo "--- :white_check_mark: Using existing build. Use 'make build REFRESH_JS_BUILD=1' to rebuild."; \
fi
@echo "--- :open_file_folder: Copying build into Android bundle"
@rm -rf ./android/Gutenberg/src/main/assets/
@cp -r ./dist/. ./android/Gutenberg/src/main/assets
$(ENSURE_ANDROID_DEVICE)
@echo "--- :android: Running Android E2E Tests (production build)"
./android/gradlew -p ./android :app:connectedDebugAndroidTest
.PHONY: test-android-e2e-dev
test-android-e2e-dev: ## Run Android E2E tests against the Vite dev server (must be running)
@if ! curl -sf http://localhost:5173 > /dev/null 2>&1; then \
echo "Error: Dev server is not running at http://localhost:5173"; \
echo "Start it first with: make dev-server"; \
exit 1; \
fi
$(ENSURE_ANDROID_DEVICE)
@echo "--- :android: Running Android E2E Tests (dev server)"
./android/gradlew -p ./android :app:connectedDebugAndroidTest
################################################################################
# Release Target
################################################################################
.PHONY: release
release: ## Create and publish a new release
@echo "--- :rocket: Starting GutenbergKit Release Process"
@echo "Usage: make release VERSION_TYPE=[<newversion> | major | minor | patch | premajor | preminor | prepatch | prerelease | from-git] [DRY_RUN=true]"
@echo ""
@echo "Version Types:"
@echo " <newversion> Custom version number (e.g., 1.2.3)"
@echo " major Increment major version (1.0.0 -> 2.0.0)"
@echo " minor Increment minor version (1.2.0 -> 1.3.0)"
@echo " patch Increment patch version (1.2.3 -> 1.2.4)"
@echo " premajor Increment major version and add prerelease (1.2.3 -> 2.0.0-alpha.0)"
@echo " preminor Increment minor version and add prerelease (1.2.3 -> 1.3.0-alpha.0)"
@echo " prepatch Increment patch version and add prerelease (1.2.3 -> 1.2.4-alpha.0)"
@echo " prerelease Increment prerelease version (1.2.3-alpha.0 -> 1.2.3-alpha.1)"
@echo " from-git Use version from git tag"
@echo ""
@echo "Examples:"
@echo " make release VERSION_TYPE=patch"
@echo " make release VERSION_TYPE=minor"
@echo " make release VERSION_TYPE=major"
@echo " make release VERSION_TYPE=1.2.3"
@echo " make release VERSION_TYPE=premajor"
@echo " make release VERSION_TYPE=prerelease"
@echo " make release VERSION_TYPE=patch DRY_RUN=true"
@echo ""
@if [ -z "$(VERSION_TYPE)" ]; then \
echo "Error: VERSION_TYPE is required."; \
echo "Use one of: <newversion>, major, minor, patch, premajor, preminor, prepatch, prerelease, from-git"; \
exit 1; \
fi
@if [ "$(DRY_RUN)" = "true" ]; then \
./bin/release.sh $(VERSION_TYPE) --dry-run; \
else \
./bin/release.sh $(VERSION_TYPE); \
fi