Skip to content

Commit 3116639

Browse files
feat(makefile): sync internal targets with dev-toolchain (#5)
Add Rust support (HAS_RUST, clippy, cargo fmt, cargo test, cargo-audit, cargo-deny), Terragrunt support (hclfmt in _format/_fix, version reporting in _docs), and the _fix target that was added in v1.3.0 but never synced to templates. Co-authored-by: Claude Opus 4.6 <noreply@anthropic.com>
1 parent 3c21191 commit 3116639

1 file changed

Lines changed: 243 additions & 0 deletions

File tree

Makefile

Lines changed: 243 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -40,6 +40,7 @@ HAS_ANSIBLE := $(filter ansible,$(LANGUAGES))
4040
HAS_RUBY := $(filter ruby,$(LANGUAGES))
4141
HAS_GO := $(filter go,$(LANGUAGES))
4242
HAS_JAVASCRIPT := $(filter javascript,$(LANGUAGES))
43+
HAS_RUST := $(filter rust,$(LANGUAGES))
4344

4445
# ---------------------------------------------------------------------------
4546
# .PHONY declarations
@@ -255,6 +256,21 @@ _lint: _check-config
255256
exit $$overall_exit; \
256257
fi; \
257258
fi; \
259+
if [ -n "$(HAS_RUST)" ]; then \
260+
ran_languages="$${ran_languages}\"rust\","; \
261+
rs_files=$$(find . -name '*.rs' -not -path './.git/*' -not -path './vendor/*' -not -path './target/*' 2>/dev/null); \
262+
if [ -n "$$rs_files" ]; then \
263+
cargo clippy --all-targets --all-features -- -D warnings || { overall_exit=1; failed_languages="$${failed_languages}\"rust\","; }; \
264+
else \
265+
echo '{"level":"info","msg":"skipping rust lint: no .rs files found","language":"rust"}' >&2; \
266+
fi; \
267+
if [ "$(DEVRAIL_FAIL_FAST)" = "1" ] && [ $$overall_exit -ne 0 ]; then \
268+
end_time=$$(date +%s%3N); \
269+
duration=$$((end_time - start_time)); \
270+
echo "{\"target\":\"lint\",\"status\":\"fail\",\"duration_ms\":$$duration,\"languages\":[$${ran_languages%,}],\"failed\":[$${failed_languages%,}]}"; \
271+
exit $$overall_exit; \
272+
fi; \
273+
fi; \
258274
end_time=$$(date +%s%3N); \
259275
duration=$$((end_time - start_time)); \
260276
if [ $$overall_exit -eq 0 ]; then \
@@ -298,6 +314,10 @@ _format: _check-config
298314
if [ -n "$(HAS_TERRAFORM)" ]; then \
299315
ran_languages="$${ran_languages}\"terraform\","; \
300316
terraform fmt -check -recursive || { overall_exit=1; failed_languages="$${failed_languages}\"terraform\","; }; \
317+
tg_files=$$(find . -name 'terragrunt.hcl' -not -path './.git/*' -not -path './.terraform/*' 2>/dev/null); \
318+
if [ -n "$$tg_files" ]; then \
319+
terragrunt hclfmt --terragrunt-check || { overall_exit=1; failed_languages="$${failed_languages}\"terraform:terragrunt\","; }; \
320+
fi; \
301321
if [ "$(DEVRAIL_FAIL_FAST)" = "1" ] && [ $$overall_exit -ne 0 ]; then \
302322
end_time=$$(date +%s%3N); \
303323
duration=$$((end_time - start_time)); \
@@ -354,6 +374,21 @@ _format: _check-config
354374
exit $$overall_exit; \
355375
fi; \
356376
fi; \
377+
if [ -n "$(HAS_RUST)" ]; then \
378+
ran_languages="$${ran_languages}\"rust\","; \
379+
rs_files=$$(find . -name '*.rs' -not -path './.git/*' -not -path './vendor/*' -not -path './target/*' 2>/dev/null); \
380+
if [ -n "$$rs_files" ]; then \
381+
cargo fmt --all -- --check || { overall_exit=1; failed_languages="$${failed_languages}\"rust\","; }; \
382+
else \
383+
echo '{"level":"info","msg":"skipping rust format: no .rs files found","language":"rust"}' >&2; \
384+
fi; \
385+
if [ "$(DEVRAIL_FAIL_FAST)" = "1" ] && [ $$overall_exit -ne 0 ]; then \
386+
end_time=$$(date +%s%3N); \
387+
duration=$$((end_time - start_time)); \
388+
echo "{\"target\":\"format\",\"status\":\"fail\",\"duration_ms\":$$duration,\"languages\":[$${ran_languages%,}],\"failed\":[$${failed_languages%,}]}"; \
389+
exit $$overall_exit; \
390+
fi; \
391+
fi; \
357392
end_time=$$(date +%s%3N); \
358393
duration=$$((end_time - start_time)); \
359394
if [ $$overall_exit -eq 0 ]; then \
@@ -363,6 +398,124 @@ _format: _check-config
363398
fi; \
364399
exit $$overall_exit
365400

401+
# --- _fix: language-specific format fixing (in-place) ---
402+
_fix: _check-config
403+
@start_time=$$(date +%s%3N); \
404+
overall_exit=0; \
405+
ran_languages=""; \
406+
failed_languages=""; \
407+
if [ -n "$(HAS_PYTHON)" ]; then \
408+
ran_languages="$${ran_languages}\"python\","; \
409+
ruff format . || { overall_exit=1; failed_languages="$${failed_languages}\"python\","; }; \
410+
if [ "$(DEVRAIL_FAIL_FAST)" = "1" ] && [ $$overall_exit -ne 0 ]; then \
411+
end_time=$$(date +%s%3N); \
412+
duration=$$((end_time - start_time)); \
413+
echo "{\"target\":\"fix\",\"status\":\"fail\",\"duration_ms\":$$duration,\"languages\":[$${ran_languages%,}],\"failed\":[$${failed_languages%,}]}"; \
414+
exit $$overall_exit; \
415+
fi; \
416+
fi; \
417+
if [ -n "$(HAS_BASH)" ]; then \
418+
ran_languages="$${ran_languages}\"bash\","; \
419+
sh_files=$$(find . -name '*.sh' -not -path './.git/*' -not -path './vendor/*' -not -path './node_modules/*' 2>/dev/null); \
420+
if [ -n "$$sh_files" ]; then \
421+
echo "$$sh_files" | xargs shfmt -w || { overall_exit=1; failed_languages="$${failed_languages}\"bash\","; }; \
422+
else \
423+
echo '{"level":"info","msg":"skipping bash fix: no .sh files found","language":"bash"}' >&2; \
424+
fi; \
425+
if [ "$(DEVRAIL_FAIL_FAST)" = "1" ] && [ $$overall_exit -ne 0 ]; then \
426+
end_time=$$(date +%s%3N); \
427+
duration=$$((end_time - start_time)); \
428+
echo "{\"target\":\"fix\",\"status\":\"fail\",\"duration_ms\":$$duration,\"languages\":[$${ran_languages%,}],\"failed\":[$${failed_languages%,}]}"; \
429+
exit $$overall_exit; \
430+
fi; \
431+
fi; \
432+
if [ -n "$(HAS_TERRAFORM)" ]; then \
433+
ran_languages="$${ran_languages}\"terraform\","; \
434+
terraform fmt -recursive || { overall_exit=1; failed_languages="$${failed_languages}\"terraform\","; }; \
435+
tg_files=$$(find . -name 'terragrunt.hcl' -not -path './.git/*' -not -path './.terraform/*' 2>/dev/null); \
436+
if [ -n "$$tg_files" ]; then \
437+
terragrunt hclfmt || { overall_exit=1; failed_languages="$${failed_languages}\"terraform:terragrunt\","; }; \
438+
fi; \
439+
if [ "$(DEVRAIL_FAIL_FAST)" = "1" ] && [ $$overall_exit -ne 0 ]; then \
440+
end_time=$$(date +%s%3N); \
441+
duration=$$((end_time - start_time)); \
442+
echo "{\"target\":\"fix\",\"status\":\"fail\",\"duration_ms\":$$duration,\"languages\":[$${ran_languages%,}],\"failed\":[$${failed_languages%,}]}"; \
443+
exit $$overall_exit; \
444+
fi; \
445+
fi; \
446+
if [ -n "$(HAS_ANSIBLE)" ]; then \
447+
ran_languages="$${ran_languages}\"ansible\","; \
448+
echo '{"target":"fix","language":"ansible","status":"skip","reason":"no formatter configured"}' >&2; \
449+
fi; \
450+
if [ -n "$(HAS_RUBY)" ]; then \
451+
ran_languages="$${ran_languages}\"ruby\","; \
452+
rb_files=$$(find . -name '*.rb' -not -path './.git/*' -not -path './vendor/*' -not -path './node_modules/*' 2>/dev/null); \
453+
if [ -n "$$rb_files" ]; then \
454+
rubocop -a . || { overall_exit=1; failed_languages="$${failed_languages}\"ruby\","; }; \
455+
else \
456+
echo '{"level":"info","msg":"skipping ruby fix: no .rb files found","language":"ruby"}' >&2; \
457+
fi; \
458+
if [ "$(DEVRAIL_FAIL_FAST)" = "1" ] && [ $$overall_exit -ne 0 ]; then \
459+
end_time=$$(date +%s%3N); \
460+
duration=$$((end_time - start_time)); \
461+
echo "{\"target\":\"fix\",\"status\":\"fail\",\"duration_ms\":$$duration,\"languages\":[$${ran_languages%,}],\"failed\":[$${failed_languages%,}]}"; \
462+
exit $$overall_exit; \
463+
fi; \
464+
fi; \
465+
if [ -n "$(HAS_GO)" ]; then \
466+
ran_languages="$${ran_languages}\"go\","; \
467+
go_files=$$(find . -name '*.go' -not -path './.git/*' -not -path './vendor/*' -not -path './node_modules/*' 2>/dev/null); \
468+
if [ -n "$$go_files" ]; then \
469+
gofumpt -w . || { overall_exit=1; failed_languages="$${failed_languages}\"go\","; }; \
470+
else \
471+
echo '{"level":"info","msg":"skipping go fix: no .go files found","language":"go"}' >&2; \
472+
fi; \
473+
if [ "$(DEVRAIL_FAIL_FAST)" = "1" ] && [ $$overall_exit -ne 0 ]; then \
474+
end_time=$$(date +%s%3N); \
475+
duration=$$((end_time - start_time)); \
476+
echo "{\"target\":\"fix\",\"status\":\"fail\",\"duration_ms\":$$duration,\"languages\":[$${ran_languages%,}],\"failed\":[$${failed_languages%,}]}"; \
477+
exit $$overall_exit; \
478+
fi; \
479+
fi; \
480+
if [ -n "$(HAS_JAVASCRIPT)" ]; then \
481+
ran_languages="$${ran_languages}\"javascript\","; \
482+
js_files=$$(find . \( -name '*.js' -o -name '*.jsx' -o -name '*.ts' -o -name '*.tsx' -o -name '*.mjs' -o -name '*.cjs' \) -not -path './.git/*' -not -path './vendor/*' -not -path './node_modules/*' -not -path './dist/*' -not -path './build/*' 2>/dev/null); \
483+
if [ -n "$$js_files" ]; then \
484+
prettier --write . || { overall_exit=1; failed_languages="$${failed_languages}\"javascript\","; }; \
485+
else \
486+
echo '{"level":"info","msg":"skipping javascript fix: no JS/TS files found","language":"javascript"}' >&2; \
487+
fi; \
488+
if [ "$(DEVRAIL_FAIL_FAST)" = "1" ] && [ $$overall_exit -ne 0 ]; then \
489+
end_time=$$(date +%s%3N); \
490+
duration=$$((end_time - start_time)); \
491+
echo "{\"target\":\"fix\",\"status\":\"fail\",\"duration_ms\":$$duration,\"languages\":[$${ran_languages%,}],\"failed\":[$${failed_languages%,}]}"; \
492+
exit $$overall_exit; \
493+
fi; \
494+
fi; \
495+
if [ -n "$(HAS_RUST)" ]; then \
496+
ran_languages="$${ran_languages}\"rust\","; \
497+
rs_files=$$(find . -name '*.rs' -not -path './.git/*' -not -path './vendor/*' -not -path './target/*' 2>/dev/null); \
498+
if [ -n "$$rs_files" ]; then \
499+
cargo fmt --all || { overall_exit=1; failed_languages="$${failed_languages}\"rust\","; }; \
500+
else \
501+
echo '{"level":"info","msg":"skipping rust fix: no .rs files found","language":"rust"}' >&2; \
502+
fi; \
503+
if [ "$(DEVRAIL_FAIL_FAST)" = "1" ] && [ $$overall_exit -ne 0 ]; then \
504+
end_time=$$(date +%s%3N); \
505+
duration=$$((end_time - start_time)); \
506+
echo "{\"target\":\"fix\",\"status\":\"fail\",\"duration_ms\":$$duration,\"languages\":[$${ran_languages%,}],\"failed\":[$${failed_languages%,}]}"; \
507+
exit $$overall_exit; \
508+
fi; \
509+
fi; \
510+
end_time=$$(date +%s%3N); \
511+
duration=$$((end_time - start_time)); \
512+
if [ $$overall_exit -eq 0 ]; then \
513+
echo "{\"target\":\"fix\",\"status\":\"pass\",\"duration_ms\":$$duration,\"languages\":[$${ran_languages%,}]}"; \
514+
else \
515+
echo "{\"target\":\"fix\",\"status\":\"fail\",\"duration_ms\":$$duration,\"languages\":[$${ran_languages%,}],\"failed\":[$${failed_languages%,}]}"; \
516+
fi; \
517+
exit $$overall_exit
518+
366519
# --- _test: language-specific test runners ---
367520
_test: _check-config
368521
@start_time=$$(date +%s%3N); \
@@ -475,6 +628,22 @@ _test: _check-config
475628
exit $$overall_exit; \
476629
fi; \
477630
fi; \
631+
if [ -n "$(HAS_RUST)" ]; then \
632+
rs_files=$$(find . -name '*.rs' -not -path './.git/*' -not -path './vendor/*' -not -path './target/*' 2>/dev/null); \
633+
if [ -n "$$rs_files" ] && [ -f "Cargo.toml" ]; then \
634+
ran_languages="$${ran_languages}\"rust\","; \
635+
cargo test --all-targets || { overall_exit=1; failed_languages="$${failed_languages}\"rust\","; }; \
636+
else \
637+
skipped_languages="$${skipped_languages}\"rust\","; \
638+
echo '{"level":"info","msg":"skipping rust tests: no .rs files or Cargo.toml found","language":"rust"}' >&2; \
639+
fi; \
640+
if [ "$(DEVRAIL_FAIL_FAST)" = "1" ] && [ $$overall_exit -ne 0 ]; then \
641+
end_time=$$(date +%s%3N); \
642+
duration=$$((end_time - start_time)); \
643+
echo "{\"target\":\"test\",\"status\":\"fail\",\"duration_ms\":$$duration,\"languages\":[$${ran_languages%,}],\"failed\":[$${failed_languages%,}],\"skipped\":[$${skipped_languages%,}]}"; \
644+
exit $$overall_exit; \
645+
fi; \
646+
fi; \
478647
end_time=$$(date +%s%3N); \
479648
duration=$$((end_time - start_time)); \
480649
if [ -z "$${ran_languages}" ] && [ -n "$${skipped_languages}" ]; then \
@@ -590,6 +759,32 @@ _security: _check-config
590759
exit $$overall_exit; \
591760
fi; \
592761
fi; \
762+
if [ -n "$(HAS_RUST)" ]; then \
763+
if [ -f "Cargo.lock" ]; then \
764+
ran_languages="$${ran_languages}\"rust\","; \
765+
cargo audit || { overall_exit=1; failed_languages="$${failed_languages}\"rust:cargo-audit\","; }; \
766+
else \
767+
skipped_languages="$${skipped_languages}\"rust:cargo-audit\","; \
768+
echo '{"level":"info","msg":"skipping cargo audit: no Cargo.lock found","language":"rust"}' >&2; \
769+
fi; \
770+
if [ "$(DEVRAIL_FAIL_FAST)" = "1" ] && [ $$overall_exit -ne 0 ]; then \
771+
end_time=$$(date +%s%3N); \
772+
duration=$$((end_time - start_time)); \
773+
echo "{\"target\":\"security\",\"status\":\"fail\",\"duration_ms\":$$duration,\"languages\":[$${ran_languages%,}],\"failed\":[$${failed_languages%,}]}"; \
774+
exit $$overall_exit; \
775+
fi; \
776+
if [ -f "deny.toml" ]; then \
777+
cargo deny check || { overall_exit=1; failed_languages="$${failed_languages}\"rust:cargo-deny\","; }; \
778+
else \
779+
echo '{"level":"info","msg":"skipping cargo deny: no deny.toml found","language":"rust"}' >&2; \
780+
fi; \
781+
if [ "$(DEVRAIL_FAIL_FAST)" = "1" ] && [ $$overall_exit -ne 0 ]; then \
782+
end_time=$$(date +%s%3N); \
783+
duration=$$((end_time - start_time)); \
784+
echo "{\"target\":\"security\",\"status\":\"fail\",\"duration_ms\":$$duration,\"languages\":[$${ran_languages%,}],\"failed\":[$${failed_languages%,}]}"; \
785+
exit $$overall_exit; \
786+
fi; \
787+
fi; \
593788
end_time=$$(date +%s%3N); \
594789
duration=$$((end_time - start_time)); \
595790
if [ -z "$${ran_languages}" ] && [ -n "$${skipped_languages}" ]; then \
@@ -682,6 +877,7 @@ _docs: _check-config
682877
_tv tfsec "tfsec --version"; \
683878
_tv checkov "checkov --version"; \
684879
_tv terraform-docs "terraform-docs --version"; \
880+
_tv terragrunt "terragrunt --version"; \
685881
fi; \
686882
if [ -n "$(HAS_ANSIBLE)" ]; then \
687883
_tv ansible-lint "ansible-lint --version"; \
@@ -709,6 +905,14 @@ _docs: _check-config
709905
_tv tsc "tsc --version"; \
710906
_tv vitest "vitest --version"; \
711907
fi; \
908+
if [ -n "$(HAS_RUST)" ]; then \
909+
_tv rustc "rustc --version"; \
910+
_tv cargo "cargo --version"; \
911+
_tv clippy "cargo clippy --version"; \
912+
_tv rustfmt "rustfmt --version"; \
913+
_tv cargo-audit "cargo audit --version"; \
914+
_tv cargo-deny "cargo deny --version"; \
915+
fi; \
712916
_tv trivy "trivy --version"; \
713917
_tv gitleaks "gitleaks version"; \
714918
_tv git-cliff "git-cliff --version"; \
@@ -915,6 +1119,45 @@ _init: _check-config
9151119
'build/' \
9161120
'coverage/'; \
9171121
fi; \
1122+
if [ -n "$(HAS_RUST)" ]; then \
1123+
scaffold clippy.toml \
1124+
'# clippy.toml -- DevRail Rust clippy configuration' \
1125+
'# See: https://doc.rust-lang.org/clippy/lint_configuration.html' \
1126+
'too-many-arguments-threshold = 7'; \
1127+
scaffold rustfmt.toml \
1128+
'# rustfmt.toml -- DevRail Rust formatter configuration' \
1129+
'edition = "2021"' \
1130+
'max_width = 100' \
1131+
'use_field_init_shorthand = true' \
1132+
'use_try_shorthand = true'; \
1133+
scaffold deny.toml \
1134+
'# deny.toml -- DevRail cargo-deny configuration' \
1135+
'# See: https://embarkstudios.github.io/cargo-deny/' \
1136+
'' \
1137+
'[advisories]' \
1138+
'vulnerability = "deny"' \
1139+
'unmaintained = "warn"' \
1140+
'yanked = "warn"' \
1141+
'' \
1142+
'[licenses]' \
1143+
'unlicensed = "deny"' \
1144+
'allow = [' \
1145+
' "MIT",' \
1146+
' "Apache-2.0",' \
1147+
' "BSD-2-Clause",' \
1148+
' "BSD-3-Clause",' \
1149+
' "ISC",' \
1150+
' "Unicode-3.0",' \
1151+
' "Unicode-DFS-2016",' \
1152+
']' \
1153+
'' \
1154+
'[bans]' \
1155+
'multiple-versions = "warn"' \
1156+
'' \
1157+
'[sources]' \
1158+
'unknown-registry = "deny"' \
1159+
'unknown-git = "warn"'; \
1160+
fi; \
9181161
echo "{\"target\":\"init\",\"created\":[$${created%,}],\"skipped\":[$${skipped%,}]}"
9191162

9201163
# --- _check: orchestrate all targets ---

0 commit comments

Comments
 (0)