diff --git a/apps/backend/Makefile b/apps/backend/Makefile index 45706867d5..0bfba0616c 100644 --- a/apps/backend/Makefile +++ b/apps/backend/Makefile @@ -45,10 +45,13 @@ endif ifeq ($(OS)$(MSYSTEM),Windows_NT) RM = cmd /c del /s /q RMDIR = cmd /c rmdir /s /q - # cmd's `mkdir` errors when the dir already exists, unlike Unix `mkdir -p`. - # Call sites use `-@$(MKDIR) $(BUILD_DIR)` (note the `-` prefix) so the - # "already exists" failure is tolerated; on Unix the prefix is a no-op. - MKDIR = cmd /c mkdir + # cmd's `mkdir` errors and prints "A subdirectory or file already + # exists." when the dir is already there, unlike Unix `mkdir -p`. Check for + # the directory first so that expected repeats stay quiet while permission + # and invalid-path errors keep their stderr and exit status. + define MKDIR + cmd /c if not exist "$(subst /,\,$(1))" mkdir "$(subst /,\,$(1))" + endef CGO_PREFIX = set CGO_ENABLED=1& DEADCODE_ENV = set GOTOOLCHAIN=$(DEADCODE_GO_TOOLCHAIN)& # Cross-compile prefixes for agentctl helpers bundled with the host build. @@ -78,7 +81,9 @@ ifeq ($(OS)$(MSYSTEM),Windows_NT) else RM = rm -f RMDIR = rm -rf - MKDIR = mkdir -p + define MKDIR + mkdir -p "$(1)" + endef CGO_PREFIX = CGO_ENABLED=1 DEADCODE_ENV = GOTOOLCHAIN=$(DEADCODE_GO_TOOLCHAIN) GO_LINUX_AMD64 = CGO_ENABLED=0 GOOS=linux GOARCH=amd64 @@ -166,13 +171,13 @@ all: build ## Build the preview CLI for deploying PR preview environments to Sprites build-preview: @echo "Building preview..." - -@$(MKDIR) $(BUILD_DIR) + @$(call MKDIR,$(BUILD_DIR)) $(GO) build $(GOFLAGS) -ldflags "$(LDFLAGS)" -o $(BUILD_DIR)/preview$(EXE) ./cmd/preview ## Build the mock-agent binary for testing build-mock-agent: @echo "Building mock-agent..." - -@$(MKDIR) $(BUILD_DIR) + @$(call MKDIR,$(BUILD_DIR)) $(GO) build $(GOFLAGS) -ldflags "$(LDFLAGS)" -o $(BUILD_DIR)/mock-agent$(EXE) ./cmd/mock-agent ## Build the winjob helper — wraps a subprocess in a Windows Job Object so @@ -183,7 +188,7 @@ build-mock-agent: ## helper stays for any other consumer. build-winjob: @echo "Building winjob..." - -@$(MKDIR) $(BUILD_DIR) + @$(call MKDIR,$(BUILD_DIR)) $(GO) build $(GOFLAGS) -ldflags "$(LDFLAGS)" -o $(BUILD_DIR)/winjob$(EXE) ./cmd/winjob ## Build and run acpdbg — usage: make acpdbg ARGS="probe auggie" @@ -193,7 +198,7 @@ acpdbg: build-acpdbg ## Build the acpdbg binary — raw ACP JSON-RPC debugger (see .agents/skills/acp-debug) build-acpdbg: @echo "Building acpdbg..." - -@$(MKDIR) $(BUILD_DIR) + @$(call MKDIR,$(BUILD_DIR)) $(GO) build $(GOFLAGS) -ldflags "$(LDFLAGS)" -o $(BUILD_DIR)/acpdbg$(EXE) ./cmd/acpdbg ## Build the complete development binary set. @@ -214,7 +219,7 @@ build-runtime: build-agentctl build-agentctl-remote build-kandev ## launcher prebuild does not pull in agentctl helpers it does not use yet. build-kandev: @echo "Building $(BINARY_NAME)..." - -@$(MKDIR) $(BUILD_DIR) + @$(call MKDIR,$(BUILD_DIR)) $(CGO_PREFIX) $(GO) build $(GOFLAGS) -tags fts5 -ldflags "$(LDFLAGS)" -o $(BUILD_DIR)/$(BINARY_NAME)$(EXE) ./cmd/kandev ## Build all binaries (unified + individual services + agentctl) @@ -225,7 +230,7 @@ build-all: build build-agentctl ## Build the agentctl sidecar binary (includes embedded MCP server) build-agentctl: @echo "Building agentctl..." - -@$(MKDIR) $(BUILD_DIR) + @$(call MKDIR,$(BUILD_DIR)) $(GO) build $(GOFLAGS) -ldflags "$(LDFLAGS)" -o $(BUILD_DIR)/agentctl$(EXE) ./cmd/agentctl ## Build only the agentctl helpers needed by the development profile. @@ -237,33 +242,33 @@ build-agentctl-remote: build-agentctl-linux build-agentctl-linux-arm64 build-age ## Build agentctl for linux/amd64 (used by Docker/Sprites and Linux SSH hosts) build-agentctl-linux: @echo "Building agentctl for linux/amd64..." - -@$(MKDIR) $(BUILD_DIR) + @$(call MKDIR,$(BUILD_DIR)) $(GO_LINUX_AMD64) $(GO) build $(GOFLAGS) -ldflags "$(LDFLAGS)" -o $(BUILD_DIR)/agentctl-linux-amd64 ./cmd/agentctl ## Build agentctl for linux/arm64 (used by ARM Linux SSH hosts, e.g. Graviton) build-agentctl-linux-arm64: @echo "Building agentctl for linux/arm64..." - -@$(MKDIR) $(BUILD_DIR) + @$(call MKDIR,$(BUILD_DIR)) $(GO_LINUX_ARM64) $(GO) build $(GOFLAGS) -ldflags "$(LDFLAGS)" -o $(BUILD_DIR)/agentctl-linux-arm64 ./cmd/agentctl ## Build agentctl for darwin/arm64 (used by Apple Silicon SSH hosts) build-agentctl-darwin-arm64: @echo "Building agentctl for darwin/arm64..." - -@$(MKDIR) $(BUILD_DIR) + @$(call MKDIR,$(BUILD_DIR)) $(GO_DARWIN_ARM64) $(GO) build $(GOFLAGS) -ldflags "$(LDFLAGS)" -o $(BUILD_DIR)/agentctl-darwin-arm64 ./cmd/agentctl $(call adhoc_sign_darwin,$(BUILD_DIR)/agentctl-darwin-arm64) ## Build agentctl for darwin/amd64 (used by Intel Mac SSH hosts) build-agentctl-darwin-amd64: @echo "Building agentctl for darwin/amd64..." - -@$(MKDIR) $(BUILD_DIR) + @$(call MKDIR,$(BUILD_DIR)) $(GO_DARWIN_AMD64) $(GO) build $(GOFLAGS) -ldflags "$(LDFLAGS)" -o $(BUILD_DIR)/agentctl-darwin-amd64 ./cmd/agentctl $(call adhoc_sign_darwin,$(BUILD_DIR)/agentctl-darwin-amd64) ## Build mock-agent for linux/amd64 (used by Docker E2E tests) build-mock-agent-linux: @echo "Building mock-agent for linux/amd64..." - @$(MKDIR) $(BUILD_DIR) + @$(call MKDIR,$(BUILD_DIR)) CGO_ENABLED=0 GOOS=linux GOARCH=amd64 $(GO) build $(GOFLAGS) -ldflags "$(LDFLAGS)" -o $(BUILD_DIR)/mock-agent-linux-amd64 ./cmd/mock-agent @@ -284,7 +289,7 @@ HOST_GOARCH := $(shell $(GO) env GOARCH) e2e-plugin-package: @echo "Packaging plugin-fixture for e2e ($(HOST_GOOS)-$(HOST_GOARCH))..." @$(RMDIR) $(FIXTURE_STAGE_DIR) - @$(MKDIR) $(FIXTURE_STAGE_DIR)/server + @$(call MKDIR,$(FIXTURE_STAGE_DIR)/server) cp $(FIXTURE_PACKAGE_DIR)/manifest.yaml $(FIXTURE_STAGE_DIR)/manifest.yaml cp -r $(FIXTURE_PACKAGE_DIR)/ui $(FIXTURE_STAGE_DIR)/ui $(GO) build $(GOFLAGS) -o $(FIXTURE_STAGE_DIR)/server/plugin-$(HOST_GOOS)-$(HOST_GOARCH)$(EXE) ./cmd/plugin-fixture @@ -385,7 +390,7 @@ PROTOC_GEN_GO_GRPC_VERSION := v1.5.1 .PHONY: proto proto: @echo "Generating proto stubs..." - @$(MKDIR) $(PROTO_TOOLS_BIN) + @$(call MKDIR,$(PROTO_TOOLS_BIN)) GOBIN=$(PROTO_TOOLS_BIN) $(GO) install google.golang.org/protobuf/cmd/protoc-gen-go@$(PROTOC_GEN_GO_VERSION) GOBIN=$(PROTO_TOOLS_BIN) $(GO) install google.golang.org/grpc/cmd/protoc-gen-go-grpc@$(PROTOC_GEN_GO_GRPC_VERSION) cd proto && PATH="$(PROTO_TOOLS_BIN):$$PATH" $(GO) run github.com/bufbuild/buf/cmd/buf@$(BUF_VERSION) generate @@ -426,7 +431,7 @@ deps: ## Build for multiple platforms build-cross: @echo "Building for multiple platforms..." - -@$(MKDIR) $(BUILD_DIR) + @$(call MKDIR,$(BUILD_DIR)) CGO_ENABLED=1 GOOS=linux GOARCH=amd64 $(GO) build -tags fts5 -ldflags "$(LDFLAGS)" -o $(BUILD_DIR)/$(BINARY_NAME)-linux-amd64 ./cmd/kandev CGO_ENABLED=1 GOOS=darwin GOARCH=amd64 $(GO) build -tags fts5 -ldflags "$(LDFLAGS)" -o $(BUILD_DIR)/$(BINARY_NAME)-darwin-amd64 ./cmd/kandev CGO_ENABLED=1 GOOS=darwin GOARCH=arm64 $(GO) build -tags fts5 -ldflags "$(LDFLAGS)" -o $(BUILD_DIR)/$(BINARY_NAME)-darwin-arm64 ./cmd/kandev diff --git a/scripts/check-make-shells b/scripts/check-make-shells index e05e79deba..16c08f6e80 100755 --- a/scripts/check-make-shells +++ b/scripts/check-make-shells @@ -1,7 +1,7 @@ #!/usr/bin/env bash # check-make-shells — assert that apps/backend/Makefile's run/dev/start-debug # and deadcode targets expand to the correct per-shell command line, without -# running them. +# building them. # # The Makefile dispatches on two independent axes: # * EXE suffix — keyed on $(OS): any Windows build (native cmd/PowerShell @@ -19,13 +19,15 @@ # without having to run on each. The harness itself is bash (grep, sed), so it # needs a POSIX shell — it runs in the Linux CI job and under Git Bash/WSL # locally, not from native cmd.exe/PowerShell. Covers the Make-target dispatch -# that the backend Go CI jobs don't exercise. +# that the backend Go CI jobs don't exercise. When cmd.exe is available, the +# script also runs an isolated mkdir probe without building any binaries. set -euo pipefail backend_dir="$(cd "$(dirname "$0")/../apps/backend" && pwd)" status=0 +windows_mkdir_recipe= # expect