mirror of
https://github.com/Sea-Haven-Industries/engineering-handbook.git
synced 2026-09-30 03:23:14 +00:00
docs(git-workflow): make ci-on-merge the sanctioned deploy path
Pipeline deploy on merge to main (or workflow_dispatch where a repo configures one) is now the only sanctioned path. Local deploy-then-merge drops to a documented legacy exception that requires a data-loss-prone stateful change plus advance sign-off, recorded in the PR notes. Also correct the hook install path for the repo's move under repositories/seahaven/, and document that core.hooksPath is a single directory rather than a search path, so a repo-local setting silently shadows the machine-global security pre-push unless the repo hook is a shim that re-execs it.
This commit is contained in:
parent
3edbb265b5
commit
cfb50ff1fc
1 changed files with 38 additions and 7 deletions
|
|
@ -52,19 +52,30 @@ The integration also accepts inline commands in commit messages to act on the is
|
|||
|
||||
Transition names are case-insensitive and match the issue's workflow (`#in-progress`, `#done`). Use these sparingly; the link itself is the main goal, not driving the whole workflow from commits.
|
||||
|
||||
## Deploy-Then-Merge
|
||||
## Deploying
|
||||
|
||||
CI-on-merge is the only sanctioned deploy path. A change reaches an environment by merging its PR into `main` and letting the repo's pipeline deploy, or through a `workflow_dispatch` run of that same pipeline where the repo configures one. Nobody deploys from a workstation.
|
||||
|
||||
The standard flow for changes that deploy to AWS:
|
||||
|
||||
1. Create a feature branch (`feature/add-receipt-parser`)
|
||||
2. Develop and commit locally
|
||||
3. Open a PR via `gh pr create`
|
||||
4. Merge the feature branch into `main` locally
|
||||
5. Deploy to the target environment (`sam deploy`, etc.)
|
||||
6. Verify in production
|
||||
7. Merge the PR on GitHub
|
||||
4. Get the review, and confirm CI is green (`gh pr checks`)
|
||||
5. Merge the PR on GitHub
|
||||
6. The pipeline deploys on the merge to `main`, or on a `workflow_dispatch` run where the repo is set up that way
|
||||
7. Verify the deployed environment; if it is wrong, roll forward with a follow-up PR
|
||||
|
||||
This ensures production works before the PR closes. If the deploy fails, the PR stays open and `main` on GitHub is still clean.
|
||||
A local deploy puts code into an environment that no reviewed commit describes, and its result depends on whoever ran it having the right credentials and a clean working tree. The pipeline deploys a known commit with the repo's own OIDC role every time. See [cicd.md](cicd.md).
|
||||
|
||||
### Legacy exception: deploy-then-merge
|
||||
|
||||
Merging the feature branch into `main` locally, deploying by hand (`sam deploy`, `cdk deploy`), and only then merging the PR on GitHub is a legacy pattern. It is not a default and it is not available on request. Both of these must hold:
|
||||
|
||||
- **The change is data-loss-prone and stateful.** A resource replacement that would recreate a table or bucket, a one-way schema or data migration, or a stack operation that has to be watched and aborted mid-flight, where an automated deploy or rollback could destroy data.
|
||||
- **Adam has signed off on that specific deploy in advance.**
|
||||
|
||||
Write the justification into the PR description under `## Notes`: what the stateful risk is, and where the sign-off happened. An exception that is not written down is not an exception, so use the pipeline.
|
||||
|
||||
## Push Discipline
|
||||
|
||||
|
|
@ -116,10 +127,30 @@ Recommended hooks live in [`hooks/`](hooks/) — copy them into `.git/hooks/` wh
|
|||
Install for a Node.js project:
|
||||
|
||||
```bash
|
||||
cp ~/Documents/repositories/engineering-handbook/hooks/pre-push .git/hooks/pre-push
|
||||
cp ~/Documents/repositories/seahaven/engineering-handbook/hooks/pre-push .git/hooks/pre-push
|
||||
chmod +x .git/hooks/pre-push
|
||||
```
|
||||
|
||||
### `core.hooksPath` shadows, it does not merge
|
||||
|
||||
`core.hooksPath` names a single directory, not a search path. Setting it in a repo (for example to a tracked `.githooks/`) makes git run hooks *only* from there and ignore the machine-global hooks directory completely. Where that global directory holds a mandatory hook, such as the workstation security `pre-push`, a repo-local `core.hooksPath` silently disables it: no error, no output, no gate.
|
||||
|
||||
A repo that sets its own `core.hooksPath` must ship a `pre-push` that re-execs the global hook instead of replacing it:
|
||||
|
||||
```bash
|
||||
#!/usr/bin/env bash
|
||||
GLOBAL="${SH_GLOBAL_HOOKS:-$HOME/.config/git/hooks}/pre-push"
|
||||
[ -x "$GLOBAL" ] && exec "$GLOBAL" "$@" # passes args and stdin, preserves the exit code
|
||||
exit 0 # nothing to delegate to
|
||||
```
|
||||
|
||||
Two consequences:
|
||||
|
||||
- An installer that sets `core.hooksPath` must verify the shim delegates **before** it touches the config, and refuse to install if the delegation is missing or broken.
|
||||
- A tracked hooks directory only exists on branches that contain it, so the gate is off on every branch that predates it. Land the hooks directory on all long-lived branches before installing.
|
||||
|
||||
Check what is actually in effect with `git config core.hooksPath` and `git config --local core.hooksPath`, then confirm the repo's `pre-push` still execs the global one.
|
||||
|
||||
## Cleaning Up
|
||||
|
||||
After a PR is merged:
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue