From e3fc8c669aaf63daa1097f771f95b247910d9f17 Mon Sep 17 00:00:00 2001 From: shenxianpeng Date: Sun, 15 Mar 2026 02:22:58 +0000 Subject: [PATCH 1/6] feat: update development container configuration with Node.js and enhanced post-create command --- .devcontainer/devcontainer.json | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/.devcontainer/devcontainer.json b/.devcontainer/devcontainer.json index 1544071..02d8160 100644 --- a/.devcontainer/devcontainer.json +++ b/.devcontainer/devcontainer.json @@ -7,7 +7,10 @@ "version": "17", "installMaven": "true" }, - "ghcr.io/devcontainers/features/github-cli:1": {} + "ghcr.io/devcontainers/features/github-cli:1": {}, + "ghcr.io/devcontainers/features/node:1": { + "version": "lts" + } }, "customizations": { @@ -18,7 +21,7 @@ } }, - "postCreateCommand": "mvn clean verify -DskipTests", + "postCreateCommand": "bash -c 'curl -fsSL https://gh.io/copilot-install | bash && curl -fsSL https://claude.ai/install.sh | bash && mvn clean verify -DskipTests'", "forwardPorts": [8080], From 7aa39fbc1bb7aa671a0f81f22fcd21e486a75d4e Mon Sep 17 00:00:00 2001 From: shenxianpeng Date: Sun, 15 Mar 2026 03:03:54 +0000 Subject: [PATCH 2/6] feat: add Makefile for simplified build and testing commands --- .github/copilot-instructions.md | 17 ++++++++--- CONTRIBUTING.md | 51 ++++++++++++++++++++------------- Makefile | 37 ++++++++++++++++++++++++ 3 files changed, 81 insertions(+), 24 deletions(-) create mode 100644 Makefile diff --git a/.github/copilot-instructions.md b/.github/copilot-instructions.md index 5b382ea..774c3ae 100644 --- a/.github/copilot-instructions.md +++ b/.github/copilot-instructions.md @@ -132,10 +132,19 @@ Use `provider.setThrowError(true)` to simulate failures, `provider.getLastCustom - Key dependencies: `jackson2-api`, `workflow-step-api`, `commons-lang3-api` ### Commands -- `mvn compile` - Compile the plugin -- `mvn test` - Run unit tests -- `mvn hpi:run` - Start Jenkins with plugin for testing -- `mvn package` - Build .hpi file + +A `Makefile` is provided for convenience — run `make help` to list all targets. + +| Make target | Maven equivalent | Purpose | +|---|---|---| +| `make build` | `mvn compile` | Compile the plugin | +| `make test` | `mvn test` | Run unit tests | +| `make verify` | `mvn verify` | Full CI check | +| `make package` | `mvn package -DskipTests` | Build .hpi file | +| `make run` | `mvn hpi:run` | Start Jenkins with plugin | +| `make debug` | `mvnDebug hpi:run` | Start Jenkins with remote debugger | +| `make lint` | `mvn checkstyle:checkstyle spotbugs:check` | Static analysis (non-blocking) | +| `make reinstall` | `mvn clean package install -DskipTests` | Clean rebuild + local install | ## Configuration & Usage diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md index 79bf1ac..bcab9ff 100644 --- a/CONTRIBUTING.md +++ b/CONTRIBUTING.md @@ -24,27 +24,28 @@ This guide will help you get started with development and contribution. 2. **Build the plugin:** + A `Makefile` is provided for convenience. Run `make help` to list all available targets. + ```bash - # Clean and compile - mvn clean compile - - # Package the plugin - mvn clean package + make build # Compile the plugin + make package # Build the .hpi file (skip tests) + make test # Run unit tests + make verify # Full CI check (compile + test + verify) + ``` - # Package without running tests (useful for development) + Or using Maven directly: + ```bash + mvn clean compile mvn clean package -DskipTests ``` 3. **Run Jenkins locally with the plugin:** ```bash - # Start Jenkins on http://localhost:8080 - mvn hpi:run - - # Or on a custom port - mvn hpi:run -Dport=5000 + make run # Start Jenkins on http://localhost:8080/jenkins + make debug # Start Jenkins with remote debugger on port 8000 - # check for code quality issues - mvn spotbugs:check + # Or on a custom port via Maven + mvn hpi:run -Dport=5000 ``` ### 2. Plugin Installation & Testing @@ -53,7 +54,8 @@ This guide will help you get started with development and contribution. 1. **Build the plugin:** ```bash - mvn clean package -DskipTests + make package + # or: mvn clean package -DskipTests ``` 2. **Install in Jenkins:** @@ -89,13 +91,15 @@ This guide will help you get started with development and contribution. ### Running Tests ```bash -# Run unit tests -mvn test +make test # Run unit tests +make verify # Run unit tests + integration/verify phase +make package # Build .hpi skipping tests (dev shortcut) +``` -# Run integration tests +Or using Maven directly: +```bash +mvn test mvn verify - -# Skip tests during development (not recommended for PRs) mvn clean package -DskipTests ``` @@ -156,6 +160,11 @@ class AIServiceTest { - **Line length**: Maximum 120 characters - **Naming**: Use descriptive names for classes and methods +To check for code quality issues: +```bash +make lint # Checkstyle report + SpotBugs (non-blocking) +``` + ### Architecture The plugin follows these patterns: @@ -198,7 +207,9 @@ src/main/java/io/jenkins/plugins/explain_error/ ## Pull Request Process 1. **Before submitting:** - - ✅ All tests pass + - ✅ All tests pass (`make test`) + - ✅ Full verify passes (`make verify`) + - ✅ No new lint issues (`make lint`) - ✅ Code follows style guidelines - ✅ Documentation updated diff --git a/Makefile b/Makefile new file mode 100644 index 0000000..689e366 --- /dev/null +++ b/Makefile @@ -0,0 +1,37 @@ +.PHONY: help build test verify clean package run debug lint + +# Default target +.DEFAULT_GOAL := help + +help: ## Show this help message + @grep -E '^[a-zA-Z_-]+:.*?## .*$$' $(MAKEFILE_LIST) | awk 'BEGIN {FS = ":.*?## "}; {printf "\033[36m%-15s\033[0m %s\n", $$1, $$2}' + +build: ## Compile the plugin (skip tests) + mvn compile + +test: ## Run all unit tests + mvn test + +verify: ## Compile, test, and verify (full CI check) + mvn verify + +clean: ## Remove build artifacts + mvn clean + +package: ## Build the .hpi plugin file (skip tests) + mvn package -DskipTests + +package-full: ## Build the .hpi plugin file (with tests) + mvn package + +run: ## Start Jenkins locally with the plugin (http://localhost:8080/jenkins) + mvn hpi:run + +debug: ## Start Jenkins in debug mode (port 8000) + mvnDebug hpi:run + +lint: ## Run Checkstyle (report only) and SpotBugs static analysis + mvn checkstyle:checkstyle spotbugs:check + +reinstall: clean package ## Clean, rebuild, and install .hpi locally + mvn install -DskipTests From d9c06b18cf0849d1dc398d704faed179c5e5e93e Mon Sep 17 00:00:00 2001 From: shenxianpeng Date: Mon, 16 Mar 2026 20:24:15 +0200 Subject: [PATCH 3/6] feat: update Makefile to configure debugging and run commands for Jenkins --- .agents/skills/review-pull-request/SKILL.md | 251 ++++++++++++++++++++ Makefile | 6 +- 2 files changed, 254 insertions(+), 3 deletions(-) create mode 100644 .agents/skills/review-pull-request/SKILL.md diff --git a/.agents/skills/review-pull-request/SKILL.md b/.agents/skills/review-pull-request/SKILL.md new file mode 100644 index 0000000..a09ca97 --- /dev/null +++ b/.agents/skills/review-pull-request/SKILL.md @@ -0,0 +1,251 @@ +# Skill: Review Pull Request for explain-error-plugin + +## Description + +Step-by-step workflow for reviewing pull requests submitted to the `jenkinsci/explain-error-plugin` repository. Produces a structured, actionable review covering security, code quality, architecture, UI, testing, and dependency management — consistent with Jenkins hosting requirements. + +## Tools + +- `github-pull-request_openPullRequest` — fetch PR metadata and diff +- `github-pull-request_doSearch` — look up related issues or prior PRs +- `file_search` / `grep_search` / `read_file` — inspect source files for context +- `get_errors` — check for compile/lint errors +- `run_in_terminal` — run `mvn test` or `mvn checkstyle:check` to validate changes + +--- + +## Workflow + +### Step 1 — Fetch the PR + +Load the PR using the PR number or URL provided by the user. + +Collect: +- Title, description, linked issue(s) +- Changed files list +- Diff/patch of each changed file + +> If no PR number is given, ask: *"Which PR number or URL would you like me to review?"* + +--- + +### Step 2 — Understand the Intent + +Read the PR description and linked issue to understand **what problem is being solved**. + +Check: +- Is there a linked issue? Does the change match the issue scope? +- Is the change scoped (minimal, focused) or does it include unrelated refactoring? +- Is there a test included? + +Flag if the description is absent or too vague to evaluate intent. + +--- + +### Step 3 — Security Review + +For every changed `.java` file, check: + +#### API Keys / Secrets +- [ ] API keys use `Secret apiKey` (not `String`) +- [ ] Access uses `Secret.toString(apiKey)` only at usage point +- [ ] No secrets logged or printed anywhere + +#### Permission Checks +- [ ] All `doXxx()` form methods that change state or validate credentials use `@RequirePOST` (or `@POST`) +- [ ] `Jenkins.get().checkPermission(Jenkins.ADMINISTER)` present in sensitive operations + +#### Nullability +- [ ] Public API methods annotated with `@NonNull` or `@CheckForNull` (from `edu.umd.cs.findbugs.annotations`) +- [ ] No unguarded `.get()` calls on `Optional` or nullable values + +#### Input Validation +- [ ] User-supplied inputs validated at system boundary (form fields, pipeline step params) +- [ ] No SQL/XSS/command injection surface (no shell exec with user data, no raw HTML output) + +--- + +### Step 4 — Code Architecture Review + +#### Jenkins Extension Points +- [ ] New config classes use `@Extension` + `@Symbol` for CasC support +- [ ] `@DataBoundConstructor` present on constructors; optional fields use `@DataBoundSetter` +- [ ] Global config provides a static `get()` method + +#### AI Provider Pattern +- [ ] New providers extend `BaseAIProvider` and implement `ExtensionPoint` +- [ ] Provider descriptor extends `BaseProviderDescriptor` with `@Symbol` annotation +- [ ] `createAssistant()` used for LangChain4j integration (no direct HTTP/JSON) +- [ ] `isNotValid()` implemented to guard against empty config + +#### Action Management +- [ ] `addOrReplaceAction()` used (not `addAction()`) to avoid duplicate actions +- [ ] New UI actions use `TransientActionFactory` instead of `RunListener` + +#### Backward Compatibility +- [ ] If config fields are renamed or removed, a `readResolve()` migration method is present +- [ ] Old fields marked `@Deprecated` and `transient` if replaced + +#### Logging +- [ ] `java.util.logging.Logger` used (not SLF4J directly, not `System.out.println`) +- [ ] Trace/debug calls use `FINE`/`FINER`/`FINEST` +- [ ] `INFO` only for significant operational events +- [ ] No `e.printStackTrace()` — exceptions logged via `LOGGER.log(Level.WARNING, "...", e)` + +#### Error Handling +- [ ] Failures throw `ExplanationException` (not returned as strings) +- [ ] Exception messages are user-friendly and actionable + +--- + +### Step 5 — UI / Jelly Review + +For `.jelly` and `.js` files: + +#### Design System +- [ ] Uses Jenkins design library components (`l:card`, `jenkins-button`, `jenkins-!-*` spacing classes) +- [ ] No hard-coded colors — uses CSS variables (`var(--background)`, `var(--text-color)`) +- [ ] Icons use symbol library (`symbol-help`, etc.) not image paths + +#### CSP Compliance +- [ ] No inline `