Skip to content

Commit a12ec18

Browse files
authored
Merge pull request CactuseSecurity#4219 from NilsPur/develop
Githooks for automated submodule synching
2 parents 5764d4a + 63d7c02 commit a12ec18

6 files changed

Lines changed: 102 additions & 12 deletions

File tree

.githooks/post-checkout

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,2 @@
1+
#!/usr/bin/env bash
2+
"$(dirname "$0")/submodule-sync"

.githooks/post-merge

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,2 @@
1+
#!/usr/bin/env bash
2+
"$(dirname "$0")/submodule-sync"

.githooks/post-rewrite

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,2 @@
1+
#!/usr/bin/env bash
2+
"$(dirname "$0")/submodule-sync"

.githooks/submodule-sync

Lines changed: 71 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,71 @@
1+
#!/usr/bin/env bash
2+
set -euo pipefail
3+
4+
# Sync submodules quietly after common Git operations.
5+
6+
# Resolve repository root; bail out if not inside a Git repo.
7+
repo_root="$(git rev-parse --show-toplevel 2>/dev/null || true)"
8+
if [[ -z "${repo_root}" ]]; then
9+
exit 0
10+
fi
11+
12+
cd "${repo_root}"
13+
14+
# No submodules configured.
15+
if [[ ! -f .gitmodules ]]; then
16+
exit 0
17+
fi
18+
19+
# No submodule paths registered in .gitmodules.
20+
if ! git config --file .gitmodules --get-regexp '^submodule\..*\.path$' >/dev/null 2>&1; then
21+
exit 0
22+
fi
23+
24+
# Disable prompts and keep this hook silent for users without repo access.
25+
export GIT_TERMINAL_PROMPT=0
26+
export GIT_ASKPASS=/bin/true
27+
export GIT_SSH_COMMAND="ssh -o BatchMode=yes"
28+
29+
run_quiet() {
30+
# Ignore failures to avoid blocking normal Git operations.
31+
"$@" >/dev/null 2>&1 || true
32+
}
33+
34+
# Initialize submodules first so each path exists.
35+
run_quiet git submodule update --init --recursive
36+
37+
# Iterate configured submodules to ensure we are on a branch (not detached).
38+
while read -r key path; do
39+
# Convert `submodule.<name>.path` -> `<name>`.
40+
name="${key#submodule.}"
41+
name="${name%.path}"
42+
43+
# Skip if the submodule path is missing or not initialized.
44+
if [[ ! -d "${path}" ]]; then
45+
continue
46+
fi
47+
48+
# Skip if the path is not a Git repo.
49+
if ! git -C "${path}" rev-parse --git-dir >/dev/null 2>&1; then
50+
continue
51+
fi
52+
53+
# Prefer repo-local submodule.<name>.branch, fallback to .gitmodules.
54+
branch="$(git config --get "submodule.${name}.branch" || true)"
55+
if [[ -z "${branch}" ]]; then
56+
branch="$(git config --file .gitmodules --get "submodule.${name}.branch" || true)"
57+
fi
58+
59+
if [[ -n "${branch}" ]]; then
60+
# Try to checkout the branch if it already exists locally.
61+
run_quiet git -C "${path}" checkout -q "${branch}"
62+
63+
# If still detached, create/reset the branch from origin.
64+
if ! git -C "${path}" symbolic-ref -q HEAD >/dev/null 2>&1; then
65+
run_quiet git -C "${path}" checkout -q -B "${branch}" "origin/${branch}"
66+
fi
67+
fi
68+
done < <(git config --file .gitmodules --get-regexp '^submodule\..*\.path$')
69+
70+
# Move submodules to the newest commit on their tracking branch, merging instead of detaching.
71+
run_quiet git submodule update --remote --merge --recursive

.gitmodules

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,4 @@
11
[submodule "agents"]
22
path = agents
33
url = https://github.com/CactuseSecurity/firewall-orchestrator-agents
4+
branch = main

documentation/developer-docs/git-howto.md

Lines changed: 24 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -117,29 +117,41 @@ How to merge fork tpurschke/master into CactuseSecurity/master
117117

118118
git push -u origin auth_frontend
119119

120-
## Update submodules
120+
## Submodules
121+
IMPORTANT: Always commit to the submodule first, then commit to the FWO repo (superproject). This avoids the problem that the FWO repo does not point to the newest commit of the submodule (it cant - since it does not exist yet). An addtional commit to the FWO-repo will be necessary to fix this.
121122

122-
### Initial update
123-
Update submodules to the commits recorded in the superproject (safe, reproducible). Initializes them if necessary.
124-
Execute this command after the initial clone of the fwo repo in the fwo repo root directory:
123+
### Automatic submodule sync via repo hooks
124+
Enable the repo-managed hooks once (per clone) to keep submodules up to date automatically:
125+
```shell
126+
git config core.hooksPath .githooks
127+
```
128+
The hooks run after `git pull`, `git checkout`, and `git rebase` and execute:
125129
```shell
126130
git submodule update --init --recursive
131+
git submodule update --remote --merge --recursive
127132
```
133+
Notes:
134+
- The hook is quiet if you do not have access to a submodule repository (no error output).
135+
- The hook checks out the configured submodule branch from `.gitmodules` before updating, to avoid detached HEAD.
136+
- This intentionally moves submodules to the newest commit on their configured branch, even if the superproject has not updated the pointer yet. Expect the submodule to appear "modified" in `git status`.
128137

129-
## Update agents repo --> might be moved to githook later
138+
### Manual submodule operations
139+
If you like to manually execute the submodule setup, see the sections below. Otherwise, please refer to the section above.
130140

131-
This updates the agents repo manually. Update submodules to the latest commit on their configured remote tracking branch. Execute this command to get the newest version of all submodules from their respective repositories.
141+
#### Initial update
142+
Update submodules to the commits recorded in the superproject (safe, reproducible). Initializes them if necessary.
143+
Execute this command after the initial clone of the fwo repo in the fwo repo root directory:
132144
```shell
133-
git submodule update --remote --recursive
145+
git submodule update --init --recursive
134146
```
135-
NB: This overwrites the agents repo data again with the one from the firewall-orchestrator repo!
136147

137-
## Configure to always pull recursively
138-
Permanent configuration change: make `git pull` recurse into submodules
148+
#### Update agents repo manually
149+
This updates the agents repo manually. Update submodules to the latest commit on their configured remote tracking branch. Execute this command to get the newest version of all submodules from their respective repositories.
139150
```shell
140-
git config submodule.recurse true
151+
git submodule update --remote --merge --recursive
141152
```
142-
## Check correct file state
153+
154+
### Check correct file state
143155
```shell
144156
tim@acantha24:~/dev/tim/fwo$ git ls-tree HEAD agents
145157
160000 commit 73cfbb4efad58dd569c0c0ab4d7ecebc63d23ddd agents

0 commit comments

Comments
 (0)