Part of CLAUDE.md Critical Conventions
When to load: Working on authentication, authorization, RBAC, or handling sensitive data
1. User Token Authentication Required
// ALWAYS for user-initiated operations
reqK8s, reqDyn := GetK8sClientsForRequest(c)
if reqK8s == nil {
c.JSON(http.StatusUnauthorized, gin.H{"error": "Invalid or missing token"})
c.Abort()
return
}2. Token Redaction in Logs
FORBIDDEN:
log.Printf("Authorization: Bearer %s", token)
log.Printf("Request headers: %v", headers)REQUIRED:
log.Printf("Token length: %d", len(token))
// Redact in URL paths
path = strings.Split(path, "?")[0] + "?token=[REDACTED]"Token Redaction Pattern: See server/server.go:22-34
// Custom log formatter that redacts tokens
func customRedactingFormatter(param gin.LogFormatterParams) string {
path := param.Path
if strings.Contains(path, "token=") {
path = strings.Split(path, "?")[0] + "?token=[REDACTED]"
}
// ... rest of formatting
}K8s TokenRequest API does NOT support non-expiring tokens. If ExpirationSeconds is omitted, K8s silently applies a default (~1h). Maximum enforced lifetime: 1 year (31536000 seconds), validated in backend CreateProjectKey. Frontend default: 90 days.
1. Always Check Permissions Before Operations
ssar := &authv1.SelfSubjectAccessReview{
Spec: authv1.SelfSubjectAccessReviewSpec{
ResourceAttributes: &authv1.ResourceAttributes{
Group: "vteam.ambient-code",
Resource: "agenticsessions",
Verb: "list",
Namespace: project,
},
},
}
res, err := reqK8s.AuthorizationV1().SelfSubjectAccessReviews().Create(ctx, ssar, v1.CreateOptions{})
if err != nil || !res.Status.Allowed {
c.JSON(http.StatusForbidden, gin.H{"error": "Unauthorized"})
return
}2. Namespace Isolation
- Each project maps to a Kubernetes namespace
- User token must have permissions in that namespace
- Never bypass namespace checks
Always Set SecurityContext for Job Pods
SecurityContext: &corev1.SecurityContext{
AllowPrivilegeEscalation: boolPtr(false),
ReadOnlyRootFilesystem: boolPtr(false), // Only if temp files needed
Capabilities: &corev1.Capabilities{
Drop: []corev1.Capability{"ALL"},
},
},1. Validate All User Input
// Validate resource names (K8s DNS label requirements)
if !isValidK8sName(name) {
c.JSON(http.StatusBadRequest, gin.H{"error": "Invalid name format"})
return
}
// Validate URLs for repository inputs
if _, err := url.Parse(repoURL); err != nil {
c.JSON(http.StatusBadRequest, gin.H{"error": "Invalid repository URL"})
return
}2. Sanitize for Log Injection
// Prevent log injection with newlines
name = strings.ReplaceAll(name, "\n", "")
name = strings.ReplaceAll(name, "\r", "")rawAuth := c.GetHeader("Authorization")
parts := strings.SplitN(rawAuth, " ", 2)
if len(parts) != 2 || !strings.EqualFold(parts[0], "Bearer") {
c.JSON(http.StatusUnauthorized, gin.H{"error": "invalid Authorization header"})
return
}
token := strings.TrimSpace(parts[1])
// NEVER log token itself
log.Printf("Processing request with token (len=%d)", len(token))func ValidateProjectContext() gin.HandlerFunc {
return func(c *gin.Context) {
projectName := c.Param("projectName")
// Get user-scoped K8s client
reqK8s, _ := GetK8sClientsForRequest(c)
if reqK8s == nil {
c.JSON(http.StatusUnauthorized, gin.H{"error": "Unauthorized"})
c.Abort()
return
}
// Check if user can access namespace
ssar := &authv1.SelfSubjectAccessReview{
Spec: authv1.SelfSubjectAccessReviewSpec{
ResourceAttributes: &authv1.ResourceAttributes{
Resource: "namespaces",
Verb: "get",
Name: projectName,
},
},
}
res, err := reqK8s.AuthorizationV1().SelfSubjectAccessReviews().Create(ctx, ssar, v1.CreateOptions{})
if err != nil || !res.Status.Allowed {
c.JSON(http.StatusForbidden, gin.H{"error": "Access denied to project"})
c.Abort()
return
}
c.Set("project", projectName)
c.Next()
}
}// Only backend service account can create tokens for runner pods
tokenRequest := &authv1.TokenRequest{
Spec: authv1.TokenRequestSpec{
ExpirationSeconds: int64Ptr(3600),
},
}
tokenResponse, err := K8sClient.CoreV1().ServiceAccounts(namespace).CreateToken(
ctx,
serviceAccountName,
tokenRequest,
v1.CreateOptions{},
)
if err != nil {
return fmt.Errorf("failed to create token: %w", err)
}
// Store token in secret (never log it)
secret := &corev1.Secret{
ObjectMeta: v1.ObjectMeta{
Name: fmt.Sprintf("%s-token", sessionName),
Namespace: namespace,
},
StringData: map[string]string{
"token": tokenResponse.Status.Token,
},
}Before committing code that handles:
Authentication:
- Using user token (GetK8sClientsForRequest) for user operations
- Returning 401 if token is invalid/missing
- Not falling back to service account on auth failure
Authorization:
- RBAC check performed before resource access
- Using correct namespace for permission check
- Returning 403 if user lacks permissions
Secrets & Tokens:
- No tokens in logs (use len(token) instead)
- No tokens in error messages
- Tokens stored in Kubernetes Secrets
- Token redaction in request logs
Input Validation:
- All user input validated
- Resource names validated (K8s DNS label format)
- URLs parsed and validated
- Log injection prevented
Container Security:
- SecurityContext set on all Job pods
- AllowPrivilegeEscalation: false
- Capabilities dropped (ALL)
- OwnerReferences set for cleanup
- OWASP Top 10: https://owasp.org/www-project-top-ten/
- Kubernetes Security Best Practices: https://kubernetes.io/docs/concepts/security/
- RBAC Documentation: https://kubernetes.io/docs/reference/access-authn-authz/rbac/