Skip to content

Commit 71e1f18

Browse files
committed
Add comprehensive mTLS and OAuth authentication to REST API v2
This commit introduces comprehensive authentication support for the cloud event notifications REST API v2, enabling secure communication in production environments. **Authentication Methods:** - mTLS (Mutual TLS) authentication with client certificate validation - OAuth JWT token authentication with strict issuer validation - Support for both OpenShift OAuth server and Kubernetes ServiceAccount tokens - Flexible authentication configuration via JSON config files **OpenShift Integration:** - Native OpenShift Service CA integration for automatic certificate management - OpenShift OAuth server integration for JWT token validation - ServiceAccount-based authentication for pod-to-pod communication - Dynamic cluster name configuration for multi-cluster deployments **Security Features:** - Strict OAuth validation with issuer verification - Comprehensive token validation (expiration, audience, signature) - Client certificate validation with configurable CA trust - Path-based authentication middleware (health endpoints bypass auth) - Localhost connection support for internal health checks **Configuration Options:** - JSON-based authentication configuration - Support for OpenShift Service CA and cert-manager - Configurable OAuth scopes and audience validation - Environment-based cluster name configuration **Core Implementation:** - `v2/auth.go`: OAuth and mTLS authentication middleware and validation logic - `v2/server.go`: Enhanced server with authentication support and TLS configuration - `go.mod`/`go.sum`: Added golang-jwt/jwt/v5 dependency for JWT validation **Documentation:** - `AUTHENTICATION.md`: Comprehensive authentication configuration guide - `OPENSHIFT_AUTHENTICATION.md`: OpenShift-specific deployment and configuration - `README.md`: Updated with authentication feature overview and links **Examples and Templates:** - `auth-config-example.json`: Example authentication configuration - `examples/openshift-auth-config.json`: OpenShift-specific configuration template - `examples/openshift-manifests.yaml`: Complete OpenShift deployment manifests - `examples/README.md`: Documentation for example configurations - **Multi-Issuer Support**: Accepts both OpenShift OAuth tokens and Kubernetes ServiceAccount tokens - **Strict Validation**: No authentication bypass mechanisms, exact issuer matching required - **Comprehensive Error Handling**: Clear error messages without exposing sensitive information - **Production Ready**: Designed for secure production deployments in OpenShift clusters - Authentication is optional and configurable - Existing deployments continue to work without authentication - Health check endpoints remain accessible for monitoring - Graceful fallback for non-authenticated deployments This implementation provides enterprise-grade security for cloud event notifications while maintaining compatibility with existing deployments and supporting flexible authentication scenarios across different Kubernetes environments. Resolves authentication requirements for secure cloud event communication in production OpenShift environments. Signed-off-by: Jack Ding <jackding@gmail.com>
1 parent 2109ea8 commit 71e1f18

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

41 files changed

+4216
-36
lines changed

AUTHENTICATION.md

Lines changed: 436 additions & 0 deletions
Large diffs are not rendered by default.

OPENSHIFT_AUTHENTICATION.md

Lines changed: 389 additions & 0 deletions
Large diffs are not rendered by default.

README.md

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,27 @@
77

88
The REST-API specification below is generated by Swagger tools. Please refer to the [Developers Guide](docs/dev-readme.md) on how to use Swagger to generate specs and documentations.
99

10+
## Authentication
11+
12+
This REST API supports enterprise-grade authentication using mTLS and OAuth with **strict security validation**. For detailed configuration instructions, see:
13+
14+
- **[Authentication Configuration](AUTHENTICATION.md)** - Complete guide for configuring mTLS and OAuth authentication
15+
- **[OpenShift Authentication](OPENSHIFT_AUTHENTICATION.md)** - OpenShift-specific deployment guide with native Service CA and OAuth server integration
16+
17+
### Security Features
18+
19+
- **Strict OAuth Validation**: JWT tokens are validated against the configured issuer with no bypass mechanisms
20+
- **Issuer Verification**: Token issuer must exactly match the configured OAuth issuer
21+
- **Expiration Checking**: Expired tokens are rejected with clear error messages
22+
- **Audience Validation**: Tokens must contain the required audience claim
23+
- **mTLS Certificate Validation**: Client certificates are verified against the configured CA
24+
25+
### Recent Security Improvements
26+
27+
- **Fixed OAuth Security Vulnerability** (v2.1.0): Implemented proper OAuth token validation to prevent unauthorized access
28+
- **Added JWT Library Support**: Uses `golang-jwt/jwt/v5` for secure token parsing and validation
29+
- **Enhanced Error Handling**: Clear error messages for authentication failures without exposing sensitive information
30+
1031
## O-RAN Compliant REST API Specification
1132

1233
Starting from release [v1.21.0](https://github.com/redhat-cne/rest-api/releases/tag/v1.21.0), the REST API implemented in this repo is compliant with [O-RAN O-Cloud Notification API Specification for Event Consumers 4.0](https://orandownloadsweb.azurewebsites.net/specifications).

auth-config-example.json

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
{
2+
"enableMTLS": true,
3+
"caCertPath": "/etc/certs/ca.crt",
4+
"serverCertPath": "/etc/certs/server.crt",
5+
"serverKeyPath": "/etc/certs/server.key",
6+
7+
"enableOAuth": true,
8+
"oauthIssuer": "https://your-oauth-provider.com",
9+
"oauthJWKSURL": "https://your-oauth-provider.com/.well-known/jwks.json",
10+
"requiredScopes": ["subscription:create", "events:read"],
11+
"requiredAudience": "rest-api-service"
12+
}

examples/README.md

Lines changed: 34 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,34 @@
1+
# Authentication Configuration Examples
2+
3+
This directory contains example configuration files for setting up authentication with the REST API.
4+
5+
## Files
6+
7+
### Configuration Examples
8+
9+
- **`openshift-auth-config.json`** - Example authentication configuration for OpenShift environments
10+
- Uses OpenShift Service CA for mTLS certificate management
11+
- Integrates with OpenShift's built-in OAuth server
12+
- Template format with placeholder URLs that should be customized for your cluster
13+
14+
### Deployment Examples
15+
16+
- **`openshift-manifests.yaml`** - Complete Kubernetes manifests for OpenShift deployment
17+
- Service definitions with Service CA annotations
18+
- ConfigMaps for cluster information and authentication configuration
19+
- ServiceAccount and RBAC resources
20+
- Template format with `{{.NodeName}}` and `{{.ClusterName}}` placeholders
21+
22+
## Usage
23+
24+
1. **For OpenShift deployments**: Use the `openshift-*` files as templates
25+
2. **Replace placeholders**: Update `your-cluster.com` with your actual cluster domain
26+
3. **Deploy**: Apply the manifests to your OpenShift cluster
27+
28+
## Template Variables
29+
30+
- `{{.NodeName}}` - Replaced with the actual node name during deployment
31+
- `{{.ClusterName}}` - Should be replaced with your cluster's domain name
32+
- `your-cluster.com` - Placeholder that should be replaced with your actual cluster domain
33+
34+
For detailed instructions, see the main [Authentication Configuration](../AUTHENTICATION.md) documentation.
Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,15 @@
1+
{
2+
"enableMTLS": true,
3+
"useServiceCA": true,
4+
"caCertPath": "/etc/cloud-event-proxy/ca-bundle/service-ca.crt",
5+
"serverCertPath": "/etc/cloud-event-proxy/server-certs/tls.crt",
6+
"serverKeyPath": "/etc/cloud-event-proxy/server-certs/tls.key",
7+
"enableOAuth": true,
8+
"useOpenShiftOAuth": true,
9+
"oauthIssuer": "https://oauth-openshift.apps.your-cluster.com",
10+
"oauthJWKSURL": "https://oauth-openshift.apps.your-cluster.com/oauth/jwks",
11+
"requiredScopes": ["user:info"],
12+
"requiredAudience": "openshift",
13+
"serviceAccountName": "cloud-event-proxy-sa",
14+
"serviceAccountToken": "/var/run/secrets/kubernetes.io/serviceaccount/token"
15+
}

examples/openshift-manifests.yaml

Lines changed: 159 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,159 @@
1+
# Unified OpenShift Authentication Configuration
2+
# Works for both single node and multi-node OpenShift clusters
3+
# Uses OpenShift's built-in Service CA and OAuth server
4+
5+
---
6+
# Service with Service CA annotation for automatic certificate generation
7+
apiVersion: v1
8+
kind: Service
9+
metadata:
10+
annotations:
11+
prometheus.io/scrape: "false"
12+
service.beta.openshift.io/serving-cert-secret-name: cloud-event-proxy-tls
13+
labels:
14+
app: linuxptp-daemon
15+
name: ptp-event-publisher-service-{{.NodeName}}
16+
namespace: openshift-ptp
17+
spec:
18+
clusterIP: None
19+
selector:
20+
app: linuxptp-daemon
21+
nodeName: {{.NodeName}}
22+
ports:
23+
- name: publisher-port
24+
port: 9043
25+
sessionAffinity: None
26+
type: ClusterIP
27+
28+
---
29+
# ConfigMap for cluster information
30+
apiVersion: v1
31+
kind: ConfigMap
32+
metadata:
33+
name: cluster-info
34+
namespace: openshift-ptp
35+
data:
36+
cluster-name: "{{.ClusterName}}"
37+
38+
---
39+
# ConfigMap for authentication configuration
40+
apiVersion: v1
41+
kind: ConfigMap
42+
metadata:
43+
name: cloud-event-proxy-auth-config
44+
namespace: openshift-ptp
45+
data:
46+
auth-config.json: |
47+
{
48+
"enableMTLS": true,
49+
"useServiceCA": true,
50+
"caCertPath": "/etc/cloud-event-proxy/ca-bundle/service-ca.crt",
51+
"serverCertPath": "/etc/cloud-event-proxy/server-certs/tls.crt",
52+
"serverKeyPath": "/etc/cloud-event-proxy/server-certs/tls.key",
53+
"enableOAuth": true,
54+
"useOpenShiftOAuth": true,
55+
"oauthIssuer": "https://oauth-openshift.apps.{{.ClusterName}}",
56+
"oauthJWKSURL": "https://oauth-openshift.apps.{{.ClusterName}}/oauth/jwks",
57+
"requiredScopes": ["user:info"],
58+
"requiredAudience": "openshift",
59+
"serviceAccountName": "cloud-event-proxy-sa",
60+
"serviceAccountToken": "/var/run/secrets/kubernetes.io/serviceaccount/token"
61+
}
62+
63+
---
64+
# ServiceAccount for the cloud-event-proxy
65+
apiVersion: v1
66+
kind: ServiceAccount
67+
metadata:
68+
name: cloud-event-proxy-sa
69+
namespace: openshift-ptp
70+
71+
---
72+
# Role for cloud-event-proxy permissions
73+
apiVersion: rbac.authorization.k8s.io/v1
74+
kind: Role
75+
metadata:
76+
name: cloud-event-proxy-role
77+
namespace: openshift-ptp
78+
rules:
79+
- apiGroups: [""]
80+
resources: ["events"]
81+
verbs: ["create", "update", "patch"]
82+
- apiGroups: [""]
83+
resources: ["configmaps"]
84+
verbs: ["get", "list", "watch"]
85+
- apiGroups: [""]
86+
resources: ["secrets"]
87+
verbs: ["get", "list", "watch"]
88+
89+
---
90+
# RoleBinding to bind ServiceAccount to Role
91+
apiVersion: rbac.authorization.k8s.io/v1
92+
kind: RoleBinding
93+
metadata:
94+
name: cloud-event-proxy-binding
95+
namespace: openshift-ptp
96+
subjects:
97+
- kind: ServiceAccount
98+
name: cloud-event-proxy-sa
99+
namespace: openshift-ptp
100+
roleRef:
101+
kind: Role
102+
name: cloud-event-proxy-role
103+
apiGroup: rbac.authorization.k8s.io
104+
105+
---
106+
# DaemonSet configuration for cloud-event-proxy
107+
# Works on both single node and multi-node clusters
108+
apiVersion: apps/v1
109+
kind: DaemonSet
110+
metadata:
111+
name: linuxptp-daemon
112+
namespace: openshift-ptp
113+
spec:
114+
selector:
115+
matchLabels:
116+
app: linuxptp-daemon
117+
nodeName: {{.NodeName}}
118+
template:
119+
metadata:
120+
labels:
121+
app: linuxptp-daemon
122+
nodeName: {{.NodeName}}
123+
spec:
124+
serviceAccountName: cloud-event-proxy-sa
125+
containers:
126+
- name: cloud-event-proxy
127+
image: quay.io/redhat-cne/cloud-event-proxy:latest
128+
args:
129+
- "--auth-config=/etc/cloud-event-proxy/auth/auth-config.json"
130+
env:
131+
- name: CLUSTER_NAME
132+
valueFrom:
133+
configMapKeyRef:
134+
name: cluster-info
135+
key: cluster-name
136+
- name: NODE_NAME
137+
valueFrom:
138+
fieldRef:
139+
fieldPath: spec.nodeName
140+
volumeMounts:
141+
- name: server-certs
142+
mountPath: /etc/cloud-event-proxy/server-certs
143+
readOnly: true
144+
- name: ca-bundle
145+
mountPath: /etc/cloud-event-proxy/ca-bundle
146+
readOnly: true
147+
- name: auth-config
148+
mountPath: /etc/cloud-event-proxy/auth
149+
readOnly: true
150+
volumes:
151+
- name: server-certs
152+
secret:
153+
secretName: cloud-event-proxy-tls
154+
- name: ca-bundle
155+
secret:
156+
secretName: cloud-event-proxy-tls
157+
- name: auth-config
158+
configMap:
159+
name: cloud-event-proxy-auth-config

go.mod

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,7 @@ require (
2020
github.com/beorn7/perks v1.0.1 // indirect
2121
github.com/cespare/xxhash/v2 v2.1.2 // indirect
2222
github.com/davecgh/go-spew v1.1.1 // indirect
23+
github.com/golang-jwt/jwt/v5 v5.3.0 // indirect
2324
github.com/golang/protobuf v1.5.2 // indirect
2425
github.com/json-iterator/go v1.1.12 // indirect
2526
github.com/matttproud/golang_protobuf_extensions v1.0.4 // indirect

go.sum

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,8 @@ github.com/cloudevents/sdk-go/v2 v2.15.2/go.mod h1:lL7kSWAE/V8VI4Wh0jbL2v/jvqsm6
99
github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
1010
github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c=
1111
github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
12+
github.com/golang-jwt/jwt/v5 v5.3.0 h1:pv4AsKCKKZuqlgs5sUmn4x8UlGa0kEVt/puTpKx9vvo=
13+
github.com/golang-jwt/jwt/v5 v5.3.0/go.mod h1:fxCRLWMO43lRc8nhHWY6LGqRcf+1gQWArsqaEUEa5bE=
1214
github.com/golang/protobuf v1.2.0/go.mod h1:6lQm79b+lXiMfvg/cZm0SGofjICqVBUtrP5yJMmIC1U=
1315
github.com/golang/protobuf v1.3.5/go.mod h1:6O5/vntMXwX2lRkT1hjjk0nAC1IDOTvTlVgjlRvqsdk=
1416
github.com/golang/protobuf v1.5.0/go.mod h1:FsONVRAS9T7sI+LIUmWTfcYkHO4aIWwzhcaSAoJOfIk=

0 commit comments

Comments
 (0)