diff --git a/.github/workflows/lint.yml b/.github/workflows/lint.yml index 68a405b612..cf6745cb79 100644 --- a/.github/workflows/lint.yml +++ b/.github/workflows/lint.yml @@ -100,7 +100,7 @@ jobs: uses: actions/checkout@1af3b93b6815bc44a9784bd300feb67ff0d1eeb3 # v6.0.0 - name: Lint Markdown - uses: DavidAnson/markdownlint-cli2-action@992badcdf24e3b8eb7e87ff9287fe931bcb00c6e # v20.0.0 + uses: DavidAnson/markdownlint-cli2-action@30a0e04f1870d58f8d717450cc6134995f993c63 # v21.0.0 with: config: .markdownlint-cli2.yaml globs: "**/*.md" diff --git a/.markdownlint-cli2.yaml b/.markdownlint-cli2.yaml index 904d6875c7..40b850cd42 100644 --- a/.markdownlint-cli2.yaml +++ b/.markdownlint-cli2.yaml @@ -20,3 +20,5 @@ config: ignores: - ".github/" - "tests/results/" + # Generated Charts docs; excluded from lint to avoid churn + - "charts/nginx-gateway-fabric/README.md" diff --git a/README.md b/README.md index 0ed4ce6437..4186e02163 100644 --- a/README.md +++ b/README.md @@ -45,10 +45,10 @@ from the main branch. The table below summarizes the options regarding the images, manifests, documentation and examples and gives your links to the correct versions: -| Version | Description | Installation Manifests | Documentation and Examples | -|----------------|------------------------------------------|--------------------------------------------------------------------------------|----------------------------------------------------------------------------------------------------------------------------------------------------------------------| -| Latest release | For production use | [Manifests](https://github.com/nginx/nginx-gateway-fabric/tree/v2.2.1/deploy). | [Documentation](https://docs.nginx.com/nginx-gateway-fabric). [Examples](https://github.com/nginx/nginx-gateway-fabric/tree/v2.2.1/examples). | -| Edge | For experimental use and latest features | [Manifests](https://github.com/nginx/nginx-gateway-fabric/tree/main/deploy). | [Examples](https://github.com/nginx/nginx-gateway-fabric/tree/main/examples). | +| Version | Description | Installation Manifests | Documentation and Examples | +| ------- | ----------- | ---------------------- | -------------------------- | +| Latest release | For production use | [Manifests](https://github.com/nginx/nginx-gateway-fabric/tree/v2.2.1/deploy). | [Documentation](https://docs.nginx.com/nginx-gateway-fabric). [Examples](https://github.com/nginx/nginx-gateway-fabric/tree/v2.2.1/examples). | +| Edge | For experimental use and latest features | [Manifests](https://github.com/nginx/nginx-gateway-fabric/tree/main/deploy). | [Examples](https://github.com/nginx/nginx-gateway-fabric/tree/main/examples). | ### Versioning diff --git a/docs/proposals/authentication-filter.md b/docs/proposals/authentication-filter.md index bbf06c17cd..ff92bbd831 100644 --- a/docs/proposals/authentication-filter.md +++ b/docs/proposals/authentication-filter.md @@ -37,11 +37,11 @@ This document also focus on HTTP Basic Authentication and JWT Authentication. Ot ### Understanding NGINX authentication methods -| **Authentication Method** | **OSS** | **Plus** | **NGINX Module** | **Details** | -|-------------------------------|--------------|----------------|----------------------------------|--------------------------------------------------------------------| -| **HTTP Basic Authentication** | ✅ | ✅ | [ngx_http_auth_basic](https://nginx.org/en/docs/http/ngx_http_auth_basic_module.html) | Requires a username and password sent in an HTTP header. | -| **JWT (JSON Web Token)** | ❌ | ✅ | [ngx_http_auth_jwt_module](https://nginx.org/en/docs/http/ngx_http_auth_jwt_module.html) | Tokens are used for stateless authentication between client and server. | -| **OpenID Connect** | ❌ | ✅ | [ngx_http_oidc_module](https://nginx.org/en/docs/http/ngx_http_oidc_module.html)| Allows authentication through third-party providers like Google. | +| **Authentication Method** | **OSS** | **Plus** | **NGINX Module** | **Details** | +| ------------------------------- | -------------- | ---------------- | ---------------------------------- | -------------------------------------------------------------------- | +| **HTTP Basic Authentication** | ✅ | ✅ | [ngx_http_auth_basic](https://nginx.org/en/docs/http/ngx_http_auth_basic_module.html) | Requires a username and password sent in an HTTP header. | +| **JWT (JSON Web Token)** | ❌ | ✅ | [ngx_http_auth_jwt_module](https://nginx.org/en/docs/http/ngx_http_auth_jwt_module.html) | Tokens are used for stateless authentication between client and server. | +| **OpenID Connect** | ❌ | ✅ | [ngx_http_oidc_module](https://nginx.org/en/docs/http/ngx_http_oidc_module.html) | Allows authentication through third-party providers like Google. | ### Understanding authentication terminology @@ -427,6 +427,7 @@ user:$apr1$prQ3Bh4t$A6bmTv7VgmemGe5eqR61j0 ``` Use these options in the `htpasswd` command for stronger hashing algorithims: + ```bash -2 Force SHA-256 hashing of the password (secure). -5 Force SHA-512 hashing of the password (secure). @@ -434,6 +435,7 @@ Use these options in the `htpasswd` command for stronger hashing algorithims: ``` You can then run this command to generate the secret from the `auth` file: + ```bash kubectl create secret generic basic-auth --from-file=auth ``` @@ -441,6 +443,7 @@ kubectl create secret generic basic-auth --from-file=auth Note: `auth` will be the default key for secrets referenced `AuthenticationFilters` of `Type: Basic`. Example secret: + ```yaml apiVersion: v1 kind: Secret diff --git a/docs/proposals/nap-waf.md b/docs/proposals/nap-waf.md index c0fd553b0a..b7f6c5902a 100644 --- a/docs/proposals/nap-waf.md +++ b/docs/proposals/nap-waf.md @@ -716,17 +716,17 @@ According to the [Policy and Metaresources GEP](https://gateway-api.sigs.k8s.io/ The `Accepted` Condition must be populated on the `WAFPolicy` CRD using the reasons defined in the [PolicyCondition API](https://github.com/kubernetes-sigs/gateway-api/blob/main/apis/v1alpha2/policy_types.go). Below are example implementation-specific reasons that describe the lifecycle phases and potential issues encountered while processing the policy: -| **Reason** | **Description** | **Example Message** | -|---------------------------|---------------------------------------------------------------------------------------------------|-------------------------------------------------------------------| -| **PolicySourceInvalid** | The `policySource` contains invalid or incomplete information. | "The policy source is invalid. Ensure fileLocation is correct." | -| **PolicyFetchError** | Failed to fetch the policy due to network issues, authentication problems, or source misconfiguration. | "Failed to fetch policy bundle due to a network issue or invalid credentials." | -| **PolicyIntegrityInvalid**| Checksum verification failed for the fetched policy bundle. | "Policy integrity check failed because of a checksum mismatch." | -| **PolicyValidationError** | The WAF policy bundle failed schema or format validation for NGINX App Protect WAF. | "The policy bundle did not pass schema validation. Update the policy and retry compilation." | -| **PolicyDeployed** | The policy was successfully deployed to the NGINX Data Plane (Pods). | "The policy has been successfully deployed and is now protecting the targeted resources." | -| **PolicyDeployedUpdate** | An updated version of the policy was successfully deployed to the NGINX Data Plane (Pods) after polling or change detection. | "The policy has been updated and successfully redeployed to the targeted resources." | -| **PolicyDeploymentError** | The data plane (NGINX Pods) failed to apply the policy. | "Failed to deploy the WAF policy to the NGINX Pods." | -| **AuthenticationError** | Authentication to the external store (e.g., S3, HTTP) failed. | "Authentication error while trying to fetch the policy bundle." | -| **PolicyConfigError** | The policy configuration prevents proper processing. | "The policy configuration is incomplete or incorrectly formatted. Correct the configuration and retry." | +| **Reason** | **Description** | **Example Message** | +| ---------- | --------------- | ------------------- | +| **PolicySourceInvalid** | The `policySource` contains invalid or incomplete information. | "The policy source is invalid. Ensure fileLocation is correct." | +| **PolicyFetchError** | Failed to fetch the policy due to network issues, authentication problems, or source misconfiguration. | "Failed to fetch policy bundle due to a network issue or invalid credentials." | +| **PolicyIntegrityInvalid** | Checksum verification failed for the fetched policy bundle. | "Policy integrity check failed because of a checksum mismatch." | +| **PolicyValidationError** | The WAF policy bundle failed schema or format validation for NGINX App Protect WAF. | "The policy bundle did not pass schema validation. Update the policy and retry compilation." | +| **PolicyDeployed** | The policy was successfully deployed to the NGINX Data Plane (Pods). | "The policy has been successfully deployed and is now protecting the targeted resources." | +| **PolicyDeployedUpdate** | An updated version of the policy was successfully deployed to the NGINX Data Plane (Pods) after polling or change detection. | "The policy has been updated and successfully redeployed to the targeted resources." | +| **PolicyDeploymentError** | The data plane (NGINX Pods) failed to apply the policy. | "Failed to deploy the WAF policy to the NGINX Pods." | +| **AuthenticationError** | Authentication to the external store (e.g., S3, HTTP) failed. | "Authentication error while trying to fetch the policy bundle." | +| **PolicyConfigError** | The policy configuration prevents proper processing. | "The policy configuration is incomplete or incorrectly formatted. Correct the configuration and retry." | ### Example Status Conditions in `WAFPolicy` diff --git a/docs/proposals/session-persistence.md b/docs/proposals/session-persistence.md index f186c758e6..818bb51fa6 100644 --- a/docs/proposals/session-persistence.md +++ b/docs/proposals/session-persistence.md @@ -129,16 +129,16 @@ Users can configure [sessionPersistence](https://gateway-api.sigs.k8s.io/referen #### Mapping the Gateway API fields to NGINX directives -| Spec Field | NGINX Directive | Notes / Limitations | -|----------------------------------------|----------------------------|-------------------------------------------------------------------------------------------------------------------------------------| -| `sessionName` | `name` | Direct mapping to `sticky cookie` name. | -| `absoluteTimeout` | `expires` | Only used when `cookieConfig.lifetimeType=Permanent`; not enforced for `Session` cookies. | -| `idleTimeout` | _not supported_ | NGINX does not support idle-based invalidation for sticky cookies. Sessions expire only when the cookie expires or the session ends.| -| `type` | `cookie` | Only cookie-based persistence is supported. If Header is specified, the sessionPersistence spec is ignored and a warning/status message is reported on the route, but the route itself remains valid. | -| `cookieConfig.lifetimeType=Session` | _no `expires` set_ | Session cookies expire when the browser session ends. | -| `cookieConfig.lifetimeType=Permanent` | `expires=`| Cookie persists until the specified timeout. `absoluteTimeout` is required when `lifetimeType` is `Permanent`. | -| no matching spec field | _no `domain` attribute_ | Cookies are host-only for both `HTTPRoute` and `GRPCRoute`. | -| no matching spec field | `path` | Behavior is described separately for `HTTPRoute` below. | +| Spec Field | NGINX Directive | Notes / Limitations | +| ---------- | --------------- | ------------------- | +| `sessionName` | `name` | Direct mapping to `sticky cookie` name. | +| `absoluteTimeout` | `expires` | Only used when `cookieConfig.lifetimeType=Permanent`; not enforced for `Session` cookies. | +| `idleTimeout` | _not supported_ | NGINX does not support idle-based invalidation for sticky cookies. Sessions expire only when the cookie expires or the session ends. | +| `type` | `cookie` | Only cookie-based persistence is supported. If Header is specified, the sessionPersistence spec is ignored and a warning/status message is reported on the route, but the route itself remains valid. | +| `cookieConfig.lifetimeType=Session` | _no `expires` set_ | Session cookies expire when the browser session ends. | +| `cookieConfig.lifetimeType=Permanent` | `expires=` | Cookie persists until the specified timeout. `absoluteTimeout` is required when `lifetimeType` is `Permanent`. | +| no matching spec field | _no `domain` attribute_ | Cookies are host-only for both `HTTPRoute` and `GRPCRoute`. | +| no matching spec field | `path` | Behavior is described separately for `HTTPRoute` below. | #### Domain and Path selection for Routes @@ -148,11 +148,11 @@ For **HTTPRoutes**, we do not set the `domain` attribute. Deriving a broader dom To determine the cookie `path` for HTTPRoutes, we handle the simple case where there is a single path match as follows: -| Path Value | Path Match Type | Cookie `Path` Value | Cookie Match Expectations | -|-------------------------------------|-----------------|---------------------|---------------------------------------------------------------------------------------------------------------------------------------------------| -| `/hello-exact` | Exact | `/hello-exact` | Cookie header is sent for `/hello-exact` path only. | -| `/hello-prefix` | Prefix | `/hello-prefix` | Cookie header is sent for `/hello-prefix` and any subpath starting with `/hello-prefix` (e.g. `/hello-prefix/foo`). | -| `/hello-regex/[a-zA-Z0-9_-]+$` | Regex | `/hello-regex` | No `path` attribute is set for pathType `RegularExpression` | +| Path Value | Path Match Type | Cookie `Path` Value | Cookie Match Expectations | +| ---------- | --------------- | ------------------- | ------------------------- | +| `/hello-exact` | Exact | `/hello-exact` | Cookie header is sent for `/hello-exact` path only. | +| `/hello-prefix` | Prefix | `/hello-prefix` | Cookie header is sent for `/hello-prefix` and any subpath starting with `/hello-prefix` (e.g. `/hello-prefix/foo`). | +| `/hello-regex/[a-zA-Z0-9_-]+$` | Regex | `/hello-regex` | No `path` attribute is set for pathType `RegularExpression` | When there are multiple path matches that share the same sessionPersistence configuration, we derive a single cookie path by computing the longest common prefix that ends on a path-segment boundary `/`. If no non-empty common prefix on a segment boundary exists, we fall back to `/` which is allowing all paths.