Compare commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
728e737dc8 |
@@ -5,3 +5,6 @@
|
|||||||
|
|
||||||
backend/target/
|
backend/target/
|
||||||
build/
|
build/
|
||||||
|
e2e/node_modules/
|
||||||
|
frontend/node_modules/
|
||||||
|
frontend/dist/
|
||||||
|
|||||||
@@ -1,5 +1,8 @@
|
|||||||
# Keycloak Authentication Patterns
|
# Keycloak Authentication Patterns
|
||||||
|
|
||||||
|
The 39-branch implementation registry is documented in
|
||||||
|
[`docs/keycloak-branch-index.md`](docs/keycloak-branch-index.md).
|
||||||
|
|
||||||
Keycloak을 중심으로 네 가지 브라우저 인증 통합 패턴을 같은 로컬
|
Keycloak을 중심으로 네 가지 브라우저 인증 통합 패턴을 같은 로컬
|
||||||
인프라에서 비교하는 학습 프로젝트입니다.
|
인프라에서 비교하는 학습 프로젝트입니다.
|
||||||
|
|
||||||
|
|||||||
@@ -0,0 +1,29 @@
|
|||||||
|
# Keycloak branch implementation index
|
||||||
|
|
||||||
|
The source inventory contains 39 `feature-keycloak-*.md` branch notes. This
|
||||||
|
repository preserves one local Git feature branch for every note and merges it
|
||||||
|
with `--no-ff` into either the common `develop` baseline or one of the four
|
||||||
|
authentication-pattern branches.
|
||||||
|
|
||||||
|
| Target | Meaning |
|
||||||
|
|---|---|
|
||||||
|
| `common` | Shared realm, federation, deployment, or governance contract. Merge into `develop`, then propagate to AP1–AP4. |
|
||||||
|
| `ap1` | Browser-based OAuth client: vanilla SPA, Authorization Code + PKCE, Resource Server. |
|
||||||
|
| `ap2` | Token-mediating confidential backend: browser receives access token only. |
|
||||||
|
| `ap3` | BFF: backend owns every OAuth token and browser owns only a session cookie. |
|
||||||
|
| `ap4` | Edge forward-auth: oauth2-proxy/Nginx owns login and backend trusts an isolated identity header. |
|
||||||
|
|
||||||
|
The machine-readable registry is
|
||||||
|
[`keycloak-branch-manifest.tsv`](keycloak-branch-manifest.tsv). Run:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
./scripts/audit-keycloak-branches.sh
|
||||||
|
```
|
||||||
|
|
||||||
|
The audit succeeds only when all 39 note names have matching local feature
|
||||||
|
branches and each feature tip is reachable from its declared target branch.
|
||||||
|
|
||||||
|
Google credentials are never committed. The default local acceptance harness
|
||||||
|
uses a second Keycloak realm as a controllable OIDC provider so claim mapping
|
||||||
|
and unsafe-linking failure paths can be reproduced. A real Google login remains
|
||||||
|
an explicit credentialed/public-HTTPS verification profile.
|
||||||
@@ -0,0 +1,40 @@
|
|||||||
|
branch target delivery
|
||||||
|
feature/keycloak-account-linking-spa-ux ap1 documented-and-contract-tested
|
||||||
|
feature/keycloak-account-linking-sub-vs-email common documented-and-contract-tested
|
||||||
|
feature/keycloak-bff-csrf-samesite-defense ap3 locally-verified
|
||||||
|
feature/keycloak-bff-oauth2login-session ap3 locally-verified
|
||||||
|
feature/keycloak-bff-vs-spa-direct ap3 documented
|
||||||
|
feature/keycloak-docker-compose-stack common locally-verified
|
||||||
|
feature/keycloak-edge-forwardauth-google-federation ap4 documented-and-config-tested
|
||||||
|
feature/keycloak-edge-forwardauth-no-google ap4 documented-and-config-tested
|
||||||
|
feature/keycloak-federation-spa-zero-change ap1 contract-tested
|
||||||
|
feature/keycloak-first-broker-login-flow common locally-verified-with-mock-idp
|
||||||
|
feature/keycloak-four-pattern-tradeoff-matrix common documented-and-evidence-linked
|
||||||
|
feature/keycloak-google-claim-attribute-mapping common locally-verified-with-mock-idp
|
||||||
|
feature/keycloak-google-redirect-uri-policy common config-tested
|
||||||
|
feature/keycloak-header-spoofing-defense ap4 locally-verified
|
||||||
|
feature/keycloak-https-termination-caddy-nginx common config-tested
|
||||||
|
feature/keycloak-idp-brokering-google-client common locally-verified-with-mock-idp
|
||||||
|
feature/keycloak-idp-mappers-claim-to-role common locally-verified-with-mock-idp
|
||||||
|
feature/keycloak-internal-spa-direct-google-federation ap1 documented-and-contract-tested
|
||||||
|
feature/keycloak-internal-spa-direct-no-google ap1 documented-and-contract-tested
|
||||||
|
feature/keycloak-iss-claim-hostname-mismatch ap1 locally-verified
|
||||||
|
feature/keycloak-nginx-auth-request-integration ap4 locally-verified
|
||||||
|
feature/keycloak-oauth2-proxy-oidc-flow ap4 locally-verified
|
||||||
|
feature/keycloak-patterns common governance
|
||||||
|
feature/keycloak-pkce-flow-stages ap1 contract-tested
|
||||||
|
feature/keycloak-public-domain-tunneling common config-tested
|
||||||
|
feature/keycloak-realm-client-export common locally-verified
|
||||||
|
feature/keycloak-refresh-rotation-and-logout ap1 locally-verified
|
||||||
|
feature/keycloak-refresh-token-rotation ap1 contract-tested
|
||||||
|
feature/keycloak-reverse-proxy-headers common config-tested
|
||||||
|
feature/keycloak-single-ec2-google-federation ap1 documented-and-config-tested
|
||||||
|
feature/keycloak-single-ec2-no-google ap1 documented-and-contract-tested
|
||||||
|
feature/keycloak-spa-token-storage-tradeoff ap1 locally-verified
|
||||||
|
feature/keycloak-spring-rs-audience-validator ap1 locally-verified
|
||||||
|
feature/keycloak-spring-rs-role-mapping ap1 locally-verified
|
||||||
|
feature/keycloak-three-leg-trust-chain ap1 documented-and-contract-tested
|
||||||
|
feature/keycloak-token-mediating-access-handoff ap2 locally-verified
|
||||||
|
feature/keycloak-token-mediating-confidential-client ap2 locally-verified
|
||||||
|
feature/keycloak-traefik-forwardauth-alternative ap4 config-tested
|
||||||
|
feature/keycloak-vanilla-js-spa-pkce ap1 locally-verified
|
||||||
|
Executable
+62
@@ -0,0 +1,62 @@
|
|||||||
|
#!/usr/bin/env sh
|
||||||
|
set -eu
|
||||||
|
|
||||||
|
manifest="${1:-docs/keycloak-branch-manifest.tsv}"
|
||||||
|
notes_dir="${KEYCLOAK_BRANCH_NOTES_DIR:-/home/donghyeon/workspace/ai-tools/llm-wiki/raw/branch-notes}"
|
||||||
|
|
||||||
|
expected_count="$(awk 'NR > 1 { count += 1 } END { print count + 0 }' "$manifest")"
|
||||||
|
if [ "$expected_count" -ne 39 ]; then
|
||||||
|
echo "manifest must contain exactly 39 Keycloak branches; found $expected_count" >&2
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
note_count="$(find "$notes_dir" -maxdepth 1 -type f -name 'feature-keycloak-*.md' | wc -l)"
|
||||||
|
if [ "$note_count" -ne 39 ]; then
|
||||||
|
echo "branch-note inventory must contain exactly 39 files; found $note_count" >&2
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
missing=0
|
||||||
|
unmerged=0
|
||||||
|
tab="$(printf '\t')"
|
||||||
|
|
||||||
|
while IFS="$tab" read -r branch target delivery; do
|
||||||
|
[ "$branch" = "branch" ] && continue
|
||||||
|
|
||||||
|
note_name="$(printf '%s\n' "$branch" |
|
||||||
|
sed 's#^feature/keycloak-#feature-keycloak-#').md"
|
||||||
|
if [ ! -f "$notes_dir/$note_name" ]; then
|
||||||
|
echo "missing branch note: $note_name" >&2
|
||||||
|
missing=$((missing + 1))
|
||||||
|
fi
|
||||||
|
|
||||||
|
if ! git show-ref --verify --quiet "refs/heads/$branch"; then
|
||||||
|
echo "missing local branch: $branch" >&2
|
||||||
|
missing=$((missing + 1))
|
||||||
|
continue
|
||||||
|
fi
|
||||||
|
|
||||||
|
case "$target" in
|
||||||
|
common) target_branch="develop" ;;
|
||||||
|
ap1) target_branch="develop-keycloak-pattern1" ;;
|
||||||
|
ap2) target_branch="develop-keycloak-pattern2" ;;
|
||||||
|
ap3) target_branch="develop-keycloak-pattern3" ;;
|
||||||
|
ap4) target_branch="develop-keycloak-pattern4" ;;
|
||||||
|
*)
|
||||||
|
echo "unknown target '$target' for $branch ($delivery)" >&2
|
||||||
|
exit 1
|
||||||
|
;;
|
||||||
|
esac
|
||||||
|
|
||||||
|
if ! git merge-base --is-ancestor "$branch" "$target_branch"; then
|
||||||
|
echo "feature tip is not merged: $branch -> $target_branch" >&2
|
||||||
|
unmerged=$((unmerged + 1))
|
||||||
|
fi
|
||||||
|
done < "$manifest"
|
||||||
|
|
||||||
|
if [ "$missing" -ne 0 ] || [ "$unmerged" -ne 0 ]; then
|
||||||
|
echo "Keycloak branch audit failed: missing=$missing unmerged=$unmerged" >&2
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
echo "Keycloak branch audit passed: 39/39 branches exist and are merged"
|
||||||
Reference in New Issue
Block a user