diff --git a/.ct.yaml b/.ct.yaml deleted file mode 100644 index 229030219..000000000 --- a/.ct.yaml +++ /dev/null @@ -1,26 +0,0 @@ -# Copyright 2024 The Kubernetes Authors. -# -# Licensed under the Apache License, Version 2.0 (the "License"); -# you may not use this file except in compliance with the License. -# You may obtain a copy of the License at -# -# http://www.apache.org/licenses/LICENSE-2.0 -# -# Unless required by applicable law or agreed to in writing, software -# distributed under the License is distributed on an "AS IS" BASIS, -# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -# See the License for the specific language governing permissions and -# limitations under the License. ---- -remote: origin -target-branch: main - -validate-maintainers: false -check-version-increment: false - -chart-repos: - - ingress-nginx=https://kubernetes.github.io/ingress-nginx -helm-extra-args: --timeout 800s - -chart-dirs: - - charts diff --git a/.gcloudignore b/.gcloudignore deleted file mode 100644 index e69de29bb..000000000 diff --git a/.github/ISSUE_TEMPLATE/bug_report.md b/.github/ISSUE_TEMPLATE/bug_report.md deleted file mode 100644 index 07770e47c..000000000 --- a/.github/ISSUE_TEMPLATE/bug_report.md +++ /dev/null @@ -1,142 +0,0 @@ ---- -name: Bug report -about: Problems and issues with code or docs -title: '' -labels: kind/bug -assignees: '' - ---- - - - - - -**What happened**: - - - -**What you expected to happen**: - - - - -**NGINX Ingress controller version** (exec into the pod and run `/nginx-ingress-controller --version`): - - -**Kubernetes version** (use `kubectl version`): - -**Environment**: - -- **Cloud provider or hardware configuration**: -- **OS** (e.g. from /etc/os-release): -- **Kernel** (e.g. `uname -a`): -- **Install tools**: - - `Please mention how/where was the cluster created like kubeadm/kops/minikube/kind etc. ` -- **Basic cluster related info**: - - `kubectl version` - - `kubectl get nodes -o wide` - -- **How was the ingress-nginx-controller installed**: - - If helm was used then please show output of `helm ls -A | grep -i ingress` - - If helm was used then please show output of `helm -n get values ` - - If helm was not used, then copy/paste the complete precise command used to install the controller, along with the flags and options used - - if you have more than one instance of the ingress-nginx-controller installed in the same cluster, please provide details for all the instances - -- **Current State of the controller**: - - `kubectl describe ingressclasses` - - `kubectl -n get all -A -o wide` - - `kubectl -n describe po ` - - `kubectl -n describe svc ` - -- **Current state of ingress object, if applicable**: - - `kubectl -n get all,ing -o wide` - - `kubectl -n describe ing ` - - If applicable, then, your complete and exact curl/grpcurl command (redacted if required) and the reponse to the curl/grpcurl command with the -v flag - -- **Others**: - - Any other related information like ; - - copy/paste of the snippet (if applicable) - - `kubectl describe ...` of any custom configmap(s) created and in use - - Any other related information that may help - - -**How to reproduce this issue**: - - -**Anything else we need to know**: - - - - diff --git a/.github/ISSUE_TEMPLATE/config.yml b/.github/ISSUE_TEMPLATE/config.yml deleted file mode 100644 index 888b1d5dd..000000000 --- a/.github/ISSUE_TEMPLATE/config.yml +++ /dev/null @@ -1,4 +0,0 @@ -contact_links: - - name: Support Request/Question - url: https://kubernetes.slack.com/messages/ingress-nginx/ - about: Support request or question relating to Ingress NGINX in Kubernetes Slack diff --git a/.github/ISSUE_TEMPLATE/cve_report.md b/.github/ISSUE_TEMPLATE/cve_report.md deleted file mode 100644 index d6e598c88..000000000 --- a/.github/ISSUE_TEMPLATE/cve_report.md +++ /dev/null @@ -1,20 +0,0 @@ ---- -name: CVE Finding Report -about: CVE reporting for ingress-nginx -title: '' -labels: kind/bug -assignees: - - Gacko - - strongjz ---- - - - - - - - - - - diff --git a/.github/ISSUE_TEMPLATE/feature_request.md b/.github/ISSUE_TEMPLATE/feature_request.md deleted file mode 100644 index 406a7ad0a..000000000 --- a/.github/ISSUE_TEMPLATE/feature_request.md +++ /dev/null @@ -1,21 +0,0 @@ ---- -name: Feature request -about: Suggest an idea for this project or its docs -title: '' -labels: kind/feature -assignees: '' - ---- - - - - - - - - - - diff --git a/.github/PULL_REQUEST_TEMPLATE.md b/.github/PULL_REQUEST_TEMPLATE.md deleted file mode 100644 index c1c815678..000000000 --- a/.github/PULL_REQUEST_TEMPLATE.md +++ /dev/null @@ -1,36 +0,0 @@ - - - - -## What this PR does / why we need it: - - - -## Types of changes - -- [ ] Bug fix (non-breaking change which fixes an issue) -- [ ] New feature (non-breaking change which adds functionality) -- [ ] CVE Report (Scanner found CVE and adding report) -- [ ] Breaking change (fix or feature that would cause existing functionality to change) -- [ ] Documentation only - -## Which issue/s this PR fixes - - -## How Has This Been Tested? - - - - -## Checklist: - - -- [ ] My change requires a change to the documentation. -- [ ] I have updated the documentation accordingly. -- [ ] I've read the [CONTRIBUTION](https://github.com/kubernetes/ingress-nginx/blob/main/CONTRIBUTING.md) guide -- [ ] I have added unit and/or e2e tests to cover my changes. -- [ ] All new and existing tests passed. diff --git a/.github/actions/mkdocs/Dockerfile b/.github/actions/mkdocs/Dockerfile deleted file mode 100644 index f00584d32..000000000 --- a/.github/actions/mkdocs/Dockerfile +++ /dev/null @@ -1,8 +0,0 @@ -FROM squidfunk/mkdocs-material:9.4.5 - -COPY action.sh /action.sh - -RUN apk add --no-cache bash \ - && chmod +x /action.sh - -ENTRYPOINT ["/action.sh"] diff --git a/.github/actions/mkdocs/action.sh b/.github/actions/mkdocs/action.sh deleted file mode 100644 index d9f8ecbfc..000000000 --- a/.github/actions/mkdocs/action.sh +++ /dev/null @@ -1,51 +0,0 @@ -#!/bin/bash - -# Copyright 2020 The Kubernetes Authors. -# -# Licensed under the Apache License, Version 2.0 (the "License"); -# you may not use this file except in compliance with the License. -# You may obtain a copy of the License at -# -# http://www.apache.org/licenses/LICENSE-2.0 -# -# Unless required by applicable law or agreed to in writing, software -# distributed under the License is distributed on an "AS IS" BASIS, -# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -# See the License for the specific language governing permissions and -# limitations under the License. - -set -e - -REQUIREMENTS="${GITHUB_WORKSPACE}/docs/requirements.txt" - -if [ -f "${REQUIREMENTS}" ]; then - pip install -r "${REQUIREMENTS}" -fi - -if [ -n "${GITHUB_TOKEN}" ]; then - remote_repo="https://x-access-token:${GITHUB_TOKEN}@github.com/${GITHUB_REPOSITORY}.git" -elif [ -n "${PERSONAL_TOKEN}" ]; then - remote_repo="https://x-access-token:${PERSONAL_TOKEN}@github.com/${GITHUB_REPOSITORY}.git" -fi - -git config --global user.name "$GITHUB_ACTOR" -git config --global user.email "$GITHUB_ACTOR@users.noreply.github.com" - -mkdocs build --config-file "${GITHUB_WORKSPACE}/mkdocs.yml" - -git clone --branch=gh-pages --depth=1 "${remote_repo}" gh-pages -cd gh-pages - -# copy current index file index.yaml before any change -temp_worktree=$(mktemp -d) -cp --force "index.yaml" "$temp_worktree/index.yaml" -# remove current content in branch gh-pages -git rm -r . -# copy new doc. -cp -r ../site/* . -# restore chart index -cp "$temp_worktree/index.yaml" . -# commit changes -git add . -git commit -m "Deploy GitHub Pages" -git push --force --quiet "${remote_repo}" gh-pages > /dev/null 2>&1 diff --git a/.github/actions/mkdocs/action.yml b/.github/actions/mkdocs/action.yml deleted file mode 100644 index 20860f3c9..000000000 --- a/.github/actions/mkdocs/action.yml +++ /dev/null @@ -1,9 +0,0 @@ -# action.yml -name: 'Deploy MkDocs' -description: 'Deploys MkDocs site' -branding: - icon: 'arrow-up-circle' - color: 'orange' -runs: - using: 'docker' - image: 'Dockerfile' diff --git a/.github/dependabot.yml b/.github/dependabot.yml deleted file mode 100644 index deb434675..000000000 --- a/.github/dependabot.yml +++ /dev/null @@ -1,43 +0,0 @@ -version: 2 -updates: - - package-ecosystem: "github-actions" - directory: "/" - schedule: - interval: "weekly" - labels: - - "area/dependency" - - "release-note-none" - - "ok-to-test" - groups: - actions: - update-types: - - "minor" - - "patch" - - package-ecosystem: "docker" - directories: - - "**/rootfs" - schedule: - interval: "weekly" - labels: - - "area/dependency" - - "release-note-none" - - "ok-to-test" - groups: - docker: - update-types: - - "minor" - - "patch" - - package-ecosystem: "gomod" - directories: - - "/" - - "**/rootfs" - schedule: - interval: "weekly" - labels: - - "area/dependency" - - "release-note-none" - - "ok-to-test" - groups: - go: - update-types: - - "patch" diff --git a/.github/workflows/chart.yaml b/.github/workflows/chart.yaml deleted file mode 100644 index 7c37447af..000000000 --- a/.github/workflows/chart.yaml +++ /dev/null @@ -1,64 +0,0 @@ -name: Chart - -on: - push: - branches: - - main - - release-* - paths: - - charts/ingress-nginx/Chart.yaml - - workflow_dispatch: - -permissions: - contents: read - -jobs: - release: - name: Release - runs-on: ubuntu-latest - - permissions: - contents: write - - steps: - - name: Set up Python - uses: actions/setup-python@42375524e23c412d93fb67b49958b491fce71c38 # v5.4.0 - with: - python-version: 3.x - - - name: Set up Helm - uses: azure/setup-helm@fe7b79cd5ee1e45176fcad797de68ecaf3ca4814 # v4.2.0 - - - name: Set up Helm Chart Testing - uses: helm/chart-testing-action@0d28d3144d3a25ea2cc349d6e59901c4ff469b3b # v2.7.0 - - - name: Set up Artifact Hub - run: | - curl --fail --location https://github.com/artifacthub/hub/releases/download/v1.20.0/ah_1.20.0_linux_amd64.tar.gz --output /tmp/ah.tar.gz - echo "9027626f19ff9f3ac668f222917130ac885e289e922e1428bfd2e7f066324e31 /tmp/ah.tar.gz" | shasum --check - sudo tar --extract --file /tmp/ah.tar.gz --directory /usr/local/bin ah - - - name: Set up Git - run: | - git config --global user.name "${GITHUB_ACTOR}" - git config --global user.email "${GITHUB_ACTOR}@users.noreply.github.com" - - - name: Checkout code - uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2 - with: - fetch-depth: 0 - - - name: Lint chart - run: | - ct lint --config .ct.yaml - ah lint --path charts/ingress-nginx - - - name: Release chart - uses: helm/chart-releaser-action@cae68fefc6b5f367a0275617c9f83181ba54714f # v1.7.0 - env: - CR_TOKEN: ${{ secrets.GITHUB_TOKEN }} - CR_RELEASE_NAME_TEMPLATE: helm-chart-{{ .Version }} - CR_SKIP_EXISTING: true - with: - charts_dir: charts diff --git a/.github/workflows/ci.yaml b/.github/workflows/ci.yaml deleted file mode 100644 index b06cef33c..000000000 --- a/.github/workflows/ci.yaml +++ /dev/null @@ -1,322 +0,0 @@ -name: CI - -on: - pull_request: - branches: - - "*" - paths-ignore: - - 'docs/**' - - 'deploy/**' - - '**.md' - - 'images/**' # Images changes should be tested on their own workflow - - '!images/nginx/**' - - push: - branches: - - main - - release-* - paths-ignore: - - 'docs/**' - - 'deploy/**' - - '**.md' - - 'images/**' # Images changes should be tested on their own workflow - - workflow_dispatch: - inputs: - run_e2e: - description: 'Force e2e to run' - required: false - type: boolean - - -permissions: - contents: read - -jobs: - - changes: - permissions: - contents: read # for dorny/paths-filter to fetch a list of changed files - pull-requests: read # for dorny/paths-filter to read pull requests - runs-on: ubuntu-latest - outputs: - go: ${{ steps.filter.outputs.go }} - charts: ${{ steps.filter.outputs.charts }} - baseimage: ${{ steps.filter.outputs.baseimage }} - - steps: - - - name: Checkout - uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2 - - - uses: dorny/paths-filter@de90cc6fb38fc0963ad72b210f1f284cd68cea36 # v3.0.2 - id: filter - with: - token: ${{ secrets.GITHUB_TOKEN }} - filters: | - go: - - '**/*.go' - - 'go.mod' - - 'go.sum' - - 'rootfs/**/*' - - 'TAG' - - 'test/e2e/**/*' - - 'NGINX_BASE' - charts: - - 'charts/ingress-nginx/Chart.yaml' - - 'charts/ingress-nginx/**/*' - - 'NGINX_BASE' - baseimage: - - 'NGINX_BASE' - - 'images/nginx/**' - docs: - - '**/*.md' - lua: - - '**/*.lua' - - lua-lint: - runs-on: ubuntu-latest - needs: changes - if: | - (needs.changes.outputs.lua == 'true') || ${{ github.event.workflow_dispatch.run_e2e == 'true' }} - steps: - - name: Checkout - uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2 - - - name: Lint Lua - uses: lunarmodules/luacheck@v1 - with: - args: --codes --globals lua_ingress --globals configuration --globals balancer --globals monitor --globals certificate --globals tcp_udp_configuration --globals tcp_udp_balancer --no-max-comment-line-length -q rootfs/etc/nginx/lua/ - - test-go: - runs-on: ubuntu-latest - needs: changes - if: | - (needs.changes.outputs.go == 'true') || ${{ github.event.workflow_dispatch.run_e2e == 'true' }} - steps: - - name: Checkout - uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2 - - - name: Get go version - run: echo "GOLANG_VERSION=$(cat GOLANG_VERSION)" >> $GITHUB_ENV - - - name: Set up Go - id: go - uses: actions/setup-go@f111f3307d8850f501ac008e886eec1fd1932a34 # v5.3.0 - with: - go-version: ${{ env.GOLANG_VERSION }} - check-latest: true - - - name: Run test - run: make test - - - verify-docs: - name: Verify Doc generation - runs-on: ubuntu-latest - needs: changes - if: | - (needs.changes.outputs.go == 'true') || (needs.changes.outputs.docs == 'true') || ${{ github.event.workflow_dispatch.run_e2e == 'true' }} - steps: - - name: Checkout - uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2 - - name: Get go version - run: echo "GOLANG_VERSION=$(cat GOLANG_VERSION)" >> $GITHUB_ENV - - name: Set up Go - id: go - uses: actions/setup-go@f111f3307d8850f501ac008e886eec1fd1932a34 # v5.3.0 - with: - go-version: ${{ env.GOLANG_VERSION }} - check-latest: true - - name: Verify Docs - run: make verify-docs - - build: - name: Build - runs-on: ubuntu-latest - needs: changes - outputs: - golangversion: ${{ steps.golangversion.outputs.version }} - if: | - (needs.changes.outputs.go == 'true') || (needs.changes.outputs.charts == 'true') || (needs.changes.outputs.baseimage == 'true') || ${{ github.event.workflow_dispatch.run_e2e == 'true' }} - - env: - PLATFORMS: linux/amd64 - steps: - - name: Checkout - uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2 - - - name: Get go version - id: golangversion - run: | - echo "version=$(cat GOLANG_VERSION)" >> "$GITHUB_OUTPUT" - - - name: Set up Go - id: go - uses: actions/setup-go@f111f3307d8850f501ac008e886eec1fd1932a34 # v5.3.0 - with: - go-version: ${{ steps.golangversion.outputs.version }} - check-latest: true - - - name: Set up QEMU - uses: docker/setup-qemu-action@4574d27a4764455b42196d70a065bc6853246a25 # v3.4.0 - - - name: Set up Docker Buildx - id: buildx - uses: docker/setup-buildx-action@f7ce87c1d6bead3e36075b2ce75da1f6cc28aaca # v3.9.0 - with: - version: latest - - - name: Available platforms - run: echo ${{ steps.buildx.outputs.platforms }} - - - name: Prepare Host - run: | - curl -LO https://dl.k8s.io/release/v1.32.2/bin/linux/amd64/kubectl - chmod +x ./kubectl - sudo mv ./kubectl /usr/local/bin/kubectl - - - name: Build NGINX Base image - if: | - needs.changes.outputs.baseimage == 'true' - run: | - export TAG=$(cat images/nginx/TAG) - cd images/nginx/rootfs && docker buildx build --platform=${{ env.PLATFORMS }} --load -t registry.k8s.io/ingress-nginx/nginx:${TAG} . - - - name: Build images - env: - TAG: 1.0.0-dev - ARCH: amd64 - REGISTRY: ingress-controller - run: | - echo "building images..." - export TAGNGINX=$(cat images/nginx/TAG) - make BASE_IMAGE=registry.k8s.io/ingress-nginx/nginx:${TAGNGINX} clean-image build image image-chroot - make -C test/e2e-image image - - echo "creating images cache..." - docker save \ - nginx-ingress-controller:e2e \ - ingress-controller/controller:1.0.0-dev \ - ingress-controller/controller-chroot:1.0.0-dev \ - | gzip > docker.tar.gz - - - name: cache - uses: actions/upload-artifact@65c4c4a1ddee5b72f698fdd19549f0f0fb45cf08 # v4.6.0 - with: - name: docker.tar.gz - path: docker.tar.gz - retention-days: 5 - - chart-lint: - name: Chart / Lint - runs-on: ubuntu-latest - needs: - - changes - - if: fromJSON(needs.changes.outputs.charts) || fromJSON(needs.changes.outputs.baseimage) || fromJSON(github.event.workflow_dispatch.run_e2e) - - steps: - - name: Set up Python - uses: actions/setup-python@42375524e23c412d93fb67b49958b491fce71c38 # v5.4.0 - with: - python-version: 3.x - - - name: Set up Helm - uses: azure/setup-helm@fe7b79cd5ee1e45176fcad797de68ecaf3ca4814 # v4.2.0 - - - name: Set up Helm Chart Testing - uses: helm/chart-testing-action@0d28d3144d3a25ea2cc349d6e59901c4ff469b3b # v2.7.0 - - - name: Set up Artifact Hub - run: | - curl --fail --location https://github.com/artifacthub/hub/releases/download/v1.20.0/ah_1.20.0_linux_amd64.tar.gz --output /tmp/ah.tar.gz - echo "9027626f19ff9f3ac668f222917130ac885e289e922e1428bfd2e7f066324e31 /tmp/ah.tar.gz" | shasum --check - sudo tar --extract --file /tmp/ah.tar.gz --directory /usr/local/bin ah - - - name: Set up Helm Docs - uses: gabe565/setup-helm-docs-action@d5c35bdc9133cfbea3b671acadf50a29029e87c2 # v1.0.4 - - - name: Set up Helm Unit Test - run: helm plugin install https://github.com/helm-unittest/helm-unittest - - - name: Checkout code - uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2 - with: - fetch-depth: 0 - - - name: Lint chart - run: | - ct lint --config .ct.yaml - ah lint --path charts/ingress-nginx - - - name: Check docs - run: | - helm-docs --chart-search-root charts - git diff --exit-code charts/ingress-nginx/README.md - - - name: Run tests - run: helm unittest charts/ingress-nginx --file "tests/**/*_test.yaml" - - chart-test: - name: Chart / Test - runs-on: ubuntu-latest - needs: - - changes - - build - - chart-lint - - if: fromJSON(needs.changes.outputs.charts) || fromJSON(needs.changes.outputs.baseimage) || fromJSON(github.event.workflow_dispatch.run_e2e) - - strategy: - matrix: - k8s: [v1.28.15, v1.29.12, v1.30.8, v1.31.4, v1.32.0] - - steps: - - name: Checkout code - uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2 - - - name: Download cache - uses: actions/download-artifact@fa0a91b85d4f404e444e00e005971372dc801d16 # v4.1.8 - with: - name: docker.tar.gz - - - name: Load cache - run: gzip --decompress --stdout docker.tar.gz | docker load - - - name: Run tests - env: - K8S_VERSION: ${{ matrix.k8s }} - SKIP_IMAGE_CREATION: true - run: | - sudo mkdir -pm 777 "${HOME}/.kube" - make kind-e2e-chart-tests - - kubernetes: - name: Kubernetes - needs: - - changes - - build - if: | - (needs.changes.outputs.go == 'true') || (needs.changes.outputs.baseimage == 'true') || ${{ github.event.workflow_dispatch.run_e2e == 'true' }} - strategy: - matrix: - k8s: [v1.28.15, v1.29.12, v1.30.8, v1.31.4, v1.32.0] - uses: ./.github/workflows/zz-tmpl-k8s-e2e.yaml - with: - k8s-version: ${{ matrix.k8s }} - - kubernetes-chroot: - name: Kubernetes chroot - needs: - - changes - - build - if: | - (needs.changes.outputs.go == 'true') || (needs.changes.outputs.baseimage == 'true') || ${{ github.event.workflow_dispatch.run_e2e == 'true' }} - strategy: - matrix: - k8s: [v1.28.15, v1.29.12, v1.30.8, v1.31.4, v1.32.0] - uses: ./.github/workflows/zz-tmpl-k8s-e2e.yaml - with: - k8s-version: ${{ matrix.k8s }} - variation: "CHROOT" diff --git a/.github/workflows/depreview.yaml b/.github/workflows/depreview.yaml deleted file mode 100644 index 6d7e44608..000000000 --- a/.github/workflows/depreview.yaml +++ /dev/null @@ -1,14 +0,0 @@ -name: 'Dependency Review' -on: [pull_request] - -permissions: - contents: read - -jobs: - dependency-review: - runs-on: ubuntu-latest - steps: - - name: 'Checkout Repository' - uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2 - - name: 'Dependency Review' - uses: actions/dependency-review-action@3b139cfc5fae8b618d3eae3675e383bb1769c019 # v4.5.0 diff --git a/.github/workflows/docs.yaml b/.github/workflows/docs.yaml deleted file mode 100644 index 40ccba278..000000000 --- a/.github/workflows/docs.yaml +++ /dev/null @@ -1,55 +0,0 @@ -name: Documentation - -on: - push: - branches: - - main - -permissions: - contents: read - -jobs: - - changes: - permissions: - contents: read # for dorny/paths-filter to fetch a list of changed files - pull-requests: read # for dorny/paths-filter to read pull requests - runs-on: ubuntu-latest - if: | - (github.repository == 'kubernetes/ingress-nginx') - outputs: - docs: ${{ steps.filter.outputs.docs }} - charts: ${{ steps.filter.outputs.charts }} - - steps: - - name: Checkout - uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2 - - - uses: dorny/paths-filter@de90cc6fb38fc0963ad72b210f1f284cd68cea36 # v3.0.2 - id: filter - with: - token: ${{ secrets.GITHUB_TOKEN }} - filters: | - docs: - - 'docs/**/*' - - docs: - name: Update - runs-on: ubuntu-latest - needs: - - changes - if: | - (github.repository == 'kubernetes/ingress-nginx') && - (needs.changes.outputs.docs == 'true') - - permissions: - contents: write # needed to write releases - - steps: - - name: Checkout master - uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2 - - - name: Deploy - uses: ./.github/actions/mkdocs - env: - PERSONAL_TOKEN: "${{ secrets.GITHUB_TOKEN }}" diff --git a/.github/workflows/golangci-lint.yml b/.github/workflows/golangci-lint.yml deleted file mode 100644 index f57878084..000000000 --- a/.github/workflows/golangci-lint.yml +++ /dev/null @@ -1,34 +0,0 @@ -name: golangci-lint - -on: - pull_request: - paths: - - '**/*.go' - - '.github/workflows/golangci-lint.yml' - -permissions: - contents: read - -jobs: - golangci: - name: lint - runs-on: ubuntu-latest - steps: - - name: Checkout - uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2 - - - name: Get go version - run: echo "GOLANG_VERSION=$(cat GOLANG_VERSION)" >> $GITHUB_ENV - - - name: Set up Go - id: go - uses: actions/setup-go@f111f3307d8850f501ac008e886eec1fd1932a34 # v5.3.0 - with: - go-version: ${{ env.GOLANG_VERSION }} - check-latest: true - - - name: golangci-lint - uses: golangci/golangci-lint-action@2226d7cb06a077cd73e56eedd38eecad18e5d837 # v6.5.0 - with: - version: v1.62 - only-new-issues: true diff --git a/.github/workflows/images.yaml b/.github/workflows/images.yaml deleted file mode 100644 index 6d32f56f6..000000000 --- a/.github/workflows/images.yaml +++ /dev/null @@ -1,192 +0,0 @@ -name: Container Images - -on: - pull_request: - branches: - - "*" - paths: - - 'images/**' - - push: - branches: - - main - paths: - - 'images/**' - -permissions: - contents: write - packages: write - -env: - PLATFORMS: linux/amd64 - -jobs: - changes: - permissions: - contents: read # for dorny/paths-filter to fetch a list of changed files - pull-requests: read # for dorny/paths-filter to read pull requests - runs-on: ubuntu-latest - outputs: - custom-error-pages: ${{ steps.filter.outputs.custom-error-pages }} - cfssl: ${{ steps.filter.outputs.cfssl }} - fastcgi-helloserver: ${{ steps.filter.outputs.fastcgi-helloserver }} - e2e-test-echo: ${{ steps.filter.outputs.e2e-test-echo }} - go-grpc-greeter-server: ${{ steps.filter.outputs.go-grpc-greeter-server }} - httpbun: ${{ steps.filter.outputs.httpbun }} - kube-webhook-certgen: ${{ steps.filter.outputs.kube-webhook-certgen }} - ext-auth-example-authsvc: ${{ steps.filter.outputs.ext-auth-example-authsvc }} - nginx: ${{ steps.filter.outputs.nginx }} - - steps: - - name: Checkout - uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2 - - uses: dorny/paths-filter@de90cc6fb38fc0963ad72b210f1f284cd68cea36 # v3.0.2 - id: filter - with: - token: ${{ secrets.GITHUB_TOKEN }} - filters: | - custom-error-pages: - - 'images/custom-error-pages/**' - cfssl: - - 'images/cfssl/**' - fastcgi-helloserver: - - 'images/fastcgi-helloserver/**' - e2e-test-echo: - - 'images/e2e-test-echo/**' - go-grpc-greeter-server: - - 'images/go-grpc-greeter-server/**' - httpbun: - - 'images/httpbun/**' - kube-webhook-certgen: - - 'images/kube-webhook-certgen/**' - ext-auth-example-authsvc: - - 'images/ext-auth-example-authsvc/**' - nginx: - - 'images/nginx/**' - - #### TODO: Make the below jobs 'less dumb' and use the job name as parameter (the github.job context does not work here) - cfssl: - needs: changes - if: | - (needs.changes.outputs.cfssl == 'true') - uses: ./.github/workflows/zz-tmpl-images.yaml - with: - name: cfssl - secrets: inherit - - custom-error-pages: - needs: changes - if: | - (needs.changes.outputs.custom-error-pages == 'true') - uses: ./.github/workflows/zz-tmpl-images.yaml - with: - name: custom-error-pages - secrets: inherit - - e2e-test-echo: - needs: changes - if: | - (needs.changes.outputs.e2e-test-echo == 'true') - uses: ./.github/workflows/zz-tmpl-images.yaml - with: - name: e2e-test-echo - secrets: inherit - - ext-auth-example-authsvc: - needs: changes - if: | - (needs.changes.outputs.ext-auth-example-authsvc == 'true') - uses: ./.github/workflows/zz-tmpl-images.yaml - with: - name: ext-auth-example-authsvc - secrets: inherit - - fastcgi-helloserver: - needs: changes - if: | - (needs.changes.outputs.fastcgi-helloserver == 'true') - uses: ./.github/workflows/zz-tmpl-images.yaml - with: - name: fastcgi-helloserver - secrets: inherit - - go-grpc-greeter-server: - needs: changes - if: | - (needs.changes.outputs.go-grpc-greeter-server == 'true') - uses: ./.github/workflows/zz-tmpl-images.yaml - with: - name: go-grpc-greeter-server - secrets: inherit - - httpbun: - needs: changes - if: | - (needs.changes.outputs.httpbun == 'true') - uses: ./.github/workflows/zz-tmpl-images.yaml - with: - name: httpbun - secrets: inherit - - kube-webhook-certgen: - runs-on: ubuntu-latest - needs: changes - if: | - (needs.changes.outputs.kube-webhook-certgen == 'true') - strategy: - matrix: - k8s: [v1.28.15, v1.29.12, v1.30.8, v1.31.4, v1.32.0] - steps: - - name: Checkout - uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2 - - - name: Get go version - run: echo "GOLANG_VERSION=$(cat GOLANG_VERSION)" >> $GITHUB_ENV - - - name: Set up Go - id: go - uses: actions/setup-go@f111f3307d8850f501ac008e886eec1fd1932a34 # v5.3.0 - with: - go-version: ${{ env.GOLANG_VERSION }} - check-latest: true - - name: image build - run: | - cd images/ && make NAME=kube-webhook-certgen build - - name: Create Kubernetes cluster - id: kind - run: | - kind create cluster --image=kindest/node:${{ matrix.k8s }} - - name: image test - run: | - cd images/ && make NAME=kube-webhook-certgen test test-e2e - - nginx: - permissions: - contents: write - packages: write - runs-on: ubuntu-latest - needs: changes - if: | - (github.event_name == 'push' && github.ref == 'refs/heads/main' && needs.changes.outputs.nginx == 'true') - env: - PLATFORMS: linux/amd64,linux/arm,linux/arm64 - steps: - - name: Checkout - uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2 - - name: Set up QEMU - uses: docker/setup-qemu-action@4574d27a4764455b42196d70a065bc6853246a25 # v3.4.0 - - name: Set up Docker Buildx - id: buildx - uses: docker/setup-buildx-action@f7ce87c1d6bead3e36075b2ce75da1f6cc28aaca # v3.9.0 - with: - version: latest - platforms: ${{ env.PLATFORMS }} - - name: Login to GitHub Container Registry - uses: docker/login-action@9780b0c442fbb1117ed29e0efdff1e18412f7567 # v3.3.0 - with: - username: ${{ secrets.DOCKERHUB_USERNAME }} - password: ${{ secrets.DOCKERHUB_TOKEN }} - - name: build-image - run: | - export TAG=$(cat images/nginx/TAG) - cd images/nginx/rootfs && docker buildx build --platform=${{ env.PLATFORMS }} --push -t ingressnginx/nginx:${TAG} . diff --git a/.github/workflows/junit-reports.yaml b/.github/workflows/junit-reports.yaml deleted file mode 100644 index e2a82910e..000000000 --- a/.github/workflows/junit-reports.yaml +++ /dev/null @@ -1,22 +0,0 @@ -name: 'E2E Test Report' - -on: - workflow_run: - workflows: ['CI'] # runs after CI workflow - types: - - completed - -permissions: - checks: write - -jobs: - report: - runs-on: ubuntu-latest - steps: - - uses: dorny/test-reporter@31a54ee7ebcacc03a09ea97a7e5465a47b84aea5 # v1.9.1 - with: - artifact: /e2e-test-reports-(.*)/ - name: JEST Tests $1 # Name of the check run which will be created - path: 'report*.xml' # Path to test results (inside artifact .zip) - reporter: jest-junit # Format of test results - fail-on-empty: 'true' diff --git a/.github/workflows/perftest.yaml b/.github/workflows/perftest.yaml deleted file mode 100644 index de22d53d9..000000000 --- a/.github/workflows/perftest.yaml +++ /dev/null @@ -1,72 +0,0 @@ -name: Performance Test - -on: - workflow_dispatch: - inputs: - logLevel: - description: 'Log level' - required: true - default: 'warning' - tags: - description: 'K6 Load Test' - -permissions: - contents: read - -jobs: - k6_test_run: - runs-on: ubuntu-latest - - steps: - - name: Checkout - uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2 - - - name: Install K6 - run: | - wget https://github.com/grafana/k6/releases/download/v0.38.2/k6-v0.38.2-linux-amd64.tar.gz - echo '7c9e5a26aaa2c638c042f6dfda7416161b8d2e0d4cb930721a38083b8be109ab *k6-v0.38.2-linux-amd64.tar.gz' | shasum -c - tar -xvf k6-v0.38.2-linux-amd64.tar.gz k6-v0.38.2-linux-amd64/k6 - mv k6-v0.38.2-linux-amd64/k6 . - ./k6 - - - name: Make dev-env - run: | - mkdir $HOME/.kube - make dev-env - podName=`kubectl -n ingress-nginx get po | grep -i controller | awk '{print $1}'` - if [[ -z ${podName} ]] ; then - sleep 5 - fi - kubectl wait pod -n ingress-nginx --for condition=Ready $podName - kubectl get all -A - - - name: Deploy workload - run: | - kubectl create deploy k6 --image kennethreitz/httpbin --port 80 && \ - kubectl expose deploy k6 --port 80 && \ - kubectl create ing k6 --class nginx \ - --rule test.ingress-nginx-controller.ga/*=k6:80 - podName=`kubectl get po | grep -i k6 | awk '{print $1}'` - if [[ -z ${podName} ]] ; then - sleep 5 - fi - kubectl wait pod --for condition=Ready $podName - kubectl get all,secrets,ing - - - name: Tune OS - run : | - sudo sysctl -A 2>/dev/null | egrep -i "local_port_range|tw_reuse|tcp_timestamps" - sudo sh -c "ulimit" - sudo sysctl -w net.ipv4.ip_local_port_range="1024 65535" - sudo sysctl -w net.ipv4.tcp_tw_reuse=1 - sudo sysctl -w net.ipv4.tcp_timestamps=1 - sudo sh -c "ulimit " - - - name: Run smoke test - run: | - vmstat -at 5 | tee vmstat_report & - #./k6 login cloud -t $K6_TOKEN - #./k6 run -o cloud ./smoketest.js - ./k6 run test/k6/smoketest.js - pkill vmstat - cat vmstat_report diff --git a/.github/workflows/plugin.yaml b/.github/workflows/plugin.yaml deleted file mode 100644 index 20f2caeae..000000000 --- a/.github/workflows/plugin.yaml +++ /dev/null @@ -1,50 +0,0 @@ -name: kubectl plugin - -on: - release: - types: [published] - -permissions: - contents: write # for goreleaser/goreleaser-action - -jobs: - release-plugin: - runs-on: ubuntu-latest - steps: - - name: Checkout - uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2 - with: - fetch-depth: 0 - - - name: Get go version - run: echo "GOLANG_VERSION=$(cat GOLANG_VERSION)" >> $GITHUB_ENV - - - name: Set up Go - uses: actions/setup-go@f111f3307d8850f501ac008e886eec1fd1932a34 # v5.3.0 - with: - go-version: ${{ env.GOLANG_VERSION }} - check-latest: true - - - name: Run GoReleaser Snapshot - if: ${{ ! startsWith(github.ref, 'refs/tags/') }} - uses: goreleaser/goreleaser-action@90a3faa9d0182683851fbfa97ca1a2cb983bfca3 # v6.2.1 - with: - version: "~> v2" - args: release --snapshot --clean - env: - GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} - - - name: Run GoReleaser - if: ${{ startsWith(github.ref, 'refs/tags/') }} - uses: goreleaser/goreleaser-action@90a3faa9d0182683851fbfa97ca1a2cb983bfca3 # v6.2.1 - with: - version: "~> v2" - args: release --clean - env: - GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} - - - name: Update new version in krew-index - if: ${{ startsWith(github.ref, 'refs/tags/') }} - uses: rajatjindal/krew-release-bot@3d9faef30a82761d610544f62afddca00993eef9 # v0.0.47 - with: - krew_template_file: cmd/plugin/krew.yaml diff --git a/.github/workflows/project.yml b/.github/workflows/project.yml deleted file mode 100644 index 9babf234e..000000000 --- a/.github/workflows/project.yml +++ /dev/null @@ -1,19 +0,0 @@ -name: Adds all issues - -on: - issues: - types: - - opened - -jobs: - add-to-project: - name: Add issue to project - runs-on: ubuntu-latest - permissions: - repository-projects: write - issues: write - steps: - - uses: actions/add-to-project@244f685bbc3b7adfa8466e08b698b5577571133e # v1.0.2 - with: - project-url: https://github.com/orgs/kubernetes/projects/104 - github-token: ${{ secrets.PROJECT_WRITER }} diff --git a/.github/workflows/scorecards.yml b/.github/workflows/scorecards.yml deleted file mode 100644 index a4473710d..000000000 --- a/.github/workflows/scorecards.yml +++ /dev/null @@ -1,64 +0,0 @@ -name: Scorecards supply-chain security - -on: - # Only the default branch is supported. - branch_protection_rule: - schedule: - - cron: '20 11 * * 5' - push: - branches: - - "main" - -# Declare default permissions as read only. -permissions: read-all - -jobs: - analysis: - name: Scorecards analysis - runs-on: ubuntu-latest - permissions: - # Needed to upload the results to code-scanning dashboard. - security-events: write - # Used to receive a badge. (Upcoming feature) - id-token: write - # Needs for private repositories. - contents: read - actions: read - - steps: - - name: "Checkout code" - uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2 - with: - persist-credentials: false - - - name: "Run analysis" - uses: ossf/scorecard-action@62b2cac7ed8198b15735ed49ab1e5cf35480ba46 # v2.4.0 - with: - results_file: results.sarif - results_format: sarif - # (Optional) Read-only PAT token. Uncomment the `repo_token` line below if: - # - you want to enable the Branch-Protection check on a *public* repository, or - # - you are installing Scorecards on a *private* repository - # To create the PAT, follow the steps in https://github.com/ossf/scorecard-action#authentication-with-pat. - # repo_token: ${{ secrets.SCORECARD_READ_TOKEN }} - - # Publish the results for public repositories to enable scorecard badges. For more details, see - # https://github.com/ossf/scorecard-action#publishing-results. - # For private repositories, `publish_results` will automatically be set to `false`, regardless - # of the value entered here. - publish_results: true - - # Upload the results as artifacts (optional). Commenting out will disable uploads of run results in SARIF - # format to the repository Actions tab. - - name: "Upload artifact" - uses: actions/upload-artifact@65c4c4a1ddee5b72f698fdd19549f0f0fb45cf08 # v4.6.0 - with: - name: SARIF file - path: results.sarif - retention-days: 5 - - # Upload the results to GitHub's code scanning dashboard. - - name: "Upload to code-scanning" - uses: github/codeql-action/upload-sarif@9e8d0789d4a0fa9ceb6b1738f7e269594bdd67f0 # v3.28.9 - with: - sarif_file: results.sarif diff --git a/.github/workflows/stale.yaml b/.github/workflows/stale.yaml deleted file mode 100644 index 45a7cd320..000000000 --- a/.github/workflows/stale.yaml +++ /dev/null @@ -1,24 +0,0 @@ -name: 'Stale Issues and PRs' - -on: - schedule: - - cron: '30 1 * * *' - -jobs: - stale: - runs-on: ubuntu-latest - - permissions: - issues: write - pull-requests: write - - steps: - - uses: actions/stale@5bef64f19d7facfb25b37b414482c7164d639639 # v9.1.0 - with: - stale-issue-message: "This is stale, but we won't close it automatically, just bare in mind the maintainers may be busy with other tasks and will reach your issue ASAP. If you have any question or request to prioritize this, please reach `#ingress-nginx-dev` on Kubernetes Slack." - stale-pr-message: "This is stale, but we won't close it automatically, just bare in mind the maintainers may be busy with other tasks and will reach your issue ASAP. If you have any question or request to prioritize this, please reach `#ingress-nginx-dev` on Kubernetes Slack." - stale-issue-label: lifecycle/frozen - stale-pr-label: lifecycle/frozen - days-before-issue-stale: 30 - days-before-pr-stale: 45 - days-before-close: -1 # dont not close issues/prs diff --git a/.github/workflows/vulnerability-scans.yaml b/.github/workflows/vulnerability-scans.yaml deleted file mode 100644 index 4461d9757..000000000 --- a/.github/workflows/vulnerability-scans.yaml +++ /dev/null @@ -1,92 +0,0 @@ -# This workflow uses actions that are not certified by GitHub. -# They are provided by a third-party and are governed by -# separate terms of service, privacy policy, and support -# documentation. - -name: Vulnerability Scan - -on: - workflow_dispatch: - release: - schedule: - - cron: '00 9 * * 1' - -permissions: - contents: read - security-events: write - -jobs: - version: - runs-on: ubuntu-latest - outputs: - versions: ${{ steps.version.outputs.TAGS }} - steps: - - name: Checkout code - uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2 - with: - fetch-depth: 0 - - - name: Latest Tag - id: version - shell: bash - run: | - readarray -t TAGS_ARRAY <<<"$(git tag --list 'controller-v*.*.*' --sort=-version:refname | grep -v 'beta\|alpha')" - FULL_TAGS=(${TAGS_ARRAY[0]} ${TAGS_ARRAY[1]} ${TAGS_ARRAY[2]}) - SHORT_TAGS=() - for i in ${FULL_TAGS[@]} - do - echo "tag: $i" - short=$(echo "$i" | cut -d - -f 2) - SHORT_TAGS+=($short) - done - echo "${SHORT_TAGS[0]},${SHORT_TAGS[1]},${SHORT_TAGS[2]}" - TAGS_JSON="[\"${SHORT_TAGS[0]}\",\"${SHORT_TAGS[1]}\",\"${SHORT_TAGS[2]}\"]" - echo "${TAGS_JSON}" - echo "TAGS=${TAGS_JSON}" >> $GITHUB_OUTPUT - - scan: - runs-on: ubuntu-latest - needs: version - strategy: - matrix: - versions: ${{ fromJSON(needs.version.outputs.versions) }} - steps: - - name: Checkout code - uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2 - - - shell: bash - id: test - run: echo "Scanning registry.k8s.io/ingress-nginx/controller@${{ matrix.versions }}" - - - name: Scan image with AquaSec/Trivy - id: scan - uses: aquasecurity/trivy-action@18f2510ee396bbf400402947b394f2dd8c87dbb0 # v0.29.0 - with: - image-ref: registry.k8s.io/ingress-nginx/controller:${{ matrix.versions }} - format: 'sarif' - output: trivy-results-${{ matrix.versions }}.sarif - exit-code: 0 - vuln-type: 'os,library' - severity: 'CRITICAL,HIGH,MEDIUM,LOW,UNKNOWN' - - - name: Output Sarif File - shell: bash - run: cat ${{ github.workspace }}/trivy-results-${{ matrix.versions }}.sarif - - # This step checks out a copy of your repository. - - name: Upload SARIF file - uses: github/codeql-action/upload-sarif@9e8d0789d4a0fa9ceb6b1738f7e269594bdd67f0 # v3.28.9 - with: - token: ${{ github.token }} - # Path to SARIF file relative to the root of the repository - sarif_file: ${{ github.workspace }}/trivy-results-${{ matrix.versions }}.sarif - - - name: Vulz Count - shell: bash - run: | - TRIVY_COUNT=$(cat ${{ github.workspace }}/trivy-results-${{ matrix.versions }}.sarif | jq '.runs[0].results | length') - echo "TRIVY_COUNT: $TRIVY_COUNT" - echo "Image Vulnerability scan output" >> $GITHUB_STEP_SUMMARY - echo "Image ID: registry.k8s.io/ingress-nginx/controller@${{ matrix.versions }}" >> $GITHUB_STEP_SUMMARY - echo "" >> $GITHUB_STEP_SUMMARY - echo "Trivy Count: $TRIVY_COUNT" >> $GITHUB_STEP_SUMMARY diff --git a/.github/workflows/zz-tmpl-images.yaml b/.github/workflows/zz-tmpl-images.yaml deleted file mode 100644 index 5e98ddf70..000000000 --- a/.github/workflows/zz-tmpl-images.yaml +++ /dev/null @@ -1,81 +0,0 @@ -#### THIS IS A TEMPLATE #### -# This workflow is created to be a template for every time an e2e test is required, - -on: - workflow_call: - inputs: - name: - required: true - type: string - platforms-test: - type: string - default: linux/amd64 - platforms-publish: - type: string - default: linux/amd64 - -env: - PLATFORMS: ${{ inputs.platforms-test }} - -permissions: - contents: write - packages: write - -jobs: - changestag: - permissions: - contents: read # for dorny/paths-filter to fetch a list of changed files - runs-on: ubuntu-latest - outputs: - tag: ${{ steps.filter.outputs.tag }} - - steps: - - name: Checkout - uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2 - - uses: dorny/paths-filter@de90cc6fb38fc0963ad72b210f1f284cd68cea36 # v3.0.2 - id: filter - with: - token: ${{ secrets.GITHUB_TOKEN }} - filters: | - tag: - - 'images/**/TAG' - - image-build: - name: Build - runs-on: ubuntu-latest - permissions: - contents: read - - steps: - - name: Checkout - uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2 - - - name: Build - run: | - cd images/ && make NAME=${{ inputs.name }} build - - image-push: - name: Push - needs: changestag - if: | - (github.event_name == 'push' && github.ref == 'refs/heads/main' && github.repository == 'kubernetes/ingress-nginx' && needs.changestag.outputs.tag == 'true') - runs-on: ubuntu-latest - permissions: - contents: write - packages: write - env: - PLATFORMS: ${{ inputs.platforms-publish }} - steps: - - name: Checkout - uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2 - - - name: Login to GitHub Container Registry - uses: docker/login-action@9780b0c442fbb1117ed29e0efdff1e18412f7567 # v3.3.0 - with: - username: ${{ secrets.DOCKERHUB_USERNAME }} - password: ${{ secrets.DOCKERHUB_TOKEN }} - - - name: Push - run: | - cd images/ && make REGISTRY=ingressnginx NAME=${{ inputs.name }} push - diff --git a/.github/workflows/zz-tmpl-k8s-e2e.yaml b/.github/workflows/zz-tmpl-k8s-e2e.yaml deleted file mode 100644 index c46e4a957..000000000 --- a/.github/workflows/zz-tmpl-k8s-e2e.yaml +++ /dev/null @@ -1,57 +0,0 @@ -#### THIS IS A TEMPLATE #### -# This workflow is created to be a template for every time an e2e test is required, - -on: - workflow_call: - inputs: - k8s-version: - required: true - type: string - variation: - type: string - -permissions: - contents: read - -jobs: - kubernetes: - name: Kubernetes ${{ inputs.variation }} - runs-on: ubuntu-latest - - steps: - - name: Checkout - uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2 - - - name: cache - uses: actions/download-artifact@fa0a91b85d4f404e444e00e005971372dc801d16 # v4.1.8 - with: - name: docker.tar.gz - - - name: Create Kubernetes ${{ inputs.k8s-version }} cluster - id: kind - run: | - kind create cluster --image=kindest/node:${{ inputs.k8s-version }} --config test/e2e/kind.yaml - - - name: Load images from cache - run: | - echo "loading docker images..." - gzip -dc docker.tar.gz | docker load - - - name: Run e2e tests ${{ inputs.variation }} - env: - KIND_CLUSTER_NAME: kind - SKIP_CLUSTER_CREATION: true - SKIP_INGRESS_IMAGE_CREATION: true - SKIP_E2E_IMAGE_CREATION: true - IS_CHROOT: ${{ inputs.variation == 'CHROOT' }} - run: | - kind get kubeconfig > $HOME/.kube/kind-config-kind - make kind-e2e-test - - - name: Upload e2e junit-reports ${{ inputs.variation }} - uses: actions/upload-artifact@65c4c4a1ddee5b72f698fdd19549f0f0fb45cf08 # v4.6.0 - if: success() || failure() - with: - name: e2e-test-reports-${{ inputs.k8s-version }}${{ inputs.variation }} - path: 'test/junitreports/report*.xml' - diff --git a/.gitignore b/.gitignore deleted file mode 100644 index 5eac1a800..000000000 --- a/.gitignore +++ /dev/null @@ -1,63 +0,0 @@ -# OSX -._* -.DS_Store - -# intellij files -.idea/* - -# Eclipse files -.classpath -.project -.settings/** - -# visual studio code -.vscode/* - -# Emacs save files -*~ -\#*\# -.\#* - -# Vim-related files -[._]*.s[a-w][a-z] -[._]s[a-w][a-z] -*.un~ -Session.vim -.netrwhist - -# mkdocs -site - -# temporal github pages -gh-pages - -# Docker-based builds -test/binaries - -# coverage artifacts -.coverprofile -gover.coverprofile - -e2e-tests -coverage.txt -test/e2e/e2e\.test -.env -.gocache/ -bin -test/e2e-image/wait-for-nginx.sh -.cache -.modcache -cover.out - -# secret terraform variables -build/images/nginx/aws.tfvars -build/images/nginx/env.tfvars - -images/fastcgi-helloserver/rootfs/fastcgi-helloserver - -cmd/plugin/release/ingress-nginx.yaml -cmd/plugin/release/*.tar.gz -cmd/plugin/release/LICENSE -tmp/ -test/junitreports/ -tests/__snapshot__ diff --git a/.golangci.yml b/.golangci.yml deleted file mode 100644 index 729468711..000000000 --- a/.golangci.yml +++ /dev/null @@ -1,236 +0,0 @@ -run: - timeout: 10m - allow-parallel-runners: true - -issues: - # Maximum issues count per one linter. Set to 0 to disable. Default is 50. - max-issues-per-linter: 0 - - # Maximum count of issues with the same text. Set to 0 to disable. Default is 3. - max-same-issues: 0 -linters: - disable-all: true - enable: - - asasalint - - asciicheck - - bidichk - - bodyclose - - contextcheck - - decorder - - dogsled - - dupl - - durationcheck - - errcheck - - errchkjson - - errname - - ginkgolinter - - gocheckcompilerdirectives - - goconst - - gocritic - - gocyclo - - godox - - gofmt - - gofumpt - - goheader - - goimports - - gomoddirectives - - gomodguard - - goprintffuncname - - gosec - - gosimple - - govet - - grouper - - importas - - ineffassign - - loggercheck - - makezero - - misspell - - musttag - - nakedret - - nolintlint - - nosprintfhostport - - prealloc - - predeclared - - promlinter - - reassign - - revive - - rowserrcheck - - sqlclosecheck - - staticcheck - - stylecheck - - tenv - - testableexamples - - typecheck - - unconvert - - unparam - - unused - - usestdlibvars - - whitespace - # - containedctx - # - cyclop - # - dupword - # - errorlint - # - exhaustive - # - exhaustruct - # - exportloopref - # - forbidigo - # - forcetypeassert - # - funlen - # - gci - # - gochecknoglobals - # - gochecknoinits - # - gocognit - # - godot - # - goerr113 - # - gomnd - # - interfacebloat - # - ireturn - # - lll - # - maintidx - # - nestif - # - nilerr - # - nilnil - # - nlreturn - # - noctx - # - nonamedreturns - # - paralleltest - # - tagliatelle - # - testpackage - # - thelper - # - tparallel - # - varnamelen - # - wastedassign - # - wrapcheck - # - wsl -linters-settings: - gocyclo: - min-complexity: 40 - godox: - keywords: - - BUG - - FIXME - - HACK - errcheck: - check-type-assertions: true - check-blank: true - gocritic: - enabled-checks: - # Diagnostic - - appendAssign - - argOrder - - badCall - - badCond - - badLock - - badRegexp - - badSorting - - builtinShadowDecl - - caseOrder - - codegenComment - - commentedOutCode - - deferInLoop - - deprecatedComment - - dupArg - - dupBranchBody - - dupCase - - dupSubExpr - - dynamicFmtString - - emptyDecl - - evalOrder - - exitAfterDefer - - externalErrorReassign - - filepathJoin - - flagDeref - - flagName - - mapKey - - nilValReturn - - offBy1 - - regexpPattern - - returnAfterHttpError - - sloppyReassign - - sloppyTypeAssert - - sortSlice - - sprintfQuotedString - - sqlQuery - - syncMapLoadAndDelete - - truncateCmp - - unnecessaryDefer - - weakCond - - # Performance - - appendCombine - - equalFold - - hugeParam - - indexAlloc - - preferDecodeRune - - preferFprint - - preferStringWriter - - preferWriteByte - - rangeExprCopy - - rangeValCopy - - sliceClear - - stringXbytes - - # Style - - assignOp - - boolExprSimplify - - captLocal - - commentFormatting - - commentedOutImport - - defaultCaseOrder - - deferUnlambda - - docStub - - dupImport - - elseif - - emptyFallthrough - - emptyStringTest - - exposedSyncMutex - - hexLiteral - - httpNoBody - - ifElseChain - - methodExprCall - - newDeref - - octalLiteral - - preferFilepathJoin - - redundantSprint - - regexpMust - - regexpSimplify - - ruleguard - - singleCaseSwitch - - sloppyLen - - stringConcatSimplify - - stringsCompare - - switchTrue - - timeExprSimplify - - tooManyResultsChecker - - typeAssertChain - - typeDefFirst - - typeSwitchVar - - underef - - unlabelStmt - - unlambda - - unslice - - valSwap - - whyNoLint - - wrapperFunc - - yodaStyleExpr - - # Opinionated - - builtinShadow - - importShadow - - initClause - - nestingReduce - - paramTypeCombine - - ptrToRefParam - - typeUnparen - - unnamedResult - - unnecessaryBlock - nolintlint: - # Enable to ensure that nolint directives are all used. Default is true. - allow-unused: false - # Exclude following linters from requiring an explanation. Default is []. - allow-no-explanation: [] - # Enable to require an explanation of nonzero length after each nolint directive. Default is false. - # TODO(lint): Enforce explanations for `nolint` directives - require-explanation: false - # Enable to require nolint directives to mention the specific linter being suppressed. Default is false. - require-specific: true diff --git a/.goreleaser.yaml b/.goreleaser.yaml deleted file mode 100644 index a0ef6eb3d..000000000 --- a/.goreleaser.yaml +++ /dev/null @@ -1,29 +0,0 @@ -project_name: ingress-nginx -release: - github: - owner: kubernetes - name: ingress-nginx -builds: - - id: ingress-nginx - goos: - - darwin - - linux - - windows - goarch: - - arm64 - - amd64 - env: - - CGO_ENABLED=0 - - GO111MODULE=on - main: cmd/plugin/main.go - binary: kubectl-ingress-nginx - ldflags: | - -s -w - -X k8s.io/ingress-nginx/version.COMMIT={{ .Commit }} - -X k8s.io/ingress-nginx/version.RELEASE={{ .Tag }} -archives: - - id: ingress-nginx - builds: - - ingress-nginx - name_template: "kubectl-{{ .ProjectName }}_{{ .Os }}_{{ .Arch }}" - format: tar.gz diff --git a/.luacheckrc b/.luacheckrc deleted file mode 100644 index 5a1c249fe..000000000 --- a/.luacheckrc +++ /dev/null @@ -1,8 +0,0 @@ -std = 'ngx_lua' -max_line_length = 100 -exclude_files = {'./rootfs/etc/nginx/lua/test/**/*.lua'} -files["rootfs/etc/nginx/lua/lua_ingress.lua"] = { - ignore = { "122" }, - -- TODO(elvinefendi) figure out why this does not work - --read_globals = {"math.randomseed"}, -} diff --git a/404.html b/404.html new file mode 100644 index 000000000..dc2056883 --- /dev/null +++ b/404.html @@ -0,0 +1 @@ + Ingress-Nginx Controller
\ No newline at end of file diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md deleted file mode 100644 index a11435aef..000000000 --- a/CONTRIBUTING.md +++ /dev/null @@ -1,52 +0,0 @@ -# Contributing Guidelines - -Read the following guide if you're interested in contributing to Ingress. [Make Ingress-Nginx Work for you, and the Community](https://youtu.be/GDm-7BlmPPg) from KubeCon Europe 2018 is a great video to get you started!! - -Note that this guide refers to contributing to actual sources of the repository. If you interested in contributing through issue triaging, have a look at [this guide](./ISSUE_TRIAGE.md). - -## Contributor License Agreements - -We'd love to accept your patches! Before we can take them, we have to jump a couple of legal hurdles. - -Please fill out either the individual or corporate Contributor License Agreement (CLA). - - * If you are an individual writing original source code and you're sure you own the intellectual property, then you'll need to sign an [individual CLA](https://identity.linuxfoundation.org/projects/cncf). - * If you work for a company that wants to allow you to contribute your work, then you'll need to sign a [corporate CLA](https://identity.linuxfoundation.org/node/285/organization-signup). - -Follow either of the two links above to access the appropriate CLA and instructions for how to sign and return it. Once we receive it, we'll be able to accept your pull requests. - -***NOTE***: Only original source code from you and other people that have signed the CLA can be accepted into the main repository. - -## Finding Issues That Need Help - -If you're new to the project and want to help, but don't know where to start, we have a semi-curated list of issues that should not need deep knowledge of the system. [Have a look and see if anything sounds interesting](https://github.com/kubernetes/ingress-nginx/issues?utf8=%E2%9C%93&q=is%3Aopen%20is%3Aissue%20label%3A%22help+wanted%22). - -Alternatively, search for the label [`triage-accepted`](https://github.com/kubernetes/ingress-nginx/issues?q=is%3Aopen+is%3Aissue+label%3Atriage%2Faccepted+) if you have some experience with ingress-nginx. Note, that it could make sense to grab issues with higher priority first. - -## Contributing a Patch - -1. If you haven't already done so, sign a Contributor License Agreement (see details above). -1. Read the [Ingress development guide](docs/developer-guide/getting-started.md). -1. Fork the desired repo, develop and test your code changes. -1. Submit a pull request. - -All changes must be code reviewed. Coding conventions and standards are explained in the official [developer docs](https://github.com/kubernetes/community/tree/master/contributors/devel). Expect reviewers to request that you avoid common [go style mistakes](https://github.com/golang/go/wiki/CodeReviewComments) in your PRs. - -### Merge Approval - -Ingress Nginx collaborators may add "/lgtm" (Looks Good To Me) to indicate that a PR is acceptable. Any change requires at least one LGTM. No pull requests can be merged until at least one Ingress Nginx collaborator signs off with an LGTM. Adding the "/lgtm" comment result in the prow bot adding the `lgtm` label. Note that a pull request still needs an `approve` label from one of the owners. - -Reviewers or members who want to become reviewers according to the [k8s membership ladder](https://github.com/kubernetes/community/blob/master/community-membership.md), could actively search for [pull requests that need a review](https://github.com/kubernetes/ingress-nginx/pulls?q=is%3Aopen+is%3Apr+label%3Atriage%2Faccepted). - -## Support Channels - -Whether you are a user or contributor, official support channels include: - -- GitHub issues: https://github.com/kubernetes/ingress-nginx/issues/new -- Slack: kubernetes-users room in the [Kubernetes Slack](http://slack.kubernetes.io/) -- Post: [Kubernetes Forum](https://discuss.kubernetes.io) - -Before opening a new issue or submitting a new pull request, it's helpful to search the project - it's likely that another user has already reported the issue you're facing, or it's a known issue that we're already aware of. - -## New Contributor Tips -If you're a new contributor, you can follow the [New Contributor Tips guide](NEW_CONTRIBUTOR.md) diff --git a/Changelog.md b/Changelog.md deleted file mode 100644 index f049654ee..000000000 --- a/Changelog.md +++ /dev/null @@ -1,4800 +0,0 @@ -# Changelog - -All New change are in [Changelog](./changelog) - -### 1.5.1 - -* Upgrade NGINX to 1.21.6 -* Upgrade Golang 1.19.2 -* Fix Service Name length Bug [9245](https://github.com/kubernetes/ingress-nginx/pull/9245) -* CVE fixes CVE-2022-32149, CVE-2022-27664, CVE-2022-1996 - -Images: - -* registry.k8s.io/ingress-nginx/controller:v1.5.1@sha256:4ba73c697770664c1e00e9f968de14e08f606ff961c76e5d7033a4a9c593c629 -* registry.k8s.io/ingress-nginx/controller-chroot:v1.5.1@sha256:c1c091b88a6c936a83bd7b098662760a87868d12452529bad0d178fb36147345 - -### All Changes: - -* chore Fixed to Support Versions table by @yutachaos in https://github.com/kubernetes/ingress-nginx/pull/9117 -* Updated incorrect version number in the Installation Guide by @afro-coder in https://github.com/kubernetes/ingress-nginx/pull/9120 -* Updated the Developer guide with New Contributor information by @afro-coder in https://github.com/kubernetes/ingress-nginx/pull/9114 -* Remove deprecated net dependency by @rikatz in https://github.com/kubernetes/ingress-nginx/pull/9110 -* Fixed docs helm-docs version by @yutachaos in https://github.com/kubernetes/ingress-nginx/pull/9121 -* Fix CVE 2022 27664 by @strongjz in https://github.com/kubernetes/ingress-nginx/pull/9109 -* upgrade to golang 1.19.2 by @strongjz in https://github.com/kubernetes/ingress-nginx/pull/9124 -* fix e2e resource leak when ginkgo exit before clear resource by @loveRhythm1990 in https://github.com/kubernetes/ingress-nginx/pull/9103 -* fix: handle 401 and 403 by external auth by @johanneswuerbach in https://github.com/kubernetes/ingress-nginx/pull/9131 -* Move bowei to emeritus owner by @rikatz in https://github.com/kubernetes/ingress-nginx/pull/9150 -* fix null ports by @tombokombo in https://github.com/kubernetes/ingress-nginx/pull/9149 -* Documentation added for implemented redirection in the proxy to ensure image pulling by @Sanghamitra-PERSONAL in https://github.com/kubernetes/ingress-nginx/pull/9098 -* updating runner with golang 1.19.2 by @strongjz in https://github.com/kubernetes/ingress-nginx/pull/9158 -* Add install command for OVHcloud by @scraly in https://github.com/kubernetes/ingress-nginx/pull/9171 -* GitHub Templates: Remove trailing whitespaces. by @Gacko in https://github.com/kubernetes/ingress-nginx/pull/9172 -* Update helm chart changelog to show that kubernetes v1.21.x is no longer supported by @cskinfill in https://github.com/kubernetes/ingress-nginx/pull/9147 -* Add section to troubleshooting docs for failure to listen on port by @jrhunger in https://github.com/kubernetes/ingress-nginx/pull/9185 -* Implement parseFloat for annotations by @kirs in https://github.com/kubernetes/ingress-nginx/pull/9195 -* fix typo in docs. by @guettli in https://github.com/kubernetes/ingress-nginx/pull/9167 -* add:(admission-webhooks) ability to set securityContext by @ybelMekk in https://github.com/kubernetes/ingress-nginx/pull/9186 -* Fix Markdown header level by @jaens in https://github.com/kubernetes/ingress-nginx/pull/9210 -* chore: bump NGINX version v1.21.4 by @tao12345666333 in https://github.com/kubernetes/ingress-nginx/pull/8889 -* chore: update NGINX to 1.21.6 by @tao12345666333 in https://github.com/kubernetes/ingress-nginx/pull/9231 -* fix svc long name by @tombokombo in https://github.com/kubernetes/ingress-nginx/pull/9245 -* update base image of nginx to 1.21.6 by @strongjz in https://github.com/kubernetes/ingress-nginx/pull/9257 -* Fix CVE-2022-32149 by @esigo in https://github.com/kubernetes/ingress-nginx/pull/9258 -* Fix CVE-2022-1996 by @esigo in https://github.com/kubernetes/ingress-nginx/pull/9244 -* Adding support for disabling liveness and readiness probes to the Helm chart by @njegosrailic in https://github.com/kubernetes/ingress-nginx/pull/9238 -* fix CVE-2022-27664 by @esigo in https://github.com/kubernetes/ingress-nginx/pull/9273 -* Add CVE-2022-27664 #9273 in latest release by @strongjz in https://github.com/kubernetes/ingress-nginx/pull/9275 - -### Dependencies updates: - -* Bump docker/setup-buildx-action from 2.0.0 to 2.1.0 by @dependabot in https://github.com/kubernetes/ingress-nginx/pull/9180 -* Bump dorny/paths-filter from 2.10.2 to 2.11.1 by @dependabot in https://github.com/kubernetes/ingress-nginx/pull/9183 -* Bump helm/chart-releaser-action from 1.4.0 to 1.4.1 by @dependabot in https://github.com/kubernetes/ingress-nginx/pull/9136 -* Bump github/codeql-action from 2.1.25 to 2.1.27 by @dependabot in https://github.com/kubernetes/ingress-nginx/pull/9137 -* Bump ossf/scorecard-action from 2.0.3 to 2.0.4 by @dependabot in https://github.com/kubernetes/ingress-nginx/pull/9138 -* Bump google.golang.org/grpc from 1.49.0 to 1.50.0 by @dependabot in https://github.com/kubernetes/ingress-nginx/pull/9134 -* Bump actions/checkout from 3.0.2 to 3.1.0 by @dependabot in https://github.com/kubernetes/ingress-nginx/pull/9135 -* Bump actions/dependency-review-action from 2.5.0 to 2.5.1 by @dependabot in https://github.com/kubernetes/ingress-nginx/pull/9237 -* Bump github/codeql-action from 2.1.28 to 2.1.29 by @dependabot in https://github.com/kubernetes/ingress-nginx/pull/9236 -* Bump github.com/spf13/cobra from 1.6.0 to 1.6.1 by @dependabot in https://github.com/kubernetes/ingress-nginx/pull/9233 -* Bump actions/upload-artifact from 3.1.0 to 3.1.1 by @dependabot in https://github.com/kubernetes/ingress-nginx/pull/9234 -* Bump azure/setup-helm from 3.3 to 3.4 by @dependabot in https://github.com/kubernetes/ingress-nginx/pull/9235 -* Bump github.com/onsi/ginkgo/v2 from 2.3.1 to 2.4.0 by @dependabot in https://github.com/kubernetes/ingress-nginx/pull/9201 -* Bump goreleaser/goreleaser-action from 3.1.0 to 3.2.0 by @dependabot in https://github.com/kubernetes/ingress-nginx/pull/9208 -* Bump github.com/stretchr/testify from 1.8.0 to 1.8.1 by @dependabot in https://github.com/kubernetes/ingress-nginx/pull/9202 -* Bump ossf/scorecard-action from 2.0.4 to 2.0.6 by @dependabot in https://github.com/kubernetes/ingress-nginx/pull/9203 -* Bump docker/setup-buildx-action from 2.1.0 to 2.2.1 by @dependabot in https://github.com/kubernetes/ingress-nginx/pull/9204 -* Bump actions/setup-go from 3.3.0 to 3.3.1 by @dependabot in https://github.com/kubernetes/ingress-nginx/pull/9205 -* Bump github/codeql-action from 2.1.27 to 2.1.28 by @dependabot in https://github.com/kubernetes/ingress-nginx/pull/9206 -* Bump actions/download-artifact from 3.0.0 to 3.0.1 by @dependabot in https://github.com/kubernetes/ingress-nginx/pull/9207 -* Bump github.com/prometheus/client_model from 0.2.0 to 0.3.0 by @dependabot in https://github.com/kubernetes/ingress-nginx/pull/9200 -* Bump github.com/spf13/cobra from 1.5.0 to 1.6.0 by @dependabot in https://github.com/kubernetes/ingress-nginx/pull/9173 -* Bump google.golang.org/grpc from 1.50.0 to 1.50.1 by @dependabot in https://github.com/kubernetes/ingress-nginx/pull/9174 -* Bump k8s.io/component-base from 0.25.2 to 0.25.3 by @dependabot in https://github.com/kubernetes/ingress-nginx/pull/9175 -* Bump github.com/fsnotify/fsnotify from 1.5.4 to 1.6.0 by @dependabot in https://github.com/kubernetes/ingress-nginx/pull/9176 -* Bump github.com/onsi/ginkgo/v2 from 2.2.0 to 2.3.1 by @dependabot in https://github.com/kubernetes/ingress-nginx/pull/9177 -* Bump geekyeggo/delete-artifact from 1.0.0 to 2.0.0 by @dependabot in https://github.com/kubernetes/ingress-nginx/pull/9178 -* Bump actions/dependency-review-action from 2.4.0 to 2.5.0 by @dependabot in https://github.com/kubernetes/ingress-nginx/pull/9179 -* Bump docker/setup-qemu-action from 2.0.0 to 2.1.0 by @dependabot in https://github.com/kubernetes/ingress-nginx/pull/9181 -* Bump securego/gosec from 2.13.1 to 2.14.0 by @dependabot in https://github.com/kubernetes/ingress-nginx/pull/9182 - - -## New Contributors -* @yutachaos made their first contribution in https://github.com/kubernetes/ingress-nginx/pull/9117 -* @Gacko made their first contribution in https://github.com/kubernetes/ingress-nginx/pull/9123 -* @loveRhythm1990 made their first contribution in https://github.com/kubernetes/ingress-nginx/pull/9103 -* @johanneswuerbach made their first contribution in https://github.com/kubernetes/ingress-nginx/pull/9131 -* @FutureMatt made their first contribution in https://github.com/kubernetes/ingress-nginx/pull/9133 -* @Sanghamitra-PERSONAL made their first contribution in https://github.com/kubernetes/ingress-nginx/pull/9098 -* @scraly made their first contribution in https://github.com/kubernetes/ingress-nginx/pull/9171 -* @cskinfill made their first contribution in https://github.com/kubernetes/ingress-nginx/pull/9147 -* @jrhunger made their first contribution in https://github.com/kubernetes/ingress-nginx/pull/9185 -* @guettli made their first contribution in https://github.com/kubernetes/ingress-nginx/pull/9167 -* @ybelMekk made their first contribution in https://github.com/kubernetes/ingress-nginx/pull/9186 -* @jaens made their first contribution in https://github.com/kubernetes/ingress-nginx/pull/9210 - -**Full Changelog**: https://github.com/kubernetes/ingress-nginx/compare/controller-v1.4.0...controller-v1.5.1 - -### 1.4.0 - -### Community Updates - -We will discuss the results of our Community Survey, progress on the stabilization project, and ideas going -forward with the project at -[Kubecon NA 2022 in Detroit](https://events.linuxfoundation.org/kubecon-cloudnativecon-north-america/). Come join us -and let us hear what you'd like to see in the future for ingress-nginx. - -https://kccncna2022.sched.com/event/18lgl?iframe=no - -[**Kubernetes Registry change notice**](https://twitter.com/BenTheElder/status/1575898507235323904) -The [@kubernetesio](https://twitter.com/kubernetesio) container image host http://k8s.gcr.io is -*actually* getting redirected to the community controlled http://registry.k8s.io starting with a small portion of -traffic on October 3rd. - -If you notice any issues, *please* ping [Ben Elder](https://twitter.com/BenTheElder), -[@thockin](https://twitter.com/thockin), [@ameukam](https://twitter.com/ameukam),or report issues in slack to -[sig-k8s-infra slack channel](https://kubernetes.slack.com/archives/CCK68P2Q2). - -### What's Changed - -* 1.4.0 updates ingress-nginx to use Endpointslices instead of Endpoints. Thank you, @tombokombo, for your work in -[8890](https://github.com/kubernetes/ingress-nginx/pull/8890) -* Update to Prometheus metric names, more information [available here]( https://github.com/kubernetes/ingress-nginx/pull/8728 -) -* Deprecated Kubernetes versions 1.20-1.21, Added support for, 1.25, currently supported versions v1.22, v1.23, v1.24, v1.25 - -ADDED -* `_request_duration_seconds` Histogram -* `_connect_duration_seconds` Histogram -* `_header_duration_seconds` Histogram -* `_response_duration_seconds` Histogram - -Updated -* `_response_size` Histogram -* `_request_size` Histogram -* `_requests` Counter - -DEPRECATED -* `_bytes_sent` Histogram -* _ingress_upstream_latency_seconds` Summary - -REMOVED -* `ingress_upstream_header_seconds` Summary - -Also upgraded to golang 1.19.1 - -Images: - -* registry.k8s.io/ingress-nginx/controller:v1.4.0@sha256:34ee929b111ffc7aa426ffd409af44da48e5a0eea1eb2207994d9e0c0882d143 -* registry.k8s.io/ingress-nginx/controller-chroot:v1.4.0@sha256:b67e889f1db8692de7e41d4d9aef8de56645bf048261f31fa7f8bfc6ea2222a0 - - -### All Changes: - -* [9104](https://github.com/kubernetes/ingress-nginx/pull/9104) Fix yaml formatting error with multiple annotations -* [9090](https://github.com/kubernetes/ingress-nginx/pull/9090) fix chroot module mount path -* [9088](https://github.com/kubernetes/ingress-nginx/pull/9088) Add annotation for setting sticky cookie domain -* [9086](https://github.com/kubernetes/ingress-nginx/pull/9086) Update Version ModSecurity and Coreruleset -* [9081](https://github.com/kubernetes/ingress-nginx/pull/9081) plugin - endpoints to slices -* [9078](https://github.com/kubernetes/ingress-nginx/pull/9078) expand CI testing for all stable versions of Kubernetes -* [9074](https://github.com/kubernetes/ingress-nginx/pull/9074) fix: do not apply job-patch psp on Kubernetes 1.25 and newer -* [9072](https://github.com/kubernetes/ingress-nginx/pull/9072) Added a Link to the New Contributors Tips -* [9069](https://github.com/kubernetes/ingress-nginx/pull/9069) Add missing space to error message -* [9059](https://github.com/kubernetes/ingress-nginx/pull/9059) kubewebhookcertgen sha change after go1191 -* [9058](https://github.com/kubernetes/ingress-nginx/pull/9058) updated testrunner image sha after bump to go1191 -* [9046](https://github.com/kubernetes/ingress-nginx/pull/9046) Parameterize metrics port name -* [9036](https://github.com/kubernetes/ingress-nginx/pull/9036) update OpenTelemetry image -* [9035](https://github.com/kubernetes/ingress-nginx/pull/9035) Added instructions for Rancher Desktop -* [9028](https://github.com/kubernetes/ingress-nginx/pull/9028) fix otel init_module -* [9023](https://github.com/kubernetes/ingress-nginx/pull/9023) updates for fixing 1.3.1 release -* [9018](https://github.com/kubernetes/ingress-nginx/pull/9018) Add v1.25 test and reduce amount of e2e tests -* [9017](https://github.com/kubernetes/ingress-nginx/pull/9017) fix LD_LIBRARY_PATH for opentelemetry - -### Dependencies updates: - -* [9085](https://github.com/kubernetes/ingress-nginx/pull/9085) Bump actions/dependency-review-action from 2.1.0 to 2.4.0 -* [9084](https://github.com/kubernetes/ingress-nginx/pull/9084) Bump actions/checkout from 1 to 3 -* [9083](https://github.com/kubernetes/ingress-nginx/pull/9083) Bump github/codeql-action from 2.1.24 to 2.1.25 -* [9089](https://github.com/kubernetes/ingress-nginx/pull/9089) Bump k8s.io/component-base from 0.25.1 to 0.25.2 -* [9066](https://github.com/kubernetes/ingress-nginx/pull/9066) Bump github/codeql-action from 2.1.23 to 2.1.24 -* [9065](https://github.com/kubernetes/ingress-nginx/pull/9065) Bump k8s.io/component-base from 0.25.0 to 0.25.1 -* [9064](https://github.com/kubernetes/ingress-nginx/pull/9064) Bump github.com/onsi/ginkgo/v2 from 2.1.6 to 2.2.0 -* [9057](https://github.com/kubernetes/ingress-nginx/pull/9057) bump go to v1.19.1 -* [9053](https://github.com/kubernetes/ingress-nginx/pull/9053) Bump ossf/scorecard-action from 2.0.2 to 2.0.3 -* [9052](https://github.com/kubernetes/ingress-nginx/pull/9052) Bump github/codeql-action from 2.1.22 to 2.1.23 -* [9045](https://github.com/kubernetes/ingress-nginx/pull/9045) Bump actions/upload-artifact from 3.0.0 to 3.1.0 -* [9044](https://github.com/kubernetes/ingress-nginx/pull/9044) Bump ossf/scorecard-action from 1.1.2 to 2.0.2 -* [9043](https://github.com/kubernetes/ingress-nginx/pull/9043) Bump k8s.io/klog/v2 from 2.80.0 to 2.80.1 -* [9022](https://github.com/kubernetes/ingress-nginx/pull/9022) Bump github.com/onsi/ginkgo/v2 from 2.1.4 to 2.1.6 -* [9021](https://github.com/kubernetes/ingress-nginx/pull/9021) Bump k8s.io/klog/v2 from 2.70.1 to 2.80.0 - -## New Contributors -* @gunamata made their first contribution in https://github.com/kubernetes/ingress-nginx/pull/9035 -* @afro-coder made their first contribution in https://github.com/kubernetes/ingress-nginx/pull/8924 -* @wilmardo made their first contribution in https://github.com/kubernetes/ingress-nginx/pull/9074 -* @nicolasjulian made their first contribution in https://github.com/kubernetes/ingress-nginx/pull/9086 -* @mtneug made their first contribution in https://github.com/kubernetes/ingress-nginx/pull/9088 -* @knbnnate made their first contribution in https://github.com/kubernetes/ingress-nginx/pull/8692 -* @mklauber made their first contribution in https://github.com/kubernetes/ingress-nginx/pull/9104 - -**Full Changelog**: https://github.com/kubernetes/ingress-nginx/compare/controller-v1.3.1...controller-v1.4.0 - -### 1.3.1 - -In v1.3.1 leader elections will be done entirely using the Lease API and no longer using configmaps. -v1.3.0 is a safe transition version, using v1.3.0 can automatically complete the merging of election locks, and then you can safely upgrade to v1.3.1. - -Also, *important note*, with the Release of Kubernetes v1.25 we are dropping support for the legacy branches, -Also, *important note*, with the release of Kubernetes v1.25, we are dropping support for the legacy edition, -that means all version <1.0.0 of the ingress-nginx-controller. - -## Image: -- registry.k8s.io/ingress-nginx/controller:v1.3.1@sha256:54f7fe2c6c5a9db9a0ebf1131797109bb7a4d91f56b9b362bde2abd237dd1974 -- registry.k8s.io/ingress-nginx/controller-chroot:v1.3.1@sha256:a8466b19c621bd550b1645e27a004a5cc85009c858a9ab19490216735ac432b1 - - -## What's Changed - -_IMPORTANT CHANGES:_ -- Update to golang 1.19 -- Started migration for Data and Control Plane splits -- Upgrade to Alpine 3.16.2 -- New kubectl plugin release workflow -- New CVE findings template - -All other Changes -- [9006](https://github.com/kubernetes/ingress-nginx/pull/9006) issue:8739 fix doc issue -- [9003](https://github.com/kubernetes/ingress-nginx/pull/9003) Bump github/codeql-action from 2.1.21 to 2.1.22 -- [9001](https://github.com/kubernetes/ingress-nginx/pull/9001) GitHub Workflows security hardening -- [8992](https://github.com/kubernetes/ingress-nginx/pull/8992) Bump github.com/opencontainers/runc from 1.1.3 to 1.1.4 -- [8991](https://github.com/kubernetes/ingress-nginx/pull/8991) Bump google.golang.org/grpc from 1.48.0 to 1.49.0 -- [8986](https://github.com/kubernetes/ingress-nginx/pull/8986) Bump goreleaser/goreleaser-action from 3.0.0 to 3.1.0 -- [8984](https://github.com/kubernetes/ingress-nginx/pull/8984) fixed deprecated ginkgo flags -- [8982](https://github.com/kubernetes/ingress-nginx/pull/8982) Bump github/codeql-action from 2.1.20 to 2.1.21 -- [8981](https://github.com/kubernetes/ingress-nginx/pull/8981) Bump actions/setup-go from 3.2.1 to 3.3.0 -- [8976](https://github.com/kubernetes/ingress-nginx/pull/8976) Update apiserver to 0.25 to remove v2 go-restful -- [8970](https://github.com/kubernetes/ingress-nginx/pull/8970) bump Golang to 1.19 #8932 -- [8969](https://github.com/kubernetes/ingress-nginx/pull/8969) fix: go-restful CVE #8745 -- [8967](https://github.com/kubernetes/ingress-nginx/pull/8967) updated to testrunnerimage with updated yamale yamllint -- [8966](https://github.com/kubernetes/ingress-nginx/pull/8966) added note on digitalocean annotations -- [8960](https://github.com/kubernetes/ingress-nginx/pull/8960) upgrade yamale and yamllint version -- [8959](https://github.com/kubernetes/ingress-nginx/pull/8959) revert changes to configmap resource permissions -- [8957](https://github.com/kubernetes/ingress-nginx/pull/8957) Bump github/codeql-action from 2.1.19 to 2.1.20 -- [8956](https://github.com/kubernetes/ingress-nginx/pull/8956) Bump azure/setup-helm from 2.1 to 3.3 -- [8954](https://github.com/kubernetes/ingress-nginx/pull/8954) Bump actions/dependency-review-action from 2.0.4 to 2.1.0 -- [8953](https://github.com/kubernetes/ingress-nginx/pull/8953) Bump aquasecurity/trivy-action from 0.5.1 to 0.7.1 -- [8952](https://github.com/kubernetes/ingress-nginx/pull/8952) Bump securego/gosec from b99b5f7838e43a4104354ad92a6a1774302ee1f9 to 2.13.1 -- [8951](https://github.com/kubernetes/ingress-nginx/pull/8951) Bump geekyeggo/delete-artifact from a6ab43859c960a8b74cbc6291f362c7fb51829ba to 1 -- [8950](https://github.com/kubernetes/ingress-nginx/pull/8950) Bump github/codeql-action from 2.1.18 to 2.1.19 -- [8948](https://github.com/kubernetes/ingress-nginx/pull/8948) updated testrunner and testecho images -- [8946](https://github.com/kubernetes/ingress-nginx/pull/8946) Clean old code and move helper functions -- [8944](https://github.com/kubernetes/ingress-nginx/pull/8944) Make keep-alive documentation more explicit for clarity -- [8939](https://github.com/kubernetes/ingress-nginx/pull/8939) bump baseimage alpine to v3.16.2 for zlib CVE fix - -## New Contributors -* @mtnezm made their first contribution in https://github.com/kubernetes/ingress-nginx/pull/8817 -* @tamcore made their first contribution in https://github.com/kubernetes/ingress-nginx/pull/8821 -* @guilhem made their first contribution in https://github.com/kubernetes/ingress-nginx/pull/8827 -* @lilien1010 made their first contribution in https://github.com/kubernetes/ingress-nginx/pull/8830 -* @qilongqiu made their first contribution in https://github.com/kubernetes/ingress-nginx/pull/8855 -* @dgoffredo made their first contribution in https://github.com/kubernetes/ingress-nginx/pull/8848 -* @Volatus made their first contribution in https://github.com/kubernetes/ingress-nginx/pull/8859 -* @europ made their first contribution in https://github.com/kubernetes/ingress-nginx/pull/8841 -* @mrksngl made their first contribution in https://github.com/kubernetes/ingress-nginx/pull/7892 -* @omichels made their first contribution in https://github.com/kubernetes/ingress-nginx/pull/8895 -* @zeeZ made their first contribution in https://github.com/kubernetes/ingress-nginx/pull/8881 -* @mjudeikis made their first contribution in https://github.com/kubernetes/ingress-nginx/pull/8928 -* @NissesSenap made their first contribution in https://github.com/kubernetes/ingress-nginx/pull/8873 -* @anders-swanson made their first contribution in https://github.com/kubernetes/ingress-nginx/pull/8665 -* @aslafy-z made their first contribution in https://github.com/kubernetes/ingress-nginx/pull/8905 -* @harry1064 made their first contribution in https://github.com/kubernetes/ingress-nginx/pull/8825 -* @sashashura made their first contribution in https://github.com/kubernetes/ingress-nginx/pull/9001 -* @sreelakshminarayananm made their first contribution in https://github.com/kubernetes/ingress-nginx/pull/9006 - -**Full Changelog**: https://github.com/kubernetes/ingress-nginx/compare/controller-v1.3.0...controller-v1.3.1 - -### 1.3.0 - -Image: -- registry.k8s.io/ingress-nginx/controller:v1.3.0@sha256:d1707ca76d3b044ab8a28277a2466a02100ee9f58a86af1535a3edf9323ea1b5 -- registry.k8s.io/ingress-nginx/controller-chroot:v1.3.0@sha256:0fcb91216a22aae43b374fc2e6a03b8afe9e8c78cbf07a09d75636dc4ea3c191 - -_IMPORTANT CHANGES:_ -* This release removes support for Kubernetes v1.19.0 -* This release adds support for Kubernetes v1.24.0 -* Starting with this release, we will need permissions on the `coordination.k8s.io/leases` resource for leaderelection lock - -_KNOWN ISSUES:_ -* This release reports a false positive on go-restful library that will be fixed with Kubernetes v1.25 release - Issue #8745 - -_Changes:_ -- "[8810](https://github.com/kubernetes/ingress-nginx/pull/8810) Prepare for v1.3.0" -- "[8808](https://github.com/kubernetes/ingress-nginx/pull/8808) revert arch var name" -- "[8805](https://github.com/kubernetes/ingress-nginx/pull/8805) Bump k8s.io/klog/v2 from 2.60.1 to 2.70.1" -- "[8803](https://github.com/kubernetes/ingress-nginx/pull/8803) Update to nginx base with alpine v3.16" -- "[8802](https://github.com/kubernetes/ingress-nginx/pull/8802) chore: start v1.3.0 release process" -- "[8798](https://github.com/kubernetes/ingress-nginx/pull/8798) Add v1.24.0 to test matrix" -- "[8796](https://github.com/kubernetes/ingress-nginx/pull/8796) fix: add MAC_OS variable for static-check" -- "[8793](https://github.com/kubernetes/ingress-nginx/pull/8793) changed to alpine-v3.16" -- "[8781](https://github.com/kubernetes/ingress-nginx/pull/8781) Bump github.com/stretchr/testify from 1.7.5 to 1.8.0" -- "[8778](https://github.com/kubernetes/ingress-nginx/pull/8778) chore: remove stable.txt from release process" -- "[8775](https://github.com/kubernetes/ingress-nginx/pull/8775) Remove stable" -- "[8773](https://github.com/kubernetes/ingress-nginx/pull/8773) Bump github/codeql-action from 2.1.14 to 2.1.15" -- "[8772](https://github.com/kubernetes/ingress-nginx/pull/8772) Bump ossf/scorecard-action from 1.1.1 to 1.1.2" -- "[8771](https://github.com/kubernetes/ingress-nginx/pull/8771) fix bullet md format" -- "[8770](https://github.com/kubernetes/ingress-nginx/pull/8770) Add condition for monitoring.coreos.com/v1 API" -- "[8769](https://github.com/kubernetes/ingress-nginx/pull/8769) Fix typos and add links to developer guide" -- "[8767](https://github.com/kubernetes/ingress-nginx/pull/8767) change v1.2.0 to v1.2.1 in deploy doc URLs" -- "[8765](https://github.com/kubernetes/ingress-nginx/pull/8765) Bump github/codeql-action from 1.0.26 to 2.1.14" -- "[8752](https://github.com/kubernetes/ingress-nginx/pull/8752) Bump github.com/spf13/cobra from 1.4.0 to 1.5.0" -- "[8751](https://github.com/kubernetes/ingress-nginx/pull/8751) Bump github.com/stretchr/testify from 1.7.2 to 1.7.5" -- "[8750](https://github.com/kubernetes/ingress-nginx/pull/8750) added announcement" -- "[8740](https://github.com/kubernetes/ingress-nginx/pull/8740) change sha e2etestrunner and echoserver" -- "[8738](https://github.com/kubernetes/ingress-nginx/pull/8738) Update docs to make it easier for noobs to follow step by step" -- "[8737](https://github.com/kubernetes/ingress-nginx/pull/8737) updated baseimage sha" -- "[8736](https://github.com/kubernetes/ingress-nginx/pull/8736) set ld-musl-path" -- "[8733](https://github.com/kubernetes/ingress-nginx/pull/8733) feat: migrate leaderelection lock to leases" -- "[8726](https://github.com/kubernetes/ingress-nginx/pull/8726) prometheus metric: upstream_latency_seconds" -- "[8720](https://github.com/kubernetes/ingress-nginx/pull/8720) Ci pin deps" -- "[8719](https://github.com/kubernetes/ingress-nginx/pull/8719) Working OpenTelemetry sidecar (base nginx image)" -- "[8714](https://github.com/kubernetes/ingress-nginx/pull/8714) Create Openssf scorecard" -- "[8708](https://github.com/kubernetes/ingress-nginx/pull/8708) Bump github.com/prometheus/common from 0.34.0 to 0.35.0" -- "[8703](https://github.com/kubernetes/ingress-nginx/pull/8703) Bump actions/dependency-review-action from 1 to 2" -- "[8701](https://github.com/kubernetes/ingress-nginx/pull/8701) Fix several typos" -- "[8699](https://github.com/kubernetes/ingress-nginx/pull/8699) fix the gosec test and a make target for it" -- "[8698](https://github.com/kubernetes/ingress-nginx/pull/8698) Bump actions/upload-artifact from 2.3.1 to 3.1.0" -- "[8697](https://github.com/kubernetes/ingress-nginx/pull/8697) Bump actions/setup-go from 2.2.0 to 3.2.0" -- "[8695](https://github.com/kubernetes/ingress-nginx/pull/8695) Bump actions/download-artifact from 2 to 3" -- "[8694](https://github.com/kubernetes/ingress-nginx/pull/8694) Bump crazy-max/ghaction-docker-buildx from 1.6.2 to 3.3.1" - -### 1.2.1 - -Image: -- k8s.gcr.io/ingress-nginx/controller:v1.2.1@sha256:5516d103a9c2ecc4f026efbd4b40662ce22dc1f824fb129ed121460aaa5c47f8 -- k8s.gcr.io/ingress-nginx/controller-chroot:v1.2.1@sha256:d301551cf62bc3fb75c69fa56f7aa1d9e87b5079333adaf38afe84d9b7439355 - -This release removes the root and alias directives in NGINX, this can avoid some potential security attacks. - -_Changes:_ - -- [8459](https://github.com/kubernetes/ingress-nginx/pull/8459) Update default allowed CORS headers -- [8202](https://github.com/kubernetes/ingress-nginx/pull/8202) disable modsecurity on error page -- [8178](https://github.com/kubernetes/ingress-nginx/pull/8178) Add header Host into mirror annotations -- [8458](https://github.com/kubernetes/ingress-nginx/pull/8458) Add portNamePreffix Helm chart parameter -- [8587](https://github.com/kubernetes/ingress-nginx/pull/8587) Add CAP_SYS_CHROOT to DS/PSP when needed -- [8213](https://github.com/kubernetes/ingress-nginx/pull/8213) feat: always set auth cookie -- [8548](https://github.com/kubernetes/ingress-nginx/pull/8548) Implement reporting status classes in metrics -- [8612](https://github.com/kubernetes/ingress-nginx/pull/8612) move so files under /etc/nginx/modules -- [8624](https://github.com/kubernetes/ingress-nginx/pull/8624) Add patch to remove root and alias directives -- [8623](https://github.com/kubernetes/ingress-nginx/pull/8623) Improve path rule - -### 1.2.0 - -Image: -- k8s.gcr.io/ingress-nginx/controller:v1.2.0@sha256:d8196e3bc1e72547c5dec66d6556c0ff92a23f6d0919b206be170bc90d5f9185 -- k8s.gcr.io/ingress-nginx/controller-chroot:v1.2.0@sha256:fb17f1700b77d4fcc52ca6f83ffc2821861ae887dbb87149cf5cbc52bea425e5 - -This minor version release, introduces 2 breaking changes. For the first time, an option to jail/chroot the nginx process, inside the controller container, is being introduced. This provides an additional layer of security, for sensitive information like K8S serviceaccounts. This release also brings a special new feature of deep inspection into objects. The inspection is a walk through of all the spec, checking for possible attempts to escape configs. Currently such an inspection only occurs for `networking.Ingress`. Additionally there are fixes for the recently announced CVEs on busybox & ssl_client. And there is a fix to a recently introduced redirection related bug, that was setting the protocol on URLs to "nil". - -_Changes:_ - -- [8481](https://github.com/kubernetes/ingress-nginx/pull/8481) Fix log creation in chroot script -- [8479](https://github.com/kubernetes/ingress-nginx/pull/8479) changed nginx base img tag to img built with alpine3.14.6 -- [8478](https://github.com/kubernetes/ingress-nginx/pull/8478) update base images and protobuf gomod -- [8468](https://github.com/kubernetes/ingress-nginx/pull/8468) Fallback to ngx.var.scheme for redirectScheme with use-forward-headers when X-Forwarded-Proto is empty -- [8456](https://github.com/kubernetes/ingress-nginx/pull/8456) Implement object deep inspector -- [8455](https://github.com/kubernetes/ingress-nginx/pull/8455) Update dependencies -- [8454](https://github.com/kubernetes/ingress-nginx/pull/8454) Update index.md -- [8447](https://github.com/kubernetes/ingress-nginx/pull/8447) typo fixing -- [8446](https://github.com/kubernetes/ingress-nginx/pull/8446) Fix suggested annotation-value-word-blocklist -- [8444](https://github.com/kubernetes/ingress-nginx/pull/8444) replace deprecated topology key in example with current one -- [8443](https://github.com/kubernetes/ingress-nginx/pull/8443) Add dependency review enforcement -- [8434](https://github.com/kubernetes/ingress-nginx/pull/8434) added new auth-tls-match-cn annotation -- [8426](https://github.com/kubernetes/ingress-nginx/pull/8426) Bump github.com/prometheus/common from 0.32.1 to 0.33.0 -- [8417](https://github.com/kubernetes/ingress-nginx/pull/8417) force helm release to artifact hub -- [8405](https://github.com/kubernetes/ingress-nginx/pull/8405) kubectl-plugin code overview info -- [8399](https://github.com/kubernetes/ingress-nginx/pull/8399) Darwin arm64 -- [8443](https://github.com/kubernetes/ingress-nginx/pull/8443) Add dependency review enforcement -- [8444](https://github.com/kubernetes/ingress-nginx/pull/8444) replace deprecated topology key in example with current one -- [8446](https://github.com/kubernetes/ingress-nginx/pull/8446) Fix suggested annotation-value-word-blocklist -- [8219](https://github.com/kubernetes/ingress-nginx/pull/8219) Add keepalive support for auth requests -- [8455](https://github.com/kubernetes/ingress-nginx/pull/8455) Update dependencies -- [8456](https://github.com/kubernetes/ingress-nginx/pull/8456) Implement object deep inspector -- [8325](https://github.com/kubernetes/ingress-nginx/pull/8325) Fix for buggy ingress sync with retries -- [8322](https://github.com/kubernetes/ingress-nginx/pull/8322) Improve req handling dashboard - -### 1.2.0-beta.0 - -**Image:** -- k8s.gcr.io/ingress-nginx/controller:v1.2.0-beta.0@sha256:92115f5062568ebbcd450cd2cf9bffdef8df9fc61e7d5868ba8a7c9d773e0961 -- k8s.gcr.io/ingress-nginx/controller-chroot:v1.2.0-beta.0@sha256:0082f0f547b147a30ad85a5d6d2ceb3edbf0848b2008ed754365b6678bdea9a5 - -This release introduces Jail/chroot nginx process inside controller container for the first time - -_Changes:_ - -- [8417](https://github.com/kubernetes/ingress-nginx/pull/8417) force helm release to artifact hub -- [8421](https://github.com/kubernetes/ingress-nginx/pull/8421) fix change log changes list -- [8405](https://github.com/kubernetes/ingress-nginx/pull/8405) kubectl-plugin code overview info -- [8399](https://github.com/kubernetes/ingress-nginx/pull/8399) Darwin arm64 -- [8443](https://github.com/kubernetes/ingress-nginx/pull/8443) Add dependency review enforcement -- [8426](https://github.com/kubernetes/ingress-nginx/pull/8426) Bump github.com/prometheus/common from 0.32.1 to 0.33.0 -- [8444](https://github.com/kubernetes/ingress-nginx/pull/8444) replace deprecated topology key in example with current one -- [8447](https://github.com/kubernetes/ingress-nginx/pull/8447) typo fixing -- [8446](https://github.com/kubernetes/ingress-nginx/pull/8446) Fix suggested annotation-value-word-blocklist -- [8219](https://github.com/kubernetes/ingress-nginx/pull/8219) Add keepalive support for auth requests -- [8337](https://github.com/kubernetes/ingress-nginx/pull/8337) Jail/chroot nginx process inside controller container -- [8454](https://github.com/kubernetes/ingress-nginx/pull/8454) Update index.md -- [8455](https://github.com/kubernetes/ingress-nginx/pull/8455) Update dependencies -- [8456](https://github.com/kubernetes/ingress-nginx/pull/8456) Implement object deep inspector -- [8325](https://github.com/kubernetes/ingress-nginx/pull/8325) Fix for buggy ingress sync with retries -- [8322](https://github.com/kubernetes/ingress-nginx/pull/8322) Improve req handling dashboard -- [8464](https://github.com/kubernetes/ingress-nginx/pull/8464) Prepare v1.2.0-beta.0 release - - -### 1.1.3 - -**Image:** -- k8s.gcr.io/ingress-nginx/controller:v1.1.3@sha256:31f47c1e202b39fadecf822a9b76370bd4baed199a005b3e7d4d1455f4fd3fe2 - -This release upgrades Alpine to 3.14.4 and nginx to 1.19.10 - -Patches [OpenSSL CVE-2022-0778](https://github.com/kubernetes/ingress-nginx/issues/8339) - -Patches [Libxml2 CVE-2022-23308](https://github.com/kubernetes/ingress-nginx/issues/8321) - -_Breaking Changes:_ - -- https://github.com/nginx/nginx/commit/d18e066d650bff39f1705d3038804873584007af Deprecated http2_recv_timeout in favor of client_header_timeout (client-header-timeout) -- https://github.com/nginx/nginx/commit/51fea093e4374dbd857dc437ff9588060ef56471 Deprecated http2_max_field_size (http2-max-field-size) and http2_max_header_size (http2-max-header-size) in favor of large_client_header_buffers (large-client-header-buffers) -- https://github.com/nginx/nginx/commit/49ab3312448495f0ee8e00143a29624dde46ef5c Deprecated http2_idle_timeout and http2_max_requests (http2-max-requests) in favor of keepalive_timeout (upstream-keepalive-timeout?) and keepalive_requests (upstream-keepalive-requests?) respectively - -_Changes:_ - -- [8415](https://github.com/kubernetes/ingress-nginx/pull/8415) base img update for e2e-test-runner & opentelemetry -- [8403](https://github.com/kubernetes/ingress-nginx/pull/8403) Add execute permissions to nginx image entrypoint.sh -- [8392](https://github.com/kubernetes/ingress-nginx/pull/8392) fix document for monitoring -- [8386](https://github.com/kubernetes/ingress-nginx/pull/8386) downgrade to 3.14.4 and fix tag -- [8379](https://github.com/kubernetes/ingress-nginx/pull/8379) bump luarocks to 3.8.0 -- [8368](https://github.com/kubernetes/ingress-nginx/pull/8368) Updated semver in install docs URLs -- [8360](https://github.com/kubernetes/ingress-nginx/pull/8360) Bump github.com/stretchr/testify from 1.7.0 to 1.7.1 -- [8334](https://github.com/kubernetes/ingress-nginx/pull/8334) Pinned GitHub workflows by SHA -- [8324](https://github.com/kubernetes/ingress-nginx/pull/8324) Added missing "repo" option on "helm upgrade" command -- [8315](https://github.com/kubernetes/ingress-nginx/pull/8315) Fix 50% split between canary and mainline tests -- [8311](https://github.com/kubernetes/ingress-nginx/pull/8311) leaving it the git tag -- [8307](https://github.com/kubernetes/ingress-nginx/pull/8307) Nginx v1.19.10 -- [8302](https://github.com/kubernetes/ingress-nginx/pull/8302) docs: fix changelog formatting for 1.1.2 -- [8300](https://github.com/kubernetes/ingress-nginx/pull/8300) Names cannot contain _ (underscore)! So I changed it to -. -- [8288](https://github.com/kubernetes/ingress-nginx/pull/8288) [docs] Missing annotations -- [8287](https://github.com/kubernetes/ingress-nginx/pull/8287) Add the shareProcessNamespace as a configurable setting in the helm chart -- [8286](https://github.com/kubernetes/ingress-nginx/pull/8286) Fix OpenTelemetry sidecar image build -- [8281](https://github.com/kubernetes/ingress-nginx/pull/8281) force prow job by changing something in images/ot dir -- [8273](https://github.com/kubernetes/ingress-nginx/pull/8273) Issue#8241 -- [8267](https://github.com/kubernetes/ingress-nginx/pull/8267) Add fsGroup value to admission-webhooks/job-patch charts -- [8262](https://github.com/kubernetes/ingress-nginx/pull/8262) Updated confusing error -- [8258](https://github.com/kubernetes/ingress-nginx/pull/8258) remove 0.46.0 from supported versions table -- [8256](https://github.com/kubernetes/ingress-nginx/pull/8256) fix: deny locations with invalid auth-url annotation -- [8253](https://github.com/kubernetes/ingress-nginx/pull/8253) Add a certificate info metric - -### 1.1.2 - -**Image:** -- k8s.gcr.io/ingress-nginx/controller:v1.1.2@sha256:28b11ce69e57843de44e3db6413e98d09de0f6688e33d4bd384002a44f78405c - -This release bumps grpc version to 1.44.0 & runc to version 1.1.0. The release also re-introduces the ingress.class annotation, which was previously declared as deprecated. Besides that, several bug fixes and improvements are listed below. - -_Changes:_ - -- [8291](https://github.com/kubernetes/ingress-nginx/pull/8291) remove git tag env from cloud build -- [8286](https://github.com/kubernetes/ingress-nginx/pull/8286) Fix OpenTelemetry sidecar image build -- [8277](https://github.com/kubernetes/ingress-nginx/pull/8277) Add OpenSSF Best practices badge -- [8273](https://github.com/kubernetes/ingress-nginx/pull/8273) Issue#8241 -- [8267](https://github.com/kubernetes/ingress-nginx/pull/8267) Add fsGroup value to admission-webhooks/job-patch charts -- [8262](https://github.com/kubernetes/ingress-nginx/pull/8262) Updated confusing error -- [8256](https://github.com/kubernetes/ingress-nginx/pull/8256) fix: deny locations with invalid auth-url annotation -- [8253](https://github.com/kubernetes/ingress-nginx/pull/8253) Add a certificate info metric -- [8236](https://github.com/kubernetes/ingress-nginx/pull/8236) webhook: remove useless code. -- [8227](https://github.com/kubernetes/ingress-nginx/pull/8227) Update libraries in webhook image -- [8225](https://github.com/kubernetes/ingress-nginx/pull/8225) fix inconsistent-label-cardinality for prometheus metrics: nginx_ingress_controller_requests -- [8221](https://github.com/kubernetes/ingress-nginx/pull/8221) Do not validate ingresses with unknown ingress class in admission webhook endpoint -- [8210](https://github.com/kubernetes/ingress-nginx/pull/8210) Bump github.com/prometheus/client_golang from 1.11.0 to 1.12.1 -- [8209](https://github.com/kubernetes/ingress-nginx/pull/8209) Bump google.golang.org/grpc from 1.43.0 to 1.44.0 -- [8204](https://github.com/kubernetes/ingress-nginx/pull/8204) Add Artifact Hub lint -- [8203](https://github.com/kubernetes/ingress-nginx/pull/8203) Fix Indentation of example and link to cert-manager tutorial -- [8201](https://github.com/kubernetes/ingress-nginx/pull/8201) feat(metrics): add path and method labels to requests countera -- [8199](https://github.com/kubernetes/ingress-nginx/pull/8199) use functional options to reduce number of methods creating an EchoDeployment -- [8196](https://github.com/kubernetes/ingress-nginx/pull/8196) docs: fix inconsistent controller annotation -- [8191](https://github.com/kubernetes/ingress-nginx/pull/8191) Using Go install for misspell -- [8186](https://github.com/kubernetes/ingress-nginx/pull/8186) prometheus+grafana using servicemonitor -- [8185](https://github.com/kubernetes/ingress-nginx/pull/8185) Append elements on match, instead of removing for cors-annotations -- [8179](https://github.com/kubernetes/ingress-nginx/pull/8179) Bump github.com/opencontainers/runc from 1.0.3 to 1.1.0 -- [8173](https://github.com/kubernetes/ingress-nginx/pull/8173) Adding annotations to the controller service account -- [8163](https://github.com/kubernetes/ingress-nginx/pull/8163) Update the $req_id placeholder description -- [8162](https://github.com/kubernetes/ingress-nginx/pull/8162) Versioned static manifests -- [8159](https://github.com/kubernetes/ingress-nginx/pull/8159) Adding some geoip variables and default values -- [8155](https://github.com/kubernetes/ingress-nginx/pull/8155) #7271 feat: avoid-pdb-creation-when-default-backend-disabled-and-replicas-gt-1 -- [8151](https://github.com/kubernetes/ingress-nginx/pull/8151) Automatically generate helm docs -- [8143](https://github.com/kubernetes/ingress-nginx/pull/8143) Allow to configure delay before controller exits -- [8136](https://github.com/kubernetes/ingress-nginx/pull/8136) add ingressClass option to helm chart - back compatibility with ingress.class annotations - - -### 1.1.1 - -**Image:** -- k8s.gcr.io/ingress-nginx/controller:v1.1.1@sha256:0bc88eb15f9e7f84e8e56c14fa5735aaa488b840983f87bd79b1054190e660de - -This release contains several fixes and improvements. This image is now built using Go v1.17.6 and gRPC v1.43.0. See detailed list below. - -_Changes:_ - -- [8120](https://github.com/kubernetes/ingress-nginx/pull/8120) Update go in runner and release v1.1.1 -- [8119](https://github.com/kubernetes/ingress-nginx/pull/8119) Update to go v1.17.6 -- [8118](https://github.com/kubernetes/ingress-nginx/pull/8118) Remove deprecated libraries, update other libs -- [8117](https://github.com/kubernetes/ingress-nginx/pull/8117) Fix codegen errors -- [8115](https://github.com/kubernetes/ingress-nginx/pull/8115) chart/ghaction: set the correct permission to have access to push a release -- [8098](https://github.com/kubernetes/ingress-nginx/pull/8098) generating SHA for CA only certs in backend_ssl.go + comparision of P… -- [8088](https://github.com/kubernetes/ingress-nginx/pull/8088) Fix Edit this page link to use main branch -- [8072](https://github.com/kubernetes/ingress-nginx/pull/8072) Expose GeoIP2 Continent code as variable -- [8061](https://github.com/kubernetes/ingress-nginx/pull/8061) docs(charts): using helm-docs for chart -- [8058](https://github.com/kubernetes/ingress-nginx/pull/8058) Bump github.com/spf13/cobra from 1.2.1 to 1.3.0 -- [8054](https://github.com/kubernetes/ingress-nginx/pull/8054) Bump google.golang.org/grpc from 1.41.0 to 1.43.0 -- [8051](https://github.com/kubernetes/ingress-nginx/pull/8051) align bug report with feature request regarding kind documentation -- [8046](https://github.com/kubernetes/ingress-nginx/pull/8046) Report expired certificates (#8045) -- [8044](https://github.com/kubernetes/ingress-nginx/pull/8044) remove G109 check till gosec resolves issues -- [8042](https://github.com/kubernetes/ingress-nginx/pull/8042) docs_multiple_instances_one_cluster_ticket_7543 -- [8041](https://github.com/kubernetes/ingress-nginx/pull/8041) docs: fix typo'd executible name -- [8035](https://github.com/kubernetes/ingress-nginx/pull/8035) Comment busy owners -- [8029](https://github.com/kubernetes/ingress-nginx/pull/8029) Add stream-snippet as a ConfigMap and Annotation option -- [8023](https://github.com/kubernetes/ingress-nginx/pull/8023) fix nginx compilation flags -- [8021](https://github.com/kubernetes/ingress-nginx/pull/8021) Disable default modsecurity_rules_file if modsecurity-snippet is specified -- [8019](https://github.com/kubernetes/ingress-nginx/pull/8019) Revise main documentation page -- [8018](https://github.com/kubernetes/ingress-nginx/pull/8018) Preserve order of plugin invocation -- [8015](https://github.com/kubernetes/ingress-nginx/pull/8015) Add newline indenting to admission webhook annotations -- [8014](https://github.com/kubernetes/ingress-nginx/pull/8014) Add link to example error page manifest in docs -- [8009](https://github.com/kubernetes/ingress-nginx/pull/8009) Fix spelling in documentation and top-level files -- [8008](https://github.com/kubernetes/ingress-nginx/pull/8008) Add relabelings in controller-servicemonitor.yaml -- [8003](https://github.com/kubernetes/ingress-nginx/pull/8003) Minor improvements (formatting, consistency) in install guide -- [8001](https://github.com/kubernetes/ingress-nginx/pull/8001) fix: go-grpc Dockerfile -- [7999](https://github.com/kubernetes/ingress-nginx/pull/7999) images: use k8s-staging-test-infra/gcb-docker-gcloud -- [7996](https://github.com/kubernetes/ingress-nginx/pull/7996) doc: improvement -- [7983](https://github.com/kubernetes/ingress-nginx/pull/7983) Fix a couple of misspellings in the annotations documentation. -- [7979](https://github.com/kubernetes/ingress-nginx/pull/7979) allow set annotations for admission Jobs -- [7977](https://github.com/kubernetes/ingress-nginx/pull/7977) Add ssl_reject_handshake to defaul server -- [7975](https://github.com/kubernetes/ingress-nginx/pull/7975) add legacy version update v0.50.0 to main changelog -- [7972](https://github.com/kubernetes/ingress-nginx/pull/7972) updated service upstream definition -- [7963](https://github.com/kubernetes/ingress-nginx/pull/7963) Change sanitization message from error to warning - -### 1.1.0 - -**Image:** -- k8s.gcr.io/ingress-nginx/controller:v1.1.0@sha256:f766669fdcf3dc26347ed273a55e754b427eb4411ee075a53f30718b4499076a - -This release makes the annotation `annotation-value-word-blocklist` backwards compatible by being an empty list instead of prescribed defaults. -Effectively reverting [7874](https://github.com/kubernetes/ingress-nginx/pull/7874) but keeping the functionality of `annotation-value-word-blocklist` - -See Issue [7939](https://github.com/kubernetes/ingress-nginx/pull/7939) for more discussion - -Admins should still consider putting a reasonable block list in place, more information on why can be found [here](https://github.com/kubernetes/ingress-nginx/issues/7837) and how in our documentation [here](https://kubernetes.github.io/ingress-nginx/user-guide/nginx-configuration/configmap/#annotation-value-word-blocklist) - -_Changes:_ -- [7963](https://github.com/kubernetes/ingress-nginx/pull/7963) Change sanitization message from error to warning (#7963) -- [7942](https://github.com/kubernetes/ingress-nginx/pull/7942) update default block list,docs, tests (#7942) -- [7948](https://github.com/kubernetes/ingress-nginx/pull/7948) applied allowPrivilegeEscalation=false (#7948) -- [7941](https://github.com/kubernetes/ingress-nginx/pull/7941) update build for darwin arm64 (#7941) - -### 1.0.5 - -**Image:** -- k8s.gcr.io/ingress-nginx/controller:v1.0.5@sha256:55a1fcda5b7657c372515fe402c3e39ad93aa59f6e4378e82acd99912fe6028d - -_Possible Breaking Change_ -We now implement string sanitization in annotation values. This means that words like "location", "by_lua" and -others will drop the reconciliation of an Ingress object. - -Users from mod_security and other features should be aware that some blocked values may be used by those features -and must be manually unblocked by the Ingress Administrator. - -For more details please check [https://kubernetes.github.io/ingress-nginx/user-guide/nginx-configuration/configmap/#annotation-value-word-blocklist] - -_Changes:_ -- [7874](https://github.com/kubernetes/ingress-nginx/pull/7874) Add option to sanitize annotation inputs -- [7854](https://github.com/kubernetes/ingress-nginx/pull/7854) Add brotli-min-length configuration option -- [7800](https://github.com/kubernetes/ingress-nginx/pull/7800) Fix thread synchronization issue -- [7711](https://github.com/kubernetes/ingress-nginx/pull/7711) Added AdmissionController metrics -- [7614](https://github.com/kubernetes/ingress-nginx/pull/7614) Support cors-allow-origin with multiple origins -- [7472](https://github.com/kubernetes/ingress-nginx/pull/7472) Support watch multiple namespaces matched witch namespace selector - -### 1.0.4 - -**Image:** -- k8s.gcr.io/ingress-nginx/controller:v1.0.4@sha256:545cff00370f28363dad31e3b59a94ba377854d3a11f18988f5f9e56841ef9ef - -_Possible Breaking Change_ -We have disabled the builtin ssl_session_cache due to possible memory fragmentation. This should not impact the majority of users, but please let us know -if you face any problem - -_Changes:_ - -- [7777](https://github.com/kubernetes/ingress-nginx/pull/7777) Disable builtin ssl_session_cache -- [7727](https://github.com/kubernetes/ingress-nginx/pull/7727) Print warning only instead of error if no IngressClass permission is available -- Bump internal libraries versions -- Fix diverse documentation - -### 1.0.3 - -**Image:** -- k8s.gcr.io/ingress-nginx/controller:v1.0.3@sha256:4ade87838eb8256b094fbb5272d7dda9b6c7fa8b759e6af5383c1300996a7452 - -**Known Issues** -* Ingress controller now (starting from v1.0.0) mandates cluster scoped access to IngressClass. This leads to problems when updating old Ingress controller to newest version, as described [here](https://github.com/kubernetes/ingress-nginx/issues/7510). We plan to fix it in v1.0.4, see [this](https://github.com/kubernetes/ingress-nginx/pull/7578). - -_New Features:_ - -_Changes:_ - -- [X] [#7727](https://github.com/kubernetes/ingress-nginx/pull/7727) Fix selector for shutting down Pods status -- [X] [#7719](https://github.com/kubernetes/ingress-nginx/pull/7719) Fix overlap check when ingress is configured as canary -- Diverse docs fixes and libraries bumping - -### 1.0.2 - -**Image:** -- k8s.gcr.io/ingress-nginx/controller:v1.0.2@sha256:85b53b493d6d658d8c013449223b0ffd739c76d76dc9bf9000786669ec04e049 - -**Known Issues** -* Ingress controller now (starting from v1.0.0) mandates cluster scoped access to IngressClass. This leads to problems when updating old Ingress controller to newest version, as described [here](https://github.com/kubernetes/ingress-nginx/issues/7510). We plan to fix it in v1.0.3, see [this](https://github.com/kubernetes/ingress-nginx/pull/7578). - -_New Features:_ - -_Changes:_ - -- [X] [#7706](https://github.com/kubernetes/ingress-nginx/pull/7706) Add build info on prometheus metrics -- [X] [#7702](https://github.com/kubernetes/ingress-nginx/pull/7702) Upgrade lua-resty-balancer to v0.04 -- [X] [#7696](https://github.com/kubernetes/ingress-nginx/pull/7696) Add canary backend name for requests metrics - -### 1.0.1 - -**Image:** -- k8s.gcr.io/ingress-nginx/controller:v1.0.1@sha256:26bbd57f32bac3b30f90373005ef669aae324a4de4c19588a13ddba399c6664e - -**Known Issues** -* Ingress controller now (starting from v1.0.0) mandates cluster scoped access to IngressClass. This leads to problems when updating old Ingress controller to newest version, as described [here](https://github.com/kubernetes/ingress-nginx/issues/7510). We plan to fix it in v1.0.2, see [this](https://github.com/kubernetes/ingress-nginx/pull/7578). - -_New Features:_ - -_Changes:_ - -- [X] [#7670](https://github.com/kubernetes/ingress-nginx/pull/7670) Change enable-snippet to allow-snippet-annotation (#7670) -- [X] [#7672](https://github.com/kubernetes/ingress-nginx/pull/7672) add option for documentiony only to pr template (#7672) -- [X] [#7668](https://github.com/kubernetes/ingress-nginx/pull/7668) added example multiple controller install to faq (#7668) -- [X] [#7665](https://github.com/kubernetes/ingress-nginx/pull/7665) Add option to force enabling snippet directives (#7665) -- [X] [#7659](https://github.com/kubernetes/ingress-nginx/pull/7659) Replace kube-lego docs with cert-manager (#7659) -- [X] [#7656](https://github.com/kubernetes/ingress-nginx/pull/7656) Changelog.md: Update references to sigs.k8s.io/promo-tools (#7656) -- [X] [#7603](https://github.com/kubernetes/ingress-nginx/pull/7603) additional info for the custom-headers documentation page (#7603) -- [X] [#7630](https://github.com/kubernetes/ingress-nginx/pull/7630) images/kube-webhook-certgen/rootfs: improvements (#7630) -- [X] [#7636](https://github.com/kubernetes/ingress-nginx/pull/7636) Add github action for building images (#7636) -- [X] [#7648](https://github.com/kubernetes/ingress-nginx/pull/7648) Update e2e-test-runner image (#7648) -- [X] [#7643](https://github.com/kubernetes/ingress-nginx/pull/7643) Update NGINX base image to v1.19 (#7643) -- [X] [#7642](https://github.com/kubernetes/ingress-nginx/pull/7642) Add security contacts (#7642) -- [X] [#7640](https://github.com/kubernetes/ingress-nginx/pull/7640) fix typos. (#7640) -- [X] [#7639](https://github.com/kubernetes/ingress-nginx/pull/7536) Downgrade nginx to v1.19 (#7639) -- [X] [#7575](https://github.com/kubernetes/ingress-nginx/pull/7575) Add e2e tests for secure cookie annotations (#7575) (#7619) -- [X] [#7625](https://github.com/kubernetes/ingress-nginx/pull/7625) Only build nginx-errors for linux/amd64 (#7625) -- [X] [#7609](https://github.com/kubernetes/ingress-nginx/pull/7609) Add new flag to watch ingressclass by name instead of spec (#7609) -- [X] [#7604](https://github.com/kubernetes/ingress-nginx/pull/7604) Change the cloudbuild timeout (#7604) -- [X] [#7460](https://github.com/kubernetes/ingress-nginx/pull/7460) Fix old tag of custom error pages used in example (#7460) -- [X] [#7577](https://github.com/kubernetes/ingress-nginx/pull/7577) Added command to get Nginx versionq! (#7577) -- [X] [#7611](https://github.com/kubernetes/ingress-nginx/pull/7611) Helm notes outputs non nil value for ingress.class annotation (#7611) -- [X] [#7469](https://github.com/kubernetes/ingress-nginx/pull/7469) Allow the usage of Services as Upstream on a global level (#7469) -- [X] [#7393](https://github.com/kubernetes/ingress-nginx/pull/7393) getEndpoints uses service target port directly if it's a number and mismatch with port name in endpoint (#7393) -- [X] [#7514](https://github.com/kubernetes/ingress-nginx/pull/7514) nginx flag: --disable-full-test flag to allow testing configfile of the current single ingress (#7514) -- [X] [#7374](https://github.com/kubernetes/ingress-nginx/pull/7374) Trigger syncIngress on Service addition/deletion #7346 (#7374) -- [X] [#7464](https://github.com/kubernetes/ingress-nginx/pull/7464) Sync Hostname and IP address from service to ingress status (#7464) -- [X] [#7560](https://github.com/kubernetes/ingress-nginx/pull/7560) put modsecurity e2e tests into their own packages (#7560) -- [X] [#7202](https://github.com/kubernetes/ingress-nginx/pull/7202) Additional AuthTLS assertions and doc change to demonstrate auth-tls-secret enables the other AuthTLS annotations (#7202) -- [X] [#7606](https://github.com/kubernetes/ingress-nginx/pull/7606) fix cli flag typo in faq (#7606) -- [X] [#7601](https://github.com/kubernetes/ingress-nginx/pull/7601) fix charts README.md to give additional detail on prometheus metrics … (#7601) -- [X] [#7596](https://github.com/kubernetes/ingress-nginx/pull/7596) Update e2e test runner image (#7596) -- [X] [#7604](https://github.com/kubernetes/ingress-nginx/pull/7604) Update cloudbuild timeout (#7604) -- [X] [#7440](https://github.com/kubernetes/ingress-nginx/pull/7440) remove timestamp when requeuing Element (#7440) -- [X] [#7598](https://github.com/kubernetes/ingress-nginx/pull/7598) correct docs on ingressClass resource being disabled (#7598) -- [X] [#7597](https://github.com/kubernetes/ingress-nginx/pull/7597) Update to the base nginx image (#7597) -- [X] [#7540](https://github.com/kubernetes/ingress-nginx/pull/7540) improve faq for migration to ingress api v1 (#7540) -- [X] [#7594](https://github.com/kubernetes/ingress-nginx/pull/7594) Remove addgroup directive from alpine building (#7594) -- [X] [#7592](https://github.com/kubernetes/ingress-nginx/pull/7592) Change builder in a new attempt to make it run (#7592) -- [X] [#7584](https://github.com/kubernetes/ingress-nginx/pull/7584) Changing gcb builder (#7584) -- [X] [#7583](https://github.com/kubernetes/ingress-nginx/pull/7583) update alpine and remove buildx restriction (#7583) -- [X] [#7561](https://github.com/kubernetes/ingress-nginx/pull/7561) Add doc ref for preserve-trailing-slash annotation (#7561) -- [X] [#7581](https://github.com/kubernetes/ingress-nginx/pull/7581) Default KinD manifest to watch ingresses without class (#7581) -- [X] [#7511](https://github.com/kubernetes/ingress-nginx/pull/7511) add same tcp and udp ports to internal load balancer (#7511) -- [X] [#7399](https://github.com/kubernetes/ingress-nginx/pull/7399) feat: add session-cookie-secure annotation (#7399) -- [X] [#7556](https://github.com/kubernetes/ingress-nginx/pull/7556) Fix YAML indentation issue (#7556) -- [X] [#7558](https://github.com/kubernetes/ingress-nginx/pull/7558) Revert "Update base nginx" (#7558) -- [X] [#7552](https://github.com/kubernetes/ingress-nginx/pull/7552) Update base nginx (#7552) -- [X] [#7541](https://github.com/kubernetes/ingress-nginx/pull/7541) Add a flag to specify address to bind the healthz server (#7541) -- [X] [#7503](https://github.com/kubernetes/ingress-nginx/pull/7503) Document the keep-alive 0 effect on http/2 requests (#7503) -- [X] [#7264](https://github.com/kubernetes/ingress-nginx/pull/7264) Update docs for new ingress api in cluster version >=1.19 (#7264) -- [X] [#7545](https://github.com/kubernetes/ingress-nginx/pull/7545) Improving e2e tests for non-service backends #7544 (#7545) -- [X] [#7537](https://github.com/kubernetes/ingress-nginx/pull/7537) improve docs for release - added step to edit README for support matrix (#7537) -- [X] [#7536](https://github.com/kubernetes/ingress-nginx/pull/7536) add known issues in changelog.md for release v1.0.0 (#7536) - -### 1.0.0 -**This is a breaking change** - -This release only supports Kubernetes versions >= v1.19. The support for Ingress Object in `networking.k8s.io/v1beta` is being dropped and manifests should now use `networking.k8s.io/v1`. - -**Image:** - -- `k8s.gcr.io/ingress-nginx/controller:v1.0.0@sha256:0851b34f69f69352bf168e6ccf30e1e20714a264ab1ecd1933e4d8c0fc3215c6` - -**Known Issues** -Ingress Controller only supports cluster scoped IngressClass and needs cluster wide permission for this object, otherwise it is not going to start. -We plan to fix this in v1.0.1 and issues #7510 and #7502 are tracking this. - -Changes: -- [X] [#7529](https://github.com/kubernetes/ingress-nginx/pull/7529) End-to-end tests for canary affinity -- [X] [#7489](https://github.com/kubernetes/ingress-nginx/pull/7489) docs: Clarify default-backend behavior -- [X] [#7524](https://github.com/kubernetes/ingress-nginx/pull/7524) docs for migration to apiVersion networking.k8s.io/v1 -- [X] [#7443](https://github.com/kubernetes/ingress-nginx/pull/7443) fix ingress-nginx panic when the certificate format is wrong. -- [X] [#7521](https://github.com/kubernetes/ingress-nginx/pull/7521) Update ingress to go 1.17 -- [X] [#7493](https://github.com/kubernetes/ingress-nginx/pull/7493) Add appProtocol field to all ServicePorts -- [X] [#7525](https://github.com/kubernetes/ingress-nginx/pull/7525) improve RELEASE.md -- [X] [#7203](https://github.com/kubernetes/ingress-nginx/pull/7203) Make HPA behavior configurable -- [X] [#7487](https://github.com/kubernetes/ingress-nginx/pull/7487)[Cherry - Pick] - Fix default backend annotation and tests -- [X] [#7459](https://github.com/kubernetes/ingress-nginx/pull/7459) Add controller.watchIngressWithoutClass config option -- [X] [#7478](https://github.com/kubernetes/ingress-nginx/pull/7478) Release new helm chart with certgen fixed -- [X] [#7341](https://github.com/kubernetes/ingress-nginx/pull/7341) Fix IngressClass logic for newer releases (#7341) -- [X] [#7355](https://github.com/kubernetes/ingress-nginx/pull/7355) Downgrade Lua modules for s390x (#7355) -- [X] [#7319](https://github.com/kubernetes/ingress-nginx/pull/7319) Lower webhook timeout for digital ocean (#7319) -- [X] [#7161](https://github.com/kubernetes/ingress-nginx/pull/7161) fix: allow scope/tcp/udp configmap namespace to altered (#7161) -- [X] [#7331](https://github.com/kubernetes/ingress-nginx/pull/7331) Fix forwarding of auth-response-headers to gRPC backends (#7331) -- [X] [#7332](https://github.com/kubernetes/ingress-nginx/pull/7332) controller: ignore non-service backends (#7332) -- [X] [#7314](https://github.com/kubernetes/ingress-nginx/pull/7314) Add configuration to disable external name service feature -- [X] [#7313](https://github.com/kubernetes/ingress-nginx/pull/7313) Add file containing stable release -- [X] [#7311](https://github.com/kubernetes/ingress-nginx/pull/7311) Handle named (non-numeric) ports correctly -- [X] [#7308](https://github.com/kubernetes/ingress-nginx/pull/7308) Updated v1beta1 to v1 as its deprecated -- [X] [#7298](https://github.com/kubernetes/ingress-nginx/pull/7298) Speed up admission hook by eliminating deep copy of Ingresses in CheckIngress -- [X] [#7242](https://github.com/kubernetes/ingress-nginx/pull/7242) Retry to download maxmind DB if it fails -- [X] [#7228](https://github.com/kubernetes/ingress-nginx/pull/7228) Discover mounted geoip db files -- [X] [#7208](https://github.com/kubernetes/ingress-nginx/pull/7208) ingress/tcp: add additional error logging on failed -- [X] [#7190](https://github.com/kubernetes/ingress-nginx/pull/7190) chart: using Helm builtin capabilities check -- [X] [#7146](https://github.com/kubernetes/ingress-nginx/pull/7146) Use ENV expansion for namespace in args -- [X] [#7107](https://github.com/kubernetes/ingress-nginx/pull/7107) Fix MaxWorkerOpenFiles calculation on high cores nodes -- [X] [#7076](https://github.com/kubernetes/ingress-nginx/pull/7076) Rewrite clean-nginx-conf.sh in Go to speed up admission webhook -- [X] [#7031](https://github.com/kubernetes/ingress-nginx/pull/7031) Remove mercurial from build -- [X] [#6990](https://github.com/kubernetes/ingress-nginx/pull/6990) Use listen to ensure the port is free -- [X] [#6944](https://github.com/kubernetes/ingress-nginx/pull/6944) Update proper default value for HTTP2MaxConcurrentStreams in Docs -- [X] [#6940](https://github.com/kubernetes/ingress-nginx/pull/6940) Fix definition order of modsecurity directives -- [X] [#7156] Drops support for Ingress Object v1beta1 - -### 0.50.0 - -**Image:** - -- `k8s.gcr.io/ingress-nginx/controller:v0.50.0@sha256:f46fc2d161c97a9d950635acb86fb3f8d4adcfb03ee241ea89c6cde16aa3fdf8` - -This release makes the annotation `annotation-value-word-blocklist` backwards compatible by being an empty list instead of prescribed defaults. -Effectively reverting [7874](https://github.com/kubernetes/ingress-nginx/pull/7874) but keeping the functionality of `annotation-value-word-blocklist` - -See Issue [7939](https://github.com/kubernetes/ingress-nginx/pull/7939) for more discussion - -Admins should still consider putting a reasonable block list in place, more information on why can be found [here](https://github.com/kubernetes/ingress-nginx/issues/7837) and how in our documentation [here](https://kubernetes.github.io/ingress-nginx/user-guide/nginx-configuration/configmap/#annotation-value-word-blocklist) - -_Changes:_ -- [7963](https://github.com/kubernetes/ingress-nginx/pull/7963) Change sanitization message from error to warning (#7963) -- [7942](https://github.com/kubernetes/ingress-nginx/pull/7942) update default block list,docs, tests (#7942) - -### 0.49.3 - -**Image:** - -- `k8s.gcr.io/ingress-nginx/controller:v0.49.3@sha256:35fe394c82164efa8f47f3ed0be981b3f23da77175bbb8268a9ae438851c8324` - -_Changes:_ - -- [X] [#7731](https://github.com/kubernetes/ingress-nginx/pull/7727) Fix selector for shutting down Pods status -- [X] [#7741](https://github.com/kubernetes/ingress-nginx/pull/7719) Fix overlap check when ingress is configured as canary - -### 0.49.2 - -**Image:** - -- `k8s.gcr.io/ingress-nginx/controller:v0.49.2@sha256:84e351228337bb7b09f0e90e6b6f5e2f8f4cf7d618c1ddc1e966f23902d273db` - -_Changes:_ - -- [x] [#7702](https://github.com/kubernetes/ingress-nginx/pull/#7702) upgrade lua-resty-balancer to v0.04 - -### 0.49.1 - -**Image:** - -- `k8s.gcr.io/ingress-nginx/controller:v0.49.1@sha256:4080849490fd4f61416ad7bdba6fdd0ee58164f2e13df1128b407ce82d5f3986` - -_New Features:_ - - -_Changes:_ - -- [x] [#7670](https://github.com/kubernetes/ingress-nginx/pull/7670) Change enable-snippet to allow-snippet-annotation (#7670) (#7677) -- [x] [#7676](https://github.com/kubernetes/ingress-nginx/pull/7676) Fix opentracing in v0.X (#7676) -- [x] [#7643](https://github.com/kubernetes/ingress-nginx/pull/7643) Update NGINX base image to v1.19 (#7643) -- [x] [#7665](https://github.com/kubernetes/ingress-nginx/pull/7665) Add option to force enabling snippet directives (7665) -- [x] [#7521](https://github.com/kubernetes/ingress-nginx/pull/7521) Update ingress to go 1.17 (#7521) - -### 0.49.0 - -**Image:** - -- `k8s.gcr.io/ingress-nginx/controller:v0.49.0@sha256:e9707504ad0d4c119036b6d41ace4a33596139d3feb9ccb6617813ce48c3eeef` - -_New Features:_ - - -_Changes:_ - -- [x] [#7486](https://github.com/kubernetes/ingress-nginx/pull/7486) Fix default backend annotation test -- [x] [#7481](https://github.com/kubernetes/ingress-nginx/pull/7481) Add linux node selector as default -- [x] [#6750](https://github.com/kubernetes/ingress-nginx/pull/6750) allow kb granularity for lua shared dicts -- [x] [#7463](https://github.com/kubernetes/ingress-nginx/pull/7463) Improved disableaccesslog tests -- [x] [#7485](https://github.com/kubernetes/ingress-nginx/pull/7485) update e2e test images to newest promoted one -- [x] [#7479](https://github.com/kubernetes/ingress-nginx/pull/7479) Make custom-default-backend upstream name more unique -- [x] [#7477](https://github.com/kubernetes/ingress-nginx/pull/7477) Trigger webhook image generation -- [x] [#7475](https://github.com/kubernetes/ingress-nginx/pull/7475) Migrate the webhook-certgen program to inside ingress repo -- [x] [#7331](https://github.com/kubernetes/ingress-nginx/pull/7331) Fix forwarding of auth-response-headers to gRPC backends -- [x] [#7228](https://github.com/kubernetes/ingress-nginx/pull/7228) fix: discover mounted geoip db files -- [x] [#7242](https://github.com/kubernetes/ingress-nginx/pull/7242) Retry to download maxmind DB if it fails -- [x] [#7473](https://github.com/kubernetes/ingress-nginx/pull/7473) update to newest image -- [x] [#7386](https://github.com/kubernetes/ingress-nginx/pull/7386) Add hostname value to override pod's hostname -- [x] [#7467](https://github.com/kubernetes/ingress-nginx/pull/7467) use listen to ensure the port is free -- [x] [#7411](https://github.com/kubernetes/ingress-nginx/pull/7411) Update versions of components for base image, including `nginx-http-auth-digest`, `ngx_http_substitutions_filter_module`, `nginx-opentracing`, `opentracing-cpp`, `ModSecurity-nginx`, `yaml-cpp`, `msgpack-c`, `lua-nginx-module`, `stream-lua-nginx-module`, `lua-upstream-nginx-module`, `luajit2`, `dd-opentracing-cpp`, `ngx_http_geoip2_module`, `nginx_ajp_module`, `lua-resty-string`, `lua-resty-balancer`, `lua-resty-core`, `lua-cjson`, `lua-resty-cookie`, `lua-resty-lrucache`, `lua-resty-dns`, `lua-resty-http`, `lua-resty-memcached`, `lua-resty-ipmatcher`. -- [x] [#7462](https://github.com/kubernetes/ingress-nginx/pull/7462) Update configmap.md -- [x] [#7369](https://github.com/kubernetes/ingress-nginx/pull/7369) Change all master reference to main -- [x] [#7245](https://github.com/kubernetes/ingress-nginx/pull/7245) Allow overriding of the default response format -- [x] [#7449](https://github.com/kubernetes/ingress-nginx/pull/7449) Fix cap for NET_BIND_SERVICE -- [x] [#7450](https://github.com/kubernetes/ingress-nginx/pull/7450) correct ingress-controller naming -- [x] [#7437](https://github.com/kubernetes/ingress-nginx/pull/7437) added K8s v1.22 tip for kind cluster,bug-report -- [x] [#7455](https://github.com/kubernetes/ingress-nginx/pull/7455) Add documentation for monitoring without helm -- [x] [#7454](https://github.com/kubernetes/ingress-nginx/pull/7454) Update go version to v1.16, modules and remove ioutil -- [x] [#7452](https://github.com/kubernetes/ingress-nginx/pull/7452) run k8s job ci pipeline with 1.21.2 in main branch -- [x] [#7451](https://github.com/kubernetes/ingress-nginx/pull/7451) Prepare for go v1.16 -- [x] [#7434](https://github.com/kubernetes/ingress-nginx/pull/7434) Helm - Enable configuring request and limit for containers in webhook jobs -- [x] [#6864](https://github.com/kubernetes/ingress-nginx/pull/6864) Add scope configuration check -- [x] [#7421](https://github.com/kubernetes/ingress-nginx/pull/7421) Bump PDB API version to v1 -- [x] [#7431](https://github.com/kubernetes/ingress-nginx/pull/7431) Add http request test to annotaion ssl cipher test -- [x] [#7426](https://github.com/kubernetes/ingress-nginx/pull/7426) Removed tabs and one extra-space -- [x] [#7423](https://github.com/kubernetes/ingress-nginx/pull/7423) Fixed chart version -- [x] [#7424](https://github.com/kubernetes/ingress-nginx/pull/7424) Add dev-v1 branch into helm releaser -- [x] [#7415](https://github.com/kubernetes/ingress-nginx/pull/7415) added checks to verify backend works with the given configs -- [x] [#7371](https://github.com/kubernetes/ingress-nginx/pull/7371) Enable session affinity for canaries -- [x] [#6985](https://github.com/kubernetes/ingress-nginx/pull/6985) auto backend protocol for HTTP/HTTPS -- [x] [#7394](https://github.com/kubernetes/ingress-nginx/pull/7394) reorder contributing infos -- [x] [#7224](https://github.com/kubernetes/ingress-nginx/pull/7224) docs:update troubleshooting.md -- [x] [#7353](https://github.com/kubernetes/ingress-nginx/pull/7353) aws-load-balancer-internal is a boolean value -- [x] [#7387](https://github.com/kubernetes/ingress-nginx/pull/7387) Automatically add area labels to help triaging -- [x] [#7360](https://github.com/kubernetes/ingress-nginx/pull/7360) grpc - replaced fortune-builder app with official greeter app -- [x] [#7361](https://github.com/kubernetes/ingress-nginx/pull/7361) doc: fix monitoring usage docs -- [x] [#7365](https://github.com/kubernetes/ingress-nginx/pull/7365) update OWNERS and aliases files -- [x] [#7039](https://github.com/kubernetes/ingress-nginx/pull/7039) Add missing tests for store/endpoint -- [x] [#7364](https://github.com/kubernetes/ingress-nginx/pull/7364) Add cpanato as Helm chart approver -- [x] [#7362](https://github.com/kubernetes/ingress-nginx/pull/7362) changed syntax from v1beta1 to v1 - -### 0.48.1 - -**Image:** - -- `k8s.gcr.io/ingress-nginx/controller:v0.48.1@sha256:e9fb216ace49dfa4a5983b183067e97496e7a8b307d2093f4278cd550c303899` - -_New Features:_ - - -_Changes:_ - -- [X] [#7298](https://github.com/kubernetes/ingress-nginx/pull/ ) Speed up admission hook by eliminating deep - copy of Ingresses in CheckIngress -- [X] [#6940](https://github.com/kubernetes/ingress-nginx/pull/6940) Fix definition order of modsecurity - directives for controller -- [X] [#7314](https://github.com/kubernetes/ingress-nginx/pull/7314) Add configuration to disable external name service feature #7314 -- [X] [#7076](https://github.com/kubernetes/ingress-nginx/pull/7076) Rewrite clean-nginx-conf.sh in Go to speed up - admission webhook -- [X] [#7255](https://github.com/kubernetes/ingress-nginx/pull/7255) Fix nilpointer in admission and remove failing - test #7255 -- [X] [#7216](https://github.com/kubernetes/ingress-nginx/pull/7216) Admission: Skip validation checks if an ingress - is marked as deleted #7216 - -### 1.0.0-beta.3 -** This is a breaking change** - -This release only supports Kubernetes versions >= v1.19. The support for Ingress Object in `networking.k8s.io/v1beta` is being dropped and manifests should now use `networking.k8s.io/v1`. - -**Image:** - -- `k8s.gcr.io/ingress-nginx/controller:v1.0.0-beta.3@sha256:44a7a06b71187a4529b0a9edee5cc22bdf71b414470eff696c3869ea8d90a695` - -Changes: - -- [X] [#7487](https://github.com/kubernetes/ingress-nginx/pull/7487)[Cherry - Pick] - Fix default backend annotation and tests -- [X] [#7459](https://github.com/kubernetes/ingress-nginx/pull/7459) Add controller.watchIngressWithoutClass config option -- [X] [#7478](https://github.com/kubernetes/ingress-nginx/pull/7478) Release new helm chart with certgen fixed - -### 1.0.0-beta.1 -**THIS IS A BREAKING CHANGE** - -This release only supports Kubernetes versions >= v1.19. The support for Ingress Object in `networking.k8s.io/v1beta` is being dropped and manifests should now use `networking.k8s.io/v1`. - -**Image:** - -- `k8s.gcr.io/ingress-nginx/controller:v1.0.0-beta.1@sha256:f058f3fdc940095957695829745956c6acddcaef839907360965e27fd3348e2e` - -_ New Features:_ - -_Changes:_ - -- [X] [#7341](https://github.com/kubernetes/ingress-nginx/pull/7341) Fix IngressClass logic for newer releases (#7341) -- [X] [#7355](https://github.com/kubernetes/ingress-nginx/pull/7355) Downgrade Lua modules for s390x (#7355) -- [X] [#7319](https://github.com/kubernetes/ingress-nginx/pull/7319) Lower webhook timeout for digital ocean (#7319) -- [X] [#7161](https://github.com/kubernetes/ingress-nginx/pull/7161) fix: allow scope/tcp/udp configmap namespace to altered (#7161) -- [X] [#7331](https://github.com/kubernetes/ingress-nginx/pull/7331) Fix forwarding of auth-response-headers to gRPC backends (#7331) -- [X] [#7332](https://github.com/kubernetes/ingress-nginx/pull/7332) controller: ignore non-service backends (#7332) - -### 1.0.0-alpha.2 -**THIS IS A BREAKING CHANGE** - -This release only supports Kubernetes versions >= v1.19. The support for Ingress Object in `networking.k8s.io/v1beta` is being dropped and manifests should now use `networking.k8s.io/v1`. - -**Image:** - -- `k8s.gcr.io/ingress-nginx/controller:v1.0.0-alpha.2@sha256:04a0ad3a1279c2a58898e789eed767eafa138ee1e5b9b23a988c6e8485cf958d` - -_ New Features:_ - -- [X] [#7314](https://github.com/kubernetes/ingress-nginx/pull/7314) Add configuration to disable external name service feature -- [X] [#7313](https://github.com/kubernetes/ingress-nginx/pull/7313) Add file containing stable release -- [X] [#7311](https://github.com/kubernetes/ingress-nginx/pull/7311) Handle named (non-numeric) ports correctly -- [X] [#7308](https://github.com/kubernetes/ingress-nginx/pull/7308) Updated v1beta1 to v1 as its deprecated -- [X] [#7298](https://github.com/kubernetes/ingress-nginx/pull/7298) Speed up admission hook by eliminating deep copy of Ingresses in CheckIngress -- [X] [#7242](https://github.com/kubernetes/ingress-nginx/pull/7242) Retry to download maxmind DB if it fails -- [X] [#7228](https://github.com/kubernetes/ingress-nginx/pull/7228) Discover mounted geoip db files -- [X] [#7208](https://github.com/kubernetes/ingress-nginx/pull/7208) ingress/tcp: add additional error logging on failed -- [X] [#7190](https://github.com/kubernetes/ingress-nginx/pull/7190) chart: using Helm builtin capabilities check -- [X] [#7146](https://github.com/kubernetes/ingress-nginx/pull/7146) Use ENV expansion for namespace in args -- [X] [#7107](https://github.com/kubernetes/ingress-nginx/pull/7107) Fix MaxWorkerOpenFiles calculation on high cores nodes -- [X] [#7076](https://github.com/kubernetes/ingress-nginx/pull/7076) Rewrite clean-nginx-conf.sh in Go to speed up admission webhook -- [X] [#7031](https://github.com/kubernetes/ingress-nginx/pull/7031) Remove mercurial from build -- [X] [#6990](https://github.com/kubernetes/ingress-nginx/pull/6990) Use listen to ensure the port is free -- [X] [#6944](https://github.com/kubernetes/ingress-nginx/pull/6944) Update proper default value for HTTP2MaxConcurrentStreams in Docs -- [X] [#6940](https://github.com/kubernetes/ingress-nginx/pull/6940) Fix definition order of modsecurity directives - -### 1.0.0-alpha.1 -**THIS IS A BREAKING CHANGE** - -This release only supports Kubernetes versions >= v1.19. The support for Ingress Object in `networking.k8s.io/v1beta` is being dropped and manifests should now use `networking.k8s.io/v1`. - -**Image:** - -- `k8s.gcr.io/ingress-nginx/controller:v1.0.0-alpha.1@sha256:32f3f02a038c0d7cf33b71a14028c3a4ddee6f4c3fe5fadfa14b915e5e0d9faf` - -_ New Features:_ - -- [X] [#7156] Drops support for Ingress Object v1beta1 - -### 0.47.0 - -**Image:** - -- `k8s.gcr.io/ingress-nginx/controller:v0.47.0@sha256:a1e4efc107be0bb78f32eaec37bef17d7a0c81bec8066cdf2572508d21351d0b` - -_New Features:_ - -- [X] [#7137] Add support for custom probes - -_Changes:_ - -- [X] [#7179](https://github.com/kubernetes/ingress-nginx/pull/7179) Upgrade Nginx to 1.20.1 -- [X] [#7101](https://github.com/kubernetes/ingress-nginx/pull/7101) Removed Codecov -- [X] [#6993](https://github.com/kubernetes/ingress-nginx/pull/6993) Fix cookieAffinity log printing error -- [X] [#7046](https://github.com/kubernetes/ingress-nginx/pull/7046) Allow configuring controller container name -- [X] [#6994](https://github.com/kubernetes/ingress-nginx/pull/6994) Fixed oauth2 callback url -- [X] [#6740](https://github.com/kubernetes/ingress-nginx/pull/6740) non-host canary ingress use default server name as host to merge -- [X] [#7126](https://github.com/kubernetes/ingress-nginx/pull/7126) set x-forwarded-scheme to be the same as x-forwarded-proto -- [X] [#6734](https://github.com/kubernetes/ingress-nginx/pull/6734) Update controller-poddisruptionbudget.yaml -- [X] [#7117](https://github.com/kubernetes/ingress-nginx/pull/7117) Adding annotations for HPA - -### 0.46.0 - -**Image:** - -- `k8s.gcr.io/ingress-nginx/controller:v0.46.0@sha256:52f0058bed0a17ab0fb35628ba97e8d52b5d32299fbc03cc0f6c7b9ff036b61a` - -_Changes:_ - -- [#7092](https://github.com/kubernetes/ingress-nginx/pull/7092) Removes the possibility of using localhost in ExternalNames as endpoints - - -### 0.45.0 - -**Image:** - -- `k8s.gcr.io/ingress-nginx/controller:v0.45.0@sha256:c4390c53f348c3bd4e60a5dd6a11c35799ae78c49388090140b9d72ccede1755` - -_New Features:_ - -- Update the Ingress Controller Image to correct OpenSSL CVEs -- Add support for Jaeger Endpoint [#6884](https://github.com/kubernetes/ingress-nginx/pull/6884) -- Allow Multiple Publish Status Addresses [#6856](https://github.com/kubernetes/ingress-nginx/pull/6856) - -_Changes:_ - -- [X] [#6995](https://github.com/kubernetes/ingress-nginx/pull/6995) updating nginx base image across repo -- [X] [#6983](https://github.com/kubernetes/ingress-nginx/pull/6983) Expose Geo IP subdivision 1 as variables -- [X] [#6979](https://github.com/kubernetes/ingress-nginx/pull/6979) Changed servicePort value for metrics -- [X] [#6971](https://github.com/kubernetes/ingress-nginx/pull/6971) Fix crl not reload when crl got updated in the ca secret -- [X] [#6957](https://github.com/kubernetes/ingress-nginx/pull/6957) Add ability to specify automountServiceAccountToken -- [X] [#6956](https://github.com/kubernetes/ingress-nginx/pull/6956) update nginx base image, handle jaeger propagation format -- [X] [#6936](https://github.com/kubernetes/ingress-nginx/pull/6936) update tracing libraries for opentracing 1.6.0 -- [X] [#6908](https://github.com/kubernetes/ingress-nginx/pull/6908) feat(chart) Add volumes to default-backend deployment #6908 -- [X] [#6884](https://github.com/kubernetes/ingress-nginx/pull/6884) jaeger-endpoint feature for non-agent trace collectors -- [X] [#6856](https://github.com/kubernetes/ingress-nginx/pull/6856) Allow multiple publish status addresses -- [X] [#6971](https://github.com/kubernetes/ingress-nginx/pull/6971) Fix bug related to CRL update - -### 0.44.0 - -**Image:** - -- `k8s.gcr.io/ingress-nginx/controller:v0.44.0@sha256:3dd0fac48073beaca2d67a78c746c7593f9c575168a17139a9955a82c63c4b9a` - -_New Features:_ - -- Update alpine to v3.13 -- client-go v0.20.2 -- New option to set a shutdown grace period [#5855](https://github.com/kubernetes/ingress-nginx/pull/5855) -- Support for Global/Distributed Rate Limiting [#6673](https://github.com/kubernetes/ingress-nginx/pull/6673 -- Update kube-webhook-certgen image to v1.5.1 - -_Changes:_ - -- [X] [#5855](https://github.com/kubernetes/ingress-nginx/pull/5855) New option to set a shutdown grace period -- [X] [#6530](https://github.com/kubernetes/ingress-nginx/pull/6530) #6477 Allow specifying the loadBalancerIP for the internal load balancer -- [X] [#6667](https://github.com/kubernetes/ingress-nginx/pull/6667) Correct the value for setting a static IP -- [X] [#6669](https://github.com/kubernetes/ingress-nginx/pull/6669) chore: Add test to internal ingress resolver pkg -- [X] [#6673](https://github.com/kubernetes/ingress-nginx/pull/6673) Add Global/Distributed Rate Limiting support -- [X] [#6679](https://github.com/kubernetes/ingress-nginx/pull/6679) Bugfix: fix incomplete log -- [X] [#6695](https://github.com/kubernetes/ingress-nginx/pull/6695) include lua-resty-ipmatcher and lua-resty-global-throttle inn the base image -- [X] [#6705](https://github.com/kubernetes/ingress-nginx/pull/6705) Update nginx alpine image to 3.12 -- [X] [#6708](https://github.com/kubernetes/ingress-nginx/pull/6708) fix generated code for the new year -- [X] [#6710](https://github.com/kubernetes/ingress-nginx/pull/6710) Update nginx base image -- [X] [#6711](https://github.com/kubernetes/ingress-nginx/pull/6711) Update test container images -- [X] [#6712](https://github.com/kubernetes/ingress-nginx/pull/6712) Update tag version -- [X] [#6717](https://github.com/kubernetes/ingress-nginx/pull/6717) fix ipmatcher installation -- [X] [#6718](https://github.com/kubernetes/ingress-nginx/pull/6718) generalize cidr parsing and improve lua tests -- [X] [#6719](https://github.com/kubernetes/ingress-nginx/pull/6719) Update nginx image -- [X] [#6720](https://github.com/kubernetes/ingress-nginx/pull/6720) Update test runner image -- [X] [#6724](https://github.com/kubernetes/ingress-nginx/pull/6724) e2e test for requiring memcached setting to configure global rate limit -- [X] [#6726](https://github.com/kubernetes/ingress-nginx/pull/6726) add body_filter_by_lua_block lua plugin to ingress-nginx -- [X] [#6730](https://github.com/kubernetes/ingress-nginx/pull/6730) Do not create HPA if default backend not enabled -- [X] [#6754](https://github.com/kubernetes/ingress-nginx/pull/6754) Fix KEDA autoscaler resource -- [X] [#6756](https://github.com/kubernetes/ingress-nginx/pull/6756) Dashboard Panel supposed to show average is showing sum. -- [X] [#6760](https://github.com/kubernetes/ingress-nginx/pull/6760) Update alpine to 3.13 -- [X] [#6761](https://github.com/kubernetes/ingress-nginx/pull/6761) Adding quotes in the serviceAccount name in Helm values. -- [X] [#6764](https://github.com/kubernetes/ingress-nginx/pull/6764) Update nginx image -- [X] [#6767](https://github.com/kubernetes/ingress-nginx/pull/6767) Remove ClusterRole when scope option is enabled -- [X] [#6783](https://github.com/kubernetes/ingress-nginx/pull/6783) Add custom annotations to ScaledObject #6757 -- [X] [#6785](https://github.com/kubernetes/ingress-nginx/pull/6785) Update kube-webhook-certgen image to v1.5.1 -- [X] [#6786](https://github.com/kubernetes/ingress-nginx/pull/6786) Release helm chart v3.21.0 -- [X] [#6787](https://github.com/kubernetes/ingress-nginx/pull/6787) Update static manifests -- [X] [#6788](https://github.com/kubernetes/ingress-nginx/pull/6788) Update go dependencies -- [X] [#6790](https://github.com/kubernetes/ingress-nginx/pull/6790) :bug: return error if tempconfig missing -- [X] [#6796](https://github.com/kubernetes/ingress-nginx/pull/6796) Updates to the custom default SSL certificate must trigger a reload -- [X] [#6802](https://github.com/kubernetes/ingress-nginx/pull/6802) Add value for configuring a custom Diffie-Hellman parameters file -- [X] [#6811](https://github.com/kubernetes/ingress-nginx/pull/6811) add --status-port flag to dbg -- [X] [#6815](https://github.com/kubernetes/ingress-nginx/pull/6815) Allow use of numeric namespaces in helm chart -- [X] [#6817](https://github.com/kubernetes/ingress-nginx/pull/6817) corrected nginx configuration doc path -- [X] [#6818](https://github.com/kubernetes/ingress-nginx/pull/6818) Release helm chart v3.22.0 -- [X] [#6819](https://github.com/kubernetes/ingress-nginx/pull/6819) Update kind and kindest images -- [X] [#6830](https://github.com/kubernetes/ingress-nginx/pull/6830) Remove extra comma for Tracing Jaeger config json -- [X] [#6832](https://github.com/kubernetes/ingress-nginx/pull/6832) Fix e2e build -- [X] [#6842](https://github.com/kubernetes/ingress-nginx/pull/6842) Change chart-testing image - -_Documentation:_ - -- [X] [#6723](https://github.com/kubernetes/ingress-nginx/pull/6723) fix link in annotation docs -- [X] [#6727](https://github.com/kubernetes/ingress-nginx/pull/6727) Fix the documentation for the proxy-ssl-secret and the auth-tls-secret annotations -- [X] [#6738](https://github.com/kubernetes/ingress-nginx/pull/6738) docs/deploy: fix grammar and inconsistencies -- [X] [#6741](https://github.com/kubernetes/ingress-nginx/pull/6741) Update mkdocs, fix nodeport link and add microk8s link -- [X] [#6746](https://github.com/kubernetes/ingress-nginx/pull/6746) Move Azure deploy note to right item on doc page -- [X] [#6749](https://github.com/kubernetes/ingress-nginx/pull/6749) Update README.md -- [X] [#6789](https://github.com/kubernetes/ingress-nginx/pull/6789) Update e2e tests link markdown -- [X] [#6813](https://github.com/kubernetes/ingress-nginx/pull/6813) Added docs to clear up PROXY definition -- [X] [#6823](https://github.com/kubernetes/ingress-nginx/pull/6823) Change break link for documentation - -### 0.43.0 - -**Image:** - -- `k8s.gcr.io/ingress-nginx/controller:v0.43.0@sha256:9bba603b99bf25f6d117cf1235b6598c16033ad027b143c90fa5b3cc583c5713` - -_New Features:_ - -- Support local GeoIP database mirror [#6685](https://github.com/kubernetes/ingress-nginx/pull/6685) - -_Changes:_ - -- [X] [#6676](https://github.com/kubernetes/ingress-nginx/pull/6676) include new resty lua libs in base image -- [X] [#6680](https://github.com/kubernetes/ingress-nginx/pull/6680) Update cloudbuild gcb-docker-gcloud image -- [X] [#6682](https://github.com/kubernetes/ingress-nginx/pull/6682) Update nginx image -- [X] [#6683](https://github.com/kubernetes/ingress-nginx/pull/6683) Remove dead code -- [X] [#6684](https://github.com/kubernetes/ingress-nginx/pull/6684) Update ingress-nginx test image -- [X] [#6685](https://github.com/kubernetes/ingress-nginx/pull/6685) Add GeoIP Local mirror support -- [X] [#6688](https://github.com/kubernetes/ingress-nginx/pull/6688) feat: allow volume-type emptyDir in controller podsecuritypolicy -- [X] [#6691](https://github.com/kubernetes/ingress-nginx/pull/6691) Helm: Ingress config change -- [X] [#6692](https://github.com/kubernetes/ingress-nginx/pull/6692) add string split function to template funcMap -- [X] [#6694](https://github.com/kubernetes/ingress-nginx/pull/6694) Release helm chart - -### 0.42.0 - -**Image:** - -- `k8s.gcr.io/ingress-nginx/controller:v0.42.0@sha256:f7187418c647af4a0039938b0ab36c2322ac3662d16be69f9cc178bfd25f7eee` - -_New Features:_ - -- NGINX 1.19.6 -- Go 1.15.6 -- client-go v0.20.0 -- Support [Keda Autoscaling](https://github.com/kubernetes/ingress-nginx/pull/6493) in helm chart -- Support custom redirect URL parameter in external authentication [#6294](https://github.com/kubernetes/ingress-nginx/pull/6294) - -_Changes:_ - -- [X] [#6294](https://github.com/kubernetes/ingress-nginx/pull/6294) Allow customisation of redirect URL parameter in external auth redirects -- [X] [#6461](https://github.com/kubernetes/ingress-nginx/pull/6461) Update kind github action -- [X] [#6469](https://github.com/kubernetes/ingress-nginx/pull/6469) Allow custom service names for controller and backend (#6457) -- [X] [#6470](https://github.com/kubernetes/ingress-nginx/pull/6470) Added role binding for 'ingress-nginx-admission' to PSP example (#6018) -- [X] [#6473](https://github.com/kubernetes/ingress-nginx/pull/6473) Enable external auth e2e tests -- [X] [#6480](https://github.com/kubernetes/ingress-nginx/pull/6480) Refactor extraction of ingress pod details -- [X] [#6485](https://github.com/kubernetes/ingress-nginx/pull/6485) Fix sum value of nginx process connections -- [X] [#6493](https://github.com/kubernetes/ingress-nginx/pull/6493) Support Keda Autoscaling -- [X] [#6499](https://github.com/kubernetes/ingress-nginx/pull/6499) Fix opentracing propagation on auth-url -- [X] [#6505](https://github.com/kubernetes/ingress-nginx/pull/6505) Reorder HPA resource list to work with GitOps tooling -- [X] [#6514](https://github.com/kubernetes/ingress-nginx/pull/6514) Remove helm2 support and update docs -- [X] [#6526](https://github.com/kubernetes/ingress-nginx/pull/6526) Fix helm repo update command -- [X] [#6529](https://github.com/kubernetes/ingress-nginx/pull/6529) Fix ErrorLogLevel in stream contexts -- [X] [#6533](https://github.com/kubernetes/ingress-nginx/pull/6533) Update nginx to 1.19.5 -- [X] [#6544](https://github.com/kubernetes/ingress-nginx/pull/6544) Fix the name of default backend variable -- [X] [#6546](https://github.com/kubernetes/ingress-nginx/pull/6546) bugfix: update trafficShapingPolicy not working in ewma load-balance -- [X] [#6550](https://github.com/kubernetes/ingress-nginx/pull/6550) Ensure any change in the charts directory trigger ci tests -- [X] [#6553](https://github.com/kubernetes/ingress-nginx/pull/6553) fixes: allow user to specify the maxmium number of retries in stream block -- [X] [#6558](https://github.com/kubernetes/ingress-nginx/pull/6558) Update kindest image -- [X] [#6560](https://github.com/kubernetes/ingress-nginx/pull/6560) Fix nginx ingress variables for definitions without hosts -- [X] [#6561](https://github.com/kubernetes/ingress-nginx/pull/6561) Disable HTTP/2 in the webhook server -- [X] [#6571](https://github.com/kubernetes/ingress-nginx/pull/6571) Add gosec action -- [X] [#6574](https://github.com/kubernetes/ingress-nginx/pull/6574) Release helm chart v3.13.0 -- [X] [#6576](https://github.com/kubernetes/ingress-nginx/pull/6576) Fix nginx ingress variables for definitions with Backend -- [X] [#6577](https://github.com/kubernetes/ingress-nginx/pull/6577) Update build TAG -- [X] [#6578](https://github.com/kubernetes/ingress-nginx/pull/6578) Update helm chart-testing image -- [X] [#6580](https://github.com/kubernetes/ingress-nginx/pull/6580) fix for 6564 -- [X] [#6586](https://github.com/kubernetes/ingress-nginx/pull/6586) fix(chart): Move 'maxmindLicenseKey' to `controller.maxmindLicenseKey` -- [X] [#6587](https://github.com/kubernetes/ingress-nginx/pull/6587) feat(nginx.tmpl): Add support for GeoLite2-Country and GeoIP2-Country databases -- [X] [#6592](https://github.com/kubernetes/ingress-nginx/pull/6592) Update github actions -- [X] [#6593](https://github.com/kubernetes/ingress-nginx/pull/6593) Rollback chart-releaser action -- [X] [#6594](https://github.com/kubernetes/ingress-nginx/pull/6594) Fix chart-releaser action -- [X] [#6595](https://github.com/kubernetes/ingress-nginx/pull/6595) Fix helm chart releaser action -- [X] [#6596](https://github.com/kubernetes/ingress-nginx/pull/6596) Fix helm chart releaser action -- [X] [#6600](https://github.com/kubernetes/ingress-nginx/pull/6600) Bugfix: some requests fail with 503 when nginx reload -- [X] [#6607](https://github.com/kubernetes/ingress-nginx/pull/6607) fix flaky lua tests -- [X] [#6608](https://github.com/kubernetes/ingress-nginx/pull/6608) make sure canary attributes are reset on ewma backend sync -- [X] [#6614](https://github.com/kubernetes/ingress-nginx/pull/6614) Refactor ingress nginx variables -- [X] [#6617](https://github.com/kubernetes/ingress-nginx/pull/6617) Allow FQDN for ExternalName Service -- [X] [#6620](https://github.com/kubernetes/ingress-nginx/pull/6620) Fix sticky session not set for host in server-alias annotation (#6448) -- [X] [#6621](https://github.com/kubernetes/ingress-nginx/pull/6621) Update go dependencies -- [X] [#6627](https://github.com/kubernetes/ingress-nginx/pull/6627) Update nginx to 1.19.6 -- [X] [#6628](https://github.com/kubernetes/ingress-nginx/pull/6628) Update nginx image -- [X] [#6629](https://github.com/kubernetes/ingress-nginx/pull/6629) Add kind e2e tests support for k8s v1.20.0 -- [X] [#6635](https://github.com/kubernetes/ingress-nginx/pull/6635) Update test images and go to 1.15.6 -- [X] [#6638](https://github.com/kubernetes/ingress-nginx/pull/6638) Update test images -- [X] [#6639](https://github.com/kubernetes/ingress-nginx/pull/6639) Don't pick tried endpoint & count the latest in ewma balancer -- [X] [#6646](https://github.com/kubernetes/ingress-nginx/pull/6646) Adding LoadBalancerIP value for internal service to Helm chart -- [X] [#6652](https://github.com/kubernetes/ingress-nginx/pull/6652) Change helm chart tag name to disambiguate purpose -- [X] [#6660](https://github.com/kubernetes/ingress-nginx/pull/6660) Fix chart-releaser action - -_Documentation:_ - -- [X] [#6481](https://github.com/kubernetes/ingress-nginx/pull/6481) docs(annotations): explicit redirect status code -- [X] [#6486](https://github.com/kubernetes/ingress-nginx/pull/6486) Fix typo -- [X] [#6528](https://github.com/kubernetes/ingress-nginx/pull/6528) Spelling -- [X] [#6494](https://github.com/kubernetes/ingress-nginx/pull/6494) Update development.md with docker version and experimental feature requirment -- [X] [#6501](https://github.com/kubernetes/ingress-nginx/pull/6501) Add Chart changelog instructions -- [X] [#6541](https://github.com/kubernetes/ingress-nginx/pull/6541) fixed misspell -- [X] [#6551](https://github.com/kubernetes/ingress-nginx/pull/6551) Add documentation to activate DHE based ciphers -- [X] [#6566](https://github.com/kubernetes/ingress-nginx/pull/6566) fix docs log-format-upstream sample -- [X] [#6579](https://github.com/kubernetes/ingress-nginx/pull/6579) Update README.md -- [X] [#6598](https://github.com/kubernetes/ingress-nginx/pull/6598) Add a link to the helm ingress-nginx `CHANGELOG.md` file to the `README.md` file -- [X] [#6623](https://github.com/kubernetes/ingress-nginx/pull/6623) fix typo -- [X] [#6636](https://github.com/kubernetes/ingress-nginx/pull/6636) Fix link to kustomize docs -- [X] [#6642](https://github.com/kubernetes/ingress-nginx/pull/6642) Update README.md -- [X] [#6665](https://github.com/kubernetes/ingress-nginx/pull/6665) added AKS specific documentation - -### 0.41.2 - -**Image:** - -- `k8s.gcr.io/ingress-nginx/controller:v0.41.2@sha256:1f4f402b9c14f3ae92b11ada1dfe9893a88f0faeb0b2f4b903e2c67a0c3bf0de` - -Fix regression introduced in 0.41.0 with external authentication - -_Changes:_ - -- [X] [#6467](https://github.com/kubernetes/ingress-nginx/pull/6467) Add PathType details in external auth location - -### 0.41.1 - -**Image:** - -- `k8s.gcr.io/ingress-nginx/controller:v0.41.1@sha256:595f5c08aaa2bdfd1afdfb2e0f1a668bc85d96f80c097ddb3d4241f0c9122549` - -Fix routing regression introduced in 0.41.0 with PathType Exact - -_Changes:_ - -- [X] [#6417](https://github.com/kubernetes/ingress-nginx/pull/6417) Reload nginx when L4 proxy protocol change -- [X] [#6422](https://github.com/kubernetes/ingress-nginx/pull/6422) Add comment indicating server-snippet section -- [X] [#6423](https://github.com/kubernetes/ingress-nginx/pull/6423) Add Default backend HPA autoscaling. -- [X] [#6426](https://github.com/kubernetes/ingress-nginx/pull/6426) Alternate to respecting setting admissionWebhooks.failurePolicy in values.yaml -- [X] [#6443](https://github.com/kubernetes/ingress-nginx/pull/6443) Refactor handling of path Prefix and Exact -- [X] [#6445](https://github.com/kubernetes/ingress-nginx/pull/6445) fix: empty IngressClassName, Error handling -- [X] [#6447](https://github.com/kubernetes/ingress-nginx/pull/6447) Improve class.IsValid logs - -### 0.41.0 - -**Image:** - -- `k8s.gcr.io/ingress-nginx/controller:v0.41.0@sha256:e6019e536cfb921afb99408d5292fa88b017c49dd29d05fc8dbc456aa770d590` - -_New Features:_ - -- NGINX 1.19.4 -- Go 1.15.3 -- client-go v0.19.3 -- alpine 3.12 -- jettech/kube-webhook-certgen v1.5.0 - -_Changes:_ - -- [X] [#6037](https://github.com/kubernetes/ingress-nginx/pull/6037) Do not append a trailing slash on redirects -- [X] [#6255](https://github.com/kubernetes/ingress-nginx/pull/6255) Update datadog opentracing plugin to v1.2.0 -- [X] [#6260](https://github.com/kubernetes/ingress-nginx/pull/6260) Allow Helm Chart to customize admission webhook's annotations, timeoutSeconds, namespaceSelector, objectSelector and cert files locations -- [X] [#6261](https://github.com/kubernetes/ingress-nginx/pull/6261) Add datadog environment as a configuration option -- [X] [#6268](https://github.com/kubernetes/ingress-nginx/pull/6268) Update helm chart -- [X] [#6282](https://github.com/kubernetes/ingress-nginx/pull/6282) Enable e2e tests for k8s v1.16 -- [X] [#6283](https://github.com/kubernetes/ingress-nginx/pull/6283) Start v0.41.0 cycle -- [X] [#6299](https://github.com/kubernetes/ingress-nginx/pull/6299) Fix helm chart release -- [X] [#6304](https://github.com/kubernetes/ingress-nginx/pull/6304) Update nginx image -- [X] [#6305](https://github.com/kubernetes/ingress-nginx/pull/6305) Add default linux nodeSelector -- [X] [#6316](https://github.com/kubernetes/ingress-nginx/pull/6316) Numerals in podAnnotations in quotes #6315 -- [X] [#6319](https://github.com/kubernetes/ingress-nginx/pull/6319) Update static manifests -- [X] [#6325](https://github.com/kubernetes/ingress-nginx/pull/6325) Filter out secrets that belong to Helm v3 -- [X] [#6326](https://github.com/kubernetes/ingress-nginx/pull/6326) Fix liveness and readiness probe path in daemonset chart -- [X] [#6331](https://github.com/kubernetes/ingress-nginx/pull/6331) fix for 6219 -- [X] [#6348](https://github.com/kubernetes/ingress-nginx/pull/6348) Add validation for wildcard server names -- [X] [#6349](https://github.com/kubernetes/ingress-nginx/pull/6349) Refactor Exact path matching -- [X] [#6356](https://github.com/kubernetes/ingress-nginx/pull/6356) Add securitycontext settings on defaultbackend -- [X] [#6366](https://github.com/kubernetes/ingress-nginx/pull/6366) Enable validation of ingress definitions from extensions package -- [X] [#6372](https://github.com/kubernetes/ingress-nginx/pull/6372) Check pod is ready -- [X] [#6373](https://github.com/kubernetes/ingress-nginx/pull/6373) Remove k8s.io/kubernetes dependency -- [X] [#6375](https://github.com/kubernetes/ingress-nginx/pull/6375) Improve log messages -- [X] [#6377](https://github.com/kubernetes/ingress-nginx/pull/6377) Added loadBalancerSourceRanges for internal lbs -- [X] [#6382](https://github.com/kubernetes/ingress-nginx/pull/6382) fix: OWASP CoreRuleSet rules for NodeJS and Java -- [X] [#6383](https://github.com/kubernetes/ingress-nginx/pull/6383) Update nginx to 1.19.4 -- [X] [#6384](https://github.com/kubernetes/ingress-nginx/pull/6384) Update nginx image to 1.19.4 -- [X] [#6385](https://github.com/kubernetes/ingress-nginx/pull/6385) Update helm stable repo -- [X] [#6388](https://github.com/kubernetes/ingress-nginx/pull/6388) Update nginx image in project images -- [X] [#6389](https://github.com/kubernetes/ingress-nginx/pull/6389) Support prefix pathtype -- [X] [#6390](https://github.com/kubernetes/ingress-nginx/pull/6390) Update go to 1.15.3 -- [X] [#6391](https://github.com/kubernetes/ingress-nginx/pull/6391) Update alpine packages -- [X] [#6392](https://github.com/kubernetes/ingress-nginx/pull/6392) Update test images -- [X] [#6395](https://github.com/kubernetes/ingress-nginx/pull/6395) Update jettech/kube-webhook-certgen image -- [X] [#6401](https://github.com/kubernetes/ingress-nginx/pull/6401) Fix controller service annotations -- [X] [#6412](https://github.com/kubernetes/ingress-nginx/pull/6412) Improve ingress class error message - -_Documentation:_ - -- [X] [#6272](https://github.com/kubernetes/ingress-nginx/pull/6272) Update hardening guide doc -- [X] [#6278](https://github.com/kubernetes/ingress-nginx/pull/6278) Sync user guide with config defaults changes -- [X] [#6321](https://github.com/kubernetes/ingress-nginx/pull/6321) Fix typo -- [X] [#6403](https://github.com/kubernetes/ingress-nginx/pull/6403) Initial helm chart changelog - -### 0.40.2 - -**Image:** - -- `k8s.gcr.io/ingress-nginx/controller:v0.40.2@sha256:46ba23c3fbaafd9e5bd01ea85b2f921d9f2217be082580edc22e6c704a83f02f` - -Improve HandleAdmission resiliency - -_Changes:_ - -- [X] [#6284](https://github.com/kubernetes/ingress-nginx/pull/6284) Improve HandleAdmission resiliency - -### 0.40.1 - -**Image:** - -- `k8s.gcr.io/ingress-nginx/controller:v0.40.1@sha256:abffcf2d25e3e7c7b67a315a7c664ec79a1588c9c945d3c7a75637c2f55caec6` - -Fix regression with clusters running v1.16 where AdmissionReview V1 is available but not enabled. - -_Changes:_ - -- [X] [#6265](https://github.com/kubernetes/ingress-nginx/pull/6265) Add support for admission review v1beta1 - - -### 0.40.0 - -**Image:** - -- `k8s.gcr.io/ingress-nginx/controller:v0.40.0@sha256:b954d8ff1466eb236162c644bd64e9027a212c82b484cbe47cc21da45fe8bc59` - -_Breaking Changes:_ - -Kubernetes v1.16 or higher is required. -Only ValidatingWebhookConfiguration AdmissionReviewVersions v1 is supported. - -Following the [Ingress extensions/v1beta1](https://kubernetes.io/blog/2019/07/18/api-deprecations-in-1-16) deprecation, please use `networking.k8s.io/v1beta1` or `networking.k8s.io/v1` (Kubernetes v1.19 or higher) for new Ingress definitions - - -_New Features:_ - -- NGINX 1.19.3 -- Go 1.15.2 -- client-go v0.19.2 -- New annotation `nginx.ingress.kubernetes.io/limit-burst-multiplier` to set value for burst multiplier on rate limit -- Switch to [structured logging](https://github.com/kubernetes/enhancements/tree/master/keps/sig-instrumentation/1602-structured-logging) -- NGINX reloads create Kubernetes events - - -_New defaults:_ - -- [server-tokens](https://kubernetes.github.io/ingress-nginx/user-guide/nginx-configuration/configmap/#server-tokens) is disabled -- [ssl-session-tickets](https://kubernetes.github.io/ingress-nginx/user-guide/nginx-configuration/configmap/#ssl-session-tickets) is disabled -- [use-gzip](https://kubernetes.github.io/ingress-nginx/user-guide/nginx-configuration/configmap/#use-gzip) is disabled -- [upstream-keepalive-requests](https://kubernetes.github.io/ingress-nginx/user-guide/nginx-configuration/configmap/#upstream-keepalive-requests) is now 10000 -- [upstream-keepalive-connections](https://kubernetes.github.io/ingress-nginx/user-guide/nginx-configuration/configmap/#upstream-keepalive-connections) is now 320 - - -_Changes:_ - -- [X] [#5348](https://github.com/kubernetes/ingress-nginx/pull/5348) Ability to separately disable access log in http and stream contexts -- [X] [#6087](https://github.com/kubernetes/ingress-nginx/pull/6087) Adding parameter for externalTrafficPolicy in internal controller service spec. -- [X] [#6097](https://github.com/kubernetes/ingress-nginx/pull/6097) Return unique addresses from service -- [X] [#6098](https://github.com/kubernetes/ingress-nginx/pull/6098) Update kubernetes kind e2e versions -- [X] [#6099](https://github.com/kubernetes/ingress-nginx/pull/6099) Update go dependencies -- [X] [#6101](https://github.com/kubernetes/ingress-nginx/pull/6101) Add annotation to set value for burst multiplier on rate limit -- [X] [#6104](https://github.com/kubernetes/ingress-nginx/pull/6104) Misc fixes for nginx-ingress chart for better keel and prom-oper -- [X] [#6111](https://github.com/kubernetes/ingress-nginx/pull/6111) Update kind node version to v1.19.0 -- [X] [#6112](https://github.com/kubernetes/ingress-nginx/pull/6112) Update go dependencies to fix build logr errors -- [X] [#6113](https://github.com/kubernetes/ingress-nginx/pull/6113) Require Kubernetes v1.14 or higher and deprecate extensions -- [X] [#6114](https://github.com/kubernetes/ingress-nginx/pull/6114) Update go to 1.5.1 and add arm64 -- [X] [#6115](https://github.com/kubernetes/ingress-nginx/pull/6115) Increase cloudbuild timeout value -- [X] [#6116](https://github.com/kubernetes/ingress-nginx/pull/6116) Update e2e image -- [X] [#6118](https://github.com/kubernetes/ingress-nginx/pull/6118) Cleanup github actions -- [X] [#6120](https://github.com/kubernetes/ingress-nginx/pull/6120) Use net.JoinHostPort to avoid IPV6 issues -- [X] [#6122](https://github.com/kubernetes/ingress-nginx/pull/6122) Update trace modules -- [X] [#6123](https://github.com/kubernetes/ingress-nginx/pull/6123) Add e2e tests to verify opentracing libraries -- [X] [#6125](https://github.com/kubernetes/ingress-nginx/pull/6125) Library dd-opentracing cannot be static -- [X] [#6129](https://github.com/kubernetes/ingress-nginx/pull/6129) Update test runner image -- [X] [#6143](https://github.com/kubernetes/ingress-nginx/pull/6143) Update default gzip level -- [X] [#6145](https://github.com/kubernetes/ingress-nginx/pull/6145) Switch modules to dynamic and remove http_dav_module -- [X] [#6146](https://github.com/kubernetes/ingress-nginx/pull/6146) Use dynamic load of modules -- [X] [#6148](https://github.com/kubernetes/ingress-nginx/pull/6148) Update cloudbuild jobs -- [X] [#6149](https://github.com/kubernetes/ingress-nginx/pull/6149) Update qemu-user-static image -- [X] [#6150](https://github.com/kubernetes/ingress-nginx/pull/6150) Reject ingresses that use the default annotation if a custom one was provided -- [X] [#6166](https://github.com/kubernetes/ingress-nginx/pull/6166) Update kind and kindest/node images -- [X] [#6167](https://github.com/kubernetes/ingress-nginx/pull/6167) Update chart requirements -- [X] [#6170](https://github.com/kubernetes/ingress-nginx/pull/6170) delete redundant NGINX config about X-Forwarded-Proto -- [X] [#6172](https://github.com/kubernetes/ingress-nginx/pull/6172) Update OSFileWatcher to support symlinks -- [X] [#6176](https://github.com/kubernetes/ingress-nginx/pull/6176) Update go modules -- [X] [#6184](https://github.com/kubernetes/ingress-nginx/pull/6184) Update static manifest yaml files -- [X] [#6186](https://github.com/kubernetes/ingress-nginx/pull/6186) Fix logr dependency issue -- [X] [#6187](https://github.com/kubernetes/ingress-nginx/pull/6187) Add validation support for networking.k8s.io/v1 -- [X] [#6190](https://github.com/kubernetes/ingress-nginx/pull/6190) Change server-tokens default value to false -- [X] [#6196](https://github.com/kubernetes/ingress-nginx/pull/6196) disable session tickets by default -- [X] [#6198](https://github.com/kubernetes/ingress-nginx/pull/6198) Delete OCSP Response cache when certificate renewed -- [X] [#6200](https://github.com/kubernetes/ingress-nginx/pull/6200) Move ocsp_response_cache:delete after certificate_data:set -- [X] [#6203](https://github.com/kubernetes/ingress-nginx/pull/6203) Refactor key/value parsing -- [X] [#6211](https://github.com/kubernetes/ingress-nginx/pull/6211) Migrate to structured logging (klog) -- [X] [#6217](https://github.com/kubernetes/ingress-nginx/pull/6217) Add annotation to configure CORS Access-Control-Expose-Headers -- [X] [#6226](https://github.com/kubernetes/ingress-nginx/pull/6226) Change defaults -- [X] [#6231](https://github.com/kubernetes/ingress-nginx/pull/6231) Clear redundant Cross-Origin-Allow- headers from response -- [X] [#6233](https://github.com/kubernetes/ingress-nginx/pull/6233) Add admission controller e2e test -- [X] [#6234](https://github.com/kubernetes/ingress-nginx/pull/6234) Add events for NGINX reloads -- [X] [#6235](https://github.com/kubernetes/ingress-nginx/pull/6235) Update go dependencies - -_Documentation:_ - -- [X] [#5757](https://github.com/kubernetes/ingress-nginx/pull/5757) feat: support to define trusted addresses for proxy protocol in stream block -- [X] [#5881](https://github.com/kubernetes/ingress-nginx/pull/5881) Doc: Adding initial hardening guide -- [X] [#6109](https://github.com/kubernetes/ingress-nginx/pull/6109) Fix documentation table layout -- [X] [#6127](https://github.com/kubernetes/ingress-nginx/pull/6127) AKS example of adding an internal loadbalancer -- [X] [#6128](https://github.com/kubernetes/ingress-nginx/pull/6128) Fixed proxy protocol link -- [X] [#6130](https://github.com/kubernetes/ingress-nginx/pull/6130) Update deploy instructions with corrections -- [X] [#6153](https://github.com/kubernetes/ingress-nginx/pull/6153) Add install command for Scaleway -- [X] [#6154](https://github.com/kubernetes/ingress-nginx/pull/6154) chart: add `topologySpreadConstraint` to controller -- [X] [#6162](https://github.com/kubernetes/ingress-nginx/pull/6162) Add helm chart options to expose metrics service as NodePort -- [X] [#6169](https://github.com/kubernetes/ingress-nginx/pull/6169) Fix Typo in example prometheus rules -- [X] [#6171](https://github.com/kubernetes/ingress-nginx/pull/6171) Docs: remove redundant --election-id arg from Multiple Ingresses -- [X] [#6177](https://github.com/kubernetes/ingress-nginx/pull/6177) Fix make help task to display options -- [X] [#6180](https://github.com/kubernetes/ingress-nginx/pull/6180) Fix helm chart admissionReviewVersions regression -- [X] [#6181](https://github.com/kubernetes/ingress-nginx/pull/6181) Improve prerequisite instructions -- [X] [#6214](https://github.com/kubernetes/ingress-nginx/pull/6214) Update annotations.md - improvements to the documentation of Client Certificate Authentication -- [X] [#6215](https://github.com/kubernetes/ingress-nginx/pull/6215) Update the comment for Makefile taks live-docs -- [X] [#6221](https://github.com/kubernetes/ingress-nginx/pull/6221) corrected reference for release - - -### 0.35.0 - -**Image:** - -- `k8s.gcr.io/ingress-nginx/controller:v0.35.0@sha256:fc4979d8b8443a831c9789b5155cded454cb7de737a8b727bc2ba0106d2eae8b` - -_New Features:_ - -- NGINX 1.19.2 -- New configmap option `enable-real-ip` to enable [realip_module](https://nginx.org/en/docs/http/ngx_http_realip_module.html) -- Use k8s.gcr.io vanity domain -- Go 1.15 -- client-go v0.18.6 -- Migrate to klog v2 - -_Changes:_ - -- [X] [#5887](https://github.com/kubernetes/ingress-nginx/pull/5887) Add force-enable-realip-module -- [X] [#5888](https://github.com/kubernetes/ingress-nginx/pull/5888) Update dev-env.sh script -- [X] [#5923](https://github.com/kubernetes/ingress-nginx/pull/5923) Fix error in grpcbin deployment and enable e2e test -- [X] [#5924](https://github.com/kubernetes/ingress-nginx/pull/5924) Validate endpoints are ready in e2e tests -- [X] [#5931](https://github.com/kubernetes/ingress-nginx/pull/5931) Add opentracing operation name settings -- [X] [#5933](https://github.com/kubernetes/ingress-nginx/pull/5933) Update opentracing nginx module -- [X] [#5946](https://github.com/kubernetes/ingress-nginx/pull/5946) Do not add namespace to cluster-scoped resources -- [X] [#5951](https://github.com/kubernetes/ingress-nginx/pull/5951) Use env expansion to provide namespace in container args -- [X] [#5952](https://github.com/kubernetes/ingress-nginx/pull/5952) Refactor shutdown e2e tests -- [X] [#5957](https://github.com/kubernetes/ingress-nginx/pull/5957) bump fsnotify to v1.4.9 -- [X] [#5958](https://github.com/kubernetes/ingress-nginx/pull/5958) Disable enable-access-log-for-default-backend e2e test -- [X] [#5984](https://github.com/kubernetes/ingress-nginx/pull/5984) Fix panic in ingress class validation -- [X] [#5986](https://github.com/kubernetes/ingress-nginx/pull/5986) Migrate to klog v2 -- [X] [#5987](https://github.com/kubernetes/ingress-nginx/pull/5987) Fix wait times in e2e tests -- [X] [#5990](https://github.com/kubernetes/ingress-nginx/pull/5990) Fix nginx command env variable reference -- [X] [#6004](https://github.com/kubernetes/ingress-nginx/pull/6004) Update nginx to 1.19.2 -- [X] [#6006](https://github.com/kubernetes/ingress-nginx/pull/6006) Update nginx image -- [X] [#6007](https://github.com/kubernetes/ingress-nginx/pull/6007) Update e2e-test-runner image -- [X] [#6008](https://github.com/kubernetes/ingress-nginx/pull/6008) Rollback update of Jaeger library to 0.5.0 and update datadog to 1.2.0 -- [X] [#6014](https://github.com/kubernetes/ingress-nginx/pull/6014) Update go dependencies -- [X] [#6039](https://github.com/kubernetes/ingress-nginx/pull/6039) Add configurable serviceMonitor metricRelabelling and targetLabels -- [X] [#6046](https://github.com/kubernetes/ingress-nginx/pull/6046) Add new Dockerfile label org.opencontainers.image.revision -- [X] [#6047](https://github.com/kubernetes/ingress-nginx/pull/6047) Increase wait times in e2e tests -- [X] [#6049](https://github.com/kubernetes/ingress-nginx/pull/6049) Improve docs and logging for --ingress-class usage -- [X] [#6052](https://github.com/kubernetes/ingress-nginx/pull/6052) Fix flaky e2e test -- [X] [#6056](https://github.com/kubernetes/ingress-nginx/pull/6056) Rollback to Poll instead of PollImmediate -- [X] [#6062](https://github.com/kubernetes/ingress-nginx/pull/6062) Adjust e2e timeouts -- [X] [#6063](https://github.com/kubernetes/ingress-nginx/pull/6063) Remove file system paths executables -- [X] [#6080](https://github.com/kubernetes/ingress-nginx/pull/6080) Use k8s.gcr.io vanity domain - -_Documentation:_ - -- [X] [#5911](https://github.com/kubernetes/ingress-nginx/pull/5911) Change image URL after switching to gcr.io in upgrade guide -- [X] [#5926](https://github.com/kubernetes/ingress-nginx/pull/5926) fixed some typos -- [X] [#5927](https://github.com/kubernetes/ingress-nginx/pull/5927) Simplify development doc -- [X] [#5942](https://github.com/kubernetes/ingress-nginx/pull/5942) Fix default backend flaking e2e test for default -- [X] [#5943](https://github.com/kubernetes/ingress-nginx/pull/5943) Add repo SECURITY.md -- [X] [#5965](https://github.com/kubernetes/ingress-nginx/pull/5965) feat(baremetal): Add kustomization.yaml -- [X] [#5971](https://github.com/kubernetes/ingress-nginx/pull/5971) Fixed typo "permanen" -- [X] [#5980](https://github.com/kubernetes/ingress-nginx/pull/5980) fix for 5590 -- [X] [#5994](https://github.com/kubernetes/ingress-nginx/pull/5994) Clean up minikube installation instructions -- [X] [#6000](https://github.com/kubernetes/ingress-nginx/pull/6000) Fix error message formatting -- [X] [#6001](https://github.com/kubernetes/ingress-nginx/pull/6001) Update psp example -- [X] [#6020](https://github.com/kubernetes/ingress-nginx/pull/6020) Added missing backend protocol. -- [X] [#6022](https://github.com/kubernetes/ingress-nginx/pull/6022) fix typo in development.md -- [X] [#6038](https://github.com/kubernetes/ingress-nginx/pull/6038) Document migration path to ingress-nginx chart from stable/nginx-ingress -- [X] [#6042](https://github.com/kubernetes/ingress-nginx/pull/6042) Fix typo -- [X] [#6044](https://github.com/kubernetes/ingress-nginx/pull/6044) Chart readme fixes -- [X] [#6075](https://github.com/kubernetes/ingress-nginx/pull/6075) Sync helm chart affinity examples -- [X] [#6076](https://github.com/kubernetes/ingress-nginx/pull/6076) Update NLB idle timeout information - -### 0.34.1 - -**Image:** - -- `us.gcr.io/k8s-artifacts-prod/ingress-nginx/controller:v0.34.1@sha256:0e072dddd1f7f8fc8909a2ca6f65e76c5f0d2fcfb8be47935ae3457e8bbceb20` -- `eu.gcr.io/k8s-artifacts-prod/ingress-nginx/controller:v0.34.1@sha256:0e072dddd1f7f8fc8909a2ca6f65e76c5f0d2fcfb8be47935ae3457e8bbceb20` -- `asia.gcr.io/k8s-artifacts-prod/ingress-nginx/controller:v0.34.1@sha256:0e072dddd1f7f8fc8909a2ca6f65e76c5f0d2fcfb8be47935ae3457e8bbceb20` - -Fix regression introduced in [#5691](https://github.com/kubernetes/ingress-nginx/pull/5691) related to annotations `use-regex` and `rewrite`. -Update go to [1.14.5](https://groups.google.com/g/golang-announce/c/XZNfaiwgt2w/m/E6gHDs32AQAJ) - -_Changes:_ - -- [X] [#5896](https://github.com/kubernetes/ingress-nginx/pull/5896) Revert "use-regex annotation should be applied to only one Location" -- [X] [#5897](https://github.com/kubernetes/ingress-nginx/pull/5897) Update go version - -### 0.34.0 - -**Image:** - -- `us.gcr.io/k8s-artifacts-prod/ingress-nginx/controller:v0.34.0@sha256:56633bd00dab33d92ba14c6e709126a762d54a75a6e72437adefeaaca0abb069` -- `eu.gcr.io/k8s-artifacts-prod/ingress-nginx/controller:v0.34.0@sha256:56633bd00dab33d92ba14c6e709126a762d54a75a6e72437adefeaaca0abb069` -- `asia.gcr.io/k8s-artifacts-prod/ingress-nginx/controller:v0.34.0@sha256:56633bd00dab33d92ba14c6e709126a762d54a75a6e72437adefeaaca0abb069` - -_Breaking Changes:_ - -The repository https://quay.io/repository/kubernetes-ingress-controller/nginx-ingress-controller is deprecated and read-only for historical purposes. - -_New Features:_ - -- NGINX 1.19.1 -- OWASP ModSecurity Core Rule Set [v3.3.0](https://github.com/coreruleset/coreruleset/releases/tag/v3.3.0) -- Configure User-Agent for [client-go](https://github.com/kubernetes/ingress-nginx/pull/5700) -- Switch to [gcr.io](https://cloud.google.com/container-registry/) as container registry -- Use cloud-build to build [container images](https://console.cloud.google.com/gcr/images/k8s-artifacts-prod/US/ingress-nginx) -- Publish images using [artifact promotion tooling](https://sigs.k8s.io/promo-tools) -- Go 1.14.4 -- client-go v0.18.5 - -_Changes:_ - -- [X] [#5671](https://github.com/kubernetes/ingress-nginx/pull/5671) Make liveness probe more resilient than readiness probe -- [X] [#5691](https://github.com/kubernetes/ingress-nginx/pull/5691) use-regex annotation should be applied to only one Location -- [X] [#5700](https://github.com/kubernetes/ingress-nginx/pull/5700) Configure User-Agent -- [X] [#5702](https://github.com/kubernetes/ingress-nginx/pull/5702) Filter out objects that belong to Helm -- [X] [#5703](https://github.com/kubernetes/ingress-nginx/pull/5703) Use build tags to make it compile on non linux platforms -- [X] [#5704](https://github.com/kubernetes/ingress-nginx/pull/5704) add custom metric to hpa template -- [X] [#5707](https://github.com/kubernetes/ingress-nginx/pull/5707) fix for #5666 -- [X] [#5708](https://github.com/kubernetes/ingress-nginx/pull/5708) Add sysctl exemptions to controller PSP -- [X] [#5709](https://github.com/kubernetes/ingress-nginx/pull/5709) fix: remove duplicated X-Forwarded-Proto header. -- [X] [#5712](https://github.com/kubernetes/ingress-nginx/pull/5712) Add proxy-ssl-server-name to pass server name on SNI -- [X] [#5713](https://github.com/kubernetes/ingress-nginx/pull/5713) Fix static manifests location -- [X] [#5717](https://github.com/kubernetes/ingress-nginx/pull/5717) Add support for an internal load balancer along with an external one -- [X] [#5722](https://github.com/kubernetes/ingress-nginx/pull/5722) Remove deprecrated --generator flag -- [X] [#5725](https://github.com/kubernetes/ingress-nginx/pull/5725) Fix e2e externalName test -- [X] [#5726](https://github.com/kubernetes/ingress-nginx/pull/5726) Dynamic LB sync non-external backends only when necessary -- [X] [#5727](https://github.com/kubernetes/ingress-nginx/pull/5727) Adjust E2E_NODES variable -- [X] [#5733](https://github.com/kubernetes/ingress-nginx/pull/5733) Fix make-clean target -- [X] [#5742](https://github.com/kubernetes/ingress-nginx/pull/5742) Allow to use a custom arch to run e2e tests -- [X] [#5743](https://github.com/kubernetes/ingress-nginx/pull/5743) build/dev-env.sh: remove docker version check -- [X] [#5745](https://github.com/kubernetes/ingress-nginx/pull/5745) Add default-type as a configurable for default_type -- [X] [#5747](https://github.com/kubernetes/ingress-nginx/pull/5747) feat: enable stream_realip_module -- [X] [#5749](https://github.com/kubernetes/ingress-nginx/pull/5749) Be configurable max batch size of metrics -- [X] [#5752](https://github.com/kubernetes/ingress-nginx/pull/5752) Update ValidatingWebhook for Ingress to support --dry-run=server -- [X] [#5761](https://github.com/kubernetes/ingress-nginx/pull/5761) Improve buildx configuration -- [X] [#5762](https://github.com/kubernetes/ingress-nginx/pull/5762) Add cloudbuild job to build nginx image -- [X] [#5764](https://github.com/kubernetes/ingress-nginx/pull/5764) Remove vendor directory and enable go modules -- [X] [#5770](https://github.com/kubernetes/ingress-nginx/pull/5770) Use admissionregistration.k8s.io/v1beta1 to be k8s < 1.16 compatible -- [X] [#5773](https://github.com/kubernetes/ingress-nginx/pull/5773) Update go dependencies -- [X] [#5774](https://github.com/kubernetes/ingress-nginx/pull/5774) Build new nginx image -- [X] [#5777](https://github.com/kubernetes/ingress-nginx/pull/5777) Improve execution of prow jobs -- [X] [#5778](https://github.com/kubernetes/ingress-nginx/pull/5778) Simplify build of e2e test image -- [X] [#5779](https://github.com/kubernetes/ingress-nginx/pull/5779) Add version check form helm -- [X] [#5791](https://github.com/kubernetes/ingress-nginx/pull/5791) Trigger of cloudbuild for nginx image and push -- [X] [#5794](https://github.com/kubernetes/ingress-nginx/pull/5794) Remove use of terraform to build nginx and ingress-controller -- [X] [#5795](https://github.com/kubernetes/ingress-nginx/pull/5795) Use fully qualified images to avoid cri-o issues -- [X] [#5796](https://github.com/kubernetes/ingress-nginx/pull/5796) Fixup docs for the ingress-class flag. -- [X] [#5797](https://github.com/kubernetes/ingress-nginx/pull/5797) Add cloudbuild configuration for cfssl test image -- [X] [#5798](https://github.com/kubernetes/ingress-nginx/pull/5798) Add cloudbuild configuration for echo test image -- [X] [#5799](https://github.com/kubernetes/ingress-nginx/pull/5799) Add cloudbuild configuration for httpbin test image -- [X] [#5800](https://github.com/kubernetes/ingress-nginx/pull/5800) Add cloudbuild configuration for fastcgi test image -- [X] [#5804](https://github.com/kubernetes/ingress-nginx/pull/5804) Increase cloudbuild timeout -- [X] [#5806](https://github.com/kubernetes/ingress-nginx/pull/5806) Use a different machine type for httpbin cloudbuild -- [X] [#5807](https://github.com/kubernetes/ingress-nginx/pull/5807) Start using e2e test images from gcr.io -- [X] [#5808](https://github.com/kubernetes/ingress-nginx/pull/5808) Remove unused variables and verbose e2e logs -- [X] [#5811](https://github.com/kubernetes/ingress-nginx/pull/5811) Get ingress-controller pod name -- [X] [#5817](https://github.com/kubernetes/ingress-nginx/pull/5817) Update kind node image version -- [X] [#5818](https://github.com/kubernetes/ingress-nginx/pull/5818) Update e2e configuration and fix flaky test -- [X] [#5823](https://github.com/kubernetes/ingress-nginx/pull/5823) Add quoting to sysctls because numeric values need to be strings -- [X] [#5826](https://github.com/kubernetes/ingress-nginx/pull/5826) Use nginx image promoted from staging -- [X] [#5827](https://github.com/kubernetes/ingress-nginx/pull/5827) Extract version to file VERSION -- [X] [#5828](https://github.com/kubernetes/ingress-nginx/pull/5828) Switch to promoted e2e images in gcr -- [X] [#5832](https://github.com/kubernetes/ingress-nginx/pull/5832) fix: remove redundant health check to avoid liveness or readiness timeout -- [X] [#5836](https://github.com/kubernetes/ingress-nginx/pull/5836) Test pull requests using github actions -- [X] [#5840](https://github.com/kubernetes/ingress-nginx/pull/5840) Update nginx image registry -- [X] [#5843](https://github.com/kubernetes/ingress-nginx/pull/5843) Update jettech/kube-webhook-certgen image -- [X] [#5845](https://github.com/kubernetes/ingress-nginx/pull/5845) Update deploy manifests -- [X] [#5846](https://github.com/kubernetes/ingress-nginx/pull/5846) Filter github actions to be executed -- [X] [#5849](https://github.com/kubernetes/ingress-nginx/pull/5849) Fix github docs github action -- [X] [#5851](https://github.com/kubernetes/ingress-nginx/pull/5851) Fix conflicts of VERSION file -- [X] [#5853](https://github.com/kubernetes/ingress-nginx/pull/5853) fix json tag for SSLPreferServerCiphers -- [X] [#5856](https://github.com/kubernetes/ingress-nginx/pull/5856) Fix proxy ssl e2e test -- [X] [#5857](https://github.com/kubernetes/ingress-nginx/pull/5857) Custom default backend service must have ports -- [X] [#5859](https://github.com/kubernetes/ingress-nginx/pull/5859) Update nginx to 1.19.1 -- [X] [#5861](https://github.com/kubernetes/ingress-nginx/pull/5861) Update nginx modules -- [X] [#5862](https://github.com/kubernetes/ingress-nginx/pull/5862) Adjust nginx cloudbuild timeout -- [X] [#5866](https://github.com/kubernetes/ingress-nginx/pull/5866) Update OWASP ModSecurity Core Rule Set -- [X] [#5867](https://github.com/kubernetes/ingress-nginx/pull/5867) Update nginx image -- [X] [#5868](https://github.com/kubernetes/ingress-nginx/pull/5868) Update go dependencies -- [X] [#5869](https://github.com/kubernetes/ingress-nginx/pull/5869) Changes in TAG file should trigger e2e testing - -_Documentation:_ - -- [X] [#5706](https://github.com/kubernetes/ingress-nginx/pull/5706) Fix controller.publishService.enabled on README -- [X] [#5711](https://github.com/kubernetes/ingress-nginx/pull/5711) Update mkdocs -- [X] [#5724](https://github.com/kubernetes/ingress-nginx/pull/5724) Update troubleshooting.md -- [X] [#5729](https://github.com/kubernetes/ingress-nginx/pull/5729) docs: update development.md -- [X] [#5751](https://github.com/kubernetes/ingress-nginx/pull/5751) docs: update development.md to use ingress-nginx-* -- [X] [#5759](https://github.com/kubernetes/ingress-nginx/pull/5759) Update helm chart name in upgrade doc -- [X] [#5760](https://github.com/kubernetes/ingress-nginx/pull/5760) Update comment about restart of pod -- [X] [#5763](https://github.com/kubernetes/ingress-nginx/pull/5763) Update e2e test suite index list doc -- [X] [#5819](https://github.com/kubernetes/ingress-nginx/pull/5819) Update krew installation doc -- [X] [#5821](https://github.com/kubernetes/ingress-nginx/pull/5821) doc: update docs and fixed typos - -### 0.33.0 - -**Image:** `quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.33.0` - -_New Features:_ - -- NGINX 1.19.0 -- TLSv1.3 is enabled by default -- Experimental support for s390x -- Allow combination of NGINX variables in annotation [upstream-hash-by](https://github.com/kubernetes/ingress-nginx/pull/5571) -- New setting to configure different access logs for http and stream sections: [http-access-log-path](https://kubernetes.github.io/ingress-nginx/user-guide/nginx-configuration/configmap/#http-access-log-path) and [stream-access-log-path](https://kubernetes.github.io/ingress-nginx/user-guide/nginx-configuration/configmap/#stream-access-log-path) options in configMap - -_Deprecations:_ - -- Setting [access-log-path](https://kubernetes.github.io/ingress-nginx/user-guide/nginx-configuration/configmap/#access-log-path) is deprecated and will be removed in 0.35.0. Please use [http-access-log-path](https://kubernetes.github.io/ingress-nginx/user-guide/nginx-configuration/configmap/#http-access-log-path) and [stream-access-log-path](https://kubernetes.github.io/ingress-nginx/user-guide/nginx-configuration/configmap/#stream-access-log-path) - -_Changes:_ - -- [X] [#5463](https://github.com/kubernetes/ingress-nginx/pull/5463) Wait before any request to the ingress controller pod -- [X] [#5488](https://github.com/kubernetes/ingress-nginx/pull/5488) Update kind -- [X] [#5491](https://github.com/kubernetes/ingress-nginx/pull/5491) Actually enable TLSv1.3 by default -- [X] [#5494](https://github.com/kubernetes/ingress-nginx/pull/5494) Add configuration option for the runAsUser parameter of the webhook patch job -- [X] [#5503](https://github.com/kubernetes/ingress-nginx/pull/5503) Update job-patchWebhook.yaml -- [X] [#5504](https://github.com/kubernetes/ingress-nginx/pull/5504) Add configuration option for the imagePullSecrets in the webhook jobs -- [X] [#5505](https://github.com/kubernetes/ingress-nginx/pull/5505) Update helm chart -- [X] [#5516](https://github.com/kubernetes/ingress-nginx/pull/5516) build: remove unnecessary tag line in e2e -- [X] [#5522](https://github.com/kubernetes/ingress-nginx/pull/5522) Remove duplicate annotation parsing for annotationAffinityCookieChangeOnFailure -- [X] [#5534](https://github.com/kubernetes/ingress-nginx/pull/5534) Add annotation ssl-prefer-server-ciphers. -- [X] [#5536](https://github.com/kubernetes/ingress-nginx/pull/5536) Fix error setting $service_name NGINX variable -- [X] [#5553](https://github.com/kubernetes/ingress-nginx/pull/5553) Check service If publish-service flag is defined -- [X] [#5571](https://github.com/kubernetes/ingress-nginx/pull/5571) feat: support the combination of Nginx variables for annotation upstream-hash-by. -- [X] [#5572](https://github.com/kubernetes/ingress-nginx/pull/5572) [chart] Add toleration support for admission webhooks -- [X] [#5578](https://github.com/kubernetes/ingress-nginx/pull/5578) Use image promoter to push images to gcr -- [X] [#5582](https://github.com/kubernetes/ingress-nginx/pull/5582) Allow pulling images by digest -- [X] [#5584](https://github.com/kubernetes/ingress-nginx/pull/5584) Add note about initial delay during first start -- [X] [#5586](https://github.com/kubernetes/ingress-nginx/pull/5586) Add MaxMind GeoIP2 Anonymous IP support -- [X] [#5589](https://github.com/kubernetes/ingress-nginx/pull/5589) Do not reload NGINX if master process dies -- [X] [#5596](https://github.com/kubernetes/ingress-nginx/pull/5596) Update go dependencies -- [X] [#5603](https://github.com/kubernetes/ingress-nginx/pull/5603) Update nginx to 1.19.0 -- [X] [#5604](https://github.com/kubernetes/ingress-nginx/pull/5604) Update debian-base image -- [X] [#5606](https://github.com/kubernetes/ingress-nginx/pull/5606) Update nginx image and go to 1.14.3 -- [X] [#5613](https://github.com/kubernetes/ingress-nginx/pull/5613) fix oauth2-proxy image repository -- [X] [#5614](https://github.com/kubernetes/ingress-nginx/pull/5614) Add support for s390x -- [X] [#5619](https://github.com/kubernetes/ingress-nginx/pull/5619) Use new multi-arch nginx image -- [X] [#5621](https://github.com/kubernetes/ingress-nginx/pull/5621) Update terraform build images -- [X] [#5624](https://github.com/kubernetes/ingress-nginx/pull/5624) feat: add lj-releng tool to check Lua code for finding the potential problems -- [X] [#5625](https://github.com/kubernetes/ingress-nginx/pull/5625) Update nginx image to use alpine 3.12 -- [X] [#5626](https://github.com/kubernetes/ingress-nginx/pull/5626) Update nginx image -- [X] [#5629](https://github.com/kubernetes/ingress-nginx/pull/5629) Build multi-arch images by default -- [X] [#5630](https://github.com/kubernetes/ingress-nginx/pull/5630) Fix makefile task names -- [X] [#5631](https://github.com/kubernetes/ingress-nginx/pull/5631) Update e2e image -- [X] [#5632](https://github.com/kubernetes/ingress-nginx/pull/5632) Update buildx progress configuration -- [X] [#5636](https://github.com/kubernetes/ingress-nginx/pull/5636) Enable coredumps for e2e tests -- [X] [#5637](https://github.com/kubernetes/ingress-nginx/pull/5637) Refactor build of docker images -- [X] [#5641](https://github.com/kubernetes/ingress-nginx/pull/5641) Add missing ARCH variable -- [X] [#5642](https://github.com/kubernetes/ingress-nginx/pull/5642) Fix dev-env makefile task -- [X] [#5643](https://github.com/kubernetes/ingress-nginx/pull/5643) Fix build of image on osx -- [X] [#5644](https://github.com/kubernetes/ingress-nginx/pull/5644) Remove copy of binaries and deprecated e2e task -- [X] [#5656](https://github.com/kubernetes/ingress-nginx/pull/5656) feat: add http-access-log-path and stream-access-log-path options in configMap -- [X] [#5659](https://github.com/kubernetes/ingress-nginx/pull/5659) Update cloud-build configuration -- [X] [#5660](https://github.com/kubernetes/ingress-nginx/pull/5660) Set missing USER in cloud-build -- [X] [#5661](https://github.com/kubernetes/ingress-nginx/pull/5661) Add missing REPO_INFO en variable to cloud-build -- [X] [#5662](https://github.com/kubernetes/ingress-nginx/pull/5662) Increase cloud-build timeout -- [X] [#5663](https://github.com/kubernetes/ingress-nginx/pull/5663) Fix cloud-timeout setting -- [X] [#5664](https://github.com/kubernetes/ingress-nginx/pull/5664) fix undefined variable $auth_cookie error due to when location is denied -- [X] [#5665](https://github.com/kubernetes/ingress-nginx/pull/5665) Fix: improve performance -- [X] [#5669](https://github.com/kubernetes/ingress-nginx/pull/5669) Serve correct TLS certificate for requests with uppercase host -- [X] [#5672](https://github.com/kubernetes/ingress-nginx/pull/5672) feat: enable lj-releng tool to lint lua code. -- [X] [#5684](https://github.com/kubernetes/ingress-nginx/pull/5684) Fix proxy_protocol duplication in listen definition - -_Documentation:_ - -- [X] [#5487](https://github.com/kubernetes/ingress-nginx/pull/5487) Add note about firewall ports for admission webhook -- [X] [#5512](https://github.com/kubernetes/ingress-nginx/pull/5512) Wrong filename in documantation example -- [X] [#5563](https://github.com/kubernetes/ingress-nginx/pull/5563) Use ingress-nginx-* naming in docs to match the default deployments -- [X] [#5566](https://github.com/kubernetes/ingress-nginx/pull/5566) Update configmap name in custom-headers/README.md -- [X] [#5639](https://github.com/kubernetes/ingress-nginx/pull/5639) Update timeout to align values -- [X] [#5646](https://github.com/kubernetes/ingress-nginx/pull/5646) Add minor doc fixes to user guide and chart readme -- [X] [#5652](https://github.com/kubernetes/ingress-nginx/pull/5652) Add documentation for loading e2e tests without using minikube -- [X] [#5677](https://github.com/kubernetes/ingress-nginx/pull/5677) Add URL to official grafana dashboards -- [X] [#5682](https://github.com/kubernetes/ingress-nginx/pull/5682) Fix typo - -### 0.32.0 - -**Image:** `quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.32.0` - -Fix regression in validating webhook when the ingress controller is installed in Kubernetes v1.18 - -_Changes:_ - -- [X] [#4271](https://github.com/kubernetes/ingress-nginx/pull/4271) Add support for multi-arch images -- [X] [#5429](https://github.com/kubernetes/ingress-nginx/pull/5429) Update krew plugin configuration -- [X] [#5430](https://github.com/kubernetes/ingress-nginx/pull/5430) Use github actions to create releases and krew plugin assets -- [X] [#5432](https://github.com/kubernetes/ingress-nginx/pull/5432) Allow releases from a github action -- [X] [#5433](https://github.com/kubernetes/ingress-nginx/pull/5433) Avoid removal of index.yaml file -- [X] [#5434](https://github.com/kubernetes/ingress-nginx/pull/5434) Disable PR against krew repository -- [X] [#5436](https://github.com/kubernetes/ingress-nginx/pull/5436) Disable github release action -- [X] [#5439](https://github.com/kubernetes/ingress-nginx/pull/5439) Change action order -- [X] [#5453](https://github.com/kubernetes/ingress-nginx/pull/5453) Ensure alpine packages are up to date -- [X] [#5456](https://github.com/kubernetes/ingress-nginx/pull/5456) Case-insensitive TLS host matching -- [X] [#5459](https://github.com/kubernetes/ingress-nginx/pull/5459) Refactor ingress validation in webhook -- [X] [#5461](https://github.com/kubernetes/ingress-nginx/pull/5461) Fix helper for defaultbackend name -- [X] [#5462](https://github.com/kubernetes/ingress-nginx/pull/5462) Remove noisy dns log -- [X] [#5469](https://github.com/kubernetes/ingress-nginx/pull/5469) Changes on services must trigger a sync event -- [X] [#5472](https://github.com/kubernetes/ingress-nginx/pull/5472) Update admission webhook image -- [X] [#5474](https://github.com/kubernetes/ingress-nginx/pull/5474) Add install command for Digital Ocean -- [X] [#5476](https://github.com/kubernetes/ingress-nginx/pull/5476) Fix chart missing default backend name -- [X] [#5481](https://github.com/kubernetes/ingress-nginx/pull/5481) fix first backend sync -- [X] [#5483](https://github.com/kubernetes/ingress-nginx/pull/5483) Fix chart maxmindLicenseKey location -- [X] [#5484](https://github.com/kubernetes/ingress-nginx/pull/5484) Only load docker images in kind worker nodes - -_Documentation:_ - -- [X] [#5404](https://github.com/kubernetes/ingress-nginx/pull/5404) update the helm v3 install way -- [X] [#5435](https://github.com/kubernetes/ingress-nginx/pull/5435) Fix deployment links -- [X] [#5438](https://github.com/kubernetes/ingress-nginx/pull/5438) Update chart instructions -- [X] [#5460](https://github.com/kubernetes/ingress-nginx/pull/5460) fix(Chart): Mismatch between README.md and values.yml (defaultBackend.enabled) -- [X] [#5465](https://github.com/kubernetes/ingress-nginx/pull/5465) Update helm v2 installation instructions -- [X] [#5468](https://github.com/kubernetes/ingress-nginx/pull/5468) Update admission webhook annotations -- [X] [#5479](https://github.com/kubernetes/ingress-nginx/pull/5479) Remove obsolete default backend settings -- [X] [#5480](https://github.com/kubernetes/ingress-nginx/pull/5480) docs(changelog): fix typo - -### 0.31.1 - -**Image:** `quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.31.1` - -Fix regression in validating webhook - -- [X] [#5445](https://github.com/kubernetes/ingress-nginx/pull/5445) Ensure webhook validation ingress has a PathType - -### 0.31.0 - -**Image:** `quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.31.0` - -_New Features:_ - -- NGINX 1.17.10 -- OpenSSL 1.1.1g - [CVE-2020-1967](https://cve.mitre.org/cgi-bin/cvename.cgi?name=2020-1967) -- OCSP stapling -- Helm chart [stable/nginx-ingress](https://github.com/helm/charts/tree/master/stable/nginx-ingress) is now maintained in the [ingress-nginx](https://github.com/kubernetes/ingress-nginx/tree/main/charts/ingress-nginx) repository -- Support for custom Maxmind GeoLite2 Databases [flag --maxmind-edition-ids](https://kubernetes.github.io/ingress-nginx/user-guide/cli-arguments/) -- New [PathType](https://kubernetes.io/docs/concepts/services-networking/ingress/#path-types) and [IngressClass](https://kubernetes.io/docs/concepts/services-networking/ingress/#ingress-class) fields. Requires Kubernetes v1.18 or higher -- Enable configuration of lua plugins using the configuration configmap -- Go 1.14 - -_Changes:_ - -- [X] [#4632](https://github.com/kubernetes/ingress-nginx/pull/4632) run lua plugin tests -- [X] [#4958](https://github.com/kubernetes/ingress-nginx/pull/4958) Add a forwarded protocol map for included x-forwarded-proto. -- [X] [#4981](https://github.com/kubernetes/ingress-nginx/pull/4981) Applying proxy-ssl-* directives on locations only -- [X] [#5131](https://github.com/kubernetes/ingress-nginx/pull/5131) Add request handling performance dashboard -- [X] [#5133](https://github.com/kubernetes/ingress-nginx/pull/5133) Lua OCSP stapling -- [X] [#5157](https://github.com/kubernetes/ingress-nginx/pull/5157) Added limit-rate annotation test -- [X] [#5158](https://github.com/kubernetes/ingress-nginx/pull/5158) Fix push task -- [X] [#5159](https://github.com/kubernetes/ingress-nginx/pull/5159) Start migration of helm chart -- [X] [#5160](https://github.com/kubernetes/ingress-nginx/pull/5160) Fix e2e test run.sh -- [X] [#5165](https://github.com/kubernetes/ingress-nginx/pull/5165) Use local chart directory for dev-env and e2e tests -- [X] [#5166](https://github.com/kubernetes/ingress-nginx/pull/5166) proxy_ssl_name support -- [X] [#5169](https://github.com/kubernetes/ingress-nginx/pull/5169) Cleanup e2e directory -- [X] [#5170](https://github.com/kubernetes/ingress-nginx/pull/5170) Update go dependencies -- [X] [#5171](https://github.com/kubernetes/ingress-nginx/pull/5171) Sync chart PR #20984 -- [X] [#5172](https://github.com/kubernetes/ingress-nginx/pull/5172) Add script to check helm chart -- [X] [#5173](https://github.com/kubernetes/ingress-nginx/pull/5173) Update go to 1.14 -- [X] [#5174](https://github.com/kubernetes/ingress-nginx/pull/5174) Update e2e image -- [X] [#5175](https://github.com/kubernetes/ingress-nginx/pull/5175) Migrate the backends handle logic to function -- [X] [#5178](https://github.com/kubernetes/ingress-nginx/pull/5178) Adding annotations support to helm chart configmaps -- [X] [#5181](https://github.com/kubernetes/ingress-nginx/pull/5181) Fix public function comment -- [X] [#5182](https://github.com/kubernetes/ingress-nginx/pull/5182) Update go mod for 1.14 -- [X] [#5183](https://github.com/kubernetes/ingress-nginx/pull/5183) Remove unused docker file -- [X] [#5185](https://github.com/kubernetes/ingress-nginx/pull/5185) [helm chart] Use recommended labels and label helpers -- [X] [#5190](https://github.com/kubernetes/ingress-nginx/pull/5190) Refactored test/e2e/annotations/proxy.go -- [X] [#5192](https://github.com/kubernetes/ingress-nginx/pull/5192) Update helm templates to match new chart name -- [X] [#5194](https://github.com/kubernetes/ingress-nginx/pull/5194) I found a typo :) -- [X] [#5201](https://github.com/kubernetes/ingress-nginx/pull/5201) Added TC for proxy connect, read, and send timeout -- [X] [#5202](https://github.com/kubernetes/ingress-nginx/pull/5202) Refactored client body buffer size TC-s. -- [X] [#5204](https://github.com/kubernetes/ingress-nginx/pull/5204) Cleanup chart code -- [X] [#5205](https://github.com/kubernetes/ingress-nginx/pull/5205) Add OWNERS file for helm chart -- [X] [#5207](https://github.com/kubernetes/ingress-nginx/pull/5207) [helm chart] Hardcode component names. -- [X] [#5211](https://github.com/kubernetes/ingress-nginx/pull/5211) Update NGINX to 1.17.9 -- [X] [#5213](https://github.com/kubernetes/ingress-nginx/pull/5213) Make quote function to render pointers in the template properly -- [X] [#5216](https://github.com/kubernetes/ingress-nginx/pull/5216) Check go exists in $PATH -- [X] [#5217](https://github.com/kubernetes/ingress-nginx/pull/5217) Added affinity-mode tc and refactored affinity.go -- [X] [#5221](https://github.com/kubernetes/ingress-nginx/pull/5221) Update NGINX image -- [X] [#5225](https://github.com/kubernetes/ingress-nginx/pull/5225) Avoid secret without tls.crt and tls.key but a valid ca.crt -- [X] [#5226](https://github.com/kubernetes/ingress-nginx/pull/5226) Fix $service_name and $service_port variables values without host -- [X] [#5232](https://github.com/kubernetes/ingress-nginx/pull/5232) Refacored proxy ssl TC-s -- [X] [#5241](https://github.com/kubernetes/ingress-nginx/pull/5241) Fix controller container name -- [X] [#5246](https://github.com/kubernetes/ingress-nginx/pull/5246) Remove checks for older versions -- [X] [#5249](https://github.com/kubernetes/ingress-nginx/pull/5249) Add support for hostPort in Deployment -- [X] [#5250](https://github.com/kubernetes/ingress-nginx/pull/5250) Use rbac scope feature in e2e tests -- [X] [#5251](https://github.com/kubernetes/ingress-nginx/pull/5251) Add support for custom healthz path in helm chart -- [X] [#5252](https://github.com/kubernetes/ingress-nginx/pull/5252) Check chart controller image tag -- [X] [#5254](https://github.com/kubernetes/ingress-nginx/pull/5254) Switch dev-env script to deployment -- [X] [#5258](https://github.com/kubernetes/ingress-nginx/pull/5258) Cleanup of chart labels -- [X] [#5262](https://github.com/kubernetes/ingress-nginx/pull/5262) Add Maxmind Editions support -- [X] [#5264](https://github.com/kubernetes/ingress-nginx/pull/5264) Fix reference to DH param secret, recommend larger parameter size -- [X] [#5266](https://github.com/kubernetes/ingress-nginx/pull/5266) Redirect for app-root should preserve current scheme -- [X] [#5268](https://github.com/kubernetes/ingress-nginx/pull/5268) do not require go for building -- [X] [#5269](https://github.com/kubernetes/ingress-nginx/pull/5269) Ensure DeleteDeployment waits until there are no pods running -- [X] [#5276](https://github.com/kubernetes/ingress-nginx/pull/5276) Fix the ability to disable ModSecurity at location level -- [X] [#5277](https://github.com/kubernetes/ingress-nginx/pull/5277) refactoring: use more specific var name -- [X] [#5281](https://github.com/kubernetes/ingress-nginx/pull/5281) Remove unnecessary logs -- [X] [#5283](https://github.com/kubernetes/ingress-nginx/pull/5283) Add retries for dns in tcp e2e test -- [X] [#5284](https://github.com/kubernetes/ingress-nginx/pull/5284) Wait for update in tcp e2e test -- [X] [#5288](https://github.com/kubernetes/ingress-nginx/pull/5288) Update client-go methods to support context and and new options -- [X] [#5289](https://github.com/kubernetes/ingress-nginx/pull/5289) Update go and e2e image -- [X] [#5290](https://github.com/kubernetes/ingress-nginx/pull/5290) Add DS_PROMETHEUS datasource for templating -- [X] [#5296](https://github.com/kubernetes/ingress-nginx/pull/5296) Added proxy-ssl-location-only test. -- [X] [#5298](https://github.com/kubernetes/ingress-nginx/pull/5298) Increase e2e concurrency -- [X] [#5301](https://github.com/kubernetes/ingress-nginx/pull/5301) Forward X-Request-ID to auth service -- [X] [#5307](https://github.com/kubernetes/ingress-nginx/pull/5307) Migrate ingress.class annotation to new IngressClassName field -- [X] [#5308](https://github.com/kubernetes/ingress-nginx/pull/5308) Set new default PathType to prefix -- [X] [#5309](https://github.com/kubernetes/ingress-nginx/pull/5309) Fix condition in server-alias annotation -- [X] [#5310](https://github.com/kubernetes/ingress-nginx/pull/5310) Added auth-tls-verify-client testcase -- [X] [#5313](https://github.com/kubernetes/ingress-nginx/pull/5313) Add script to generate yaml files from helm -- [X] [#5314](https://github.com/kubernetes/ingress-nginx/pull/5314) Set default resource requests limits -- [X] [#5315](https://github.com/kubernetes/ingress-nginx/pull/5315) Fix definition order of modsecurity directives -- [X] [#5320](https://github.com/kubernetes/ingress-nginx/pull/5320) Change condition order that produces endless loop -- [X] [#5324](https://github.com/kubernetes/ingress-nginx/pull/5324) Add support for PathTypeExact -- [X] [#5329](https://github.com/kubernetes/ingress-nginx/pull/5329) Update e2e dev image to v1.18.0 -- [X] [#5330](https://github.com/kubernetes/ingress-nginx/pull/5330) Set k8s version kind should use for dev environment -- [X] [#5331](https://github.com/kubernetes/ingress-nginx/pull/5331) Enable configuration of plugins using configmap -- [X] [#5332](https://github.com/kubernetes/ingress-nginx/pull/5332) Add lifecycle hook and option to enable mimalloc -- [X] [#5333](https://github.com/kubernetes/ingress-nginx/pull/5333) Remove duplicated annotations definition and refactor hostPort conf -- [X] [#5336](https://github.com/kubernetes/ingress-nginx/pull/5336) Fix deployment strategy -- [X] [#5340](https://github.com/kubernetes/ingress-nginx/pull/5340) fix: remove unnecessary if statement when redirect annotation is defined -- [X] [#5341](https://github.com/kubernetes/ingress-nginx/pull/5341) ensure make lua-test runs locally -- [X] [#5346](https://github.com/kubernetes/ingress-nginx/pull/5346) Ensure krew plugin includes license -- [X] [#5357](https://github.com/kubernetes/ingress-nginx/pull/5357) Fix broken symlink to mimalloc -- [X] [#5361](https://github.com/kubernetes/ingress-nginx/pull/5361) Cleanup parsing of annotations with lists -- [X] [#5362](https://github.com/kubernetes/ingress-nginx/pull/5362) Cleanup httpbin image -- [X] [#5363](https://github.com/kubernetes/ingress-nginx/pull/5363) Remove version dependency in mimalloc symlink -- [X] [#5369](https://github.com/kubernetes/ingress-nginx/pull/5369) Update luajit and nginx to 1.17.10 -- [X] [#5371](https://github.com/kubernetes/ingress-nginx/pull/5371) Update e2e image -- [X] [#5372](https://github.com/kubernetes/ingress-nginx/pull/5372) Update Go to 1.14.2 -- [X] [#5374](https://github.com/kubernetes/ingress-nginx/pull/5374) Add port for plain HTTP to HTTPS redirection -- [X] [#5375](https://github.com/kubernetes/ingress-nginx/pull/5375) Remove chart old podSecurityPolicy check -- [X] [#5380](https://github.com/kubernetes/ingress-nginx/pull/5380) Use official mkdocs image and github action -- [X] [#5381](https://github.com/kubernetes/ingress-nginx/pull/5381) Add e2e tests for helm chart -- [X] [#5387](https://github.com/kubernetes/ingress-nginx/pull/5387) Add e2e test for OCSP and new configmap setting -- [X] [#5388](https://github.com/kubernetes/ingress-nginx/pull/5388) Remove TODO that were done -- [X] [#5392](https://github.com/kubernetes/ingress-nginx/pull/5392) Add new cfssl image and update e2e tests to use it -- [X] [#5393](https://github.com/kubernetes/ingress-nginx/pull/5393) Fix dev-env script to use new hostPort setting -- [X] [#5403](https://github.com/kubernetes/ingress-nginx/pull/5403) staple only when OCSP response status is "good" -- [X] [#5407](https://github.com/kubernetes/ingress-nginx/pull/5407) Update go dependencies -- [X] [#5409](https://github.com/kubernetes/ingress-nginx/pull/5409) Removed wrong code -- [X] [#5410](https://github.com/kubernetes/ingress-nginx/pull/5410) Add support for IngressClass and ingress.class annotation -- [X] [#5414](https://github.com/kubernetes/ingress-nginx/pull/5414) Pin mimalloc version and update openssl -- [X] [#5415](https://github.com/kubernetes/ingress-nginx/pull/5415) Update nginx image to fix openssl CVE-2020-1967 -- [X] [#5419](https://github.com/kubernetes/ingress-nginx/pull/5419) Improve build time of httpbin e2e test image - -_Documentation:_ - -- [X] [#5162](https://github.com/kubernetes/ingress-nginx/pull/5162) Migrate release of docs from travis-ci to github actions -- [X] [#5163](https://github.com/kubernetes/ingress-nginx/pull/5163) Cleanup build of documentation and update to mkdocs 1.1 -- [X] [#5114](https://github.com/kubernetes/ingress-nginx/pull/5114) Feat: add header-pattern annotation. -- [X] [#5274](https://github.com/kubernetes/ingress-nginx/pull/5274) [docs]: fix deploy Prerequisite section -- [X] [#5347](https://github.com/kubernetes/ingress-nginx/pull/5347) docs: fix use-gzip wrong markdown style -- [X] [#5349](https://github.com/kubernetes/ingress-nginx/pull/5349) Update doc for validating Webhook with helm -- [X] [#5351](https://github.com/kubernetes/ingress-nginx/pull/5351) Remove deprecated flags and update docs -- [X] [#5355](https://github.com/kubernetes/ingress-nginx/pull/5355) ingress-nginx lua plugins docs -- [X] [#5360](https://github.com/kubernetes/ingress-nginx/pull/5360) Update deployment documentation -- [X] [#5365](https://github.com/kubernetes/ingress-nginx/pull/5365) Fix broken link for Layer 2 configuration mode -- [X] [#5370](https://github.com/kubernetes/ingress-nginx/pull/5370) Fix plugin README.md link -- [X] [#5395](https://github.com/kubernetes/ingress-nginx/pull/5395) Fix from-to-www link -- [X] [#5399](https://github.com/kubernetes/ingress-nginx/pull/5399) Cleanup deploy docs and remove old yaml manifests -- [X] [#5400](https://github.com/kubernetes/ingress-nginx/pull/5400) Update images README.md -- [X] [#5408](https://github.com/kubernetes/ingress-nginx/pull/5408) Add manifest for kind documentation -- [X] [#5420](https://github.com/kubernetes/ingress-nginx/pull/5420) Remove lua-resty-waf docs -- [X] [#5422](https://github.com/kubernetes/ingress-nginx/pull/5422) update notes.txt example with networking.k8s.io - -### 0.30.0 - -**Image:** `quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.30.0` - -- Allow service type ExternalName with different port and targetPort -- Update datadog tracer to v1.1.3 -- Update default variables_hash_bucket_size value to 256 -- Enable Opentracing for authentication subrequests (auth_request) - -_Changes:_ - -- [X] [#5080](https://github.com/kubernetes/ingress-nginx/pull/5080) Add label selector for plugin -- [X] [#5083](https://github.com/kubernetes/ingress-nginx/pull/5083) Cleanup docker build -- [X] [#5084](https://github.com/kubernetes/ingress-nginx/pull/5084) Cleanup docker build -- [X] [#5085](https://github.com/kubernetes/ingress-nginx/pull/5085) Cleanup build of nginx image -- [X] [#5086](https://github.com/kubernetes/ingress-nginx/pull/5086) Migration e2e installation to helm -- [X] [#5087](https://github.com/kubernetes/ingress-nginx/pull/5087) Fox docker opencontainers version label -- [X] [#5088](https://github.com/kubernetes/ingress-nginx/pull/5088) Remove .cache directory with make clean. -- [X] [#5089](https://github.com/kubernetes/ingress-nginx/pull/5089) Abort any task in case of errors running shell commands -- [X] [#5090](https://github.com/kubernetes/ingress-nginx/pull/5090) Cleanup and standardization of e2e test definitions -- [X] [#5091](https://github.com/kubernetes/ingress-nginx/pull/5091) Add case for when user agent is nil -- [X] [#5092](https://github.com/kubernetes/ingress-nginx/pull/5092) Print information about e2e suite tests -- [X] [#5094](https://github.com/kubernetes/ingress-nginx/pull/5094) Remove comment from e2e_test.go -- [X] [#5095](https://github.com/kubernetes/ingress-nginx/pull/5095) Update datadog tracer to v1.1.3 -- [X] [#5097](https://github.com/kubernetes/ingress-nginx/pull/5097) New e2e test: log-format-escape-json and log-format-upstream -- [X] [#5098](https://github.com/kubernetes/ingress-nginx/pull/5098) Fix make dev-env -- [X] [#5100](https://github.com/kubernetes/ingress-nginx/pull/5100) Ensure make dev-env support rolling updates -- [X] [#5101](https://github.com/kubernetes/ingress-nginx/pull/5101) Add keep-alive config check test -- [X] [#5102](https://github.com/kubernetes/ingress-nginx/pull/5102) Migrate e2e libaries -- [X] [#5103](https://github.com/kubernetes/ingress-nginx/pull/5103) Added configmap test for no-tls-redirect-locations -- [X] [#5105](https://github.com/kubernetes/ingress-nginx/pull/5105) Reuse-port check e2e tc (config check only) -- [X] [#5109](https://github.com/kubernetes/ingress-nginx/pull/5109) Added basic limit-rate configmap test. -- [X] [#5111](https://github.com/kubernetes/ingress-nginx/pull/5111) ingress-path-matching: doc typo -- [X] [#5117](https://github.com/kubernetes/ingress-nginx/pull/5117) Hash size e2e check test case -- [X] [#5122](https://github.com/kubernetes/ingress-nginx/pull/5122) refactor ssl handling in preparation of OCSP stapling -- [X] [#5123](https://github.com/kubernetes/ingress-nginx/pull/5123) Ensure helm repository and charts are available -- [X] [#5124](https://github.com/kubernetes/ingress-nginx/pull/5124) make dev-env improvements -- [X] [#5125](https://github.com/kubernetes/ingress-nginx/pull/5125) Added tc for limit-connection annotation -- [X] [#5131](https://github.com/kubernetes/ingress-nginx/pull/5131) Add request handling performance dashboard -- [X] [#5132](https://github.com/kubernetes/ingress-nginx/pull/5132) Lint go code -- [X] [#5134](https://github.com/kubernetes/ingress-nginx/pull/5134) Update list of e2e tests -- [X] [#5136](https://github.com/kubernetes/ingress-nginx/pull/5136) Add upstream keep alive tests -- [X] [#5139](https://github.com/kubernetes/ingress-nginx/pull/5139) Fixes https://github.com/kubernetes/ingress-nginx/issues/5120 -- [X] [#5140](https://github.com/kubernetes/ingress-nginx/pull/5140) Added configmap test for ssl-ciphers. -- [X] [#5141](https://github.com/kubernetes/ingress-nginx/pull/5141) Allow service type ExternalName with different port and targetPort -- [X] [#5145](https://github.com/kubernetes/ingress-nginx/pull/5145) Refactor the HSTS related test file and add config check to the HSTS tests -- [X] [#5149](https://github.com/kubernetes/ingress-nginx/pull/5149) Use helm template instead of update to install dev cluster -- [X] [#5150](https://github.com/kubernetes/ingress-nginx/pull/5150) Update default VariablesHashBucketSize value to 256 -- [X] [#5151](https://github.com/kubernetes/ingress-nginx/pull/5151) Check there is a difference in the template besides the checksum -- [X] [#5152](https://github.com/kubernetes/ingress-nginx/pull/5152) Clean template -- [X] [#5153](https://github.com/kubernetes/ingress-nginx/pull/5153) Update nginx and e2e images - -_Documentation:_ - -- [X] [#5018](https://github.com/kubernetes/ingress-nginx/pull/5018) Update developer document on dependency updates -- [X] [#5081](https://github.com/kubernetes/ingress-nginx/pull/5081) Fixed incorrect documentation of cli flag --default-backend-service -- [X] [#5093](https://github.com/kubernetes/ingress-nginx/pull/5093) Generate doc with list of e2e tests -- [X] [#5135](https://github.com/kubernetes/ingress-nginx/pull/5135) Correct spelling of the word "Original" in annotations documentation - -### 0.29.0 - -**Image:** `quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.29.0` - -_New Features:_ - -- NGINX 1.17.8 -- Add SameSite support for [Cookie Affinity](https://kubernetes.github.io/ingress-nginx/user-guide/nginx-configuration/annotations/#cookie-affinity) https://www.chromium.org/updates/same-site -- Refactor of [mirror](https://kubernetes.github.io/ingress-nginx/user-guide/nginx-configuration/annotations/#mirror) feature to remove additional annotations - -_Changes:_ - -- [X] [#4949](https://github.com/kubernetes/ingress-nginx/pull/4949) Add SameSite support - omit None for old browsers -- [X] [#4973](https://github.com/kubernetes/ingress-nginx/pull/4973) Fix release script -- [X] [#4975](https://github.com/kubernetes/ingress-nginx/pull/4975) Fix docker installation in travis script -- [X] [#4976](https://github.com/kubernetes/ingress-nginx/pull/4976) Fix travis -- [X] [#4977](https://github.com/kubernetes/ingress-nginx/pull/4977) Fix image version -- [X] [#4983](https://github.com/kubernetes/ingress-nginx/pull/4983) Fix enable opentracing per location -- [X] [#4987](https://github.com/kubernetes/ingress-nginx/pull/4987) Dump kind logs after e2e tests -- [X] [#4993](https://github.com/kubernetes/ingress-nginx/pull/4993) Calculation algorithm for server_names_hash_bucket_size should consid… -- [X] [#4995](https://github.com/kubernetes/ingress-nginx/pull/4995) Cleanup main makefile and remove the need of sed -- [X] [#4996](https://github.com/kubernetes/ingress-nginx/pull/4996) Fix status update for clusters where networking.k8s.io is not available -- [X] [#4999](https://github.com/kubernetes/ingress-nginx/pull/4999) Fix limitrange definition -- [X] [#5000](https://github.com/kubernetes/ingress-nginx/pull/5000) Update python syntax in OAuth2 example -- [X] [#5003](https://github.com/kubernetes/ingress-nginx/pull/5003) Fix server aliases -- [X] [#5008](https://github.com/kubernetes/ingress-nginx/pull/5008) Fix docker buildx check in Makefile -- [X] [#5009](https://github.com/kubernetes/ingress-nginx/pull/5009) Move mod-security logic from template to go code -- [X] [#5010](https://github.com/kubernetes/ingress-nginx/pull/5010) Update nginx image -- [X] [#5011](https://github.com/kubernetes/ingress-nginx/pull/5011) Update nginx image, go to 1.13.7 and e2e image -- [X] [#5015](https://github.com/kubernetes/ingress-nginx/pull/5015) Refactor mirror feature -- [X] [#5016](https://github.com/kubernetes/ingress-nginx/pull/5016) Fix dep-ensure task -- [X] [#5023](https://github.com/kubernetes/ingress-nginx/pull/5023) Update metric dependencies and restore default Objectives -- [X] [#5028](https://github.com/kubernetes/ingress-nginx/pull/5028) Add echo image to avoid building and installing dependencies in each … -- [X] [#5031](https://github.com/kubernetes/ingress-nginx/pull/5031) Update kindest/node version to v1.17.2 -- [X] [#5032](https://github.com/kubernetes/ingress-nginx/pull/5032) Fix fortune-teller app manifest -- [X] [#5035](https://github.com/kubernetes/ingress-nginx/pull/5035) Update github.com/paultag/sniff dependency -- [X] [#5036](https://github.com/kubernetes/ingress-nginx/pull/5036) Disable DIND in script run-in-docker.sh -- [X] [#5038](https://github.com/kubernetes/ingress-nginx/pull/5038) Update code to use pault.ag/go/sniff package -- [X] [#5042](https://github.com/kubernetes/ingress-nginx/pull/5042) Fix X-Forwarded-Proto based on proxy-protocol server port -- [X] [#5050](https://github.com/kubernetes/ingress-nginx/pull/5050) Add flag to allow custom ingress status update intervals -- [X] [#5052](https://github.com/kubernetes/ingress-nginx/pull/5052) Change the handling of ConfigMap creation -- [X] [#5053](https://github.com/kubernetes/ingress-nginx/pull/5053) Validation of header in authreq should be done only in the key -- [X] [#5055](https://github.com/kubernetes/ingress-nginx/pull/5055) Only set mirror source when a target is configured -- [X] [#5059](https://github.com/kubernetes/ingress-nginx/pull/5059) Remove minikube and only use kind -- [X] [#5060](https://github.com/kubernetes/ingress-nginx/pull/5060) Cleanup e2e tests -- [X] [#5061](https://github.com/kubernetes/ingress-nginx/pull/5061) Fix scripts to run in osx -- [X] [#5062](https://github.com/kubernetes/ingress-nginx/pull/5062) Ensure scripts and dev-env works in osx -- [X] [#5067](https://github.com/kubernetes/ingress-nginx/pull/5067) Make sure set-cookie is retained from external auth endpoint -- [X] [#5069](https://github.com/kubernetes/ingress-nginx/pull/5069) Enable grpc e2e tests -- [X] [#5070](https://github.com/kubernetes/ingress-nginx/pull/5070) Update go to 1.13.8 -- [X] [#5071](https://github.com/kubernetes/ingress-nginx/pull/5071) Add gzip-min-length as a Configuration Option - -_Documentation:_ - -- [X] [#4974](https://github.com/kubernetes/ingress-nginx/pull/4974) Add travis script for docs -- [X] [#4991](https://github.com/kubernetes/ingress-nginx/pull/4991) doc: added hint why regular expressions might not be accepted -- [X] [#5018](https://github.com/kubernetes/ingress-nginx/pull/5018) Update developer document on dependency updates -- [X] [#5020](https://github.com/kubernetes/ingress-nginx/pull/5020) docs(deploy): fix helm install command for helm v3 -- [X] [#5037](https://github.com/kubernetes/ingress-nginx/pull/5037) Cleanup README.md -- [X] [#5040](https://github.com/kubernetes/ingress-nginx/pull/5040) Update documentation and remove hack fixed by upstream cookie library -- [X] [#5041](https://github.com/kubernetes/ingress-nginx/pull/5041) 36.94% size reduction of image assets using lossless compression from ImgBot -- [X] [#5043](https://github.com/kubernetes/ingress-nginx/pull/5043) Cleanup docs -- [X] [#5068](https://github.com/kubernetes/ingress-nginx/pull/5068) docs: reference buildx as a requirement for docker builds -- [X] [#5073](https://github.com/kubernetes/ingress-nginx/pull/5073) oauth-external-auth: README.md: Link to oauth2-proxy, dashboard-ingress.yaml - -### 0.28.0 - -**Image:** `quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.28.0` - -Fix occasional prometheus `http: superfluous response.WriteHeader call...` error [#4943](https://github.com/kubernetes/ingress-nginx/pull/4943) -Remove prometheus socket before the start of metrics collector [#4961](https://github.com/kubernetes/ingress-nginx/pull/4961) -Reduce CPU utilization when the ingress controller is shutting down [#4959](https://github.com/kubernetes/ingress-nginx/pull/4959) -Fixes a flaw (CVE-2020-8553) when auth-type basic annotation is used [#4960](https://github.com/kubernetes/ingress-nginx/pull/4960) - -_Changes:_ - -- [X] [#4912](https://github.com/kubernetes/ingress-nginx/pull/4912) Update README.md -- [X] [#4914](https://github.com/kubernetes/ingress-nginx/pull/4914) Disable docker in docker tasks in terraform release script -- [X] [#4932](https://github.com/kubernetes/ingress-nginx/pull/4932) Cleanup dev-env script -- [X] [#4943](https://github.com/kubernetes/ingress-nginx/pull/4943) Update client_golang dependency to v1.3.0 -- [X] [#4956](https://github.com/kubernetes/ingress-nginx/pull/4956) Fix proxy protocol support for X-Forwarded-Port -- [X] [#4959](https://github.com/kubernetes/ingress-nginx/pull/4959) Refactor how to handle sigterm and nginx process goroutine -- [X] [#4960](https://github.com/kubernetes/ingress-nginx/pull/4960) Avoid overlap of configuration definitions -- [X] [#4961](https://github.com/kubernetes/ingress-nginx/pull/4961) Remove prometheus socket before listen -- [X] [#4962](https://github.com/kubernetes/ingress-nginx/pull/4962) Cleanup of e2e docker images -- [X] [#4965](https://github.com/kubernetes/ingress-nginx/pull/4965) Move opentracing configuration for location to go -- [X] [#4966](https://github.com/kubernetes/ingress-nginx/pull/4966) Add verification of docker buildx support -- [X] [#4967](https://github.com/kubernetes/ingress-nginx/pull/4967) Update go dependencies - -### 0.27.1 - -**Image:** `quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.27.1` - -Fix regression in Jaeger opentracing module, incorrect UID in webhook AdmissionResponse in Kubernetes > 1.16.0. - -_Changes:_ - -- [X] [#4920](https://github.com/kubernetes/ingress-nginx/pull/4920) Rollback jaeger module version -- [X] [#4922](https://github.com/kubernetes/ingress-nginx/pull/4922) Use docker buildx and remove qemu-static -- [X] [#4927](https://github.com/kubernetes/ingress-nginx/pull/4927) Fix incorrect UID in webhook AdmissionResponse - -### 0.27.0 - -**Image:** `quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.27.0` - -_New Features:_ - -- NGINX 1.17.7 -- Migration to alpinelinux. -- Global [Modsecurity Snippet via ConfigMap](https://github.com/kubernetes/ingress-nginx/pull/4087) -- Support Datadog sample rate with global trace sampling from configmap [#4897](https://github.com/kubernetes/ingress-nginx/pull/4897) -- Modsecurity CRS v3.2.0 [#4829](https://github.com/kubernetes/ingress-nginx/pull/4829) -- Modsecurity-nginx v1.0.1 [#4842](https://github.com/kubernetes/ingress-nginx/pull/4842) -- Allow enabling/disabling opentracing for ingresses [#4732](https://github.com/kubernetes/ingress-nginx/pull/4732) - -_Breaking Changes:_ - -- Enable download of GeoLite2 databases [#4896](https://github.com/kubernetes/ingress-nginx/pull/4896) - - _From maxmind website:_ - - ``` - Due to upcoming data privacy regulations, we are making significant changes to how you access free GeoLite2 databases starting December 30, 2019. - Learn more on our blog https://blog.maxmind.com/2019/12/significant-changes-to-accessing-and-using-geolite2-databases/ - ``` - - Because of this change, it is not clear we can provide the databases directly from the docker image. - To enable the feature, we provide two options: - - Add the flag `--maxmind-license-key` to download the databases when the ingress controller starts. - - or add a volume to mount the files `GeoLite2-City.mmdb` and `GeoLite2-ASN.mmdb` in the directory `/etc/nginx/geoip`. - - **If any of these conditions are not met, the geoip2 module will be disabled** - -- The feature `lua-resty-waf` was removed. - -- Due to the migration to alpinelinux the uid of the user is different. Please make sure to update it `runAsUser: 101` or the ingress controller will not start (CrashLoopBackOff). - -_Changes:_ - -- [X] [#4087](https://github.com/kubernetes/ingress-nginx/pull/4087) Define Modsecurity Snippet via ConfigMap -- [X] [#4603](https://github.com/kubernetes/ingress-nginx/pull/4603) optimize: local cache global variable and reduce string object creation. -- [X] [#4613](https://github.com/kubernetes/ingress-nginx/pull/4613) Terraform release -- [X] [#4619](https://github.com/kubernetes/ingress-nginx/pull/4619) Issue 4244 -- [X] [#4620](https://github.com/kubernetes/ingress-nginx/pull/4620) ISSUE-4244 e2e test -- [X] [#4645](https://github.com/kubernetes/ingress-nginx/pull/4645) Bind ingress controller to linux nodes to avoid Windows scheduling on kubernetes cluster includes linux nodes and windows nodes -- [X] [#4650](https://github.com/kubernetes/ingress-nginx/pull/4650) Expose GeoIP2 Organization as variable $geoip2_org -- [X] [#4658](https://github.com/kubernetes/ingress-nginx/pull/4658) Need to quote expansion of `$cfg.LogFormatStream` in `log_stream` access log -- [X] [#4664](https://github.com/kubernetes/ingress-nginx/pull/4664) warn when ConfigMap is missing or not parsable instead of erroring -- [X] [#4669](https://github.com/kubernetes/ingress-nginx/pull/4669) Simplify initialization function of bytes.Buffer -- [X] [#4671](https://github.com/kubernetes/ingress-nginx/pull/4671) Discontinue use of a single DNS query to validate an endpoint name -- [X] [#4673](https://github.com/kubernetes/ingress-nginx/pull/4673) More helpful dns error -- [X] [#4678](https://github.com/kubernetes/ingress-nginx/pull/4678) Increase the kubernetes 1.14 version to the installation prompt -- [X] [#4689](https://github.com/kubernetes/ingress-nginx/pull/4689) Server-only authentication of backends and per-location SSL config -- [X] [#4693](https://github.com/kubernetes/ingress-nginx/pull/4693) Adding some documentation about the use of metrics-per-host and enabl… -- [X] [#4694](https://github.com/kubernetes/ingress-nginx/pull/4694) Enhancement : add remote_addr in TCP access log -- [X] [#4695](https://github.com/kubernetes/ingress-nginx/pull/4695) Removing secure-verify-ca-secret support -- [X] [#4700](https://github.com/kubernetes/ingress-nginx/pull/4700) adds hability to use externalIP when controller service is of type NodePort -- [X] [#4730](https://github.com/kubernetes/ingress-nginx/pull/4730) add configuration for http2_max_concurrent_streams -- [X] [#4732](https://github.com/kubernetes/ingress-nginx/pull/4732) Allow enabling/disabling opentracing for ingresses -- [X] [#4745](https://github.com/kubernetes/ingress-nginx/pull/4745) add cmluciano to owners -- [X] [#4747](https://github.com/kubernetes/ingress-nginx/pull/4747) Docker image: Add source code reference label -- [X] [#4766](https://github.com/kubernetes/ingress-nginx/pull/4766) dev-env.sh: fix for parsing `minikube status` output of newer versions, fix shellcheck lints -- [X] [#4779](https://github.com/kubernetes/ingress-nginx/pull/4779) Remove lua-resty-waf feature -- [X] [#4780](https://github.com/kubernetes/ingress-nginx/pull/4780) Update nginx image to use openresty master -- [X] [#4785](https://github.com/kubernetes/ingress-nginx/pull/4785) Update nginx image and Go to 1.13.4 -- [X] [#4791](https://github.com/kubernetes/ingress-nginx/pull/4791) deploy: add protocol to all Container/ServicePorts -- [X] [#4793](https://github.com/kubernetes/ingress-nginx/pull/4793) Fix issue in logic of modsec template -- [X] [#4794](https://github.com/kubernetes/ingress-nginx/pull/4794) Remove extra annotation when Enabling ModSecurity -- [X] [#4797](https://github.com/kubernetes/ingress-nginx/pull/4797) Add a datasource variable $DS_PROMETHEUS -- [X] [#4803](https://github.com/kubernetes/ingress-nginx/pull/4803) Update nginx image to fix regression in jaeger tracing -- [X] [#4805](https://github.com/kubernetes/ingress-nginx/pull/4805) Update nginx and e2e images -- [X] [#4806](https://github.com/kubernetes/ingress-nginx/pull/4806) Add log to parallel command to dump logs in case of errors -- [X] [#4807](https://github.com/kubernetes/ingress-nginx/pull/4807) Allow custom CA certificate when flag --api-server is specified -- [X] [#4813](https://github.com/kubernetes/ingress-nginx/pull/4813) Update default SSL ciphers -- [X] [#4816](https://github.com/kubernetes/ingress-nginx/pull/4816) apply default certificate again in cases of invalid or incomplete cert config -- [X] [#4823](https://github.com/kubernetes/ingress-nginx/pull/4823) Update go dependencies to v1.17.0 -- [X] [#4826](https://github.com/kubernetes/ingress-nginx/pull/4826) regression test and fix for duplicate hsts bug -- [X] [#4827](https://github.com/kubernetes/ingress-nginx/pull/4827) Migrate ingress definitions from extensions to networking.k8s.io -- [X] [#4829](https://github.com/kubernetes/ingress-nginx/pull/4829) Update modsecurity crs to v3.2.0 -- [X] [#4840](https://github.com/kubernetes/ingress-nginx/pull/4840) Return specific type -- [X] [#4842](https://github.com/kubernetes/ingress-nginx/pull/4842) Update Modsecurity-nginx to latest (v1.0.1) -- [X] [#4843](https://github.com/kubernetes/ingress-nginx/pull/4843) Define minimum limits to run the ingress controller -- [X] [#4848](https://github.com/kubernetes/ingress-nginx/pull/4848) Update nginx image -- [X] [#4859](https://github.com/kubernetes/ingress-nginx/pull/4859) Use a named location for authSignURL -- [X] [#4862](https://github.com/kubernetes/ingress-nginx/pull/4862) Update nginx image -- [X] [#4863](https://github.com/kubernetes/ingress-nginx/pull/4863) Switch to nginx again -- [X] [#4866](https://github.com/kubernetes/ingress-nginx/pull/4866) Improve issue and pull request template -- [X] [#4867](https://github.com/kubernetes/ingress-nginx/pull/4867) Fix sticky session for ingress without host -- [X] [#4870](https://github.com/kubernetes/ingress-nginx/pull/4870) Default backend protocol only supports http -- [X] [#4871](https://github.com/kubernetes/ingress-nginx/pull/4871) Fix ingress status regression introduced in #4490 -- [X] [#4875](https://github.com/kubernetes/ingress-nginx/pull/4875) Remove /build endpoint -- [X] [#4880](https://github.com/kubernetes/ingress-nginx/pull/4880) Remove download of geoip databases -- [X] [#4882](https://github.com/kubernetes/ingress-nginx/pull/4882) Use yaml files from a particular tag, not from master -- [X] [#4883](https://github.com/kubernetes/ingress-nginx/pull/4883) Update e2e image -- [X] [#4884](https://github.com/kubernetes/ingress-nginx/pull/4884) Update e2e image -- [X] [#4886](https://github.com/kubernetes/ingress-nginx/pull/4886) Fix flaking e2e tests -- [X] [#4887](https://github.com/kubernetes/ingress-nginx/pull/4887) Master branch uses a master tag image -- [X] [#4891](https://github.com/kubernetes/ingress-nginx/pull/4891) Add help task -- [X] [#4893](https://github.com/kubernetes/ingress-nginx/pull/4893) Use docker to run makefile tasks -- [X] [#4894](https://github.com/kubernetes/ingress-nginx/pull/4894) Remove todo from lua test -- [X] [#4896](https://github.com/kubernetes/ingress-nginx/pull/4896) Enable download of GeoLite2 databases -- [X] [#4897](https://github.com/kubernetes/ingress-nginx/pull/4897) Support Datadog sample rate with global trace sampling from configmap -- [X] [#4907](https://github.com/kubernetes/ingress-nginx/pull/4907) Add script to check go version and fix output directory permissions - -_Documentation:_ - -- [X] [#4623](https://github.com/kubernetes/ingress-nginx/pull/4623) remove duplicated line in docs -- [X] [#4681](https://github.com/kubernetes/ingress-nginx/pull/4681) Fix docs/development.md describing inaccurate issues -- [X] [#4683](https://github.com/kubernetes/ingress-nginx/pull/4683) Fixed upgrading example command -- [X] [#4708](https://github.com/kubernetes/ingress-nginx/pull/4708) add proxy-max-temp-file-size doc -- [X] [#4727](https://github.com/kubernetes/ingress-nginx/pull/4727) update docs, remove output in prometheus deploy command -- [X] [#4744](https://github.com/kubernetes/ingress-nginx/pull/4744) Fix generation of sitemap.xml file -- [X] [#4746](https://github.com/kubernetes/ingress-nginx/pull/4746) Fix broken links in documentation -- [X] [#4748](https://github.com/kubernetes/ingress-nginx/pull/4748) Update documentation for static ip example -- [X] [#4749](https://github.com/kubernetes/ingress-nginx/pull/4749) Update documentation for rate limiting -- [X] [#4765](https://github.com/kubernetes/ingress-nginx/pull/4765) Fix extra word -- [X] [#4777](https://github.com/kubernetes/ingress-nginx/pull/4777) [docs] Add info about x-forwarded-prefix breaking change -- [X] [#4800](https://github.com/kubernetes/ingress-nginx/pull/4800) Update sysctl example -- [X] [#4801](https://github.com/kubernetes/ingress-nginx/pull/4801) Fix markdown list -- [X] [#4849](https://github.com/kubernetes/ingress-nginx/pull/4849) Fixed documentation for FCGI annotation. -- [X] [#4885](https://github.com/kubernetes/ingress-nginx/pull/4885) Correct MetalLB setup instructions. - -### 0.26.2 - -**Image:** `quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.26.2` - -_Changes:_ - -- [X] [#4859](https://github.com/kubernetes/ingress-nginx/pull/4859) Use a named location for authSignURL - -### 0.26.1 - -**Image:** `quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.26.1` - -_Changes:_ - -- [X] [#4617](https://github.com/kubernetes/ingress-nginx/pull/4617) Fix ports collision when hostNetwork=true -- [X] [#4619](https://github.com/kubernetes/ingress-nginx/pull/4619) Fix issue #4244 - -### 0.26.0 - -**Image:** `quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.26.0` - -_New Features:_ - -- Add support for NGINX [proxy_ssl_* directives](https://github.com/kubernetes/ingress-nginx/pull/4327) -- Add support for [FastCGI backends](https://github.com/kubernetes/ingress-nginx/pull/4344) -- [Only support SSL dynamic mode](https://github.com/kubernetes/ingress-nginx/pull/4356) -- [Add nginx ssl_early_data option support](https://github.com/kubernetes/ingress-nginx/pull/4412) -- [Add support for multiple alias and remove duplication of SSL certificates](https://github.com/kubernetes/ingress-nginx/pull/4472) -- [Support configuring basic auth credentials as a map of user/password hashes](https://github.com/kubernetes/ingress-nginx/pull/4560) -- Caching support for external authentication annotation with new annotations [auth-cache-key and auth-cache-duration](https://github.com/kubernetes/ingress-nginx/pull/4278) -- Allow Requests to be [Mirrored to different backends](https://kubernetes.github.io/ingress-nginx/user-guide/nginx-configuration/annotations/#mirror) [#4379](https://github.com/kubernetes/ingress-nginx/pull/4379) -- Improve connection draining when ingress controller pod is deleted using a lifecycle hook: - - With this new hook, we increased the default `terminationGracePeriodSeconds` from 30 seconds to 300, allowing the draining of connections up to five minutes. - - If the active connections end before that, the pod will terminate gracefully at that time. - - To effectively take advantage of this feature, the Configmap feature [worker-shutdown-timeout](https://kubernetes.github.io/ingress-nginx/user-guide/nginx-configuration/configmap/#worker-shutdown-timeout) new value is `240s` instead of `10s`. - - **IMPORTANT:** this value has a side effect during reloads, consuming more memory until the old NGINX workers are replaced. - - ```yaml - lifecycle: - preStop: - exec: - command: - - /wait-shutdown - ``` - -- [mimalloc](https://github.com/microsoft/mimalloc) as a drop-in replacement for malloc. - - This feature can be enabled using the [LD_PRELOAD](http://man7.org/linux/man-pages/man8/ld.so.8.html) environment variable in the ingress controller deployment - - Example: - - ```yaml - env: - - name: LD_PRELOAD - value: /usr/local/lib/libmimalloc.so - ``` - - Please check the additional [options](https://github.com/microsoft/mimalloc#environment-options) it provides. - -_Breaking Changes:_ - -- The variable [$the_real_ip variable](https://github.com/kubernetes/ingress-nginx/pull/4557) was removed from template and default `log_format`. -- The default value of configmap setting [proxy-add-original-uri-header](https://github.com/kubernetes/ingress-nginx/pull/4604) is now `"false"`. - - When the setting `proxy-add-original-uri-header` is `"true"`, the ingress controller adds a new header `X-Original-Uri` with the value of NGINX variable `$request_uri`. - - In most of the cases this is not an issue but with request with long URLs it could lead to unexpected errors in the application defined in the Ingress serviceName, - like issue 4593 - [431 Request Header Fields Too Large](https://github.com/kubernetes/ingress-nginx/issues/4593) - -_Non-functional improvements:_ - -- [Removal of internal NGINX unix sockets](https://github.com/kubernetes/ingress-nginx/pull/4531) -- Automation of NGINX image using [terraform scripts](https://github.com/kubernetes/ingress-nginx/pull/4484) -- Removal of Go profiling on port `:10254` to use `localhost:10245` - - To profile the ingress controller Go binary, use: - - ```console - INGRESS_PODS=($(kubectl get pods -n ingress-nginx -l app.kubernetes.io/name=ingress-nginx -o 'jsonpath={..metadata.name}')) - kubectl port-forward -n ingress-nginx pod/${INGRESS_PODS[0]} 10245 - ``` - -Using the URL http://localhost:10245/debug/pprof/ to reach the profiler. - -_Changes:_ - -- [X] [#3164](https://github.com/kubernetes/ingress-nginx/pull/3164) Initial support for CRL in Ingress Controller -- [X] [#4086](https://github.com/kubernetes/ingress-nginx/pull/4086) Resolve #4038, move X-Forwarded-Port variable to the location context -- [X] [#4278](https://github.com/kubernetes/ingress-nginx/pull/4278) feat: auth-req caching -- [X] [#4286](https://github.com/kubernetes/ingress-nginx/pull/4286) fix lua lints -- [X] [#4287](https://github.com/kubernetes/ingress-nginx/pull/4287) Add script for luacheck -- [X] [#4288](https://github.com/kubernetes/ingress-nginx/pull/4288) added proxy-http-version annotation to override the HTTP/1.1 default … -- [X] [#4289](https://github.com/kubernetes/ingress-nginx/pull/4289) Apply fixes suggested by staticcheck -- [X] [#4290](https://github.com/kubernetes/ingress-nginx/pull/4290) Make dev-env.sh script work on Linux -- [X] [#4291](https://github.com/kubernetes/ingress-nginx/pull/4291) hack scripts do not need PKG var -- [X] [#4298](https://github.com/kubernetes/ingress-nginx/pull/4298) Fix RBAC issues with networking.k8s.io -- [X] [#4299](https://github.com/kubernetes/ingress-nginx/pull/4299) Fix scripts to be able to run tests in docker -- [X] [#4302](https://github.com/kubernetes/ingress-nginx/pull/4302) Squash rules regarding ingresses -- [X] [#4306](https://github.com/kubernetes/ingress-nginx/pull/4306) Remove unnecessary output -- [X] [#4307](https://github.com/kubernetes/ingress-nginx/pull/4307) Disable access log in stream section for configuration socket -- [X] [#4313](https://github.com/kubernetes/ingress-nginx/pull/4313) avoid warning during lua unit test -- [X] [#4322](https://github.com/kubernetes/ingress-nginx/pull/4322) Update go dependencies -- [X] [#4327](https://github.com/kubernetes/ingress-nginx/pull/4327) Add proxy_ssl_* directives -- [X] [#4333](https://github.com/kubernetes/ingress-nginx/pull/4333) Add [$proxy_alternative_upstream_name] -- [X] [#4334](https://github.com/kubernetes/ingress-nginx/pull/4334) Refactor http client for unix sockets -- [X] [#4341](https://github.com/kubernetes/ingress-nginx/pull/4341) duplicate argument "--disable-catch-all" -- [X] [#4344](https://github.com/kubernetes/ingress-nginx/pull/4344) Add FastCGI backend support (#2982) -- [X] [#4356](https://github.com/kubernetes/ingress-nginx/pull/4356) Only support SSL dynamic mode -- [X] [#4365](https://github.com/kubernetes/ingress-nginx/pull/4365) memoize balancer for a request -- [X] [#4369](https://github.com/kubernetes/ingress-nginx/pull/4369) Fix broken test's filenames -- [X] [#4371](https://github.com/kubernetes/ingress-nginx/pull/4371) Update datadog tracing plugin to v1.0.1 -- [X] [#4379](https://github.com/kubernetes/ingress-nginx/pull/4379) Allow Requests to be Mirrored to different backends -- [X] [#4383](https://github.com/kubernetes/ingress-nginx/pull/4383) Add support for psp -- [X] [#4386](https://github.com/kubernetes/ingress-nginx/pull/4386) Update go dependencies -- [X] [#4405](https://github.com/kubernetes/ingress-nginx/pull/4405) Lua shared cfg -- [X] [#4409](https://github.com/kubernetes/ingress-nginx/pull/4409) sort ingress by namespace and name when ingress.CreationTimestamp identical -- [X] [#4410](https://github.com/kubernetes/ingress-nginx/pull/4410) fix dev-env script -- [X] [#4412](https://github.com/kubernetes/ingress-nginx/pull/4412) Add nginx ssl_early_data option support -- [X] [#4415](https://github.com/kubernetes/ingress-nginx/pull/4415) more dev-env script improvements -- [X] [#4416](https://github.com/kubernetes/ingress-nginx/pull/4416) Remove invalid log "Failed to executing diff command: exit status 1" -- [X] [#4418](https://github.com/kubernetes/ingress-nginx/pull/4418) Remove dynamic TLS records -- [X] [#4420](https://github.com/kubernetes/ingress-nginx/pull/4420) Cleanup -- [X] [#4422](https://github.com/kubernetes/ingress-nginx/pull/4422) teach lua about search and ndots settings in resolv.conf -- [X] [#4423](https://github.com/kubernetes/ingress-nginx/pull/4423) Add quote function in template -- [X] [#4426](https://github.com/kubernetes/ingress-nginx/pull/4426) Update klog -- [X] [#4428](https://github.com/kubernetes/ingress-nginx/pull/4428) Add timezone value into $geoip2_time_zone variable -- [X] [#4435](https://github.com/kubernetes/ingress-nginx/pull/4435) Add option to use existing images -- [X] [#4437](https://github.com/kubernetes/ingress-nginx/pull/4437) Refactor version helper -- [X] [#4438](https://github.com/kubernetes/ingress-nginx/pull/4438) Add helper to extract prometheus metrics in e2e tests -- [X] [#4439](https://github.com/kubernetes/ingress-nginx/pull/4439) Move listen logic to go -- [X] [#4440](https://github.com/kubernetes/ingress-nginx/pull/4440) Fixes for CVE-2018-16843, CVE-2018-16844, CVE-2019-9511, CVE-2019-9513, and CVE-2019-9516 -- [X] [#4443](https://github.com/kubernetes/ingress-nginx/pull/4443) Lua resolv conf parser -- [X] [#4445](https://github.com/kubernetes/ingress-nginx/pull/4445) use latest openresty with CVE patches -- [X] [#4446](https://github.com/kubernetes/ingress-nginx/pull/4446) lua-shared-dicts improvements, fixes and documentation -- [X] [#4448](https://github.com/kubernetes/ingress-nginx/pull/4448) ewma improvements -- [X] [#4449](https://github.com/kubernetes/ingress-nginx/pull/4449) Fix service type external name using the name -- [X] [#4450](https://github.com/kubernetes/ingress-nginx/pull/4450) Add nginx proxy_max_temp_file_size configuration option -- [X] [#4451](https://github.com/kubernetes/ingress-nginx/pull/4451) post data to Lua only if it changes -- [X] [#4452](https://github.com/kubernetes/ingress-nginx/pull/4452) Fix test description on error -- [X] [#4456](https://github.com/kubernetes/ingress-nginx/pull/4456) Fix file permissions to support volumes -- [X] [#4458](https://github.com/kubernetes/ingress-nginx/pull/4458) implementation proposal for zone aware routing -- [X] [#4459](https://github.com/kubernetes/ingress-nginx/pull/4459) cleanup logging message typos in rewrite.go -- [X] [#4460](https://github.com/kubernetes/ingress-nginx/pull/4460) cleanup: fix typos in framework.go -- [X] [#4463](https://github.com/kubernetes/ingress-nginx/pull/4463) Always set headers with add-headers option -- [X] [#4466](https://github.com/kubernetes/ingress-nginx/pull/4466) Add rate limit units and error status -- [X] [#4471](https://github.com/kubernetes/ingress-nginx/pull/4471) Lint code using staticcheck -- [X] [#4472](https://github.com/kubernetes/ingress-nginx/pull/4472) Add support for multiple alias and remove duplication of SSL certificates -- [X] [#4476](https://github.com/kubernetes/ingress-nginx/pull/4476) Initialize nginx process error channel -- [X] [#4478](https://github.com/kubernetes/ingress-nginx/pull/4478) Re-add Support for Wildcard Hosts with Sticky Sessions -- [X] [#4484](https://github.com/kubernetes/ingress-nginx/pull/4484) Add terraform scripts to build nginx image -- [X] [#4487](https://github.com/kubernetes/ingress-nginx/pull/4487) Refactor health checks and wait until NGINX process ends -- [X] [#4489](https://github.com/kubernetes/ingress-nginx/pull/4489) Fix log format markdown -- [X] [#4490](https://github.com/kubernetes/ingress-nginx/pull/4490) Refactor ingress status IP address -- [X] [#4492](https://github.com/kubernetes/ingress-nginx/pull/4492) fix lua certificate handling tests -- [X] [#4495](https://github.com/kubernetes/ingress-nginx/pull/4495) point users to kubectl ingress-nginx plugin -- [X] [#4500](https://github.com/kubernetes/ingress-nginx/pull/4500) Fix nginx variable service_port (nginx) -- [X] [#4501](https://github.com/kubernetes/ingress-nginx/pull/4501) Move nginx helper -- [X] [#4502](https://github.com/kubernetes/ingress-nginx/pull/4502) Remove hard-coded names from e2e test and use local docker dependencies -- [X] [#4506](https://github.com/kubernetes/ingress-nginx/pull/4506) Fix panic on multiple ingress mess up upstream is primary or not -- [X] [#4509](https://github.com/kubernetes/ingress-nginx/pull/4509) Update openresty and third party modules -- [X] [#4520](https://github.com/kubernetes/ingress-nginx/pull/4520) fix typo -- [X] [#4521](https://github.com/kubernetes/ingress-nginx/pull/4521) backward compatibility for k8s version < 1.14 -- [X] [#4522](https://github.com/kubernetes/ingress-nginx/pull/4522) Fix relative links -- [X] [#4524](https://github.com/kubernetes/ingress-nginx/pull/4524) Update go dependencies -- [X] [#4527](https://github.com/kubernetes/ingress-nginx/pull/4527) Switch to official kind images -- [X] [#4528](https://github.com/kubernetes/ingress-nginx/pull/4528) Cleanup of docker images -- [X] [#4530](https://github.com/kubernetes/ingress-nginx/pull/4530) Update nginx image to 0.92 -- [X] [#4531](https://github.com/kubernetes/ingress-nginx/pull/4531) Remove nginx unix sockets -- [X] [#4534](https://github.com/kubernetes/ingress-nginx/pull/4534) Show current reloads count, not total -- [X] [#4535](https://github.com/kubernetes/ingress-nginx/pull/4535) Improve the time to run e2e tests -- [X] [#4543](https://github.com/kubernetes/ingress-nginx/pull/4543) Correctly format ipv6 resolver config for lua -- [X] [#4545](https://github.com/kubernetes/ingress-nginx/pull/4545) Rollback luarocks version to 3.1.3 -- [X] [#4547](https://github.com/kubernetes/ingress-nginx/pull/4547) Fix terraform build of nginx images -- [X] [#4548](https://github.com/kubernetes/ingress-nginx/pull/4548) regression test for the issue fixed in #4543 -- [X] [#4549](https://github.com/kubernetes/ingress-nginx/pull/4549) Cleanup of docker build -- [X] [#4556](https://github.com/kubernetes/ingress-nginx/pull/4556) Allow multiple CA Certificates -- [X] [#4557](https://github.com/kubernetes/ingress-nginx/pull/4557) Remove the_real_ip variable -- [X] [#4560](https://github.com/kubernetes/ingress-nginx/pull/4560) Support configuring basic auth credentials as a map of user/password hashes -- [X] [#4569](https://github.com/kubernetes/ingress-nginx/pull/4569) allow to configure jaeger header names -- [X] [#4570](https://github.com/kubernetes/ingress-nginx/pull/4570) Update nginx image -- [X] [#4571](https://github.com/kubernetes/ingress-nginx/pull/4571) Increase log level for identical CreationTimestamp warning -- [X] [#4572](https://github.com/kubernetes/ingress-nginx/pull/4572) Fix log format after #4557 -- [X] [#4575](https://github.com/kubernetes/ingress-nginx/pull/4575) Update go dependencies for kubernetes 1.16.0 -- [X] [#4583](https://github.com/kubernetes/ingress-nginx/pull/4583) Disable go modules -- [X] [#4584](https://github.com/kubernetes/ingress-nginx/pull/4584) Remove retries to ExternalName -- [X] [#4586](https://github.com/kubernetes/ingress-nginx/pull/4586) Fix reload when a configmap changes -- [X] [#4587](https://github.com/kubernetes/ingress-nginx/pull/4587) Avoid unnecessary reloads generating lua_shared_dict directives -- [X] [#4591](https://github.com/kubernetes/ingress-nginx/pull/4591) optimize: local cache global variable and avoid single lines over 80 -- [X] [#4592](https://github.com/kubernetes/ingress-nginx/pull/4592) refactor force ssl redirect logic -- [X] [#4594](https://github.com/kubernetes/ingress-nginx/pull/4594) cleanup unused certificates -- [X] [#4595](https://github.com/kubernetes/ingress-nginx/pull/4595) Rollback change of ModSecurity setting SecAuditLog -- [X] [#4596](https://github.com/kubernetes/ingress-nginx/pull/4596) sort auth proxy headers from configmap -- [X] [#4597](https://github.com/kubernetes/ingress-nginx/pull/4597) more meaningful assertion for tls hsts test -- [X] [#4598](https://github.com/kubernetes/ingress-nginx/pull/4598) delete redundant config -- [X] [#4600](https://github.com/kubernetes/ingress-nginx/pull/4600) Update nginx image -- [X] [#4601](https://github.com/kubernetes/ingress-nginx/pull/4601) Hsts refactoring -- [X] [#4602](https://github.com/kubernetes/ingress-nginx/pull/4602) fix bug with new and running configuration comparison -- [X] [#4604](https://github.com/kubernetes/ingress-nginx/pull/4604) Change default for proxy-add-original-uri-header -- [X] [#4606](https://github.com/kubernetes/ingress-nginx/pull/4606) Mount temporal directory volume for ingress controller -- [X] [#4611](https://github.com/kubernetes/ingress-nginx/pull/4611) Fix custom default backend switch to default - -_Documentation:_ - -- [X] [#4277](https://github.com/kubernetes/ingress-nginx/pull/4277) doc: fix image link. -- [X] [#4316](https://github.com/kubernetes/ingress-nginx/pull/4316) Update how-it-works.md -- [X] [#4329](https://github.com/kubernetes/ingress-nginx/pull/4329) Update references to oauth2_proxy -- [X] [#4348](https://github.com/kubernetes/ingress-nginx/pull/4348) KEP process -- [X] [#4351](https://github.com/kubernetes/ingress-nginx/pull/4351) KEP: Remove static SSL configuration mode -- [X] [#4389](https://github.com/kubernetes/ingress-nginx/pull/4389) Fix docs build due to an invalid link -- [X] [#4455](https://github.com/kubernetes/ingress-nginx/pull/4455) KEP: availability zone aware routing -- [X] [#4581](https://github.com/kubernetes/ingress-nginx/pull/4581) Fix spelling and remove local reference of 404 docker image -- [X] [#4582](https://github.com/kubernetes/ingress-nginx/pull/4582) Update kubectl-plugin docs -- [X] [#4588](https://github.com/kubernetes/ingress-nginx/pull/4588) tls user guide --default-ssl-certificate clarification - -### 0.25.1 - -**Image:** `quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.25.1` - -_Changes:_ - -- [X] [#4440](https://github.com/kubernetes/ingress-nginx/pull/4440) Fixes for CVE-2018-16843, CVE-2018-16844, CVE-2019-9511, CVE-2019-9513, and CVE-2019-9516 - -### 0.25.0 - -**Image:** `quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.25.0` - -_New Features:_ - -- Validating webhook for ingress sanity check [documentation](https://kubernetes.github.io/ingress-nginx/deploy/validating-webhook/) -- Migration from NGINX to [OpenResty](https://openresty.org/en/) 1.15.8 -- [ARM image](https://quay.io/repository/kubernetes-ingress-controller/nginx-ingress-controller-arm?tab=logs) -- Improve external authorization concept from opt-in to secure-by-default [3506](https://github.com/kubernetes/ingress-nginx/pull/3506) -- Reduce memory footprint and cpu usage when modsecurity is enabled [4091](https://github.com/kubernetes/ingress-nginx/pull/4091) -- Support new `networking.k8s.io/v1beta1` package (for Kubernetes cluster > v1.14.0) [4127](https://github.com/kubernetes/ingress-nginx/pull/4127) -- New variable `$proxy_alternative_upstream_name` in the log to show a hit in a canary endpoint [#4246](https://github.com/kubernetes/ingress-nginx/pull/4246) - -_Non-functional improvements:_ - -- Migration from travis-ci to [Prow](https://prow.k8s.io/tide-history?repo=kubernetes%2Fingress-nginx&branch=master) -- [Testgrid dashboards](https://testgrid.k8s.io/sig-network-ingress-nginx#Summary) for ingress-nginx -- Update kind to [v0.4.0](https://github.com/kubernetes-sigs/kind/releases/tag/v0.4.0) -- Switch to go modules -- Go v1.12.6 -- Docker size image reduced by 20% - -_Changes:_ - -- [X] [#3506](https://github.com/kubernetes/ingress-nginx/pull/3506) Improve the external authorization concept from opt-in to secure-by-default -- [X] [#3802](https://github.com/kubernetes/ingress-nginx/pull/3802) Add a validating webhook for ingress sanity check -- [X] [#3803](https://github.com/kubernetes/ingress-nginx/pull/3803) use nkeys for counting lua table elements -- [X] [#3852](https://github.com/kubernetes/ingress-nginx/pull/3852) Enable arm again -- [X] [#4004](https://github.com/kubernetes/ingress-nginx/pull/4004) Remove valgrind -- [X] [#4005](https://github.com/kubernetes/ingress-nginx/pull/4005) Support proxy_next_upstream_timeout -- [X] [#4008](https://github.com/kubernetes/ingress-nginx/pull/4008) refactor GetFakeSSLCert -- [X] [#4009](https://github.com/kubernetes/ingress-nginx/pull/4009) Update nginx to 1.15.12 -- [X] [#4010](https://github.com/kubernetes/ingress-nginx/pull/4010) Update nginx image and Go to 1.12.4 -- [X] [#4012](https://github.com/kubernetes/ingress-nginx/pull/4012) Switch to go modules -- [X] [#4022](https://github.com/kubernetes/ingress-nginx/pull/4022) Add e2e test coverage for mult-auth -- [X] [#4042](https://github.com/kubernetes/ingress-nginx/pull/4042) Release custom error pages image v0.4 [skip-ci] -- [X] [#4048](https://github.com/kubernetes/ingress-nginx/pull/4048) Change upstream on error when sticky session balancer is used -- [X] [#4055](https://github.com/kubernetes/ingress-nginx/pull/4055) Rearrange deployment files into kustomizations -- [X] [#4064](https://github.com/kubernetes/ingress-nginx/pull/4064) Update go to 1.12.5, kubectl to 1.14.1 and kind to 0.2.1 -- [X] [#4067](https://github.com/kubernetes/ingress-nginx/pull/4067) Trim spaces from annotations that can contain multiple lines -- [X] [#4069](https://github.com/kubernetes/ingress-nginx/pull/4069) fix e2e-test make target -- [X] [#4070](https://github.com/kubernetes/ingress-nginx/pull/4070) Don't try to create e2e runner rbac resources twice -- [X] [#4080](https://github.com/kubernetes/ingress-nginx/pull/4080) Load modsecurity config with OWASP core rules -- [X] [#4088](https://github.com/kubernetes/ingress-nginx/pull/4088) Migrate to Prow -- [X] [#4091](https://github.com/kubernetes/ingress-nginx/pull/4091) reduce memory footprint and cpu usage when modsecurity and owasp rule -- [X] [#4100](https://github.com/kubernetes/ingress-nginx/pull/4100) Remove stop controller endpoint -- [X] [#4101](https://github.com/kubernetes/ingress-nginx/pull/4101) Refactor whitelist from map to standard allow directives -- [X] [#4102](https://github.com/kubernetes/ingress-nginx/pull/4102) Refactor ListIngresses to add filters -- [X] [#4105](https://github.com/kubernetes/ingress-nginx/pull/4105) UPT: Add variable to define custom sampler host and port -- [X] [#4108](https://github.com/kubernetes/ingress-nginx/pull/4108) Add retry to LookupHost used to check the content of ExternalName -- [X] [#4109](https://github.com/kubernetes/ingress-nginx/pull/4109) Use real apiserver -- [X] [#4110](https://github.com/kubernetes/ingress-nginx/pull/4110) Update e2e images -- [X] [#4113](https://github.com/kubernetes/ingress-nginx/pull/4113) Force GOOS to linux -- [X] [#4119](https://github.com/kubernetes/ingress-nginx/pull/4119) Only load module ngx_http_modsecurity_module.so when option enable-mo… -- [X] [#4120](https://github.com/kubernetes/ingress-nginx/pull/4120) log info when endpoints change for a balancer -- [X] [#4122](https://github.com/kubernetes/ingress-nginx/pull/4122) Update Nginx to 1.17.0 and upgrade some other modules -- [X] [#4123](https://github.com/kubernetes/ingress-nginx/pull/4123) Update nginx image to 0.86 -- [X] [#4127](https://github.com/kubernetes/ingress-nginx/pull/4127) Migrate to new networking.k8s.io/v1beta1 package -- [X] [#4128](https://github.com/kubernetes/ingress-nginx/pull/4128) feature(collectors): Added services to collectorLabels -- [X] [#4133](https://github.com/kubernetes/ingress-nginx/pull/4133) Run PodSecurityPolicy E2E test in parallel -- [X] [#4135](https://github.com/kubernetes/ingress-nginx/pull/4135) Use apps/v1 api group in e2e tests -- [X] [#4140](https://github.com/kubernetes/ingress-nginx/pull/4140) update modsecurity to latest, libmodsecurity to v3.0.3 and owasp-scrs… -- [X] [#4150](https://github.com/kubernetes/ingress-nginx/pull/4150) Update nginx -- [X] [#4160](https://github.com/kubernetes/ingress-nginx/pull/4160) SSL expiration metrics cannot be tied to dynamic updates -- [X] [#4162](https://github.com/kubernetes/ingress-nginx/pull/4162) Add "text/javascript" to compressible MIME types -- [X] [#4164](https://github.com/kubernetes/ingress-nginx/pull/4164) fix source file mods -- [X] [#4166](https://github.com/kubernetes/ingress-nginx/pull/4166) Session Affinity ChangeOnFailure should be boolean -- [X] [#4169](https://github.com/kubernetes/ingress-nginx/pull/4169) simplify sticky balancer and fix a bug -- [X] [#4180](https://github.com/kubernetes/ingress-nginx/pull/4180) Service type=ExternalName can be defined with ports -- [X] [#4185](https://github.com/kubernetes/ingress-nginx/pull/4185) Fix: fillout missing health check timeout on health check. -- [X] [#4187](https://github.com/kubernetes/ingress-nginx/pull/4187) Add unit test cases for balancer lua module -- [X] [#4191](https://github.com/kubernetes/ingress-nginx/pull/4191) increase lua_shared_dict config data -- [X] [#4204](https://github.com/kubernetes/ingress-nginx/pull/4204) Add e2e test for service type=ExternalName -- [X] [#4212](https://github.com/kubernetes/ingress-nginx/pull/4212) Add e2e tests for grpc -- [X] [#4214](https://github.com/kubernetes/ingress-nginx/pull/4214) Update go dependencies -- [X] [#4219](https://github.com/kubernetes/ingress-nginx/pull/4219) Get AuthTLS annotation unit tests to 100% -- [X] [#4220](https://github.com/kubernetes/ingress-nginx/pull/4220) Migrate to openresty -- [X] [#4221](https://github.com/kubernetes/ingress-nginx/pull/4221) Switch to openresty image -- [X] [#4223](https://github.com/kubernetes/ingress-nginx/pull/4223) Remove travis-ci badge -- [X] [#4224](https://github.com/kubernetes/ingress-nginx/pull/4224) fix monitor test after move to openresty -- [X] [#4225](https://github.com/kubernetes/ingress-nginx/pull/4225) Update image dependencies -- [X] [#4226](https://github.com/kubernetes/ingress-nginx/pull/4226) Update nginx image -- [X] [#4227](https://github.com/kubernetes/ingress-nginx/pull/4227) Fix misspelled and e2e check -- [X] [#4229](https://github.com/kubernetes/ingress-nginx/pull/4229) Do not send empty certificates to nginx -- [X] [#4232](https://github.com/kubernetes/ingress-nginx/pull/4232) override least recently used entries when certificate_data dict is full -- [X] [#4233](https://github.com/kubernetes/ingress-nginx/pull/4233) Update nginx image to 0.90 -- [X] [#4235](https://github.com/kubernetes/ingress-nginx/pull/4235) Add new lints -- [X] [#4236](https://github.com/kubernetes/ingress-nginx/pull/4236) Add e2e test suite to detect memory leaks in lua -- [X] [#4237](https://github.com/kubernetes/ingress-nginx/pull/4237) Update go dependencies -- [X] [#4246](https://github.com/kubernetes/ingress-nginx/pull/4246) introduce proxy_alternative_upstream_name Nginx var -- [X] [#4249](https://github.com/kubernetes/ingress-nginx/pull/4249) test to make sure dynamic cert works trailing dot in domains -- [X] [#4250](https://github.com/kubernetes/ingress-nginx/pull/4250) Lint shell scripts -- [X] [#4251](https://github.com/kubernetes/ingress-nginx/pull/4251) Refactor prometheus leader helper -- [X] [#4253](https://github.com/kubernetes/ingress-nginx/pull/4253) Remove kubeclient configuration -- [X] [#4254](https://github.com/kubernetes/ingress-nginx/pull/4254) Update kind to 0.4.0 -- [X] [#4257](https://github.com/kubernetes/ingress-nginx/pull/4257) Fix error deleting temporal directory in case of errors -- [X] [#4258](https://github.com/kubernetes/ingress-nginx/pull/4258) Fix go imports -- [X] [#4267](https://github.com/kubernetes/ingress-nginx/pull/4267) More e2e tests -- [X] [#4270](https://github.com/kubernetes/ingress-nginx/pull/4270) GetLbAlgorithm helper func for e2e -- [X] [#4272](https://github.com/kubernetes/ingress-nginx/pull/4272) introduce ngx.var.balancer_ewma_score -- [X] [#4273](https://github.com/kubernetes/ingress-nginx/pull/4273) Check and complete intermediate SSL certificates -- [X] [#4274](https://github.com/kubernetes/ingress-nginx/pull/4274) Support trailing dot - -_Documentation:_ - -- [X] [#3966](https://github.com/kubernetes/ingress-nginx/pull/3966) Documentation example code fix -- [X] [#3978](https://github.com/kubernetes/ingress-nginx/pull/3978) Fix CA certificate example docs -- [X] [#3981](https://github.com/kubernetes/ingress-nginx/pull/3981) Add missing PR in changelog [skip ci] -- [X] [#3982](https://github.com/kubernetes/ingress-nginx/pull/3982) Add kubectl plugin docs -- [X] [#3987](https://github.com/kubernetes/ingress-nginx/pull/3987) Link to kubectl plugin docs in nav -- [X] [#4014](https://github.com/kubernetes/ingress-nginx/pull/4014) Update plugin krew manifest -- [X] [#4034](https://github.com/kubernetes/ingress-nginx/pull/4034) 🔧 fix navigation error in file baremetal.md -- [X] [#4036](https://github.com/kubernetes/ingress-nginx/pull/4036) Docs have incorrect command in baremetal.md -- [X] [#4037](https://github.com/kubernetes/ingress-nginx/pull/4037) [doc] fixing regex in example of rewrite -- [X] [#4040](https://github.com/kubernetes/ingress-nginx/pull/4040) Fix default Content-Type for custom-error-pages example -- [X] [#4068](https://github.com/kubernetes/ingress-nginx/pull/4068) fix typo: deployement->deployment -- [X] [#4082](https://github.com/kubernetes/ingress-nginx/pull/4082) Explain references in custom-headers documentation -- [X] [#4089](https://github.com/kubernetes/ingress-nginx/pull/4089) Docs: configmap: use-gzip -- [X] [#4099](https://github.com/kubernetes/ingress-nginx/pull/4099) Docs - Update capture group `placeholder` -- [X] [#4098](https://github.com/kubernetes/ingress-nginx/pull/4098) Update configmap about adding custom locations -- [X] [#4107](https://github.com/kubernetes/ingress-nginx/pull/4107) Clear up some inconsistent / unclear wording -- [X] [#4132](https://github.com/kubernetes/ingress-nginx/pull/4132) Update README.md for external-auth Test 4 -- [X] [#4153](https://github.com/kubernetes/ingress-nginx/pull/4153) Add clarification on how to enable path matching -- [X] [#4159](https://github.com/kubernetes/ingress-nginx/pull/4159) Partially revert usage of kustomize for installation -- [X] [#4217](https://github.com/kubernetes/ingress-nginx/pull/4217) Fix typo in annotations -- [X] [#4228](https://github.com/kubernetes/ingress-nginx/pull/4228) Add notes on timeouts while using long GRPC streams - -### 0.24.1 - -**Image:** `quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.24.1` - -_Changes:_ - -- [X] [#3990](https://github.com/kubernetes/ingress-nginx/pull/3990) Fix dynamic cert issue with default-ssl-certificate -- [X] [#3980](https://github.com/kubernetes/ingress-nginx/pull/3980) Refactor isIterable -- [X] [#4000](https://github.com/kubernetes/ingress-nginx/pull/4000) Dynamic ssl improvements -- [X] [#4007](https://github.com/kubernetes/ingress-nginx/pull/4007) do not create empty access_by_lua_block - -### 0.24.0 - -**Image:** `quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.24.0` - -_New Features:_ - -- NGINX 1.15.10 - -_Breaking changes:_ - -- `x-forwarded-prefix` annotation changed from a boolean to a string, see [#3786](https://github.com/kubernetes/ingress-nginx/pull/3786) - -_Changes:_ - -- [X] [#3743](https://github.com/kubernetes/ingress-nginx/pull/3743) Remove session-cookie-hash annotation -- [X] [#3786](https://github.com/kubernetes/ingress-nginx/pull/3786) Fix x-forwarded-prefix annotation -- [X] [#3798](https://github.com/kubernetes/ingress-nginx/pull/3798) Move some configuration logic from Nginx config to Lua code -- [X] [#3806](https://github.com/kubernetes/ingress-nginx/pull/3806) Migrate e2e cluster to kind -- [X] [#3807](https://github.com/kubernetes/ingress-nginx/pull/3807) Lua plugin system - MVP -- [X] [#3808](https://github.com/kubernetes/ingress-nginx/pull/3808) make dynamic SSL mode default -- [X] [#3827](https://github.com/kubernetes/ingress-nginx/pull/3827) Fix plugin install location -- [X] [#3829](https://github.com/kubernetes/ingress-nginx/pull/3829) Prevent e2e-tests from running on non-local clusters -- [X] [#3833](https://github.com/kubernetes/ingress-nginx/pull/3833) bump luajit version to v2.1-20190228 -- [X] [#3835](https://github.com/kubernetes/ingress-nginx/pull/3835) Update nginx image -- [X] [#3839](https://github.com/kubernetes/ingress-nginx/pull/3839) Fix panic on multiple non-matching canary -- [X] [#3846](https://github.com/kubernetes/ingress-nginx/pull/3846) Fix race condition in metric process collector test -- [X] [#3849](https://github.com/kubernetes/ingress-nginx/pull/3849) Use Gauge instead of Counter for connections_active Prometheus metric -- [X] [#3853](https://github.com/kubernetes/ingress-nginx/pull/3853) Remove authbind -- [X] [#3856](https://github.com/kubernetes/ingress-nginx/pull/3856) Fix ssl-dh-param issue when secret does not exit -- [X] [#3864](https://github.com/kubernetes/ingress-nginx/pull/3864) ing.Service with multiple hosts fix -- [X] [#3870](https://github.com/kubernetes/ingress-nginx/pull/3870) Improve kubectl plugin -- [X] [#3871](https://github.com/kubernetes/ingress-nginx/pull/3871) Fix name of field used to sort ingresses [skip-ci] -- [X] [#3875](https://github.com/kubernetes/ingress-nginx/pull/3875) Allow the use of a secret located in a different namespace -- [X] [#3882](https://github.com/kubernetes/ingress-nginx/pull/3882) Add support for IPV6 resolvers -- [X] [#3884](https://github.com/kubernetes/ingress-nginx/pull/3884) update GKE header to match link in contents -- [X] [#3885](https://github.com/kubernetes/ingress-nginx/pull/3885) Refactor status update -- [X] [#3886](https://github.com/kubernetes/ingress-nginx/pull/3886) Clean up ssl package and fix dynamic cert mode -- [X] [#3887](https://github.com/kubernetes/ingress-nginx/pull/3887) Remove useless nodeip calls and deprecate --force-namespace-isolation -- [X] [#3889](https://github.com/kubernetes/ingress-nginx/pull/3889) Separate out annotation assignment logic -- [X] [#3895](https://github.com/kubernetes/ingress-nginx/pull/3895) Correctly format ipv6 resolver config for lua -- [X] [#3900](https://github.com/kubernetes/ingress-nginx/pull/3900) Add lint subcommand to plugin -- [X] [#3907](https://github.com/kubernetes/ingress-nginx/pull/3907) Remove unnecessary copy of GeoIP databases -- [X] [#3908](https://github.com/kubernetes/ingress-nginx/pull/3908) Update nginx image -- [X] [#3918](https://github.com/kubernetes/ingress-nginx/pull/3918) Set `X-Request-ID` for the `default-backend`, too. -- [X] [#3927](https://github.com/kubernetes/ingress-nginx/pull/3927) Update apiVersion to apps/v1, drop duplicate line -- [X] [#3932](https://github.com/kubernetes/ingress-nginx/pull/3932) Fix dynamic SSL certificate for aliases and redirect-from-to-www -- [X] [#3933](https://github.com/kubernetes/ingress-nginx/pull/3933) Update nginx to 1.15.10 -- [X] [#3934](https://github.com/kubernetes/ingress-nginx/pull/3934) Update nginx image -- [X] [#3943](https://github.com/kubernetes/ingress-nginx/pull/3943) Update dependencies -- [X] [#3947](https://github.com/kubernetes/ingress-nginx/pull/3947) Adds a log warning when falling back to default fake cert -- [X] [#3950](https://github.com/kubernetes/ingress-nginx/pull/3950) Fix forwarded host parsing -- [X] [#3954](https://github.com/kubernetes/ingress-nginx/pull/3954) Fix load-balance configmap value -- [X] [#3955](https://github.com/kubernetes/ingress-nginx/pull/3955) Plugin select deployment using replicaset name -- [X] [#3958](https://github.com/kubernetes/ingress-nginx/pull/3958) Refactor equals -- [X] [#3960](https://github.com/kubernetes/ingress-nginx/pull/3960) Fix segfault on reference to nonexistent configmap -- [X] [#3968](https://github.com/kubernetes/ingress-nginx/pull/3968) Update nginx image -- [X] [#3969](https://github.com/kubernetes/ingress-nginx/pull/3969) Update nginx image to 0.84 - -_Documentation:_ - -- [X] [#3841](https://github.com/kubernetes/ingress-nginx/pull/3841) Improve "Sticky session" docs -- [X] [#3836](https://github.com/kubernetes/ingress-nginx/pull/3836) Update mkdocs [skip ci] -- [X] [#3847](https://github.com/kubernetes/ingress-nginx/pull/3847) Add missing basic usage documentation link -- [X] [#3874](https://github.com/kubernetes/ingress-nginx/pull/3874) Update embargo doc link in SECURITY_CONTACTS and change PST to PSC -- [X] [#3890](https://github.com/kubernetes/ingress-nginx/pull/3890) Make sure cli-arguments doc is in alphabetical order -- [X] [#3945](https://github.com/kubernetes/ingress-nginx/pull/3945) fix typo: delete '`' - -### 0.23.0 - -**Image:** `quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.23.0` - -_New Features:_ - -- NGINX 1.15.9 -- New `canary-by-header-value` [annotation](https://github.com/kubernetes/ingress-nginx/blob/main/docs/user-guide/nginx-configuration/annotations.md#canary). -- New debug binary to get runtime information from lua [3686](https://github.com/kubernetes/ingress-nginx/pull/3686) -- Support for Opentracing with Datadog -- New [kubectl plugin](https://github.com/kubernetes/ingress-nginx/pull/3779) **Alpha** - -_Breaking changes:_ - -- The NGINX server listening in port 18080 was removed. It was replaced by a server using an unix socket as port [#3684](https://github.com/kubernetes/ingress-nginx/pull/3684) - This server was internal to the ingress controller. In case this was being acceded from the outside, you can restore the old server using the `http-snippet` feature in the configuration configmap like: - - ```yaml - http-snippet: | - server { - listen 18080; - - location /nginx_status { - allow 127.0.0.1; - allow ::1; - deny all; - stub_status on; - } - - location / { - return 404; - } - } - ``` - -_Changes:_ - -- [X] [#3619](https://github.com/kubernetes/ingress-nginx/pull/3619) add header-value annotation -- [X] [#3628](https://github.com/kubernetes/ingress-nginx/pull/3628) Fix 503 error generation on empty endpoints -- [X] [#3666](https://github.com/kubernetes/ingress-nginx/pull/3666) rename sysctlFSFileMax to rlimitMaxNumFiles to reflect what it actually does -- [X] [#3667](https://github.com/kubernetes/ingress-nginx/pull/3667) worker_connections should be less (3/4th) than worker_rlimit_nofile -- [X] [#3671](https://github.com/kubernetes/ingress-nginx/pull/3671) bugfix: fixed duplicated seeds. -- [X] [#3673](https://github.com/kubernetes/ingress-nginx/pull/3673) used table functions of LuaJIT for better performance. -- [X] [#3674](https://github.com/kubernetes/ingress-nginx/pull/3674) used cjson.safe instead of pcall. -- [X] [#3682](https://github.com/kubernetes/ingress-nginx/pull/3682) enable use-forwarded-headers for L7 LB -- [X] [#3684](https://github.com/kubernetes/ingress-nginx/pull/3684) Replace Status port using a socket -- [X] [#3686](https://github.com/kubernetes/ingress-nginx/pull/3686) Add debug binary to the docker image -- [X] [#3695](https://github.com/kubernetes/ingress-nginx/pull/3695) > Don't reload nginx when L4 endpoints changed -- [X] [#3696](https://github.com/kubernetes/ingress-nginx/pull/3696) Apply annotations to default location -- [X] [#3698](https://github.com/kubernetes/ingress-nginx/pull/3698) Fix --disable-catch-all -- [X] [#3702](https://github.com/kubernetes/ingress-nginx/pull/3702) Add params for access log -- [X] [#3704](https://github.com/kubernetes/ingress-nginx/pull/3704) make sure dev-env forces context to be minikube -- [X] [#3728](https://github.com/kubernetes/ingress-nginx/pull/3728) Fix flaky test -- [X] [#3730](https://github.com/kubernetes/ingress-nginx/pull/3730) Changes CustomHTTPErrors annotation to use custom default backend -- [X] [#3734](https://github.com/kubernetes/ingress-nginx/pull/3734) remove old unused lua dicts -- [X] [#3736](https://github.com/kubernetes/ingress-nginx/pull/3736) do not unnecessarily log -- [X] [#3737](https://github.com/kubernetes/ingress-nginx/pull/3737) Adjust probe timeouts -- [X] [#3739](https://github.com/kubernetes/ingress-nginx/pull/3739) dont log unnecessarily -- [X] [#3740](https://github.com/kubernetes/ingress-nginx/pull/3740) Fix ingress updating for session-cookie-* annotation changes -- [X] [#3747](https://github.com/kubernetes/ingress-nginx/pull/3747) Update nginx and modules -- [X] [#3748](https://github.com/kubernetes/ingress-nginx/pull/3748) Update nginx image -- [X] [#3749](https://github.com/kubernetes/ingress-nginx/pull/3749) Enhance Unit Tests for Annotations -- [X] [#3750](https://github.com/kubernetes/ingress-nginx/pull/3750) Update go dependencies -- [X] [#3751](https://github.com/kubernetes/ingress-nginx/pull/3751) Parse environment variables in OpenTracing configuration -- [X] [#3756](https://github.com/kubernetes/ingress-nginx/pull/3756) Create custom annotation for satisfy "value" -- [X] [#3757](https://github.com/kubernetes/ingress-nginx/pull/3757) Add mention of secure-backends to backend-protocol docs -- [X] [#3764](https://github.com/kubernetes/ingress-nginx/pull/3764) delete confusing CustomErrors attribute to make things more explicit -- [X] [#3765](https://github.com/kubernetes/ingress-nginx/pull/3765) simplify customhttperrors e2e test and add regression test and fix a bug -- [X] [#3766](https://github.com/kubernetes/ingress-nginx/pull/3766) Support Opentracing with Datadog - part 2 -- [X] [#3767](https://github.com/kubernetes/ingress-nginx/pull/3767) Support Opentracing with Datadog - part 1 -- [X] [#3771](https://github.com/kubernetes/ingress-nginx/pull/3771) Do not log unnecessarily -- [X] [#3772](https://github.com/kubernetes/ingress-nginx/pull/3772) Fix dashboard link [skip ci] -- [X] [#3775](https://github.com/kubernetes/ingress-nginx/pull/3775) Fix DNS lookup failures in L4 services -- [X] [#3779](https://github.com/kubernetes/ingress-nginx/pull/3779) Add kubectl plugin -- [X] [#3780](https://github.com/kubernetes/ingress-nginx/pull/3780) Enable access log for default backend -- [X] [#3781](https://github.com/kubernetes/ingress-nginx/pull/3781) feat: configurable proxy buffers number -- [X] [#3782](https://github.com/kubernetes/ingress-nginx/pull/3782) Lua bridge tracer -- [X] [#3784](https://github.com/kubernetes/ingress-nginx/pull/3784) use correct host for jaeger-collector-host in docs -- [X] [#3785](https://github.com/kubernetes/ingress-nginx/pull/3785) use latest base nginx image -- [X] [#3787](https://github.com/kubernetes/ingress-nginx/pull/3787) Use UsePortInRedirects only if enabled -- [X] [#3791](https://github.com/kubernetes/ingress-nginx/pull/3791) - remove annotations in nginxcontroller struct -- [X] [#3792](https://github.com/kubernetes/ingress-nginx/pull/3792) dont restart minikube when it is already running -- [X] [#3793](https://github.com/kubernetes/ingress-nginx/pull/3793) Update mergo dependency -- [X] [#3794](https://github.com/kubernetes/ingress-nginx/pull/3794) use use-context that actually changes the context -- [X] [#3795](https://github.com/kubernetes/ingress-nginx/pull/3795) do not warn when optional annotations arent set -- [X] [#3799](https://github.com/kubernetes/ingress-nginx/pull/3799) Add /dbg certs command -- [X] [#3800](https://github.com/kubernetes/ingress-nginx/pull/3800) Refactor e2e -- [X] [#3809](https://github.com/kubernetes/ingress-nginx/pull/3809) Upgrade openresty/lua-resty-balancer -- [X] [#3810](https://github.com/kubernetes/ingress-nginx/pull/3810) Update nginx image -- [X] [#3811](https://github.com/kubernetes/ingress-nginx/pull/3811) Fix e2e tests -- [X] [#3812](https://github.com/kubernetes/ingress-nginx/pull/3812) Removes unused const from customhttperrors e2e test -- [X] [#3813](https://github.com/kubernetes/ingress-nginx/pull/3813) Prevent dep from vendoring grpc-fortune-teller dependencies -- [X] [#3819](https://github.com/kubernetes/ingress-nginx/pull/3819) Fix e2e test in osx -- [X] [#3820](https://github.com/kubernetes/ingress-nginx/pull/3820) Update nginx image -- [X] [#3821](https://github.com/kubernetes/ingress-nginx/pull/3821) Update nginx to 1.15.9 -- [X] [#3822](https://github.com/kubernetes/ingress-nginx/pull/3822) Set default for satisfy annotation to nothing - -_Documentation:_ - -- [X] [#3680](https://github.com/kubernetes/ingress-nginx/pull/3680) mention rewrite-target change for 0.22.0 -- [X] [#3693](https://github.com/kubernetes/ingress-nginx/pull/3693) Correcting links for gRPC Fortune Teller app -- [X] [#3701](https://github.com/kubernetes/ingress-nginx/pull/3701) Update usage documentation for default-backend annotation -- [X] [#3705](https://github.com/kubernetes/ingress-nginx/pull/3705) Increase Unit Test Coverage for Templates -- [X] [#3708](https://github.com/kubernetes/ingress-nginx/pull/3708) Update OWNERS -- [X] [#3731](https://github.com/kubernetes/ingress-nginx/pull/3731) Update a doc example that uses rewrite-target - -_Deprecations:_ - -- The annotation `session-cookie-hash` is deprecated and will be removed in 0.24. -- Flag `--force-namespace-isolation` is deprecated and will be removed in 0.24. Currently this annotation is being replaced by `--watch-namespace` - -### 0.22.0 - -**Image:** `quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.22.0` - -_New Features:_ - -- NGINX 1.15.8 -- New balancer implementation: consistent hash subset -- Adds support for HTTP2 Push Preload annotation -- Allow to disable NGINX prometheus metrics -- New --disable-catch-all flag to ignore catch-all ingresses -- Add flag --metrics-per-host to make per-host metrics optional - -_Breaking changes:_ - -- Annotation `nginx.ingress.kubernetes.io/rewrite-target` has changed and will not behave as expected if you don't update them. - - Refer to [https://kubernetes.github.io/ingress-nginx/examples/rewrite/#rewrite-target](https://kubernetes.github.io/ingress-nginx/examples/rewrite/#rewrite-target) on how to change it. - - Refer to [https://github.com/kubernetes/ingress-nginx/pull/3174#issuecomment-455665710](https://github.com/kubernetes/ingress-nginx/pull/3174#issuecomment-455665710) on how to do seamless migration. - -- Annotations `nginx.ingress.kubernetes.io/add-base-url` and `nginx.ingress.kubernetes.io/base-url-scheme` were removed. - - Please check issue [#3174](https://github.com/kubernetes/ingress-nginx/pull/3174) for details. - -- By default do not trust any client to extract true client IP address from X-Forwarded-For header using realip module (`use-forwarded-headers: "false"`) - -_Changes:_ - -- [X] [#3174](https://github.com/kubernetes/ingress-nginx/pull/3174) Generalize Rewrite Block Creation and Deprecate AddBaseUrl (not backwards compatible) -- [X] [#3240](https://github.com/kubernetes/ingress-nginx/pull/3240) Adds support for HTTP2 Push Preload annotation -- [X] [#3333](https://github.com/kubernetes/ingress-nginx/pull/3333) breaking change: by default do not trust any client -- [X] [#3342](https://github.com/kubernetes/ingress-nginx/pull/3342) Allow privilege escalation -- [X] [#3363](https://github.com/kubernetes/ingress-nginx/pull/3363) Document for cookie expires annotation -- [X] [#3396](https://github.com/kubernetes/ingress-nginx/pull/3396) New balancer implementation: consistent hash subset -- [X] [#3446](https://github.com/kubernetes/ingress-nginx/pull/3446) add more testing for mergeAlternativeBackends -- [X] [#3453](https://github.com/kubernetes/ingress-nginx/pull/3453) Monitor fixes -- [X] [#3455](https://github.com/kubernetes/ingress-nginx/pull/3455) Watch controller Pods and make then available in k8sStore -- [X] [#3465](https://github.com/kubernetes/ingress-nginx/pull/3465) Bump nginx-opentracing for gRPC support -- [X] [#3467](https://github.com/kubernetes/ingress-nginx/pull/3467) store ewma stats per backend -- [X] [#3470](https://github.com/kubernetes/ingress-nginx/pull/3470) Use opentracing_grpc_propagate_context when necessary -- [X] [#3474](https://github.com/kubernetes/ingress-nginx/pull/3474) Improve parsing of annotations and use of Ingress wrapper -- [X] [#3476](https://github.com/kubernetes/ingress-nginx/pull/3476) Fix nginx directory permissions -- [X] [#3477](https://github.com/kubernetes/ingress-nginx/pull/3477) clarify canary ingress -- [X] [#3478](https://github.com/kubernetes/ingress-nginx/pull/3478) delete unused buildLoadBalancingConfig -- [X] [#3487](https://github.com/kubernetes/ingress-nginx/pull/3487) dynamic certificate mode should support widlcard hosts -- [X] [#3488](https://github.com/kubernetes/ingress-nginx/pull/3488) Add probes to deployments used in e2e tests -- [X] [#3492](https://github.com/kubernetes/ingress-nginx/pull/3492) Fix data size validations -- [X] [#3494](https://github.com/kubernetes/ingress-nginx/pull/3494) Since dynamic mode only checking for 'return 503' is not valid anymore -- [X] [#3495](https://github.com/kubernetes/ingress-nginx/pull/3495) Adjust default timeout for e2e tests -- [X] [#3497](https://github.com/kubernetes/ingress-nginx/pull/3497) Wait for the right number of endpoints -- [X] [#3498](https://github.com/kubernetes/ingress-nginx/pull/3498) Update godeps -- [X] [#3501](https://github.com/kubernetes/ingress-nginx/pull/3501) be consistent with what Nginx supports -- [X] [#3503](https://github.com/kubernetes/ingress-nginx/pull/3503) compare error with error types from k8s.io/apimachinery/pkg/api/errors -- [X] [#3504](https://github.com/kubernetes/ingress-nginx/pull/3504) fix an ewma unit test -- [X] [#3505](https://github.com/kubernetes/ingress-nginx/pull/3505) Update lua configuration_data when number of controller pod change -- [X] [#3507](https://github.com/kubernetes/ingress-nginx/pull/3507) Remove temporal configuration file after a while -- [X] [#3508](https://github.com/kubernetes/ingress-nginx/pull/3508) Update nginx to 1.15.7 -- [X] [#3509](https://github.com/kubernetes/ingress-nginx/pull/3509) [1759] Ingress affinity session cookie with Secure flag for HTTPS -- [X] [#3512](https://github.com/kubernetes/ingress-nginx/pull/3512) Allow to disable NGINX metrics -- [X] [#3518](https://github.com/kubernetes/ingress-nginx/pull/3518) Fix log output format -- [X] [#3521](https://github.com/kubernetes/ingress-nginx/pull/3521) Fix a bug with Canary becoming main server -- [X] [#3522](https://github.com/kubernetes/ingress-nginx/pull/3522) {tcp,udp}-services cm appear twice -- [X] [#3525](https://github.com/kubernetes/ingress-nginx/pull/3525) make canary ingresses independent of the order they were applied -- [X] [#3530](https://github.com/kubernetes/ingress-nginx/pull/3530) Update nginx image -- [X] [#3532](https://github.com/kubernetes/ingress-nginx/pull/3532) Ignore updates of ingresses with invalid class -- [X] [#3536](https://github.com/kubernetes/ingress-nginx/pull/3536) Replace dockerfile entrypoint -- [X] [#3548](https://github.com/kubernetes/ingress-nginx/pull/3548) e2e test to ensure graceful shutdown does not lose requests -- [X] [#3551](https://github.com/kubernetes/ingress-nginx/pull/3551) Fix --enable-dynamic-certificates for nested subdomain -- [X] [#3553](https://github.com/kubernetes/ingress-nginx/pull/3553) handle_error_when_executing_diff -- [X] [#3562](https://github.com/kubernetes/ingress-nginx/pull/3562) Rename nginx.yaml to nginx.json -- [X] [#3566](https://github.com/kubernetes/ingress-nginx/pull/3566) Add Unit Tests for getIngressInformation -- [X] [#3569](https://github.com/kubernetes/ingress-nginx/pull/3569) fix status updated: make sure ingress.status is copied -- [X] [#3573](https://github.com/kubernetes/ingress-nginx/pull/3573) Update Certificate Generation Docs to not use MD5 -- [X] [#3581](https://github.com/kubernetes/ingress-nginx/pull/3581) lua randomseed per worker -- [X] [#3582](https://github.com/kubernetes/ingress-nginx/pull/3582) Sort ingresses by creation timestamp -- [X] [#3584](https://github.com/kubernetes/ingress-nginx/pull/3584) Update go to 1.11.4 -- [X] [#3586](https://github.com/kubernetes/ingress-nginx/pull/3586) Add --disable-catch-all option to disable catch-all server -- [X] [#3587](https://github.com/kubernetes/ingress-nginx/pull/3587) adjust dind istallation -- [X] [#3594](https://github.com/kubernetes/ingress-nginx/pull/3594) Add a flag to make per-host metrics optional -- [X] [#3596](https://github.com/kubernetes/ingress-nginx/pull/3596) Fix proxy_host variable configuration -- [X] [#3601](https://github.com/kubernetes/ingress-nginx/pull/3601) Update nginx to 1.15.8 -- [X] [#3602](https://github.com/kubernetes/ingress-nginx/pull/3602) Update nginx image -- [X] [#3604](https://github.com/kubernetes/ingress-nginx/pull/3604) Add an option to automatically set worker_connections based on worker_rlimit_nofile -- [X] [#3615](https://github.com/kubernetes/ingress-nginx/pull/3615) Pass k8s `Service` data through to the TCP balancer script. -- [X] [#3620](https://github.com/kubernetes/ingress-nginx/pull/3620) Added server alias to metrics -- [X] [#3624](https://github.com/kubernetes/ingress-nginx/pull/3624) Update nginx to fix geoip database deprecation -- [X] [#3625](https://github.com/kubernetes/ingress-nginx/pull/3625) Update nginx image -- [X] [#3633](https://github.com/kubernetes/ingress-nginx/pull/3633) Fix a bug in Ingress update handler -- [X] [#3634](https://github.com/kubernetes/ingress-nginx/pull/3634) canary by cookie should support hypen in cookie name -- [X] [#3635](https://github.com/kubernetes/ingress-nginx/pull/3635) Fix duplicate alternative backend merging -- [X] [#3637](https://github.com/kubernetes/ingress-nginx/pull/3637) Add support for redirect https to https (from-to-www-redirect) -- [X] [#3640](https://github.com/kubernetes/ingress-nginx/pull/3640) add limit connection status code -- [X] [#3641](https://github.com/kubernetes/ingress-nginx/pull/3641) Replace deprecated apiVersion in deploy folder -- [X] [#3643](https://github.com/kubernetes/ingress-nginx/pull/3643) Update nginx -- [X] [#3644](https://github.com/kubernetes/ingress-nginx/pull/3644) Update nginx image -- [X] [#3648](https://github.com/kubernetes/ingress-nginx/pull/3648) Remove stickyness cookie domain from Lua balancer to match old behavior -- [X] [#3649](https://github.com/kubernetes/ingress-nginx/pull/3649) Empty access_by_lua_block breaks satisfy any -- [X] [#3655](https://github.com/kubernetes/ingress-nginx/pull/3655) Remove flag sort-backends -- [X] [#3656](https://github.com/kubernetes/ingress-nginx/pull/3656) Change default value of flag for ssl chain completion -- [X] [#3660](https://github.com/kubernetes/ingress-nginx/pull/3660) Revert max-worker-connections default value -- [X] [#3664](https://github.com/kubernetes/ingress-nginx/pull/3664) Fix invalid validation creating prometheus valid host values - -_Documentation:_ - -- [X] [#3513](https://github.com/kubernetes/ingress-nginx/pull/3513) Revert removal of TCP and UDP support configmaps in mandatroy manifest -- [X] [#3456](https://github.com/kubernetes/ingress-nginx/pull/3456) Revert TCP/UDP documentation removal and links -- [X] [#3482](https://github.com/kubernetes/ingress-nginx/pull/3482) Annotations doc links: minor fixes and unification -- [X] [#3491](https://github.com/kubernetes/ingress-nginx/pull/3491) Update example to use latest Dashboard version. -- [X] [#3510](https://github.com/kubernetes/ingress-nginx/pull/3510) Update mkdocs [skip ci] -- [X] [#3516](https://github.com/kubernetes/ingress-nginx/pull/3516) Fix error in configmap yaml definition -- [X] [#3575](https://github.com/kubernetes/ingress-nginx/pull/3575) Add documentation for spec.rules.host format -- [X] [#3577](https://github.com/kubernetes/ingress-nginx/pull/3577) Add standard labels to namespace specs -- [X] [#3592](https://github.com/kubernetes/ingress-nginx/pull/3592) Add inside the User Guide documentation section a basic usage section and example -- [X] [#3605](https://github.com/kubernetes/ingress-nginx/pull/3605) Fix CLA URLs -- [X] [#3627](https://github.com/kubernetes/ingress-nginx/pull/3627) Typo: docs/examples/rewrite/README.md -- [X] [#3632](https://github.com/kubernetes/ingress-nginx/pull/3632) Fixed: error parsing with-rbac.yaml: error converting YAML to JSON - -### 0.21.0 - -**Image:** `quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.21.0` - -_New Features:_ - -- NGINX 1.15.6 with fixes for vulnerabilities in HTTP/2 ([CVE-2018-16843](http://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2018-16843), [CVE-2018-16844](http://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2018-16844)) -- Support for TLSv1.3. Disabled by default. Use [ssl-protocols](https://kubernetes.github.io/ingress-nginx/user-guide/nginx-configuration/configmap/#ssl-protocols) `ssl-protocols: TLSv1.3 TLSv1.2` -- New annotation for [canary deployments](https://kubernetes.github.io/ingress-nginx/user-guide/nginx-configuration/annotations/#canary) -- Support for configuration snippets when the authentication annotation is used -- Support for custom ModSecurity configuration -- LUA upstream configuration for TCP and UDP services - -_Changes:_ - -- [X] [#3156](https://github.com/kubernetes/ingress-nginx/pull/3156) [404-server] Removes 404 server -- [X] [#3170](https://github.com/kubernetes/ingress-nginx/pull/3170) Move mainSnippet before events to fix load_module issue. -- [X] [#3187](https://github.com/kubernetes/ingress-nginx/pull/3187) UPT: annotation enhancement for resty-lua-waf -- [X] [#3190](https://github.com/kubernetes/ingress-nginx/pull/3190) Refactor e2e Tests to use common helper -- [X] [#3193](https://github.com/kubernetes/ingress-nginx/pull/3193) Add E2E tests for HealthCheck -- [X] [#3194](https://github.com/kubernetes/ingress-nginx/pull/3194) Make literal $ character work in set $location_path -- [X] [#3195](https://github.com/kubernetes/ingress-nginx/pull/3195) Add e2e Tests for AuthTLS -- [X] [#3196](https://github.com/kubernetes/ingress-nginx/pull/3196) Remove default backend requirement -- [X] [#3197](https://github.com/kubernetes/ingress-nginx/pull/3197) Remove support for TCP and UDP services -- [X] [#3198](https://github.com/kubernetes/ingress-nginx/pull/3198) Only support dynamic configuration -- [X] [#3199](https://github.com/kubernetes/ingress-nginx/pull/3199) Remove duplication in files -- [X] [#3201](https://github.com/kubernetes/ingress-nginx/pull/3201) no data shows for config reloads charts when select to namespace or controller -- [X] [#3203](https://github.com/kubernetes/ingress-nginx/pull/3203) Remove annotations grpc-backend and secure-backend already deprecated -- [X] [#3204](https://github.com/kubernetes/ingress-nginx/pull/3204) Flags publish-service and publish-status-address are mutually exclusive -- [X] [#3205](https://github.com/kubernetes/ingress-nginx/pull/3205) Update OWNERS [skip ci] -- [X] [#3207](https://github.com/kubernetes/ingress-nginx/pull/3207) delete upstream healthcheck annotation -- [X] [#3209](https://github.com/kubernetes/ingress-nginx/pull/3209) Fix: update config map name -- [X] [#3212](https://github.com/kubernetes/ingress-nginx/pull/3212) Add some extra detail to the client cert auth example regarding potential gotcha -- [X] [#3213](https://github.com/kubernetes/ingress-nginx/pull/3213) Update deps -- [X] [#3214](https://github.com/kubernetes/ingress-nginx/pull/3214) Cleanup of nginx image -- [X] [#3219](https://github.com/kubernetes/ingress-nginx/pull/3219) Update nginx image -- [X] [#3222](https://github.com/kubernetes/ingress-nginx/pull/3222) Allow Ability to Configure Upstream Keepalive -- [X] [#3230](https://github.com/kubernetes/ingress-nginx/pull/3230) Retry initial backend configuration -- [X] [#3231](https://github.com/kubernetes/ingress-nginx/pull/3231) Improve dynamic lua configuration -- [X] [#3234](https://github.com/kubernetes/ingress-nginx/pull/3234) Added e2e tests for backend protocols -- [X] [#3247](https://github.com/kubernetes/ingress-nginx/pull/3247) Refactor probe url requests -- [X] [#3252](https://github.com/kubernetes/ingress-nginx/pull/3252) remove the command args of enable-dynamic-configuration -- [X] [#3257](https://github.com/kubernetes/ingress-nginx/pull/3257) Add e2e tests for upstream vhost -- [X] [#3260](https://github.com/kubernetes/ingress-nginx/pull/3260) fix logging calls -- [X] [#3261](https://github.com/kubernetes/ingress-nginx/pull/3261) Mount minikube volume to docker container -- [X] [#3265](https://github.com/kubernetes/ingress-nginx/pull/3265) Update kubeadm-dind-cluster -- [X] [#3266](https://github.com/kubernetes/ingress-nginx/pull/3266) fix two bugs with backend-protocol annotation -- [X] [#3267](https://github.com/kubernetes/ingress-nginx/pull/3267) Fix status update in case of connection errors -- [X] [#3270](https://github.com/kubernetes/ingress-nginx/pull/3270) Don't sort IngressStatus from each Goroutine(update for each ingress) -- [X] [#3277](https://github.com/kubernetes/ingress-nginx/pull/3277) Add e2e test for configuration snippet -- [X] [#3279](https://github.com/kubernetes/ingress-nginx/pull/3279) Fix usages of %q formatting for numbers (%d) -- [X] [#3280](https://github.com/kubernetes/ingress-nginx/pull/3280) Add e2e test for from-to-www-redirect -- [X] [#3281](https://github.com/kubernetes/ingress-nginx/pull/3281) Add e2e test for log -- [X] [#3285](https://github.com/kubernetes/ingress-nginx/pull/3285) Add health-check-timeout as command line argument -- [X] [#3286](https://github.com/kubernetes/ingress-nginx/pull/3286) fix bug with balancer.lua configuration -- [X] [#3295](https://github.com/kubernetes/ingress-nginx/pull/3295) Refactor EWMA to not use shared dictionaries -- [X] [#3296](https://github.com/kubernetes/ingress-nginx/pull/3296) Update nginx and add support for TLSv1.3 -- [X] [#3297](https://github.com/kubernetes/ingress-nginx/pull/3297) Add e2e test for force-ssl-redirect -- [X] [#3301](https://github.com/kubernetes/ingress-nginx/pull/3301) Add e2e tests for IP Whitelist -- [X] [#3302](https://github.com/kubernetes/ingress-nginx/pull/3302) Add e2e test for server snippet -- [X] [#3304](https://github.com/kubernetes/ingress-nginx/pull/3304) Update kubeadm-dind-cluster script -- [X] [#3305](https://github.com/kubernetes/ingress-nginx/pull/3305) Add e2e test for app-root -- [X] [#3306](https://github.com/kubernetes/ingress-nginx/pull/3306) Update e2e test to verify redirect code -- [X] [#3309](https://github.com/kubernetes/ingress-nginx/pull/3309) Customize ModSecurity to be used in Locations -- [X] [#3310](https://github.com/kubernetes/ingress-nginx/pull/3310) Fix geoip2 db files -- [X] [#3313](https://github.com/kubernetes/ingress-nginx/pull/3313) Support cookie expires -- [X] [#3320](https://github.com/kubernetes/ingress-nginx/pull/3320) Update nginx image and QEMU version -- [X] [#3321](https://github.com/kubernetes/ingress-nginx/pull/3321) Add configuration for geoip2 module -- [X] [#3322](https://github.com/kubernetes/ingress-nginx/pull/3322) Remove e2e boilerplate -- [X] [#3324](https://github.com/kubernetes/ingress-nginx/pull/3324) Fix sticky session -- [X] [#3325](https://github.com/kubernetes/ingress-nginx/pull/3325) Fix e2e tests -- [X] [#3328](https://github.com/kubernetes/ingress-nginx/pull/3328) Code linting -- [X] [#3332](https://github.com/kubernetes/ingress-nginx/pull/3332) Update build-single-manifest-sh,remove tcp-services-configmap.yaml and udp-services-configmap.yaml -- [X] [#3338](https://github.com/kubernetes/ingress-nginx/pull/3338) Avoid reloads when endpoints are not available -- [X] [#3341](https://github.com/kubernetes/ingress-nginx/pull/3341) Add canary annotation and alternative backends for traffic shaping -- [X] [#3343](https://github.com/kubernetes/ingress-nginx/pull/3343) Auth snippet -- [X] [#3344](https://github.com/kubernetes/ingress-nginx/pull/3344) Adds CustomHTTPErrors ingress annotation and test -- [X] [#3345](https://github.com/kubernetes/ingress-nginx/pull/3345) update annotation -- [X] [#3346](https://github.com/kubernetes/ingress-nginx/pull/3346) Add e2e test for session-cookie-hash -- [X] [#3347](https://github.com/kubernetes/ingress-nginx/pull/3347) Add e2e test for ssl-redirect -- [X] [#3348](https://github.com/kubernetes/ingress-nginx/pull/3348) Update cli-arguments.md. Remove tcp and udp, add health-check-timeout. -- [X] [#3353](https://github.com/kubernetes/ingress-nginx/pull/3353) Update nginx modules -- [X] [#3354](https://github.com/kubernetes/ingress-nginx/pull/3354) Update nginx image -- [X] [#3356](https://github.com/kubernetes/ingress-nginx/pull/3356) Download latest dep releases instead of fetching from HEAD -- [X] [#3357](https://github.com/kubernetes/ingress-nginx/pull/3357) Add missing modsecurity unicode.mapping file -- [X] [#3367](https://github.com/kubernetes/ingress-nginx/pull/3367) Remove reloads when there is no endpoints -- [X] [#3372](https://github.com/kubernetes/ingress-nginx/pull/3372) Add annotation for session affinity path -- [X] [#3373](https://github.com/kubernetes/ingress-nginx/pull/3373) Update nginx -- [X] [#3374](https://github.com/kubernetes/ingress-nginx/pull/3374) Revert removal of support for TCP and UDP services -- [X] [#3383](https://github.com/kubernetes/ingress-nginx/pull/3383) Only set cookies on paths that enable session affinity -- [X] [#3387](https://github.com/kubernetes/ingress-nginx/pull/3387) Modify the wrong function name -- [X] [#3390](https://github.com/kubernetes/ingress-nginx/pull/3390) Add e2e test for round robin load balancing -- [X] [#3400](https://github.com/kubernetes/ingress-nginx/pull/3400) Add Snippet for ModSecurity -- [X] [#3404](https://github.com/kubernetes/ingress-nginx/pull/3404) Update nginx image -- [X] [#3405](https://github.com/kubernetes/ingress-nginx/pull/3405) Prevent X-Forwarded-Proto forward during external auth subrequest -- [X] [#3406](https://github.com/kubernetes/ingress-nginx/pull/3406) Update nginx and e2e image -- [X] [#3407](https://github.com/kubernetes/ingress-nginx/pull/3407) Restructure load balance e2e tests and update round robin test -- [X] [#3408](https://github.com/kubernetes/ingress-nginx/pull/3408) Fix modsecurity configuration file location -- [X] [#3409](https://github.com/kubernetes/ingress-nginx/pull/3409) Convert isValidClientBodyBufferSize to something more generic -- [X] [#3410](https://github.com/kubernetes/ingress-nginx/pull/3410) fix logging calls -- [X] [#3415](https://github.com/kubernetes/ingress-nginx/pull/3415) bugfix: set canary attributes when initializing balancer -- [X] [#3417](https://github.com/kubernetes/ingress-nginx/pull/3417) bugfix: do not merge catch-all canary backends with itself -- [X] [#3421](https://github.com/kubernetes/ingress-nginx/pull/3421) Fix X-Forwarded-Proto typo -- [X] [#3424](https://github.com/kubernetes/ingress-nginx/pull/3424) Update nginx image -- [X] [#3425](https://github.com/kubernetes/ingress-nginx/pull/3425) Update nginx modules -- [X] [#3428](https://github.com/kubernetes/ingress-nginx/pull/3428) Set proxy_host variable to avoid using default value from proxy_pass -- [X] [#3437](https://github.com/kubernetes/ingress-nginx/pull/3437) Use struct to pack Ingress and its annotations -- [X] [#3441](https://github.com/kubernetes/ingress-nginx/pull/3441) Match buffer -- [X] [#3442](https://github.com/kubernetes/ingress-nginx/pull/3442) Increase log level when there is an invalid size value -- [X] [#3453](https://github.com/kubernetes/ingress-nginx/pull/3453) Monitor fixes - -_Documentation:_ - -- [X] [#3166](https://github.com/kubernetes/ingress-nginx/pull/3166) Added ingress tls values.yaml example to documentation -- [X] [#3215](https://github.com/kubernetes/ingress-nginx/pull/3215) align opentracing user-guide with nginx configmap configuration -- [X] [#3229](https://github.com/kubernetes/ingress-nginx/pull/3229) Fix documentation links [skip ci] -- [X] [#3232](https://github.com/kubernetes/ingress-nginx/pull/3232) Fix typo -- [X] [#3242](https://github.com/kubernetes/ingress-nginx/pull/3242) Add a note to the deployment into GKE -- [X] [#3249](https://github.com/kubernetes/ingress-nginx/pull/3249) Clarify mandatory script doc -- [X] [#3262](https://github.com/kubernetes/ingress-nginx/pull/3262) Add e2e test for connection -- [X] [#3263](https://github.com/kubernetes/ingress-nginx/pull/3263) "diretly" typo -- [X] [#3264](https://github.com/kubernetes/ingress-nginx/pull/3264) Add missing annotations to Docs -- [X] [#3271](https://github.com/kubernetes/ingress-nginx/pull/3271) the sample ingress spec error -- [X] [#3275](https://github.com/kubernetes/ingress-nginx/pull/3275) Add Better Documentation for using AuthTLS -- [X] [#3282](https://github.com/kubernetes/ingress-nginx/pull/3282) Fix some typos -- [X] [#3312](https://github.com/kubernetes/ingress-nginx/pull/3312) Delete some extra words -- [X] [#3319](https://github.com/kubernetes/ingress-nginx/pull/3319) Fix links in deploy index docs -- [X] [#3326](https://github.com/kubernetes/ingress-nginx/pull/3326) fix broken link -- [X] [#3349](https://github.com/kubernetes/ingress-nginx/pull/3349) fix typo -- [X] [#3364](https://github.com/kubernetes/ingress-nginx/pull/3364) Fix links format [skip-ci] -- [X] [#3366](https://github.com/kubernetes/ingress-nginx/pull/3366) Fix some typos -- [X] [#3369](https://github.com/kubernetes/ingress-nginx/pull/3369) Fix some typos -- [X] [#3370](https://github.com/kubernetes/ingress-nginx/pull/3370) Fix typo: whitlelist -> whitelist -- [X] [#3377](https://github.com/kubernetes/ingress-nginx/pull/3377) Fix typos and default value -- [X] [#3379](https://github.com/kubernetes/ingress-nginx/pull/3379) Fix typos -- [X] [#3382](https://github.com/kubernetes/ingress-nginx/pull/3382) Fix typos: reqrite -> rewrite -- [X] [#3388](https://github.com/kubernetes/ingress-nginx/pull/3388) Update annotations.md. Remove Duplication. -- [X] [#3392](https://github.com/kubernetes/ingress-nginx/pull/3392) Fix link in documentation [skip ci] -- [X] [#3395](https://github.com/kubernetes/ingress-nginx/pull/3395) Fix some documents issues - -### 0.20.0 - -**Image:** `quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.20.0` - -_New Features:_ - -- NGINX 1.15.5 -- Support for *regular expressions* in paths https://github.com/kubernetes/ingress-nginx/blob/main/docs/user-guide/ingress-path-matching.md -- Provide possibility to block IPs, User-Agents and Referers globally -- Remove --default-backend-service requirement. Use the flag only for custom default backends -- Valgrind and Openresty gdb tools - -_Changes:_ - -- [X] [#2997](https://github.com/kubernetes/ingress-nginx/pull/2997) Provide possibility to block IPs, User-Agents and Referers globally -- [X] [#3016](https://github.com/kubernetes/ingress-nginx/pull/3016) Log Errors Missing in Internal -- [X] [#3017](https://github.com/kubernetes/ingress-nginx/pull/3017) Add e2e tests for CORS -- [X] [#3022](https://github.com/kubernetes/ingress-nginx/pull/3022) Add support for valgrind -- [X] [#3029](https://github.com/kubernetes/ingress-nginx/pull/3029) add support for http2-max-requests in configmap -- [X] [#3035](https://github.com/kubernetes/ingress-nginx/pull/3035) Fixup #2970: Add Missing Label `app.kubernetes.io/part-of: ingress-nginx` -- [X] [#3049](https://github.com/kubernetes/ingress-nginx/pull/3049) fix: Don't try and find local certs when secretName is not specified -- [X] [#3050](https://github.com/kubernetes/ingress-nginx/pull/3050) Add Ingress variable in Grafana dashboard -- [X] [#3062](https://github.com/kubernetes/ingress-nginx/pull/3062) Pass Host header for custom errors -- [X] [#3065](https://github.com/kubernetes/ingress-nginx/pull/3065) Join host/port with go helper (supports ipv6) -- [X] [#3067](https://github.com/kubernetes/ingress-nginx/pull/3067) fix missing datasource value -- [X] [#3069](https://github.com/kubernetes/ingress-nginx/pull/3069) Replace client-go deprecated method -- [X] [#3072](https://github.com/kubernetes/ingress-nginx/pull/3072) Update ingress service IP -- [X] [#3073](https://github.com/kubernetes/ingress-nginx/pull/3073) do not hardcode the path -- [X] [#3078](https://github.com/kubernetes/ingress-nginx/pull/3078) Fix Rewrite-Target Annotation Edge Case -- [X] [#3079](https://github.com/kubernetes/ingress-nginx/pull/3079) Openresty gdb tools -- [X] [#3080](https://github.com/kubernetes/ingress-nginx/pull/3080) Update nginx image to 0.62 -- [X] [#3098](https://github.com/kubernetes/ingress-nginx/pull/3098) make upstream keepalive work for http -- [X] [#3100](https://github.com/kubernetes/ingress-nginx/pull/3100) update annotation name from rewrite-log to enable-rewrite-log -- [X] [#3118](https://github.com/kubernetes/ingress-nginx/pull/3118) Replace standard json encoding with jsoniter -- [X] [#3121](https://github.com/kubernetes/ingress-nginx/pull/3121) Typo fix: adresses -> addresses -- [X] [#3126](https://github.com/kubernetes/ingress-nginx/pull/3126) do not require --default-backend-service -- [X] [#3130](https://github.com/kubernetes/ingress-nginx/pull/3130) fix newlines location denied -- [X] [#3133](https://github.com/kubernetes/ingress-nginx/pull/3133) multi-tls readme example to reference the file -- [X] [#3134](https://github.com/kubernetes/ingress-nginx/pull/3134) Update nginx to 1.15.4 -- [X] [#3135](https://github.com/kubernetes/ingress-nginx/pull/3135) Remove payload from post log -- [X] [#3136](https://github.com/kubernetes/ingress-nginx/pull/3136) Update nginx image -- [X] [#3137](https://github.com/kubernetes/ingress-nginx/pull/3137) Docker run as user -- [X] [#3143](https://github.com/kubernetes/ingress-nginx/pull/3143) Ensure monitoring for custom error pages -- [X] [#3144](https://github.com/kubernetes/ingress-nginx/pull/3144) Fix incorrect .DisableLua access. -- [X] [#3145](https://github.com/kubernetes/ingress-nginx/pull/3145) Add "use-regex" Annotation to Toggle Regular Expression Location Modifier -- [X] [#3146](https://github.com/kubernetes/ingress-nginx/pull/3146) Update default backend image -- [X] [#3147](https://github.com/kubernetes/ingress-nginx/pull/3147) Fix error publishing docs [skip ci] -- [X] [#3149](https://github.com/kubernetes/ingress-nginx/pull/3149) Add e2e Tests for Proxy Annotations -- [X] [#3151](https://github.com/kubernetes/ingress-nginx/pull/3151) Add e2e test for SSL-Ciphers -- [X] [#3159](https://github.com/kubernetes/ingress-nginx/pull/3159) Pass --shell to minikube docker-env -- [X] [#3178](https://github.com/kubernetes/ingress-nginx/pull/3178) Update nginx to 1.15.5 -- [X] [#3179](https://github.com/kubernetes/ingress-nginx/pull/3179) Update nginx image -- [X] [#3182](https://github.com/kubernetes/ingress-nginx/pull/3182) Allow curly braces to be used in regex paths - -_Documentation:_ - -- [X] [#3021](https://github.com/kubernetes/ingress-nginx/pull/3021) Fix documentation search -- [X] [#3027](https://github.com/kubernetes/ingress-nginx/pull/3027) Add documentation about running Ingress NGINX on bare-metal -- [X] [#3039](https://github.com/kubernetes/ingress-nginx/pull/3039) Remove link to invalid example [ci-skip] -- [X] [#3046](https://github.com/kubernetes/ingress-nginx/pull/3046) Document when to modify ELB idle timeouts and set default value to 60s -- [X] [#3059](https://github.com/kubernetes/ingress-nginx/pull/3059) fix some typos -- [X] [#3068](https://github.com/kubernetes/ingress-nginx/pull/3068) Complete documentation about SSL Passthrough -- [X] [#3074](https://github.com/kubernetes/ingress-nginx/pull/3074) Add MetalLB to bare-metal deployment page -- [X] [#3090](https://github.com/kubernetes/ingress-nginx/pull/3090) Add note about default namespace and merge behavior -- [X] [#3092](https://github.com/kubernetes/ingress-nginx/pull/3092) Update mkdocs and travis-ci -- [X] [#3094](https://github.com/kubernetes/ingress-nginx/pull/3094) Fix baremetal images [skip ci] -- [X] [#3097](https://github.com/kubernetes/ingress-nginx/pull/3097) Added notes to regarding external access when using TCP/UDP proxy in Ingress -- [X] [#3102](https://github.com/kubernetes/ingress-nginx/pull/3102) Replace kubernetes-users mailing list links with discuss forum link -- [X] [#3111](https://github.com/kubernetes/ingress-nginx/pull/3111) doc issue related to monitor part -- [X] [#3113](https://github.com/kubernetes/ingress-nginx/pull/3113) fix typos -- [X] [#3115](https://github.com/kubernetes/ingress-nginx/pull/3115) Fixed link to aws elastic loadbalancer -- [X] [#3162](https://github.com/kubernetes/ingress-nginx/pull/3162) update name of config map in README.md -- [X] [#3175](https://github.com/kubernetes/ingress-nginx/pull/3175) Fix yaml indentation in annotations server-snippet doc - -### 0.19.0 - -**Image:** `quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.19.0` - -_New Features:_ - -- NGINX 1.15.3 -- Serve SSL certificates synamically instead of reloading NGINX when they are created, updated, or deleted. - Feature behind the flag `--enable-dynamic-certificates` -- GDB binary is included in the image to help [troubleshooting issues](https://github.com/kubernetes/ingress-nginx/pull/3002) -- Adjust the number of CPUs when CGROUP limits are defined (`worker-processes=auto` uses all the availables) - -_Changes:_ - -- [x] [#2616](https://github.com/kubernetes/ingress-nginx/pull/2616) Add use-forwarded-headers configmap option. -- [x] [#2857](https://github.com/kubernetes/ingress-nginx/pull/2857) remove unnecessary encoding/decoding also fix ipv6 issue -- [x] [#2884](https://github.com/kubernetes/ingress-nginx/pull/2884) [grafana] Rate over 2 minutes since default Prometheus interval is 1m -- [x] [#2889](https://github.com/kubernetes/ingress-nginx/pull/2889) Add Lua endpoint to support dynamic certificate serving functionality -- [x] [#2899](https://github.com/kubernetes/ingress-nginx/pull/2899) fixed rewrites for paths not ending in / -- [x] [#2923](https://github.com/kubernetes/ingress-nginx/pull/2923) Add dynamic certificate serving feature to controller -- [x] [#2925](https://github.com/kubernetes/ingress-nginx/pull/2925) Update nginx dependencies -- [x] [#2932](https://github.com/kubernetes/ingress-nginx/pull/2932) Fixed typo in flags.go -- [x] [#2934](https://github.com/kubernetes/ingress-nginx/pull/2934) Datasource input variable -- [x] [#2941](https://github.com/kubernetes/ingress-nginx/pull/2941) now actually using the $controller and $namespace variables -- [x] [#2942](https://github.com/kubernetes/ingress-nginx/pull/2942) Update nginx image -- [x] [#2946](https://github.com/kubernetes/ingress-nginx/pull/2946) Add unit tests to configuration_test.lua that cover Backends configuration -- [x] [#2955](https://github.com/kubernetes/ingress-nginx/pull/2955) Update nginx opentracing zipkin module -- [x] [#2956](https://github.com/kubernetes/ingress-nginx/pull/2956) Update nginx and e2e images -- [x] [#2957](https://github.com/kubernetes/ingress-nginx/pull/2957) Batch metrics and flush periodically -- [x] [#2964](https://github.com/kubernetes/ingress-nginx/pull/2964) fix variable parsing when key is number -- [x] [#2965](https://github.com/kubernetes/ingress-nginx/pull/2965) Add Lua module to serve SSL Certificates dynamically -- [x] [#2966](https://github.com/kubernetes/ingress-nginx/pull/2966) Add unit tests for sticky lua module -- [x] [#2970](https://github.com/kubernetes/ingress-nginx/pull/2970) Update labels -- [x] [#2972](https://github.com/kubernetes/ingress-nginx/pull/2972) consistently fallback to default certificate when TLS is configured -- [x] [#2977](https://github.com/kubernetes/ingress-nginx/pull/2977) Pass real source IP address to auth request -- [x] [#2979](https://github.com/kubernetes/ingress-nginx/pull/2979) clear dynamic configuration e2e tests -- [x] [#2987](https://github.com/kubernetes/ingress-nginx/pull/2987) cleanup dynamic cert e2e tests -- [x] [#2988](https://github.com/kubernetes/ingress-nginx/pull/2988) Update go to 1.11 -- [x] [#2990](https://github.com/kubernetes/ingress-nginx/pull/2990) Check if cgroup cpu limits are defined to get the number of CPUs -- [x] [#3003](https://github.com/kubernetes/ingress-nginx/pull/3003) Update nginx to 1.15.3 -- [x] [#3004](https://github.com/kubernetes/ingress-nginx/pull/3004) Update nginx image -- [x] [#3005](https://github.com/kubernetes/ingress-nginx/pull/3005) Fix gdb issue and update e2e image -- [x] [#3006](https://github.com/kubernetes/ingress-nginx/pull/3006) apply nginx patch to make ssl_certificate_by_lua_block work properly -- [x] [#3011](https://github.com/kubernetes/ingress-nginx/pull/3011) Update nginx image - -_Documentation:_ - -- [x] [#2806](https://github.com/kubernetes/ingress-nginx/pull/2806) add help for tls prerequisite for ingress.yaml -- [x] [#2912](https://github.com/kubernetes/ingress-nginx/pull/2912) Add documentation to install prometheus and grafana -- [x] [#2928](https://github.com/kubernetes/ingress-nginx/pull/2928) docs: Precisations on the usage of the InfluxDB module -- [x] [#2962](https://github.com/kubernetes/ingress-nginx/pull/2962) Fix broken anchor link to GCE/GKE -- [x] [#2983](https://github.com/kubernetes/ingress-nginx/pull/2983) Add documentation for enable-dynamic-certificates feature -- [x] [#2998](https://github.com/kubernetes/ingress-nginx/pull/2998) fixed jsonpath command in examples -- [x] [#3002](https://github.com/kubernetes/ingress-nginx/pull/3002) Enhance Troubleshooting Documentation - -### 0.18.0 - -**Image:** `quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.18.0` - -_New Features:_ - -- NGINX 1.15.2 -- Dynamic configuration is enabled by default -- Support for AJP protocol -- Use of authbind to bind privileged ports -- Replace minikube with [kubeadm-dind-cluster](https://github.com/kubernetes-sigs/kubeadm-dind-cluster) to run e2e tests - -_Changes:_ - -- [x] [#2789](https://github.com/kubernetes/ingress-nginx/pull/2789) Remove KubeConfig Dependency for Store Tests -- [x] [#2794](https://github.com/kubernetes/ingress-nginx/pull/2794) enable dynamic backend configuration by default -- [x] [#2795](https://github.com/kubernetes/ingress-nginx/pull/2795) start minikube before trying to build the image -- [x] [#2804](https://github.com/kubernetes/ingress-nginx/pull/2804) add support for ExternalName service type in dynamic mode -- [x] [#2808](https://github.com/kubernetes/ingress-nginx/pull/2808) fix the bug #2799, add prefix (?i) in rewrite statement. -- [x] [#2811](https://github.com/kubernetes/ingress-nginx/pull/2811) Escape $request_uri for external auth -- [x] [#2812](https://github.com/kubernetes/ingress-nginx/pull/2812) modified annotation name "rewrite-to" to "rewrite-target" in comments -- [x] [#2819](https://github.com/kubernetes/ingress-nginx/pull/2819) Catch errors waiting for controller deployment -- [x] [#2823](https://github.com/kubernetes/ingress-nginx/pull/2823) Multiple optimizations to build targets -- [x] [#2825](https://github.com/kubernetes/ingress-nginx/pull/2825) Refactoring of how we run as user -- [x] [#2826](https://github.com/kubernetes/ingress-nginx/pull/2826) Remove setcap from image and update nginx to 0.15.1 -- [x] [#2827](https://github.com/kubernetes/ingress-nginx/pull/2827) Use nginx image as base and install go on top -- [x] [#2829](https://github.com/kubernetes/ingress-nginx/pull/2829) use resty-cli for running lua unit tests -- [x] [#2830](https://github.com/kubernetes/ingress-nginx/pull/2830) Remove lua mocks -- [x] [#2834](https://github.com/kubernetes/ingress-nginx/pull/2834) Added permanent-redirect-code -- [x] [#2844](https://github.com/kubernetes/ingress-nginx/pull/2844) Do not allow invalid latency values in metrics -- [x] [#2852](https://github.com/kubernetes/ingress-nginx/pull/2852) fix custom-error-pages functionality in dynamic mode -- [x] [#2853](https://github.com/kubernetes/ingress-nginx/pull/2853) improve annotations/default_backend e2e test -- [x] [#2858](https://github.com/kubernetes/ingress-nginx/pull/2858) Update build image -- [x] [#2859](https://github.com/kubernetes/ingress-nginx/pull/2859) Fix inconsistent metric labels -- [x] [#2863](https://github.com/kubernetes/ingress-nginx/pull/2863) Replace minikube for e2e tests -- [x] [#2867](https://github.com/kubernetes/ingress-nginx/pull/2867) fix bug with lua e2e test suite -- [x] [#2868](https://github.com/kubernetes/ingress-nginx/pull/2868) Use an existing e2e image -- [x] [#2869](https://github.com/kubernetes/ingress-nginx/pull/2869) describe under what circumstances and how we avoid Nginx reload -- [x] [#2871](https://github.com/kubernetes/ingress-nginx/pull/2871) Add support for AJP protocol -- [x] [#2872](https://github.com/kubernetes/ingress-nginx/pull/2872) Update nginx to 1.15.2 -- [x] [#2874](https://github.com/kubernetes/ingress-nginx/pull/2874) Delay initial prometheus status metric -- [x] [#2876](https://github.com/kubernetes/ingress-nginx/pull/2876) Remove dashboard an tune sync-frequency -- [x] [#2877](https://github.com/kubernetes/ingress-nginx/pull/2877) Refactor entrypoint to avoid issues with volumes -- [x] [#2885](https://github.com/kubernetes/ingress-nginx/pull/2885) fix: Sort TCP/UDP upstream order -- [x] [#2888](https://github.com/kubernetes/ingress-nginx/pull/2888) Fix grafana datasources -- [x] [#2890](https://github.com/kubernetes/ingress-nginx/pull/2890) Usability improvements to build steps -- [x] [#2893](https://github.com/kubernetes/ingress-nginx/pull/2893) Update nginx image -- [x] [#2894](https://github.com/kubernetes/ingress-nginx/pull/2894) Use authbind to bind privileged ports -- [x] [#2895](https://github.com/kubernetes/ingress-nginx/pull/2895) support custom configuration to main context of nginx config -- [x] [#2896](https://github.com/kubernetes/ingress-nginx/pull/2896) support configuring multi_accept directive via configmap -- [x] [#2897](https://github.com/kubernetes/ingress-nginx/pull/2897) Enable reuse-port by default -- [x] [#2905](https://github.com/kubernetes/ingress-nginx/pull/2905) Fix IPV6 detection - -_Documentation:_ - -- [x] [#2816](https://github.com/kubernetes/ingress-nginx/pull/2816) doc log-format: add variables about ingress -- [x] [#2866](https://github.com/kubernetes/ingress-nginx/pull/2866) Update index.md -- [x] [#2898](https://github.com/kubernetes/ingress-nginx/pull/2898) Fix default sync-period doc -- [x] [#2903](https://github.com/kubernetes/ingress-nginx/pull/2903) Very minor grammar fix - -### 0.17.1 - -**Image:** `quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.17.1` - -_Changes:_ - -- [x] [#2782](https://github.com/kubernetes/ingress-nginx/pull/2782) Add Better Error Handling for SSLSessionTicketKey -- [x] [#2790](https://github.com/kubernetes/ingress-nginx/pull/2790) Update prometheus labels - -_Documentation:_ - -- [x] [#2770](https://github.com/kubernetes/ingress-nginx/pull/2770) Basic-Auth doc misleading: fix double quotes leading to nginx config error - -### 0.17.0 - -**Image:** `quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.17.0` - -_New Features:_ - -- [Grafana dashboards](https://github.com/kubernetes/ingress-nginx/tree/main/deploy/grafana/dashboards) - -_Changes:_ - -- [x] [#2705](https://github.com/kubernetes/ingress-nginx/pull/2705) Remove duplicated securityContext -- [x] [#2719](https://github.com/kubernetes/ingress-nginx/pull/2719) Sample rate configmap option for zipkin in nginx-opentracing -- [x] [#2726](https://github.com/kubernetes/ingress-nginx/pull/2726) Cleanup prometheus metrics after a reload -- [x] [#2727](https://github.com/kubernetes/ingress-nginx/pull/2727) Add e2e tests for Client-Body-Buffer-Size -- [x] [#2732](https://github.com/kubernetes/ingress-nginx/pull/2732) Improve logging -- [x] [#2741](https://github.com/kubernetes/ingress-nginx/pull/2741) Add redirect uri for oauth2 login -- [x] [#2744](https://github.com/kubernetes/ingress-nginx/pull/2744) fix: Use the correct opentracing plugin for Jaeger -- [x] [#2747](https://github.com/kubernetes/ingress-nginx/pull/2747) Update opentracing-cpp and modsecurity -- [x] [#2748](https://github.com/kubernetes/ingress-nginx/pull/2748) Update nginx image to 0.54 -- [x] [#2749](https://github.com/kubernetes/ingress-nginx/pull/2749) Use docker to build go binaries -- [x] [#2754](https://github.com/kubernetes/ingress-nginx/pull/2754) Allow gzip compression level to be controlled via ConfigMap -- [x] [#2760](https://github.com/kubernetes/ingress-nginx/pull/2760) Fix ingress rule parsing error -- [x] [#2767](https://github.com/kubernetes/ingress-nginx/pull/2767) Fix regression introduced in #2732 -- [x] [#2771](https://github.com/kubernetes/ingress-nginx/pull/2771) Grafana Dashboard -- [x] [#2775](https://github.com/kubernetes/ingress-nginx/pull/2775) Simplify handler registration and updates prometheus -- [x] [#2776](https://github.com/kubernetes/ingress-nginx/pull/2776) Fix configuration hash calculation - -_Documentation:_ - -- [x] [#2717](https://github.com/kubernetes/ingress-nginx/pull/2717) GCE/GKE proxy mentioned for Azure -- [x] [#2743](https://github.com/kubernetes/ingress-nginx/pull/2743) Clarify Installation Document by Separating Helm Steps -- [x] [#2761](https://github.com/kubernetes/ingress-nginx/pull/2761) Fix spelling mistake -- [x] [#2764](https://github.com/kubernetes/ingress-nginx/pull/2764) Use language neutral links to MDN -- [x] [#2765](https://github.com/kubernetes/ingress-nginx/pull/2765) Add FOSSA status badge -- [x] [#2777](https://github.com/kubernetes/ingress-nginx/pull/2777) Build docs using local docker image [ci skip] - -### 0.16.2 - -**Image:** `quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.16.2` - -_Breaking changes:_ - -Running as user requires an update in the deployment manifest. - -```yaml -securityContext: - capabilities: - drop: - - ALL - add: - - NET_BIND_SERVICE - # www-data -> 33 - runAsUser: 33 -``` - -Note: the deploy [guide](https://kubernetes.github.io/ingress-nginx/deploy/#mandatory-command) contains this change - -_Changes:_ - -- [x] [#2678](https://github.com/kubernetes/ingress-nginx/pull/2678) Refactor server type to include SSLCert -- [x] [#2685](https://github.com/kubernetes/ingress-nginx/pull/2685) Fix qemu docker build -- [x] [#2696](https://github.com/kubernetes/ingress-nginx/pull/2696) If server_tokens is disabled completely remove the Server header -- [x] [#2698](https://github.com/kubernetes/ingress-nginx/pull/2698) Improve best-cert guessing with empty tls.hosts -- [x] [#2701](https://github.com/kubernetes/ingress-nginx/pull/2701) Remove prometheus labels with high cardinality - -_Documentation:_ - -- [x] [#2368](https://github.com/kubernetes/ingress-nginx/pull/2368) [aggregate] Fix typos across codebase -- [x] [#2681](https://github.com/kubernetes/ingress-nginx/pull/2681) Typo fix in error message: encounted->encountered -- [x] [#2697](https://github.com/kubernetes/ingress-nginx/pull/2697) Enhance Distributed Tracing Documentation - -### 0.16.1 - -**Image:** `quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.16.1` - -_Breaking changes:_ - -Running as user requires an update in the deployment manifest. - -```yaml -securityContext: - capabilities: - drop: - - ALL - add: - - NET_BIND_SERVICE - # www-data -> 33 - runAsUser: 33 -``` - -Note: the deploy [guide](https://kubernetes.github.io/ingress-nginx/deploy/#mandatory-command) contains this change - -_New Features:_ - -- Run as user dropping root privileges -- New prometheus metric implementation (VTS module was removed) -- [InfluxDB integration](https://kubernetes.github.io/ingress-nginx/user-guide/nginx-configuration/annotations/#influxdb) -- [Module GeoIP2](https://github.com/leev/ngx_http_geoip2_module) - -_Changes:_ - -- [x] [#2692](https://github.com/kubernetes/ingress-nginx/pull/2692) Fix initial read of configuration configmap -- [x] [#2693](https://github.com/kubernetes/ingress-nginx/pull/2693) Revert #2669 -- [x] [#2694](https://github.com/kubernetes/ingress-nginx/pull/2694) Add note about status update - -### 0.16.0 - -**Image:** `quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.16.1` - -_Breaking changes:_ - -Running as user requires an update in the deployment manifest. - -```yaml -securityContext: - capabilities: - drop: - - ALL - add: - - NET_BIND_SERVICE - # www-data -> 33 - runAsUser: 33 -``` - -Note: the deploy [guide](https://kubernetes.github.io/ingress-nginx/deploy/#mandatory-command) contains this change - -_New Features:_ - -- Run as user dropping root privileges -- New prometheus metric implementation (VTS module was removed) -- [InfluxDB integration](https://kubernetes.github.io/ingress-nginx/user-guide/nginx-configuration/annotations/#influxdb) -- [Module GeoIP2](https://github.com/leev/ngx_http_geoip2_module) - -_Changes:_ - -- [x] [#2423](https://github.com/kubernetes/ingress-nginx/pull/2423) Resolves issue with proxy-redirect nginx configuration -- [x] [#2451](https://github.com/kubernetes/ingress-nginx/pull/2451) fix for #1930, make sessions sticky, for ingress with multiple rules … -- [x] [#2484](https://github.com/kubernetes/ingress-nginx/pull/2484) Fix bugs in Lua implementation of sticky sessions -- [x] [#2486](https://github.com/kubernetes/ingress-nginx/pull/2486) Extend kubernetes interrelation variables in nginx.tmpl -- [x] [#2504](https://github.com/kubernetes/ingress-nginx/pull/2504) Add Timeout For TLS Passthrough -- [x] [#2505](https://github.com/kubernetes/ingress-nginx/pull/2505) Annotations for the InfluxDB module -- [x] [#2517](https://github.com/kubernetes/ingress-nginx/pull/2517) Fix typo about the kind of request -- [x] [#2523](https://github.com/kubernetes/ingress-nginx/pull/2523) Add tests for bind-address -- [x] [#2524](https://github.com/kubernetes/ingress-nginx/pull/2524) Add support for grpc_set_header -- [x] [#2526](https://github.com/kubernetes/ingress-nginx/pull/2526) Fix upstream hash lua test -- [x] [#2528](https://github.com/kubernetes/ingress-nginx/pull/2528) Remove go-bindata -- [x] [#2533](https://github.com/kubernetes/ingress-nginx/pull/2533) NGINX image update: add the influxdb module -- [x] [#2534](https://github.com/kubernetes/ingress-nginx/pull/2534) Set Focus for E2E Tests -- [x] [#2537](https://github.com/kubernetes/ingress-nginx/pull/2537) Update nginx modules -- [x] [#2542](https://github.com/kubernetes/ingress-nginx/pull/2542) Instrument controller to show configReload metrics -- [x] [#2543](https://github.com/kubernetes/ingress-nginx/pull/2543) introduce a balancer interface -- [x] [#2548](https://github.com/kubernetes/ingress-nginx/pull/2548) Implement generate-request-id -- [x] [#2554](https://github.com/kubernetes/ingress-nginx/pull/2554) use better defaults for proxy-next-upstream(-tries) -- [x] [#2558](https://github.com/kubernetes/ingress-nginx/pull/2558) Update qemu to 2.12.0 [ci skip] -- [x] [#2559](https://github.com/kubernetes/ingress-nginx/pull/2559) Add geoip2 module and DB to nginx build -- [x] [#2564](https://github.com/kubernetes/ingress-nginx/pull/2564) Add security contacts file [ci skip] -- [x] [#2569](https://github.com/kubernetes/ingress-nginx/pull/2569) Update nginx modules to fix core dump [ci skip] -- [x] [#2570](https://github.com/kubernetes/ingress-nginx/pull/2570) Enable core dumps during tests -- [x] [#2573](https://github.com/kubernetes/ingress-nginx/pull/2573) Refactor e2e tests and update go dependencies -- [x] [#2574](https://github.com/kubernetes/ingress-nginx/pull/2574) Fix default-backend annotation -- [x] [#2575](https://github.com/kubernetes/ingress-nginx/pull/2575) Print information about NGINX version -- [x] [#2577](https://github.com/kubernetes/ingress-nginx/pull/2577) make sure ingress-nginx instances are watching their namespace only during test runs -- [x] [#2588](https://github.com/kubernetes/ingress-nginx/pull/2588) Update nginx dependencies -- [x] [#2590](https://github.com/kubernetes/ingress-nginx/pull/2590) Typo fix: muthual autentication -> mutual authentication -- [x] [#2591](https://github.com/kubernetes/ingress-nginx/pull/2591) Access log improvements -- [x] [#2597](https://github.com/kubernetes/ingress-nginx/pull/2597) Fix arm paths for liblua.so and lua_package_cpath -- [x] [#2598](https://github.com/kubernetes/ingress-nginx/pull/2598) Always sort upstream list to provide stable iteration order -- [x] [#2600](https://github.com/kubernetes/ingress-nginx/pull/2600) typo fix futher to further && preformance to performance -- [x] [#2602](https://github.com/kubernetes/ingress-nginx/pull/2602) Crossplat fixes -- [x] [#2603](https://github.com/kubernetes/ingress-nginx/pull/2603) Bump nginx influxdb module to f8732268d44aea706ecf8d9c6036e9b6dacc99b2 -- [x] [#2608](https://github.com/kubernetes/ingress-nginx/pull/2608) Expose UDP message on /metrics endpoint -- [x] [#2611](https://github.com/kubernetes/ingress-nginx/pull/2611) Add metric emitter lua module -- [x] [#2614](https://github.com/kubernetes/ingress-nginx/pull/2614) fix nginx conf test error when not found active service endpoints -- [x] [#2617](https://github.com/kubernetes/ingress-nginx/pull/2617) Update go to 1.10.3 -- [x] [#2618](https://github.com/kubernetes/ingress-nginx/pull/2618) Update nginx to 1.15.0 and remove VTS module -- [x] [#2619](https://github.com/kubernetes/ingress-nginx/pull/2619) Run as user dropping privileges -- [x] [#2623](https://github.com/kubernetes/ingress-nginx/pull/2623) Proofread cmd package and update flags description -- [x] [#2634](https://github.com/kubernetes/ingress-nginx/pull/2634) Disable resync period -- [x] [#2636](https://github.com/kubernetes/ingress-nginx/pull/2636) Add missing equality comparisons for ingress.Server -- [x] [#2638](https://github.com/kubernetes/ingress-nginx/pull/2638) Wait the result of the controller deployment before running any test -- [x] [#2639](https://github.com/kubernetes/ingress-nginx/pull/2639) Clarify log messages in controller package -- [x] [#2643](https://github.com/kubernetes/ingress-nginx/pull/2643) Remove VTS from the ingress controller -- [x] [#2644](https://github.com/kubernetes/ingress-nginx/pull/2644) Update nginx image version -- [x] [#2646](https://github.com/kubernetes/ingress-nginx/pull/2646) Rollback nginx 1.15.0 to 1.13.12 -- [x] [#2649](https://github.com/kubernetes/ingress-nginx/pull/2649) Add support for IPV6 in stream upstream servers -- [x] [#2652](https://github.com/kubernetes/ingress-nginx/pull/2652) Use a unix socket instead udp for reception of metrics -- [x] [#2653](https://github.com/kubernetes/ingress-nginx/pull/2653) Remove dummy file watcher -- [x] [#2654](https://github.com/kubernetes/ingress-nginx/pull/2654) Hotfix: influxdb module enable disable toggle -- [x] [#2656](https://github.com/kubernetes/ingress-nginx/pull/2656) Improve configuration change detection -- [x] [#2658](https://github.com/kubernetes/ingress-nginx/pull/2658) Do not wait informer initialization to read configuration -- [x] [#2659](https://github.com/kubernetes/ingress-nginx/pull/2659) Update nginx image -- [x] [#2660](https://github.com/kubernetes/ingress-nginx/pull/2660) Change modsecurity directories -- [x] [#2661](https://github.com/kubernetes/ingress-nginx/pull/2661) Add additional header when debug is enabled -- [x] [#2664](https://github.com/kubernetes/ingress-nginx/pull/2664) refactor some lua code -- [x] [#2669](https://github.com/kubernetes/ingress-nginx/pull/2669) Remove unnecessary sync when the leader change -- [x] [#2672](https://github.com/kubernetes/ingress-nginx/pull/2672) After a configmap change parse ingress annotations (again) -- [x] [#2673](https://github.com/kubernetes/ingress-nginx/pull/2673) Add new approvers to the project -- [x] [#2674](https://github.com/kubernetes/ingress-nginx/pull/2674) Add e2e test for configmap change and reload -- [x] [#2675](https://github.com/kubernetes/ingress-nginx/pull/2675) Update opentracing nginx module -- [x] [#2676](https://github.com/kubernetes/ingress-nginx/pull/2676) Update opentracing configuration - -_Documentation:_ - -- [x] [#2479](https://github.com/kubernetes/ingress-nginx/pull/2479) Document how the NGINX Ingress controller build nginx.conf -- [x] [#2515](https://github.com/kubernetes/ingress-nginx/pull/2515) Simplify installation and e2e manifests -- [x] [#2531](https://github.com/kubernetes/ingress-nginx/pull/2531) Mention the #ingress-nginx Slack channel -- [x] [#2540](https://github.com/kubernetes/ingress-nginx/pull/2540) DOCS: Correct ssl-passthrough annotation description. -- [x] [#2544](https://github.com/kubernetes/ingress-nginx/pull/2544) [docs] Fix manifest URL for GKE + Azure -- [x] [#2566](https://github.com/kubernetes/ingress-nginx/pull/2566) Fix wrong default value for `enable-brotli` -- [x] [#2581](https://github.com/kubernetes/ingress-nginx/pull/2581) Improved link in modsecurity.md -- [x] [#2583](https://github.com/kubernetes/ingress-nginx/pull/2583) docs: add secret scheme details to the example -- [x] [#2592](https://github.com/kubernetes/ingress-nginx/pull/2592) Typo fix: are be->are/to on->to -- [x] [#2595](https://github.com/kubernetes/ingress-nginx/pull/2595) Typo fix: successfull->successful -- [x] [#2601](https://github.com/kubernetes/ingress-nginx/pull/2601) fix changelog link in README.md -- [x] [#2624](https://github.com/kubernetes/ingress-nginx/pull/2624) Fix minor documentation example -- [x] [#2625](https://github.com/kubernetes/ingress-nginx/pull/2625) Add annotation doc on proxy buffer size -- [x] [#2630](https://github.com/kubernetes/ingress-nginx/pull/2630) Update documentation for custom error pages -- [x] [#2666](https://github.com/kubernetes/ingress-nginx/pull/2666) Add documentation for proxy-cookie-domain annotation (#2034) - -### 0.15.0 - -**Image:** `quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.15.0` - -_Changes:_ - -- [x] [#2440](https://github.com/kubernetes/ingress-nginx/pull/2440) TLS tests -- [x] [#2443](https://github.com/kubernetes/ingress-nginx/pull/2443) improve build-dev-env.sh script -- [x] [#2446](https://github.com/kubernetes/ingress-nginx/pull/2446) always use x-request-id -- [x] [#2447](https://github.com/kubernetes/ingress-nginx/pull/2447) Add basic security context to deployment YAMLs -- [x] [#2453](https://github.com/kubernetes/ingress-nginx/pull/2453) Add google analytics [ci skip] -- [x] [#2456](https://github.com/kubernetes/ingress-nginx/pull/2456) Assert or install go-bindata before incanting -- [x] [#2472](https://github.com/kubernetes/ingress-nginx/pull/2472) Refactor Lua balancer -- [x] [#2477](https://github.com/kubernetes/ingress-nginx/pull/2477) Change TrimLeft for TrimPrefix on the from-to-www redirect -- [x] [#2490](https://github.com/kubernetes/ingress-nginx/pull/2490) add resty cookie -- [x] [#2495](https://github.com/kubernetes/ingress-nginx/pull/2495) [ci skip] bump nginx baseimage version -- [x] [#2501](https://github.com/kubernetes/ingress-nginx/pull/2501) Refactor update of status removing initial check for loadbalancer -- [x] [#2502](https://github.com/kubernetes/ingress-nginx/pull/2502) Update go version in fortune teller image -- [x] [#2511](https://github.com/kubernetes/ingress-nginx/pull/2511) force backend sync when worker starts -- [x] [#2512](https://github.com/kubernetes/ingress-nginx/pull/2512) Remove warning when secret is used only for authentication -- [x] [#2514](https://github.com/kubernetes/ingress-nginx/pull/2514) Fix and simplify local dev workflow and execution of e2e tests - -_Documentation:_ - -- [x] [#2448](https://github.com/kubernetes/ingress-nginx/pull/2448) Update GitHub pull request template -- [x] [#2449](https://github.com/kubernetes/ingress-nginx/pull/2449) Improve documentation format -- [x] [#2454](https://github.com/kubernetes/ingress-nginx/pull/2454) Add gRPC annotation doc -- [x] [#2455](https://github.com/kubernetes/ingress-nginx/pull/2455) Adjust size of tables and only adjust the first column on mobile -- [x] [#2457](https://github.com/kubernetes/ingress-nginx/pull/2457) Add Getting the Code section to Quick Start -- [x] [#2464](https://github.com/kubernetes/ingress-nginx/pull/2464) Documentation fixes & improvements -- [x] [#2467](https://github.com/kubernetes/ingress-nginx/pull/2467) Fixed broken link in deploy README -- [x] [#2498](https://github.com/kubernetes/ingress-nginx/pull/2498) Add some clarification around multiple ingress controller behavior -- [x] [#2503](https://github.com/kubernetes/ingress-nginx/pull/2503) Add KubeCon Europe 2018 Video to documentation - -### 0.14.0 - -**Image:** `quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.14.0` - -_New Features:_ - -- [Documentation web page](https://kubernetes.github.io/ingress-nginx/) -- Support for `upstream-hash-by` annotation in dynamic configuration mode -- Improved e2e test suite - -_Changes:_ - -- [x] [#2346](https://github.com/kubernetes/ingress-nginx/pull/2346) Move ConfigMap updating methods into e2e/framework -- [x] [#2347](https://github.com/kubernetes/ingress-nginx/pull/2347) Update owners -- [x] [#2348](https://github.com/kubernetes/ingress-nginx/pull/2348) Use same convention, curl + kubectl for GKE -- [x] [#2350](https://github.com/kubernetes/ingress-nginx/pull/2350) Correct some returned messages in server_tokens.go -- [x] [#2352](https://github.com/kubernetes/ingress-nginx/pull/2352) Correct some info in flags.go -- [x] [#2353](https://github.com/kubernetes/ingress-nginx/pull/2353) Add proxy-add-original-uri-header config flag -- [x] [#2356](https://github.com/kubernetes/ingress-nginx/pull/2356) Add vts-sum-key config flag -- [x] [#2361](https://github.com/kubernetes/ingress-nginx/pull/2361) Check ingress rule contains HTTP paths -- [x] [#2363](https://github.com/kubernetes/ingress-nginx/pull/2363) Review $request_id -- [x] [#2365](https://github.com/kubernetes/ingress-nginx/pull/2365) Clean JSON before post request to update configuration -- [x] [#2369](https://github.com/kubernetes/ingress-nginx/pull/2369) Update nginx image to fix modsecurity crs issues -- [x] [#2370](https://github.com/kubernetes/ingress-nginx/pull/2370) Update nginx image -- [x] [#2374](https://github.com/kubernetes/ingress-nginx/pull/2374) Remove most of the time.Sleep from the e2e tests -- [x] [#2379](https://github.com/kubernetes/ingress-nginx/pull/2379) Add busted unit testing framework for lua code -- [x] [#2382](https://github.com/kubernetes/ingress-nginx/pull/2382) Accept ns/name Secret reference in annotations -- [x] [#2383](https://github.com/kubernetes/ingress-nginx/pull/2383) Improve speed of e2e tests -- [x] [#2385](https://github.com/kubernetes/ingress-nginx/pull/2385) include lua-resty-balancer in nginx image -- [x] [#2386](https://github.com/kubernetes/ingress-nginx/pull/2386) upstream-hash-by annotation support for dynamic configuraton mode -- [x] [#2388](https://github.com/kubernetes/ingress-nginx/pull/2388) Silence unnecessary MissingAnnotations errors -- [x] [#2392](https://github.com/kubernetes/ingress-nginx/pull/2392) Ensure dep fix fsnotify -- [x] [#2395](https://github.com/kubernetes/ingress-nginx/pull/2395) Fix flaky test -- [x] [#2396](https://github.com/kubernetes/ingress-nginx/pull/2396) Update go dependencies -- [x] [#2398](https://github.com/kubernetes/ingress-nginx/pull/2398) Allow tls section without hosts in Ingress rule -- [x] [#2399](https://github.com/kubernetes/ingress-nginx/pull/2399) Add test for store helper ListIngresses -- [x] [#2401](https://github.com/kubernetes/ingress-nginx/pull/2401) Add tests for controller getEndpoints -- [x] [#2408](https://github.com/kubernetes/ingress-nginx/pull/2408) Read backends data even if buffered to temp file -- [x] [#2410](https://github.com/kubernetes/ingress-nginx/pull/2410) Add balancer unit tests -- [x] [#2411](https://github.com/kubernetes/ingress-nginx/pull/2411) Update nginx-opentracing to 0.3.0 -- [x] [#2414](https://github.com/kubernetes/ingress-nginx/pull/2414) Fix golint installation -- [x] [#2416](https://github.com/kubernetes/ingress-nginx/pull/2416) Update nginx image -- [x] [#2417](https://github.com/kubernetes/ingress-nginx/pull/2417) Automate building developer environment -- [x] [#2421](https://github.com/kubernetes/ingress-nginx/pull/2421) Apply gometalinter suggestions -- [x] [#2428](https://github.com/kubernetes/ingress-nginx/pull/2428) Add buffer configuration to external auth location config -- [x] [#2433](https://github.com/kubernetes/ingress-nginx/pull/2433) Remove data races from tests -- [x] [#2434](https://github.com/kubernetes/ingress-nginx/pull/2434) Check ginkgo is installed before running e2e tests -- [x] [#2437](https://github.com/kubernetes/ingress-nginx/pull/2437) Add annotation to enable rewrite logs in a location - -_Documentation:_ - -- [x] [#2351](https://github.com/kubernetes/ingress-nginx/pull/2351) Typo fix in cli-arguments.md -- [x] [#2372](https://github.com/kubernetes/ingress-nginx/pull/2372) fix the default cookie name in doc -- [x] [#2377](https://github.com/kubernetes/ingress-nginx/pull/2377) DOCS: Add clarification regarding ssl passthrough -- [x] [#2409](https://github.com/kubernetes/ingress-nginx/pull/2409) Add deployment instructions for Docker for Mac (Edge) -- [x] [#2413](https://github.com/kubernetes/ingress-nginx/pull/2413) Reorganize documentation -- [x] [#2438](https://github.com/kubernetes/ingress-nginx/pull/2438) Update custom-errors.md -- [x] [#2439](https://github.com/kubernetes/ingress-nginx/pull/2439) Update README.md -- [x] [#2430](https://github.com/kubernetes/ingress-nginx/pull/2430) Add scripts and tasks to publish docs to github pages -- [x] [#2431](https://github.com/kubernetes/ingress-nginx/pull/2431) Improve readme file -- [x] [#2366](https://github.com/kubernetes/ingress-nginx/pull/2366) fix: fill missing patch yaml config. -- [x] [#2432](https://github.com/kubernetes/ingress-nginx/pull/2432) Fix broken links in the docs -- [x] [#2436](https://github.com/kubernetes/ingress-nginx/pull/2436) Update exposing-tcp-udp-services.md - -### 0.13.0 - -**Image:** `quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.13.0` - -_New Features:_ - -- NGINX 1.13.12 -- Support for gRPC: - - The annotation `nginx.ingress.kubernetes.io/grpc-backend: "true"` enable this feature - - If the gRPC service requires TLS `nginx.ingress.kubernetes.io/secure-backends: "true"` -- Configurable load balancing with EWMA -- Support for [lua-resty-waf](https://github.com/p0pr0ck5/lua-resty-waf) as alternative to ModSecurity. [Check configuration guide](https://github.com/kubernetes/ingress-nginx/blob/main/docs/user-guide/annotations.md#lua-resty-waf) -- Support for session affinity when dynamic configuration is enabled. -- Add NoAuthLocations and default it to "/.well-known/acme-challenge" - -_Changes:_ - -- [x] [#2078](https://github.com/kubernetes/ingress-nginx/pull/2078) Expose SSL client cert data to external auth provider. -- [x] [#2187](https://github.com/kubernetes/ingress-nginx/pull/2187) Managing a whitelist for \_/nginx_status -- [x] [#2208](https://github.com/kubernetes/ingress-nginx/pull/2208) Add missing lua bindata change -- [x] [#2209](https://github.com/kubernetes/ingress-nginx/pull/2209) fix go test TestSkipEnqueue error, move queue.Run -- [x] [#2210](https://github.com/kubernetes/ingress-nginx/pull/2210) allow ipv6 localhost when enabled -- [x] [#2212](https://github.com/kubernetes/ingress-nginx/pull/2212) Fix dynamic configuration when custom errors are enabled -- [x] [#2215](https://github.com/kubernetes/ingress-nginx/pull/2215) fix wrong config generation when upstream-hash-by is set -- [x] [#2220](https://github.com/kubernetes/ingress-nginx/pull/2220) fix: cannot set $service_name if use rewrite -- [x] [#2221](https://github.com/kubernetes/ingress-nginx/pull/2221) Update nginx to 1.13.10 and enable gRPC -- [x] [#2223](https://github.com/kubernetes/ingress-nginx/pull/2223) Add support for gRPC -- [x] [#2227](https://github.com/kubernetes/ingress-nginx/pull/2227) do not hardcode keepalive for upstream_balancer -- [x] [#2228](https://github.com/kubernetes/ingress-nginx/pull/2228) Fix broken links in multi-tls -- [x] [#2229](https://github.com/kubernetes/ingress-nginx/pull/2229) Configurable load balancing with EWMA -- [x] [#2232](https://github.com/kubernetes/ingress-nginx/pull/2232) Make proxy_next_upstream_tries configurable -- [x] [#2233](https://github.com/kubernetes/ingress-nginx/pull/2233) clean backends data before sending to Lua endpoint -- [x] [#2234](https://github.com/kubernetes/ingress-nginx/pull/2234) Update go dependencies -- [x] [#2235](https://github.com/kubernetes/ingress-nginx/pull/2235) add proxy header ssl-client-issuer-dn, fix #2178 -- [x] [#2241](https://github.com/kubernetes/ingress-nginx/pull/2241) Revert "Get file max from fs/file-max. (#2050)" -- [x] [#2243](https://github.com/kubernetes/ingress-nginx/pull/2243) Add NoAuthLocations and default it to "/.well-known/acme-challenge" -- [x] [#2244](https://github.com/kubernetes/ingress-nginx/pull/2244) fix: empty ingress path -- [x] [#2246](https://github.com/kubernetes/ingress-nginx/pull/2246) Fix grpc json tag name -- [x] [#2254](https://github.com/kubernetes/ingress-nginx/pull/2254) e2e tests for dynamic configuration and Lua features and a bug fix -- [x] [#2263](https://github.com/kubernetes/ingress-nginx/pull/2263) clean up tmpl -- [x] [#2270](https://github.com/kubernetes/ingress-nginx/pull/2270) Revert deleted code in #2146 -- [x] [#2271](https://github.com/kubernetes/ingress-nginx/pull/2271) Use SharedIndexInformers in place of Informers -- [x] [#2272](https://github.com/kubernetes/ingress-nginx/pull/2272) Disable opentracing for nginx internal urls -- [x] [#2273](https://github.com/kubernetes/ingress-nginx/pull/2273) Update go to 1.10.1 -- [x] [#2280](https://github.com/kubernetes/ingress-nginx/pull/2280) Fix bug when auth req is enabled(external authentication) -- [x] [#2283](https://github.com/kubernetes/ingress-nginx/pull/2283) Fix flaky e2e tests -- [x] [#2285](https://github.com/kubernetes/ingress-nginx/pull/2285) Update controller.go -- [x] [#2290](https://github.com/kubernetes/ingress-nginx/pull/2290) Update nginx to 1.13.11 -- [x] [#2294](https://github.com/kubernetes/ingress-nginx/pull/2294) Fix HSTS without preload -- [x] [#2296](https://github.com/kubernetes/ingress-nginx/pull/2296) Improve indentation of generated nginx.conf -- [x] [#2298](https://github.com/kubernetes/ingress-nginx/pull/2298) Disable dynamic configuration in s390x and ppc64le -- [x] [#2300](https://github.com/kubernetes/ingress-nginx/pull/2300) Fix race condition when Ingress does not contains a secret -- [x] [#2301](https://github.com/kubernetes/ingress-nginx/pull/2301) include lua-resty-waf and its dependencies in the base Nginx image -- [x] [#2303](https://github.com/kubernetes/ingress-nginx/pull/2303) More lua dependencies -- [x] [#2304](https://github.com/kubernetes/ingress-nginx/pull/2304) Lua resty waf controller -- [x] [#2305](https://github.com/kubernetes/ingress-nginx/pull/2305) Fix issues building nginx image in different platforms -- [x] [#2306](https://github.com/kubernetes/ingress-nginx/pull/2306) Disable lua waf where luajit is not available -- [x] [#2308](https://github.com/kubernetes/ingress-nginx/pull/2308) Add verification of lua load balancer to health check -- [x] [#2309](https://github.com/kubernetes/ingress-nginx/pull/2309) Configure upload limits for setup of lua load balancer -- [x] [#2314](https://github.com/kubernetes/ingress-nginx/pull/2314) annotation to ignore given list of WAF rulesets -- [x] [#2315](https://github.com/kubernetes/ingress-nginx/pull/2315) extra waf rules per ingress -- [x] [#2317](https://github.com/kubernetes/ingress-nginx/pull/2317) run lua-resty-waf in different modes -- [x] [#2327](https://github.com/kubernetes/ingress-nginx/pull/2327) Update nginx to 1.13.12 -- [x] [#2328](https://github.com/kubernetes/ingress-nginx/pull/2328) Update nginx image -- [x] [#2331](https://github.com/kubernetes/ingress-nginx/pull/2331) fix nil pointer when ssl with ca.crt -- [x] [#2333](https://github.com/kubernetes/ingress-nginx/pull/2333) disable lua for arch s390x and ppc64le -- [x] [#2340](https://github.com/kubernetes/ingress-nginx/pull/2340) Fix buildupstream name to work with dynamic session affinity -- [x] [#2341](https://github.com/kubernetes/ingress-nginx/pull/2341) Add session affinity to custom load balancing -- [x] [#2342](https://github.com/kubernetes/ingress-nginx/pull/2342) Sync SSL certificates on events - -_Documentation:_ - -- [x] [#2236](https://github.com/kubernetes/ingress-nginx/pull/2236) Add missing configuration in #2235 -- [x] [#1785](https://github.com/kubernetes/ingress-nginx/pull/1785) Add deployment docs for AWS NLB -- [x] [#2213](https://github.com/kubernetes/ingress-nginx/pull/2213) Update cli-arguments.md -- [x] [#2219](https://github.com/kubernetes/ingress-nginx/pull/2219) Fix log format documentation -- [x] [#2238](https://github.com/kubernetes/ingress-nginx/pull/2238) Correct typo -- [x] [#2239](https://github.com/kubernetes/ingress-nginx/pull/2239) fix-link -- [x] [#2240](https://github.com/kubernetes/ingress-nginx/pull/2240) fix:"any value other" should be "any other value" -- [x] [#2255](https://github.com/kubernetes/ingress-nginx/pull/2255) Update annotations.md -- [x] [#2267](https://github.com/kubernetes/ingress-nginx/pull/2267) Update README.md -- [x] [#2274](https://github.com/kubernetes/ingress-nginx/pull/2274) Typo fixes in modsecurity.md -- [x] [#2276](https://github.com/kubernetes/ingress-nginx/pull/2276) Update README.md -- [x] [#2282](https://github.com/kubernetes/ingress-nginx/pull/2282) Fix nlb instructions - -### 0.12.0 - -**Image:** `quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.12.0` - -_New Features:_ - -- Live NGINX configuration update without reloading using the flag `--enable-dynamic-configuration` (disabled by default). -- New flag `--publish-status-address` to manually set the Ingress status IP address. -- Add worker-cpu-affinity NGINX option. -- Enable remote logging using syslog. -- Do not redirect `/.well-known/acme-challenge` to HTTPS. - -_Changes:_ - -- [x] [#2125](https://github.com/kubernetes/ingress-nginx/pull/2125) Add GCB config to build defaultbackend -- [x] [#2127](https://github.com/kubernetes/ingress-nginx/pull/2127) Revert deletion of dependency version override -- [x] [#2137](https://github.com/kubernetes/ingress-nginx/pull/2137) Updated log level to v2 for sysctlFSFileMax. -- [x] [#2140](https://github.com/kubernetes/ingress-nginx/pull/2140) Cors header should always be returned -- [x] [#2141](https://github.com/kubernetes/ingress-nginx/pull/2141) Fix error loading modules -- [x] [#2143](https://github.com/kubernetes/ingress-nginx/pull/2143) Only add HSTS headers in HTTPS -- [x] [#2144](https://github.com/kubernetes/ingress-nginx/pull/2144) Add annotation to disable logs in a location -- [x] [#2145](https://github.com/kubernetes/ingress-nginx/pull/2145) Add option in the configuration configmap to enable remote logging -- [x] [#2146](https://github.com/kubernetes/ingress-nginx/pull/2146) In case of TLS errors do not allow traffic -- [x] [#2148](https://github.com/kubernetes/ingress-nginx/pull/2148) Add publish-status-address flag -- [x] [#2155](https://github.com/kubernetes/ingress-nginx/pull/2155) Update nginx with new modules -- [x] [#2162](https://github.com/kubernetes/ingress-nginx/pull/2162) Remove duplicated BuildConfigFromFlags func -- [x] [#2163](https://github.com/kubernetes/ingress-nginx/pull/2163) include lua-upstream-nginx-module in Nginx build -- [x] [#2164](https://github.com/kubernetes/ingress-nginx/pull/2164) use the correct error channel -- [x] [#2167](https://github.com/kubernetes/ingress-nginx/pull/2167) configuring load balancing per ingress -- [x] [#2172](https://github.com/kubernetes/ingress-nginx/pull/2172) include lua-resty-lock in nginx image -- [x] [#2174](https://github.com/kubernetes/ingress-nginx/pull/2174) Live Nginx configuration update without reloading -- [x] [#2180](https://github.com/kubernetes/ingress-nginx/pull/2180) Include tests in golint checks, fix warnings -- [x] [#2181](https://github.com/kubernetes/ingress-nginx/pull/2181) change nginx process pgid -- [x] [#2185](https://github.com/kubernetes/ingress-nginx/pull/2185) Remove ProxyPassParams setting -- [x] [#2191](https://github.com/kubernetes/ingress-nginx/pull/2191) Add checker test for bad pid -- [x] [#2193](https://github.com/kubernetes/ingress-nginx/pull/2193) fix wrong json tag -- [x] [#2201](https://github.com/kubernetes/ingress-nginx/pull/2201) Add worker-cpu-affinity nginx option -- [x] [#2202](https://github.com/kubernetes/ingress-nginx/pull/2202) Allow config to disable geoip -- [x] [#2205](https://github.com/kubernetes/ingress-nginx/pull/2205) add luacheck to lint lua files - -_Documentation:_ - -- [x] [#2124](https://github.com/kubernetes/ingress-nginx/pull/2124) Document how to provide list types in configmap -- [x] [#2133](https://github.com/kubernetes/ingress-nginx/pull/2133) fix limit-req-status-code doc -- [x] [#2139](https://github.com/kubernetes/ingress-nginx/pull/2139) Update documentation for nginx-ingress-role RBAC. -- [x] [#2165](https://github.com/kubernetes/ingress-nginx/pull/2165) Typo fix "api server " -> "API server" -- [x] [#2169](https://github.com/kubernetes/ingress-nginx/pull/2169) Add documentation about secure-verify-ca-secret -- [x] [#2200](https://github.com/kubernetes/ingress-nginx/pull/2200) fix grammer mistake - -### 0.11.0 - -**Image:** `quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.11.0` - -_New Features:_ - -- NGINX 1.13.9 - -_Changes:_ - -- [x] [#1992](https://github.com/kubernetes/ingress-nginx/pull/1992) Added configmap option to disable IPv6 in nginx DNS resolver -- [x] [#1993](https://github.com/kubernetes/ingress-nginx/pull/1993) Enable Customization of Auth Request Redirect -- [x] [#1996](https://github.com/kubernetes/ingress-nginx/pull/1996) Use v3/dev/performance of ModSecurity because of performance -- [x] [#1997](https://github.com/kubernetes/ingress-nginx/pull/1997) fix var checked -- [x] [#1998](https://github.com/kubernetes/ingress-nginx/pull/1998) Add support to enable/disable proxy buffering -- [x] [#1999](https://github.com/kubernetes/ingress-nginx/pull/1999) Add connection-proxy-header annotation -- [x] [#2001](https://github.com/kubernetes/ingress-nginx/pull/2001) Add limit-request-status-code option -- [x] [#2005](https://github.com/kubernetes/ingress-nginx/pull/2005) fix typo error for server name \_ -- [x] [#2006](https://github.com/kubernetes/ingress-nginx/pull/2006) Add support for enabling ssl_ciphers per host -- [x] [#2019](https://github.com/kubernetes/ingress-nginx/pull/2019) Update nginx image -- [x] [#2021](https://github.com/kubernetes/ingress-nginx/pull/2021) Add nginx_cookie_flag_module -- [x] [#2026](https://github.com/kubernetes/ingress-nginx/pull/2026) update KUBERNETES from v1.8.0 to 1.9.0 -- [x] [#2027](https://github.com/kubernetes/ingress-nginx/pull/2027) Show pod information in http-svc example -- [x] [#2030](https://github.com/kubernetes/ingress-nginx/pull/2030) do not ignore $http_host and $http_x_forwarded_host -- [x] [#2031](https://github.com/kubernetes/ingress-nginx/pull/2031) The maximum number of open file descriptors should be maxOpenFiles. -- [x] [#2036](https://github.com/kubernetes/ingress-nginx/pull/2036) add matchLabels in Deployment yaml, that both API extensions/v1beta1 … -- [x] [#2050](https://github.com/kubernetes/ingress-nginx/pull/2050) Get file max from fs/file-max. -- [x] [#2063](https://github.com/kubernetes/ingress-nginx/pull/2063) Run one test at a time -- [x] [#2065](https://github.com/kubernetes/ingress-nginx/pull/2065) Always return an IP address -- [x] [#2069](https://github.com/kubernetes/ingress-nginx/pull/2069) Do not cancel the synchronization of secrets -- [x] [#2071](https://github.com/kubernetes/ingress-nginx/pull/2071) Update Go to 1.9.4 -- [x] [#2082](https://github.com/kubernetes/ingress-nginx/pull/2082) Use a ring channel to avoid blocking write of events -- [x] [#2089](https://github.com/kubernetes/ingress-nginx/pull/2089) Retry initial connection to the Kubernetes cluster -- [x] [#2093](https://github.com/kubernetes/ingress-nginx/pull/2093) Only pods in running phase are vallid for status -- [x] [#2099](https://github.com/kubernetes/ingress-nginx/pull/2099) Added GeoIP Organisational data -- [x] [#2107](https://github.com/kubernetes/ingress-nginx/pull/2107) Enabled the dynamic reload of GeoIP data -- [x] [#2119](https://github.com/kubernetes/ingress-nginx/pull/2119) Remove deprecated flag disable-node-list -- [x] [#2120](https://github.com/kubernetes/ingress-nginx/pull/2120) Migrate to codecov.io - -_Documentation:_ - -- [x] [#1987](https://github.com/kubernetes/ingress-nginx/pull/1987) add kube-system namespace for oauth2-proxy example -- [x] [#1991](https://github.com/kubernetes/ingress-nginx/pull/1991) Add comment about bolean and number values -- [x] [#2009](https://github.com/kubernetes/ingress-nginx/pull/2009) docs/user-guide/tls: remove duplicated section -- [x] [#2011](https://github.com/kubernetes/ingress-nginx/pull/2011) broken link for sticky-ingress.yaml -- [x] [#2014](https://github.com/kubernetes/ingress-nginx/pull/2014) Add document for connection-proxy-header annotation -- [x] [#2016](https://github.com/kubernetes/ingress-nginx/pull/2016) Minor link fix in deployment docs -- [x] [#2018](https://github.com/kubernetes/ingress-nginx/pull/2018) Added documentation for Permanent Redirect -- [x] [#2035](https://github.com/kubernetes/ingress-nginx/pull/2035) fix broken links in static-ip readme -- [x] [#2038](https://github.com/kubernetes/ingress-nginx/pull/2038) fix typo: appropiate -> [appropriate] -- [x] [#2039](https://github.com/kubernetes/ingress-nginx/pull/2039) fix typo stickyness to stickiness -- [x] [#2040](https://github.com/kubernetes/ingress-nginx/pull/2040) fix wrong annotation -- [x] [#2041](https://github.com/kubernetes/ingress-nginx/pull/2041) fix spell error reslover -> resolver -- [x] [#2046](https://github.com/kubernetes/ingress-nginx/pull/2046) Fix typos -- [x] [#2054](https://github.com/kubernetes/ingress-nginx/pull/2054) Adding documentation for helm with RBAC enabled -- [x] [#2075](https://github.com/kubernetes/ingress-nginx/pull/2075) Fix opentracing configuration when multiple options are configured -- [x] [#2076](https://github.com/kubernetes/ingress-nginx/pull/2076) Fix spelling errors -- [x] [#2077](https://github.com/kubernetes/ingress-nginx/pull/2077) Remove initContainer from default deployment - -### 0.10.2 - -**Image:** `quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.10.2` - -_Changes:_ - -- [x] [#1978](https://github.com/kubernetes/ingress-nginx/pull/1978) Fix chain completion and default certificate flag issues - -### 0.10.1 - -**Image:** `quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.10.1` - -_Changes:_ - -- [x] [#1945](https://github.com/kubernetes/ingress-nginx/pull/1945) When a secret is updated read ingress annotations (again) -- [x] [#1948](https://github.com/kubernetes/ingress-nginx/pull/1948) Update go to 1.9.3 -- [x] [#1953](https://github.com/kubernetes/ingress-nginx/pull/1953) Added annotation for upstream-vhost -- [x] [#1960](https://github.com/kubernetes/ingress-nginx/pull/1960) Adjust sysctl values to improve nginx performance -- [x] [#1963](https://github.com/kubernetes/ingress-nginx/pull/1963) Fix tests -- [x] [#1969](https://github.com/kubernetes/ingress-nginx/pull/1969) Rollback #1854 -- [x] [#1970](https://github.com/kubernetes/ingress-nginx/pull/1970) By default brotli is disabled - -### 0.10.0 - -**Image:** `quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.10.0` - -_Breaking changes:_ - -Changed the names of default Nginx ingress prometheus metrics. -If you are scraping default Nginx ingress metrics with prometheus the metrics changes are as follows: - -``` -nginx_active_connections_total -> nginx_connections_total{state="active"} -nginx_accepted_connections_total -> nginx_connections_total{state="accepted"} -nginx_handled_connections_total -> nginx_connections_total{state="handled"} -nginx_current_reading_connections_total -> nginx_connections{state="reading"} -nginx_current_writing_connections_total -> nginx_connections{state="writing"} -current_waiting_connections_total -> nginx_connections{state="waiting"} -``` - -_New Features:_ - -- NGINX 1.13.8 -- Support to hide headers from upstream servers -- Support for Jaeger -- CORS max age annotation - -_Changes:_ - -- [x] [#1782](https://github.com/kubernetes/ingress-nginx/pull/1782) auth-tls-pass-certificate-to-upstream should be bool -- [x] [#1787](https://github.com/kubernetes/ingress-nginx/pull/1787) force external_auth requests to http/1.1 -- [x] [#1800](https://github.com/kubernetes/ingress-nginx/pull/1800) Add control of the configuration refresh interval -- [x] [#1805](https://github.com/kubernetes/ingress-nginx/pull/1805) Add X-Forwarded-Prefix on rewrites -- [x] [#1844](https://github.com/kubernetes/ingress-nginx/pull/1844) Validate x-forwarded-proto and connection scheme before redirect to https -- [x] [#1852](https://github.com/kubernetes/ingress-nginx/pull/1852) Update nginx to v1.13.8 and update modules -- [x] [#1854](https://github.com/kubernetes/ingress-nginx/pull/1854) Fix redirect to ssl -- [x] [#1858](https://github.com/kubernetes/ingress-nginx/pull/1858) When upstream-hash-by annotation is used do not configure a lb algorithm -- [x] [#1861](https://github.com/kubernetes/ingress-nginx/pull/1861) Improve speed of tests execution -- [x] [#1869](https://github.com/kubernetes/ingress-nginx/pull/1869) "proxy_redirect default" should be placed after the "proxy_pass" -- [x] [#1870](https://github.com/kubernetes/ingress-nginx/pull/1870) Fix SSL Passthrough template issue and custom ports in redirect to HTTPS -- [x] [#1871](https://github.com/kubernetes/ingress-nginx/pull/1871) Update nginx image to 0.31 -- [x] [#1872](https://github.com/kubernetes/ingress-nginx/pull/1872) Fix data race updating ingress status -- [x] [#1880](https://github.com/kubernetes/ingress-nginx/pull/1880) Update go dependencies and cleanup deprecated packages -- [x] [#1888](https://github.com/kubernetes/ingress-nginx/pull/1888) Add CORS max age annotation -- [x] [#1891](https://github.com/kubernetes/ingress-nginx/pull/1891) Refactor initial synchronization of ingress objects -- [x] [#1903](https://github.com/kubernetes/ingress-nginx/pull/1903) If server_tokens is disabled remove the Server header -- [x] [#1906](https://github.com/kubernetes/ingress-nginx/pull/1906) Random string function should only contains letters -- [x] [#1907](https://github.com/kubernetes/ingress-nginx/pull/1907) Fix custom port in redirects -- [x] [#1909](https://github.com/kubernetes/ingress-nginx/pull/1909) Release nginx 0.32 -- [x] [#1910](https://github.com/kubernetes/ingress-nginx/pull/1910) updating prometheus metrics names according to naming best practices -- [x] [#1912](https://github.com/kubernetes/ingress-nginx/pull/1912) removing \_total prefix from nginx guage metrics -- [x] [#1914](https://github.com/kubernetes/ingress-nginx/pull/1914) Add --with-http_secure_link_module for the Nginx build configuration -- [x] [#1916](https://github.com/kubernetes/ingress-nginx/pull/1916) Add support for jaeger backend -- [x] [#1918](https://github.com/kubernetes/ingress-nginx/pull/1918) Update nginx image to 0.32 -- [x] [#1919](https://github.com/kubernetes/ingress-nginx/pull/1919) Add option for reuseport in nginx listen section -- [x] [#1926](https://github.com/kubernetes/ingress-nginx/pull/1926) Do not use port from host header -- [x] [#1927](https://github.com/kubernetes/ingress-nginx/pull/1927) Remove sendfile configuration -- [x] [#1928](https://github.com/kubernetes/ingress-nginx/pull/1928) Add support to hide headers from upstream servers -- [x] [#1929](https://github.com/kubernetes/ingress-nginx/pull/1929) Refactoring of kubernetes informers and local caches -- [x] [#1933](https://github.com/kubernetes/ingress-nginx/pull/1933) Remove deploy of ingress controller from the example - -_Documentation:_ - -- [x] [#1786](https://github.com/kubernetes/ingress-nginx/pull/1786) fix: some typo. -- [x] [#1792](https://github.com/kubernetes/ingress-nginx/pull/1792) Add note about annotation values -- [x] [#1814](https://github.com/kubernetes/ingress-nginx/pull/1814) Fix link to custom configuration -- [x] [#1826](https://github.com/kubernetes/ingress-nginx/pull/1826) Add note about websocket and load balancers -- [x] [#1840](https://github.com/kubernetes/ingress-nginx/pull/1840) Add note about default log files -- [x] [#1853](https://github.com/kubernetes/ingress-nginx/pull/1853) Clarify docs for add-headers and proxy-set-headers -- [x] [#1864](https://github.com/kubernetes/ingress-nginx/pull/1864) configmap.md: Convert hyphens in name column to non-breaking-hyphens -- [x] [#1865](https://github.com/kubernetes/ingress-nginx/pull/1865) Add docs for legacy TLS version and ciphers -- [x] [#1867](https://github.com/kubernetes/ingress-nginx/pull/1867) Fix publish-service patch and update README -- [x] [#1913](https://github.com/kubernetes/ingress-nginx/pull/1913) Missing r -- [x] [#1925](https://github.com/kubernetes/ingress-nginx/pull/1925) Fix doc links - -### 0.9.0 - -**Image:** `quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.9.0` - -_Changes:_ - -- [x] [#1731](https://github.com/kubernetes/ingress-nginx/pull/1731) Allow configuration of proxy_responses value for tcp/udp configmaps -- [x] [#1766](https://github.com/kubernetes/ingress-nginx/pull/1766) Fix ingress typo -- [x] [#1768](https://github.com/kubernetes/ingress-nginx/pull/1768) Custom default backend must use annotations if present -- [x] [#1769](https://github.com/kubernetes/ingress-nginx/pull/1769) Use custom https port in redirects -- [x] [#1771](https://github.com/kubernetes/ingress-nginx/pull/1771) Add additional check for old SSL certificates -- [x] [#1776](https://github.com/kubernetes/ingress-nginx/pull/1776) Add option to configure the redirect code - -### 0.9-beta.19 - -**Image:** `quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.9.0-beta.19` - -_Changes:_ - -- Fix regression with ingress.class annotation introduced in 0.9-beta.18 - -### 0.9-beta.18 - -**Image:** `quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.9.0-beta.18` - -_Breaking changes:_ - -- The NGINX ingress annotations contains a new prefix: **nginx.ingress.kubernetes.io**. This change is behind a flag to avoid breaking running deployments. - To avoid breaking a running NGINX ingress controller add the flag **--annotations-prefix=ingress.kubernetes.io** to the nginx ingress controller deployment. - There is one exception, the annotation `kubernetes.io/ingress.class` remains unchanged (this annotation is used in multiple ingress controllers) - -_New Features:_ - -- NGINX 1.13.7 -- Support for s390x -- e2e tests - -_Changes:_ - -- [x] [#1648](https://github.com/kubernetes/ingress-nginx/pull/1648) Remove GenericController and add tests -- [x] [#1650](https://github.com/kubernetes/ingress-nginx/pull/1650) Fix misspell errors -- [x] [#1651](https://github.com/kubernetes/ingress-nginx/pull/1651) Remove node lister -- [x] [#1652](https://github.com/kubernetes/ingress-nginx/pull/1652) Remove node lister -- [x] [#1653](https://github.com/kubernetes/ingress-nginx/pull/1653) Fix diff execution -- [x] [#1654](https://github.com/kubernetes/ingress-nginx/pull/1654) Fix travis script and update kubernetes to 1.8.0 -- [x] [#1658](https://github.com/kubernetes/ingress-nginx/pull/1658) Tests -- [x] [#1659](https://github.com/kubernetes/ingress-nginx/pull/1659) Add nginx helper tests -- [x] [#1662](https://github.com/kubernetes/ingress-nginx/pull/1662) Refactor annotations -- [x] [#1665](https://github.com/kubernetes/ingress-nginx/pull/1665) Add the original http request method to the auth request -- [x] [#1687](https://github.com/kubernetes/ingress-nginx/pull/1687) Fix use merge of annotations -- [x] [#1689](https://github.com/kubernetes/ingress-nginx/pull/1689) Enable s390x -- [x] [#1693](https://github.com/kubernetes/ingress-nginx/pull/1693) Fix docker build -- [x] [#1695](https://github.com/kubernetes/ingress-nginx/pull/1695) Update nginx to v0.29 -- [x] [#1696](https://github.com/kubernetes/ingress-nginx/pull/1696) Always add cors headers when enabled -- [x] [#1697](https://github.com/kubernetes/ingress-nginx/pull/1697) Disable features not availables in some platforms -- [x] [#1698](https://github.com/kubernetes/ingress-nginx/pull/1698) Auth e2e tests -- [x] [#1699](https://github.com/kubernetes/ingress-nginx/pull/1699) Refactor SSL intermediate CA certificate check -- [x] [#1700](https://github.com/kubernetes/ingress-nginx/pull/1700) Add patch command to append publish-service flag -- [x] [#1701](https://github.com/kubernetes/ingress-nginx/pull/1701) fix: Core() is deprecated use CoreV1() instead. -- [x] [#1702](https://github.com/kubernetes/ingress-nginx/pull/1702) Fix TLS example [ci skip] -- [x] [#1704](https://github.com/kubernetes/ingress-nginx/pull/1704) Add e2e tests to verify the correct source IP address -- [x] [#1705](https://github.com/kubernetes/ingress-nginx/pull/1705) Add annotation for setting proxy_redirect -- [x] [#1706](https://github.com/kubernetes/ingress-nginx/pull/1706) Increase ELB idle timeouts [ci skip] -- [x] [#1710](https://github.com/kubernetes/ingress-nginx/pull/1710) Do not update a secret not referenced by ingress rules -- [x] [#1713](https://github.com/kubernetes/ingress-nginx/pull/1713) add --report-node-internal-ip-address describe to cli-arguments.md -- [x] [#1717](https://github.com/kubernetes/ingress-nginx/pull/1717) Fix command used to detect version -- [x] [#1720](https://github.com/kubernetes/ingress-nginx/pull/1720) Add docker-registry example [ci skip] -- [x] [#1722](https://github.com/kubernetes/ingress-nginx/pull/1722) Add annotation to enable passing the certificate to the upstream server -- [x] [#1723](https://github.com/kubernetes/ingress-nginx/pull/1723) Add timeouts to http server and additional pprof routes -- [x] [#1724](https://github.com/kubernetes/ingress-nginx/pull/1724) Cleanup main -- [x] [#1725](https://github.com/kubernetes/ingress-nginx/pull/1725) Enable all e2e tests -- [x] [#1726](https://github.com/kubernetes/ingress-nginx/pull/1726) fix: replace deprecated methods. -- [x] [#1734](https://github.com/kubernetes/ingress-nginx/pull/1734) Changes ssl-client-cert header -- [x] [#1737](https://github.com/kubernetes/ingress-nginx/pull/1737) Update nginx v1.13.7 -- [x] [#1738](https://github.com/kubernetes/ingress-nginx/pull/1738) Cleanup -- [x] [#1739](https://github.com/kubernetes/ingress-nginx/pull/1739) Improve e2e checks -- [x] [#1740](https://github.com/kubernetes/ingress-nginx/pull/1740) Update nginx -- [x] [#1745](https://github.com/kubernetes/ingress-nginx/pull/1745) Simplify annotations -- [x] [#1746](https://github.com/kubernetes/ingress-nginx/pull/1746) Cleanup of e2e helpers - -_Documentation:_ - -- [x] [#1657](https://github.com/kubernetes/ingress-nginx/pull/1657) Add better documentation for deploying for dev -- [x] [#1680](https://github.com/kubernetes/ingress-nginx/pull/1680) Add doc for log-format-escape-json [ci skip] -- [x] [#1685](https://github.com/kubernetes/ingress-nginx/pull/1685) Fix default SSL certificate flag docs [ci skip] -- [x] [#1686](https://github.com/kubernetes/ingress-nginx/pull/1686) Fix development doc [ci skip] -- [x] [#1727](https://github.com/kubernetes/ingress-nginx/pull/1727) fix: fix typos in docs. -- [x] [#1747](https://github.com/kubernetes/ingress-nginx/pull/1747) Add config-map usage and options to Documentation - -### 0.9-beta.17 - -**Image:** `quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.9.0-beta.17` - -_Changes:_ - -- Fix regression with annotations introduced in 0.9-beta.16 (thanks @tomlanyon) - -### 0.9-beta.16 - -**Image:** `quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.9.0-beta.16` - -_New Features:_ - -- Images are published to [quay.io](https://quay.io/repository/kubernetes-ingress-controller) -- NGINX 1.13.6 -- OpenTracing Jaeger support inNGINX -- [ModSecurity support](https://github.com/SpiderLabs/ModSecurity-nginx) -- Support for [brotli compression in NGINX](https://certsimple.com/blog/nginx-brotli) -- Return 503 error instead of 404 when no endpoint is available - -_Breaking changes:_ - -- The default SSL configuration was updated to use `TLSv1.2` and the default cipher list is `ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-CHACHA20-POLY1305:ECDHE-RSA-CHACHA20-POLY1305:ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES256-SHA384:ECDHE-RSA-AES256-SHA384:ECDHE-ECDSA-AES128-SHA256:ECDHE-RSA-AES128-SHA256` - -_Known issues:_ - -- When ModSecurity is enabled a segfault could occur - [ModSecurity#1590](https://github.com/SpiderLabs/ModSecurity/issues/1590) - -_Changes:_ - -- [x] [#1489](https://github.com/kubernetes/ingress-nginx/pull/1489) Compute a real `X-Forwarded-For` header -- [x] [#1490](https://github.com/kubernetes/ingress-nginx/pull/1490) Introduce an upstream-hash-by annotation to support consistent hashing by nginx variable or text -- [x] [#1498](https://github.com/kubernetes/ingress-nginx/pull/1498) Add modsecurity module -- [x] [#1500](https://github.com/kubernetes/ingress-nginx/pull/1500) Enable modsecurity feature -- [x] [#1501](https://github.com/kubernetes/ingress-nginx/pull/1501) Request ingress controller version in issue template -- [x] [#1502](https://github.com/kubernetes/ingress-nginx/pull/1502) Force reload on template change -- [x] [#1503](https://github.com/kubernetes/ingress-nginx/pull/1503) Add falg to report node internal IP address in ingress status -- [x] [#1505](https://github.com/kubernetes/ingress-nginx/pull/1505) Increase size of variable hash bucket -- [x] [#1506](https://github.com/kubernetes/ingress-nginx/pull/1506) Update nginx ssl configuration -- [x] [#1507](https://github.com/kubernetes/ingress-nginx/pull/1507) Add tls session ticket key setting -- [x] [#1511](https://github.com/kubernetes/ingress-nginx/pull/1511) fix deprecated ssl_client_cert. add ssl_client_verify header -- [x] [#1513](https://github.com/kubernetes/ingress-nginx/pull/1513) Return 503 by default when no endpoint is available -- [x] [#1520](https://github.com/kubernetes/ingress-nginx/pull/1520) Change alias behaviour not to create new server section needlessly -- [x] [#1523](https://github.com/kubernetes/ingress-nginx/pull/1523) Include the serversnippet from the config map in server blocks -- [x] [#1533](https://github.com/kubernetes/ingress-nginx/pull/1533) Remove authentication send body annotation -- [x] [#1535](https://github.com/kubernetes/ingress-nginx/pull/1535) Remove auth-send-body [ci skip] -- [x] [#1538](https://github.com/kubernetes/ingress-nginx/pull/1538) Rename service-nodeport.yml to service-nodeport.yaml -- [x] [#1543](https://github.com/kubernetes/ingress-nginx/pull/1543) Fix glog initialization error -- [x] [#1544](https://github.com/kubernetes/ingress-nginx/pull/1544) Fix `make container` for OSX. -- [x] [#1547](https://github.com/kubernetes/ingress-nginx/pull/1547) fix broken GCE-GKE service descriptor -- [x] [#1550](https://github.com/kubernetes/ingress-nginx/pull/1550) Add e2e tests - default backend -- [x] [#1553](https://github.com/kubernetes/ingress-nginx/pull/1553) Cors features improvements -- [x] [#1554](https://github.com/kubernetes/ingress-nginx/pull/1554) Add missing unit test for nextPowerOf2 function -- [x] [#1556](https://github.com/kubernetes/ingress-nginx/pull/1556) fixed https port forwarding in Azure LB service -- [x] [#1566](https://github.com/kubernetes/ingress-nginx/pull/1566) Release nginx-slim 0.27 -- [x] [#1568](https://github.com/kubernetes/ingress-nginx/pull/1568) update defaultbackend tag -- [x] [#1569](https://github.com/kubernetes/ingress-nginx/pull/1569) Update 404 server image -- [x] [#1570](https://github.com/kubernetes/ingress-nginx/pull/1570) Update nginx version -- [x] [#1571](https://github.com/kubernetes/ingress-nginx/pull/1571) Fix cors tests -- [x] [#1572](https://github.com/kubernetes/ingress-nginx/pull/1572) Certificate Auth Bugfix -- [x] [#1577](https://github.com/kubernetes/ingress-nginx/pull/1577) Do not use relative urls for yaml files -- [x] [#1580](https://github.com/kubernetes/ingress-nginx/pull/1580) Upgrade to use the latest version of nginx-opentracing. -- [x] [#1581](https://github.com/kubernetes/ingress-nginx/pull/1581) Fix Makefile to work in OSX. -- [x] [#1582](https://github.com/kubernetes/ingress-nginx/pull/1582) Add scripts to release from travis-ci -- [x] [#1584](https://github.com/kubernetes/ingress-nginx/pull/1584) Add missing probes in deployments -- [x] [#1585](https://github.com/kubernetes/ingress-nginx/pull/1585) Add version flag -- [x] [#1587](https://github.com/kubernetes/ingress-nginx/pull/1587) Use pass access scheme in signin url -- [x] [#1589](https://github.com/kubernetes/ingress-nginx/pull/1589) Fix upstream vhost Equal comparison -- [x] [#1590](https://github.com/kubernetes/ingress-nginx/pull/1590) Fix Equals Comparison for CORS annotation -- [x] [#1592](https://github.com/kubernetes/ingress-nginx/pull/1592) Update opentracing module and release image to quay.io -- [x] [#1593](https://github.com/kubernetes/ingress-nginx/pull/1593) Fix makefile default task -- [x] [#1605](https://github.com/kubernetes/ingress-nginx/pull/1605) Fix ExternalName services -- [x] [#1607](https://github.com/kubernetes/ingress-nginx/pull/1607) Add support for named ports with service-upstream. #1459 -- [x] [#1608](https://github.com/kubernetes/ingress-nginx/pull/1608) Fix issue with clusterIP detection on service upstream. #1534 -- [x] [#1610](https://github.com/kubernetes/ingress-nginx/pull/1610) Only set alias if not already set -- [x] [#1618](https://github.com/kubernetes/ingress-nginx/pull/1618) Fix full XFF with PROXY -- [x] [#1620](https://github.com/kubernetes/ingress-nginx/pull/1620) Add gzip_vary -- [x] [#1621](https://github.com/kubernetes/ingress-nginx/pull/1621) Fix path to ELB listener image -- [x] [#1627](https://github.com/kubernetes/ingress-nginx/pull/1627) Add brotli support -- [x] [#1629](https://github.com/kubernetes/ingress-nginx/pull/1629) Add ssl-client-dn header -- [x] [#1632](https://github.com/kubernetes/ingress-nginx/pull/1632) Rename OWNERS assignees: to approvers: -- [x] [#1635](https://github.com/kubernetes/ingress-nginx/pull/1635) Install dumb-init using apt-get -- [x] [#1636](https://github.com/kubernetes/ingress-nginx/pull/1636) Update go to 1.9.2 -- [x] [#1640](https://github.com/kubernetes/ingress-nginx/pull/1640) Update nginx to 0.28 and enable brotli - -_Documentation:_ - -- [x] [#1491](https://github.com/kubernetes/ingress-nginx/pull/1491) Note that GCE has moved to a new repo -- [x] [#1492](https://github.com/kubernetes/ingress-nginx/pull/1492) Cleanup readme.md -- [x] [#1494](https://github.com/kubernetes/ingress-nginx/pull/1494) Cleanup -- [x] [#1497](https://github.com/kubernetes/ingress-nginx/pull/1497) Cleanup examples directory -- [x] [#1504](https://github.com/kubernetes/ingress-nginx/pull/1504) Clean readme -- [x] [#1508](https://github.com/kubernetes/ingress-nginx/pull/1508) Fixed link in prometheus example -- [x] [#1527](https://github.com/kubernetes/ingress-nginx/pull/1527) Split documentation -- [x] [#1536](https://github.com/kubernetes/ingress-nginx/pull/1536) Update documentation and examples [ci skip] -- [x] [#1541](https://github.com/kubernetes/ingress-nginx/pull/1541) fix(documentation): Fix some typos -- [x] [#1548](https://github.com/kubernetes/ingress-nginx/pull/1548) link to prometheus docs -- [x] [#1562](https://github.com/kubernetes/ingress-nginx/pull/1562) Fix development guide link -- [x] [#1563](https://github.com/kubernetes/ingress-nginx/pull/1563) Add task to verify markdown links -- [x] [#1583](https://github.com/kubernetes/ingress-nginx/pull/1583) Add note for certificate authentication in Cloudflare -- [x] [#1617](https://github.com/kubernetes/ingress-nginx/pull/1617) fix typo in user-guide/annotations.md - -### 0.9-beta.15 - -**Image:** `gcr.io/google_containers/nginx-ingress-controller:0.9.0-beta.15` - -_New Features:_ - -- Add OCSP support -- Configurable ssl_verify_client - -_Changes:_ - -- [x] [#1468](https://github.com/kubernetes/ingress/pull/1468) Add the original URL to the auth request -- [x] [#1469](https://github.com/kubernetes/ingress/pull/1469) Typo: Add missing {{ }} -- [x] [#1472](https://github.com/kubernetes/ingress/pull/1472) Fix X-Auth-Request-Redirect value to reflect the request uri -- [x] [#1473](https://github.com/kubernetes/ingress/pull/1473) Fix proxy protocol check -- [x] [#1475](https://github.com/kubernetes/ingress/pull/1475) Add OCSP support -- [x] [#1477](https://github.com/kubernetes/ingress/pull/1477) Fix semicolons in global configuration -- [x] [#1478](https://github.com/kubernetes/ingress/pull/1478) Pass redirect field in login page to get a proper redirect -- [x] [#1480](https://github.com/kubernetes/ingress/pull/1480) configurable ssl_verify_client -- [x] [#1485](https://github.com/kubernetes/ingress/pull/1485) Fix source IP address -- [x] [#1486](https://github.com/kubernetes/ingress/pull/1486) Fix overwrite of custom configuration - -_Documentation:_ - -- [x] [#1460](https://github.com/kubernetes/ingress/pull/1460) Expose UDP port in UDP ingress example -- [x] [#1465](https://github.com/kubernetes/ingress/pull/1465) review prometheus docs - -### 0.9-beta.14 - -**Image:** `gcr.io/google_containers/nginx-ingress-controller:0.9.0-beta.14` - -_New Features:_ - -- Opentracing support for NGINX -- Setting upstream vhost for nginx -- Allow custom global configuration at multiple levels -- Add support for proxy protocol decoding and encoding in TCP services - -_Changes:_ - -- [x] [#719](https://github.com/kubernetes/ingress/pull/719) Setting upstream vhost for nginx. -- [x] [#1321](https://github.com/kubernetes/ingress/pull/1321) Enable keepalive in upstreams -- [x] [#1322](https://github.com/kubernetes/ingress/pull/1322) parse real ip -- [x] [#1323](https://github.com/kubernetes/ingress/pull/1323) use $the_real_ip for rate limit whitelist -- [x] [#1326](https://github.com/kubernetes/ingress/pull/1326) Pass headers from the custom error backend -- [x] [#1328](https://github.com/kubernetes/ingress/pull/1328) update deprecated interface -- [x] [#1329](https://github.com/kubernetes/ingress/pull/1329) add example for nginx-ingress -- [x] [#1330](https://github.com/kubernetes/ingress/pull/1330) Increase coverage in template.go for nginx controller -- [x] [#1335](https://github.com/kubernetes/ingress/pull/1335) Configurable proxy_request_buffering per location.. -- [x] [#1338](https://github.com/kubernetes/ingress/pull/1338) Fix multiple leader election -- [x] [#1339](https://github.com/kubernetes/ingress/pull/1339) Enable status port listening in all interfaces -- [x] [#1340](https://github.com/kubernetes/ingress/pull/1340) Update sha256sum of nginx substitutions -- [x] [#1341](https://github.com/kubernetes/ingress/pull/1341) Fix typos -- [x] [#1345](https://github.com/kubernetes/ingress/pull/1345) refactor controllers.go -- [x] [#1349](https://github.com/kubernetes/ingress/pull/1349) Force reload if a secret is updated -- [x] [#1363](https://github.com/kubernetes/ingress/pull/1363) Fix proxy request buffering default configuration -- [x] [#1365](https://github.com/kubernetes/ingress/pull/1365) Fix equals comparsion returing False if both objects have nil Targets or Services. -- [x] [#1367](https://github.com/kubernetes/ingress/pull/1367) Fix typos -- [x] [#1379](https://github.com/kubernetes/ingress/pull/1379) Fix catch all upstream server -- [x] [#1380](https://github.com/kubernetes/ingress/pull/1380) Cleanup -- [x] [#1381](https://github.com/kubernetes/ingress/pull/1381) Refactor X-Forwarded-\* headers -- [x] [#1382](https://github.com/kubernetes/ingress/pull/1382) Cleanup -- [x] [#1387](https://github.com/kubernetes/ingress/pull/1387) Improve resource usage in nginx controller -- [x] [#1392](https://github.com/kubernetes/ingress/pull/1392) Avoid issues with goroutines updating fields -- [x] [#1393](https://github.com/kubernetes/ingress/pull/1393) Limit the number of goroutines used for the update of ingress status -- [x] [#1394](https://github.com/kubernetes/ingress/pull/1394) Improve equals -- [x] [#1402](https://github.com/kubernetes/ingress/pull/1402) fix error when cert or key is nil -- [x] [#1403](https://github.com/kubernetes/ingress/pull/1403) Added tls ports to rbac nginx ingress controller and service -- [x] [#1404](https://github.com/kubernetes/ingress/pull/1404) Use nginx default value for SSLECDHCurve -- [x] [#1411](https://github.com/kubernetes/ingress/pull/1411) Add more descriptive logging in certificate loading -- [x] [#1412](https://github.com/kubernetes/ingress/pull/1412) Correct Error Handling to avoid panics and add more logging to template -- [x] [#1413](https://github.com/kubernetes/ingress/pull/1413) Validate external names -- [x] [#1418](https://github.com/kubernetes/ingress/pull/1418) Fix links after design proposals move -- [x] [#1419](https://github.com/kubernetes/ingress/pull/1419) Remove duplicated ingress check code -- [x] [#1420](https://github.com/kubernetes/ingress/pull/1420) Process queue items by time window -- [x] [#1423](https://github.com/kubernetes/ingress/pull/1423) Fix cast error -- [x] [#1424](https://github.com/kubernetes/ingress/pull/1424) Allow overriding the tag and registry -- [x] [#1426](https://github.com/kubernetes/ingress/pull/1426) Enhance Certificate Logging and Clearup Mutual Auth Docs -- [x] [#1430](https://github.com/kubernetes/ingress/pull/1430) Add support for proxy protocol decoding and encoding in TCP services -- [x] [#1434](https://github.com/kubernetes/ingress/pull/1434) Fix exec of readSecrets -- [x] [#1435](https://github.com/kubernetes/ingress/pull/1435) Add header to upstream server for external authentication -- [x] [#1438](https://github.com/kubernetes/ingress/pull/1438) Do not intercept errors from the custom error service -- [x] [#1439](https://github.com/kubernetes/ingress/pull/1439) Nginx master process killed thus no further reloads -- [x] [#1440](https://github.com/kubernetes/ingress/pull/1440) Kill worker processes to allow the restart of nginx -- [x] [#1445](https://github.com/kubernetes/ingress/pull/1445) Updated godeps -- [x] [#1450](https://github.com/kubernetes/ingress/pull/1450) Fix links -- [x] [#1451](https://github.com/kubernetes/ingress/pull/1451) Add example of server-snippet -- [x] [#1452](https://github.com/kubernetes/ingress/pull/1452) Fix sync of secrets (kube lego) -- [x] [#1454](https://github.com/kubernetes/ingress/pull/1454) Allow custom global configuration at multiple levels - -_Documentation:_ - -- [x] [#1400](https://github.com/kubernetes/ingress/pull/1400) Fix ConfigMap link in doc -- [x] [#1422](https://github.com/kubernetes/ingress/pull/1422) Add docs for opentracing -- [x] [#1441](https://github.com/kubernetes/ingress/pull/1441) Improve custom error pages doc -- [x] [#1442](https://github.com/kubernetes/ingress/pull/1442) Opentracing docs -- [x] [#1446](https://github.com/kubernetes/ingress/pull/1446) Add custom timeout annotations doc - -### 0.9-beta.13 - -**Image:** `gcr.io/google_containers/nginx-ingress-controller:0.9.0-beta.13` - -_New Features:_ - -- NGINX 1.3.5 -- New flag to disable node listing -- Custom X-Forwarder-Header (CloudFlare uses `CF-Connecting-IP` as header) -- Custom error page in Client Certificate Authentication - -_Changes:_ - -- [x] [#1272](https://github.com/kubernetes/ingress/pull/1272) Delete useless statement -- [x] [#1277](https://github.com/kubernetes/ingress/pull/1277) Add indent for nginx.conf -- [x] [#1278](https://github.com/kubernetes/ingress/pull/1278) Add proxy-pass-params annotation and Backend field -- [x] [#1282](https://github.com/kubernetes/ingress/pull/1282) Fix nginx stats -- [x] [#1288](https://github.com/kubernetes/ingress/pull/1288) Allow PATCH in enable-cors -- [x] [#1290](https://github.com/kubernetes/ingress/pull/1290) Add flag to disabling node listing -- [x] [#1293](https://github.com/kubernetes/ingress/pull/1293) Adds support for error page in Client Certificate Authentication -- [x] [#1308](https://github.com/kubernetes/ingress/pull/1308) A trivial typo in config -- [x] [#1310](https://github.com/kubernetes/ingress/pull/1310) Refactoring nginx configuration configmap -- [x] [#1311](https://github.com/kubernetes/ingress/pull/1311) Enable nginx async writes -- [x] [#1312](https://github.com/kubernetes/ingress/pull/1312) Allow custom forwarded for header -- [x] [#1313](https://github.com/kubernetes/ingress/pull/1313) Fix eol in nginx template -- [x] [#1315](https://github.com/kubernetes/ingress/pull/1315) Fix nginx custom error pages - -_Documentation:_ - -- [x] [#1270](https://github.com/kubernetes/ingress/pull/1270) add missing yamls in controllers/nginx -- [x] [#1276](https://github.com/kubernetes/ingress/pull/1276) Link rbac sample from deployment docs -- [x] [#1291](https://github.com/kubernetes/ingress/pull/1291) fix link to conformance suite -- [x] [#1295](https://github.com/kubernetes/ingress/pull/1295) fix README of nginx-ingress-controller -- [x] [#1299](https://github.com/kubernetes/ingress/pull/1299) fix two doc issues in nginx/README -- [x] [#1306](https://github.com/kubernetes/ingress/pull/1306) Fix kubeconfig example for nginx deployment - -### 0.9-beta.12 - -**Image:** `gcr.io/google_containers/nginx-ingress-controller:0.9.0-beta.12` - -_Breaking changes:_ - -- SSL passthrough is disabled by default. To enable the feature use `--enable-ssl-passthrough` - -_New Features:_ - -- Support for arm64 -- New flags to customize listen ports -- Per minute rate limiting -- Rate limit whitelist -- Configuration of nginx worker timeout (to avoid zombie nginx workers processes) -- Redirects from non-www to www -- Custom default backend (per Ingress) -- Graceful shutdown for NGINX - -_Changes:_ - -- [x] [#977](https://github.com/kubernetes/ingress/pull/977) Add sort-backends command line option -- [x] [#981](https://github.com/kubernetes/ingress/pull/981) Add annotation to allow use of service ClusterIP for NGINX upstream. -- [x] [#991](https://github.com/kubernetes/ingress/pull/991) Remove secret sync loop -- [x] [#992](https://github.com/kubernetes/ingress/pull/992) Check errors generating pem files -- [x] [#993](https://github.com/kubernetes/ingress/pull/993) Fix the sed command to work on macOS -- [x] [#1013](https://github.com/kubernetes/ingress/pull/1013) The fields of vtsDate are unified in the form of plural -- [x] [#1025](https://github.com/kubernetes/ingress/pull/1025) Fix file watch -- [x] [#1027](https://github.com/kubernetes/ingress/pull/1027) Lint code -- [x] [#1031](https://github.com/kubernetes/ingress/pull/1031) Change missing secret name log level to V(3) -- [x] [#1032](https://github.com/kubernetes/ingress/pull/1032) Alternative syncSecret approach #1030 -- [x] [#1042](https://github.com/kubernetes/ingress/pull/1042) Add function to allow custom values in Ingress status -- [x] [#1043](https://github.com/kubernetes/ingress/pull/1043) Return reference to object providing Endpoint -- [x] [#1046](https://github.com/kubernetes/ingress/pull/1046) Add field FileSHA in BasicDigest struct -- [x] [#1058](https://github.com/kubernetes/ingress/pull/1058) add per minute rate limiting -- [x] [#1060](https://github.com/kubernetes/ingress/pull/1060) Update fsnotify dependency to fix arm64 issue -- [x] [#1065](https://github.com/kubernetes/ingress/pull/1065) Add more descriptive steps in Dev Documentation -- [x] [#1073](https://github.com/kubernetes/ingress/pull/1073) Release nginx-slim 0.22 -- [x] [#1074](https://github.com/kubernetes/ingress/pull/1074) Remove lua and use fastcgi to render errors -- [x] [#1075](https://github.com/kubernetes/ingress/pull/1075) (feat/ #374) support proxy timeout -- [x] [#1076](https://github.com/kubernetes/ingress/pull/1076) Add more ssl test cases -- [x] [#1078](https://github.com/kubernetes/ingress/pull/1078) fix the same udp port and tcp port, update nginx.conf error -- [x] [#1080](https://github.com/kubernetes/ingress/pull/1080) Disable platform s390x -- [x] [#1081](https://github.com/kubernetes/ingress/pull/1081) Spit Static check and Coverage in diff Stages of Travis CI -- [x] [#1082](https://github.com/kubernetes/ingress/pull/1082) Fix build tasks -- [x] [#1087](https://github.com/kubernetes/ingress/pull/1087) Release nginx-slim 0.23 -- [x] [#1088](https://github.com/kubernetes/ingress/pull/1088) Configure nginx worker timeout -- [x] [#1089](https://github.com/kubernetes/ingress/pull/1089) Update nginx to 1.13.4 -- [x] [#1098](https://github.com/kubernetes/ingress/pull/1098) Exposing the event recorder to allow other controllers to create events -- [x] [#1102](https://github.com/kubernetes/ingress/pull/1102) Fix lose SSL Passthrough -- [x] [#1104](https://github.com/kubernetes/ingress/pull/1104) Simplify verification of hostname in ssl certificates -- [x] [#1109](https://github.com/kubernetes/ingress/pull/1109) Cleanup remote address in nginx template -- [x] [#1110](https://github.com/kubernetes/ingress/pull/1110) Fix Endpoint comparison -- [x] [#1118](https://github.com/kubernetes/ingress/pull/1118) feat(#733)Support nginx bandwidth control -- [x] [#1124](https://github.com/kubernetes/ingress/pull/1124) check fields len in dns.go -- [x] [#1130](https://github.com/kubernetes/ingress/pull/1130) Update nginx.go -- [x] [#1134](https://github.com/kubernetes/ingress/pull/1134) replace deprecated interface with versioned ones -- [x] [#1136](https://github.com/kubernetes/ingress/pull/1136) Fix status update - changed in #1074 -- [x] [#1138](https://github.com/kubernetes/ingress/pull/1138) update nginx.go: performance improve -- [x] [#1139](https://github.com/kubernetes/ingress/pull/1139) Fix Todo:convert sequence to table -- [x] [#1162](https://github.com/kubernetes/ingress/pull/1162) Optimize CI build time -- [x] [#1164](https://github.com/kubernetes/ingress/pull/1164) Use variable request_uri as redirect after auth -- [x] [#1179](https://github.com/kubernetes/ingress/pull/1179) Fix sticky upstream not used when enable rewrite -- [x] [#1184](https://github.com/kubernetes/ingress/pull/1184) Add support for temporal and permanent redirects -- [x] [#1185](https://github.com/kubernetes/ingress/pull/1185) Add more info about Server-Alias usage -- [x] [#1186](https://github.com/kubernetes/ingress/pull/1186) Add annotation for client-body-buffer-size per location -- [x] [#1190](https://github.com/kubernetes/ingress/pull/1190) Add flag to disable SSL passthrough -- [x] [#1193](https://github.com/kubernetes/ingress/pull/1193) fix broken link -- [x] [#1198](https://github.com/kubernetes/ingress/pull/1198) Add option for specific scheme for base url -- [x] [#1202](https://github.com/kubernetes/ingress/pull/1202) formatIP issue -- [x] [#1203](https://github.com/kubernetes/ingress/pull/1203) NGINX not reloading correctly -- [x] [#1204](https://github.com/kubernetes/ingress/pull/1204) Fix template error -- [x] [#1205](https://github.com/kubernetes/ingress/pull/1205) Add initial sync of secrets -- [x] [#1206](https://github.com/kubernetes/ingress/pull/1206) Update ssl-passthrough docs -- [x] [#1207](https://github.com/kubernetes/ingress/pull/1207) delete broken link -- [x] [#1208](https://github.com/kubernetes/ingress/pull/1208) fix some typo -- [x] [#1210](https://github.com/kubernetes/ingress/pull/1210) add rate limit whitelist -- [x] [#1215](https://github.com/kubernetes/ingress/pull/1215) Replace base64 encoding with random uuid -- [x] [#1218](https://github.com/kubernetes/ingress/pull/1218) Trivial fixes in core/pkg/net -- [x] [#1219](https://github.com/kubernetes/ingress/pull/1219) keep zones unique per ingress resource -- [x] [#1221](https://github.com/kubernetes/ingress/pull/1221) Move certificate authentication from location to server -- [x] [#1223](https://github.com/kubernetes/ingress/pull/1223) Add doc for non-www to www annotation -- [x] [#1224](https://github.com/kubernetes/ingress/pull/1224) refactor rate limit whitelist -- [x] [#1226](https://github.com/kubernetes/ingress/pull/1226) Remove useless variable in nginx.tmpl -- [x] [#1227](https://github.com/kubernetes/ingress/pull/1227) Update annotations doc with base-url-scheme -- [x] [#1233](https://github.com/kubernetes/ingress/pull/1233) Fix ClientBodyBufferSize annotation -- [x] [#1234](https://github.com/kubernetes/ingress/pull/1234) Lint code -- [x] [#1235](https://github.com/kubernetes/ingress/pull/1235) Fix Equal comparison -- [x] [#1236](https://github.com/kubernetes/ingress/pull/1236) Add Validation for Client Body Buffer Size -- [x] [#1238](https://github.com/kubernetes/ingress/pull/1238) Add support for 'client_body_timeout' and 'client_header_timeout' -- [x] [#1239](https://github.com/kubernetes/ingress/pull/1239) Add flags to customize listen ports and detect port collisions -- [x] [#1243](https://github.com/kubernetes/ingress/pull/1243) Add support for access-log-path and error-log-path -- [x] [#1244](https://github.com/kubernetes/ingress/pull/1244) Add custom default backend annotation -- [x] [#1246](https://github.com/kubernetes/ingress/pull/1246) Add additional headers when custom default backend is used -- [x] [#1247](https://github.com/kubernetes/ingress/pull/1247) Make Ingress annotations available in template -- [x] [#1248](https://github.com/kubernetes/ingress/pull/1248) Improve nginx controller performance -- [x] [#1254](https://github.com/kubernetes/ingress/pull/1254) fix Type transform panic -- [x] [#1257](https://github.com/kubernetes/ingress/pull/1257) Graceful shutdown for Nginx -- [x] [#1261](https://github.com/kubernetes/ingress/pull/1261) Add support for 'worker-shutdown-timeout' - -_Documentation:_ - -- [x] [#976](https://github.com/kubernetes/ingress/pull/976) Update annotations doc -- [x] [#979](https://github.com/kubernetes/ingress/pull/979) Missing auth example -- [x] [#980](https://github.com/kubernetes/ingress/pull/980) Add nginx basic auth example -- [x] [#1001](https://github.com/kubernetes/ingress/pull/1001) examples/nginx/rbac: Give access to own namespace -- [x] [#1005](https://github.com/kubernetes/ingress/pull/1005) Update configuration.md -- [x] [#1018](https://github.com/kubernetes/ingress/pull/1018) add docs for `proxy-set-headers` and `add-headers` -- [x] [#1038](https://github.com/kubernetes/ingress/pull/1038) typo / spelling in README.md -- [x] [#1039](https://github.com/kubernetes/ingress/pull/1039) typo in examples/tcp/nginx/README.md -- [x] [#1049](https://github.com/kubernetes/ingress/pull/1049) Fix config name in the example. -- [x] [#1054](https://github.com/kubernetes/ingress/pull/1054) Fix link to UDP example -- [x] [#1084](https://github.com/kubernetes/ingress/pull/1084) (issue #310)Fix some broken link -- [x] [#1103](https://github.com/kubernetes/ingress/pull/1103) Add GoDoc Widget -- [x] [#1105](https://github.com/kubernetes/ingress/pull/1105) Make Readme file more readable -- [x] [#1106](https://github.com/kubernetes/ingress/pull/1106) Update annotations.md -- [x] [#1107](https://github.com/kubernetes/ingress/pull/1107) Fix Broken Link -- [x] [#1119](https://github.com/kubernetes/ingress/pull/1119) fix typos in controllers/nginx/README.md -- [x] [#1122](https://github.com/kubernetes/ingress/pull/1122) Fix broken link -- [x] [#1131](https://github.com/kubernetes/ingress/pull/1131) Add short help doc in configuration for nginx limit rate -- [x] [#1143](https://github.com/kubernetes/ingress/pull/1143) Minor Typo Fix -- [x] [#1144](https://github.com/kubernetes/ingress/pull/1144) Minor Typo fix -- [x] [#1145](https://github.com/kubernetes/ingress/pull/1145) Minor Typo fix -- [x] [#1146](https://github.com/kubernetes/ingress/pull/1146) Fix Minor Typo in Readme -- [x] [#1147](https://github.com/kubernetes/ingress/pull/1147) Minor Typo Fix -- [x] [#1148](https://github.com/kubernetes/ingress/pull/1148) Minor Typo Fix in Getting-Started.md -- [x] [#1149](https://github.com/kubernetes/ingress/pull/1149) Fix Minor Typo in TLS authentication -- [x] [#1150](https://github.com/kubernetes/ingress/pull/1150) Fix Minor Typo in Customize the HAProxy configuration -- [x] [#1151](https://github.com/kubernetes/ingress/pull/1151) Fix Minor Typo in customization custom-template -- [x] [#1152](https://github.com/kubernetes/ingress/pull/1152) Fix minor typo in HAProxy Multi TLS certificate termination -- [x] [#1153](https://github.com/kubernetes/ingress/pull/1153) Fix minor typo in Multi TLS certificate termination -- [x] [#1154](https://github.com/kubernetes/ingress/pull/1154) Fix minor typo in Role Based Access Control -- [x] [#1155](https://github.com/kubernetes/ingress/pull/1155) Fix minor typo in TCP loadbalancing -- [x] [#1156](https://github.com/kubernetes/ingress/pull/1156) Fix minor typo in UDP loadbalancing -- [x] [#1157](https://github.com/kubernetes/ingress/pull/1157) Fix minor typos in Prerequisites -- [x] [#1158](https://github.com/kubernetes/ingress/pull/1158) Fix minor typo in Ingress examples -- [x] [#1159](https://github.com/kubernetes/ingress/pull/1159) Fix minor typos in Ingress admin guide -- [x] [#1160](https://github.com/kubernetes/ingress/pull/1160) Fix a broken href and typo in Ingress FAQ -- [x] [#1165](https://github.com/kubernetes/ingress/pull/1165) Update CONTRIBUTING.md -- [x] [#1168](https://github.com/kubernetes/ingress/pull/1168) finx link to running-locally.md -- [x] [#1170](https://github.com/kubernetes/ingress/pull/1170) Update dead link in nginx/HTTPS section -- [x] [#1172](https://github.com/kubernetes/ingress/pull/1172) Update README.md -- [x] [#1173](https://github.com/kubernetes/ingress/pull/1173) Update admin.md -- [x] [#1174](https://github.com/kubernetes/ingress/pull/1174) fix several titles -- [x] [#1177](https://github.com/kubernetes/ingress/pull/1177) fix typos -- [x] [#1188](https://github.com/kubernetes/ingress/pull/1188) Fix minor typo -- [x] [#1189](https://github.com/kubernetes/ingress/pull/1189) Fix sign in URL redirect parameter -- [x] [#1192](https://github.com/kubernetes/ingress/pull/1192) Update README.md -- [x] [#1195](https://github.com/kubernetes/ingress/pull/1195) Update troubleshooting.md -- [x] [#1196](https://github.com/kubernetes/ingress/pull/1196) Update README.md -- [x] [#1209](https://github.com/kubernetes/ingress/pull/1209) Update README.md -- [x] [#1085](https://github.com/kubernetes/ingress/pull/1085) Fix ConfigMap's namespace in custom configuration example for nginx -- [x] [#1142](https://github.com/kubernetes/ingress/pull/1142) Fix typo in multiple docs -- [x] [#1228](https://github.com/kubernetes/ingress/pull/1228) Update release doc in getting-started.md -- [x] [#1230](https://github.com/kubernetes/ingress/pull/1230) Update godep guide link - -### 0.9-beta.11 - -**Image:** `gcr.io/google_containers/nginx-ingress-controller:0.9.0-beta.11` - -Fixes NGINX [CVE-2017-7529](http://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2017-7529) - -_Changes:_ - -- [x] [#659](https://github.com/kubernetes/ingress/pull/659) [nginx] TCP configmap should allow listen proxy_protocol per service -- [x] [#730](https://github.com/kubernetes/ingress/pull/730) Add support for add_headers -- [x] [#808](https://github.com/kubernetes/ingress/pull/808) HTTP->HTTPS redirect does not work with use-proxy-protocol: "true" -- [x] [#921](https://github.com/kubernetes/ingress/pull/921) Make proxy-real-ip-cidr a comma separated list -- [x] [#930](https://github.com/kubernetes/ingress/pull/930) Add support for proxy protocol in TCP services -- [x] [#933](https://github.com/kubernetes/ingress/pull/933) Lint code -- [x] [#937](https://github.com/kubernetes/ingress/pull/937) Fix lint code errors -- [x] [#940](https://github.com/kubernetes/ingress/pull/940) Sets parameters for a shared memory zone of limit_conn_zone -- [x] [#949](https://github.com/kubernetes/ingress/pull/949) fix nginx version to 1.13.3 to fix integer overflow -- [x] [#956](https://github.com/kubernetes/ingress/pull/956) Simplify handling of ssl certificates -- [x] [#958](https://github.com/kubernetes/ingress/pull/958) Release ubuntu-slim:0.13 -- [x] [#959](https://github.com/kubernetes/ingress/pull/959) Release nginx-slim 0.21 -- [x] [#960](https://github.com/kubernetes/ingress/pull/960) Update nginx in ingress controller -- [x] [#964](https://github.com/kubernetes/ingress/pull/964) Support for proxy_headers_hash_bucket_size and proxy_headers_hash_max_size -- [x] [#966](https://github.com/kubernetes/ingress/pull/966) Fix error checking for pod name & NS -- [x] [#967](https://github.com/kubernetes/ingress/pull/967) Fix runningAddresses typo -- [x] [#968](https://github.com/kubernetes/ingress/pull/968) Fix missing hyphen in yaml for nginx RBAC example -- [x] [#973](https://github.com/kubernetes/ingress/pull/973) check number of servers in configuration comparator - -### 0.9-beta.10 - -**Image:** `gcr.io/google_containers/nginx-ingress-controller:0.9.0-beta.10` - -Fix release 0.9-beta.9 - -### 0.9-beta.9 - -**Image:** `gcr.io/google_containers/nginx-ingress-controller:0.9.0-beta.9` - -_New Features:_ - -- Add support for arm and ppc64le - -_Changes:_ - -- [x] [#548](https://github.com/kubernetes/ingress/pull/548) nginx: support multidomain certificates -- [x] [#620](https://github.com/kubernetes/ingress/pull/620) [nginx] Listening ports are not configurable, so ingress can't be run multiple times per node when using CNI -- [x] [#648](https://github.com/kubernetes/ingress/pull/648) publish-service argument isn't honored when ELB is internal only facing. -- [x] [#833](https://github.com/kubernetes/ingress/pull/833) WIP: Avoid reloads implementing Equals in structs -- [x] [#838](https://github.com/kubernetes/ingress/pull/838) Feature request: Add ingress annotation to enable upstream "keepalive" option -- [x] [#844](https://github.com/kubernetes/ingress/pull/844) ingress annotations affinity is not working -- [x] [#862](https://github.com/kubernetes/ingress/pull/862) Avoid reloads implementing Equaler interface -- [x] [#864](https://github.com/kubernetes/ingress/pull/864) Remove dead code -- [x] [#868](https://github.com/kubernetes/ingress/pull/868) Lint nginx code -- [x] [#871](https://github.com/kubernetes/ingress/pull/871) Add feature to allow sticky sessions per location -- [x] [#873](https://github.com/kubernetes/ingress/pull/873) Update README.md -- [x] [#876](https://github.com/kubernetes/ingress/pull/876) Add information about nginx controller flags -- [x] [#878](https://github.com/kubernetes/ingress/pull/878) Update go to 1.8.3 -- [x] [#881](https://github.com/kubernetes/ingress/pull/881) Option to not remove loadBalancer status record? -- [x] [#882](https://github.com/kubernetes/ingress/pull/882) Add flag to skip the update of Ingress status on shutdown -- [x] [#885](https://github.com/kubernetes/ingress/pull/885) Don't use $proxy_protocol var which may be undefined. -- [x] [#886](https://github.com/kubernetes/ingress/pull/886) Add support for SubjectAltName in SSL certificates -- [x] [#888](https://github.com/kubernetes/ingress/pull/888) Update nginx-slim to 0.19 -- [x] [#889](https://github.com/kubernetes/ingress/pull/889) Add PHOST to backend -- [x] [#890](https://github.com/kubernetes/ingress/pull/890) Improve variable configuration for source IP address -- [x] [#892](https://github.com/kubernetes/ingress/pull/892) Add upstream keepalive connections cache -- [x] [#897](https://github.com/kubernetes/ingress/pull/897) Update outdated ingress resource link -- [x] [#898](https://github.com/kubernetes/ingress/pull/898) add error check right when reload nginx fail -- [x] [#899](https://github.com/kubernetes/ingress/pull/899) Fix nginx error check -- [x] [#900](https://github.com/kubernetes/ingress/pull/900) After #862 changes in the configmap do not trigger a reload -- [x] [#901](https://github.com/kubernetes/ingress/pull/901) [doc] Update NGinX status port to 18080 -- [x] [#902](https://github.com/kubernetes/ingress/pull/902) Always reload after a change in the configuration -- [x] [#904](https://github.com/kubernetes/ingress/pull/904) Fix nginx sticky sessions -- [x] [#906](https://github.com/kubernetes/ingress/pull/906) Fix race condition with closed channels -- [x] [#907](https://github.com/kubernetes/ingress/pull/907) nginx/proxy: allow specifying next upstream behaviour -- [x] [#910](https://github.com/kubernetes/ingress/pull/910) Feature request: use `X-Forwarded-Host` from the reverse proxy before -- [x] [#911](https://github.com/kubernetes/ingress/pull/911) Improve X-Forwarded-Host support -- [x] [#915](https://github.com/kubernetes/ingress/pull/915) Release nginx-slim 0.20 -- [x] [#916](https://github.com/kubernetes/ingress/pull/916) Add arm and ppc64le support -- [x] [#919](https://github.com/kubernetes/ingress/pull/919) Apply the 'ssl-redirect' annotation per-location -- [x] [#922](https://github.com/kubernetes/ingress/pull/922) Add example of TLS termination using a classic ELB - -### 0.9-beta.8 - -**Image:** `gcr.io/google_containers/nginx-ingress-controller:0.9.0-beta.8` - -_Changes:_ - -- [x] [#761](https://github.com/kubernetes/ingress/pull/761) NGINX TCP Ingresses do not bind on IPv6 -- [x] [#850](https://github.com/kubernetes/ingress/pull/850) Fix IPv6 UDP stream section -- [x] [#851](https://github.com/kubernetes/ingress/pull/851) ensure private key and certificate match -- [x] [#852](https://github.com/kubernetes/ingress/pull/852) Don't expose certificate metrics for default server -- [x] [#846](https://github.com/kubernetes/ingress/pull/846) Match ServicePort to Endpoints by Name -- [x] [#854](https://github.com/kubernetes/ingress/pull/854) Document log-format-stream and log-format-upstream -- [x] [#847](https://github.com/kubernetes/ingress/pull/847) fix semicolon -- [x] [#848](https://github.com/kubernetes/ingress/pull/848) Add metric "ssl certificate expiration" -- [x] [#839](https://github.com/kubernetes/ingress/pull/839) "No endpoints" issue -- [x] [#845](https://github.com/kubernetes/ingress/pull/845) Fix no endpoints issue when named ports are used -- [x] [#822](https://github.com/kubernetes/ingress/pull/822) Release ubuntu-slim 0.11 -- [x] [#824](https://github.com/kubernetes/ingress/pull/824) Update nginx-slim to 0.18 -- [x] [#823](https://github.com/kubernetes/ingress/pull/823) Release nginx-slim 0.18 -- [x] [#827](https://github.com/kubernetes/ingress/pull/827) Introduce working example of nginx controller with rbac -- [x] [#835](https://github.com/kubernetes/ingress/pull/835) Make log format json escaping configurable -- [x] [#843](https://github.com/kubernetes/ingress/pull/843) Avoid setting maximum number of open file descriptors lower than 1024 -- [x] [#837](https://github.com/kubernetes/ingress/pull/837) Cleanup interface -- [x] [#836](https://github.com/kubernetes/ingress/pull/836) Make log format json escaping configurable -- [x] [#828](https://github.com/kubernetes/ingress/pull/828) Wrap IPv6 endpoints in [] -- [x] [#821](https://github.com/kubernetes/ingress/pull/821) nginx-ingress: occasional 503 Service Temporarily Unavailable -- [x] [#829](https://github.com/kubernetes/ingress/pull/829) feat(template): wrap IPv6 addresses in [] -- [x] [#786](https://github.com/kubernetes/ingress/pull/786) Update echoserver image version in examples -- [x] [#825](https://github.com/kubernetes/ingress/pull/825) Create or delete ingress based on class annotation -- [x] [#790](https://github.com/kubernetes/ingress/pull/790) #789 removing duplicate X-Real-IP header -- [x] [#792](https://github.com/kubernetes/ingress/pull/792) Avoid checking if the controllers are synced -- [x] [#798](https://github.com/kubernetes/ingress/pull/798) nginx: RBAC for leader election -- [x] [#799](https://github.com/kubernetes/ingress/pull/799) could not build variables_hash -- [x] [#809](https://github.com/kubernetes/ingress/pull/809) Fix dynamic variable name -- [x] [#804](https://github.com/kubernetes/ingress/pull/804) Fix #798 - RBAC for leader election -- [x] [#806](https://github.com/kubernetes/ingress/pull/806) fix ingress rbac roles -- [x] [#811](https://github.com/kubernetes/ingress/pull/811) external auth - proxy_pass_request_body off + big bodies give 500/413 -- [x] [#785](https://github.com/kubernetes/ingress/pull/785) Publish echoheader image -- [x] [#813](https://github.com/kubernetes/ingress/pull/813) Added client_max_body_size to authPath location -- [x] [#814](https://github.com/kubernetes/ingress/pull/814) rbac-nginx: resourceNames cannot filter create verb -- [x] [#774](https://github.com/kubernetes/ingress/pull/774) Add IPv6 support in TCP and UDP stream section -- [x] [#784](https://github.com/kubernetes/ingress/pull/784) Allow customization of variables hash tables -- [x] [#782](https://github.com/kubernetes/ingress/pull/782) Set "proxy_pass_header Server;" -- [x] [#783](https://github.com/kubernetes/ingress/pull/783) nginx/README.md: clarify app-root and fix example hyperlink -- [x] [#787](https://github.com/kubernetes/ingress/pull/787) Add setting to allow returning the Server header from the backend - -### 0.9-beta.7 - -**Image:** `gcr.io/google_containers/nginx-ingress-controller:0.9.0-beta.7` - -_Changes:_ - -- [x] [#777](https://github.com/kubernetes/ingress/pull/777) Update sniff parser to fix index out of bound error - -### 0.9-beta.6 - -**Image:** `gcr.io/google_containers/nginx-ingress-controller:0.9.0-beta.6` - -_Changes:_ - -- [x] [#647](https://github.com/kubernetes/ingress/pull/647) ingress.class enhancement for debugging. -- [x] [#708](https://github.com/kubernetes/ingress/pull/708) ingress losing real source IP when tls enabled -- [x] [#760](https://github.com/kubernetes/ingress/pull/760) Change recorder event scheme -- [x] [#704](https://github.com/kubernetes/ingress/pull/704) fix nginx reload flags '-c' -- [x] [#757](https://github.com/kubernetes/ingress/pull/757) Replace use of endpoints as locks with configmap -- [x] [#752](https://github.com/kubernetes/ingress/pull/752) nginx ingress header config backwards -- [x] [#756](https://github.com/kubernetes/ingress/pull/756) Fix bad variable assignment in template nginx -- [x] [#729](https://github.com/kubernetes/ingress/pull/729) Release nginx-slim 0.17 -- [x] [#755](https://github.com/kubernetes/ingress/pull/755) Fix server name hash maxSize default value -- [x] [#741](https://github.com/kubernetes/ingress/pull/741) Update golang dependencies -- [x] [#749](https://github.com/kubernetes/ingress/pull/749) Remove service annotation for namedPorts -- [x] [#740](https://github.com/kubernetes/ingress/pull/740) Refactoring whitelist source IP verification -- [x] [#734](https://github.com/kubernetes/ingress/pull/734) Specify nginx image arch -- [x] [#728](https://github.com/kubernetes/ingress/pull/728) Update nginx image -- [x] [#723](https://github.com/kubernetes/ingress/pull/723) update readme about vts metrics -- [x] [#726](https://github.com/kubernetes/ingress/pull/726) Release ubuntu-slim 0.10 -- [x] [#727](https://github.com/kubernetes/ingress/pull/727) [nginx] whitelist-source-range doesn’t work on ssl port -- [x] [#709](https://github.com/kubernetes/ingress/pull/709) Add config for X-Forwarded-For trust -- [x] [#679](https://github.com/kubernetes/ingress/pull/679) add getenv -- [x] [#680](https://github.com/kubernetes/ingress/pull/680) nginx/pkg/config: delete unuseful variable -- [x] [#716](https://github.com/kubernetes/ingress/pull/716) Add secure-verify-ca-secret annotation -- [x] [#722](https://github.com/kubernetes/ingress/pull/722) Remove go-reap and use tini as process reaper -- [x] [#725](https://github.com/kubernetes/ingress/pull/725) Add keepalive_requests and client_body_buffer_size options -- [x] [#724](https://github.com/kubernetes/ingress/pull/724) change the directory of default-backend.yaml -- [x] [#656](https://github.com/kubernetes/ingress/pull/656) Nginx Ingress Controller - Specify load balancing method -- [x] [#717](https://github.com/kubernetes/ingress/pull/717) delete unuseful variable -- [x] [#712](https://github.com/kubernetes/ingress/pull/712) Set $proxy_upstream_name before location directive -- [x] [#715](https://github.com/kubernetes/ingress/pull/715) Corrected annotation ex `signin-url` to `auth-url` -- [x] [#718](https://github.com/kubernetes/ingress/pull/718) nodeController sync -- [x] [#694](https://github.com/kubernetes/ingress/pull/694) SSL-Passthrough broken in beta.5 -- [x] [#678](https://github.com/kubernetes/ingress/pull/678) Convert CN SSL Certificate to lowercase before comparison -- [x] [#690](https://github.com/kubernetes/ingress/pull/690) Fix IP in logs for https traffic -- [x] [#673](https://github.com/kubernetes/ingress/pull/673) Override load balancer alg view config map -- [x] [#675](https://github.com/kubernetes/ingress/pull/675) Use proxy-protocol to pass through source IP to nginx -- [x] [#707](https://github.com/kubernetes/ingress/pull/707) use nginx vts module version 0.1.14 -- [x] [#702](https://github.com/kubernetes/ingress/pull/702) Document passing of ssl_client_cert to backend -- [x] [#688](https://github.com/kubernetes/ingress/pull/688) Add example of UDP loadbalancing -- [x] [#696](https://github.com/kubernetes/ingress/pull/696) [nginx] pass non-SNI TLS hello to default backend, Fixes #693 -- [x] [#685](https://github.com/kubernetes/ingress/pull/685) Fix error in generated nginx.conf for optional hsts-preload - -### 0.9-beta.5 - -**Image:** `gcr.io/google_containers/nginx-ingress-controller:0.9.0-beta.5` - -_Changes:_ - -- [x] [#663](https://github.com/kubernetes/ingress/pull/663) Remove helper required in go < 1.8 -- [x] [#662](https://github.com/kubernetes/ingress/pull/662) Add debug information about ingress class -- [x] [#661](https://github.com/kubernetes/ingress/pull/661) Avoid running nginx if the configuration file is empty -- [x] [#660](https://github.com/kubernetes/ingress/pull/660) Rollback queue refactoring -- [x] [#654](https://github.com/kubernetes/ingress/pull/654) Update go version to 1.8 - -### 0.9-beta.4 - -**Image:** `gcr.io/google_containers/nginx-ingress-controller:0.9.0-beta.4` - -_New Features:_ - -- Add support for services of type ExternalName - -_Changes:_ - -- [x] [#635](https://github.com/kubernetes/ingress/pull/635) Allow configuration of features underscores_in_headers and ignore_invalid_headers -- [x] [#633](https://github.com/kubernetes/ingress/pull/633) Fix lint errors -- [x] [#630](https://github.com/kubernetes/ingress/pull/630) Add example of TCP loadbalancing -- [x] [#629](https://github.com/kubernetes/ingress/pull/629) Add support for services of type ExternalName -- [x] [#624](https://github.com/kubernetes/ingress/pull/624) Compute server_names_hash_bucket_size correctly -- [x] [#615](https://github.com/kubernetes/ingress/pull/615) Process exited cleanly before we hit wait4 -- [x] [#614](https://github.com/kubernetes/ingress/pull/614) Refactor nginx ssl passthrough -- [x] [#613](https://github.com/kubernetes/ingress/pull/613) Status leader election must consired the ingress class -- [x] [#607](https://github.com/kubernetes/ingress/pull/607) Allow custom server_names_hash_max_size & server_names_hash_bucket_size -- [x] [#601](https://github.com/kubernetes/ingress/pull/601) add a judgment -- [x] [#601](https://github.com/kubernetes/ingress/pull/600) Replace custom child reap code with go-reap -- [x] [#597](https://github.com/kubernetes/ingress/pull/599) Add flag to force namespace isolation -- [x] [#595](https://github.com/kubernetes/ingress/pull/595) Remove Host header from auth_request proxy configuration -- [x] [#588](https://github.com/kubernetes/ingress/pull/588) Read resolv.conf file just once -- [x] [#586](https://github.com/kubernetes/ingress/pull/586) Updated instructions to create an ingress controller build -- [x] [#583](https://github.com/kubernetes/ingress/pull/583) fixed lua_package_path in nginx.tmpl -- [x] [#580](https://github.com/kubernetes/ingress/pull/580) Updated faq for running multiple ingress controller -- [x] [#579](https://github.com/kubernetes/ingress/pull/579) Detect if the ingress controller is running with multiple replicas -- [x] [#578](https://github.com/kubernetes/ingress/pull/578) Set different listeners per protocol version -- [x] [#577](https://github.com/kubernetes/ingress/pull/577) Avoid zombie child processes -- [x] [#576](https://github.com/kubernetes/ingress/pull/576) Replace secret workqueue -- [x] [#568](https://github.com/kubernetes/ingress/pull/568) Revert merge annotations to the implicit root context -- [x] [#563](https://github.com/kubernetes/ingress/pull/563) Add option to disable hsts preload -- [x] [#560](https://github.com/kubernetes/ingress/pull/560) Fix intermittent misconfiguration of backend.secure and SessionAffinity -- [x] [#556](https://github.com/kubernetes/ingress/pull/556) Update nginx version and remove dumb-init -- [x] [#551](https://github.com/kubernetes/ingress/pull/551) Build namespace and ingress class as label -- [x] [#546](https://github.com/kubernetes/ingress/pull/546) Fix a couple of 'does not contains' typos -- [x] [#542](https://github.com/kubernetes/ingress/pull/542) Fix lint errors -- [x] [#540](https://github.com/kubernetes/ingress/pull/540) Add Backends.SSLPassthrough attribute -- [x] [#539](https://github.com/kubernetes/ingress/pull/539) Migrate to client-go -- [x] [#536](https://github.com/kubernetes/ingress/pull/536) add unit test cases for core/pkg/ingress/controller/backend_ssl -- [x] [#535](https://github.com/kubernetes/ingress/pull/535) Add test for ingress status update -- [x] [#532](https://github.com/kubernetes/ingress/pull/532) Add setting to configure ecdh curve -- [x] [#531](https://github.com/kubernetes/ingress/pull/531) Fix link to examples -- [x] [#530](https://github.com/kubernetes/ingress/pull/530) Fix link to custom nginx configuration -- [x] [#528](https://github.com/kubernetes/ingress/pull/528) Add reference to apiserver-host flag -- [x] [#527](https://github.com/kubernetes/ingress/pull/527) Add annotations to location of default backend (root context) -- [x] [#525](https://github.com/kubernetes/ingress/pull/525) Avoid negative values configuring the max number of open files -- [x] [#523](https://github.com/kubernetes/ingress/pull/523) Fix a typo in an error message -- [x] [#521](https://github.com/kubernetes/ingress/pull/521) nginx-ingress-controller is built twice by docker-build target -- [x] [#517](https://github.com/kubernetes/ingress/pull/517) Use whitelist-source-range from configmap when no annotation on ingress -- [x] [#516](https://github.com/kubernetes/ingress/pull/516) Convert WorkerProcesses setting to string to allow the value auto -- [x] [#512](https://github.com/kubernetes/ingress/pull/512) Fix typos regarding the ssl-passthrough annotation documentation -- [x] [#505](https://github.com/kubernetes/ingress/pull/505) add unit test cases for core/pkg/ingress/controller/annotations -- [x] [#503](https://github.com/kubernetes/ingress/pull/503) Add example for nginx in aws -- [x] [#502](https://github.com/kubernetes/ingress/pull/502) Add information about SSL Passthrough annotation -- [x] [#500](https://github.com/kubernetes/ingress/pull/500) Improve TLS secret configuration -- [x] [#498](https://github.com/kubernetes/ingress/pull/498) Proper enqueue a secret on the secret queue -- [x] [#493](https://github.com/kubernetes/ingress/pull/493) Update nginx and vts module -- [x] [#490](https://github.com/kubernetes/ingress/pull/490) Add unit test case for named_port -- [x] [#488](https://github.com/kubernetes/ingress/pull/488) Adds support for CORS on error responses and Authorization header -- [x] [#485](https://github.com/kubernetes/ingress/pull/485) Fix typo nginx configMap vts metrics customization -- [x] [#481](https://github.com/kubernetes/ingress/pull/481) Remove unnecessary quote in nginx log format -- [x] [#471](https://github.com/kubernetes/ingress/pull/471) prometheus scrape annotations -- [x] [#460](https://github.com/kubernetes/ingress/pull/460) add example of 'run multiple haproxy ingress controllers as a deployment' -- [x] [#459](https://github.com/kubernetes/ingress/pull/459) Add information about SSL certificates in the default log level -- [x] [#456](https://github.com/kubernetes/ingress/pull/456) Avoid upstreams with multiple servers with the same port -- [x] [#454](https://github.com/kubernetes/ingress/pull/454) Pass request port to real server -- [x] [#450](https://github.com/kubernetes/ingress/pull/450) fix nginx-tcp-and-udp on same port -- [x] [#446](https://github.com/kubernetes/ingress/pull/446) remove configmap validations -- [x] [#445](https://github.com/kubernetes/ingress/pull/445) Remove snakeoil certificate generation -- [x] [#442](https://github.com/kubernetes/ingress/pull/442) Fix a few bugs in the nginx-ingress-controller Makefile -- [x] [#441](https://github.com/kubernetes/ingress/pull/441) skip validation when configmap is empty -- [x] [#439](https://github.com/kubernetes/ingress/pull/439) Avoid a nil-reference when the temporary file cannot be created -- [x] [#438](https://github.com/kubernetes/ingress/pull/438) Improve English in error messages -- [x] [#437](https://github.com/kubernetes/ingress/pull/437) Reference constant - -### 0.9-beta.3 - -**Image:** `gcr.io/google_containers/nginx-ingress-controller:0.9.0-beta.3` - -_New Features:_ - -- Custom log formats using `log-format-upstream` directive in the configuration configmap. -- Force redirect to SSL using the annotation `ingress.kubernetes.io/force-ssl-redirect` -- Prometheus metric for VTS status module (transparent, just enable vts stats) -- Improved external authentication adding `ingress.kubernetes.io/auth-signin` annotation. Please check this [example](https://github.com/kubernetes/ingress/tree/main/examples/external-auth/nginx) - -_Breaking changes:_ - -- `ssl-dh-param` configuration in configmap is now the name of a secret that contains the Diffie-Hellman key - -_Changes:_ - -- [x] [#433](https://github.com/kubernetes/ingress/pull/433) close over the ingress variable or the last assignment will be used -- [x] [#424](https://github.com/kubernetes/ingress/pull/424) Manually sync secrets from certificate authentication annotations -- [x] [#423](https://github.com/kubernetes/ingress/pull/423) Scrap json metrics from nginx vts module when enabled -- [x] [#418](https://github.com/kubernetes/ingress/pull/418) Only update Ingress status for the configured class -- [x] [#415](https://github.com/kubernetes/ingress/pull/415) Improve external authentication docs -- [x] [#410](https://github.com/kubernetes/ingress/pull/410) Add support for "signin url" -- [x] [#409](https://github.com/kubernetes/ingress/pull/409) Allow custom http2 header sizes -- [x] [#408](https://github.com/kubernetes/ingress/pull/408) Review docs -- [x] [#406](https://github.com/kubernetes/ingress/pull/406) Add debug info and fix spelling -- [x] [#402](https://github.com/kubernetes/ingress/pull/402) allow specifying custom dh param -- [x] [#397](https://github.com/kubernetes/ingress/pull/397) Fix external auth -- [x] [#394](https://github.com/kubernetes/ingress/pull/394) Update README.md -- [x] [#392](https://github.com/kubernetes/ingress/pull/392) Fix http2 header size -- [x] [#391](https://github.com/kubernetes/ingress/pull/391) remove tmp nginx-diff files -- [x] [#390](https://github.com/kubernetes/ingress/pull/390) Fix RateLimit comment -- [x] [#385](https://github.com/kubernetes/ingress/pull/385) add Copyright -- [x] [#382](https://github.com/kubernetes/ingress/pull/382) Ingress Fake Certificate generation -- [x] [#380](https://github.com/kubernetes/ingress/pull/380) Fix custom log format -- [x] [#373](https://github.com/kubernetes/ingress/pull/373) Cleanup -- [x] [#371](https://github.com/kubernetes/ingress/pull/371) add configuration to disable listening on ipv6 -- [x] [#370](https://github.com/kubernetes/ingress/pull/270) Add documentation for ingress.kubernetes.io/force-ssl-redirect -- [x] [#369](https://github.com/kubernetes/ingress/pull/369) Minor text fix for "ApiServer" -- [x] [#367](https://github.com/kubernetes/ingress/pull/367) BuildLogFormatUpstream was always using the default log-format -- [x] [#366](https://github.com/kubernetes/ingress/pull/366) add_judgment -- [x] [#365](https://github.com/kubernetes/ingress/pull/365) add ForceSSLRedirect ingress annotation -- [x] [#364](https://github.com/kubernetes/ingress/pull/364) Fix error caused by increasing proxy_buffer_size (#363) -- [x] [#362](https://github.com/kubernetes/ingress/pull/362) Fix ingress class -- [x] [#360](https://github.com/kubernetes/ingress/pull/360) add example of 'run multiple nginx ingress controllers as a deployment' -- [x] [#358](https://github.com/kubernetes/ingress/pull/358) Checks if the TLS secret contains a valid keypair structure -- [x] [#356](https://github.com/kubernetes/ingress/pull/356) Disable listen only on ipv6 and fix proxy_protocol -- [x] [#354](https://github.com/kubernetes/ingress/pull/354) add judgment -- [x] [#352](https://github.com/kubernetes/ingress/pull/352) Add ability to customize upstream and stream log format -- [x] [#351](https://github.com/kubernetes/ingress/pull/351) Enable custom election id for status sync. -- [x] [#347](https://github.com/kubernetes/ingress/pull/347) Fix client source IP address -- [x] [#345](https://github.com/kubernetes/ingress/pull/345) Fix lint error -- [x] [#344](https://github.com/kubernetes/ingress/pull/344) Refactoring of TCP and UDP services -- [x] [#343](https://github.com/kubernetes/ingress/pull/343) Fix node lister when --watch-namespace is used -- [x] [#341](https://github.com/kubernetes/ingress/pull/341) Do not run coverage check in the default target. -- [x] [#340](https://github.com/kubernetes/ingress/pull/340) Add support for specify proxy cookie path/domain -- [x] [#337](https://github.com/kubernetes/ingress/pull/337) Fix for formatting error introduced in #304 -- [x] [#335](https://github.com/kubernetes/ingress/pull/335) Fix for vet complaints: -- [x] [#332](https://github.com/kubernetes/ingress/pull/332) Add annotation to customize nginx configuration -- [x] [#331](https://github.com/kubernetes/ingress/pull/331) Correct spelling mistake -- [x] [#328](https://github.com/kubernetes/ingress/pull/328) fix misspell "affinity" in main.go -- [x] [#326](https://github.com/kubernetes/ingress/pull/326) add nginx daemonset example -- [x] [#311](https://github.com/kubernetes/ingress/pull/311) Sort stream service ports to avoid extra reloads -- [x] [#307](https://github.com/kubernetes/ingress/pull/307) Add docs for body-size annotation -- [x] [#306](https://github.com/kubernetes/ingress/pull/306) modify nginx readme -- [x] [#304](https://github.com/kubernetes/ingress/pull/304) change 'buildSSPassthrouthUpstreams' to 'buildSSLPassthroughUpstreams' - -### 0.9-beta.2 - -**Image:** `gcr.io/google_containers/nginx-ingress-controller:0.9.0-beta.2` - -_New Features:_ - -- New configuration flag `proxy-set-headers` to allow set custom headers before send traffic to backends. [Example here](https://github.com/kubernetes/ingress/tree/main/examples/customization/custom-headers/nginx) -- Disable directive access_log globally using `disable-access-log: "true"` in the configuration ConfigMap. -- Sticky session per Ingress rule using the annotation `ingress.kubernetes.io/affinity`. [Example here](https://github.com/kubernetes/ingress/tree/main/examples/affinity/cookie/nginx) - -_Changes:_ - -- [x] [#300](https://github.com/kubernetes/ingress/pull/300) Change nginx variable to use in filter of access_log -- [x] [#296](https://github.com/kubernetes/ingress/pull/296) Fix rewrite regex to match the start of the URL and not a substring -- [x] [#293](https://github.com/kubernetes/ingress/pull/293) Update makefile gcloud docker command -- [x] [#290](https://github.com/kubernetes/ingress/pull/290) Update nginx version in ingress controller to 1.11.10 -- [x] [#286](https://github.com/kubernetes/ingress/pull/286) Add logs to help debugging and simplify default upstream configuration -- [x] [#285](https://github.com/kubernetes/ingress/pull/285) Added a Node StoreLister type -- [x] [#281](https://github.com/kubernetes/ingress/pull/281) Add chmod up directory tree for world read/execute on directories -- [x] [#279](https://github.com/kubernetes/ingress/pull/279) fix wrong link in the file of examples/README.md -- [x] [#275](https://github.com/kubernetes/ingress/pull/275) Pass headers to custom error backend -- [x] [#272](https://github.com/kubernetes/ingress/pull/272) Fix error getting class information from Ingress annotations -- [x] [#268](https://github.com/kubernetes/ingress/pull/268) minor: Fix typo in nginx README -- [x] [#265](https://github.com/kubernetes/ingress/pull/265) Fix rewrite annotation parser -- [x] [#262](https://github.com/kubernetes/ingress/pull/262) Add nginx README and configuration docs back -- [x] [#261](https://github.com/kubernetes/ingress/pull/261) types.go: fix typo in godoc -- [x] [#258](https://github.com/kubernetes/ingress/pull/258) Nginx sticky annotations -- [x] [#255](https://github.com/kubernetes/ingress/pull/255) Adds support for disabling access_log globally -- [x] [#247](https://github.com/kubernetes/ingress/pull/247) Fix wrong URL in nginx ingress configuration -- [x] [#246](https://github.com/kubernetes/ingress/pull/246) Add support for custom proxy headers using a ConfigMap -- [x] [#244](https://github.com/kubernetes/ingress/pull/244) Add information about cors annotation -- [x] [#241](https://github.com/kubernetes/ingress/pull/241) correct a spell mistake -- [x] [#232](https://github.com/kubernetes/ingress/pull/232) Change searchs with searches -- [x] [#231](https://github.com/kubernetes/ingress/pull/231) Add information about proxy_protocol in port 442 -- [x] [#228](https://github.com/kubernetes/ingress/pull/228) Fix worker check issue -- [x] [#227](https://github.com/kubernetes/ingress/pull/227) proxy_protocol on ssl_passthrough listener -- [x] [#223](https://github.com/kubernetes/ingress/pull/223) Fix panic if a tempfile cannot be created -- [x] [#220](https://github.com/kubernetes/ingress/pull/220) Fixes for minikube usage instructions. -- [x] [#219](https://github.com/kubernetes/ingress/pull/219) Fix typo, add a couple of links. -- [x] [#218](https://github.com/kubernetes/ingress/pull/218) Improve links from CONTRIBUTING. -- [x] [#217](https://github.com/kubernetes/ingress/pull/217) Fix an e2e link. -- [x] [#212](https://github.com/kubernetes/ingress/pull/212) Simplify code to obtain TCP or UDP services -- [x] [#208](https://github.com/kubernetes/ingress/pull/208) Fix nil HTTP field -- [x] [#198](https://github.com/kubernetes/ingress/pull/198) Add an example for static-ip and deployment - -### 0.9-beta.1 - -**Image:** `gcr.io/google_containers/nginx-ingress-controller:0.9.0-beta.1` - -_New Features:_ - -- SSL Passthrough -- New Flag `--publish-service` that set the Service fronting the ingress controllers -- Ingress status shows the correct IP/hostname address without duplicates -- Custom body sizes per Ingress -- Prometheus metrics - -_Breaking changes:_ - -- Flag `--nginx-configmap` was replaced with `--configmap` -- Configmap field `body-size` was replaced with `proxy-body-size` - -_Changes:_ - -- [x] [#184](https://github.com/kubernetes/ingress/pull/184) Fix template error -- [x] [#179](https://github.com/kubernetes/ingress/pull/179) Allows the usage of Default SSL Cert -- [x] [#178](https://github.com/kubernetes/ingress/pull/178) Add initialization of proxy variable -- [x] [#177](https://github.com/kubernetes/ingress/pull/177) Refactoring sysctlFSFileMax helper -- [x] [#176](https://github.com/kubernetes/ingress/pull/176) Fix TLS does not get updated when changed -- [x] [#174](https://github.com/kubernetes/ingress/pull/174) Update nginx to 1.11.9 -- [x] [#172](https://github.com/kubernetes/ingress/pull/172) add some unit test cases for some packages under folder "core.pkg.ingress" -- [x] [#168](https://github.com/kubernetes/ingress/pull/168) Changes the SSL Temp file to something inside the same SSL Directory -- [x] [#165](https://github.com/kubernetes/ingress/pull/165) Fix rate limit issue when more than 2 servers enabled in ingress -- [x] [#161](https://github.com/kubernetes/ingress/pull/161) Document some missing parameters and their defaults for NGINX controller -- [x] [#158](https://github.com/kubernetes/ingress/pull/158) prefect unit test cases for annotation.proxy -- [x] [#156](https://github.com/kubernetes/ingress/pull/156) Fix issue for ratelimit -- [x] [#154](https://github.com/kubernetes/ingress/pull/154) add unit test cases for core.pkg.ingress.annotations.cors -- [x] [#151](https://github.com/kubernetes/ingress/pull/151) Port in redirect -- [x] [#150](https://github.com/kubernetes/ingress/pull/150) Add support for custom header sizes -- [x] [#149](https://github.com/kubernetes/ingress/pull/149) Add flag to allow switch off the update of Ingress status -- [x] [#148](https://github.com/kubernetes/ingress/pull/148) Add annotation to allow custom body sizes -- [x] [#145](https://github.com/kubernetes/ingress/pull/145) fix wrong links and punctuations -- [x] [#144](https://github.com/kubernetes/ingress/pull/144) add unit test cases for core.pkg.k8s -- [x] [#143](https://github.com/kubernetes/ingress/pull/143) Use protobuf instead of rest to connect to apiserver host and add troubleshooting doc -- [x] [#142](https://github.com/kubernetes/ingress/pull/142) Use system fs.max-files as limits instead of hard-coded value -- [x] [#141](https://github.com/kubernetes/ingress/pull/141) Add reuse port and backlog to port 80 and 443 -- [x] [#138](https://github.com/kubernetes/ingress/pull/138) reference to const -- [x] [#136](https://github.com/kubernetes/ingress/pull/136) Add content and descriptions about nginx's configuration -- [x] [#135](https://github.com/kubernetes/ingress/pull/135) correct improper punctuation -- [x] [#134](https://github.com/kubernetes/ingress/pull/134) fix typo -- [x] [#133](https://github.com/kubernetes/ingress/pull/133) Add TCP and UDP services removed in migration -- [x] [#132](https://github.com/kubernetes/ingress/pull/132) Document nginx controller configuration tweaks -- [x] [#128](https://github.com/kubernetes/ingress/pull/128) Add tests and godebug to compare structs -- [x] [#126](https://github.com/kubernetes/ingress/pull/126) change the type of imagePullPolicy -- [x] [#123](https://github.com/kubernetes/ingress/pull/123) Add resolver configuration to nginx -- [x] [#119](https://github.com/kubernetes/ingress/pull/119) add unit test case for annotations.service -- [x] [#115](https://github.com/kubernetes/ingress/pull/115) add default_server to listen statement for default backend -- [x] [#114](https://github.com/kubernetes/ingress/pull/114) fix typo -- [x] [#113](https://github.com/kubernetes/ingress/pull/113) Add condition of enqueue and unit test cases for task.Queue -- [x] [#108](https://github.com/kubernetes/ingress/pull/108) annotations: print error and skip if malformed -- [x] [#107](https://github.com/kubernetes/ingress/pull/107) fix some wrong links of examples which to be used for nginx -- [x] [#103](https://github.com/kubernetes/ingress/pull/103) Update the nginx controller manifests -- [x] [#101](https://github.com/kubernetes/ingress/pull/101) Add unit test for strings.StringInSlice -- [x] [#99](https://github.com/kubernetes/ingress/pull/99) Update nginx to 1.11.8 -- [x] [#97](https://github.com/kubernetes/ingress/pull/97) Fix gofmt -- [x] [#96](https://github.com/kubernetes/ingress/pull/96) Fix typo PassthrougBackends -> PassthroughBackends -- [x] [#95](https://github.com/kubernetes/ingress/pull/95) Deny location mapping in case of specific errors -- [x] [#94](https://github.com/kubernetes/ingress/pull/94) Add support to disable server_tokens directive -- [x] [#93](https://github.com/kubernetes/ingress/pull/93) Fix sort for catch all server -- [x] [#92](https://github.com/kubernetes/ingress/pull/92) Refactoring of nginx configuration deserialization -- [x] [#91](https://github.com/kubernetes/ingress/pull/91) Fix x-forwarded-port mapping -- [x] [#90](https://github.com/kubernetes/ingress/pull/90) fix the wrong link to build/test/release -- [x] [#89](https://github.com/kubernetes/ingress/pull/89) fix the wrong links to the examples and developer documentation -- [x] [#88](https://github.com/kubernetes/ingress/pull/88) Fix multiple tls hosts sharing the same secretName -- [x] [#86](https://github.com/kubernetes/ingress/pull/86) Update X-Forwarded-Port -- [x] [#82](https://github.com/kubernetes/ingress/pull/82) Fix incorrect X-Forwarded-Port for TLS -- [x] [#81](https://github.com/kubernetes/ingress/pull/81) Do not push containers to remote repo as part of test-e2e -- [x] [#78](https://github.com/kubernetes/ingress/pull/78) Fix #76: hardcode X-Forwarded-Port due to SSL Passthrough -- [x] [#77](https://github.com/kubernetes/ingress/pull/77) Add support for IPV6 in dns resolvers -- [x] [#66](https://github.com/kubernetes/ingress/pull/66) Start FAQ docs -- [x] [#65](https://github.com/kubernetes/ingress/pull/65) Support hostnames in Ingress status -- [x] [#64](https://github.com/kubernetes/ingress/pull/64) Sort whitelist list to avoid random orders -- [x] [#62](https://github.com/kubernetes/ingress/pull/62) Fix e2e make targets -- [x] [#61](https://github.com/kubernetes/ingress/pull/61) Ignore coverage profile files -- [x] [#58](https://github.com/kubernetes/ingress/pull/58) Fix "invalid port in upstream" on nginx controller -- [x] [#57](https://github.com/kubernetes/ingress/pull/57) Fix invalid port in upstream -- [x] [#54](https://github.com/kubernetes/ingress/pull/54) Expand developer docs -- [x] [#52](https://github.com/kubernetes/ingress/pull/52) fix typo in variable ProxyRealIPCIDR -- [x] [#44](https://github.com/kubernetes/ingress/pull/44) Bump nginx version to one higher than that in contrib -- [x] [#36](https://github.com/kubernetes/ingress/pull/36) Add nginx metrics to prometheus -- [x] [#34](https://github.com/kubernetes/ingress/pull/34) nginx: also listen on ipv6 -- [x] [#32](https://github.com/kubernetes/ingress/pull/32) Restart nginx if master process dies -- [x] [#31](https://github.com/kubernetes/ingress/pull/31) Add healthz checker -- [x] [#25](https://github.com/kubernetes/ingress/pull/25) Fix a data race in TestFileWatcher -- [x] [#12](https://github.com/kubernetes/ingress/pull/12) Split implementations from generic code -- [x] [#10](https://github.com/kubernetes/ingress/pull/10) Copy Ingress history from kubernetes/contrib -- [x] [#1498](https://github.com/kubernetes/contrib/pull/1498) Refactoring of template handling -- [x] [#1571](https://github.com/kubernetes/contrib/pull/1571) use POD_NAMESPACE as a namespace in cli parameters -- [x] [#1591](https://github.com/kubernetes/contrib/pull/1591) Always listen on port 443, even without ingress rules -- [x] [#1596](https://github.com/kubernetes/contrib/pull/1596) Adapt nginx hash sizes to the number of ingress -- [x] [#1653](https://github.com/kubernetes/contrib/pull/1653) Update image version -- [x] [#1672](https://github.com/kubernetes/contrib/pull/1672) Add firewall rules and ing class clarifications -- [x] [#1711](https://github.com/kubernetes/contrib/pull/1711) Add function helpers to nginx template -- [x] [#1743](https://github.com/kubernetes/contrib/pull/1743) Allow customisation of the nginx proxy_buffer_size directive via ConfigMap -- [x] [#1749](https://github.com/kubernetes/contrib/pull/1749) Readiness probe that works behind a CP lb -- [x] [#1751](https://github.com/kubernetes/contrib/pull/1751) Add the name of the upstream in the log -- [x] [#1758](https://github.com/kubernetes/contrib/pull/1758) Update nginx to 1.11.4 -- [x] [#1759](https://github.com/kubernetes/contrib/pull/1759) Add support for default backend in Ingress rule -- [x] [#1762](https://github.com/kubernetes/contrib/pull/1762) Add cloud detection -- [x] [#1766](https://github.com/kubernetes/contrib/pull/1766) Clarify the controller uses endpoints and not services -- [x] [#1767](https://github.com/kubernetes/contrib/pull/1767) Update godeps -- [x] [#1772](https://github.com/kubernetes/contrib/pull/1772) Avoid replacing nginx.conf file if the new configuration is invalid -- [x] [#1773](https://github.com/kubernetes/contrib/pull/1773) Add annotation to add CORS support -- [x] [#1786](https://github.com/kubernetes/contrib/pull/1786) Add docs about go template -- [x] [#1796](https://github.com/kubernetes/contrib/pull/1796) Add external authentication support using auth_request -- [x] [#1802](https://github.com/kubernetes/contrib/pull/1802) Initialize proxy_upstream_name variable -- [x] [#1806](https://github.com/kubernetes/contrib/pull/1806) Add docs about the log format -- [x] [#1808](https://github.com/kubernetes/contrib/pull/1808) WebSocket documentation -- [x] [#1847](https://github.com/kubernetes/contrib/pull/1847) Change structure of packages -- [x] Add annotation for custom upstream timeouts -- [x] Mutual TLS auth (https://github.com/kubernetes/contrib/issues/1870) - -### 0.8.3 - -- [x] [#1450](https://github.com/kubernetes/contrib/pull/1450) Check for errors in nginx template -- [ ] [#1498](https://github.com/kubernetes/contrib/pull/1498) Refactoring of template handling -- [x] [#1467](https://github.com/kubernetes/contrib/pull/1467) Use ClientConfig to configure connection -- [x] [#1575](https://github.com/kubernetes/contrib/pull/1575) Update nginx to 1.11.3 - -### 0.8.2 - -- [x] [#1336](https://github.com/kubernetes/contrib/pull/1336) Add annotation to skip ingress rule -- [x] [#1338](https://github.com/kubernetes/contrib/pull/1338) Add HTTPS default backend -- [x] [#1351](https://github.com/kubernetes/contrib/pull/1351) Avoid generation of invalid ssl certificates -- [x] [#1379](https://github.com/kubernetes/contrib/pull/1379) improve nginx performance -- [x] [#1350](https://github.com/kubernetes/contrib/pull/1350) Improve performance (listen backlog=net.core.somaxconn) -- [x] [#1384](https://github.com/kubernetes/contrib/pull/1384) Unset Authorization header when proxying -- [x] [#1398](https://github.com/kubernetes/contrib/pull/1398) Mitigate HTTPoxy Vulnerability - -### 0.8.1 - -- [x] [#1317](https://github.com/kubernetes/contrib/pull/1317) Fix duplicated real_ip_header -- [x] [#1315](https://github.com/kubernetes/contrib/pull/1315) Addresses #1314 - -### 0.8 - -- [x] [#1063](https://github.com/kubernetes/contrib/pull/1063) watches referenced tls secrets -- [x] [#850](https://github.com/kubernetes/contrib/pull/850) adds configurable SSL redirect nginx controller -- [x] [#1136](https://github.com/kubernetes/contrib/pull/1136) Fix nginx rewrite rule order -- [x] [#1144](https://github.com/kubernetes/contrib/pull/1144) Add cidr whitelist support -- [x] [#1230](https://github.com/kubernetes/contrib/pull/1130) Improve docs and examples -- [x] [#1258](https://github.com/kubernetes/contrib/pull/1258) Avoid sync without a reachable -- [x] [#1235](https://github.com/kubernetes/contrib/pull/1235) Fix stats by country in nginx status page -- [x] [#1236](https://github.com/kubernetes/contrib/pull/1236) Update nginx to add dynamic TLS records and spdy -- [x] [#1238](https://github.com/kubernetes/contrib/pull/1238) Add support for dynamic TLS records and spdy -- [x] [#1239](https://github.com/kubernetes/contrib/pull/1239) Add support for conditional log of urls -- [x] [#1253](https://github.com/kubernetes/contrib/pull/1253) Use delayed queue -- [x] [#1296](https://github.com/kubernetes/contrib/pull/1296) Fix formatting -- [x] [#1299](https://github.com/kubernetes/contrib/pull/1299) Fix formatting - -### 0.7 - -- [x] [#898](https://github.com/kubernetes/contrib/pull/898) reorder locations. Location / must be the last one to avoid errors routing to subroutes -- [x] [#946](https://github.com/kubernetes/contrib/pull/946) Add custom authentication (Basic or Digest) to ingress rules -- [x] [#926](https://github.com/kubernetes/contrib/pull/926) Custom errors should be optional -- [x] [#1002](https://github.com/kubernetes/contrib/pull/1002) Use k8s probes (disable NGINX checks) -- [x] [#962](https://github.com/kubernetes/contrib/pull/962) Make optional http2 -- [x] [#1054](https://github.com/kubernetes/contrib/pull/1054) force reload if some certificate change -- [x] [#958](https://github.com/kubernetes/contrib/pull/958) update NGINX to 1.11.0 and add digest module -- [x] [#960](https://github.com/kubernetes/contrib/issues/960) https://trac.nginx.org/nginx/changeset/ce94f07d50826fcc8d48f046fe19d59329420fdb/nginx -- [x] [#1057](https://github.com/kubernetes/contrib/pull/1057) Remove loadBalancer ip on shutdown -- [x] [#1079](https://github.com/kubernetes/contrib/pull/1079) path rewrite -- [x] [#1093](https://github.com/kubernetes/contrib/pull/1093) rate limiting -- [x] [#1102](https://github.com/kubernetes/contrib/pull/1102) geolocation of traffic in stats -- [x] [#884](https://github.com/kubernetes/contrib/issues/884) support services running ssl -- [x] [#930](https://github.com/kubernetes/contrib/issues/930) detect changes in configuration configmaps diff --git a/GOLANG_VERSION b/GOLANG_VERSION deleted file mode 100644 index d8c40e539..000000000 --- a/GOLANG_VERSION +++ /dev/null @@ -1 +0,0 @@ -1.23.6 diff --git a/ISSUE_TRIAGE.md b/ISSUE_TRIAGE.md deleted file mode 100644 index e6d2c1d8e..000000000 --- a/ISSUE_TRIAGE.md +++ /dev/null @@ -1,89 +0,0 @@ -# Triage Process - -As any kind of contributor (triage, reviewer ...), always have in mind that if a user came to us and raised an issue, the user may have a real problem. We must assume that, and not the opposite (the user needs to prove to us that this is a bug). Keeping that in mind, **be nice with users, even if you don’t agree with them** - -Note that this guide refers to contributing through issue triaging. If you are interested in contributing to actual sources of the repository, see [this guide](./CONTRIBUTING.md). - -## General Information - -The triage process of the ingress-nginx maintainers is based on the [triage process guidelines](https://github.com/kubernetes/community/blob/master/contributors/guide/issue-triage.md) of the Kubernetes community - -However the exact process of the ingress-nginx maintainers may differ in certain aspects. This doc gives a more precise overview on how the ingress-nginx maintainers approach the issue triage process and other processes that are related. - -## Triage Flow (Issues) - -This section describes the different stages of the triage flow for issues. - -### Prepare Issues -New issues come in with the labels `needs-triage` and `needs-priority` and one of: `kind/bug`, `kind/feature` or `kind/support`. Unfortunately there are also some legacy issues that only have a `kind/*` label but neither `needs-triage` nor `needs-priority` . However for every issue that does not have the `triage-accepted` label the following steps have to be done to prepare them for further processing: - -* Filter for issues [without the `triage-accepted`](https://github.com/kubernetes/ingress-nginx/issues?q=is%3Aopen+-label%3Atriage%2Faccepted+is%3Aissue) label. -* Check if all necessary information are available. This is basically true, if people filled out the issue template correctly. If necessary information is missing, ask the author to add the missing information and add the label `triage/needs-information` if not already present. If already present, send the author a friendly reminder to add those. -* Check if the used versions of ingress-nginx and Kubernetes is supported. Note that [we only support n-3 versions](https://github.com/kubernetes/ingress-nginx#support-versions-table). If the version is not supported, ask the author to upgrade to newer versions and see if the error still persists. -* Read through the issue description and comments briefly to understand what the issue is about. Also check if the kind and area is correct, and adjust it if necessary. If the issue is understandable add the label `triage-accepted`. -* If at any point you don't know how to proceed with an issue during the triage process, tag one of the [core maintainers](OWNERS_ALIASES) in the issue to raise attention or alternatively come to [this slack channel](https://kubernetes.slack.com/archives/C021E147ZA4) which may be the quicker way as people tend to miss github notifications. - -Note: Issues that are stale for 90 days are being closed automatically. However we could be missing a bug here, so from time to time it makes sense to go over the closed ones and see if there is something important. Use [this filter](https://github.com/kubernetes/ingress-nginx/issues?q=is%3Aclosed+is%3Aissue+label%3Alifecycle%2Frotten+) to find those. - -Who and When? -* Basically everyone who wants to contribute can do the mentioned steps at any time. - -### Issue Prioritization -For all issues, where all necessary information is available thus triage is accepted, we need to do some prioritization: - -* Go through all issues with label [`triage-accepted`](https://github.com/kubernetes/ingress-nginx/issues?q=is%3Aopen+is%3Aissue+label%3Atriage%2Faccepted+). -* Add appropriate priority label: `priority/backlog`, `priority/critical-urgent`, `priority/awaiting-more-evidence`, `priority/important-longterm`, `priority/important-soon` or `good first issue` - -Who and When? -* Basically every contributor should be able to do that. -* Tricky/important ones could be brought up during community meetings - -## Triage Flow (Pull Requests) - -This section describes the different stages of the triage flow for pull requests. - -### Prepare Pull Requests -Pull requests come in with the labels `needs-triage`, `needs-priority` and `needs-kind` and one that indicates the size(`size/*`). Unfortunately there are also some legacy pull requests that only have a `size/*` label but neither `needs-triage` nor `needs-priority` . However for every pull request that does not have the `triage-accepted` label the following steps should be done to prepare them for further processing: - -* Filter for pull requests [without the `triage-accepted`](https://github.com/kubernetes/ingress-nginx/pulls?q=is%3Aopen+-label%3Atriage%2Faccepted+is%3Apr) label. -* Check if the cla is signed and all necessary information are available. This is basically true, if people filled out the pull request template correctly. If everything is fine add the `triage-accepted` label. -* If at any point you don't know how to proceed with an issue during the triage process, tag one of the [core maintainers](OWNERS_ALIASES) in the issue to raise attention or alternatively come to [this slack channel](https://kubernetes.slack.com/archives/C021E147ZA4) which may be the quicker way as people tend to miss github notifications. - -Who and When? -* Basically everyone who wants to contribute can do the mentioned steps at any time. - -### Pull Request Prioritization -For all pull requests, where all necessary information is available and cla is signed thus triage is accepted, we need to do some prioritization: - -* Go through all pull requests with label [`triage-accepted`](https://github.com/kubernetes/ingress-nginx/pulls?q=is%3Aopen+is%3Apr+label%3Atriage%2Faccepted). -* Sync the `kind/*` and `priority/*` label from the linked issue for the pull request. If the pull request does not have any issue associated (which normally should not be the case), add an appropriate priority and kind label (one of: `priority/backlog`, `priority/critical-urgent`, `priority/important-longterm`, `priority/important-soon`) - -Who and When? -* Basically every contributor should be able to do that. -* Tricky/important ones could be brought up during community meetings - -## Labels -Labels are helpful for issues or pull requests to indicate in which lifecycle state they are currently and to categorize them. This section describes the most important ones with the additional info about how to add those. A complete label list of the Kubernetes community can be found [here](https://github.com/kubernetes/kubernetes/labels) while a complete label list for this project can be found [here](https://github.com/kubernetes/ingress-nginx/labels). However, here the most important ones: - -* Triage: - * [`needs-triage`](https://github.com/kubernetes/ingress-nginx/issues?q=is%3Aopen+is%3Aissue+label%3Aneeds-triage): Indicates that the issue or pull request needs triage. Automatically added. - * [`triage/accepted`](https://github.com/kubernetes/ingress-nginx/issues?q=is%3Aopen+label%3Atriage%2Faccepted+is%3Aissue+): Indicates that the issue is ready for further processing. Add with `/triage accepted`. - * [`triage/needs-information`](https://github.com/kubernetes/ingress-nginx/issues?q=is%3Aopen+label%3Atriage%2Fneeds-information+is%3Aissue+): Indicates that the issue lacks information. Add with `/triage needs-information`. -* Kind: - * [`kind/bug`](https://github.com/kubernetes/ingress-nginx/issues?q=is%3Aopen+label%3Akind%2Fbug+is%3Aissue): Indicates that the issue is assumed to be a bug. Add with `/kind bug`. Remove with `/remove-kind bug`. - * [`kind/feature`](https://github.com/kubernetes/ingress-nginx/issues?q=is%3Aopen+label%3Akind%2Ffeature+is%3Aissue+): Indicates that the issue is a feature request. Add with `/kind feature`. Remove with `/remove-kind feature`. - * [`kind/documentation`](https://github.com/kubernetes/ingress-nginx/issues?q=is%3Aopen+label%3Akind%2Fdocumentation+is%3Aissue+): Indicates that the issue is documentation related. Add with `/kind documentation`. Remove with `/remove-kind documentation`. - * [`kind/support`](https://github.com/kubernetes/ingress-nginx/issues?q=is%3Aopen+label%3Akind%2Fsupport+is%3Aissue+): Indicates the the issue is a support request. Add with `/kind support`. Remove with `/remove-kind support`. -* Area: - * [`area/helm`](https://github.com/kubernetes/ingress-nginx/issues?q=is%3Aopen+label%3Aarea%2Fhelm+is%3Aissue+): Indicates that the issue is related to helm charts. Add with `/area helm`. - * [`area/lua`](https://github.com/kubernetes/ingress-nginx/issues?q=is%3Aopen+label%3Aarea%2Flua+is%3Aissue+): Indicates that the issue is related to lua. Add with `/area lua`. - * [`area/docs`](https://github.com/kubernetes/ingress-nginx/issues?q=is%3Aopen+label%3Aarea%2Fdocs+is%3Aissue): Indicates that the issue is related to documentation. Add with `/area docs` . -* Priority: - * [`needs-priority`](https://github.com/kubernetes/ingress-nginx/issues?q=is%3Aopen+is%3Aissue+label%3Aneeds-priority): Indicates that the issue has no prioritization yet. Automatically added. - * [`priority/critical-urgent`](https://github.com/kubernetes/ingress-nginx/issues?q=is%3Aopen+label%3Apriority%2Fcritical-urgent+is%3Aissue+): indicates that the issue has highest priority. Add with `/priority critical-urgent`. - * [`priority/important-soon`](https://github.com/kubernetes/ingress-nginx/issues?q=is%3Aopen+label%3Apriority%2Fimportant-soon+is%3Aissue+): indicates that the issue should be worked on either currently soon, ideally in time for the next release. Add with `/priority important-soon`. - * [`priority/important-longterm`](https://github.com/kubernetes/ingress-nginx/issues?q=is%3Aopen+label%3Apriority%2Fimportant-longterm+is%3Aissue+): indicates that the issue is not important for now, but should be worked on in one of the upcoming releases. Add with `/priority important-longterm`. - * [`priority/backlog`](https://github.com/kubernetes/ingress-nginx/issues?q=is%3Aopen+label%3Apriority%2Fbacklog+is%3Aissue+): Indicates that the issue has the lowest priority. Add with `/priority backlog`. -* Other: - * [`help wanted`](https://github.com/kubernetes/ingress-nginx/issues?q=is%3Aopen+is%3Aissue+label%3A%22help+wanted%22): indicates that the issue needs help from a contributor. Add with `/help`. - * [`good first issue`](https://github.com/kubernetes/ingress-nginx/issues?q=is%3Aopen+is%3Aissue+label%3A%22good+first+issue%22): indicates that the issue needs help from a contributor and is a good first issue for new contributors. Add with `/good-first-issue`. \ No newline at end of file diff --git a/LICENSE b/LICENSE deleted file mode 100644 index 8dada3eda..000000000 --- a/LICENSE +++ /dev/null @@ -1,201 +0,0 @@ - Apache License - Version 2.0, January 2004 - http://www.apache.org/licenses/ - - TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION - - 1. Definitions. - - "License" shall mean the terms and conditions for use, reproduction, - and distribution as defined by Sections 1 through 9 of this document. - - "Licensor" shall mean the copyright owner or entity authorized by - the copyright owner that is granting the License. - - "Legal Entity" shall mean the union of the acting entity and all - other entities that control, are controlled by, or are under common - control with that entity. For the purposes of this definition, - "control" means (i) the power, direct or indirect, to cause the - direction or management of such entity, whether by contract or - otherwise, or (ii) ownership of fifty percent (50%) or more of the - outstanding shares, or (iii) beneficial ownership of such entity. - - "You" (or "Your") shall mean an individual or Legal Entity - exercising permissions granted by this License. - - "Source" form shall mean the preferred form for making modifications, - including but not limited to software source code, documentation - source, and configuration files. - - "Object" form shall mean any form resulting from mechanical - transformation or translation of a Source form, including but - not limited to compiled object code, generated documentation, - and conversions to other media types. - - "Work" shall mean the work of authorship, whether in Source or - Object form, made available under the License, as indicated by a - copyright notice that is included in or attached to the work - (an example is provided in the Appendix below). - - "Derivative Works" shall mean any work, whether in Source or Object - form, that is based on (or derived from) the Work and for which the - editorial revisions, annotations, elaborations, or other modifications - represent, as a whole, an original work of authorship. For the purposes - of this License, Derivative Works shall not include works that remain - separable from, or merely link (or bind by name) to the interfaces of, - the Work and Derivative Works thereof. - - "Contribution" shall mean any work of authorship, including - the original version of the Work and any modifications or additions - to that Work or Derivative Works thereof, that is intentionally - submitted to Licensor for inclusion in the Work by the copyright owner - or by an individual or Legal Entity authorized to submit on behalf of - the copyright owner. For the purposes of this definition, "submitted" - means any form of electronic, verbal, or written communication sent - to the Licensor or its representatives, including but not limited to - communication on electronic mailing lists, source code control systems, - and issue tracking systems that are managed by, or on behalf of, the - Licensor for the purpose of discussing and improving the Work, but - excluding communication that is conspicuously marked or otherwise - designated in writing by the copyright owner as "Not a Contribution." - - "Contributor" shall mean Licensor and any individual or Legal Entity - on behalf of whom a Contribution has been received by Licensor and - subsequently incorporated within the Work. - - 2. Grant of Copyright License. Subject to the terms and conditions of - this License, each Contributor hereby grants to You a perpetual, - worldwide, non-exclusive, no-charge, royalty-free, irrevocable - copyright license to reproduce, prepare Derivative Works of, - publicly display, publicly perform, sublicense, and distribute the - Work and such Derivative Works in Source or Object form. - - 3. Grant of Patent License. Subject to the terms and conditions of - this License, each Contributor hereby grants to You a perpetual, - worldwide, non-exclusive, no-charge, royalty-free, irrevocable - (except as stated in this section) patent license to make, have made, - use, offer to sell, sell, import, and otherwise transfer the Work, - where such license applies only to those patent claims licensable - by such Contributor that are necessarily infringed by their - Contribution(s) alone or by combination of their Contribution(s) - with the Work to which such Contribution(s) was submitted. If You - institute patent litigation against any entity (including a - cross-claim or counterclaim in a lawsuit) alleging that the Work - or a Contribution incorporated within the Work constitutes direct - or contributory patent infringement, then any patent licenses - granted to You under this License for that Work shall terminate - as of the date such litigation is filed. - - 4. Redistribution. You may reproduce and distribute copies of the - Work or Derivative Works thereof in any medium, with or without - modifications, and in Source or Object form, provided that You - meet the following conditions: - - (a) You must give any other recipients of the Work or - Derivative Works a copy of this License; and - - (b) You must cause any modified files to carry prominent notices - stating that You changed the files; and - - (c) You must retain, in the Source form of any Derivative Works - that You distribute, all copyright, patent, trademark, and - attribution notices from the Source form of the Work, - excluding those notices that do not pertain to any part of - the Derivative Works; and - - (d) If the Work includes a "NOTICE" text file as part of its - distribution, then any Derivative Works that You distribute must - include a readable copy of the attribution notices contained - within such NOTICE file, excluding those notices that do not - pertain to any part of the Derivative Works, in at least one - of the following places: within a NOTICE text file distributed - as part of the Derivative Works; within the Source form or - documentation, if provided along with the Derivative Works; or, - within a display generated by the Derivative Works, if and - wherever such third-party notices normally appear. The contents - of the NOTICE file are for informational purposes only and - do not modify the License. You may add Your own attribution - notices within Derivative Works that You distribute, alongside - or as an addendum to the NOTICE text from the Work, provided - that such additional attribution notices cannot be construed - as modifying the License. - - You may add Your own copyright statement to Your modifications and - may provide additional or different license terms and conditions - for use, reproduction, or distribution of Your modifications, or - for any such Derivative Works as a whole, provided Your use, - reproduction, and distribution of the Work otherwise complies with - the conditions stated in this License. - - 5. Submission of Contributions. Unless You explicitly state otherwise, - any Contribution intentionally submitted for inclusion in the Work - by You to the Licensor shall be under the terms and conditions of - this License, without any additional terms or conditions. - Notwithstanding the above, nothing herein shall supersede or modify - the terms of any separate license agreement you may have executed - with Licensor regarding such Contributions. - - 6. Trademarks. This License does not grant permission to use the trade - names, trademarks, service marks, or product names of the Licensor, - except as required for reasonable and customary use in describing the - origin of the Work and reproducing the content of the NOTICE file. - - 7. Disclaimer of Warranty. Unless required by applicable law or - agreed to in writing, Licensor provides the Work (and each - Contributor provides its Contributions) on an "AS IS" BASIS, - WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or - implied, including, without limitation, any warranties or conditions - of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A - PARTICULAR PURPOSE. You are solely responsible for determining the - appropriateness of using or redistributing the Work and assume any - risks associated with Your exercise of permissions under this License. - - 8. Limitation of Liability. In no event and under no legal theory, - whether in tort (including negligence), contract, or otherwise, - unless required by applicable law (such as deliberate and grossly - negligent acts) or agreed to in writing, shall any Contributor be - liable to You for damages, including any direct, indirect, special, - incidental, or consequential damages of any character arising as a - result of this License or out of the use or inability to use the - Work (including but not limited to damages for loss of goodwill, - work stoppage, computer failure or malfunction, or any and all - other commercial damages or losses), even if such Contributor - has been advised of the possibility of such damages. - - 9. Accepting Warranty or Additional Liability. While redistributing - the Work or Derivative Works thereof, You may choose to offer, - and charge a fee for, acceptance of support, warranty, indemnity, - or other liability obligations and/or rights consistent with this - License. However, in accepting such obligations, You may act only - on Your own behalf and on Your sole responsibility, not on behalf - of any other Contributor, and only if You agree to indemnify, - defend, and hold each Contributor harmless for any liability - incurred by, or claims asserted against, such Contributor by reason - of your accepting any such warranty or additional liability. - - END OF TERMS AND CONDITIONS - - APPENDIX: How to apply the Apache License to your work. - - To apply the Apache License to your work, attach the following - boilerplate notice, with the fields enclosed by brackets "{}" - replaced with your own identifying information. (Don't include - the brackets!) The text should be enclosed in the appropriate - comment syntax for the file format. We also recommend that a - file or class name and description of purpose be included on the - same "printed page" as the copyright notice for easier - identification within third-party archives. - - Copyright {yyyy} {name of copyright owner} - - Licensed under the Apache License, Version 2.0 (the "License"); - you may not use this file except in compliance with the License. - You may obtain a copy of the License at - - http://www.apache.org/licenses/LICENSE-2.0 - - Unless required by applicable law or agreed to in writing, software - distributed under the License is distributed on an "AS IS" BASIS, - WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - See the License for the specific language governing permissions and - limitations under the License. diff --git a/MANUAL_RELEASE.md b/MANUAL_RELEASE.md deleted file mode 100644 index 0ae7a4e37..000000000 --- a/MANUAL_RELEASE.md +++ /dev/null @@ -1,300 +0,0 @@ -# RELEASE PROCESS - -## 1. BUILD the new Ingress-Nginx-Controller image - -### a. Make changes in codebase - -- Make changes as per issue - -### b. Make changes to appropriate files in [images directory ](images) - -- Make changes in /images - -### c. Create Pull Request - -- Open a Pull Request for your changes considering the following steps to fire cloudbuild of a new image for the Ingress-Nginx-Controller: - - - In case of rare CVE fix or other reason to rebuild the nginx-base-image itself, look at the /images directory [NGINX Base Image](https://github.com/kubernetes/ingress-nginx/tree/main/images/nginx). - - - Example [NGINX_VERSION](images/nginx/rootfs/build.sh#L21), [SHA256](images/nginx/rootfs/build.sh#L124). - - - If you are updating any component in [build.sh](images/nginx/rootfs/build.sh) please also update the SHA256 checksum of that component as well, the cloud build will fail with an exit 10 if not. - -### d. Merge - -- Merging will fire cloudbuild, which will result in images being promoted to the [staging container registry](https://console.cloud.google.com/gcr/images/k8s-staging-ingress-nginx). - -### e. Make sure cloudbuild is a success - -- Wait for [cloud build](https://console.cloud.google.com/cloud-build/builds?project=k8s-staging-ingress-nginx). If you don't have access to cloudbuild, you can also have a look at [this](https://prow.k8s.io/?repo=kubernetes%2Fingress-nginx&job=post-*), to see the progress of the build. - -- Proceed only after cloud-build is successful in building a new Ingress-Nginx-Controller image. - - -## 2. If applicable, BUILD other images - -- If applicable, then build a new image of any other related component, ONLY IF APPLICABLE TO THE RELEASE - -### a. If applicable then make changes in relevant codebase - -- Change code as per issue - -### b. Make changes to appropriate files in [images directory ](images) - -- Sometimes, you may also be needing to rebuild, images for one or multiple other related components of the Ingress-Nginx-Controller ecosystem. Make changes to the required files in the /images directory, if/as applicable, in the context of the release you are attempting. : - - - [e2e](https://github.com/kubernetes/ingress-nginx/tree/main/test/e2e-image) - - - Update references to e2e-test-runner image [If applicable] : - - - [e2e-image](https://github.com/kubernetes/ingress-nginx/blob/main/test/e2e-image/Dockerfile#L1) - - [run-in-docker.sh](https://github.com/kubernetes/ingress-nginx/blob/main/build/run-in-docker.sh#L37) - - - [test-runner](https://github.com/kubernetes/ingress-nginx/tree/main/images/test-runner) - - - [echo](https://github.com/kubernetes/ingress-nginx/tree/main/images/echo) - - - [cfssl](https://github.com/kubernetes/ingress-nginx/tree/main/images/cfssl) - - - [fastcgi-helloserver](https://github.com/kubernetes/ingress-nginx/tree/main/images/fastcgi-helloserver) - - - [httpbin](https://github.com/kubernetes/ingress-nginx/tree/main/images/httpbin) - - - [kube-webhook-certgen](https://github.com/kubernetes/ingress-nginx/tree/main/images/kube-webhook-certgen) - -### c. Create PR - -- Open pull request(s) accordingly, to fire cloudbuild for rebuilding the component's image (if applicable). - -### d. Merge - -- Merging will fire cloudbuild, which will result in images being promoted to the [staging container registry](https://console.cloud.google.com/gcr/images/k8s-staging-ingress-nginx). - -### e. Make sure cloudbuild is a success - -- Wait for [cloud build](https://console.cloud.google.com/cloud-build/builds?project=k8s-staging-ingress-nginx). If you don't have access to cloudbuild, you can also have a look at [this](https://prow.k8s.io/?repo=kubernetes%2Fingress-nginx&job=post-*), to see the progress of the build. - -- Proceed only after cloud-build is successful in building a new Ingress-Nginx-Controller image. - - -## 3. PROMOTE the Image(s): - -Promoting the images basically means that images, that were pushed to staging container registry in the steps above, now are also pushed to the public container registry. Thus are publicly available. Follow these steps to promote images: - -### a. Get the sha - -- Get the sha of the new image(s) of the controller, (and any other component image IF APPLICABLE to release), from the cloudbuild, from steps above - - - The sha is available in output from [cloud build](https://console.cloud.google.com/cloud-build/builds?project=k8s-staging-ingress-nginx) - - - The sha is also visible here https://console.cloud.google.com/gcr/images/k8s-staging-ingress-nginx/global/controller - - - The sha is also visible [here](https://prow.k8s.io/?repo=kubernetes%2Fingress-nginx&job=post-*), after cloud build is finished. Click on the respective job, go to `Artifacts` section in the UI, then again `artifacts` in the directory browser. In the `build.log` at the very bottom you see something like this: - - ``` - ... - pushing manifest for us-central1-docker.pkg.dev/k8s-staging-images/ingress-nginx/controller:v1.0.2@sha256:e15fac6e8474d77e1f017edc33d804ce72a184e3c0a30963b2a0d7f0b89f6b16 - ... - ``` - -### b. Add the new image to [k8s.io](http://github.com/kubernetes/k8s.io) - -- The sha(s) from the step before (and the tag(s) for the new image(s) have to be added, as a new line, in a file, of the [k8s.io](http://github.com/kubernetes/k8s.io) project of Kubernetes organization. - -- Fork that other project (if you don't have a fork already). - -- Other project to fork [GitHub repo kubernetes/k8s.io](http://github.com/kubernetes/k8s.io) - -- Fetch --all and rebase to upstream if already forked. - -- Create a branch in your fork, named as the issue number for this release - -- In the related branch, of your fork, edit the file /registry.k8s.io/images/k8s-staging-ingress-nginx/images.yaml. - -- For making, it easier, you can edit your branch directly in the browser. But be careful about making any mistake. - -- Insert the sha(s) & the tag(s), in a new line, in this file [Project kubernetes/k8s.io Ingress-Nginx-Controller Images](https://github.com/kubernetes/k8s.io/blob/main/registry.k8s.io/images/k8s-staging-ingress-nginx/images.yaml) Look at this [example PR and the diff](https://github.com/kubernetes/k8s.io/pull/2536) to see how it was done before - -- Save and commit - -### c. Create PR - -- Open pull request to promote the new controller image. - -### d. Merge - -- Merge success is required for next step - -- Proceed only after cloud-build is successful in building a new Ingress-Nginx-Controller image. - - -## 4. PREPARE for a new Release - -- Make sure to get the tag and sha of the promoted image from the step before, either from cloudbuild or from [here](https://console.cloud.google.com/gcr/images/k8s-artifacts-prod/us/ingress-nginx/controller). - -- This involves editing of several files. So carefully follow the steps below and double check all changes with diff/grep etc., repeatedly. Mistakes here impact endusers. - -### a. Make sure your git workspace is ready - -- Get your git workspace ready - - - If not using a pre-existing fork, then Fork the repo kubernetes/ingress-nginx - - - Clone (to laptop or wherever) - - - Add upstream - - - Set upstream url to no_push - - - Checkout & switch to branch, named as per related new-release-issue-number - - - If already forked, and upstream already added, then `git fetch --all` and `git rebase upstream/main` (not origin) - - - Checkout a branch in your fork's clone - - - Perform any other diligence as needed - -- Prefer to edit only and only in your branch, in your Fork - -### b. Edit the semver tag - - [TAG](https://github.com/kubernetes/ingress-nginx/blob/main/TAG#L1) - -### c. Edit the helm Chart - - Change the below-mentioned [Fields in Chart.yaml](https://github.com/kubernetes/ingress-nginx/blob/main/charts/ingress-nginx/Chart.yaml) - - version - - appVersion - - kubeVersion (**ONLY if applicable**) - - annotations - - artifacthub.io/prerelease: "true" - - artifacthub.io/changes: | - - Replace this line and other lines under this annotation with the Changelog. One process to generate the Changelog is described below - - Install and configure GitHub cli as per the docs of gh-cli https://cli.github.com/, - - Change dir to your clone, of your fork, of the ingress-nginx project - - Run the below command and save the output to a txt file - - ``` - gh pr list -R kubernetes/ingress-nginx -s merged -L 38 -B main | cut -f1,2 | tee ~/Downloads/prlist.txt - ``` - - The -L 38 was used for 2 reasons. - - Default number of results is 30 and there were more than 30 PRs merged while releasing v1.1.1. If you see the current/soon-to-be-old changelog, you can look at the most recent PR number that has been accounted for already, and start from after that last accounted for PR. - - The other reason to use -L 38 was to omit the 39th, the 40th and the 41st line in the resulting list. These were non-relevant PRs. - - If you save the output of above command to a file called prlist.txt. It looks somewhat like this ; - - ``` - % cat ~/Downloads/prlist.txt - 8129 fix syntax in docs for multi-tls example - 8120 Update go in runner and release v1.1.1 - 8119 Update to go v1.17.6 - 8118 Remove deprecated libraries, update other libs - 8117 Fix codegen errors - 8115 chart/ghaction: set the correct permission to have access to push a release - .... - ``` - You can delete the lines, that refer to PRs of the release process itself. We only need to list the feature/bugfix PRs. You can also delete the lines that are housekeeping or not really worth mentioning in the changelog. - - you use some easy automation in bash/python/other, to get the PR-List that can be used in the changelog. For example, it's possible to use a bash scripty way, seen below, to convert those plaintext PR numbers into clickable links. - - ``` - #!/usr/bin/bash - - file="$1" - - while read -r line; do - pr_num=`echo "$line" | cut -f1` - pr_title=`echo "$line" | cut -f2` - echo "[$pr_num](https://github.com/kubernetes/ingress-nginx/pull/$pr_num) $pr_title" - done <$file - - ``` - - There was a parsing issue and path issue on MacOS, so above script had to be modified and MacOS monterey compatible script is below ; - - ``` - #!/bin/bash - - file="$1" - - while read -r line; do - pr_num=`echo "$line" | cut -f1` - pr_title=`echo "$line" | cut -f2` - echo \""[$pr_num](https://github.com/kubernetes/ingress-nginx/pull/$pr_num) $pr_title"\" - done <$file - - ``` - - If you saved the bash script content above, in a file like `$HOME/bin/prlist_to_changelog.sh`, then you could execute a command like this to get your prlist in a text file called changelog_content.txt;` - - ``` - prlist_to_changelog.sh ~/Downloads/prlist.txt | tee ~/Downloads//changelog_content.txt - ``` - -### d. Edit the values.yaml and run helm-docs - - - [Fields to edit in values.yaml](https://github.com/kubernetes/ingress-nginx/blob/main/charts/ingress-nginx/values.yaml) - - - tag - - digest - - - [helm-docs](https://github.com/norwoodj/helm-docs) is a tool that generates the README.md for a Helm chart automatically. In the CI pipeline workflow of GitHub actions (.github/workflows/ci.yaml), you can see how helm-docs is used. The CI pipeline is not designed to make commits back into the project, so we need to run helm-docs manually and commit the resulting generated README.md. You can obtain a recent version of the helm-docs binary here: https://github.com/norwoodj/helm-docs/releases. - ``` - helm-docs --chart-search-root charts - git diff charts/ingress-nginx/README.md - ``` - Take care of not leaving the helm-docs executable in your clone workspace or not committing the new README.md. - -### e. Edit the static manifests - - - Prepare to use a script to update the edit the static manifests and set the "image", "digest", "version" etc. fields to the desired value. - - - This script depends on kustomize and helm. The versions are pinned in `hack/.tool-versions` and you can use [asdf](https://github.com/asdf-vm/asdf#asdf) to install them - - - Execute the script to update static manifests using that script [hack/generate-deploy-scripts.sh](https://github.com/kubernetes/ingress-nginx/blob/main/hack/generate-deploy-scripts.sh) - - Open some of the manifests and check if the script worked properly - - - Use `grep -ir image: | less` on the deploy directory, to view for any misses by the script on image digest value or other undesired changes. The script should properly set the image and the digest fields to the desired tag and semver - - -### f. Edit the changelog - - [Changelog.md](https://github.com/kubernetes/ingress-nginx/blob/main/Changelog.md) -- Each time a release is made, a new section is added to the Changelog.md file -- A new section in the Changelog.md file consists of 3 components listed below - - the "Image" - - the "Description" - - the "PRs list" -- Look at the previous content to understand what the 3 components look like. -- You can easily get the "Image" from a yaml manifest but be sure to look at a manifest in your git clone now and not the upstream on github. This is because, if you are following this documentation, then you generated manifests with new updated digest for the image, in step 4e above. You also most likely promoted the new image in a step above. Look at the previous release section in Changelog.md. The format looks like `registry.k8s.io/ingress-nginx/controller:.......`. One example of a yaml file to look at is /deploy/static/provider/baremetal/deploy.yaml (in your git clone branch and not on the upstream). -- Next, you need to have a good overview of the changes introduced in this release and based on that you write a description. Look at previous descriptions. Ask the ingress-nginx-dev channel if required. -- And then you need to add a list of the PRs merged, since the previous release. -- One process to generate this list of PRs is already described above in step 4c. So if you are following this document, then you have done this already and very likely have retained the file containing the list of PRs, in the format that is needed. - -### g. Edit the Documentation: - -- Update the version in [docs/deploy/index.md](docs/deploy/index.md) -- Update Supported versions in the Support Versions table in the README.md -- Execute the script to update e2e docs [hack/generate-e2e-suite-doc.sh](https://github.com/kubernetes/ingress-nginx/blob/main/hack/generate-e2e-suite-doc.sh) - -### h. Update README.md - -- Update the table in README.md in the root of the project to reflect the support matrix. Add the new release version and details in there. - -## 5. RELEASE new version - -### a. Create PR - -- Open PR for releasing the new version of the Ingress-Nginx-Controller ; - - Look at this PR for how it was done before [example PR](https://github.com/kubernetes/ingress-nginx/pull/7490) - - Create a PR - -### b. Merge - -- Merge should produce manifests as well as chart -- Check - - `helm repo update` - - `helm search repo ingress-nginx` - -## 6. GitHub release - -- Release to github - -- Edit the ghpages file as needed - -## TODO -- Automate & simplify as much as possible, whenever possible, however possible diff --git a/Makefile b/Makefile deleted file mode 100644 index 0b8f1f5c2..000000000 --- a/Makefile +++ /dev/null @@ -1,282 +0,0 @@ -# Copyright 2017 The Kubernetes Authors. -# -# Licensed under the Apache License, Version 2.0 (the "License"); -# you may not use this file except in compliance with the License. -# You may obtain a copy of the License at -# -# http://www.apache.org/licenses/LICENSE-2.0 -# -# Unless required by applicable law or agreed to in writing, software -# distributed under the License is distributed on an "AS IS" BASIS, -# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -# See the License for the specific language governing permissions and -# limitations under the License. - -# Add the following 'help' target to your Makefile -# And add help text after each target name starting with '\#\#' - -.DEFAULT_GOAL:=help - -.EXPORT_ALL_VARIABLES: - -ifndef VERBOSE -.SILENT: -endif - -# set default shell -SHELL=/bin/bash -o pipefail -o errexit - -# Use the 0.0 tag for testing, it shouldn't clobber any release builds -TAG ?= $(shell cat TAG) - -# The env below is called GO_VERSION and not GOLANG_VERSION because -# the gcb image we use to build already defines GOLANG_VERSION and is a -# really old version -GO_VERSION ?= $(shell cat GOLANG_VERSION) - -# e2e settings -# Allow limiting the scope of the e2e tests. By default run everything -FOCUS ?= -# number of parallel test -E2E_NODES ?= 7 -# run e2e test suite with tests that check for memory leaks? (default is false) -E2E_CHECK_LEAKS ?= - -REPO_INFO ?= $(shell git config --get remote.origin.url) -COMMIT_SHA ?= git-$(shell git rev-parse --short HEAD) -BUILD_ID ?= "UNSET" - -PKG = k8s.io/ingress-nginx - -HOST_ARCH = $(shell which go >/dev/null 2>&1 && go env GOARCH) -ARCH ?= $(HOST_ARCH) -ifeq ($(ARCH),) - $(error mandatory variable ARCH is empty, either set it when calling the command or make sure 'go env GOARCH' works) -endif - -ifneq ($(PLATFORM),) - PLATFORM_FLAG="--platform" -endif - -REGISTRY ?= us-central1-docker.pkg.dev/k8s-staging-images/ingress-nginx - -BASE_IMAGE ?= $(shell cat NGINX_BASE) - -GOARCH=$(ARCH) - -help: ## Display this help - @awk 'BEGIN {FS = ":.*##"; printf "\nUsage:\n make \033[36m\033[0m\n"} /^[a-zA-Z0-9_-]+:.*?##/ { printf " \033[36m%-15s\033[0m %s\n", $$1, $$2 } /^##@/ { printf "\n\033[1m%s\033[0m\n", substr($$0, 5) } ' $(MAKEFILE_LIST) - -.PHONY: image -image: clean-image ## Build image for a particular arch. - echo "Building docker image ($(ARCH))..." - docker build \ - ${PLATFORM_FLAG} ${PLATFORM} \ - --no-cache \ - --build-arg BASE_IMAGE="$(BASE_IMAGE)" \ - --build-arg VERSION="$(TAG)" \ - --build-arg TARGETARCH="$(ARCH)" \ - --build-arg COMMIT_SHA="$(COMMIT_SHA)" \ - --build-arg BUILD_ID="$(BUILD_ID)" \ - -t $(REGISTRY)/controller:$(TAG) rootfs - -.PHONY: gosec -gosec: - docker run --rm -it -w /source/ -v "$(pwd)"/:/source securego/gosec:2.11.0 -exclude=G109,G601,G104,G204,G304,G306,G307 -tests=false -exclude-dir=test -exclude-dir=images/ -exclude-dir=docs/ /source/... - -.PHONY: image-chroot -image-chroot: clean-chroot-image ## Build image for a particular arch. - echo "Building docker image ($(ARCH))..." - docker build \ - --no-cache \ - --build-arg BASE_IMAGE="$(BASE_IMAGE)" \ - --build-arg VERSION="$(TAG)" \ - --build-arg TARGETARCH="$(ARCH)" \ - --build-arg COMMIT_SHA="$(COMMIT_SHA)" \ - --build-arg BUILD_ID="$(BUILD_ID)" \ - -t $(REGISTRY)/controller-chroot:$(TAG) rootfs -f rootfs/Dockerfile-chroot - -.PHONY: clean-image -clean-image: ## Removes local image - echo "removing old image $(REGISTRY)/controller:$(TAG)" - @docker rmi -f $(REGISTRY)/controller:$(TAG) || true - - -.PHONY: clean-chroot-image -clean-chroot-image: ## Removes local image - echo "removing old image $(REGISTRY)/controller-chroot:$(TAG)" - @docker rmi -f $(REGISTRY)/controller-chroot:$(TAG) || true - - -.PHONY: build -build: ## Build ingress controller, debug tool and pre-stop hook. - E2E_IMAGE=golang:$(GO_VERSION)-alpine3.21 USE_SHELL=/bin/sh build/run-in-docker.sh \ - MAC_OS=$(MAC_OS) \ - PKG=$(PKG) \ - ARCH=$(ARCH) \ - COMMIT_SHA=$(COMMIT_SHA) \ - REPO_INFO=$(REPO_INFO) \ - TAG=$(TAG) \ - build/build.sh - - -.PHONY: clean -clean: ## Remove .gocache directory. - rm -rf bin/ .gocache/ .cache/ - -.PHONY: verify-docs -verify-docs: ## Verify doc generation - hack/verify-annotation-docs.sh - -.PHONY: static-check -static-check: ## Run verification script for boilerplate, codegen, gofmt, golint, lualint and chart-lint. - @build/run-in-docker.sh \ - MAC_OS=$(MAC_OS) \ - hack/verify-all.sh - -.PHONY: golint-check -golint-check: - @build/run-in-docker.sh \ - MAC_OS=$(MAC_OS) \ - hack/verify-golint.sh - -############################### -# Tests for ingress-nginx -############################### - -.PHONY: test -test: ## Run go unit tests. - @build/run-in-docker.sh \ - PKG=$(PKG) \ - MAC_OS=$(MAC_OS) \ - ARCH=$(ARCH) \ - COMMIT_SHA=$(COMMIT_SHA) \ - REPO_INFO=$(REPO_INFO) \ - TAG=$(TAG) \ - GOFLAGS="-buildvcs=false" \ - test/test.sh - -.PHONY: lua-test -lua-test: ## Run lua unit tests. - @build/run-in-docker.sh \ - MAC_OS=$(MAC_OS) \ - test/test-lua.sh - -.PHONY: e2e-test -e2e-test: ## Run e2e tests (expects access to a working Kubernetes cluster). - @test/e2e/run-e2e-suite.sh - -.PHONY: kind-e2e-test -kind-e2e-test: ## Run e2e tests using kind. - @test/e2e/run-kind-e2e.sh - -.PHONY: kind-e2e-chart-tests -kind-e2e-chart-tests: ## Run helm chart e2e tests - @test/e2e/run-chart-test.sh - -.PHONY: e2e-test-binary -e2e-test-binary: ## Build binary for e2e tests. - @build/run-in-docker.sh \ - MAC_OS=$(MAC_OS) \ - ginkgo build ./test/e2e - -.PHONY: print-e2e-suite -print-e2e-suite: e2e-test-binary ## Prints information about the suite of e2e tests. - @build/run-in-docker.sh \ - MAC_OS=$(MAC_OS) \ - hack/print-e2e-suite.sh - -.PHONY: vet -vet: - @go vet $(shell go list ${PKG}/internal/... | grep -v vendor) - -.PHONY: check_dead_links -check_dead_links: ## Check if the documentation contains dead links. - @docker run ${PLATFORM_FLAG} ${PLATFORM} -t \ - -w /tmp \ - -v $$PWD:/tmp dkhamsing/awesome_bot:1.20.0 \ - --allow-dupe \ - --allow-redirect $(shell find $$PWD -mindepth 1 -name vendor -prune -o -name .modcache -prune -o -iname Changelog.md -prune -o -name "*.md" | sed -e "s#$$PWD/##") - -.PHONY: dev-env -dev-env: ## Starts a local Kubernetes cluster using kind, building and deploying the ingress controller. - @build/dev-env.sh - -.PHONY: dev-env-stop -dev-env-stop: ## Deletes local Kubernetes cluster created by kind. - @kind delete cluster --name ingress-nginx-dev - - - -.PHONY: live-docs -live-docs: ## Build and launch a local copy of the documentation website in http://localhost:8000 - @docker build ${PLATFORM_FLAG} ${PLATFORM} \ - --no-cache \ - -t ingress-nginx-docs .github/actions/mkdocs - @docker run ${PLATFORM_FLAG} ${PLATFORM} --rm -it \ - -p 8000:8000 \ - -v ${PWD}:/docs \ - --entrypoint /bin/bash \ - ingress-nginx-docs \ - -c "pip install -r /docs/docs/requirements.txt && mkdocs serve --dev-addr=0.0.0.0:8000" - -.PHONY: misspell -misspell: ## Check for spelling errors. - @go install github.com/client9/misspell/cmd/misspell@latest - misspell \ - -locale US \ - -error \ - cmd/* internal/* deploy/* docs/* design/* test/* README.md - -.PHONY: run-ingress-controller -run-ingress-controller: ## Run the ingress controller locally using a kubectl proxy connection. - @build/run-ingress-controller.sh - -.PHONY: ensure-buildx -ensure-buildx: - ./hack/init-buildx.sh - -.PHONY: show-version -show-version: - echo -n $(TAG) - -PLATFORMS ?= amd64 arm arm64 -BUILDX_PLATFORMS ?= linux/amd64,linux/arm,linux/arm64 - -.PHONY: release # Build a multi-arch docker image -release: ensure-buildx clean - echo "Building binaries..." - $(foreach PLATFORM,$(PLATFORMS), echo -n "$(PLATFORM)..."; ARCH=$(PLATFORM) make build;) - - echo "Building and pushing ingress-nginx image...$(BUILDX_PLATFORMS)" - - docker buildx build \ - --no-cache \ - $(MAC_DOCKER_FLAGS) \ - --push \ - --pull \ - --progress plain \ - --platform $(BUILDX_PLATFORMS) \ - --build-arg BASE_IMAGE="$(BASE_IMAGE)" \ - --build-arg VERSION="$(TAG)" \ - --build-arg COMMIT_SHA="$(COMMIT_SHA)" \ - --build-arg BUILD_ID="$(BUILD_ID)" \ - -t $(REGISTRY)/controller:$(TAG) rootfs - - docker buildx build \ - --no-cache \ - $(MAC_DOCKER_FLAGS) \ - --push \ - --pull \ - --progress plain \ - --platform $(BUILDX_PLATFORMS) \ - --build-arg BASE_IMAGE="$(BASE_IMAGE)" \ - --build-arg VERSION="$(TAG)" \ - --build-arg COMMIT_SHA="$(COMMIT_SHA)" \ - --build-arg BUILD_ID="$(BUILD_ID)" \ - -t $(REGISTRY)/controller-chroot:$(TAG) rootfs -f rootfs/Dockerfile-chroot - -.PHONY: build-docs -build-docs: - pip install -r docs/requirements.txt - mkdocs build --config-file mkdocs.yml diff --git a/NEW_CONTRIBUTOR.md b/NEW_CONTRIBUTOR.md deleted file mode 100644 index c9668430c..000000000 --- a/NEW_CONTRIBUTOR.md +++ /dev/null @@ -1,852 +0,0 @@ -## New Contributor Tips - -Welcome to the Ingress Nginx new contributor tips. -This guide briefly outlines the necessary knowledge & tools, required to start working on Ingress-NGINX Issues. - -### Prerequisites -- Basic understanding of linux -- Familiarity with the command line on linux -- OSI Model(Links below) - -### Introduction -It all starts with the OSI model... -> The Open Systems Interconnection (OSI) model describes seven layers that computer systems use to communicate over a network. It was the first standard model for network communications, adopted by all major computer and telecommunication companies - -![Describes the 7 Layers of the OSI Model](https://i.imgur.com/qF0KjBq.png) - -#### Reading material for OSI Model -[OSI Model CertificationKits](https://www.certificationkits.com/cisco-certification/cisco-ccna-640-802-exam-certification-guide/cisco-ccna-the-osi-model/) - -### Approaching the problem - - -Not everybody knows everything. But the factors that help are a love/passion for this to begin. But to move forward, it's the approach and not the knowledge that sustains prolonged joy, while working on issues. If the approach is simple and powered by good-wishes-for-community, then info & tools are forthcoming and easy. - -Here we take a bird's eye-view of the hops in the network plumbing, that a packet takes, from source to destination, when we run `curl`, from a laptop to a nginx webserver process, running in a container, inside a pod, inside a Kubernetes cluster, created using `kind` or `minikube` or any other cluster-management tool. - -### [Kind](https://kind.sigs.k8s.io/) cluster example on a Linux Host - -#### TL;DR -The destination of the packet from the curl command, is looked up, in the `routing table`. Based on the route, the packet first travels to the virtual bridge `172.18.0.1` interface, created by docker, when we created the kind cluster on a laptop. Next the packet is forwarded to `172.18.0.2`(See below on how we got this IP address), within the kind cluster. The `kube-proxy` container creates iptables rules that make sure the packet goes to the correct pod ip in this case `10.244.0.5` - -Command: -``` -# docker ps -CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES -230e7246a32c kindest/node:v1.24.1 "/usr/local/bin/entr…" 2 weeks ago Up 54 seconds 127.0.0.1:38143->6443/tcp kind-control-plane - -# docker inspect kind-control-plane -f '{{ .NetworkSettings.Networks.kind.IPAddress }}' -172.18.0.2 - -``` - - - -If this part is confusing, you would first need to understand what a [bridge](https://tldp.org/HOWTO/BRIDGE-STP-HOWTO/what-is-a-bridge.html) is and what [docker network](https://docs.docker.com/network/) is. - - - -#### The journey of a curl packet. -Let's begin with creating a [Kind](https://kind.sigs.k8s.io/docs/user/quick-start/) Cluster on your laptop -``` -# kind create cluster -``` -This will create a cluster called `kind`, to view the clusters type -``` -# kind get clusters    -kind -``` -Kind ships with `kubectl`, so we can use that to communicate with our clusters. -``` -# kubectl get no -o wide    -NAME STATUS ROLES AGE VERSION INTERNAL-IP EXTERNAL-IP OS-IMAGE KERNEL-VERSION CONTAINER-RUNTIME -kind-control-plane Ready control-plane 5d23h v1.24.1 172.18.0.2 Ubuntu 21.10 5.18.12-arch1-1 containerd://1.6.4 -``` -Kind creates a cluster using docker container as nodes, it does this using [containerd](https://containerd.io/) within the docker container. -The concept of Docker in Docker is very important here. - -To start with simply create a nginx deployment using `kubectl`. -``` -# kubectl create deployment nginx --image nginx:alpine --port=80 -deployment.apps/nginx created -``` -Then we expose this as a NodePort Service. -``` -# kubectl expose deployment/nginx --type=NodePort -service/nginx-new exposed -``` -Command: Now we can see that the service has been exposed. -``` -# kubectl get svc -o wide -NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE SELECTOR -nginx NodePort 10.96.176.241 80:32329/TCP 4d8h app=nginx -``` -Output Relevance: From the above output, we can see that our nginx pod is being exposed as the `NodePort` service type, and now we can curl the Node IP `172.18.0.2` with the exposed port `32329` - -Command: The pod has an IP as shown below -``` -# kubectl get po -o wide   -NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES -nginx-6c8b449b8f-pdvdk 1/1 Running 1 (32h ago) 4d8h 10.244.0.5 kind-control-plane -``` - -Command: We can use `curl` on the laptop to view the nginx container that is running on port `32329`. - -``` -# curl 172.18.0.2:32329 - - - - -Welcome to nginx! - - - -

Welcome to nginx!

-

If you see this page, the nginx web server is successfully installed and -working. Further configuration is required.

- -

For online documentation and support please refer to -nginx.org.
-Commercial support is available at -nginx.com.

- -

Thank you for using nginx.

- - -``` -Now, we can check the ip interfaces as well subnets for our system is connected to: - -``` -$ ifconfig -ethbr0: flags=4163 mtu 1500 - inet 192.168.31.9 netmask 255.255.255.0 broadcast 192.168.31.255 - inet6 fe80::7530:9ae5:3e8d:e45a prefixlen 64 scopeid 0x20 - ether 2e:90:b3:e8:52:5b txqueuelen 1000 (Ethernet) - RX packets 31220566 bytes 44930589084 (41.8 GiB) - RX errors 0 dropped 0 overruns 0 frame 0 - TX packets 18104006 bytes 1757183680 (1.6 GiB) - TX errors 0 dropped 0 overruns 0 carrier 0 collisions 0 - -br-2fffe5cd5d9e: flags=4163 mtu 1500 - inet 172.18.0.1 netmask 255.255.0.0 broadcast 172.18.255.255 - inet6 fc00:f853:ccd:e793::1 prefixlen 64 scopeid 0x0 - inet6 fe80::42:12ff:fed3:8fb0 prefixlen 64 scopeid 0x20 - inet6 fe80::1 prefixlen 64 scopeid 0x20 - ether 02:42:12:d3:8f:b0 txqueuelen 0 (Ethernet) - RX packets 3547 bytes 414792 (405.0 KiB) - RX errors 0 dropped 0 overruns 0 frame 0 - TX packets 6267 bytes 8189931 (7.8 MiB) - TX errors 0 dropped 0 overruns 0 carrier 0 collisions 0 -docker0: flags=4099 mtu 1500 - inet 172.17.0.1 netmask 255.255.0.0 broadcast 172.17.255.255 - inet6 fe80::42:a2ff:fe09:5edb prefixlen 64 scopeid 0x20 - ether 02:42:a2:09:5e:db txqueuelen 0 (Ethernet) - RX packets 14 bytes 2143 (2.0 KiB) - RX errors 0 dropped 0 overruns 0 frame 0 - TX packets 40 bytes 6406 (6.2 KiB) - TX errors 0 dropped 0 overruns 0 carrier 0 collisions 0 -``` -From the above output we can see that, there are two bridges connected to our systems network interface,one is the docker default bridge`docker0` and the other created by kind -`br-2fffe5cd5d9e`. - -Since kind creates nodes as containers, this is easily accessible via `docker ps`. -``` -$ docker ps - -CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES -230e7246a32c kindest/node:v1.24.1 "/usr/local/bin/entr…" 6 days ago Up 33 hours 127.0.0.1:38143->6443/tcp kind-control-plane -``` -If we do a docker `exec` we can enter the container, we can also see the network interfaces within the container. -``` -# docker exec -it 230e7246a32c bash - -# root@kind-control-plane:/# ip a -1: lo: mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1000 - link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00 - inet 127.0.0.1/8 scope host lo - valid_lft forever preferred_lft forever - inet6 ::1/128 scope host - valid_lft forever preferred_lft forever -2: vethdb0d1da1@if2: mtu 1500 qdisc noqueue state UP group default - link/ether a2:a1:ce:08:d2:39 brd ff:ff:ff:ff:ff:ff link-netns cni-ddc25710-030a-cc05-c600-5a183fae01f7 - inet 10.244.0.1/32 scope global vethdb0d1da1 - valid_lft forever preferred_lft forever -3: veth4d76603f@if2: mtu 1500 qdisc noqueue state UP group default - link/ether 9a:9b:6b:3e:d1:53 brd ff:ff:ff:ff:ff:ff link-netns cni-f2270000-8fc8-6f89-e56b-4759ae10a084 - inet 10.244.0.1/32 scope global veth4d76603f - valid_lft forever preferred_lft forever -4: vethcc2586d6@if2: mtu 1500 qdisc noqueue state UP group default - link/ether 52:f9:20:63:62:a2 brd ff:ff:ff:ff:ff:ff link-netns cni-97e337cd-1322-c1fa-7523-789af94f397f - inet 10.244.0.1/32 scope global vethcc2586d6 - valid_lft forever preferred_lft forever -5: veth783189a9@if2: mtu 1500 qdisc noqueue state UP group default - link/ether ba:e1:55:1f:6f:12 brd ff:ff:ff:ff:ff:ff link-netns cni-90849001-668a-03d2-7d9e-192de79ccc59 - inet 10.244.0.1/32 scope global veth783189a9 - valid_lft forever preferred_lft forever -6: veth79c98c12@if2: mtu 1500 qdisc noqueue state UP group default - link/ether 22:05:55:c7:86:e9 brd ff:ff:ff:ff:ff:ff link-netns cni-734dfac9-9f70-ab33-265b-21569d90312a - inet 10.244.0.1/32 scope global veth79c98c12 - valid_lft forever preferred_lft forever -7: veth5b221c83@if2: mtu 1500 qdisc noqueue state UP group default - link/ether 92:3f:04:54:72:5a brd ff:ff:ff:ff:ff:ff link-netns cni-d8f6666b-1cfb-ef08-4bf8-237a7fc32da2 - inet 10.244.0.1/32 scope global veth5b221c83 - valid_lft forever preferred_lft forever -8: vethad630fb8@if2: mtu 1500 qdisc noqueue state UP group default - link/ether 32:78:ec:f6:01:ea brd ff:ff:ff:ff:ff:ff link-netns cni-6cb3c179-cb17-3b81-2051-27231c44a3c4 - inet 10.244.0.1/32 scope global vethad630fb8 - valid_lft forever preferred_lft forever -9: veth573a629b@if2: mtu 1500 qdisc noqueue state UP group default - link/ether e2:57:f8:c9:bc:94 brd ff:ff:ff:ff:ff:ff link-netns cni-d2dbb903-8310-57b4-7ba4-9f353dbc79dc - inet 10.244.0.1/32 scope global veth573a629b - valid_lft forever preferred_lft forever -10: eth0@if11: mtu 1500 qdisc noqueue state UP group default - link/ether 02:42:ac:12:00:02 brd ff:ff:ff:ff:ff:ff link-netnsid 0 - inet 172.18.0.2/16 brd 172.18.255.255 scope global eth0 - valid_lft forever preferred_lft forever - inet6 fc00:f853:ccd:e793::2/64 scope global nodad - valid_lft forever preferred_lft forever - inet6 fe80::42:acff:fe12:2/64 scope link - valid_lft forever preferred_lft forever -11: vethd7368e27@if2: mtu 1500 qdisc noqueue state UP group default - link/ether 8a:74:ec:f6:d6:c9 brd ff:ff:ff:ff:ff:ff link-netns cni-7c7eb9cd-bbb1-65b0-0480-b8f1265f2f36 - inet 10.244.0.1/32 scope global vethd7368e27 - valid_lft forever preferred_lft forever -12: veth7cadbf2b@if2: mtu 1500 qdisc noqueue state UP group default - link/ether 12:48:10:b7:b8:f5 brd ff:ff:ff:ff:ff:ff link-netns cni-b39e37b5-1bc8-626a-a553-a0be2f94a117 - inet 10.244.0.1/32 scope global veth7cadbf2b - valid_lft forever preferred_lft forever - -``` -When we run `curl 172.18.0.2:32329` on the laptop it first needs to figure out where `172.18.0.2`, to do this it refers to the host routing table. -``` -sudo netstat -rn    main  -Kernel IP routing table -Destination Gateway Genmask Flags MSS Window irtt Iface -0.0.0.0 192.168.31.1 0.0.0.0 UG 0 0 0 ethbr0 -172.17.0.0 0.0.0.0 255.255.0.0 U 0 0 0 docker0 -172.18.0.0 0.0.0.0 255.255.0.0 U 0 0 0 br-2fffe5cd5d9e -172.19.0.0 0.0.0.0 255.255.0.0 U 0 0 0 br-be5b544733a3 -192.168.31.0 0.0.0.0 255.255.255.0 U 0 0 0 ethbr0 -192.168.31.0 0.0.0.0 255.255.255.0 U 0 0 0 ethbr0 -192.168.39.0 0.0.0.0 255.255.255.0 U 0 0 0 virbr2 -192.168.122.0 0.0.0.0 255.255.255.0 U 0 0 0 virbr0 -``` -Output Relevance: From the above output, you can see that the `iface`(Interface) for `172.18.0.0` is `br-2fffe5cd5d9e`, which means traffic that needs to go to `172.18.0.0` will go through `br-2fffe5cd5d9e` which is created by docker for the kind container (this is the node in case of kind cluster). - -Now we need to understand how the packet travels from the container interface to the pod with IP `10.244.0.5`. The component that handles this is called kube-proxy - -So what exactly is [kube-proxy](https://kubernetes.io/docs/concepts/overview/components/#kube-proxy): -> Kube-Proxy is a network proxy that runs on each node in your cluster, implementing part of the Kubernetes Service concept. -kube-proxy maintains network rules on nodes. These network rules allow network communication to your Pods from network sessions inside or outside of your cluster - -So, as we can see that kube proxy handles the network rules required to aid the communication to the pods, we will look at the [iptables](https://linux.die.net/man/8/iptables) -> `iptables` is a command line interface used to set up and maintain tables for the Netfilter firewall for IPv4, included in the Linux kernel. The firewall matches packets with rules defined in these tables and then takes the specified action on a possible match. Tables is the name for a set of chains - -Command: -``` -# iptables -t nat -L PREROUTING -n -Chain PREROUTING (policy ACCEPT) -target prot opt source destination -KUBE-SERVICES all -- 0.0.0.0/0 0.0.0.0/0 /* kubernetes service portals */ -DOCKER_OUTPUT all -- 0.0.0.0/0 172.18.0.1 -CNI-HOSTPORT-DNAT all -- 0.0.0.0/0 0.0.0.0/0 ADDRTYPE match dst-type LOCAL -``` - -``` -# iptables-save | grep PREROUTING --A PREROUTING -m comment --comment "kubernetes service portals" -j KUBE-SERVICES -``` -Output Relevance: -> -A: append new iptable rule -> -j: jump to the target -> KUBE-SERVICES: target - -> The above output appends a new rule for PREROUTING which every network packet will go through first as they try to access any kubernetes service - - -What is `PREROUTING` in iptables? ->PREROUTING: This chain is used to make any routing related decisions before (PRE) sending any packets - -To dig in further we need to go to the target, `KUBE-SERVICES` for our nginx service. -``` -# iptables -t nat -L KUBE-SERVICES -n| grep nginx -KUBE-SVC-2CMXP7HKUVJN7L6M tcp -- 0.0.0.0/0 10.96.176.241 /* default/nginx cluster IP */ tcp dpt:80 -``` -Command: -``` -# iptables -t nat -L KUBE-SVC-2CMXP7HKUVJN7L6M -n -Chain KUBE-SVC-2CMXP7HKUVJN7L6M (2 references) -target prot opt source destination -KUBE-MARK-MASQ tcp -- !10.244.0.0/16 10.96.176.241 /* default/nginx cluster IP */ tcp dpt:80 -KUBE-SEP-4IEO3WJHPKXV3AOH all -- 0.0.0.0/0 0.0.0.0/0 /* default/nginx -> 10.244.0.5:80 */ - -# iptables -t nat -L KUBE-MARK-MASQ -n -Chain KUBE-MARK-MASQ (31 references) -target prot opt source destination -MARK all -- 0.0.0.0/0 0.0.0.0/0 MARK or 0x4000 - -# iptables -t nat -L KUBE-SEP-4IEO3WJHPKXV3AOH -n -Chain KUBE-SEP-4IEO3WJHPKXV3AOH (1 references) -target prot opt source destination -KUBE-MARK-MASQ all -- 10.244.0.5 0.0.0.0/0 /* default/nginx */ -DNAT tcp -- 0.0.0.0/0 0.0.0.0/0 /* default/nginx */ tcp to:10.244.0.5:80 -``` - - -``` -iptables-save | grep 10.96.176.241 - --A KUBE-SERVICES -d 10.96.176.241/32 -p tcp -m comment --comment "default/nginx cluster IP" -m tcp --dport 80 -j KUBE-SVC-2CMXP7HKUVJN7L6M --A KUBE-SVC-2CMXP7HKUVJN7L6M ! -s 10.244.0.0/16 -d 10.96.176.241/32 -p tcp -m comment --comment "default/nginx cluster IP" -m tcp --dport 80 -j KUBE-MARK-MASQ -``` - -As you can see the rules added by `kube-proxy` helps the packet reach to the destination service. - -### Minikube KVM VM Example on Linux - -#### TL;DR -Now we look at the curl packet journey on minikube. The `routing table` is looked up to know the destination of the curl packet. The packet then first travels to the virtual bridge `192.168.39.1`, created by minikube kvm2 driver, when we created the minikube cluster, on a linux laptop. Then this packet is forwarded to `192.168.39.57`, within the minikube VM. We have docker containers running in the VM. Among them, the `kube-proxy` container creates iptables rules that make sure the packet goes to the correct pod ip, in this case `172.17.0.4`. - - -To begin with the minikube example, we first need to create a minikube cluster on a linux laptop. In this example I'll be using the `kvm2` driver option for `minikube start` command, as default. - -``` -minikube start -😄 minikube v1.26.0 on Arch "rolling" -🆕 Kubernetes 1.24.2 is now available. If you would like to upgrade, specify: --kubernetes-version=v1.24.2 -✨ Using the kvm2 driver based on existing profile -👍 Starting control plane node minikube in cluster minikube -🏃 Updating the running kvm2 "minikube" VM ... -🐳 Preparing Kubernetes v1.23.3 on Docker 20.10.12 ... - ▪ kubelet.housekeeping-interval=5m -🔎 Verifying Kubernetes components... - ▪ Using image registry.k8s.io/ingress-nginx/kube-webhook-certgen:v1.1.1 - ▪ Using image registry.k8s.io/ingress-nginx/kube-webhook-certgen:v1.1.1 - ▪ Using image registry.k8s.io/ingress-nginx/controller:v1.2.1 - ▪ Using image gcr.io/k8s-minikube/storage-provisioner:v5 -🔎 Verifying ingress addon... -🌟 Enabled addons: ingress, storage-provisioner, default-storageclass -🏄 Done! kubectl is now configured to use "minikube" cluster and "default" namespace by default -``` -**Note**: The KVM driver provides a lot of options on customizing the cluster, however that is currently beyond the scope of this guide. - -Next we will get the Node IP. -``` -$ kubectl get no -o wide   -NAME STATUS ROLES AGE VERSION INTERNAL-IP EXTERNAL-IP OS-IMAGE KERNEL-VERSION CONTAINER-RUNTIME -minikube Ready control-plane,master 25d v1.23.3 192.168.39.57 Buildroot 2021.02.4 4.19.202 docker://20.10.12 -``` -Minikube creates a Virtual Machine using the KVM2 driver(Other drivers such as Virtualbox do exist see `minikube start --help` for more information ), you should be able to see this with the following output(You may have to use sudo to get this output) - -``` -$ virsh --connect qemu:///system list - Id Name State --------------------------- - 1 minikube running - - or - - $ sudo virsh list - Id Name State --------------------------- - 1 minikube running - -``` - -Moving on, simply create a nginx deployment using `kubectl`. -``` -# kubectl create deployment nginx --image nginx:alpine --port=80 -deployment.apps/nginx created -``` -Then we expose this as a NodePort Service. -``` -# kubectl expose deployment/nginx --type=NodePort -service/nginx-new exposed -``` -Command: Now we can see that the service has been exposed. -``` -# kubectl get svc -o wide    main  -NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE SELECTOR -kubernetes ClusterIP 10.96.0.1 443/TCP 25d -nginx-minikube NodePort 10.97.44.4 80:32007/TCP 45h app=nginx-minikube -``` -Output Relevance: From the above output, we can see that our nginx pod is being exposed as the `NodePort` service type, and now we can curl the Node IP `192.168.39.57` with the exposed port `32007` - -Command: The pod has an IP as shown below -``` -# kubectl get po -o wide -NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES -nginx-minikube-7546f79bd8-x88bt 1/1 Running 3 (43m ago) 45h 172.17.0.4 minikube - -``` - -Command: We can use `curl` on the laptop to view the nginx container that is running on port `32007`. -``` -curl 192.168.39.57:32007 - - - -Welcome to nginx! - - - -

Welcome to nginx!

-

If you see this page, the nginx web server is successfully installed and -working. Further configuration is required.

- -

For online documentation and support please refer to -nginx.org.
-Commercial support is available at -nginx.com.

- -

Thank you for using nginx.

- - -``` - -So, how does this packet travel, lets dive in. -We can check the ip interfaces as well subnets for our system is connected to: -``` -$ ifconfig -virbr2: flags=4163 mtu 1500 - inet 192.168.39.1 netmask 255.255.255.0 broadcast 192.168.39.255 - ether 52:54:00:19:29:93 txqueuelen 1000 (Ethernet) - RX packets 5132 bytes 1777099 (1.6 MiB) - RX errors 0 dropped 0 overruns 0 frame 0 - TX packets 6113 bytes 998530 (975.1 KiB) - TX errors 0 dropped 0 overruns 0 carrier 0 collisions 0 - -virbr0: flags=4163 mtu 1500 - inet 192.168.122.1 netmask 255.255.255.0 broadcast 192.168.122.255 - ether 52:54:00:48:ee:35 txqueuelen 1000 (Ethernet) - RX packets 23648 bytes 1265196 (1.2 MiB) - RX errors 0 dropped 0 overruns 0 frame 0 - TX packets 40751 bytes 60265308 (57.4 MiB) - TX errors 0 dropped 0 overruns 0 carrier 0 collisions 0 -``` -Output Relevance: From the above output you can see there are two Virtual Bridges created by minikube when we created the cluster on the network. Here, `virbr0` is the default NAT network bridge while `virbr2` is a isolated network bridge on which the pods run. - -Minikube creates a Virtual Machine, to enter the virtual machine we can simply do: -``` -# minikube ssh -``` - -The interfaces within the Virtual Machine are as follows. -``` -docker0 Link encap:Ethernet HWaddr 02:42:03:24:26:78 - inet addr:172.17.0.1 Bcast:172.17.255.255 Mask:255.255.0.0 - UP BROADCAST RUNNING MULTICAST MTU:1500 Metric:1 - RX packets:31478 errors:0 dropped:0 overruns:0 frame:0 - TX packets:36704 errors:0 dropped:0 overruns:0 carrier:0 - collisions:0 txqueuelen:0 - RX bytes:3264056 (3.1 MiB) TX bytes:14061883 (13.4 MiB) - -eth0 Link encap:Ethernet HWaddr 52:54:00:C9:3A:73 - inet addr:192.168.39.57 Bcast:192.168.39.255 Mask:255.255.255.0 - UP BROADCAST RUNNING MULTICAST MTU:1500 Metric:1 - RX packets:8245 errors:0 dropped:9 overruns:0 frame:0 - TX packets:3876 errors:0 dropped:0 overruns:0 carrier:0 - collisions:0 txqueuelen:1000 - RX bytes:812006 (792.9 KiB) TX bytes:1044724 (1020.2 KiB) - -eth1 Link encap:Ethernet HWaddr 52:54:00:7B:37:79 - inet addr:192.168.122.35 Bcast:192.168.122.255 Mask:255.255.255.0 - UP BROADCAST RUNNING MULTICAST MTU:1500 Metric:1 - RX packets:4459 errors:0 dropped:9 overruns:0 frame:0 - TX packets:201 errors:0 dropped:0 overruns:0 carrier:0 - collisions:0 txqueuelen:1000 - RX bytes:298528 (291.5 KiB) TX bytes:25813 (25.2 KiB) - -lo Link encap:Local Loopback - inet addr:127.0.0.1 Mask:255.0.0.0 - UP LOOPBACK RUNNING MTU:65536 Metric:1 - RX packets:946772 errors:0 dropped:0 overruns:0 frame:0 - TX packets:946772 errors:0 dropped:0 overruns:0 carrier:0 - collisions:0 txqueuelen:1000 - RX bytes:213465460 (203.5 MiB) TX bytes:213465460 (203.5 MiB) - -vetha4f1dc5 Link encap:Ethernet HWaddr 3E:1C:FE:C9:75:86 - UP BROADCAST RUNNING MULTICAST MTU:1500 Metric:1 - RX packets:10 errors:0 dropped:0 overruns:0 frame:0 - TX packets:16 errors:0 dropped:0 overruns:0 carrier:0 - collisions:0 txqueuelen:0 - RX bytes:1413 (1.3 KiB) TX bytes:955 (955.0 B) - -vethbf35613 Link encap:Ethernet HWaddr BA:31:7D:AE:2A:BF - UP BROADCAST RUNNING MULTICAST MTU:1500 Metric:1 - RX packets:3526 errors:0 dropped:0 overruns:0 frame:0 - TX packets:3934 errors:0 dropped:0 overruns:0 carrier:0 - collisions:0 txqueuelen:0 - RX bytes:342408 (334.3 KiB) TX bytes:380193 (371.2 KiB) - -vethe092a51 Link encap:Ethernet HWaddr 8A:37:D3:D9:D9:0E - UP BROADCAST RUNNING MULTICAST MTU:1500 Metric:1 - RX packets:9603 errors:0 dropped:0 overruns:0 frame:0 - TX packets:11151 errors:0 dropped:0 overruns:0 carrier:0 - collisions:0 txqueuelen:0 - RX bytes:1199235 (1.1 MiB) TX bytes:5449408 (5.1 MiB) -``` -Output Relevance: Here we have the Virtual Ethernet and we have docker bridges too since docker runs within the Virtual Machine. - -When we do a `curl` to `192.168.39.57:32007` on the laptop the packet first goes to the route table -``` -Destination Gateway Genmask Flags MSS Window irtt Iface -0.0.0.0 192.168.31.1 0.0.0.0 UG 0 0 0 ethbr0 -172.17.0.0 0.0.0.0 255.255.0.0 U 0 0 0 docker0 -172.18.0.0 0.0.0.0 255.255.0.0 U 0 0 0 br-2fffe5cd5d9e -172.19.0.0 0.0.0.0 255.255.0.0 U 0 0 0 br-be5b544733a3 -192.168.31.0 0.0.0.0 255.255.255.0 U 0 0 0 ethbr0 -192.168.31.0 0.0.0.0 255.255.255.0 U 0 0 0 ethbr0 -192.168.39.0 0.0.0.0 255.255.255.0 U 0 0 0 virbr2 -192.168.122.0 0.0.0.0 255.255.255.0 U 0 0 0 virbr0 -``` -Output Relevance: As you can see multiple routes are defined here, of which our Virtual Machine Node IP(192.168.39.57) is also shown in the table, so the packet now knows where it has to go. - -With that clear we now know how the packet goes from the laptop to the virtual bridge and then enters the Virtual Machine. - -Inside the virtual machine, [kube-proxy](https://kubernetes.io/docs/concepts/overview/components/#kube-proxy) handles the routing using iptables. - -So what exactly is [kube-proxy](https://kubernetes.io/docs/concepts/overview/components/#kube-proxy)(For those who skipped the kind example): -> Kube-Proxy is a network proxy that runs on each node in your cluster, implementing part of the Kubernetes Service concept. -kube-proxy maintains network rules on nodes. These network rules allow network communication to your Pods from network sessions inside or outside of your cluster - -So, as we can see that kube proxy handles the network rules required to aid the communication to the pods, we will look at the [iptables](https://linux.die.net/man/8/iptables) -> `iptables` is a command line interface used to set up and maintain tables for the Netfilter firewall for IPv4, included in the Linux kernel. The firewall matches packets with rules defined in these tables and then takes the specified action on a possible match. Tables is the name for a set of chains - -Command: - -``` -# minikube ssh   - _ _ - _ _ ( ) ( ) - ___ ___ (_) ___ (_)| |/') _ _ | |_ __ -/' _ ` _ `\| |/' _ `\| || , < ( ) ( )| '_`\ /'__`\ -| ( ) ( ) || || ( ) || || |\`\ | (_) || |_) )( ___/ -(_) (_) (_)(_)(_) (_)(_)(_) (_)`\___/'(_,__/'`\____) - -$ sudo iptables -t nat -L PREROUTING -n -Chain PREROUTING (policy ACCEPT) -target prot opt source destination -KUBE-SERVICES all -- 0.0.0.0/0 0.0.0.0/0 /* kubernetes service portals */ -DOCKER all -- 0.0.0.0/0 0.0.0.0/0 ADDRTYPE match dst-type LOCAL - -$ iptables-save | grep PREROUTING --A PREROUTING -m comment --comment "kubernetes service portals" -j KUBE-SERVICES - -``` - -Output Relevance: -> -A: append new iptable rule -> -j: jump to the target -> KUBE-SERVICES: target - -> The above output appends a new rule for PREROUTING which every network packet will go through first as they try to access any kubernetes service - - -What is `PREROUTING` in iptables? ->PREROUTING: This chain is used to make any routing related decisions before (PRE) sending any packets - -To dig in further we need to go to the target, `KUBE-SERVICES` for our nginx service. -``` -# iptables -t nat -L KUBE-SERVICES -n| grep nginx -KUBE-SVC-NRDCJV6H42SDXARP tcp -- 0.0.0.0/0 10.97.44.4 /* default/nginx-minikube cluster IP */ tcp dpt:80 -``` -Command: -``` -$ sudo iptables -t nat -L| grep KUBE-SVC-NRDCJV6H42SDXARP -KUBE-SVC-NRDCJV6H42SDXARP tcp -- 0.0.0.0/0 0.0.0.0/0 /* default/nginx-minikube */ tcp dpt:32007 -KUBE-SVC-NRDCJV6H42SDXARP tcp -- 0.0.0.0/0 10.97.44.4 /* default/nginx-minikube cluster IP */ tcp dpt:80 - -$ sudo iptables -t nat -L KUBE-MARK-MASQ -n -Chain KUBE-MARK-MASQ (19 references) -target prot opt source destination -MARK all -- 0.0.0.0/0 0.0.0.0/0 MARK or 0x4000 - -sudo iptables-save | grep 172.17.0.4 --A KUBE-SEP-AHQQ7ZFXMEBNX76B -s 172.17.0.4/32 -m comment --comment "default/nginx-minikube" -j KUBE-MARK-MASQ --A KUBE-SEP-AHQQ7ZFXMEBNX76B -p tcp -m comment --comment "default/nginx-minikube" -m tcp -j DNAT --to-destination 172.17.0.4:80 -``` -As you can see the rules added by kube-proxy helps the packet reach to the destination service. - - -### Connection termination -Connection termination is a type of event that occurs when there are load balancers present, the information for this is quite scarce, however I've found the following article, [IBM - Network Termination](https://www.ibm.com/docs/en/sva/9.0.4?topic=balancer-network-termination) that describes what it means by connection termination between clients(laptop) and server(load balancer) and the various other services. - -### Different types of connection errors. -The following article on [TCP/IP errors](https://www.ibm.com/docs/en/db2/11.1?topic=message-tcpip-errors) has a list of the important tcp timeout errors that we need to know. - - -| Common TCP/IP errors | Meaning | -| -------- | -------- | -| Resource temporarily unavailable.| Self-explanatory. | -| No space is left on a device or system table.|The disk partition is full| -|No route to the host is available.|The routing table doesn't know where to route the packet.| -|Connection was reset by the partner.|This usually means the packet was dropped as soon as it reached the server can be due to a firewall.| -|The connection was timed out.|This indicates the firewall blocking your connection or the connection took too long.| - -## OSI Model Layer 7 (Application Layer) - -[What is layer 7?](https://www.cloudflare.com/learning/ddos/what-is-layer-7/) -#### Summary -Layer 7 refers to the seventh and topmost layer of the Open Systems Interconnect (OSI) Model known as the application layer. This is the highest layer which supports end-user processes and applications. Layer 7 identifies the communicating parties and the quality of service between them, considers privacy and user authentication, as well as identifies any constraints on the data syntax. This layer is wholly application-specific. - - -## Setting up Ingress-Nginx Controller - -Since we are doing this on our local laptop, we are going to use the following tools: -- [Minikube using KVM driver](https://minikube.sigs.k8s.io/docs/start/) - The host is linux-based in our example -- [Metallb](https://metallb.universe.tf/) - Baremetal load-balancer. -- [KVM](https://www.linux-kvm.org/page/Main_Page) / [Oracle VirtualBox](https://www.virtualbox.org/wiki/Downloads) / [VMWare](https://www.vmware.com/in/products/workstation-pro.html) - - -### So let's begin with Metallb and Ingress-Nginx setup. - -For setting up metallb, we are going to follow the below steps: - - - To begin the installation, we will execute: -``` -minikube start -``` -- To install Metallb, one can install it using the [manifest](https://metallb.universe.tf/installation/#installation-by-manifest) or by using [helm](https://metallb.universe.tf/installation/#installation-with-helm), for now we will use the Manifest method: -``` -kubectl apply -f https://raw.githubusercontent.com/metallb/metallb/v0.13.4/config/manifests/metallb-native.yaml -``` - -- We need to now configure Metallb, we are using [Layer 2 configuration](https://metallb.universe.tf/configuration/#announce-the-service-ips), let's head over to the [Metallb Configuration](https://metallb.universe.tf/configuration/) website, here you will see how to setup metallb. ->Layer 2 mode does not require the IPs to be bound to the network interfaces of your worker nodes. It works by responding to ARP requests on your local network directly, to give the machine’s MAC address to clients. -In order to advertise the IP coming from an IPAddressPool, an L2Advertisement instance must be associated to the IPAddressPool. -- We have modified the IP address pool so that our loadbalancer knows which subnet to choose an IP from.Since we have only one minikube IP we need to modify the code given in the documentation. -Save this as `metallb-config.yaml`: -``` -apiVersion: metallb.io/v1beta1 -kind: IPAddressPool -metadata: - name: first-pool - namespace: metallb-system -spec: - addresses: - # The configuration website show's you this - - #- 192.168.10.0/24 - #- 192.168.9.1-192.168.9.5 - #- fc00:f853:0ccd:e799::/124 - - # We are going to change this to `minikube ip` as such - - 192.168.39.57/32 -``` -Now deploy it using `kubectl` -``` -kubectl apply -f metallb-config.yaml -``` -- Now that metallb is setup, let's install [ingress-nginx](https://kubernetes.github.io/ingress-nginx/deploy/#quick-start) on the laptop. -Note: We are using the install by manifest option from the Installation manual -``` -kubectl apply -f https://raw.githubusercontent.com/kubernetes/ingress-nginx/controller-v1.3.0/deploy/static/provider/cloud/deploy.yaml -``` -or one can also install it using the minikube addons: -``` -minikube addons enable ingress -``` - - Once your Ingress-Nginx controller is created you can run the following commands to see the output of the setup done. -``` -kubectl get pods -n ingress-nginx -NAME READY STATUS RESTARTS AGE -ingress-nginx-admission-create-65bld 0/1 Completed 0 14m -ingress-nginx-admission-patch-rwq4x 0/1 Completed 0 14m -ingress-nginx-controller-6dc865cd86-7c5zd 1/1 Running 0 14m -``` -The Ingress controller creates a Service with the type LoadBalancer and metallb provides the IP address. - -``` -kubectl -n ingress-nginx get svc - -NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE -ingress-nginx-controller LoadBalancer 10.108.154.53 192.168.39.223 80:30367/TCP,443:31491/TCP 4d15h -ingress-nginx-controller-admission ClusterIP 10.98.54.3 443/TCP 4d15h -``` - -#### Creating an Ingress - -We will deploy a `httpd` service in a `httpd` namespace and create a ingress for it. - -First, let's create a namespace. -``` -kubectl create namespace httpd -``` - -Next we will create a deployment -``` -kubectl create deployment httpd -n httpd --image=httpd:alpine -``` - -Now, In order to create a service, let's expose this deployment -``` -kubectl expose deployment -n httpd httpd --port 80 -``` -Let's check the `pod` that is created - -``` -kubectl get po -n httpd -NAME READY STATUS RESTARTS AGE -httpd-fb7fcdc77-w287c 1/1 Running 0 64s -``` - -Let's list the services in the `httpd` namespace -``` -kubectl get svc -n httpd -NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE -httpd ClusterIP 10.104.111.0 80/TCP 13s -``` - -Once we have this we can now create an ingress using the following -``` -kubectl -n httpd create ingress httpd --class nginx --rule httpd.dev.leonnunes.com/"*"=httpd:80 -``` -The above output, creates an ingress, for us with the rule to match the service if the host is `httpd.dev.leonnunes.com`. The class here is retrieved from the below command. - -To list the `ingressclasses` use -``` -kubectl get ingressclasses -NAME CONTROLLER PARAMETERS AGE -nginx k8s.io/ingress-nginx 6h49m -``` - -The following command shows the ingress created -``` -$ kubectl get ingress -A -o wide - -NAMESPACE NAME CLASS HOSTS ADDRESS PORTS AGE -httpd httpd nginx httpd.dev.leonnunes.com 192.168.39.223 80 11d -``` - -To test if the rule works we can now do -``` -$ minikube ip -192.168.39.223 - -$ curl --resolve httpd.dev.leonnunes.com:80:192.168.39.223 httpd.dev.leonnunes.com -

It works!

- -or - -curl -H "Host: httpd.dev.leonnunes.com" 192.168.39.223 -``` - -#### Example of Information found on layer 7 -We have setup `Ingress-Nginx`, using `nginx` as a class and `httpd` for this example. - -In order to display the info on Layer - 7, we have extracted the Layer 7 information from a simple `curl` request, and then using `tcpdump` command within the `httpd` pod we extracted the network packets and opened it using the `Wireshark` utility. - -Below given is the output that is important: -```bash -Frame 4: 391 bytes on wire (3128 bits), 391 bytes captured (3128 bits) -Linux cooked capture v2 -Internet Protocol Version 4, Src: 172.17.0.4, Dst: 172.17.0.3 -Transmission Control Protocol, Src Port: 49074, Dst Port: 80, Seq: 1, Ack: 1, Len: 319 -Hypertext Transfer Protocol - GET / HTTP/1.1\r\n - Host: httpd.dev.leonnunes.com\r\n - X-Request-ID: 6e1a790412a0d1615dc0231358dc9c8b\r\n - X-Real-IP: 172.17.0.1\r\n - X-Forwarded-For: 172.17.0.1\r\n - X-Forwarded-Host: httpd.dev.leonnunes.com\r\n - X-Forwarded-Port: 80\r\n - X-Forwarded-Proto: http\r\n - X-Forwarded-Scheme: http\r\n - X-Scheme: http\r\n - User-Agent: curl/7.84.0\r\n - Accept: */*\r\n - \r\n - [Full request URI: http://httpd.dev.leonnunes.com/] - [HTTP request 1/1] - [Response in frame: 6] - -``` -The above output shows the information that the `httpd` pod receives. The `curl` command sends the host header, `Host: httpd.dev.leonnunes.com`, to the nginx controller, that then matches the rule and sends the information to the right controller - -The following output shows what is sent via the laptop. -``` -curl --resolve httpd.dev.leonnunes.com:80:192.168.39.57 -H "Host: httpd.dev.leonnunes.com" 192.168.39.57 -vL -* Added httpd.dev.leonnunes.com:80:192.168.39.57 to DNS cache -* Trying 192.168.39.57:80... -* Connected to 192.168.39.57 (192.168.39.57) port 80 (#0) -> GET / HTTP/1.1 -> Host: httpd.dev.leonnunes.com -> User-Agent: curl/7.84.0 -> Accept: */* -> -* Mark bundle as not supporting multiuse -< HTTP/1.1 200 OK -< Date: Mon, 22 Aug 2022 16:05:27 GMT -< Content-Type: text/html -< Content-Length: 45 -< Connection: keep-alive -< Last-Modified: Mon, 11 Jun 2007 18:53:14 GMT -< ETag: "2d-432a5e4a73a80" -< Accept-Ranges: bytes -< -

It works!

-* Connection #0 to host 192.168.39.57 left intact -``` -As you can see from the above output there are several headers added to the curl output after it reaches the `httpd` pod, these headers are added by the Ingress Nginx Controller. - - -### References -#### Basics of Networking - - https://www.cisco.com/en/US/docs/security/vpn5000/manager/reference/guide/appA.html - - http://web.stanford.edu/class/cs101/ - - https://www.geeksforgeeks.org/basics-computer-networking/ - - Subnetting - - https://www.computernetworkingnotes.com/ccna-study-guide/subnetting-tutorial-subnetting-explained-with-examples.html - -#### Video Links - - https://www.youtube.com/playlist?list=PLhfrWIlLOoKPc2RecyiM_A9nf3fUU3e6g - - https://www.youtube.com/watch?v=S7MNX_UD7vY&list=PLIhvC56v63IJVXv0GJcl9vO5Z6znCVb1P - -### Topics to read about - - Docker in Docker - - [Docker/Containers](https://www.oreilly.com/library/view/docker-deep-dive/9781800565135/) - - Containers - -### Basics of Kubernetes -#### Reading Material -- https://nubenetes.com/kubernetes-tutorials/ -- https://kubernetes.io/docs/concepts/ -#### Video Material -- [Techworld with Nana 101](https://www.youtube.com/playlist?list=PLy7NrYWoggjziYQIDorlXjTvvwweTYoNC) -- [Jeff Geerling Kubernetes 101](https://www.youtube.com/watch?v=IcslsH7OoYo&list=PL2_OBreMn7FoYmfx27iSwocotjiikS5BD) - -#### Hands-On Kubernetes -- https://kube.academy/ -- https://www.civo.com/academy - -### Networking in Kubernetes -- [Kubernetes Networking 101](https://youtu.be/CYnwBIpvSlM?t=284) -- [CNCF Kubernetes 101](https://www.youtube.com/watch?v=cUGXu2tiZMc) - -### Tools/Commands to help with troubleshooting. -- [mtr](https://www.redhat.com/sysadmin/linux-mtr-command) - Tracing the packet from the source to destination -- [tcpdump](https://linuxconfig.org/how-to-use-tcpdump-command-on-linux) - Monitor packets -- [wireshark](https://www.lifewire.com/wireshark-tutorial-4143298) - Read/Sniff packets -- [nslookup](https://phoenixnap.com/kb/nslookup-command) - Lookup Nameservers -- [netstat](https://www.lifewire.com/netstat-command-2618098) - List network details -- [curl](https://linuxhandbook.com/curl-command-examples/) - Curl a website from the command line -- [ifconfig](https://www.tecmint.com/ifconfig-command-examples/)/[ip](https://www.geeksforgeeks.org/ip-command-in-linux-with-examples/) - Show ip address configuration -- [dig](https://www.geeksforgeeks.org/dig-command-in-linux-with-examples/) - Query Nameservers -- [ipcalc](https://www.linux.com/topic/networking/how-calculate-network-addresses-ipcalc/) - Calculate IP addresses -- Advanced Tools for troubleshooting - - [Netshoot](https://github.com/nicolaka/netshoot) - Troubleshoot Networks -- Cluster Creation tools - - [kind](https://kind.sigs.k8s.io/docs/user/quick-start/) - - [minikube](https://minikube.sigs.k8s.io/docs/start/) -- MacOS users - - [docker-mac-net-connect](https://github.com/chipmk/docker-mac-net-connect) - See this [issue](https://github.com/kubernetes/minikube/issues/7332) diff --git a/NEW_RELEASE_PROCESS.md b/NEW_RELEASE_PROCESS.md deleted file mode 100644 index cdb683abf..000000000 --- a/NEW_RELEASE_PROCESS.md +++ /dev/null @@ -1,9 +0,0 @@ -# Semi-Automated Release Process - -1. Update TAG -2. Cloud Build -3. k8s.io PR -4. git pull origin main -5. git checkout -b $RELEASE_VERSION -6. mage release:newrelease $RELEASE_VERSION -7. Wait for PR \ No newline at end of file diff --git a/NGINX_BASE b/NGINX_BASE deleted file mode 100644 index dd8d6c586..000000000 --- a/NGINX_BASE +++ /dev/null @@ -1 +0,0 @@ -registry.k8s.io/ingress-nginx/nginx:v2.0.0@sha256:3e7bda4cf5111d283ed1e4ff5cc9a2b5cdc5ebe62d50ba67473d3e25b1389133 diff --git a/OWNERS b/OWNERS index bafe6b3f7..245cb8688 100644 --- a/OWNERS +++ b/OWNERS @@ -1,13 +1,7 @@ # See the OWNERS docs: https://www.kubernetes.dev/docs/guide/owners approvers: -- ingress-nginx-maintainers +- ingress-nginx-docs-maintainers -reviewers: -- ingress-nginx-reviewers - -emeritus_approvers: -- aledbf # 2020-04-02 -- bowei # 2022-10-12 -- ElvinEfendi # 2023-04-23 -- rikatz # 2024-12-15 +labels: +- area/docs diff --git a/OWNERS_ALIASES b/OWNERS_ALIASES deleted file mode 100644 index 314202c10..000000000 --- a/OWNERS_ALIASES +++ /dev/null @@ -1,17 +0,0 @@ -# See the OWNERS docs: https://www.kubernetes.dev/docs/guide/owners - -aliases: - ingress-nginx-maintainers: - - cpanato - - Gacko - - strongjz - - tao12345666333 - - ingress-nginx-reviewers: - - cpanato - - Gacko - - strongjz - - tao12345666333 - - ingress-nginx-docs-maintainers: - - longwuyuan diff --git a/README.md b/README.md deleted file mode 100644 index c95e644de..000000000 --- a/README.md +++ /dev/null @@ -1,94 +0,0 @@ -# Ingress NGINX Controller - -[![CII Best Practices](https://bestpractices.coreinfrastructure.org/projects/5691/badge)](https://bestpractices.coreinfrastructure.org/projects/5691) -[![Go Report Card](https://goreportcard.com/badge/github.com/kubernetes/ingress-nginx)](https://goreportcard.com/report/github.com/kubernetes/ingress-nginx) -[![GitHub license](https://img.shields.io/github/license/kubernetes/ingress-nginx.svg)](https://github.com/kubernetes/ingress-nginx/blob/main/LICENSE) -[![GitHub stars](https://img.shields.io/github/stars/kubernetes/ingress-nginx.svg)](https://github.com/kubernetes/ingress-nginx/stargazers) -[![GitHub stars](https://img.shields.io/badge/contributions-welcome-orange.svg)](https://github.com/kubernetes/ingress-nginx/blob/main/CONTRIBUTING.md) - -## Overview - -ingress-nginx is an Ingress controller for Kubernetes using [NGINX](https://www.nginx.org/) as a reverse proxy and load -balancer. - -[Learn more about Ingress on the Kubernetes documentation site](https://kubernetes.io/docs/concepts/services-networking/ingress/). - -## Get started - -See the [Getting Started](https://kubernetes.github.io/ingress-nginx/deploy/) document. - -Do not use in multi-tenant Kubernetes production installations. This project assumes that users that can create Ingress objects are administrators of the cluster. See the [FAQ](https://kubernetes.github.io/ingress-nginx/faq/#faq) for more. - -## Troubleshooting - -If you encounter issues, review the [troubleshooting docs](docs/troubleshooting.md), -[file an issue](https://github.com/kubernetes/ingress-nginx/issues), or talk to us on the -[#ingress-nginx channel](https://kubernetes.slack.com/messages/ingress-nginx) on the Kubernetes Slack server. - -## Changelog - -See [the list of releases](https://github.com/kubernetes/ingress-nginx/releases) for all changes. -For detailed changes for each release, please check the [changelog-$version.md](./changelog) file for the release version. -For detailed changes on the `ingress-nginx` helm chart, please check the changelog folder for a specific version. -[CHANGELOG-$current-version.md](./charts/ingress-nginx/changelog) file. - -### Supported Versions table - -Supported versions for the ingress-nginx project mean that we have completed E2E tests, and they are passing for -the versions listed. Ingress-Nginx versions **may** work on older versions, but the project does not make that guarantee. - -| Supported | Ingress-NGINX version | k8s supported version | Alpine Version | Nginx Version | Helm Chart Version | -| :-------: | --------------------- | ----------------------------- | -------------- | ------------- | ------------------ | -| 🔄 | **v1.12.0** | 1.32, 1.31, 1.30, 1.29, 1.28 | 3.21.0 | 1.25.5 | 4.12.0 | -| 🔄 | **v1.12.0-beta.0** | 1.32, 1.31, 1.30, 1.29, 1.28 | 3.20.3 | 1.25.5 | 4.12.0-beta.0 | -| 🔄 | **v1.11.4** | 1.30, 1.29, 1.28, 1.27, 1.26 | 3.21.0 | 1.25.5 | 4.11.4 | -| 🔄 | **v1.11.3** | 1.30, 1.29, 1.28, 1.27, 1.26 | 3.20.3 | 1.25.5 | 4.11.3 | -| 🔄 | **v1.11.2** | 1.30, 1.29, 1.28, 1.27, 1.26 | 3.20.0 | 1.25.5 | 4.11.2 | -| 🔄 | **v1.11.1** | 1.30, 1.29, 1.28, 1.27, 1.26 | 3.20.0 | 1.25.5 | 4.11.1 | -| 🔄 | **v1.11.0** | 1.30, 1.29, 1.28, 1.27, 1.26 | 3.20.0 | 1.25.5 | 4.11.0 | -| | **v1.10.6** | 1.30, 1.29, 1.28, 1.27, 1.26 | 3.21.0 | 1.25.5 | 4.10.6 | -| | **v1.10.5** | 1.30, 1.29, 1.28, 1.27, 1.26 | 3.20.3 | 1.25.5 | 4.10.5 | -| | **v1.10.4** | 1.30, 1.29, 1.28, 1.27, 1.26 | 3.20.0 | 1.25.5 | 4.10.4 | -| | **v1.10.3** | 1.30, 1.29, 1.28, 1.27, 1.26 | 3.20.0 | 1.25.5 | 4.10.3 | -| | **v1.10.2** | 1.30, 1.29, 1.28, 1.27, 1.26 | 3.20.0 | 1.25.5 | 4.10.2 | -| | **v1.10.1** | 1.30, 1.29, 1.28, 1.27, 1.26 | 3.19.1 | 1.25.3 | 4.10.1 | -| | **v1.10.0** | 1.29, 1.28, 1.27, 1.26 | 3.19.1 | 1.25.3 | 4.10.0 | -| | v1.9.6 | 1.29, 1.28, 1.27, 1.26, 1.25 | 3.19.0 | 1.21.6 | 4.9.1 | -| | v1.9.5 | 1.28, 1.27, 1.26, 1.25 | 3.18.4 | 1.21.6 | 4.9.0 | -| | v1.9.4 | 1.28, 1.27, 1.26, 1.25 | 3.18.4 | 1.21.6 | 4.8.3 | -| | v1.9.3 | 1.28, 1.27, 1.26, 1.25 | 3.18.4 | 1.21.6 | 4.8.* | -| | v1.9.1 | 1.28, 1.27, 1.26, 1.25 | 3.18.4 | 1.21.6 | 4.8.* | -| | v1.9.0 | 1.28, 1.27, 1.26, 1.25 | 3.18.2 | 1.21.6 | 4.8.* | -| | v1.8.4 | 1.27, 1.26, 1.25, 1.24 | 3.18.2 | 1.21.6 | 4.7.* | -| | v1.7.1 | 1.27, 1.26, 1.25, 1.24 | 3.17.2 | 1.21.6 | 4.6.* | -| | v1.6.4 | 1.26, 1.25, 1.24, 1.23 | 3.17.0 | 1.21.6 | 4.5.* | -| | v1.5.1 | 1.25, 1.24, 1.23 | 3.16.2 | 1.21.6 | 4.4.* | -| | v1.4.0 | 1.25, 1.24, 1.23, 1.22 | 3.16.2 | 1.19.10† | 4.3.0 | -| | v1.3.1 | 1.24, 1.23, 1.22, 1.21, 1.20 | 3.16.2 | 1.19.10† | 4.2.5 | - -See [this article](https://kubernetes.io/blog/2021/07/26/update-with-ingress-nginx/) if you want upgrade to the stable -Ingress API. - -## Get Involved - -Thanks for taking the time to join our community and start contributing! - -- This project adheres to the [Kubernetes Community Code of Conduct](https://git.k8s.io/community/code-of-conduct.md). - By participating in this project, you agree to abide by its terms. -- **Contributing**: Contributions of all kinds are welcome! - - - Read [`CONTRIBUTING.md`](CONTRIBUTING.md) for information about setting up your environment, the workflow that we - expect, and instructions on the developer certificate of origin that we require. - - Join our Kubernetes Slack channel for developer discussion : [#ingress-nginx-dev](https://kubernetes.slack.com/archives/C021E147ZA4). - - Submit GitHub issues for any feature enhancements, bugs, or documentation problems. - - Please make sure to read the [Issue Reporting Checklist](https://github.com/kubernetes/ingress-nginx/blob/main/CONTRIBUTING.md#issue-reporting-guidelines) before opening an issue. Issues not conforming to the guidelines **may be closed immediately**. - - Join our [ingress-nginx-dev mailing list](https://groups.google.com/a/kubernetes.io/g/ingress-nginx-dev/c/ebbBMo-zX-w) -- **Support**: - - - Join the [#ingress-nginx-users](https://kubernetes.slack.com/messages/CANQGM8BA/) channel inside the [Kubernetes Slack](http://slack.kubernetes.io/) to ask questions or get support from the maintainers and other users. - - The [GitHub issues](https://github.com/kubernetes/ingress-nginx/issues) in the repository are **exclusively** for bug reports and feature requests. - - **Discuss**: Tweet using the `#IngressNginx` hashtag or sharing with us [@IngressNginx](https://twitter.com/IngressNGINX). - -## License - -[Apache License 2.0](https://github.com/kubernetes/ingress-nginx/blob/main/LICENSE) diff --git a/SECURITY.md b/SECURITY.md deleted file mode 100644 index 2083d44cd..000000000 --- a/SECURITY.md +++ /dev/null @@ -1,22 +0,0 @@ -# Security Policy - -## Security Announcements - -Join the [kubernetes-security-announce] group for security and vulnerability announcements. - -You can also subscribe to an RSS feed of the above using [this link][kubernetes-security-announce-rss]. - -## Reporting a Vulnerability - -Instructions for reporting a vulnerability can be found on the -[Kubernetes Security and Disclosure Information] page. - -## Supported Versions - -Information about supported Kubernetes versions can be found on the -[Kubernetes version and version skew support policy] page on the Kubernetes website. - -[kubernetes-security-announce]: https://groups.google.com/forum/#!forum/kubernetes-security-announce -[kubernetes-security-announce-rss]: https://groups.google.com/forum/feed/kubernetes-security-announce/msgs/rss_v2_0.xml?num=50 -[Kubernetes version and version skew support policy]: https://kubernetes.io/docs/setup/release/version-skew-policy/#supported-versions -[Kubernetes Security and Disclosure Information]: https://kubernetes.io/docs/reference/issues-security/security/#report-a-vulnerability diff --git a/SECURITY_CONTACTS b/SECURITY_CONTACTS deleted file mode 100644 index 587c7e016..000000000 --- a/SECURITY_CONTACTS +++ /dev/null @@ -1,13 +0,0 @@ -# Defined below are the security contacts for this repo. -# -# They are the contact point for the Product Security Committee to reach out -# to for triaging and handling of incoming issues. -# -# The below names agree to abide by the -# [Embargo Policy](https://git.k8s.io/security/private-distributors-list.md#embargo-policy) -# and will be removed and replaced if they violate that agreement. -# -# DO NOT REPORT SECURITY VULNERABILITIES DIRECTLY TO THESE NAMES, FOLLOW THE -# INSTRUCTIONS AT https://kubernetes.io/security/ -Gacko -strongjz diff --git a/assets/images/favicon.png b/assets/images/favicon.png new file mode 100644 index 000000000..1cf13b9f9 Binary files /dev/null and b/assets/images/favicon.png differ diff --git a/assets/javascripts/bundle.aecac24b.min.js b/assets/javascripts/bundle.aecac24b.min.js new file mode 100644 index 000000000..464603d80 --- /dev/null +++ b/assets/javascripts/bundle.aecac24b.min.js @@ -0,0 +1,29 @@ +"use strict";(()=>{var wi=Object.create;var ur=Object.defineProperty;var Si=Object.getOwnPropertyDescriptor;var Ti=Object.getOwnPropertyNames,kt=Object.getOwnPropertySymbols,Oi=Object.getPrototypeOf,dr=Object.prototype.hasOwnProperty,Zr=Object.prototype.propertyIsEnumerable;var Xr=(e,t,r)=>t in e?ur(e,t,{enumerable:!0,configurable:!0,writable:!0,value:r}):e[t]=r,R=(e,t)=>{for(var r in t||(t={}))dr.call(t,r)&&Xr(e,r,t[r]);if(kt)for(var r of kt(t))Zr.call(t,r)&&Xr(e,r,t[r]);return e};var eo=(e,t)=>{var r={};for(var o in e)dr.call(e,o)&&t.indexOf(o)<0&&(r[o]=e[o]);if(e!=null&&kt)for(var o of kt(e))t.indexOf(o)<0&&Zr.call(e,o)&&(r[o]=e[o]);return r};var hr=(e,t)=>()=>(t||e((t={exports:{}}).exports,t),t.exports);var Mi=(e,t,r,o)=>{if(t&&typeof t=="object"||typeof t=="function")for(let n of Ti(t))!dr.call(e,n)&&n!==r&&ur(e,n,{get:()=>t[n],enumerable:!(o=Si(t,n))||o.enumerable});return e};var Ht=(e,t,r)=>(r=e!=null?wi(Oi(e)):{},Mi(t||!e||!e.__esModule?ur(r,"default",{value:e,enumerable:!0}):r,e));var ro=hr((br,to)=>{(function(e,t){typeof br=="object"&&typeof to!="undefined"?t():typeof define=="function"&&define.amd?define(t):t()})(br,function(){"use strict";function e(r){var o=!0,n=!1,i=null,s={text:!0,search:!0,url:!0,tel:!0,email:!0,password:!0,number:!0,date:!0,month:!0,week:!0,time:!0,datetime:!0,"datetime-local":!0};function a(C){return!!(C&&C!==document&&C.nodeName!=="HTML"&&C.nodeName!=="BODY"&&"classList"in C&&"contains"in C.classList)}function c(C){var it=C.type,Ne=C.tagName;return!!(Ne==="INPUT"&&s[it]&&!C.readOnly||Ne==="TEXTAREA"&&!C.readOnly||C.isContentEditable)}function p(C){C.classList.contains("focus-visible")||(C.classList.add("focus-visible"),C.setAttribute("data-focus-visible-added",""))}function l(C){C.hasAttribute("data-focus-visible-added")&&(C.classList.remove("focus-visible"),C.removeAttribute("data-focus-visible-added"))}function f(C){C.metaKey||C.altKey||C.ctrlKey||(a(r.activeElement)&&p(r.activeElement),o=!0)}function u(C){o=!1}function d(C){a(C.target)&&(o||c(C.target))&&p(C.target)}function v(C){a(C.target)&&(C.target.classList.contains("focus-visible")||C.target.hasAttribute("data-focus-visible-added"))&&(n=!0,window.clearTimeout(i),i=window.setTimeout(function(){n=!1},100),l(C.target))}function b(C){document.visibilityState==="hidden"&&(n&&(o=!0),z())}function z(){document.addEventListener("mousemove",G),document.addEventListener("mousedown",G),document.addEventListener("mouseup",G),document.addEventListener("pointermove",G),document.addEventListener("pointerdown",G),document.addEventListener("pointerup",G),document.addEventListener("touchmove",G),document.addEventListener("touchstart",G),document.addEventListener("touchend",G)}function K(){document.removeEventListener("mousemove",G),document.removeEventListener("mousedown",G),document.removeEventListener("mouseup",G),document.removeEventListener("pointermove",G),document.removeEventListener("pointerdown",G),document.removeEventListener("pointerup",G),document.removeEventListener("touchmove",G),document.removeEventListener("touchstart",G),document.removeEventListener("touchend",G)}function G(C){C.target.nodeName&&C.target.nodeName.toLowerCase()==="html"||(o=!1,K())}document.addEventListener("keydown",f,!0),document.addEventListener("mousedown",u,!0),document.addEventListener("pointerdown",u,!0),document.addEventListener("touchstart",u,!0),document.addEventListener("visibilitychange",b,!0),z(),r.addEventListener("focus",d,!0),r.addEventListener("blur",v,!0),r.nodeType===Node.DOCUMENT_FRAGMENT_NODE&&r.host?r.host.setAttribute("data-js-focus-visible",""):r.nodeType===Node.DOCUMENT_NODE&&(document.documentElement.classList.add("js-focus-visible"),document.documentElement.setAttribute("data-js-focus-visible",""))}if(typeof window!="undefined"&&typeof document!="undefined"){window.applyFocusVisiblePolyfill=e;var t;try{t=new CustomEvent("focus-visible-polyfill-ready")}catch(r){t=document.createEvent("CustomEvent"),t.initCustomEvent("focus-visible-polyfill-ready",!1,!1,{})}window.dispatchEvent(t)}typeof document!="undefined"&&e(document)})});var Vr=hr((Ot,Dr)=>{/*! + * clipboard.js v2.0.11 + * https://clipboardjs.com/ + * + * Licensed MIT © Zeno Rocha + */(function(t,r){typeof Ot=="object"&&typeof Dr=="object"?Dr.exports=r():typeof define=="function"&&define.amd?define([],r):typeof Ot=="object"?Ot.ClipboardJS=r():t.ClipboardJS=r()})(Ot,function(){return function(){var e={686:function(o,n,i){"use strict";i.d(n,{default:function(){return Ei}});var s=i(279),a=i.n(s),c=i(370),p=i.n(c),l=i(817),f=i.n(l);function u(U){try{return document.execCommand(U)}catch(O){return!1}}var d=function(O){var S=f()(O);return u("cut"),S},v=d;function b(U){var O=document.documentElement.getAttribute("dir")==="rtl",S=document.createElement("textarea");S.style.fontSize="12pt",S.style.border="0",S.style.padding="0",S.style.margin="0",S.style.position="absolute",S.style[O?"right":"left"]="-9999px";var $=window.pageYOffset||document.documentElement.scrollTop;return S.style.top="".concat($,"px"),S.setAttribute("readonly",""),S.value=U,S}var z=function(O,S){var $=b(O);S.container.appendChild($);var F=f()($);return u("copy"),$.remove(),F},K=function(O){var S=arguments.length>1&&arguments[1]!==void 0?arguments[1]:{container:document.body},$="";return typeof O=="string"?$=z(O,S):O instanceof HTMLInputElement&&!["text","search","url","tel","password"].includes(O==null?void 0:O.type)?$=z(O.value,S):($=f()(O),u("copy")),$},G=K;function C(U){"@babel/helpers - typeof";return typeof Symbol=="function"&&typeof Symbol.iterator=="symbol"?C=function(S){return typeof S}:C=function(S){return S&&typeof Symbol=="function"&&S.constructor===Symbol&&S!==Symbol.prototype?"symbol":typeof S},C(U)}var it=function(){var O=arguments.length>0&&arguments[0]!==void 0?arguments[0]:{},S=O.action,$=S===void 0?"copy":S,F=O.container,Q=O.target,_e=O.text;if($!=="copy"&&$!=="cut")throw new Error('Invalid "action" value, use either "copy" or "cut"');if(Q!==void 0)if(Q&&C(Q)==="object"&&Q.nodeType===1){if($==="copy"&&Q.hasAttribute("disabled"))throw new Error('Invalid "target" attribute. Please use "readonly" instead of "disabled" attribute');if($==="cut"&&(Q.hasAttribute("readonly")||Q.hasAttribute("disabled")))throw new Error(`Invalid "target" attribute. You can't cut text from elements with "readonly" or "disabled" attributes`)}else throw new Error('Invalid "target" value, use a valid Element');if(_e)return G(_e,{container:F});if(Q)return $==="cut"?v(Q):G(Q,{container:F})},Ne=it;function Pe(U){"@babel/helpers - typeof";return typeof Symbol=="function"&&typeof Symbol.iterator=="symbol"?Pe=function(S){return typeof S}:Pe=function(S){return S&&typeof Symbol=="function"&&S.constructor===Symbol&&S!==Symbol.prototype?"symbol":typeof S},Pe(U)}function ui(U,O){if(!(U instanceof O))throw new TypeError("Cannot call a class as a function")}function Jr(U,O){for(var S=0;S0&&arguments[0]!==void 0?arguments[0]:{};this.action=typeof F.action=="function"?F.action:this.defaultAction,this.target=typeof F.target=="function"?F.target:this.defaultTarget,this.text=typeof F.text=="function"?F.text:this.defaultText,this.container=Pe(F.container)==="object"?F.container:document.body}},{key:"listenClick",value:function(F){var Q=this;this.listener=p()(F,"click",function(_e){return Q.onClick(_e)})}},{key:"onClick",value:function(F){var Q=F.delegateTarget||F.currentTarget,_e=this.action(Q)||"copy",Ct=Ne({action:_e,container:this.container,target:this.target(Q),text:this.text(Q)});this.emit(Ct?"success":"error",{action:_e,text:Ct,trigger:Q,clearSelection:function(){Q&&Q.focus(),window.getSelection().removeAllRanges()}})}},{key:"defaultAction",value:function(F){return fr("action",F)}},{key:"defaultTarget",value:function(F){var Q=fr("target",F);if(Q)return document.querySelector(Q)}},{key:"defaultText",value:function(F){return fr("text",F)}},{key:"destroy",value:function(){this.listener.destroy()}}],[{key:"copy",value:function(F){var Q=arguments.length>1&&arguments[1]!==void 0?arguments[1]:{container:document.body};return G(F,Q)}},{key:"cut",value:function(F){return v(F)}},{key:"isSupported",value:function(){var F=arguments.length>0&&arguments[0]!==void 0?arguments[0]:["copy","cut"],Q=typeof F=="string"?[F]:F,_e=!!document.queryCommandSupported;return Q.forEach(function(Ct){_e=_e&&!!document.queryCommandSupported(Ct)}),_e}}]),S}(a()),Ei=yi},828:function(o){var n=9;if(typeof Element!="undefined"&&!Element.prototype.matches){var i=Element.prototype;i.matches=i.matchesSelector||i.mozMatchesSelector||i.msMatchesSelector||i.oMatchesSelector||i.webkitMatchesSelector}function s(a,c){for(;a&&a.nodeType!==n;){if(typeof a.matches=="function"&&a.matches(c))return a;a=a.parentNode}}o.exports=s},438:function(o,n,i){var s=i(828);function a(l,f,u,d,v){var b=p.apply(this,arguments);return l.addEventListener(u,b,v),{destroy:function(){l.removeEventListener(u,b,v)}}}function c(l,f,u,d,v){return typeof l.addEventListener=="function"?a.apply(null,arguments):typeof u=="function"?a.bind(null,document).apply(null,arguments):(typeof l=="string"&&(l=document.querySelectorAll(l)),Array.prototype.map.call(l,function(b){return a(b,f,u,d,v)}))}function p(l,f,u,d){return function(v){v.delegateTarget=s(v.target,f),v.delegateTarget&&d.call(l,v)}}o.exports=c},879:function(o,n){n.node=function(i){return i!==void 0&&i instanceof HTMLElement&&i.nodeType===1},n.nodeList=function(i){var s=Object.prototype.toString.call(i);return i!==void 0&&(s==="[object NodeList]"||s==="[object HTMLCollection]")&&"length"in i&&(i.length===0||n.node(i[0]))},n.string=function(i){return typeof i=="string"||i instanceof String},n.fn=function(i){var s=Object.prototype.toString.call(i);return s==="[object Function]"}},370:function(o,n,i){var s=i(879),a=i(438);function c(u,d,v){if(!u&&!d&&!v)throw new Error("Missing required arguments");if(!s.string(d))throw new TypeError("Second argument must be a String");if(!s.fn(v))throw new TypeError("Third argument must be a Function");if(s.node(u))return p(u,d,v);if(s.nodeList(u))return l(u,d,v);if(s.string(u))return f(u,d,v);throw new TypeError("First argument must be a String, HTMLElement, HTMLCollection, or NodeList")}function p(u,d,v){return u.addEventListener(d,v),{destroy:function(){u.removeEventListener(d,v)}}}function l(u,d,v){return Array.prototype.forEach.call(u,function(b){b.addEventListener(d,v)}),{destroy:function(){Array.prototype.forEach.call(u,function(b){b.removeEventListener(d,v)})}}}function f(u,d,v){return a(document.body,u,d,v)}o.exports=c},817:function(o){function n(i){var s;if(i.nodeName==="SELECT")i.focus(),s=i.value;else if(i.nodeName==="INPUT"||i.nodeName==="TEXTAREA"){var a=i.hasAttribute("readonly");a||i.setAttribute("readonly",""),i.select(),i.setSelectionRange(0,i.value.length),a||i.removeAttribute("readonly"),s=i.value}else{i.hasAttribute("contenteditable")&&i.focus();var c=window.getSelection(),p=document.createRange();p.selectNodeContents(i),c.removeAllRanges(),c.addRange(p),s=c.toString()}return s}o.exports=n},279:function(o){function n(){}n.prototype={on:function(i,s,a){var c=this.e||(this.e={});return(c[i]||(c[i]=[])).push({fn:s,ctx:a}),this},once:function(i,s,a){var c=this;function p(){c.off(i,p),s.apply(a,arguments)}return p._=s,this.on(i,p,a)},emit:function(i){var s=[].slice.call(arguments,1),a=((this.e||(this.e={}))[i]||[]).slice(),c=0,p=a.length;for(c;c{"use strict";/*! + * escape-html + * Copyright(c) 2012-2013 TJ Holowaychuk + * Copyright(c) 2015 Andreas Lubbe + * Copyright(c) 2015 Tiancheng "Timothy" Gu + * MIT Licensed + */var Ha=/["'&<>]/;Un.exports=$a;function $a(e){var t=""+e,r=Ha.exec(t);if(!r)return t;var o,n="",i=0,s=0;for(i=r.index;i0&&i[i.length-1])&&(p[0]===6||p[0]===2)){r=0;continue}if(p[0]===3&&(!i||p[1]>i[0]&&p[1]=e.length&&(e=void 0),{value:e&&e[o++],done:!e}}};throw new TypeError(t?"Object is not iterable.":"Symbol.iterator is not defined.")}function N(e,t){var r=typeof Symbol=="function"&&e[Symbol.iterator];if(!r)return e;var o=r.call(e),n,i=[],s;try{for(;(t===void 0||t-- >0)&&!(n=o.next()).done;)i.push(n.value)}catch(a){s={error:a}}finally{try{n&&!n.done&&(r=o.return)&&r.call(o)}finally{if(s)throw s.error}}return i}function D(e,t,r){if(r||arguments.length===2)for(var o=0,n=t.length,i;o1||a(u,d)})})}function a(u,d){try{c(o[u](d))}catch(v){f(i[0][3],v)}}function c(u){u.value instanceof Ze?Promise.resolve(u.value.v).then(p,l):f(i[0][2],u)}function p(u){a("next",u)}function l(u){a("throw",u)}function f(u,d){u(d),i.shift(),i.length&&a(i[0][0],i[0][1])}}function io(e){if(!Symbol.asyncIterator)throw new TypeError("Symbol.asyncIterator is not defined.");var t=e[Symbol.asyncIterator],r;return t?t.call(e):(e=typeof we=="function"?we(e):e[Symbol.iterator](),r={},o("next"),o("throw"),o("return"),r[Symbol.asyncIterator]=function(){return this},r);function o(i){r[i]=e[i]&&function(s){return new Promise(function(a,c){s=e[i](s),n(a,c,s.done,s.value)})}}function n(i,s,a,c){Promise.resolve(c).then(function(p){i({value:p,done:a})},s)}}function k(e){return typeof e=="function"}function at(e){var t=function(o){Error.call(o),o.stack=new Error().stack},r=e(t);return r.prototype=Object.create(Error.prototype),r.prototype.constructor=r,r}var Rt=at(function(e){return function(r){e(this),this.message=r?r.length+` errors occurred during unsubscription: +`+r.map(function(o,n){return n+1+") "+o.toString()}).join(` + `):"",this.name="UnsubscriptionError",this.errors=r}});function De(e,t){if(e){var r=e.indexOf(t);0<=r&&e.splice(r,1)}}var Ie=function(){function e(t){this.initialTeardown=t,this.closed=!1,this._parentage=null,this._finalizers=null}return e.prototype.unsubscribe=function(){var t,r,o,n,i;if(!this.closed){this.closed=!0;var s=this._parentage;if(s)if(this._parentage=null,Array.isArray(s))try{for(var a=we(s),c=a.next();!c.done;c=a.next()){var p=c.value;p.remove(this)}}catch(b){t={error:b}}finally{try{c&&!c.done&&(r=a.return)&&r.call(a)}finally{if(t)throw t.error}}else s.remove(this);var l=this.initialTeardown;if(k(l))try{l()}catch(b){i=b instanceof Rt?b.errors:[b]}var f=this._finalizers;if(f){this._finalizers=null;try{for(var u=we(f),d=u.next();!d.done;d=u.next()){var v=d.value;try{ao(v)}catch(b){i=i!=null?i:[],b instanceof Rt?i=D(D([],N(i)),N(b.errors)):i.push(b)}}}catch(b){o={error:b}}finally{try{d&&!d.done&&(n=u.return)&&n.call(u)}finally{if(o)throw o.error}}}if(i)throw new Rt(i)}},e.prototype.add=function(t){var r;if(t&&t!==this)if(this.closed)ao(t);else{if(t instanceof e){if(t.closed||t._hasParent(this))return;t._addParent(this)}(this._finalizers=(r=this._finalizers)!==null&&r!==void 0?r:[]).push(t)}},e.prototype._hasParent=function(t){var r=this._parentage;return r===t||Array.isArray(r)&&r.includes(t)},e.prototype._addParent=function(t){var r=this._parentage;this._parentage=Array.isArray(r)?(r.push(t),r):r?[r,t]:t},e.prototype._removeParent=function(t){var r=this._parentage;r===t?this._parentage=null:Array.isArray(r)&&De(r,t)},e.prototype.remove=function(t){var r=this._finalizers;r&&De(r,t),t instanceof e&&t._removeParent(this)},e.EMPTY=function(){var t=new e;return t.closed=!0,t}(),e}();var gr=Ie.EMPTY;function Pt(e){return e instanceof Ie||e&&"closed"in e&&k(e.remove)&&k(e.add)&&k(e.unsubscribe)}function ao(e){k(e)?e():e.unsubscribe()}var Ae={onUnhandledError:null,onStoppedNotification:null,Promise:void 0,useDeprecatedSynchronousErrorHandling:!1,useDeprecatedNextContext:!1};var st={setTimeout:function(e,t){for(var r=[],o=2;o0},enumerable:!1,configurable:!0}),t.prototype._trySubscribe=function(r){return this._throwIfClosed(),e.prototype._trySubscribe.call(this,r)},t.prototype._subscribe=function(r){return this._throwIfClosed(),this._checkFinalizedStatuses(r),this._innerSubscribe(r)},t.prototype._innerSubscribe=function(r){var o=this,n=this,i=n.hasError,s=n.isStopped,a=n.observers;return i||s?gr:(this.currentObservers=null,a.push(r),new Ie(function(){o.currentObservers=null,De(a,r)}))},t.prototype._checkFinalizedStatuses=function(r){var o=this,n=o.hasError,i=o.thrownError,s=o.isStopped;n?r.error(i):s&&r.complete()},t.prototype.asObservable=function(){var r=new P;return r.source=this,r},t.create=function(r,o){return new ho(r,o)},t}(P);var ho=function(e){ie(t,e);function t(r,o){var n=e.call(this)||this;return n.destination=r,n.source=o,n}return t.prototype.next=function(r){var o,n;(n=(o=this.destination)===null||o===void 0?void 0:o.next)===null||n===void 0||n.call(o,r)},t.prototype.error=function(r){var o,n;(n=(o=this.destination)===null||o===void 0?void 0:o.error)===null||n===void 0||n.call(o,r)},t.prototype.complete=function(){var r,o;(o=(r=this.destination)===null||r===void 0?void 0:r.complete)===null||o===void 0||o.call(r)},t.prototype._subscribe=function(r){var o,n;return(n=(o=this.source)===null||o===void 0?void 0:o.subscribe(r))!==null&&n!==void 0?n:gr},t}(x);var yt={now:function(){return(yt.delegate||Date).now()},delegate:void 0};var Et=function(e){ie(t,e);function t(r,o,n){r===void 0&&(r=1/0),o===void 0&&(o=1/0),n===void 0&&(n=yt);var i=e.call(this)||this;return i._bufferSize=r,i._windowTime=o,i._timestampProvider=n,i._buffer=[],i._infiniteTimeWindow=!0,i._infiniteTimeWindow=o===1/0,i._bufferSize=Math.max(1,r),i._windowTime=Math.max(1,o),i}return t.prototype.next=function(r){var o=this,n=o.isStopped,i=o._buffer,s=o._infiniteTimeWindow,a=o._timestampProvider,c=o._windowTime;n||(i.push(r),!s&&i.push(a.now()+c)),this._trimBuffer(),e.prototype.next.call(this,r)},t.prototype._subscribe=function(r){this._throwIfClosed(),this._trimBuffer();for(var o=this._innerSubscribe(r),n=this,i=n._infiniteTimeWindow,s=n._buffer,a=s.slice(),c=0;c0?e.prototype.requestAsyncId.call(this,r,o,n):(r.actions.push(this),r._scheduled||(r._scheduled=lt.requestAnimationFrame(function(){return r.flush(void 0)})))},t.prototype.recycleAsyncId=function(r,o,n){var i;if(n===void 0&&(n=0),n!=null?n>0:this.delay>0)return e.prototype.recycleAsyncId.call(this,r,o,n);var s=r.actions;o!=null&&((i=s[s.length-1])===null||i===void 0?void 0:i.id)!==o&&(lt.cancelAnimationFrame(o),r._scheduled=void 0)},t}(jt);var go=function(e){ie(t,e);function t(){return e!==null&&e.apply(this,arguments)||this}return t.prototype.flush=function(r){this._active=!0;var o=this._scheduled;this._scheduled=void 0;var n=this.actions,i;r=r||n.shift();do if(i=r.execute(r.state,r.delay))break;while((r=n[0])&&r.id===o&&n.shift());if(this._active=!1,i){for(;(r=n[0])&&r.id===o&&n.shift();)r.unsubscribe();throw i}},t}(Wt);var Oe=new go(vo);var L=new P(function(e){return e.complete()});function Ut(e){return e&&k(e.schedule)}function Or(e){return e[e.length-1]}function Qe(e){return k(Or(e))?e.pop():void 0}function Me(e){return Ut(Or(e))?e.pop():void 0}function Nt(e,t){return typeof Or(e)=="number"?e.pop():t}var mt=function(e){return e&&typeof e.length=="number"&&typeof e!="function"};function Dt(e){return k(e==null?void 0:e.then)}function Vt(e){return k(e[pt])}function zt(e){return Symbol.asyncIterator&&k(e==null?void 0:e[Symbol.asyncIterator])}function qt(e){return new TypeError("You provided "+(e!==null&&typeof e=="object"?"an invalid object":"'"+e+"'")+" where a stream was expected. You can provide an Observable, Promise, ReadableStream, Array, AsyncIterable, or Iterable.")}function Pi(){return typeof Symbol!="function"||!Symbol.iterator?"@@iterator":Symbol.iterator}var Kt=Pi();function Qt(e){return k(e==null?void 0:e[Kt])}function Yt(e){return no(this,arguments,function(){var r,o,n,i;return $t(this,function(s){switch(s.label){case 0:r=e.getReader(),s.label=1;case 1:s.trys.push([1,,9,10]),s.label=2;case 2:return[4,Ze(r.read())];case 3:return o=s.sent(),n=o.value,i=o.done,i?[4,Ze(void 0)]:[3,5];case 4:return[2,s.sent()];case 5:return[4,Ze(n)];case 6:return[4,s.sent()];case 7:return s.sent(),[3,2];case 8:return[3,10];case 9:return r.releaseLock(),[7];case 10:return[2]}})})}function Bt(e){return k(e==null?void 0:e.getReader)}function I(e){if(e instanceof P)return e;if(e!=null){if(Vt(e))return Ii(e);if(mt(e))return Fi(e);if(Dt(e))return ji(e);if(zt(e))return xo(e);if(Qt(e))return Wi(e);if(Bt(e))return Ui(e)}throw qt(e)}function Ii(e){return new P(function(t){var r=e[pt]();if(k(r.subscribe))return r.subscribe(t);throw new TypeError("Provided object does not correctly implement Symbol.observable")})}function Fi(e){return new P(function(t){for(var r=0;r=2;return function(o){return o.pipe(e?M(function(n,i){return e(n,i,o)}):ue,xe(1),r?He(t):Io(function(){return new Jt}))}}function Fo(){for(var e=[],t=0;t=2,!0))}function le(e){e===void 0&&(e={});var t=e.connector,r=t===void 0?function(){return new x}:t,o=e.resetOnError,n=o===void 0?!0:o,i=e.resetOnComplete,s=i===void 0?!0:i,a=e.resetOnRefCountZero,c=a===void 0?!0:a;return function(p){var l,f,u,d=0,v=!1,b=!1,z=function(){f==null||f.unsubscribe(),f=void 0},K=function(){z(),l=u=void 0,v=b=!1},G=function(){var C=l;K(),C==null||C.unsubscribe()};return g(function(C,it){d++,!b&&!v&&z();var Ne=u=u!=null?u:r();it.add(function(){d--,d===0&&!b&&!v&&(f=Hr(G,c))}),Ne.subscribe(it),!l&&d>0&&(l=new tt({next:function(Pe){return Ne.next(Pe)},error:function(Pe){b=!0,z(),f=Hr(K,n,Pe),Ne.error(Pe)},complete:function(){v=!0,z(),f=Hr(K,s),Ne.complete()}}),I(C).subscribe(l))})(p)}}function Hr(e,t){for(var r=[],o=2;oe.next(document)),e}function q(e,t=document){return Array.from(t.querySelectorAll(e))}function W(e,t=document){let r=ce(e,t);if(typeof r=="undefined")throw new ReferenceError(`Missing element: expected "${e}" to be present`);return r}function ce(e,t=document){return t.querySelector(e)||void 0}function Re(){return document.activeElement instanceof HTMLElement&&document.activeElement||void 0}var na=_(h(document.body,"focusin"),h(document.body,"focusout")).pipe(ke(1),V(void 0),m(()=>Re()||document.body),J(1));function Zt(e){return na.pipe(m(t=>e.contains(t)),X())}function Je(e){return{x:e.offsetLeft,y:e.offsetTop}}function No(e){return _(h(window,"load"),h(window,"resize")).pipe(Ce(0,Oe),m(()=>Je(e)),V(Je(e)))}function er(e){return{x:e.scrollLeft,y:e.scrollTop}}function dt(e){return _(h(e,"scroll"),h(window,"resize")).pipe(Ce(0,Oe),m(()=>er(e)),V(er(e)))}function Do(e,t){if(typeof t=="string"||typeof t=="number")e.innerHTML+=t.toString();else if(t instanceof Node)e.appendChild(t);else if(Array.isArray(t))for(let r of t)Do(e,r)}function T(e,t,...r){let o=document.createElement(e);if(t)for(let n of Object.keys(t))typeof t[n]!="undefined"&&(typeof t[n]!="boolean"?o.setAttribute(n,t[n]):o.setAttribute(n,""));for(let n of r)Do(o,n);return o}function tr(e){if(e>999){let t=+((e-950)%1e3>99);return`${((e+1e-6)/1e3).toFixed(t)}k`}else return e.toString()}function ht(e){let t=T("script",{src:e});return H(()=>(document.head.appendChild(t),_(h(t,"load"),h(t,"error").pipe(E(()=>Mr(()=>new ReferenceError(`Invalid script: ${e}`))))).pipe(m(()=>{}),A(()=>document.head.removeChild(t)),xe(1))))}var Vo=new x,ia=H(()=>typeof ResizeObserver=="undefined"?ht("https://unpkg.com/resize-observer-polyfill"):j(void 0)).pipe(m(()=>new ResizeObserver(e=>{for(let t of e)Vo.next(t)})),E(e=>_(Ve,j(e)).pipe(A(()=>e.disconnect()))),J(1));function he(e){return{width:e.offsetWidth,height:e.offsetHeight}}function ye(e){return ia.pipe(w(t=>t.observe(e)),E(t=>Vo.pipe(M(({target:r})=>r===e),A(()=>t.unobserve(e)),m(()=>he(e)))),V(he(e)))}function bt(e){return{width:e.scrollWidth,height:e.scrollHeight}}function zo(e){let t=e.parentElement;for(;t&&(e.scrollWidth<=t.scrollWidth&&e.scrollHeight<=t.scrollHeight);)t=(e=t).parentElement;return t?e:void 0}var qo=new x,aa=H(()=>j(new IntersectionObserver(e=>{for(let t of e)qo.next(t)},{threshold:0}))).pipe(E(e=>_(Ve,j(e)).pipe(A(()=>e.disconnect()))),J(1));function rr(e){return aa.pipe(w(t=>t.observe(e)),E(t=>qo.pipe(M(({target:r})=>r===e),A(()=>t.unobserve(e)),m(({isIntersecting:r})=>r))))}function Ko(e,t=16){return dt(e).pipe(m(({y:r})=>{let o=he(e),n=bt(e);return r>=n.height-o.height-t}),X())}var or={drawer:W("[data-md-toggle=drawer]"),search:W("[data-md-toggle=search]")};function Qo(e){return or[e].checked}function Ke(e,t){or[e].checked!==t&&or[e].click()}function We(e){let t=or[e];return h(t,"change").pipe(m(()=>t.checked),V(t.checked))}function sa(e,t){switch(e.constructor){case HTMLInputElement:return e.type==="radio"?/^Arrow/.test(t):!0;case HTMLSelectElement:case HTMLTextAreaElement:return!0;default:return e.isContentEditable}}function ca(){return _(h(window,"compositionstart").pipe(m(()=>!0)),h(window,"compositionend").pipe(m(()=>!1))).pipe(V(!1))}function Yo(){let e=h(window,"keydown").pipe(M(t=>!(t.metaKey||t.ctrlKey)),m(t=>({mode:Qo("search")?"search":"global",type:t.key,claim(){t.preventDefault(),t.stopPropagation()}})),M(({mode:t,type:r})=>{if(t==="global"){let o=Re();if(typeof o!="undefined")return!sa(o,r)}return!0}),le());return ca().pipe(E(t=>t?L:e))}function pe(){return new URL(location.href)}function ot(e,t=!1){if(te("navigation.instant")&&!t){let r=T("a",{href:e.href});document.body.appendChild(r),r.click(),r.remove()}else location.href=e.href}function Bo(){return new x}function Go(){return location.hash.slice(1)}function nr(e){let t=T("a",{href:e});t.addEventListener("click",r=>r.stopPropagation()),t.click()}function pa(e){return _(h(window,"hashchange"),e).pipe(m(Go),V(Go()),M(t=>t.length>0),J(1))}function Jo(e){return pa(e).pipe(m(t=>ce(`[id="${t}"]`)),M(t=>typeof t!="undefined"))}function Fr(e){let t=matchMedia(e);return Xt(r=>t.addListener(()=>r(t.matches))).pipe(V(t.matches))}function Xo(){let e=matchMedia("print");return _(h(window,"beforeprint").pipe(m(()=>!0)),h(window,"afterprint").pipe(m(()=>!1))).pipe(V(e.matches))}function jr(e,t){return e.pipe(E(r=>r?t():L))}function ir(e,t){return new P(r=>{let o=new XMLHttpRequest;o.open("GET",`${e}`),o.responseType="blob",o.addEventListener("load",()=>{o.status>=200&&o.status<300?(r.next(o.response),r.complete()):r.error(new Error(o.statusText))}),o.addEventListener("error",()=>{r.error(new Error("Network Error"))}),o.addEventListener("abort",()=>{r.error(new Error("Request aborted"))}),typeof(t==null?void 0:t.progress$)!="undefined"&&(o.addEventListener("progress",n=>{t.progress$.next(n.loaded/n.total*100)}),t.progress$.next(5)),o.send()})}function Ue(e,t){return ir(e,t).pipe(E(r=>r.text()),m(r=>JSON.parse(r)),J(1))}function Zo(e,t){let r=new DOMParser;return ir(e,t).pipe(E(o=>o.text()),m(o=>r.parseFromString(o,"text/xml")),J(1))}function en(){return{x:Math.max(0,scrollX),y:Math.max(0,scrollY)}}function tn(){return _(h(window,"scroll",{passive:!0}),h(window,"resize",{passive:!0})).pipe(m(en),V(en()))}function rn(){return{width:innerWidth,height:innerHeight}}function on(){return h(window,"resize",{passive:!0}).pipe(m(rn),V(rn()))}function nn(){return B([tn(),on()]).pipe(m(([e,t])=>({offset:e,size:t})),J(1))}function ar(e,{viewport$:t,header$:r}){let o=t.pipe(ee("size")),n=B([o,r]).pipe(m(()=>Je(e)));return B([r,t,n]).pipe(m(([{height:i},{offset:s,size:a},{x:c,y:p}])=>({offset:{x:s.x-c,y:s.y-p+i},size:a})))}function la(e){return h(e,"message",t=>t.data)}function ma(e){let t=new x;return t.subscribe(r=>e.postMessage(r)),t}function an(e,t=new Worker(e)){let r=la(t),o=ma(t),n=new x;n.subscribe(o);let i=o.pipe(Z(),re(!0));return n.pipe(Z(),qe(r.pipe(Y(i))),le())}var fa=W("#__config"),vt=JSON.parse(fa.textContent);vt.base=`${new URL(vt.base,pe())}`;function me(){return vt}function te(e){return vt.features.includes(e)}function be(e,t){return typeof t!="undefined"?vt.translations[e].replace("#",t.toString()):vt.translations[e]}function Ee(e,t=document){return W(`[data-md-component=${e}]`,t)}function oe(e,t=document){return q(`[data-md-component=${e}]`,t)}function ua(e){let t=W(".md-typeset > :first-child",e);return h(t,"click",{once:!0}).pipe(m(()=>W(".md-typeset",e)),m(r=>({hash:__md_hash(r.innerHTML)})))}function sn(e){if(!te("announce.dismiss")||!e.childElementCount)return L;if(!e.hidden){let t=W(".md-typeset",e);__md_hash(t.innerHTML)===__md_get("__announce")&&(e.hidden=!0)}return H(()=>{let t=new x;return t.subscribe(({hash:r})=>{e.hidden=!0,__md_set("__announce",r)}),ua(e).pipe(w(r=>t.next(r)),A(()=>t.complete()),m(r=>R({ref:e},r)))})}function da(e,{target$:t}){return t.pipe(m(r=>({hidden:r!==e})))}function cn(e,t){let r=new x;return r.subscribe(({hidden:o})=>{e.hidden=o}),da(e,t).pipe(w(o=>r.next(o)),A(()=>r.complete()),m(o=>R({ref:e},o)))}function ha(e,t){let r=H(()=>B([No(e),dt(t)])).pipe(m(([{x:o,y:n},i])=>{let{width:s,height:a}=he(e);return{x:o-i.x+s/2,y:n-i.y+a/2}}));return Zt(e).pipe(E(o=>r.pipe(m(n=>({active:o,offset:n})),xe(+!o||1/0))))}function pn(e,t,{target$:r}){let[o,n]=Array.from(e.children);return H(()=>{let i=new x,s=i.pipe(Z(),re(!0));return i.subscribe({next({offset:a}){e.style.setProperty("--md-tooltip-x",`${a.x}px`),e.style.setProperty("--md-tooltip-y",`${a.y}px`)},complete(){e.style.removeProperty("--md-tooltip-x"),e.style.removeProperty("--md-tooltip-y")}}),rr(e).pipe(Y(s)).subscribe(a=>{e.toggleAttribute("data-md-visible",a)}),_(i.pipe(M(({active:a})=>a)),i.pipe(ke(250),M(({active:a})=>!a))).subscribe({next({active:a}){a?e.prepend(o):o.remove()},complete(){e.prepend(o)}}),i.pipe(Ce(16,Oe)).subscribe(({active:a})=>{o.classList.toggle("md-tooltip--active",a)}),i.pipe(Pr(125,Oe),M(()=>!!e.offsetParent),m(()=>e.offsetParent.getBoundingClientRect()),m(({x:a})=>a)).subscribe({next(a){a?e.style.setProperty("--md-tooltip-0",`${-a}px`):e.style.removeProperty("--md-tooltip-0")},complete(){e.style.removeProperty("--md-tooltip-0")}}),h(n,"click").pipe(Y(s),M(a=>!(a.metaKey||a.ctrlKey))).subscribe(a=>{a.stopPropagation(),a.preventDefault()}),h(n,"mousedown").pipe(Y(s),ne(i)).subscribe(([a,{active:c}])=>{var p;if(a.button!==0||a.metaKey||a.ctrlKey)a.preventDefault();else if(c){a.preventDefault();let l=e.parentElement.closest(".md-annotation");l instanceof HTMLElement?l.focus():(p=Re())==null||p.blur()}}),r.pipe(Y(s),M(a=>a===o),ze(125)).subscribe(()=>e.focus()),ha(e,t).pipe(w(a=>i.next(a)),A(()=>i.complete()),m(a=>R({ref:e},a)))})}function Wr(e){return T("div",{class:"md-tooltip",id:e},T("div",{class:"md-tooltip__inner md-typeset"}))}function ln(e,t){if(t=t?`${t}_annotation_${e}`:void 0,t){let r=t?`#${t}`:void 0;return T("aside",{class:"md-annotation",tabIndex:0},Wr(t),T("a",{href:r,class:"md-annotation__index",tabIndex:-1},T("span",{"data-md-annotation-id":e})))}else return T("aside",{class:"md-annotation",tabIndex:0},Wr(t),T("span",{class:"md-annotation__index",tabIndex:-1},T("span",{"data-md-annotation-id":e})))}function mn(e){return T("button",{class:"md-clipboard md-icon",title:be("clipboard.copy"),"data-clipboard-target":`#${e} > code`})}function Ur(e,t){let r=t&2,o=t&1,n=Object.keys(e.terms).filter(c=>!e.terms[c]).reduce((c,p)=>[...c,T("del",null,p)," "],[]).slice(0,-1),i=me(),s=new URL(e.location,i.base);te("search.highlight")&&s.searchParams.set("h",Object.entries(e.terms).filter(([,c])=>c).reduce((c,[p])=>`${c} ${p}`.trim(),""));let{tags:a}=me();return T("a",{href:`${s}`,class:"md-search-result__link",tabIndex:-1},T("article",{class:"md-search-result__article md-typeset","data-md-score":e.score.toFixed(2)},r>0&&T("div",{class:"md-search-result__icon md-icon"}),r>0&&T("h1",null,e.title),r<=0&&T("h2",null,e.title),o>0&&e.text.length>0&&e.text,e.tags&&e.tags.map(c=>{let p=a?c in a?`md-tag-icon md-tag--${a[c]}`:"md-tag-icon":"";return T("span",{class:`md-tag ${p}`},c)}),o>0&&n.length>0&&T("p",{class:"md-search-result__terms"},be("search.result.term.missing"),": ",...n)))}function fn(e){let t=e[0].score,r=[...e],o=me(),n=r.findIndex(l=>!`${new URL(l.location,o.base)}`.includes("#")),[i]=r.splice(n,1),s=r.findIndex(l=>l.scoreUr(l,1)),...c.length?[T("details",{class:"md-search-result__more"},T("summary",{tabIndex:-1},T("div",null,c.length>0&&c.length===1?be("search.result.more.one"):be("search.result.more.other",c.length))),...c.map(l=>Ur(l,1)))]:[]];return T("li",{class:"md-search-result__item"},p)}function un(e){return T("ul",{class:"md-source__facts"},Object.entries(e).map(([t,r])=>T("li",{class:`md-source__fact md-source__fact--${t}`},typeof r=="number"?tr(r):r)))}function Nr(e){let t=`tabbed-control tabbed-control--${e}`;return T("div",{class:t,hidden:!0},T("button",{class:"tabbed-button",tabIndex:-1,"aria-hidden":"true"}))}function dn(e){return T("div",{class:"md-typeset__scrollwrap"},T("div",{class:"md-typeset__table"},e))}function ba(e){let t=me(),r=new URL(`../${e.version}/`,t.base);return T("li",{class:"md-version__item"},T("a",{href:`${r}`,class:"md-version__link"},e.title))}function hn(e,t){return T("div",{class:"md-version"},T("button",{class:"md-version__current","aria-label":be("select.version")},t.title),T("ul",{class:"md-version__list"},e.map(ba)))}function va(e){return e.tagName==="CODE"?q(".c, .c1, .cm",e):[e]}function ga(e){let t=[];for(let r of va(e)){let o=[],n=document.createNodeIterator(r,NodeFilter.SHOW_TEXT);for(let i=n.nextNode();i;i=n.nextNode())o.push(i);for(let i of o){let s;for(;s=/(\(\d+\))(!)?/.exec(i.textContent);){let[,a,c]=s;if(typeof c=="undefined"){let p=i.splitText(s.index);i=p.splitText(a.length),t.push(p)}else{i.textContent=a,t.push(i);break}}}}return t}function bn(e,t){t.append(...Array.from(e.childNodes))}function sr(e,t,{target$:r,print$:o}){let n=t.closest("[id]"),i=n==null?void 0:n.id,s=new Map;for(let a of ga(t)){let[,c]=a.textContent.match(/\((\d+)\)/);ce(`:scope > li:nth-child(${c})`,e)&&(s.set(c,ln(c,i)),a.replaceWith(s.get(c)))}return s.size===0?L:H(()=>{let a=new x,c=a.pipe(Z(),re(!0)),p=[];for(let[l,f]of s)p.push([W(".md-typeset",f),W(`:scope > li:nth-child(${l})`,e)]);return o.pipe(Y(c)).subscribe(l=>{e.hidden=!l,e.classList.toggle("md-annotation-list",l);for(let[f,u]of p)l?bn(f,u):bn(u,f)}),_(...[...s].map(([,l])=>pn(l,t,{target$:r}))).pipe(A(()=>a.complete()),le())})}function vn(e){if(e.nextElementSibling){let t=e.nextElementSibling;if(t.tagName==="OL")return t;if(t.tagName==="P"&&!t.children.length)return vn(t)}}function gn(e,t){return H(()=>{let r=vn(e);return typeof r!="undefined"?sr(r,e,t):L})}var yn=Ht(Vr());var xa=0;function En(e){if(e.nextElementSibling){let t=e.nextElementSibling;if(t.tagName==="OL")return t;if(t.tagName==="P"&&!t.children.length)return En(t)}}function xn(e){return ye(e).pipe(m(({width:t})=>({scrollable:bt(e).width>t})),ee("scrollable"))}function wn(e,t){let{matches:r}=matchMedia("(hover)"),o=H(()=>{let n=new x;if(n.subscribe(({scrollable:s})=>{s&&r?e.setAttribute("tabindex","0"):e.removeAttribute("tabindex")}),yn.default.isSupported()&&(e.closest(".copy")||te("content.code.copy")&&!e.closest(".no-copy"))){let s=e.closest("pre");s.id=`__code_${xa++}`,s.insertBefore(mn(s.id),e)}let i=e.closest(".highlight");if(i instanceof HTMLElement){let s=En(i);if(typeof s!="undefined"&&(i.classList.contains("annotate")||te("content.code.annotate"))){let a=sr(s,e,t);return xn(e).pipe(w(c=>n.next(c)),A(()=>n.complete()),m(c=>R({ref:e},c)),qe(ye(i).pipe(m(({width:c,height:p})=>c&&p),X(),E(c=>c?a:L))))}}return xn(e).pipe(w(s=>n.next(s)),A(()=>n.complete()),m(s=>R({ref:e},s)))});return te("content.lazy")?rr(e).pipe(M(n=>n),xe(1),E(()=>o)):o}function ya(e,{target$:t,print$:r}){let o=!0;return _(t.pipe(m(n=>n.closest("details:not([open])")),M(n=>e===n),m(()=>({action:"open",reveal:!0}))),r.pipe(M(n=>n||!o),w(()=>o=e.open),m(n=>({action:n?"open":"close"}))))}function Sn(e,t){return H(()=>{let r=new x;return r.subscribe(({action:o,reveal:n})=>{e.toggleAttribute("open",o==="open"),n&&e.scrollIntoView()}),ya(e,t).pipe(w(o=>r.next(o)),A(()=>r.complete()),m(o=>R({ref:e},o)))})}var Tn=".node circle,.node ellipse,.node path,.node polygon,.node rect{fill:var(--md-mermaid-node-bg-color);stroke:var(--md-mermaid-node-fg-color)}marker{fill:var(--md-mermaid-edge-color)!important}.edgeLabel .label rect{fill:#0000}.label{color:var(--md-mermaid-label-fg-color);font-family:var(--md-mermaid-font-family)}.label foreignObject{line-height:normal;overflow:visible}.label div .edgeLabel{color:var(--md-mermaid-label-fg-color)}.edgeLabel,.edgeLabel rect,.label div .edgeLabel{background-color:var(--md-mermaid-label-bg-color)}.edgeLabel,.edgeLabel rect{fill:var(--md-mermaid-label-bg-color);color:var(--md-mermaid-edge-color)}.edgePath .path,.flowchart-link{stroke:var(--md-mermaid-edge-color);stroke-width:.05rem}.edgePath .arrowheadPath{fill:var(--md-mermaid-edge-color);stroke:none}.cluster rect{fill:var(--md-default-fg-color--lightest);stroke:var(--md-default-fg-color--lighter)}.cluster span{color:var(--md-mermaid-label-fg-color);font-family:var(--md-mermaid-font-family)}g #flowchart-circleEnd,g #flowchart-circleStart,g #flowchart-crossEnd,g #flowchart-crossStart,g #flowchart-pointEnd,g #flowchart-pointStart{stroke:none}g.classGroup line,g.classGroup rect{fill:var(--md-mermaid-node-bg-color);stroke:var(--md-mermaid-node-fg-color)}g.classGroup text{fill:var(--md-mermaid-label-fg-color);font-family:var(--md-mermaid-font-family)}.classLabel .box{fill:var(--md-mermaid-label-bg-color);background-color:var(--md-mermaid-label-bg-color);opacity:1}.classLabel .label{fill:var(--md-mermaid-label-fg-color);font-family:var(--md-mermaid-font-family)}.node .divider{stroke:var(--md-mermaid-node-fg-color)}.relation{stroke:var(--md-mermaid-edge-color)}.cardinality{fill:var(--md-mermaid-label-fg-color);font-family:var(--md-mermaid-font-family)}.cardinality text{fill:inherit!important}defs #classDiagram-compositionEnd,defs #classDiagram-compositionStart,defs #classDiagram-dependencyEnd,defs #classDiagram-dependencyStart,defs #classDiagram-extensionEnd,defs #classDiagram-extensionStart{fill:var(--md-mermaid-edge-color)!important;stroke:var(--md-mermaid-edge-color)!important}defs #classDiagram-aggregationEnd,defs #classDiagram-aggregationStart{fill:var(--md-mermaid-label-bg-color)!important;stroke:var(--md-mermaid-edge-color)!important}g.stateGroup rect{fill:var(--md-mermaid-node-bg-color);stroke:var(--md-mermaid-node-fg-color)}g.stateGroup .state-title{fill:var(--md-mermaid-label-fg-color)!important;font-family:var(--md-mermaid-font-family)}g.stateGroup .composit{fill:var(--md-mermaid-label-bg-color)}.nodeLabel{color:var(--md-mermaid-label-fg-color);font-family:var(--md-mermaid-font-family)}.node circle.state-end,.node circle.state-start,.start-state{fill:var(--md-mermaid-edge-color);stroke:none}.end-state-inner,.end-state-outer{fill:var(--md-mermaid-edge-color)}.end-state-inner,.node circle.state-end{stroke:var(--md-mermaid-label-bg-color)}.transition{stroke:var(--md-mermaid-edge-color)}[id^=state-fork] rect,[id^=state-join] rect{fill:var(--md-mermaid-edge-color)!important;stroke:none!important}.statediagram-cluster.statediagram-cluster .inner{fill:var(--md-default-bg-color)}.statediagram-cluster rect{fill:var(--md-mermaid-node-bg-color);stroke:var(--md-mermaid-node-fg-color)}.statediagram-state rect.divider{fill:var(--md-default-fg-color--lightest);stroke:var(--md-default-fg-color--lighter)}defs #statediagram-barbEnd{stroke:var(--md-mermaid-edge-color)}.attributeBoxEven,.attributeBoxOdd{fill:var(--md-mermaid-node-bg-color);stroke:var(--md-mermaid-node-fg-color)}.entityBox{fill:var(--md-mermaid-label-bg-color);stroke:var(--md-mermaid-node-fg-color)}.entityLabel{fill:var(--md-mermaid-label-fg-color);font-family:var(--md-mermaid-font-family)}.relationshipLabelBox{fill:var(--md-mermaid-label-bg-color);fill-opacity:1;background-color:var(--md-mermaid-label-bg-color);opacity:1}.relationshipLabel{fill:var(--md-mermaid-label-fg-color)}.relationshipLine{stroke:var(--md-mermaid-edge-color)}defs #ONE_OR_MORE_END *,defs #ONE_OR_MORE_START *,defs #ONLY_ONE_END *,defs #ONLY_ONE_START *,defs #ZERO_OR_MORE_END *,defs #ZERO_OR_MORE_START *,defs #ZERO_OR_ONE_END *,defs #ZERO_OR_ONE_START *{stroke:var(--md-mermaid-edge-color)!important}defs #ZERO_OR_MORE_END circle,defs #ZERO_OR_MORE_START circle{fill:var(--md-mermaid-label-bg-color)}.actor{fill:var(--md-mermaid-sequence-actor-bg-color);stroke:var(--md-mermaid-sequence-actor-border-color)}text.actor>tspan{fill:var(--md-mermaid-sequence-actor-fg-color);font-family:var(--md-mermaid-font-family)}line{stroke:var(--md-mermaid-sequence-actor-line-color)}.actor-man circle,.actor-man line{fill:var(--md-mermaid-sequence-actorman-bg-color);stroke:var(--md-mermaid-sequence-actorman-line-color)}.messageLine0,.messageLine1{stroke:var(--md-mermaid-sequence-message-line-color)}.note{fill:var(--md-mermaid-sequence-note-bg-color);stroke:var(--md-mermaid-sequence-note-border-color)}.loopText,.loopText>tspan,.messageText,.noteText>tspan{stroke:none;font-family:var(--md-mermaid-font-family)!important}.messageText{fill:var(--md-mermaid-sequence-message-fg-color)}.loopText,.loopText>tspan{fill:var(--md-mermaid-sequence-loop-fg-color)}.noteText>tspan{fill:var(--md-mermaid-sequence-note-fg-color)}#arrowhead path{fill:var(--md-mermaid-sequence-message-line-color);stroke:none}.loopLine{fill:var(--md-mermaid-sequence-loop-bg-color);stroke:var(--md-mermaid-sequence-loop-border-color)}.labelBox{fill:var(--md-mermaid-sequence-label-bg-color);stroke:none}.labelText,.labelText>span{fill:var(--md-mermaid-sequence-label-fg-color);font-family:var(--md-mermaid-font-family)}.sequenceNumber{fill:var(--md-mermaid-sequence-number-fg-color)}rect.rect{fill:var(--md-mermaid-sequence-box-bg-color);stroke:none}rect.rect+text.text{fill:var(--md-mermaid-sequence-box-fg-color)}defs #sequencenumber{fill:var(--md-mermaid-sequence-number-bg-color)!important}";var zr,wa=0;function Sa(){return typeof mermaid=="undefined"||mermaid instanceof Element?ht("https://unpkg.com/mermaid@9.4.3/dist/mermaid.min.js"):j(void 0)}function On(e){return e.classList.remove("mermaid"),zr||(zr=Sa().pipe(w(()=>mermaid.initialize({startOnLoad:!1,themeCSS:Tn,sequence:{actorFontSize:"16px",messageFontSize:"16px",noteFontSize:"16px"}})),m(()=>{}),J(1))),zr.subscribe(()=>{e.classList.add("mermaid");let t=`__mermaid_${wa++}`,r=T("div",{class:"mermaid"}),o=e.textContent;mermaid.mermaidAPI.render(t,o,(n,i)=>{let s=r.attachShadow({mode:"closed"});s.innerHTML=n,e.replaceWith(r),i==null||i(s)})}),zr.pipe(m(()=>({ref:e})))}var Mn=T("table");function Ln(e){return e.replaceWith(Mn),Mn.replaceWith(dn(e)),j({ref:e})}function Ta(e){let t=q(":scope > input",e),r=t.find(o=>o.checked)||t[0];return _(...t.map(o=>h(o,"change").pipe(m(()=>W(`label[for="${o.id}"]`))))).pipe(V(W(`label[for="${r.id}"]`)),m(o=>({active:o})))}function _n(e,{viewport$:t}){let r=Nr("prev");e.append(r);let o=Nr("next");e.append(o);let n=W(".tabbed-labels",e);return H(()=>{let i=new x,s=i.pipe(Z(),re(!0));return B([i,ye(e)]).pipe(Ce(1,Oe),Y(s)).subscribe({next([{active:a},c]){let p=Je(a),{width:l}=he(a);e.style.setProperty("--md-indicator-x",`${p.x}px`),e.style.setProperty("--md-indicator-width",`${l}px`);let f=er(n);(p.xf.x+c.width)&&n.scrollTo({left:Math.max(0,p.x-16),behavior:"smooth"})},complete(){e.style.removeProperty("--md-indicator-x"),e.style.removeProperty("--md-indicator-width")}}),B([dt(n),ye(n)]).pipe(Y(s)).subscribe(([a,c])=>{let p=bt(n);r.hidden=a.x<16,o.hidden=a.x>p.width-c.width-16}),_(h(r,"click").pipe(m(()=>-1)),h(o,"click").pipe(m(()=>1))).pipe(Y(s)).subscribe(a=>{let{width:c}=he(n);n.scrollBy({left:c*a,behavior:"smooth"})}),te("content.tabs.link")&&i.pipe(je(1),ne(t)).subscribe(([{active:a},{offset:c}])=>{let p=a.innerText.trim();if(a.hasAttribute("data-md-switching"))a.removeAttribute("data-md-switching");else{let l=e.offsetTop-c.y;for(let u of q("[data-tabs]"))for(let d of q(":scope > input",u)){let v=W(`label[for="${d.id}"]`);if(v!==a&&v.innerText.trim()===p){v.setAttribute("data-md-switching",""),d.click();break}}window.scrollTo({top:e.offsetTop-l});let f=__md_get("__tabs")||[];__md_set("__tabs",[...new Set([p,...f])])}}),i.pipe(Y(s)).subscribe(()=>{for(let a of q("audio, video",e))a.pause()}),Ta(e).pipe(w(a=>i.next(a)),A(()=>i.complete()),m(a=>R({ref:e},a)))}).pipe(rt(ae))}function An(e,{viewport$:t,target$:r,print$:o}){return _(...q(".annotate:not(.highlight)",e).map(n=>gn(n,{target$:r,print$:o})),...q("pre:not(.mermaid) > code",e).map(n=>wn(n,{target$:r,print$:o})),...q("pre.mermaid",e).map(n=>On(n)),...q("table:not([class])",e).map(n=>Ln(n)),...q("details",e).map(n=>Sn(n,{target$:r,print$:o})),...q("[data-tabs]",e).map(n=>_n(n,{viewport$:t})))}function Oa(e,{alert$:t}){return t.pipe(E(r=>_(j(!0),j(!1).pipe(ze(2e3))).pipe(m(o=>({message:r,active:o})))))}function Cn(e,t){let r=W(".md-typeset",e);return H(()=>{let o=new x;return o.subscribe(({message:n,active:i})=>{e.classList.toggle("md-dialog--active",i),r.textContent=n}),Oa(e,t).pipe(w(n=>o.next(n)),A(()=>o.complete()),m(n=>R({ref:e},n)))})}function Ma({viewport$:e}){if(!te("header.autohide"))return j(!1);let t=e.pipe(m(({offset:{y:n}})=>n),Le(2,1),m(([n,i])=>[nMath.abs(i-n.y)>100),m(([,[n]])=>n),X()),o=We("search");return B([e,o]).pipe(m(([{offset:n},i])=>n.y>400&&!i),X(),E(n=>n?r:j(!1)),V(!1))}function kn(e,t){return H(()=>B([ye(e),Ma(t)])).pipe(m(([{height:r},o])=>({height:r,hidden:o})),X((r,o)=>r.height===o.height&&r.hidden===o.hidden),J(1))}function Hn(e,{header$:t,main$:r}){return H(()=>{let o=new x,n=o.pipe(Z(),re(!0));return o.pipe(ee("active"),Ge(t)).subscribe(([{active:i},{hidden:s}])=>{e.classList.toggle("md-header--shadow",i&&!s),e.hidden=s}),r.subscribe(o),t.pipe(Y(n),m(i=>R({ref:e},i)))})}function La(e,{viewport$:t,header$:r}){return ar(e,{viewport$:t,header$:r}).pipe(m(({offset:{y:o}})=>{let{height:n}=he(e);return{active:o>=n}}),ee("active"))}function $n(e,t){return H(()=>{let r=new x;r.subscribe({next({active:n}){e.classList.toggle("md-header__title--active",n)},complete(){e.classList.remove("md-header__title--active")}});let o=ce(".md-content h1");return typeof o=="undefined"?L:La(o,t).pipe(w(n=>r.next(n)),A(()=>r.complete()),m(n=>R({ref:e},n)))})}function Rn(e,{viewport$:t,header$:r}){let o=r.pipe(m(({height:i})=>i),X()),n=o.pipe(E(()=>ye(e).pipe(m(({height:i})=>({top:e.offsetTop,bottom:e.offsetTop+i})),ee("bottom"))));return B([o,n,t]).pipe(m(([i,{top:s,bottom:a},{offset:{y:c},size:{height:p}}])=>(p=Math.max(0,p-Math.max(0,s-c,i)-Math.max(0,p+c-a)),{offset:s-i,height:p,active:s-i<=c})),X((i,s)=>i.offset===s.offset&&i.height===s.height&&i.active===s.active))}function _a(e){let t=__md_get("__palette")||{index:e.findIndex(r=>matchMedia(r.getAttribute("data-md-color-media")).matches)};return j(...e).pipe(se(r=>h(r,"change").pipe(m(()=>r))),V(e[Math.max(0,t.index)]),m(r=>({index:e.indexOf(r),color:{scheme:r.getAttribute("data-md-color-scheme"),primary:r.getAttribute("data-md-color-primary"),accent:r.getAttribute("data-md-color-accent")}})),J(1))}function Pn(e){let t=T("meta",{name:"theme-color"});document.head.appendChild(t);let r=T("meta",{name:"color-scheme"});return document.head.appendChild(r),H(()=>{let o=new x;o.subscribe(i=>{document.body.setAttribute("data-md-color-switching","");for(let[s,a]of Object.entries(i.color))document.body.setAttribute(`data-md-color-${s}`,a);for(let s=0;s{let i=Ee("header"),s=window.getComputedStyle(i);return r.content=s.colorScheme,s.backgroundColor.match(/\d+/g).map(a=>(+a).toString(16).padStart(2,"0")).join("")})).subscribe(i=>t.content=`#${i}`),o.pipe(Se(ae)).subscribe(()=>{document.body.removeAttribute("data-md-color-switching")});let n=q("input",e);return _a(n).pipe(w(i=>o.next(i)),A(()=>o.complete()),m(i=>R({ref:e},i)))})}function In(e,{progress$:t}){return H(()=>{let r=new x;return r.subscribe(({value:o})=>{e.style.setProperty("--md-progress-value",`${o}`)}),t.pipe(w(o=>r.next({value:o})),A(()=>r.complete()),m(o=>({ref:e,value:o})))})}var qr=Ht(Vr());function Aa(e){e.setAttribute("data-md-copying","");let t=e.closest("[data-copy]"),r=t?t.getAttribute("data-copy"):e.innerText;return e.removeAttribute("data-md-copying"),r}function Fn({alert$:e}){qr.default.isSupported()&&new P(t=>{new qr.default("[data-clipboard-target], [data-clipboard-text]",{text:r=>r.getAttribute("data-clipboard-text")||Aa(W(r.getAttribute("data-clipboard-target")))}).on("success",r=>t.next(r))}).pipe(w(t=>{t.trigger.focus()}),m(()=>be("clipboard.copied"))).subscribe(e)}function Ca(e){if(e.length<2)return[""];let[t,r]=[...e].sort((n,i)=>n.length-i.length).map(n=>n.replace(/[^/]+$/,"")),o=0;if(t===r)o=t.length;else for(;t.charCodeAt(o)===r.charCodeAt(o);)o++;return e.map(n=>n.replace(t.slice(0,o),""))}function cr(e){let t=__md_get("__sitemap",sessionStorage,e);if(t)return j(t);{let r=me();return Zo(new URL("sitemap.xml",e||r.base)).pipe(m(o=>Ca(q("loc",o).map(n=>n.textContent))),de(()=>L),He([]),w(o=>__md_set("__sitemap",o,sessionStorage,e)))}}function jn(e){let t=W("[rel=canonical]",e);t.href=t.href.replace("//localhost:","//127.0.0.1");let r=new Map;for(let o of q(":scope > *",e)){let n=o.outerHTML;for(let i of["href","src"]){let s=o.getAttribute(i);if(s===null)continue;let a=new URL(s,t.href),c=o.cloneNode();c.setAttribute(i,`${a}`),n=c.outerHTML;break}r.set(n,o)}return r}function Wn({location$:e,viewport$:t,progress$:r}){let o=me();if(location.protocol==="file:")return L;let n=cr().pipe(m(l=>l.map(f=>`${new URL(f,o.base)}`))),i=h(document.body,"click").pipe(ne(n),E(([l,f])=>{if(!(l.target instanceof Element))return L;let u=l.target.closest("a");if(u===null)return L;if(u.target||l.metaKey||l.ctrlKey)return L;let d=new URL(u.href);return d.search=d.hash="",f.includes(`${d}`)?(l.preventDefault(),j(new URL(u.href))):L}),le());i.pipe(xe(1)).subscribe(()=>{let l=ce("link[rel=icon]");typeof l!="undefined"&&(l.href=l.href)}),h(window,"beforeunload").subscribe(()=>{history.scrollRestoration="auto"}),i.pipe(ne(t)).subscribe(([l,{offset:f}])=>{history.scrollRestoration="manual",history.replaceState(f,""),history.pushState(null,"",l)}),i.subscribe(e);let s=e.pipe(V(pe()),ee("pathname"),je(1),E(l=>ir(l,{progress$:r}).pipe(de(()=>(ot(l,!0),L))))),a=new DOMParser,c=s.pipe(E(l=>l.text()),E(l=>{let f=a.parseFromString(l,"text/html");for(let b of["[data-md-component=announce]","[data-md-component=container]","[data-md-component=header-topic]","[data-md-component=outdated]","[data-md-component=logo]","[data-md-component=skip]",...te("navigation.tabs.sticky")?["[data-md-component=tabs]"]:[]]){let z=ce(b),K=ce(b,f);typeof z!="undefined"&&typeof K!="undefined"&&z.replaceWith(K)}let u=jn(document.head),d=jn(f.head);for(let[b,z]of d)z.getAttribute("rel")==="stylesheet"||z.hasAttribute("src")||(u.has(b)?u.delete(b):document.head.appendChild(z));for(let b of u.values())b.getAttribute("rel")==="stylesheet"||b.hasAttribute("src")||b.remove();let v=Ee("container");return Fe(q("script",v)).pipe(E(b=>{let z=f.createElement("script");if(b.src){for(let K of b.getAttributeNames())z.setAttribute(K,b.getAttribute(K));return b.replaceWith(z),new P(K=>{z.onload=()=>K.complete()})}else return z.textContent=b.textContent,b.replaceWith(z),L}),Z(),re(f))}),le());return h(window,"popstate").pipe(m(pe)).subscribe(e),e.pipe(V(pe()),Le(2,1),M(([l,f])=>l.pathname===f.pathname&&l.hash!==f.hash),m(([,l])=>l)).subscribe(l=>{var f,u;history.state!==null||!l.hash?window.scrollTo(0,(u=(f=history.state)==null?void 0:f.y)!=null?u:0):(history.scrollRestoration="auto",nr(l.hash),history.scrollRestoration="manual")}),e.pipe(Cr(i),V(pe()),Le(2,1),M(([l,f])=>l.pathname===f.pathname&&l.hash===f.hash),m(([,l])=>l)).subscribe(l=>{history.scrollRestoration="auto",nr(l.hash),history.scrollRestoration="manual",history.back()}),c.pipe(ne(e)).subscribe(([,l])=>{var f,u;history.state!==null||!l.hash?window.scrollTo(0,(u=(f=history.state)==null?void 0:f.y)!=null?u:0):nr(l.hash)}),t.pipe(ee("offset"),ke(100)).subscribe(({offset:l})=>{history.replaceState(l,"")}),c}var Dn=Ht(Nn());function Vn(e){let t=e.separator.split("|").map(n=>n.replace(/(\(\?[!=<][^)]+\))/g,"").length===0?"\uFFFD":n).join("|"),r=new RegExp(t,"img"),o=(n,i,s)=>`${i}${s}`;return n=>{n=n.replace(/[\s*+\-:~^]+/g," ").trim();let i=new RegExp(`(^|${e.separator}|)(${n.replace(/[|\\{}()[\]^$+*?.-]/g,"\\$&").replace(r,"|")})`,"img");return s=>(0,Dn.default)(s).replace(i,o).replace(/<\/mark>(\s+)]*>/img,"$1")}}function Mt(e){return e.type===1}function pr(e){return e.type===3}function zn(e,t){let r=an(e);return _(j(location.protocol!=="file:"),We("search")).pipe($e(o=>o),E(()=>t)).subscribe(({config:o,docs:n})=>r.next({type:0,data:{config:o,docs:n,options:{suggest:te("search.suggest")}}})),r}function qn({document$:e}){let t=me(),r=Ue(new URL("../versions.json",t.base)).pipe(de(()=>L)),o=r.pipe(m(n=>{let[,i]=t.base.match(/([^/]+)\/?$/);return n.find(({version:s,aliases:a})=>s===i||a.includes(i))||n[0]}));r.pipe(m(n=>new Map(n.map(i=>[`${new URL(`../${i.version}/`,t.base)}`,i]))),E(n=>h(document.body,"click").pipe(M(i=>!i.metaKey&&!i.ctrlKey),ne(o),E(([i,s])=>{if(i.target instanceof Element){let a=i.target.closest("a");if(a&&!a.target&&n.has(a.href)){let c=a.href;return!i.target.closest(".md-version")&&n.get(c)===s?L:(i.preventDefault(),j(c))}}return L}),E(i=>{let{version:s}=n.get(i);return cr(new URL(i)).pipe(m(a=>{let p=pe().href.replace(t.base,"");return a.includes(p.split("#")[0])?new URL(`../${s}/${p}`,t.base):new URL(i)}))})))).subscribe(n=>ot(n,!0)),B([r,o]).subscribe(([n,i])=>{W(".md-header__topic").appendChild(hn(n,i))}),e.pipe(E(()=>o)).subscribe(n=>{var s;let i=__md_get("__outdated",sessionStorage);if(i===null){i=!0;let a=((s=t.version)==null?void 0:s.default)||"latest";Array.isArray(a)||(a=[a]);e:for(let c of a)for(let p of n.aliases)if(new RegExp(c,"i").test(p)){i=!1;break e}__md_set("__outdated",i,sessionStorage)}if(i)for(let a of oe("outdated"))a.hidden=!1})}function Pa(e,{worker$:t}){let{searchParams:r}=pe();r.has("q")&&(Ke("search",!0),e.value=r.get("q"),e.focus(),We("search").pipe($e(i=>!i)).subscribe(()=>{let i=pe();i.searchParams.delete("q"),history.replaceState({},"",`${i}`)}));let o=Zt(e),n=_(t.pipe($e(Mt)),h(e,"keyup"),o).pipe(m(()=>e.value),X());return B([n,o]).pipe(m(([i,s])=>({value:i,focus:s})),J(1))}function Kn(e,{worker$:t}){let r=new x,o=r.pipe(Z(),re(!0));B([t.pipe($e(Mt)),r],(i,s)=>s).pipe(ee("value")).subscribe(({value:i})=>t.next({type:2,data:i})),r.pipe(ee("focus")).subscribe(({focus:i})=>{i&&Ke("search",i)}),h(e.form,"reset").pipe(Y(o)).subscribe(()=>e.focus());let n=W("header [for=__search]");return h(n,"click").subscribe(()=>e.focus()),Pa(e,{worker$:t}).pipe(w(i=>r.next(i)),A(()=>r.complete()),m(i=>R({ref:e},i)),J(1))}function Qn(e,{worker$:t,query$:r}){let o=new x,n=Ko(e.parentElement).pipe(M(Boolean)),i=e.parentElement,s=W(":scope > :first-child",e),a=W(":scope > :last-child",e);We("search").subscribe(l=>a.setAttribute("role",l?"list":"presentation")),o.pipe(ne(r),$r(t.pipe($e(Mt)))).subscribe(([{items:l},{value:f}])=>{switch(l.length){case 0:s.textContent=f.length?be("search.result.none"):be("search.result.placeholder");break;case 1:s.textContent=be("search.result.one");break;default:let u=tr(l.length);s.textContent=be("search.result.other",u)}});let c=o.pipe(w(()=>a.innerHTML=""),E(({items:l})=>_(j(...l.slice(0,10)),j(...l.slice(10)).pipe(Le(4),Ir(n),E(([f])=>f)))),m(fn),le());return c.subscribe(l=>a.appendChild(l)),c.pipe(se(l=>{let f=ce("details",l);return typeof f=="undefined"?L:h(f,"toggle").pipe(Y(o),m(()=>f))})).subscribe(l=>{l.open===!1&&l.offsetTop<=i.scrollTop&&i.scrollTo({top:l.offsetTop})}),t.pipe(M(pr),m(({data:l})=>l)).pipe(w(l=>o.next(l)),A(()=>o.complete()),m(l=>R({ref:e},l)))}function Ia(e,{query$:t}){return t.pipe(m(({value:r})=>{let o=pe();return o.hash="",r=r.replace(/\s+/g,"+").replace(/&/g,"%26").replace(/=/g,"%3D"),o.search=`q=${r}`,{url:o}}))}function Yn(e,t){let r=new x,o=r.pipe(Z(),re(!0));return r.subscribe(({url:n})=>{e.setAttribute("data-clipboard-text",e.href),e.href=`${n}`}),h(e,"click").pipe(Y(o)).subscribe(n=>n.preventDefault()),Ia(e,t).pipe(w(n=>r.next(n)),A(()=>r.complete()),m(n=>R({ref:e},n)))}function Bn(e,{worker$:t,keyboard$:r}){let o=new x,n=Ee("search-query"),i=_(h(n,"keydown"),h(n,"focus")).pipe(Se(ae),m(()=>n.value),X());return o.pipe(Ge(i),m(([{suggest:a},c])=>{let p=c.split(/([\s-]+)/);if(a!=null&&a.length&&p[p.length-1]){let l=a[a.length-1];l.startsWith(p[p.length-1])&&(p[p.length-1]=l)}else p.length=0;return p})).subscribe(a=>e.innerHTML=a.join("").replace(/\s/g," ")),r.pipe(M(({mode:a})=>a==="search")).subscribe(a=>{switch(a.type){case"ArrowRight":e.innerText.length&&n.selectionStart===n.value.length&&(n.value=e.innerText);break}}),t.pipe(M(pr),m(({data:a})=>a)).pipe(w(a=>o.next(a)),A(()=>o.complete()),m(()=>({ref:e})))}function Gn(e,{index$:t,keyboard$:r}){let o=me();try{let n=zn(o.search,t),i=Ee("search-query",e),s=Ee("search-result",e);h(e,"click").pipe(M(({target:c})=>c instanceof Element&&!!c.closest("a"))).subscribe(()=>Ke("search",!1)),r.pipe(M(({mode:c})=>c==="search")).subscribe(c=>{let p=Re();switch(c.type){case"Enter":if(p===i){let l=new Map;for(let f of q(":first-child [href]",s)){let u=f.firstElementChild;l.set(f,parseFloat(u.getAttribute("data-md-score")))}if(l.size){let[[f]]=[...l].sort(([,u],[,d])=>d-u);f.click()}c.claim()}break;case"Escape":case"Tab":Ke("search",!1),i.blur();break;case"ArrowUp":case"ArrowDown":if(typeof p=="undefined")i.focus();else{let l=[i,...q(":not(details) > [href], summary, details[open] [href]",s)],f=Math.max(0,(Math.max(0,l.indexOf(p))+l.length+(c.type==="ArrowUp"?-1:1))%l.length);l[f].focus()}c.claim();break;default:i!==Re()&&i.focus()}}),r.pipe(M(({mode:c})=>c==="global")).subscribe(c=>{switch(c.type){case"f":case"s":case"/":i.focus(),i.select(),c.claim();break}});let a=Kn(i,{worker$:n});return _(a,Qn(s,{worker$:n,query$:a})).pipe(qe(...oe("search-share",e).map(c=>Yn(c,{query$:a})),...oe("search-suggest",e).map(c=>Bn(c,{worker$:n,keyboard$:r}))))}catch(n){return e.hidden=!0,Ve}}function Jn(e,{index$:t,location$:r}){return B([t,r.pipe(V(pe()),M(o=>!!o.searchParams.get("h")))]).pipe(m(([o,n])=>Vn(o.config)(n.searchParams.get("h"))),m(o=>{var s;let n=new Map,i=document.createNodeIterator(e,NodeFilter.SHOW_TEXT);for(let a=i.nextNode();a;a=i.nextNode())if((s=a.parentElement)!=null&&s.offsetHeight){let c=a.textContent,p=o(c);p.length>c.length&&n.set(a,p)}for(let[a,c]of n){let{childNodes:p}=T("span",null,c);a.replaceWith(...Array.from(p))}return{ref:e,nodes:n}}))}function Fa(e,{viewport$:t,main$:r}){let o=e.closest(".md-grid"),n=o.offsetTop-o.parentElement.offsetTop;return B([r,t]).pipe(m(([{offset:i,height:s},{offset:{y:a}}])=>(s=s+Math.min(n,Math.max(0,a-i))-n,{height:s,locked:a>=i+n})),X((i,s)=>i.height===s.height&&i.locked===s.locked))}function Kr(e,o){var n=o,{header$:t}=n,r=eo(n,["header$"]);let i=W(".md-sidebar__scrollwrap",e),{y:s}=Je(i);return H(()=>{let a=new x,c=a.pipe(Z(),re(!0)),p=a.pipe(Ce(0,Oe));return p.pipe(ne(t)).subscribe({next([{height:l},{height:f}]){i.style.height=`${l-2*s}px`,e.style.top=`${f}px`},complete(){i.style.height="",e.style.top=""}}),p.pipe($e()).subscribe(()=>{for(let l of q(".md-nav__link--active[href]",e)){if(!l.clientHeight)continue;let f=l.closest(".md-sidebar__scrollwrap");if(typeof f!="undefined"){let u=l.offsetTop-f.offsetTop,{height:d}=he(f);f.scrollTo({top:u-d/2})}}}),ge(q("label[tabindex]",e)).pipe(se(l=>h(l,"click").pipe(Se(ae),m(()=>l),Y(c)))).subscribe(l=>{let f=W(`[id="${l.htmlFor}"]`);W(`[aria-labelledby="${l.id}"]`).setAttribute("aria-expanded",`${f.checked}`)}),Fa(e,r).pipe(w(l=>a.next(l)),A(()=>a.complete()),m(l=>R({ref:e},l)))})}function Xn(e,t){if(typeof t!="undefined"){let r=`https://api.github.com/repos/${e}/${t}`;return St(Ue(`${r}/releases/latest`).pipe(de(()=>L),m(o=>({version:o.tag_name})),He({})),Ue(r).pipe(de(()=>L),m(o=>({stars:o.stargazers_count,forks:o.forks_count})),He({}))).pipe(m(([o,n])=>R(R({},o),n)))}else{let r=`https://api.github.com/users/${e}`;return Ue(r).pipe(m(o=>({repositories:o.public_repos})),He({}))}}function Zn(e,t){let r=`https://${e}/api/v4/projects/${encodeURIComponent(t)}`;return Ue(r).pipe(de(()=>L),m(({star_count:o,forks_count:n})=>({stars:o,forks:n})),He({}))}function ei(e){let t=e.match(/^.+github\.com\/([^/]+)\/?([^/]+)?/i);if(t){let[,r,o]=t;return Xn(r,o)}if(t=e.match(/^.+?([^/]*gitlab[^/]+)\/(.+?)\/?$/i),t){let[,r,o]=t;return Zn(r,o)}return L}var ja;function Wa(e){return ja||(ja=H(()=>{let t=__md_get("__source",sessionStorage);if(t)return j(t);if(oe("consent").length){let o=__md_get("__consent");if(!(o&&o.github))return L}return ei(e.href).pipe(w(o=>__md_set("__source",o,sessionStorage)))}).pipe(de(()=>L),M(t=>Object.keys(t).length>0),m(t=>({facts:t})),J(1)))}function ti(e){let t=W(":scope > :last-child",e);return H(()=>{let r=new x;return r.subscribe(({facts:o})=>{t.appendChild(un(o)),t.classList.add("md-source__repository--active")}),Wa(e).pipe(w(o=>r.next(o)),A(()=>r.complete()),m(o=>R({ref:e},o)))})}function Ua(e,{viewport$:t,header$:r}){return ye(document.body).pipe(E(()=>ar(e,{header$:r,viewport$:t})),m(({offset:{y:o}})=>({hidden:o>=10})),ee("hidden"))}function ri(e,t){return H(()=>{let r=new x;return r.subscribe({next({hidden:o}){e.hidden=o},complete(){e.hidden=!1}}),(te("navigation.tabs.sticky")?j({hidden:!1}):Ua(e,t)).pipe(w(o=>r.next(o)),A(()=>r.complete()),m(o=>R({ref:e},o)))})}function Na(e,{viewport$:t,header$:r}){let o=new Map,n=q("[href^=\\#]",e);for(let a of n){let c=decodeURIComponent(a.hash.substring(1)),p=ce(`[id="${c}"]`);typeof p!="undefined"&&o.set(a,p)}let i=r.pipe(ee("height"),m(({height:a})=>{let c=Ee("main"),p=W(":scope > :first-child",c);return a+.8*(p.offsetTop-c.offsetTop)}),le());return ye(document.body).pipe(ee("height"),E(a=>H(()=>{let c=[];return j([...o].reduce((p,[l,f])=>{for(;c.length&&o.get(c[c.length-1]).tagName>=f.tagName;)c.pop();let u=f.offsetTop;for(;!u&&f.parentElement;)f=f.parentElement,u=f.offsetTop;let d=f.offsetParent;for(;d;d=d.offsetParent)u+=d.offsetTop;return p.set([...c=[...c,l]].reverse(),u)},new Map))}).pipe(m(c=>new Map([...c].sort(([,p],[,l])=>p-l))),Ge(i),E(([c,p])=>t.pipe(kr(([l,f],{offset:{y:u},size:d})=>{let v=u+d.height>=Math.floor(a.height);for(;f.length;){let[,b]=f[0];if(b-p=u&&!v)f=[l.pop(),...f];else break}return[l,f]},[[],[...c]]),X((l,f)=>l[0]===f[0]&&l[1]===f[1])))))).pipe(m(([a,c])=>({prev:a.map(([p])=>p),next:c.map(([p])=>p)})),V({prev:[],next:[]}),Le(2,1),m(([a,c])=>a.prev.length{let i=new x,s=i.pipe(Z(),re(!0));if(i.subscribe(({prev:a,next:c})=>{for(let[p]of c)p.classList.remove("md-nav__link--passed"),p.classList.remove("md-nav__link--active");for(let[p,[l]]of a.entries())l.classList.add("md-nav__link--passed"),l.classList.toggle("md-nav__link--active",p===a.length-1)}),te("toc.follow")){let a=_(t.pipe(ke(1),m(()=>{})),t.pipe(ke(250),m(()=>"smooth")));i.pipe(M(({prev:c})=>c.length>0),Ge(o.pipe(Se(ae))),ne(a)).subscribe(([[{prev:c}],p])=>{let[l]=c[c.length-1];if(l.offsetHeight){let f=zo(l);if(typeof f!="undefined"){let u=l.offsetTop-f.offsetTop,{height:d}=he(f);f.scrollTo({top:u-d/2,behavior:p})}}})}return te("navigation.tracking")&&t.pipe(Y(s),ee("offset"),ke(250),je(1),Y(n.pipe(je(1))),Tt({delay:250}),ne(i)).subscribe(([,{prev:a}])=>{let c=pe(),p=a[a.length-1];if(p&&p.length){let[l]=p,{hash:f}=new URL(l.href);c.hash!==f&&(c.hash=f,history.replaceState({},"",`${c}`))}else c.hash="",history.replaceState({},"",`${c}`)}),Na(e,{viewport$:t,header$:r}).pipe(w(a=>i.next(a)),A(()=>i.complete()),m(a=>R({ref:e},a)))})}function Da(e,{viewport$:t,main$:r,target$:o}){let n=t.pipe(m(({offset:{y:s}})=>s),Le(2,1),m(([s,a])=>s>a&&a>0),X()),i=r.pipe(m(({active:s})=>s));return B([i,n]).pipe(m(([s,a])=>!(s&&a)),X(),Y(o.pipe(je(1))),re(!0),Tt({delay:250}),m(s=>({hidden:s})))}function ni(e,{viewport$:t,header$:r,main$:o,target$:n}){let i=new x,s=i.pipe(Z(),re(!0));return i.subscribe({next({hidden:a}){e.hidden=a,a?(e.setAttribute("tabindex","-1"),e.blur()):e.removeAttribute("tabindex")},complete(){e.style.top="",e.hidden=!0,e.removeAttribute("tabindex")}}),r.pipe(Y(s),ee("height")).subscribe(({height:a})=>{e.style.top=`${a+16}px`}),h(e,"click").subscribe(a=>{a.preventDefault(),window.scrollTo({top:0})}),Da(e,{viewport$:t,main$:o,target$:n}).pipe(w(a=>i.next(a)),A(()=>i.complete()),m(a=>R({ref:e},a)))}function ii({document$:e,tablet$:t}){e.pipe(E(()=>q(".md-toggle--indeterminate")),w(r=>{r.indeterminate=!0,r.checked=!1}),se(r=>h(r,"change").pipe(Rr(()=>r.classList.contains("md-toggle--indeterminate")),m(()=>r))),ne(t)).subscribe(([r,o])=>{r.classList.remove("md-toggle--indeterminate"),o&&(r.checked=!1)})}function Va(){return/(iPad|iPhone|iPod)/.test(navigator.userAgent)}function ai({document$:e}){e.pipe(E(()=>q("[data-md-scrollfix]")),w(t=>t.removeAttribute("data-md-scrollfix")),M(Va),se(t=>h(t,"touchstart").pipe(m(()=>t)))).subscribe(t=>{let r=t.scrollTop;r===0?t.scrollTop=1:r+t.offsetHeight===t.scrollHeight&&(t.scrollTop=r-1)})}function si({viewport$:e,tablet$:t}){B([We("search"),t]).pipe(m(([r,o])=>r&&!o),E(r=>j(r).pipe(ze(r?400:100))),ne(e)).subscribe(([r,{offset:{y:o}}])=>{if(r)document.body.setAttribute("data-md-scrolllock",""),document.body.style.top=`-${o}px`;else{let n=-1*parseInt(document.body.style.top,10);document.body.removeAttribute("data-md-scrolllock"),document.body.style.top="",n&&window.scrollTo(0,n)}})}Object.entries||(Object.entries=function(e){let t=[];for(let r of Object.keys(e))t.push([r,e[r]]);return t});Object.values||(Object.values=function(e){let t=[];for(let r of Object.keys(e))t.push(e[r]);return t});typeof Element!="undefined"&&(Element.prototype.scrollTo||(Element.prototype.scrollTo=function(e,t){typeof e=="object"?(this.scrollLeft=e.left,this.scrollTop=e.top):(this.scrollLeft=e,this.scrollTop=t)}),Element.prototype.replaceWith||(Element.prototype.replaceWith=function(...e){let t=this.parentNode;if(t){e.length===0&&t.removeChild(this);for(let r=e.length-1;r>=0;r--){let o=e[r];typeof o=="string"?o=document.createTextNode(o):o.parentNode&&o.parentNode.removeChild(o),r?t.insertBefore(this.previousSibling,o):t.replaceChild(o,this)}}}));function za(){return location.protocol==="file:"?ht(`${new URL("search/search_index.js",Qr.base)}`).pipe(m(()=>__index),J(1)):Ue(new URL("search/search_index.json",Qr.base))}document.documentElement.classList.remove("no-js");document.documentElement.classList.add("js");var nt=Uo(),_t=Bo(),gt=Jo(_t),Yr=Yo(),Te=nn(),lr=Fr("(min-width: 960px)"),pi=Fr("(min-width: 1220px)"),li=Xo(),Qr=me(),mi=document.forms.namedItem("search")?za():Ve,Br=new x;Fn({alert$:Br});var Gr=new x;te("navigation.instant")&&Wn({location$:_t,viewport$:Te,progress$:Gr}).subscribe(nt);var ci;((ci=Qr.version)==null?void 0:ci.provider)==="mike"&&qn({document$:nt});_(_t,gt).pipe(ze(125)).subscribe(()=>{Ke("drawer",!1),Ke("search",!1)});Yr.pipe(M(({mode:e})=>e==="global")).subscribe(e=>{switch(e.type){case"p":case",":let t=ce("link[rel=prev]");typeof t!="undefined"&&ot(t);break;case"n":case".":let r=ce("link[rel=next]");typeof r!="undefined"&&ot(r);break;case"Enter":let o=Re();o instanceof HTMLLabelElement&&o.click()}});ii({document$:nt,tablet$:lr});ai({document$:nt});si({viewport$:Te,tablet$:lr});var Xe=kn(Ee("header"),{viewport$:Te}),Lt=nt.pipe(m(()=>Ee("main")),E(e=>Rn(e,{viewport$:Te,header$:Xe})),J(1)),qa=_(...oe("consent").map(e=>cn(e,{target$:gt})),...oe("dialog").map(e=>Cn(e,{alert$:Br})),...oe("header").map(e=>Hn(e,{viewport$:Te,header$:Xe,main$:Lt})),...oe("palette").map(e=>Pn(e)),...oe("progress").map(e=>In(e,{progress$:Gr})),...oe("search").map(e=>Gn(e,{index$:mi,keyboard$:Yr})),...oe("source").map(e=>ti(e))),Ka=H(()=>_(...oe("announce").map(e=>sn(e)),...oe("content").map(e=>An(e,{viewport$:Te,target$:gt,print$:li})),...oe("content").map(e=>te("search.highlight")?Jn(e,{index$:mi,location$:_t}):L),...oe("header-title").map(e=>$n(e,{viewport$:Te,header$:Xe})),...oe("sidebar").map(e=>e.getAttribute("data-md-type")==="navigation"?jr(pi,()=>Kr(e,{viewport$:Te,header$:Xe,main$:Lt})):jr(lr,()=>Kr(e,{viewport$:Te,header$:Xe,main$:Lt}))),...oe("tabs").map(e=>ri(e,{viewport$:Te,header$:Xe})),...oe("toc").map(e=>oi(e,{viewport$:Te,header$:Xe,main$:Lt,target$:gt})),...oe("top").map(e=>ni(e,{viewport$:Te,header$:Xe,main$:Lt,target$:gt})))),fi=nt.pipe(E(()=>Ka),qe(qa),J(1));fi.subscribe();window.document$=nt;window.location$=_t;window.target$=gt;window.keyboard$=Yr;window.viewport$=Te;window.tablet$=lr;window.screen$=pi;window.print$=li;window.alert$=Br;window.progress$=Gr;window.component$=fi;})(); +//# sourceMappingURL=bundle.aecac24b.min.js.map + diff --git a/assets/javascripts/bundle.aecac24b.min.js.map b/assets/javascripts/bundle.aecac24b.min.js.map new file mode 100644 index 000000000..b1534de53 --- /dev/null +++ b/assets/javascripts/bundle.aecac24b.min.js.map @@ -0,0 +1,7 @@ +{ + "version": 3, + "sources": ["node_modules/focus-visible/dist/focus-visible.js", "node_modules/clipboard/dist/clipboard.js", "node_modules/escape-html/index.js", "src/templates/assets/javascripts/bundle.ts", "node_modules/rxjs/node_modules/tslib/tslib.es6.js", "node_modules/rxjs/src/internal/util/isFunction.ts", "node_modules/rxjs/src/internal/util/createErrorClass.ts", "node_modules/rxjs/src/internal/util/UnsubscriptionError.ts", "node_modules/rxjs/src/internal/util/arrRemove.ts", "node_modules/rxjs/src/internal/Subscription.ts", "node_modules/rxjs/src/internal/config.ts", "node_modules/rxjs/src/internal/scheduler/timeoutProvider.ts", "node_modules/rxjs/src/internal/util/reportUnhandledError.ts", "node_modules/rxjs/src/internal/util/noop.ts", "node_modules/rxjs/src/internal/NotificationFactories.ts", "node_modules/rxjs/src/internal/util/errorContext.ts", "node_modules/rxjs/src/internal/Subscriber.ts", "node_modules/rxjs/src/internal/symbol/observable.ts", "node_modules/rxjs/src/internal/util/identity.ts", "node_modules/rxjs/src/internal/util/pipe.ts", "node_modules/rxjs/src/internal/Observable.ts", "node_modules/rxjs/src/internal/util/lift.ts", "node_modules/rxjs/src/internal/operators/OperatorSubscriber.ts", "node_modules/rxjs/src/internal/scheduler/animationFrameProvider.ts", "node_modules/rxjs/src/internal/util/ObjectUnsubscribedError.ts", "node_modules/rxjs/src/internal/Subject.ts", "node_modules/rxjs/src/internal/scheduler/dateTimestampProvider.ts", "node_modules/rxjs/src/internal/ReplaySubject.ts", "node_modules/rxjs/src/internal/scheduler/Action.ts", "node_modules/rxjs/src/internal/scheduler/intervalProvider.ts", "node_modules/rxjs/src/internal/scheduler/AsyncAction.ts", "node_modules/rxjs/src/internal/Scheduler.ts", "node_modules/rxjs/src/internal/scheduler/AsyncScheduler.ts", "node_modules/rxjs/src/internal/scheduler/async.ts", "node_modules/rxjs/src/internal/scheduler/AnimationFrameAction.ts", "node_modules/rxjs/src/internal/scheduler/AnimationFrameScheduler.ts", "node_modules/rxjs/src/internal/scheduler/animationFrame.ts", "node_modules/rxjs/src/internal/observable/empty.ts", "node_modules/rxjs/src/internal/util/isScheduler.ts", "node_modules/rxjs/src/internal/util/args.ts", "node_modules/rxjs/src/internal/util/isArrayLike.ts", "node_modules/rxjs/src/internal/util/isPromise.ts", "node_modules/rxjs/src/internal/util/isInteropObservable.ts", "node_modules/rxjs/src/internal/util/isAsyncIterable.ts", "node_modules/rxjs/src/internal/util/throwUnobservableError.ts", "node_modules/rxjs/src/internal/symbol/iterator.ts", "node_modules/rxjs/src/internal/util/isIterable.ts", "node_modules/rxjs/src/internal/util/isReadableStreamLike.ts", "node_modules/rxjs/src/internal/observable/innerFrom.ts", "node_modules/rxjs/src/internal/util/executeSchedule.ts", "node_modules/rxjs/src/internal/operators/observeOn.ts", "node_modules/rxjs/src/internal/operators/subscribeOn.ts", "node_modules/rxjs/src/internal/scheduled/scheduleObservable.ts", "node_modules/rxjs/src/internal/scheduled/schedulePromise.ts", "node_modules/rxjs/src/internal/scheduled/scheduleArray.ts", "node_modules/rxjs/src/internal/scheduled/scheduleIterable.ts", "node_modules/rxjs/src/internal/scheduled/scheduleAsyncIterable.ts", "node_modules/rxjs/src/internal/scheduled/scheduleReadableStreamLike.ts", "node_modules/rxjs/src/internal/scheduled/scheduled.ts", "node_modules/rxjs/src/internal/observable/from.ts", "node_modules/rxjs/src/internal/observable/of.ts", "node_modules/rxjs/src/internal/observable/throwError.ts", "node_modules/rxjs/src/internal/util/EmptyError.ts", "node_modules/rxjs/src/internal/util/isDate.ts", "node_modules/rxjs/src/internal/operators/map.ts", "node_modules/rxjs/src/internal/util/mapOneOrManyArgs.ts", "node_modules/rxjs/src/internal/util/argsArgArrayOrObject.ts", "node_modules/rxjs/src/internal/util/createObject.ts", "node_modules/rxjs/src/internal/observable/combineLatest.ts", "node_modules/rxjs/src/internal/operators/mergeInternals.ts", "node_modules/rxjs/src/internal/operators/mergeMap.ts", "node_modules/rxjs/src/internal/operators/mergeAll.ts", "node_modules/rxjs/src/internal/operators/concatAll.ts", "node_modules/rxjs/src/internal/observable/concat.ts", "node_modules/rxjs/src/internal/observable/defer.ts", "node_modules/rxjs/src/internal/observable/fromEvent.ts", "node_modules/rxjs/src/internal/observable/fromEventPattern.ts", "node_modules/rxjs/src/internal/observable/timer.ts", "node_modules/rxjs/src/internal/observable/merge.ts", "node_modules/rxjs/src/internal/observable/never.ts", "node_modules/rxjs/src/internal/util/argsOrArgArray.ts", "node_modules/rxjs/src/internal/operators/filter.ts", "node_modules/rxjs/src/internal/observable/zip.ts", "node_modules/rxjs/src/internal/operators/audit.ts", "node_modules/rxjs/src/internal/operators/auditTime.ts", "node_modules/rxjs/src/internal/operators/bufferCount.ts", "node_modules/rxjs/src/internal/operators/catchError.ts", "node_modules/rxjs/src/internal/operators/scanInternals.ts", "node_modules/rxjs/src/internal/operators/combineLatest.ts", "node_modules/rxjs/src/internal/operators/combineLatestWith.ts", "node_modules/rxjs/src/internal/operators/debounceTime.ts", "node_modules/rxjs/src/internal/operators/defaultIfEmpty.ts", "node_modules/rxjs/src/internal/operators/take.ts", "node_modules/rxjs/src/internal/operators/ignoreElements.ts", "node_modules/rxjs/src/internal/operators/mapTo.ts", "node_modules/rxjs/src/internal/operators/delayWhen.ts", "node_modules/rxjs/src/internal/operators/delay.ts", "node_modules/rxjs/src/internal/operators/distinctUntilChanged.ts", "node_modules/rxjs/src/internal/operators/distinctUntilKeyChanged.ts", "node_modules/rxjs/src/internal/operators/throwIfEmpty.ts", "node_modules/rxjs/src/internal/operators/endWith.ts", "node_modules/rxjs/src/internal/operators/finalize.ts", "node_modules/rxjs/src/internal/operators/first.ts", "node_modules/rxjs/src/internal/operators/merge.ts", "node_modules/rxjs/src/internal/operators/mergeWith.ts", "node_modules/rxjs/src/internal/operators/repeat.ts", "node_modules/rxjs/src/internal/operators/sample.ts", "node_modules/rxjs/src/internal/operators/scan.ts", "node_modules/rxjs/src/internal/operators/share.ts", "node_modules/rxjs/src/internal/operators/shareReplay.ts", "node_modules/rxjs/src/internal/operators/skip.ts", "node_modules/rxjs/src/internal/operators/skipUntil.ts", "node_modules/rxjs/src/internal/operators/startWith.ts", "node_modules/rxjs/src/internal/operators/switchMap.ts", "node_modules/rxjs/src/internal/operators/takeUntil.ts", "node_modules/rxjs/src/internal/operators/takeWhile.ts", "node_modules/rxjs/src/internal/operators/tap.ts", "node_modules/rxjs/src/internal/operators/throttle.ts", "node_modules/rxjs/src/internal/operators/throttleTime.ts", "node_modules/rxjs/src/internal/operators/withLatestFrom.ts", "node_modules/rxjs/src/internal/operators/zip.ts", "node_modules/rxjs/src/internal/operators/zipWith.ts", "src/templates/assets/javascripts/browser/document/index.ts", "src/templates/assets/javascripts/browser/element/_/index.ts", "src/templates/assets/javascripts/browser/element/focus/index.ts", "src/templates/assets/javascripts/browser/element/offset/_/index.ts", "src/templates/assets/javascripts/browser/element/offset/content/index.ts", "src/templates/assets/javascripts/utilities/h/index.ts", "src/templates/assets/javascripts/utilities/round/index.ts", "src/templates/assets/javascripts/browser/script/index.ts", "src/templates/assets/javascripts/browser/element/size/_/index.ts", "src/templates/assets/javascripts/browser/element/size/content/index.ts", "src/templates/assets/javascripts/browser/element/visibility/index.ts", "src/templates/assets/javascripts/browser/toggle/index.ts", "src/templates/assets/javascripts/browser/keyboard/index.ts", "src/templates/assets/javascripts/browser/location/_/index.ts", "src/templates/assets/javascripts/browser/location/hash/index.ts", "src/templates/assets/javascripts/browser/media/index.ts", "src/templates/assets/javascripts/browser/request/index.ts", "src/templates/assets/javascripts/browser/viewport/offset/index.ts", "src/templates/assets/javascripts/browser/viewport/size/index.ts", "src/templates/assets/javascripts/browser/viewport/_/index.ts", "src/templates/assets/javascripts/browser/viewport/at/index.ts", "src/templates/assets/javascripts/browser/worker/index.ts", "src/templates/assets/javascripts/_/index.ts", "src/templates/assets/javascripts/components/_/index.ts", "src/templates/assets/javascripts/components/announce/index.ts", "src/templates/assets/javascripts/components/consent/index.ts", "src/templates/assets/javascripts/components/content/annotation/_/index.ts", "src/templates/assets/javascripts/templates/tooltip/index.tsx", "src/templates/assets/javascripts/templates/annotation/index.tsx", "src/templates/assets/javascripts/templates/clipboard/index.tsx", "src/templates/assets/javascripts/templates/search/index.tsx", "src/templates/assets/javascripts/templates/source/index.tsx", "src/templates/assets/javascripts/templates/tabbed/index.tsx", "src/templates/assets/javascripts/templates/table/index.tsx", "src/templates/assets/javascripts/templates/version/index.tsx", "src/templates/assets/javascripts/components/content/annotation/list/index.ts", "src/templates/assets/javascripts/components/content/annotation/block/index.ts", "src/templates/assets/javascripts/components/content/code/_/index.ts", "src/templates/assets/javascripts/components/content/details/index.ts", "src/templates/assets/javascripts/components/content/mermaid/index.css", "src/templates/assets/javascripts/components/content/mermaid/index.ts", "src/templates/assets/javascripts/components/content/table/index.ts", "src/templates/assets/javascripts/components/content/tabs/index.ts", "src/templates/assets/javascripts/components/content/_/index.ts", "src/templates/assets/javascripts/components/dialog/index.ts", "src/templates/assets/javascripts/components/header/_/index.ts", "src/templates/assets/javascripts/components/header/title/index.ts", "src/templates/assets/javascripts/components/main/index.ts", "src/templates/assets/javascripts/components/palette/index.ts", "src/templates/assets/javascripts/components/progress/index.ts", "src/templates/assets/javascripts/integrations/clipboard/index.ts", "src/templates/assets/javascripts/integrations/sitemap/index.ts", "src/templates/assets/javascripts/integrations/instant/index.ts", "src/templates/assets/javascripts/integrations/search/highlighter/index.ts", "src/templates/assets/javascripts/integrations/search/worker/message/index.ts", "src/templates/assets/javascripts/integrations/search/worker/_/index.ts", "src/templates/assets/javascripts/integrations/version/index.ts", "src/templates/assets/javascripts/components/search/query/index.ts", "src/templates/assets/javascripts/components/search/result/index.ts", "src/templates/assets/javascripts/components/search/share/index.ts", "src/templates/assets/javascripts/components/search/suggest/index.ts", "src/templates/assets/javascripts/components/search/_/index.ts", "src/templates/assets/javascripts/components/search/highlight/index.ts", "src/templates/assets/javascripts/components/sidebar/index.ts", "src/templates/assets/javascripts/components/source/facts/github/index.ts", "src/templates/assets/javascripts/components/source/facts/gitlab/index.ts", "src/templates/assets/javascripts/components/source/facts/_/index.ts", "src/templates/assets/javascripts/components/source/_/index.ts", "src/templates/assets/javascripts/components/tabs/index.ts", "src/templates/assets/javascripts/components/toc/index.ts", "src/templates/assets/javascripts/components/top/index.ts", "src/templates/assets/javascripts/patches/indeterminate/index.ts", "src/templates/assets/javascripts/patches/scrollfix/index.ts", "src/templates/assets/javascripts/patches/scrolllock/index.ts", "src/templates/assets/javascripts/polyfills/index.ts"], + "sourcesContent": ["(function (global, factory) {\n typeof exports === 'object' && typeof module !== 'undefined' ? factory() :\n typeof define === 'function' && define.amd ? define(factory) :\n (factory());\n}(this, (function () { 'use strict';\n\n /**\n * Applies the :focus-visible polyfill at the given scope.\n * A scope in this case is either the top-level Document or a Shadow Root.\n *\n * @param {(Document|ShadowRoot)} scope\n * @see https://github.com/WICG/focus-visible\n */\n function applyFocusVisiblePolyfill(scope) {\n var hadKeyboardEvent = true;\n var hadFocusVisibleRecently = false;\n var hadFocusVisibleRecentlyTimeout = null;\n\n var inputTypesAllowlist = {\n text: true,\n search: true,\n url: true,\n tel: true,\n email: true,\n password: true,\n number: true,\n date: true,\n month: true,\n week: true,\n time: true,\n datetime: true,\n 'datetime-local': true\n };\n\n /**\n * Helper function for legacy browsers and iframes which sometimes focus\n * elements like document, body, and non-interactive SVG.\n * @param {Element} el\n */\n function isValidFocusTarget(el) {\n if (\n el &&\n el !== document &&\n el.nodeName !== 'HTML' &&\n el.nodeName !== 'BODY' &&\n 'classList' in el &&\n 'contains' in el.classList\n ) {\n return true;\n }\n return false;\n }\n\n /**\n * Computes whether the given element should automatically trigger the\n * `focus-visible` class being added, i.e. whether it should always match\n * `:focus-visible` when focused.\n * @param {Element} el\n * @return {boolean}\n */\n function focusTriggersKeyboardModality(el) {\n var type = el.type;\n var tagName = el.tagName;\n\n if (tagName === 'INPUT' && inputTypesAllowlist[type] && !el.readOnly) {\n return true;\n }\n\n if (tagName === 'TEXTAREA' && !el.readOnly) {\n return true;\n }\n\n if (el.isContentEditable) {\n return true;\n }\n\n return false;\n }\n\n /**\n * Add the `focus-visible` class to the given element if it was not added by\n * the author.\n * @param {Element} el\n */\n function addFocusVisibleClass(el) {\n if (el.classList.contains('focus-visible')) {\n return;\n }\n el.classList.add('focus-visible');\n el.setAttribute('data-focus-visible-added', '');\n }\n\n /**\n * Remove the `focus-visible` class from the given element if it was not\n * originally added by the author.\n * @param {Element} el\n */\n function removeFocusVisibleClass(el) {\n if (!el.hasAttribute('data-focus-visible-added')) {\n return;\n }\n el.classList.remove('focus-visible');\n el.removeAttribute('data-focus-visible-added');\n }\n\n /**\n * If the most recent user interaction was via the keyboard;\n * and the key press did not include a meta, alt/option, or control key;\n * then the modality is keyboard. Otherwise, the modality is not keyboard.\n * Apply `focus-visible` to any current active element and keep track\n * of our keyboard modality state with `hadKeyboardEvent`.\n * @param {KeyboardEvent} e\n */\n function onKeyDown(e) {\n if (e.metaKey || e.altKey || e.ctrlKey) {\n return;\n }\n\n if (isValidFocusTarget(scope.activeElement)) {\n addFocusVisibleClass(scope.activeElement);\n }\n\n hadKeyboardEvent = true;\n }\n\n /**\n * If at any point a user clicks with a pointing device, ensure that we change\n * the modality away from keyboard.\n * This avoids the situation where a user presses a key on an already focused\n * element, and then clicks on a different element, focusing it with a\n * pointing device, while we still think we're in keyboard modality.\n * @param {Event} e\n */\n function onPointerDown(e) {\n hadKeyboardEvent = false;\n }\n\n /**\n * On `focus`, add the `focus-visible` class to the target if:\n * - the target received focus as a result of keyboard navigation, or\n * - the event target is an element that will likely require interaction\n * via the keyboard (e.g. a text box)\n * @param {Event} e\n */\n function onFocus(e) {\n // Prevent IE from focusing the document or HTML element.\n if (!isValidFocusTarget(e.target)) {\n return;\n }\n\n if (hadKeyboardEvent || focusTriggersKeyboardModality(e.target)) {\n addFocusVisibleClass(e.target);\n }\n }\n\n /**\n * On `blur`, remove the `focus-visible` class from the target.\n * @param {Event} e\n */\n function onBlur(e) {\n if (!isValidFocusTarget(e.target)) {\n return;\n }\n\n if (\n e.target.classList.contains('focus-visible') ||\n e.target.hasAttribute('data-focus-visible-added')\n ) {\n // To detect a tab/window switch, we look for a blur event followed\n // rapidly by a visibility change.\n // If we don't see a visibility change within 100ms, it's probably a\n // regular focus change.\n hadFocusVisibleRecently = true;\n window.clearTimeout(hadFocusVisibleRecentlyTimeout);\n hadFocusVisibleRecentlyTimeout = window.setTimeout(function() {\n hadFocusVisibleRecently = false;\n }, 100);\n removeFocusVisibleClass(e.target);\n }\n }\n\n /**\n * If the user changes tabs, keep track of whether or not the previously\n * focused element had .focus-visible.\n * @param {Event} e\n */\n function onVisibilityChange(e) {\n if (document.visibilityState === 'hidden') {\n // If the tab becomes active again, the browser will handle calling focus\n // on the element (Safari actually calls it twice).\n // If this tab change caused a blur on an element with focus-visible,\n // re-apply the class when the user switches back to the tab.\n if (hadFocusVisibleRecently) {\n hadKeyboardEvent = true;\n }\n addInitialPointerMoveListeners();\n }\n }\n\n /**\n * Add a group of listeners to detect usage of any pointing devices.\n * These listeners will be added when the polyfill first loads, and anytime\n * the window is blurred, so that they are active when the window regains\n * focus.\n */\n function addInitialPointerMoveListeners() {\n document.addEventListener('mousemove', onInitialPointerMove);\n document.addEventListener('mousedown', onInitialPointerMove);\n document.addEventListener('mouseup', onInitialPointerMove);\n document.addEventListener('pointermove', onInitialPointerMove);\n document.addEventListener('pointerdown', onInitialPointerMove);\n document.addEventListener('pointerup', onInitialPointerMove);\n document.addEventListener('touchmove', onInitialPointerMove);\n document.addEventListener('touchstart', onInitialPointerMove);\n document.addEventListener('touchend', onInitialPointerMove);\n }\n\n function removeInitialPointerMoveListeners() {\n document.removeEventListener('mousemove', onInitialPointerMove);\n document.removeEventListener('mousedown', onInitialPointerMove);\n document.removeEventListener('mouseup', onInitialPointerMove);\n document.removeEventListener('pointermove', onInitialPointerMove);\n document.removeEventListener('pointerdown', onInitialPointerMove);\n document.removeEventListener('pointerup', onInitialPointerMove);\n document.removeEventListener('touchmove', onInitialPointerMove);\n document.removeEventListener('touchstart', onInitialPointerMove);\n document.removeEventListener('touchend', onInitialPointerMove);\n }\n\n /**\n * When the polfyill first loads, assume the user is in keyboard modality.\n * If any event is received from a pointing device (e.g. mouse, pointer,\n * touch), turn off keyboard modality.\n * This accounts for situations where focus enters the page from the URL bar.\n * @param {Event} e\n */\n function onInitialPointerMove(e) {\n // Work around a Safari quirk that fires a mousemove on whenever the\n // window blurs, even if you're tabbing out of the page. \u00AF\\_(\u30C4)_/\u00AF\n if (e.target.nodeName && e.target.nodeName.toLowerCase() === 'html') {\n return;\n }\n\n hadKeyboardEvent = false;\n removeInitialPointerMoveListeners();\n }\n\n // For some kinds of state, we are interested in changes at the global scope\n // only. For example, global pointer input, global key presses and global\n // visibility change should affect the state at every scope:\n document.addEventListener('keydown', onKeyDown, true);\n document.addEventListener('mousedown', onPointerDown, true);\n document.addEventListener('pointerdown', onPointerDown, true);\n document.addEventListener('touchstart', onPointerDown, true);\n document.addEventListener('visibilitychange', onVisibilityChange, true);\n\n addInitialPointerMoveListeners();\n\n // For focus and blur, we specifically care about state changes in the local\n // scope. This is because focus / blur events that originate from within a\n // shadow root are not re-dispatched from the host element if it was already\n // the active element in its own scope:\n scope.addEventListener('focus', onFocus, true);\n scope.addEventListener('blur', onBlur, true);\n\n // We detect that a node is a ShadowRoot by ensuring that it is a\n // DocumentFragment and also has a host property. This check covers native\n // implementation and polyfill implementation transparently. If we only cared\n // about the native implementation, we could just check if the scope was\n // an instance of a ShadowRoot.\n if (scope.nodeType === Node.DOCUMENT_FRAGMENT_NODE && scope.host) {\n // Since a ShadowRoot is a special kind of DocumentFragment, it does not\n // have a root element to add a class to. So, we add this attribute to the\n // host element instead:\n scope.host.setAttribute('data-js-focus-visible', '');\n } else if (scope.nodeType === Node.DOCUMENT_NODE) {\n document.documentElement.classList.add('js-focus-visible');\n document.documentElement.setAttribute('data-js-focus-visible', '');\n }\n }\n\n // It is important to wrap all references to global window and document in\n // these checks to support server-side rendering use cases\n // @see https://github.com/WICG/focus-visible/issues/199\n if (typeof window !== 'undefined' && typeof document !== 'undefined') {\n // Make the polyfill helper globally available. This can be used as a signal\n // to interested libraries that wish to coordinate with the polyfill for e.g.,\n // applying the polyfill to a shadow root:\n window.applyFocusVisiblePolyfill = applyFocusVisiblePolyfill;\n\n // Notify interested libraries of the polyfill's presence, in case the\n // polyfill was loaded lazily:\n var event;\n\n try {\n event = new CustomEvent('focus-visible-polyfill-ready');\n } catch (error) {\n // IE11 does not support using CustomEvent as a constructor directly:\n event = document.createEvent('CustomEvent');\n event.initCustomEvent('focus-visible-polyfill-ready', false, false, {});\n }\n\n window.dispatchEvent(event);\n }\n\n if (typeof document !== 'undefined') {\n // Apply the polyfill to the global document, so that no JavaScript\n // coordination is required to use the polyfill in the top-level document:\n applyFocusVisiblePolyfill(document);\n }\n\n})));\n", "/*!\n * clipboard.js v2.0.11\n * https://clipboardjs.com/\n *\n * Licensed MIT \u00A9 Zeno Rocha\n */\n(function webpackUniversalModuleDefinition(root, factory) {\n\tif(typeof exports === 'object' && typeof module === 'object')\n\t\tmodule.exports = factory();\n\telse if(typeof define === 'function' && define.amd)\n\t\tdefine([], factory);\n\telse if(typeof exports === 'object')\n\t\texports[\"ClipboardJS\"] = factory();\n\telse\n\t\troot[\"ClipboardJS\"] = factory();\n})(this, function() {\nreturn /******/ (function() { // webpackBootstrap\n/******/ \tvar __webpack_modules__ = ({\n\n/***/ 686:\n/***/ (function(__unused_webpack_module, __webpack_exports__, __webpack_require__) {\n\n\"use strict\";\n\n// EXPORTS\n__webpack_require__.d(__webpack_exports__, {\n \"default\": function() { return /* binding */ clipboard; }\n});\n\n// EXTERNAL MODULE: ./node_modules/tiny-emitter/index.js\nvar tiny_emitter = __webpack_require__(279);\nvar tiny_emitter_default = /*#__PURE__*/__webpack_require__.n(tiny_emitter);\n// EXTERNAL MODULE: ./node_modules/good-listener/src/listen.js\nvar listen = __webpack_require__(370);\nvar listen_default = /*#__PURE__*/__webpack_require__.n(listen);\n// EXTERNAL MODULE: ./node_modules/select/src/select.js\nvar src_select = __webpack_require__(817);\nvar select_default = /*#__PURE__*/__webpack_require__.n(src_select);\n;// CONCATENATED MODULE: ./src/common/command.js\n/**\n * Executes a given operation type.\n * @param {String} type\n * @return {Boolean}\n */\nfunction command(type) {\n try {\n return document.execCommand(type);\n } catch (err) {\n return false;\n }\n}\n;// CONCATENATED MODULE: ./src/actions/cut.js\n\n\n/**\n * Cut action wrapper.\n * @param {String|HTMLElement} target\n * @return {String}\n */\n\nvar ClipboardActionCut = function ClipboardActionCut(target) {\n var selectedText = select_default()(target);\n command('cut');\n return selectedText;\n};\n\n/* harmony default export */ var actions_cut = (ClipboardActionCut);\n;// CONCATENATED MODULE: ./src/common/create-fake-element.js\n/**\n * Creates a fake textarea element with a value.\n * @param {String} value\n * @return {HTMLElement}\n */\nfunction createFakeElement(value) {\n var isRTL = document.documentElement.getAttribute('dir') === 'rtl';\n var fakeElement = document.createElement('textarea'); // Prevent zooming on iOS\n\n fakeElement.style.fontSize = '12pt'; // Reset box model\n\n fakeElement.style.border = '0';\n fakeElement.style.padding = '0';\n fakeElement.style.margin = '0'; // Move element out of screen horizontally\n\n fakeElement.style.position = 'absolute';\n fakeElement.style[isRTL ? 'right' : 'left'] = '-9999px'; // Move element to the same position vertically\n\n var yPosition = window.pageYOffset || document.documentElement.scrollTop;\n fakeElement.style.top = \"\".concat(yPosition, \"px\");\n fakeElement.setAttribute('readonly', '');\n fakeElement.value = value;\n return fakeElement;\n}\n;// CONCATENATED MODULE: ./src/actions/copy.js\n\n\n\n/**\n * Create fake copy action wrapper using a fake element.\n * @param {String} target\n * @param {Object} options\n * @return {String}\n */\n\nvar fakeCopyAction = function fakeCopyAction(value, options) {\n var fakeElement = createFakeElement(value);\n options.container.appendChild(fakeElement);\n var selectedText = select_default()(fakeElement);\n command('copy');\n fakeElement.remove();\n return selectedText;\n};\n/**\n * Copy action wrapper.\n * @param {String|HTMLElement} target\n * @param {Object} options\n * @return {String}\n */\n\n\nvar ClipboardActionCopy = function ClipboardActionCopy(target) {\n var options = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : {\n container: document.body\n };\n var selectedText = '';\n\n if (typeof target === 'string') {\n selectedText = fakeCopyAction(target, options);\n } else if (target instanceof HTMLInputElement && !['text', 'search', 'url', 'tel', 'password'].includes(target === null || target === void 0 ? void 0 : target.type)) {\n // If input type doesn't support `setSelectionRange`. Simulate it. https://developer.mozilla.org/en-US/docs/Web/API/HTMLInputElement/setSelectionRange\n selectedText = fakeCopyAction(target.value, options);\n } else {\n selectedText = select_default()(target);\n command('copy');\n }\n\n return selectedText;\n};\n\n/* harmony default export */ var actions_copy = (ClipboardActionCopy);\n;// CONCATENATED MODULE: ./src/actions/default.js\nfunction _typeof(obj) { \"@babel/helpers - typeof\"; if (typeof Symbol === \"function\" && typeof Symbol.iterator === \"symbol\") { _typeof = function _typeof(obj) { return typeof obj; }; } else { _typeof = function _typeof(obj) { return obj && typeof Symbol === \"function\" && obj.constructor === Symbol && obj !== Symbol.prototype ? \"symbol\" : typeof obj; }; } return _typeof(obj); }\n\n\n\n/**\n * Inner function which performs selection from either `text` or `target`\n * properties and then executes copy or cut operations.\n * @param {Object} options\n */\n\nvar ClipboardActionDefault = function ClipboardActionDefault() {\n var options = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : {};\n // Defines base properties passed from constructor.\n var _options$action = options.action,\n action = _options$action === void 0 ? 'copy' : _options$action,\n container = options.container,\n target = options.target,\n text = options.text; // Sets the `action` to be performed which can be either 'copy' or 'cut'.\n\n if (action !== 'copy' && action !== 'cut') {\n throw new Error('Invalid \"action\" value, use either \"copy\" or \"cut\"');\n } // Sets the `target` property using an element that will be have its content copied.\n\n\n if (target !== undefined) {\n if (target && _typeof(target) === 'object' && target.nodeType === 1) {\n if (action === 'copy' && target.hasAttribute('disabled')) {\n throw new Error('Invalid \"target\" attribute. Please use \"readonly\" instead of \"disabled\" attribute');\n }\n\n if (action === 'cut' && (target.hasAttribute('readonly') || target.hasAttribute('disabled'))) {\n throw new Error('Invalid \"target\" attribute. You can\\'t cut text from elements with \"readonly\" or \"disabled\" attributes');\n }\n } else {\n throw new Error('Invalid \"target\" value, use a valid Element');\n }\n } // Define selection strategy based on `text` property.\n\n\n if (text) {\n return actions_copy(text, {\n container: container\n });\n } // Defines which selection strategy based on `target` property.\n\n\n if (target) {\n return action === 'cut' ? actions_cut(target) : actions_copy(target, {\n container: container\n });\n }\n};\n\n/* harmony default export */ var actions_default = (ClipboardActionDefault);\n;// CONCATENATED MODULE: ./src/clipboard.js\nfunction clipboard_typeof(obj) { \"@babel/helpers - typeof\"; if (typeof Symbol === \"function\" && typeof Symbol.iterator === \"symbol\") { clipboard_typeof = function _typeof(obj) { return typeof obj; }; } else { clipboard_typeof = function _typeof(obj) { return obj && typeof Symbol === \"function\" && obj.constructor === Symbol && obj !== Symbol.prototype ? \"symbol\" : typeof obj; }; } return clipboard_typeof(obj); }\n\nfunction _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError(\"Cannot call a class as a function\"); } }\n\nfunction _defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if (\"value\" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } }\n\nfunction _createClass(Constructor, protoProps, staticProps) { if (protoProps) _defineProperties(Constructor.prototype, protoProps); if (staticProps) _defineProperties(Constructor, staticProps); return Constructor; }\n\nfunction _inherits(subClass, superClass) { if (typeof superClass !== \"function\" && superClass !== null) { throw new TypeError(\"Super expression must either be null or a function\"); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, writable: true, configurable: true } }); if (superClass) _setPrototypeOf(subClass, superClass); }\n\nfunction _setPrototypeOf(o, p) { _setPrototypeOf = Object.setPrototypeOf || function _setPrototypeOf(o, p) { o.__proto__ = p; return o; }; return _setPrototypeOf(o, p); }\n\nfunction _createSuper(Derived) { var hasNativeReflectConstruct = _isNativeReflectConstruct(); return function _createSuperInternal() { var Super = _getPrototypeOf(Derived), result; if (hasNativeReflectConstruct) { var NewTarget = _getPrototypeOf(this).constructor; result = Reflect.construct(Super, arguments, NewTarget); } else { result = Super.apply(this, arguments); } return _possibleConstructorReturn(this, result); }; }\n\nfunction _possibleConstructorReturn(self, call) { if (call && (clipboard_typeof(call) === \"object\" || typeof call === \"function\")) { return call; } return _assertThisInitialized(self); }\n\nfunction _assertThisInitialized(self) { if (self === void 0) { throw new ReferenceError(\"this hasn't been initialised - super() hasn't been called\"); } return self; }\n\nfunction _isNativeReflectConstruct() { if (typeof Reflect === \"undefined\" || !Reflect.construct) return false; if (Reflect.construct.sham) return false; if (typeof Proxy === \"function\") return true; try { Date.prototype.toString.call(Reflect.construct(Date, [], function () {})); return true; } catch (e) { return false; } }\n\nfunction _getPrototypeOf(o) { _getPrototypeOf = Object.setPrototypeOf ? Object.getPrototypeOf : function _getPrototypeOf(o) { return o.__proto__ || Object.getPrototypeOf(o); }; return _getPrototypeOf(o); }\n\n\n\n\n\n\n/**\n * Helper function to retrieve attribute value.\n * @param {String} suffix\n * @param {Element} element\n */\n\nfunction getAttributeValue(suffix, element) {\n var attribute = \"data-clipboard-\".concat(suffix);\n\n if (!element.hasAttribute(attribute)) {\n return;\n }\n\n return element.getAttribute(attribute);\n}\n/**\n * Base class which takes one or more elements, adds event listeners to them,\n * and instantiates a new `ClipboardAction` on each click.\n */\n\n\nvar Clipboard = /*#__PURE__*/function (_Emitter) {\n _inherits(Clipboard, _Emitter);\n\n var _super = _createSuper(Clipboard);\n\n /**\n * @param {String|HTMLElement|HTMLCollection|NodeList} trigger\n * @param {Object} options\n */\n function Clipboard(trigger, options) {\n var _this;\n\n _classCallCheck(this, Clipboard);\n\n _this = _super.call(this);\n\n _this.resolveOptions(options);\n\n _this.listenClick(trigger);\n\n return _this;\n }\n /**\n * Defines if attributes would be resolved using internal setter functions\n * or custom functions that were passed in the constructor.\n * @param {Object} options\n */\n\n\n _createClass(Clipboard, [{\n key: \"resolveOptions\",\n value: function resolveOptions() {\n var options = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : {};\n this.action = typeof options.action === 'function' ? options.action : this.defaultAction;\n this.target = typeof options.target === 'function' ? options.target : this.defaultTarget;\n this.text = typeof options.text === 'function' ? options.text : this.defaultText;\n this.container = clipboard_typeof(options.container) === 'object' ? options.container : document.body;\n }\n /**\n * Adds a click event listener to the passed trigger.\n * @param {String|HTMLElement|HTMLCollection|NodeList} trigger\n */\n\n }, {\n key: \"listenClick\",\n value: function listenClick(trigger) {\n var _this2 = this;\n\n this.listener = listen_default()(trigger, 'click', function (e) {\n return _this2.onClick(e);\n });\n }\n /**\n * Defines a new `ClipboardAction` on each click event.\n * @param {Event} e\n */\n\n }, {\n key: \"onClick\",\n value: function onClick(e) {\n var trigger = e.delegateTarget || e.currentTarget;\n var action = this.action(trigger) || 'copy';\n var text = actions_default({\n action: action,\n container: this.container,\n target: this.target(trigger),\n text: this.text(trigger)\n }); // Fires an event based on the copy operation result.\n\n this.emit(text ? 'success' : 'error', {\n action: action,\n text: text,\n trigger: trigger,\n clearSelection: function clearSelection() {\n if (trigger) {\n trigger.focus();\n }\n\n window.getSelection().removeAllRanges();\n }\n });\n }\n /**\n * Default `action` lookup function.\n * @param {Element} trigger\n */\n\n }, {\n key: \"defaultAction\",\n value: function defaultAction(trigger) {\n return getAttributeValue('action', trigger);\n }\n /**\n * Default `target` lookup function.\n * @param {Element} trigger\n */\n\n }, {\n key: \"defaultTarget\",\n value: function defaultTarget(trigger) {\n var selector = getAttributeValue('target', trigger);\n\n if (selector) {\n return document.querySelector(selector);\n }\n }\n /**\n * Allow fire programmatically a copy action\n * @param {String|HTMLElement} target\n * @param {Object} options\n * @returns Text copied.\n */\n\n }, {\n key: \"defaultText\",\n\n /**\n * Default `text` lookup function.\n * @param {Element} trigger\n */\n value: function defaultText(trigger) {\n return getAttributeValue('text', trigger);\n }\n /**\n * Destroy lifecycle.\n */\n\n }, {\n key: \"destroy\",\n value: function destroy() {\n this.listener.destroy();\n }\n }], [{\n key: \"copy\",\n value: function copy(target) {\n var options = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : {\n container: document.body\n };\n return actions_copy(target, options);\n }\n /**\n * Allow fire programmatically a cut action\n * @param {String|HTMLElement} target\n * @returns Text cutted.\n */\n\n }, {\n key: \"cut\",\n value: function cut(target) {\n return actions_cut(target);\n }\n /**\n * Returns the support of the given action, or all actions if no action is\n * given.\n * @param {String} [action]\n */\n\n }, {\n key: \"isSupported\",\n value: function isSupported() {\n var action = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : ['copy', 'cut'];\n var actions = typeof action === 'string' ? [action] : action;\n var support = !!document.queryCommandSupported;\n actions.forEach(function (action) {\n support = support && !!document.queryCommandSupported(action);\n });\n return support;\n }\n }]);\n\n return Clipboard;\n}((tiny_emitter_default()));\n\n/* harmony default export */ var clipboard = (Clipboard);\n\n/***/ }),\n\n/***/ 828:\n/***/ (function(module) {\n\nvar DOCUMENT_NODE_TYPE = 9;\n\n/**\n * A polyfill for Element.matches()\n */\nif (typeof Element !== 'undefined' && !Element.prototype.matches) {\n var proto = Element.prototype;\n\n proto.matches = proto.matchesSelector ||\n proto.mozMatchesSelector ||\n proto.msMatchesSelector ||\n proto.oMatchesSelector ||\n proto.webkitMatchesSelector;\n}\n\n/**\n * Finds the closest parent that matches a selector.\n *\n * @param {Element} element\n * @param {String} selector\n * @return {Function}\n */\nfunction closest (element, selector) {\n while (element && element.nodeType !== DOCUMENT_NODE_TYPE) {\n if (typeof element.matches === 'function' &&\n element.matches(selector)) {\n return element;\n }\n element = element.parentNode;\n }\n}\n\nmodule.exports = closest;\n\n\n/***/ }),\n\n/***/ 438:\n/***/ (function(module, __unused_webpack_exports, __webpack_require__) {\n\nvar closest = __webpack_require__(828);\n\n/**\n * Delegates event to a selector.\n *\n * @param {Element} element\n * @param {String} selector\n * @param {String} type\n * @param {Function} callback\n * @param {Boolean} useCapture\n * @return {Object}\n */\nfunction _delegate(element, selector, type, callback, useCapture) {\n var listenerFn = listener.apply(this, arguments);\n\n element.addEventListener(type, listenerFn, useCapture);\n\n return {\n destroy: function() {\n element.removeEventListener(type, listenerFn, useCapture);\n }\n }\n}\n\n/**\n * Delegates event to a selector.\n *\n * @param {Element|String|Array} [elements]\n * @param {String} selector\n * @param {String} type\n * @param {Function} callback\n * @param {Boolean} useCapture\n * @return {Object}\n */\nfunction delegate(elements, selector, type, callback, useCapture) {\n // Handle the regular Element usage\n if (typeof elements.addEventListener === 'function') {\n return _delegate.apply(null, arguments);\n }\n\n // Handle Element-less usage, it defaults to global delegation\n if (typeof type === 'function') {\n // Use `document` as the first parameter, then apply arguments\n // This is a short way to .unshift `arguments` without running into deoptimizations\n return _delegate.bind(null, document).apply(null, arguments);\n }\n\n // Handle Selector-based usage\n if (typeof elements === 'string') {\n elements = document.querySelectorAll(elements);\n }\n\n // Handle Array-like based usage\n return Array.prototype.map.call(elements, function (element) {\n return _delegate(element, selector, type, callback, useCapture);\n });\n}\n\n/**\n * Finds closest match and invokes callback.\n *\n * @param {Element} element\n * @param {String} selector\n * @param {String} type\n * @param {Function} callback\n * @return {Function}\n */\nfunction listener(element, selector, type, callback) {\n return function(e) {\n e.delegateTarget = closest(e.target, selector);\n\n if (e.delegateTarget) {\n callback.call(element, e);\n }\n }\n}\n\nmodule.exports = delegate;\n\n\n/***/ }),\n\n/***/ 879:\n/***/ (function(__unused_webpack_module, exports) {\n\n/**\n * Check if argument is a HTML element.\n *\n * @param {Object} value\n * @return {Boolean}\n */\nexports.node = function(value) {\n return value !== undefined\n && value instanceof HTMLElement\n && value.nodeType === 1;\n};\n\n/**\n * Check if argument is a list of HTML elements.\n *\n * @param {Object} value\n * @return {Boolean}\n */\nexports.nodeList = function(value) {\n var type = Object.prototype.toString.call(value);\n\n return value !== undefined\n && (type === '[object NodeList]' || type === '[object HTMLCollection]')\n && ('length' in value)\n && (value.length === 0 || exports.node(value[0]));\n};\n\n/**\n * Check if argument is a string.\n *\n * @param {Object} value\n * @return {Boolean}\n */\nexports.string = function(value) {\n return typeof value === 'string'\n || value instanceof String;\n};\n\n/**\n * Check if argument is a function.\n *\n * @param {Object} value\n * @return {Boolean}\n */\nexports.fn = function(value) {\n var type = Object.prototype.toString.call(value);\n\n return type === '[object Function]';\n};\n\n\n/***/ }),\n\n/***/ 370:\n/***/ (function(module, __unused_webpack_exports, __webpack_require__) {\n\nvar is = __webpack_require__(879);\nvar delegate = __webpack_require__(438);\n\n/**\n * Validates all params and calls the right\n * listener function based on its target type.\n *\n * @param {String|HTMLElement|HTMLCollection|NodeList} target\n * @param {String} type\n * @param {Function} callback\n * @return {Object}\n */\nfunction listen(target, type, callback) {\n if (!target && !type && !callback) {\n throw new Error('Missing required arguments');\n }\n\n if (!is.string(type)) {\n throw new TypeError('Second argument must be a String');\n }\n\n if (!is.fn(callback)) {\n throw new TypeError('Third argument must be a Function');\n }\n\n if (is.node(target)) {\n return listenNode(target, type, callback);\n }\n else if (is.nodeList(target)) {\n return listenNodeList(target, type, callback);\n }\n else if (is.string(target)) {\n return listenSelector(target, type, callback);\n }\n else {\n throw new TypeError('First argument must be a String, HTMLElement, HTMLCollection, or NodeList');\n }\n}\n\n/**\n * Adds an event listener to a HTML element\n * and returns a remove listener function.\n *\n * @param {HTMLElement} node\n * @param {String} type\n * @param {Function} callback\n * @return {Object}\n */\nfunction listenNode(node, type, callback) {\n node.addEventListener(type, callback);\n\n return {\n destroy: function() {\n node.removeEventListener(type, callback);\n }\n }\n}\n\n/**\n * Add an event listener to a list of HTML elements\n * and returns a remove listener function.\n *\n * @param {NodeList|HTMLCollection} nodeList\n * @param {String} type\n * @param {Function} callback\n * @return {Object}\n */\nfunction listenNodeList(nodeList, type, callback) {\n Array.prototype.forEach.call(nodeList, function(node) {\n node.addEventListener(type, callback);\n });\n\n return {\n destroy: function() {\n Array.prototype.forEach.call(nodeList, function(node) {\n node.removeEventListener(type, callback);\n });\n }\n }\n}\n\n/**\n * Add an event listener to a selector\n * and returns a remove listener function.\n *\n * @param {String} selector\n * @param {String} type\n * @param {Function} callback\n * @return {Object}\n */\nfunction listenSelector(selector, type, callback) {\n return delegate(document.body, selector, type, callback);\n}\n\nmodule.exports = listen;\n\n\n/***/ }),\n\n/***/ 817:\n/***/ (function(module) {\n\nfunction select(element) {\n var selectedText;\n\n if (element.nodeName === 'SELECT') {\n element.focus();\n\n selectedText = element.value;\n }\n else if (element.nodeName === 'INPUT' || element.nodeName === 'TEXTAREA') {\n var isReadOnly = element.hasAttribute('readonly');\n\n if (!isReadOnly) {\n element.setAttribute('readonly', '');\n }\n\n element.select();\n element.setSelectionRange(0, element.value.length);\n\n if (!isReadOnly) {\n element.removeAttribute('readonly');\n }\n\n selectedText = element.value;\n }\n else {\n if (element.hasAttribute('contenteditable')) {\n element.focus();\n }\n\n var selection = window.getSelection();\n var range = document.createRange();\n\n range.selectNodeContents(element);\n selection.removeAllRanges();\n selection.addRange(range);\n\n selectedText = selection.toString();\n }\n\n return selectedText;\n}\n\nmodule.exports = select;\n\n\n/***/ }),\n\n/***/ 279:\n/***/ (function(module) {\n\nfunction E () {\n // Keep this empty so it's easier to inherit from\n // (via https://github.com/lipsmack from https://github.com/scottcorgan/tiny-emitter/issues/3)\n}\n\nE.prototype = {\n on: function (name, callback, ctx) {\n var e = this.e || (this.e = {});\n\n (e[name] || (e[name] = [])).push({\n fn: callback,\n ctx: ctx\n });\n\n return this;\n },\n\n once: function (name, callback, ctx) {\n var self = this;\n function listener () {\n self.off(name, listener);\n callback.apply(ctx, arguments);\n };\n\n listener._ = callback\n return this.on(name, listener, ctx);\n },\n\n emit: function (name) {\n var data = [].slice.call(arguments, 1);\n var evtArr = ((this.e || (this.e = {}))[name] || []).slice();\n var i = 0;\n var len = evtArr.length;\n\n for (i; i < len; i++) {\n evtArr[i].fn.apply(evtArr[i].ctx, data);\n }\n\n return this;\n },\n\n off: function (name, callback) {\n var e = this.e || (this.e = {});\n var evts = e[name];\n var liveEvents = [];\n\n if (evts && callback) {\n for (var i = 0, len = evts.length; i < len; i++) {\n if (evts[i].fn !== callback && evts[i].fn._ !== callback)\n liveEvents.push(evts[i]);\n }\n }\n\n // Remove event from queue to prevent memory leak\n // Suggested by https://github.com/lazd\n // Ref: https://github.com/scottcorgan/tiny-emitter/commit/c6ebfaa9bc973b33d110a84a307742b7cf94c953#commitcomment-5024910\n\n (liveEvents.length)\n ? e[name] = liveEvents\n : delete e[name];\n\n return this;\n }\n};\n\nmodule.exports = E;\nmodule.exports.TinyEmitter = E;\n\n\n/***/ })\n\n/******/ \t});\n/************************************************************************/\n/******/ \t// The module cache\n/******/ \tvar __webpack_module_cache__ = {};\n/******/ \t\n/******/ \t// The require function\n/******/ \tfunction __webpack_require__(moduleId) {\n/******/ \t\t// Check if module is in cache\n/******/ \t\tif(__webpack_module_cache__[moduleId]) {\n/******/ \t\t\treturn __webpack_module_cache__[moduleId].exports;\n/******/ \t\t}\n/******/ \t\t// Create a new module (and put it into the cache)\n/******/ \t\tvar module = __webpack_module_cache__[moduleId] = {\n/******/ \t\t\t// no module.id needed\n/******/ \t\t\t// no module.loaded needed\n/******/ \t\t\texports: {}\n/******/ \t\t};\n/******/ \t\n/******/ \t\t// Execute the module function\n/******/ \t\t__webpack_modules__[moduleId](module, module.exports, __webpack_require__);\n/******/ \t\n/******/ \t\t// Return the exports of the module\n/******/ \t\treturn module.exports;\n/******/ \t}\n/******/ \t\n/************************************************************************/\n/******/ \t/* webpack/runtime/compat get default export */\n/******/ \t!function() {\n/******/ \t\t// getDefaultExport function for compatibility with non-harmony modules\n/******/ \t\t__webpack_require__.n = function(module) {\n/******/ \t\t\tvar getter = module && module.__esModule ?\n/******/ \t\t\t\tfunction() { return module['default']; } :\n/******/ \t\t\t\tfunction() { return module; };\n/******/ \t\t\t__webpack_require__.d(getter, { a: getter });\n/******/ \t\t\treturn getter;\n/******/ \t\t};\n/******/ \t}();\n/******/ \t\n/******/ \t/* webpack/runtime/define property getters */\n/******/ \t!function() {\n/******/ \t\t// define getter functions for harmony exports\n/******/ \t\t__webpack_require__.d = function(exports, definition) {\n/******/ \t\t\tfor(var key in definition) {\n/******/ \t\t\t\tif(__webpack_require__.o(definition, key) && !__webpack_require__.o(exports, key)) {\n/******/ \t\t\t\t\tObject.defineProperty(exports, key, { enumerable: true, get: definition[key] });\n/******/ \t\t\t\t}\n/******/ \t\t\t}\n/******/ \t\t};\n/******/ \t}();\n/******/ \t\n/******/ \t/* webpack/runtime/hasOwnProperty shorthand */\n/******/ \t!function() {\n/******/ \t\t__webpack_require__.o = function(obj, prop) { return Object.prototype.hasOwnProperty.call(obj, prop); }\n/******/ \t}();\n/******/ \t\n/************************************************************************/\n/******/ \t// module exports must be returned from runtime so entry inlining is disabled\n/******/ \t// startup\n/******/ \t// Load entry module and return exports\n/******/ \treturn __webpack_require__(686);\n/******/ })()\n.default;\n});", "/*!\n * escape-html\n * Copyright(c) 2012-2013 TJ Holowaychuk\n * Copyright(c) 2015 Andreas Lubbe\n * Copyright(c) 2015 Tiancheng \"Timothy\" Gu\n * MIT Licensed\n */\n\n'use strict';\n\n/**\n * Module variables.\n * @private\n */\n\nvar matchHtmlRegExp = /[\"'&<>]/;\n\n/**\n * Module exports.\n * @public\n */\n\nmodule.exports = escapeHtml;\n\n/**\n * Escape special characters in the given string of html.\n *\n * @param {string} string The string to escape for inserting into HTML\n * @return {string}\n * @public\n */\n\nfunction escapeHtml(string) {\n var str = '' + string;\n var match = matchHtmlRegExp.exec(str);\n\n if (!match) {\n return str;\n }\n\n var escape;\n var html = '';\n var index = 0;\n var lastIndex = 0;\n\n for (index = match.index; index < str.length; index++) {\n switch (str.charCodeAt(index)) {\n case 34: // \"\n escape = '"';\n break;\n case 38: // &\n escape = '&';\n break;\n case 39: // '\n escape = ''';\n break;\n case 60: // <\n escape = '<';\n break;\n case 62: // >\n escape = '>';\n break;\n default:\n continue;\n }\n\n if (lastIndex !== index) {\n html += str.substring(lastIndex, index);\n }\n\n lastIndex = index + 1;\n html += escape;\n }\n\n return lastIndex !== index\n ? html + str.substring(lastIndex, index)\n : html;\n}\n", "/*\n * Copyright (c) 2016-2023 Martin Donath \n *\n * Permission is hereby granted, free of charge, to any person obtaining a copy\n * of this software and associated documentation files (the \"Software\"), to\n * deal in the Software without restriction, including without limitation the\n * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or\n * sell copies of the Software, and to permit persons to whom the Software is\n * furnished to do so, subject to the following conditions:\n *\n * The above copyright notice and this permission notice shall be included in\n * all copies or substantial portions of the Software.\n *\n * THE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR\n * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,\n * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL THE\n * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER\n * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING\n * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS\n * IN THE SOFTWARE.\n */\n\nimport \"focus-visible\"\n\nimport {\n EMPTY,\n NEVER,\n Observable,\n Subject,\n defer,\n delay,\n filter,\n map,\n merge,\n mergeWith,\n shareReplay,\n switchMap\n} from \"rxjs\"\n\nimport { configuration, feature } from \"./_\"\nimport {\n at,\n getActiveElement,\n getOptionalElement,\n requestJSON,\n setLocation,\n setToggle,\n watchDocument,\n watchKeyboard,\n watchLocation,\n watchLocationTarget,\n watchMedia,\n watchPrint,\n watchScript,\n watchViewport\n} from \"./browser\"\nimport {\n getComponentElement,\n getComponentElements,\n mountAnnounce,\n mountBackToTop,\n mountConsent,\n mountContent,\n mountDialog,\n mountHeader,\n mountHeaderTitle,\n mountPalette,\n mountProgress,\n mountSearch,\n mountSearchHiglight,\n mountSidebar,\n mountSource,\n mountTableOfContents,\n mountTabs,\n watchHeader,\n watchMain\n} from \"./components\"\nimport {\n SearchIndex,\n setupClipboardJS,\n setupInstantNavigation,\n setupVersionSelector\n} from \"./integrations\"\nimport {\n patchIndeterminate,\n patchScrollfix,\n patchScrolllock\n} from \"./patches\"\nimport \"./polyfills\"\n\n/* ----------------------------------------------------------------------------\n * Functions - @todo refactor\n * ------------------------------------------------------------------------- */\n\n/**\n * Fetch search index\n *\n * @returns Search index observable\n */\nfunction fetchSearchIndex(): Observable {\n if (location.protocol === \"file:\") {\n return watchScript(\n `${new URL(\"search/search_index.js\", config.base)}`\n )\n .pipe(\n // @ts-ignore - @todo fix typings\n map(() => __index),\n shareReplay(1)\n )\n } else {\n return requestJSON(\n new URL(\"search/search_index.json\", config.base)\n )\n }\n}\n\n/* ----------------------------------------------------------------------------\n * Application\n * ------------------------------------------------------------------------- */\n\n/* Yay, JavaScript is available */\ndocument.documentElement.classList.remove(\"no-js\")\ndocument.documentElement.classList.add(\"js\")\n\n/* Set up navigation observables and subjects */\nconst document$ = watchDocument()\nconst location$ = watchLocation()\nconst target$ = watchLocationTarget(location$)\nconst keyboard$ = watchKeyboard()\n\n/* Set up media observables */\nconst viewport$ = watchViewport()\nconst tablet$ = watchMedia(\"(min-width: 960px)\")\nconst screen$ = watchMedia(\"(min-width: 1220px)\")\nconst print$ = watchPrint()\n\n/* Retrieve search index, if search is enabled */\nconst config = configuration()\nconst index$ = document.forms.namedItem(\"search\")\n ? fetchSearchIndex()\n : NEVER\n\n/* Set up Clipboard.js integration */\nconst alert$ = new Subject()\nsetupClipboardJS({ alert$ })\n\n/* Set up progress indicator */\nconst progress$ = new Subject()\n\n/* Set up instant navigation, if enabled */\nif (feature(\"navigation.instant\"))\n setupInstantNavigation({ location$, viewport$, progress$ })\n .subscribe(document$)\n\n/* Set up version selector */\nif (config.version?.provider === \"mike\")\n setupVersionSelector({ document$ })\n\n/* Always close drawer and search on navigation */\nmerge(location$, target$)\n .pipe(\n delay(125)\n )\n .subscribe(() => {\n setToggle(\"drawer\", false)\n setToggle(\"search\", false)\n })\n\n/* Set up global keyboard handlers */\nkeyboard$\n .pipe(\n filter(({ mode }) => mode === \"global\")\n )\n .subscribe(key => {\n switch (key.type) {\n\n /* Go to previous page */\n case \"p\":\n case \",\":\n const prev = getOptionalElement(\"link[rel=prev]\")\n if (typeof prev !== \"undefined\")\n setLocation(prev)\n break\n\n /* Go to next page */\n case \"n\":\n case \".\":\n const next = getOptionalElement(\"link[rel=next]\")\n if (typeof next !== \"undefined\")\n setLocation(next)\n break\n\n /* Expand navigation, see https://bit.ly/3ZjG5io */\n case \"Enter\":\n const active = getActiveElement()\n if (active instanceof HTMLLabelElement)\n active.click()\n }\n })\n\n/* Set up patches */\npatchIndeterminate({ document$, tablet$ })\npatchScrollfix({ document$ })\npatchScrolllock({ viewport$, tablet$ })\n\n/* Set up header and main area observable */\nconst header$ = watchHeader(getComponentElement(\"header\"), { viewport$ })\nconst main$ = document$\n .pipe(\n map(() => getComponentElement(\"main\")),\n switchMap(el => watchMain(el, { viewport$, header$ })),\n shareReplay(1)\n )\n\n/* Set up control component observables */\nconst control$ = merge(\n\n /* Consent */\n ...getComponentElements(\"consent\")\n .map(el => mountConsent(el, { target$ })),\n\n /* Dialog */\n ...getComponentElements(\"dialog\")\n .map(el => mountDialog(el, { alert$ })),\n\n /* Header */\n ...getComponentElements(\"header\")\n .map(el => mountHeader(el, { viewport$, header$, main$ })),\n\n /* Color palette */\n ...getComponentElements(\"palette\")\n .map(el => mountPalette(el)),\n\n /* Progress bar */\n ...getComponentElements(\"progress\")\n .map(el => mountProgress(el, { progress$ })),\n\n /* Search */\n ...getComponentElements(\"search\")\n .map(el => mountSearch(el, { index$, keyboard$ })),\n\n /* Repository information */\n ...getComponentElements(\"source\")\n .map(el => mountSource(el))\n)\n\n/* Set up content component observables */\nconst content$ = defer(() => merge(\n\n /* Announcement bar */\n ...getComponentElements(\"announce\")\n .map(el => mountAnnounce(el)),\n\n /* Content */\n ...getComponentElements(\"content\")\n .map(el => mountContent(el, { viewport$, target$, print$ })),\n\n /* Search highlighting */\n ...getComponentElements(\"content\")\n .map(el => feature(\"search.highlight\")\n ? mountSearchHiglight(el, { index$, location$ })\n : EMPTY\n ),\n\n /* Header title */\n ...getComponentElements(\"header-title\")\n .map(el => mountHeaderTitle(el, { viewport$, header$ })),\n\n /* Sidebar */\n ...getComponentElements(\"sidebar\")\n .map(el => el.getAttribute(\"data-md-type\") === \"navigation\"\n ? at(screen$, () => mountSidebar(el, { viewport$, header$, main$ }))\n : at(tablet$, () => mountSidebar(el, { viewport$, header$, main$ }))\n ),\n\n /* Navigation tabs */\n ...getComponentElements(\"tabs\")\n .map(el => mountTabs(el, { viewport$, header$ })),\n\n /* Table of contents */\n ...getComponentElements(\"toc\")\n .map(el => mountTableOfContents(el, {\n viewport$, header$, main$, target$\n })),\n\n /* Back-to-top button */\n ...getComponentElements(\"top\")\n .map(el => mountBackToTop(el, { viewport$, header$, main$, target$ }))\n))\n\n/* Set up component observables */\nconst component$ = document$\n .pipe(\n switchMap(() => content$),\n mergeWith(control$),\n shareReplay(1)\n )\n\n/* Subscribe to all components */\ncomponent$.subscribe()\n\n/* ----------------------------------------------------------------------------\n * Exports\n * ------------------------------------------------------------------------- */\n\nwindow.document$ = document$ /* Document observable */\nwindow.location$ = location$ /* Location subject */\nwindow.target$ = target$ /* Location target observable */\nwindow.keyboard$ = keyboard$ /* Keyboard observable */\nwindow.viewport$ = viewport$ /* Viewport observable */\nwindow.tablet$ = tablet$ /* Media tablet observable */\nwindow.screen$ = screen$ /* Media screen observable */\nwindow.print$ = print$ /* Media print observable */\nwindow.alert$ = alert$ /* Alert subject */\nwindow.progress$ = progress$ /* Progress indicator subject */\nwindow.component$ = component$ /* Component observable */\n", "/*! *****************************************************************************\r\nCopyright (c) Microsoft Corporation.\r\n\r\nPermission to use, copy, modify, and/or distribute this software for any\r\npurpose with or without fee is hereby granted.\r\n\r\nTHE SOFTWARE IS PROVIDED \"AS IS\" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH\r\nREGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY\r\nAND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT,\r\nINDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM\r\nLOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR\r\nOTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR\r\nPERFORMANCE OF THIS SOFTWARE.\r\n***************************************************************************** */\r\n/* global Reflect, Promise */\r\n\r\nvar extendStatics = function(d, b) {\r\n extendStatics = Object.setPrototypeOf ||\r\n ({ __proto__: [] } instanceof Array && function (d, b) { d.__proto__ = b; }) ||\r\n function (d, b) { for (var p in b) if (Object.prototype.hasOwnProperty.call(b, p)) d[p] = b[p]; };\r\n return extendStatics(d, b);\r\n};\r\n\r\nexport function __extends(d, b) {\r\n if (typeof b !== \"function\" && b !== null)\r\n throw new TypeError(\"Class extends value \" + String(b) + \" is not a constructor or null\");\r\n extendStatics(d, b);\r\n function __() { this.constructor = d; }\r\n d.prototype = b === null ? Object.create(b) : (__.prototype = b.prototype, new __());\r\n}\r\n\r\nexport var __assign = function() {\r\n __assign = Object.assign || function __assign(t) {\r\n for (var s, i = 1, n = arguments.length; i < n; i++) {\r\n s = arguments[i];\r\n for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p)) t[p] = s[p];\r\n }\r\n return t;\r\n }\r\n return __assign.apply(this, arguments);\r\n}\r\n\r\nexport function __rest(s, e) {\r\n var t = {};\r\n for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p) && e.indexOf(p) < 0)\r\n t[p] = s[p];\r\n if (s != null && typeof Object.getOwnPropertySymbols === \"function\")\r\n for (var i = 0, p = Object.getOwnPropertySymbols(s); i < p.length; i++) {\r\n if (e.indexOf(p[i]) < 0 && Object.prototype.propertyIsEnumerable.call(s, p[i]))\r\n t[p[i]] = s[p[i]];\r\n }\r\n return t;\r\n}\r\n\r\nexport function __decorate(decorators, target, key, desc) {\r\n var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;\r\n if (typeof Reflect === \"object\" && typeof Reflect.decorate === \"function\") r = Reflect.decorate(decorators, target, key, desc);\r\n else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;\r\n return c > 3 && r && Object.defineProperty(target, key, r), r;\r\n}\r\n\r\nexport function __param(paramIndex, decorator) {\r\n return function (target, key) { decorator(target, key, paramIndex); }\r\n}\r\n\r\nexport function __metadata(metadataKey, metadataValue) {\r\n if (typeof Reflect === \"object\" && typeof Reflect.metadata === \"function\") return Reflect.metadata(metadataKey, metadataValue);\r\n}\r\n\r\nexport function __awaiter(thisArg, _arguments, P, generator) {\r\n function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }\r\n return new (P || (P = Promise))(function (resolve, reject) {\r\n function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }\r\n function rejected(value) { try { step(generator[\"throw\"](value)); } catch (e) { reject(e); } }\r\n function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }\r\n step((generator = generator.apply(thisArg, _arguments || [])).next());\r\n });\r\n}\r\n\r\nexport function __generator(thisArg, body) {\r\n var _ = { label: 0, sent: function() { if (t[0] & 1) throw t[1]; return t[1]; }, trys: [], ops: [] }, f, y, t, g;\r\n return g = { next: verb(0), \"throw\": verb(1), \"return\": verb(2) }, typeof Symbol === \"function\" && (g[Symbol.iterator] = function() { return this; }), g;\r\n function verb(n) { return function (v) { return step([n, v]); }; }\r\n function step(op) {\r\n if (f) throw new TypeError(\"Generator is already executing.\");\r\n while (_) try {\r\n if (f = 1, y && (t = op[0] & 2 ? y[\"return\"] : op[0] ? y[\"throw\"] || ((t = y[\"return\"]) && t.call(y), 0) : y.next) && !(t = t.call(y, op[1])).done) return t;\r\n if (y = 0, t) op = [op[0] & 2, t.value];\r\n switch (op[0]) {\r\n case 0: case 1: t = op; break;\r\n case 4: _.label++; return { value: op[1], done: false };\r\n case 5: _.label++; y = op[1]; op = [0]; continue;\r\n case 7: op = _.ops.pop(); _.trys.pop(); continue;\r\n default:\r\n if (!(t = _.trys, t = t.length > 0 && t[t.length - 1]) && (op[0] === 6 || op[0] === 2)) { _ = 0; continue; }\r\n if (op[0] === 3 && (!t || (op[1] > t[0] && op[1] < t[3]))) { _.label = op[1]; break; }\r\n if (op[0] === 6 && _.label < t[1]) { _.label = t[1]; t = op; break; }\r\n if (t && _.label < t[2]) { _.label = t[2]; _.ops.push(op); break; }\r\n if (t[2]) _.ops.pop();\r\n _.trys.pop(); continue;\r\n }\r\n op = body.call(thisArg, _);\r\n } catch (e) { op = [6, e]; y = 0; } finally { f = t = 0; }\r\n if (op[0] & 5) throw op[1]; return { value: op[0] ? op[1] : void 0, done: true };\r\n }\r\n}\r\n\r\nexport var __createBinding = Object.create ? (function(o, m, k, k2) {\r\n if (k2 === undefined) k2 = k;\r\n Object.defineProperty(o, k2, { enumerable: true, get: function() { return m[k]; } });\r\n}) : (function(o, m, k, k2) {\r\n if (k2 === undefined) k2 = k;\r\n o[k2] = m[k];\r\n});\r\n\r\nexport function __exportStar(m, o) {\r\n for (var p in m) if (p !== \"default\" && !Object.prototype.hasOwnProperty.call(o, p)) __createBinding(o, m, p);\r\n}\r\n\r\nexport function __values(o) {\r\n var s = typeof Symbol === \"function\" && Symbol.iterator, m = s && o[s], i = 0;\r\n if (m) return m.call(o);\r\n if (o && typeof o.length === \"number\") return {\r\n next: function () {\r\n if (o && i >= o.length) o = void 0;\r\n return { value: o && o[i++], done: !o };\r\n }\r\n };\r\n throw new TypeError(s ? \"Object is not iterable.\" : \"Symbol.iterator is not defined.\");\r\n}\r\n\r\nexport function __read(o, n) {\r\n var m = typeof Symbol === \"function\" && o[Symbol.iterator];\r\n if (!m) return o;\r\n var i = m.call(o), r, ar = [], e;\r\n try {\r\n while ((n === void 0 || n-- > 0) && !(r = i.next()).done) ar.push(r.value);\r\n }\r\n catch (error) { e = { error: error }; }\r\n finally {\r\n try {\r\n if (r && !r.done && (m = i[\"return\"])) m.call(i);\r\n }\r\n finally { if (e) throw e.error; }\r\n }\r\n return ar;\r\n}\r\n\r\n/** @deprecated */\r\nexport function __spread() {\r\n for (var ar = [], i = 0; i < arguments.length; i++)\r\n ar = ar.concat(__read(arguments[i]));\r\n return ar;\r\n}\r\n\r\n/** @deprecated */\r\nexport function __spreadArrays() {\r\n for (var s = 0, i = 0, il = arguments.length; i < il; i++) s += arguments[i].length;\r\n for (var r = Array(s), k = 0, i = 0; i < il; i++)\r\n for (var a = arguments[i], j = 0, jl = a.length; j < jl; j++, k++)\r\n r[k] = a[j];\r\n return r;\r\n}\r\n\r\nexport function __spreadArray(to, from, pack) {\r\n if (pack || arguments.length === 2) for (var i = 0, l = from.length, ar; i < l; i++) {\r\n if (ar || !(i in from)) {\r\n if (!ar) ar = Array.prototype.slice.call(from, 0, i);\r\n ar[i] = from[i];\r\n }\r\n }\r\n return to.concat(ar || Array.prototype.slice.call(from));\r\n}\r\n\r\nexport function __await(v) {\r\n return this instanceof __await ? (this.v = v, this) : new __await(v);\r\n}\r\n\r\nexport function __asyncGenerator(thisArg, _arguments, generator) {\r\n if (!Symbol.asyncIterator) throw new TypeError(\"Symbol.asyncIterator is not defined.\");\r\n var g = generator.apply(thisArg, _arguments || []), i, q = [];\r\n return i = {}, verb(\"next\"), verb(\"throw\"), verb(\"return\"), i[Symbol.asyncIterator] = function () { return this; }, i;\r\n function verb(n) { if (g[n]) i[n] = function (v) { return new Promise(function (a, b) { q.push([n, v, a, b]) > 1 || resume(n, v); }); }; }\r\n function resume(n, v) { try { step(g[n](v)); } catch (e) { settle(q[0][3], e); } }\r\n function step(r) { r.value instanceof __await ? Promise.resolve(r.value.v).then(fulfill, reject) : settle(q[0][2], r); }\r\n function fulfill(value) { resume(\"next\", value); }\r\n function reject(value) { resume(\"throw\", value); }\r\n function settle(f, v) { if (f(v), q.shift(), q.length) resume(q[0][0], q[0][1]); }\r\n}\r\n\r\nexport function __asyncDelegator(o) {\r\n var i, p;\r\n return i = {}, verb(\"next\"), verb(\"throw\", function (e) { throw e; }), verb(\"return\"), i[Symbol.iterator] = function () { return this; }, i;\r\n function verb(n, f) { i[n] = o[n] ? function (v) { return (p = !p) ? { value: __await(o[n](v)), done: n === \"return\" } : f ? f(v) : v; } : f; }\r\n}\r\n\r\nexport function __asyncValues(o) {\r\n if (!Symbol.asyncIterator) throw new TypeError(\"Symbol.asyncIterator is not defined.\");\r\n var m = o[Symbol.asyncIterator], i;\r\n return m ? m.call(o) : (o = typeof __values === \"function\" ? __values(o) : o[Symbol.iterator](), i = {}, verb(\"next\"), verb(\"throw\"), verb(\"return\"), i[Symbol.asyncIterator] = function () { return this; }, i);\r\n function verb(n) { i[n] = o[n] && function (v) { return new Promise(function (resolve, reject) { v = o[n](v), settle(resolve, reject, v.done, v.value); }); }; }\r\n function settle(resolve, reject, d, v) { Promise.resolve(v).then(function(v) { resolve({ value: v, done: d }); }, reject); }\r\n}\r\n\r\nexport function __makeTemplateObject(cooked, raw) {\r\n if (Object.defineProperty) { Object.defineProperty(cooked, \"raw\", { value: raw }); } else { cooked.raw = raw; }\r\n return cooked;\r\n};\r\n\r\nvar __setModuleDefault = Object.create ? (function(o, v) {\r\n Object.defineProperty(o, \"default\", { enumerable: true, value: v });\r\n}) : function(o, v) {\r\n o[\"default\"] = v;\r\n};\r\n\r\nexport function __importStar(mod) {\r\n if (mod && mod.__esModule) return mod;\r\n var result = {};\r\n if (mod != null) for (var k in mod) if (k !== \"default\" && Object.prototype.hasOwnProperty.call(mod, k)) __createBinding(result, mod, k);\r\n __setModuleDefault(result, mod);\r\n return result;\r\n}\r\n\r\nexport function __importDefault(mod) {\r\n return (mod && mod.__esModule) ? mod : { default: mod };\r\n}\r\n\r\nexport function __classPrivateFieldGet(receiver, state, kind, f) {\r\n if (kind === \"a\" && !f) throw new TypeError(\"Private accessor was defined without a getter\");\r\n if (typeof state === \"function\" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError(\"Cannot read private member from an object whose class did not declare it\");\r\n return kind === \"m\" ? f : kind === \"a\" ? f.call(receiver) : f ? f.value : state.get(receiver);\r\n}\r\n\r\nexport function __classPrivateFieldSet(receiver, state, value, kind, f) {\r\n if (kind === \"m\") throw new TypeError(\"Private method is not writable\");\r\n if (kind === \"a\" && !f) throw new TypeError(\"Private accessor was defined without a setter\");\r\n if (typeof state === \"function\" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError(\"Cannot write private member to an object whose class did not declare it\");\r\n return (kind === \"a\" ? f.call(receiver, value) : f ? f.value = value : state.set(receiver, value)), value;\r\n}\r\n", "/**\n * Returns true if the object is a function.\n * @param value The value to check\n */\nexport function isFunction(value: any): value is (...args: any[]) => any {\n return typeof value === 'function';\n}\n", "/**\n * Used to create Error subclasses until the community moves away from ES5.\n *\n * This is because compiling from TypeScript down to ES5 has issues with subclassing Errors\n * as well as other built-in types: https://github.com/Microsoft/TypeScript/issues/12123\n *\n * @param createImpl A factory function to create the actual constructor implementation. The returned\n * function should be a named function that calls `_super` internally.\n */\nexport function createErrorClass(createImpl: (_super: any) => any): T {\n const _super = (instance: any) => {\n Error.call(instance);\n instance.stack = new Error().stack;\n };\n\n const ctorFunc = createImpl(_super);\n ctorFunc.prototype = Object.create(Error.prototype);\n ctorFunc.prototype.constructor = ctorFunc;\n return ctorFunc;\n}\n", "import { createErrorClass } from './createErrorClass';\n\nexport interface UnsubscriptionError extends Error {\n readonly errors: any[];\n}\n\nexport interface UnsubscriptionErrorCtor {\n /**\n * @deprecated Internal implementation detail. Do not construct error instances.\n * Cannot be tagged as internal: https://github.com/ReactiveX/rxjs/issues/6269\n */\n new (errors: any[]): UnsubscriptionError;\n}\n\n/**\n * An error thrown when one or more errors have occurred during the\n * `unsubscribe` of a {@link Subscription}.\n */\nexport const UnsubscriptionError: UnsubscriptionErrorCtor = createErrorClass(\n (_super) =>\n function UnsubscriptionErrorImpl(this: any, errors: (Error | string)[]) {\n _super(this);\n this.message = errors\n ? `${errors.length} errors occurred during unsubscription:\n${errors.map((err, i) => `${i + 1}) ${err.toString()}`).join('\\n ')}`\n : '';\n this.name = 'UnsubscriptionError';\n this.errors = errors;\n }\n);\n", "/**\n * Removes an item from an array, mutating it.\n * @param arr The array to remove the item from\n * @param item The item to remove\n */\nexport function arrRemove(arr: T[] | undefined | null, item: T) {\n if (arr) {\n const index = arr.indexOf(item);\n 0 <= index && arr.splice(index, 1);\n }\n}\n", "import { isFunction } from './util/isFunction';\nimport { UnsubscriptionError } from './util/UnsubscriptionError';\nimport { SubscriptionLike, TeardownLogic, Unsubscribable } from './types';\nimport { arrRemove } from './util/arrRemove';\n\n/**\n * Represents a disposable resource, such as the execution of an Observable. A\n * Subscription has one important method, `unsubscribe`, that takes no argument\n * and just disposes the resource held by the subscription.\n *\n * Additionally, subscriptions may be grouped together through the `add()`\n * method, which will attach a child Subscription to the current Subscription.\n * When a Subscription is unsubscribed, all its children (and its grandchildren)\n * will be unsubscribed as well.\n *\n * @class Subscription\n */\nexport class Subscription implements SubscriptionLike {\n /** @nocollapse */\n public static EMPTY = (() => {\n const empty = new Subscription();\n empty.closed = true;\n return empty;\n })();\n\n /**\n * A flag to indicate whether this Subscription has already been unsubscribed.\n */\n public closed = false;\n\n private _parentage: Subscription[] | Subscription | null = null;\n\n /**\n * The list of registered finalizers to execute upon unsubscription. Adding and removing from this\n * list occurs in the {@link #add} and {@link #remove} methods.\n */\n private _finalizers: Exclude[] | null = null;\n\n /**\n * @param initialTeardown A function executed first as part of the finalization\n * process that is kicked off when {@link #unsubscribe} is called.\n */\n constructor(private initialTeardown?: () => void) {}\n\n /**\n * Disposes the resources held by the subscription. May, for instance, cancel\n * an ongoing Observable execution or cancel any other type of work that\n * started when the Subscription was created.\n * @return {void}\n */\n unsubscribe(): void {\n let errors: any[] | undefined;\n\n if (!this.closed) {\n this.closed = true;\n\n // Remove this from it's parents.\n const { _parentage } = this;\n if (_parentage) {\n this._parentage = null;\n if (Array.isArray(_parentage)) {\n for (const parent of _parentage) {\n parent.remove(this);\n }\n } else {\n _parentage.remove(this);\n }\n }\n\n const { initialTeardown: initialFinalizer } = this;\n if (isFunction(initialFinalizer)) {\n try {\n initialFinalizer();\n } catch (e) {\n errors = e instanceof UnsubscriptionError ? e.errors : [e];\n }\n }\n\n const { _finalizers } = this;\n if (_finalizers) {\n this._finalizers = null;\n for (const finalizer of _finalizers) {\n try {\n execFinalizer(finalizer);\n } catch (err) {\n errors = errors ?? [];\n if (err instanceof UnsubscriptionError) {\n errors = [...errors, ...err.errors];\n } else {\n errors.push(err);\n }\n }\n }\n }\n\n if (errors) {\n throw new UnsubscriptionError(errors);\n }\n }\n }\n\n /**\n * Adds a finalizer to this subscription, so that finalization will be unsubscribed/called\n * when this subscription is unsubscribed. If this subscription is already {@link #closed},\n * because it has already been unsubscribed, then whatever finalizer is passed to it\n * will automatically be executed (unless the finalizer itself is also a closed subscription).\n *\n * Closed Subscriptions cannot be added as finalizers to any subscription. Adding a closed\n * subscription to a any subscription will result in no operation. (A noop).\n *\n * Adding a subscription to itself, or adding `null` or `undefined` will not perform any\n * operation at all. (A noop).\n *\n * `Subscription` instances that are added to this instance will automatically remove themselves\n * if they are unsubscribed. Functions and {@link Unsubscribable} objects that you wish to remove\n * will need to be removed manually with {@link #remove}\n *\n * @param teardown The finalization logic to add to this subscription.\n */\n add(teardown: TeardownLogic): void {\n // Only add the finalizer if it's not undefined\n // and don't add a subscription to itself.\n if (teardown && teardown !== this) {\n if (this.closed) {\n // If this subscription is already closed,\n // execute whatever finalizer is handed to it automatically.\n execFinalizer(teardown);\n } else {\n if (teardown instanceof Subscription) {\n // We don't add closed subscriptions, and we don't add the same subscription\n // twice. Subscription unsubscribe is idempotent.\n if (teardown.closed || teardown._hasParent(this)) {\n return;\n }\n teardown._addParent(this);\n }\n (this._finalizers = this._finalizers ?? []).push(teardown);\n }\n }\n }\n\n /**\n * Checks to see if a this subscription already has a particular parent.\n * This will signal that this subscription has already been added to the parent in question.\n * @param parent the parent to check for\n */\n private _hasParent(parent: Subscription) {\n const { _parentage } = this;\n return _parentage === parent || (Array.isArray(_parentage) && _parentage.includes(parent));\n }\n\n /**\n * Adds a parent to this subscription so it can be removed from the parent if it\n * unsubscribes on it's own.\n *\n * NOTE: THIS ASSUMES THAT {@link _hasParent} HAS ALREADY BEEN CHECKED.\n * @param parent The parent subscription to add\n */\n private _addParent(parent: Subscription) {\n const { _parentage } = this;\n this._parentage = Array.isArray(_parentage) ? (_parentage.push(parent), _parentage) : _parentage ? [_parentage, parent] : parent;\n }\n\n /**\n * Called on a child when it is removed via {@link #remove}.\n * @param parent The parent to remove\n */\n private _removeParent(parent: Subscription) {\n const { _parentage } = this;\n if (_parentage === parent) {\n this._parentage = null;\n } else if (Array.isArray(_parentage)) {\n arrRemove(_parentage, parent);\n }\n }\n\n /**\n * Removes a finalizer from this subscription that was previously added with the {@link #add} method.\n *\n * Note that `Subscription` instances, when unsubscribed, will automatically remove themselves\n * from every other `Subscription` they have been added to. This means that using the `remove` method\n * is not a common thing and should be used thoughtfully.\n *\n * If you add the same finalizer instance of a function or an unsubscribable object to a `Subscription` instance\n * more than once, you will need to call `remove` the same number of times to remove all instances.\n *\n * All finalizer instances are removed to free up memory upon unsubscription.\n *\n * @param teardown The finalizer to remove from this subscription\n */\n remove(teardown: Exclude): void {\n const { _finalizers } = this;\n _finalizers && arrRemove(_finalizers, teardown);\n\n if (teardown instanceof Subscription) {\n teardown._removeParent(this);\n }\n }\n}\n\nexport const EMPTY_SUBSCRIPTION = Subscription.EMPTY;\n\nexport function isSubscription(value: any): value is Subscription {\n return (\n value instanceof Subscription ||\n (value && 'closed' in value && isFunction(value.remove) && isFunction(value.add) && isFunction(value.unsubscribe))\n );\n}\n\nfunction execFinalizer(finalizer: Unsubscribable | (() => void)) {\n if (isFunction(finalizer)) {\n finalizer();\n } else {\n finalizer.unsubscribe();\n }\n}\n", "import { Subscriber } from './Subscriber';\nimport { ObservableNotification } from './types';\n\n/**\n * The {@link GlobalConfig} object for RxJS. It is used to configure things\n * like how to react on unhandled errors.\n */\nexport const config: GlobalConfig = {\n onUnhandledError: null,\n onStoppedNotification: null,\n Promise: undefined,\n useDeprecatedSynchronousErrorHandling: false,\n useDeprecatedNextContext: false,\n};\n\n/**\n * The global configuration object for RxJS, used to configure things\n * like how to react on unhandled errors. Accessible via {@link config}\n * object.\n */\nexport interface GlobalConfig {\n /**\n * A registration point for unhandled errors from RxJS. These are errors that\n * cannot were not handled by consuming code in the usual subscription path. For\n * example, if you have this configured, and you subscribe to an observable without\n * providing an error handler, errors from that subscription will end up here. This\n * will _always_ be called asynchronously on another job in the runtime. This is because\n * we do not want errors thrown in this user-configured handler to interfere with the\n * behavior of the library.\n */\n onUnhandledError: ((err: any) => void) | null;\n\n /**\n * A registration point for notifications that cannot be sent to subscribers because they\n * have completed, errored or have been explicitly unsubscribed. By default, next, complete\n * and error notifications sent to stopped subscribers are noops. However, sometimes callers\n * might want a different behavior. For example, with sources that attempt to report errors\n * to stopped subscribers, a caller can configure RxJS to throw an unhandled error instead.\n * This will _always_ be called asynchronously on another job in the runtime. This is because\n * we do not want errors thrown in this user-configured handler to interfere with the\n * behavior of the library.\n */\n onStoppedNotification: ((notification: ObservableNotification, subscriber: Subscriber) => void) | null;\n\n /**\n * The promise constructor used by default for {@link Observable#toPromise toPromise} and {@link Observable#forEach forEach}\n * methods.\n *\n * @deprecated As of version 8, RxJS will no longer support this sort of injection of a\n * Promise constructor. If you need a Promise implementation other than native promises,\n * please polyfill/patch Promise as you see appropriate. Will be removed in v8.\n */\n Promise?: PromiseConstructorLike;\n\n /**\n * If true, turns on synchronous error rethrowing, which is a deprecated behavior\n * in v6 and higher. This behavior enables bad patterns like wrapping a subscribe\n * call in a try/catch block. It also enables producer interference, a nasty bug\n * where a multicast can be broken for all observers by a downstream consumer with\n * an unhandled error. DO NOT USE THIS FLAG UNLESS IT'S NEEDED TO BUY TIME\n * FOR MIGRATION REASONS.\n *\n * @deprecated As of version 8, RxJS will no longer support synchronous throwing\n * of unhandled errors. All errors will be thrown on a separate call stack to prevent bad\n * behaviors described above. Will be removed in v8.\n */\n useDeprecatedSynchronousErrorHandling: boolean;\n\n /**\n * If true, enables an as-of-yet undocumented feature from v5: The ability to access\n * `unsubscribe()` via `this` context in `next` functions created in observers passed\n * to `subscribe`.\n *\n * This is being removed because the performance was severely problematic, and it could also cause\n * issues when types other than POJOs are passed to subscribe as subscribers, as they will likely have\n * their `this` context overwritten.\n *\n * @deprecated As of version 8, RxJS will no longer support altering the\n * context of next functions provided as part of an observer to Subscribe. Instead,\n * you will have access to a subscription or a signal or token that will allow you to do things like\n * unsubscribe and test closed status. Will be removed in v8.\n */\n useDeprecatedNextContext: boolean;\n}\n", "import type { TimerHandle } from './timerHandle';\ntype SetTimeoutFunction = (handler: () => void, timeout?: number, ...args: any[]) => TimerHandle;\ntype ClearTimeoutFunction = (handle: TimerHandle) => void;\n\ninterface TimeoutProvider {\n setTimeout: SetTimeoutFunction;\n clearTimeout: ClearTimeoutFunction;\n delegate:\n | {\n setTimeout: SetTimeoutFunction;\n clearTimeout: ClearTimeoutFunction;\n }\n | undefined;\n}\n\nexport const timeoutProvider: TimeoutProvider = {\n // When accessing the delegate, use the variable rather than `this` so that\n // the functions can be called without being bound to the provider.\n setTimeout(handler: () => void, timeout?: number, ...args) {\n const { delegate } = timeoutProvider;\n if (delegate?.setTimeout) {\n return delegate.setTimeout(handler, timeout, ...args);\n }\n return setTimeout(handler, timeout, ...args);\n },\n clearTimeout(handle) {\n const { delegate } = timeoutProvider;\n return (delegate?.clearTimeout || clearTimeout)(handle as any);\n },\n delegate: undefined,\n};\n", "import { config } from '../config';\nimport { timeoutProvider } from '../scheduler/timeoutProvider';\n\n/**\n * Handles an error on another job either with the user-configured {@link onUnhandledError},\n * or by throwing it on that new job so it can be picked up by `window.onerror`, `process.on('error')`, etc.\n *\n * This should be called whenever there is an error that is out-of-band with the subscription\n * or when an error hits a terminal boundary of the subscription and no error handler was provided.\n *\n * @param err the error to report\n */\nexport function reportUnhandledError(err: any) {\n timeoutProvider.setTimeout(() => {\n const { onUnhandledError } = config;\n if (onUnhandledError) {\n // Execute the user-configured error handler.\n onUnhandledError(err);\n } else {\n // Throw so it is picked up by the runtime's uncaught error mechanism.\n throw err;\n }\n });\n}\n", "/* tslint:disable:no-empty */\nexport function noop() { }\n", "import { CompleteNotification, NextNotification, ErrorNotification } from './types';\n\n/**\n * A completion object optimized for memory use and created to be the\n * same \"shape\" as other notifications in v8.\n * @internal\n */\nexport const COMPLETE_NOTIFICATION = (() => createNotification('C', undefined, undefined) as CompleteNotification)();\n\n/**\n * Internal use only. Creates an optimized error notification that is the same \"shape\"\n * as other notifications.\n * @internal\n */\nexport function errorNotification(error: any): ErrorNotification {\n return createNotification('E', undefined, error) as any;\n}\n\n/**\n * Internal use only. Creates an optimized next notification that is the same \"shape\"\n * as other notifications.\n * @internal\n */\nexport function nextNotification(value: T) {\n return createNotification('N', value, undefined) as NextNotification;\n}\n\n/**\n * Ensures that all notifications created internally have the same \"shape\" in v8.\n *\n * TODO: This is only exported to support a crazy legacy test in `groupBy`.\n * @internal\n */\nexport function createNotification(kind: 'N' | 'E' | 'C', value: any, error: any) {\n return {\n kind,\n value,\n error,\n };\n}\n", "import { config } from '../config';\n\nlet context: { errorThrown: boolean; error: any } | null = null;\n\n/**\n * Handles dealing with errors for super-gross mode. Creates a context, in which\n * any synchronously thrown errors will be passed to {@link captureError}. Which\n * will record the error such that it will be rethrown after the call back is complete.\n * TODO: Remove in v8\n * @param cb An immediately executed function.\n */\nexport function errorContext(cb: () => void) {\n if (config.useDeprecatedSynchronousErrorHandling) {\n const isRoot = !context;\n if (isRoot) {\n context = { errorThrown: false, error: null };\n }\n cb();\n if (isRoot) {\n const { errorThrown, error } = context!;\n context = null;\n if (errorThrown) {\n throw error;\n }\n }\n } else {\n // This is the general non-deprecated path for everyone that\n // isn't crazy enough to use super-gross mode (useDeprecatedSynchronousErrorHandling)\n cb();\n }\n}\n\n/**\n * Captures errors only in super-gross mode.\n * @param err the error to capture\n */\nexport function captureError(err: any) {\n if (config.useDeprecatedSynchronousErrorHandling && context) {\n context.errorThrown = true;\n context.error = err;\n }\n}\n", "import { isFunction } from './util/isFunction';\nimport { Observer, ObservableNotification } from './types';\nimport { isSubscription, Subscription } from './Subscription';\nimport { config } from './config';\nimport { reportUnhandledError } from './util/reportUnhandledError';\nimport { noop } from './util/noop';\nimport { nextNotification, errorNotification, COMPLETE_NOTIFICATION } from './NotificationFactories';\nimport { timeoutProvider } from './scheduler/timeoutProvider';\nimport { captureError } from './util/errorContext';\n\n/**\n * Implements the {@link Observer} interface and extends the\n * {@link Subscription} class. While the {@link Observer} is the public API for\n * consuming the values of an {@link Observable}, all Observers get converted to\n * a Subscriber, in order to provide Subscription-like capabilities such as\n * `unsubscribe`. Subscriber is a common type in RxJS, and crucial for\n * implementing operators, but it is rarely used as a public API.\n *\n * @class Subscriber\n */\nexport class Subscriber extends Subscription implements Observer {\n /**\n * A static factory for a Subscriber, given a (potentially partial) definition\n * of an Observer.\n * @param next The `next` callback of an Observer.\n * @param error The `error` callback of an\n * Observer.\n * @param complete The `complete` callback of an\n * Observer.\n * @return A Subscriber wrapping the (partially defined)\n * Observer represented by the given arguments.\n * @nocollapse\n * @deprecated Do not use. Will be removed in v8. There is no replacement for this\n * method, and there is no reason to be creating instances of `Subscriber` directly.\n * If you have a specific use case, please file an issue.\n */\n static create(next?: (x?: T) => void, error?: (e?: any) => void, complete?: () => void): Subscriber {\n return new SafeSubscriber(next, error, complete);\n }\n\n /** @deprecated Internal implementation detail, do not use directly. Will be made internal in v8. */\n protected isStopped: boolean = false;\n /** @deprecated Internal implementation detail, do not use directly. Will be made internal in v8. */\n protected destination: Subscriber | Observer; // this `any` is the escape hatch to erase extra type param (e.g. R)\n\n /**\n * @deprecated Internal implementation detail, do not use directly. Will be made internal in v8.\n * There is no reason to directly create an instance of Subscriber. This type is exported for typings reasons.\n */\n constructor(destination?: Subscriber | Observer) {\n super();\n if (destination) {\n this.destination = destination;\n // Automatically chain subscriptions together here.\n // if destination is a Subscription, then it is a Subscriber.\n if (isSubscription(destination)) {\n destination.add(this);\n }\n } else {\n this.destination = EMPTY_OBSERVER;\n }\n }\n\n /**\n * The {@link Observer} callback to receive notifications of type `next` from\n * the Observable, with a value. The Observable may call this method 0 or more\n * times.\n * @param {T} [value] The `next` value.\n * @return {void}\n */\n next(value?: T): void {\n if (this.isStopped) {\n handleStoppedNotification(nextNotification(value), this);\n } else {\n this._next(value!);\n }\n }\n\n /**\n * The {@link Observer} callback to receive notifications of type `error` from\n * the Observable, with an attached `Error`. Notifies the Observer that\n * the Observable has experienced an error condition.\n * @param {any} [err] The `error` exception.\n * @return {void}\n */\n error(err?: any): void {\n if (this.isStopped) {\n handleStoppedNotification(errorNotification(err), this);\n } else {\n this.isStopped = true;\n this._error(err);\n }\n }\n\n /**\n * The {@link Observer} callback to receive a valueless notification of type\n * `complete` from the Observable. Notifies the Observer that the Observable\n * has finished sending push-based notifications.\n * @return {void}\n */\n complete(): void {\n if (this.isStopped) {\n handleStoppedNotification(COMPLETE_NOTIFICATION, this);\n } else {\n this.isStopped = true;\n this._complete();\n }\n }\n\n unsubscribe(): void {\n if (!this.closed) {\n this.isStopped = true;\n super.unsubscribe();\n this.destination = null!;\n }\n }\n\n protected _next(value: T): void {\n this.destination.next(value);\n }\n\n protected _error(err: any): void {\n try {\n this.destination.error(err);\n } finally {\n this.unsubscribe();\n }\n }\n\n protected _complete(): void {\n try {\n this.destination.complete();\n } finally {\n this.unsubscribe();\n }\n }\n}\n\n/**\n * This bind is captured here because we want to be able to have\n * compatibility with monoid libraries that tend to use a method named\n * `bind`. In particular, a library called Monio requires this.\n */\nconst _bind = Function.prototype.bind;\n\nfunction bind any>(fn: Fn, thisArg: any): Fn {\n return _bind.call(fn, thisArg);\n}\n\n/**\n * Internal optimization only, DO NOT EXPOSE.\n * @internal\n */\nclass ConsumerObserver implements Observer {\n constructor(private partialObserver: Partial>) {}\n\n next(value: T): void {\n const { partialObserver } = this;\n if (partialObserver.next) {\n try {\n partialObserver.next(value);\n } catch (error) {\n handleUnhandledError(error);\n }\n }\n }\n\n error(err: any): void {\n const { partialObserver } = this;\n if (partialObserver.error) {\n try {\n partialObserver.error(err);\n } catch (error) {\n handleUnhandledError(error);\n }\n } else {\n handleUnhandledError(err);\n }\n }\n\n complete(): void {\n const { partialObserver } = this;\n if (partialObserver.complete) {\n try {\n partialObserver.complete();\n } catch (error) {\n handleUnhandledError(error);\n }\n }\n }\n}\n\nexport class SafeSubscriber extends Subscriber {\n constructor(\n observerOrNext?: Partial> | ((value: T) => void) | null,\n error?: ((e?: any) => void) | null,\n complete?: (() => void) | null\n ) {\n super();\n\n let partialObserver: Partial>;\n if (isFunction(observerOrNext) || !observerOrNext) {\n // The first argument is a function, not an observer. The next\n // two arguments *could* be observers, or they could be empty.\n partialObserver = {\n next: (observerOrNext ?? undefined) as (((value: T) => void) | undefined),\n error: error ?? undefined,\n complete: complete ?? undefined,\n };\n } else {\n // The first argument is a partial observer.\n let context: any;\n if (this && config.useDeprecatedNextContext) {\n // This is a deprecated path that made `this.unsubscribe()` available in\n // next handler functions passed to subscribe. This only exists behind a flag\n // now, as it is *very* slow.\n context = Object.create(observerOrNext);\n context.unsubscribe = () => this.unsubscribe();\n partialObserver = {\n next: observerOrNext.next && bind(observerOrNext.next, context),\n error: observerOrNext.error && bind(observerOrNext.error, context),\n complete: observerOrNext.complete && bind(observerOrNext.complete, context),\n };\n } else {\n // The \"normal\" path. Just use the partial observer directly.\n partialObserver = observerOrNext;\n }\n }\n\n // Wrap the partial observer to ensure it's a full observer, and\n // make sure proper error handling is accounted for.\n this.destination = new ConsumerObserver(partialObserver);\n }\n}\n\nfunction handleUnhandledError(error: any) {\n if (config.useDeprecatedSynchronousErrorHandling) {\n captureError(error);\n } else {\n // Ideal path, we report this as an unhandled error,\n // which is thrown on a new call stack.\n reportUnhandledError(error);\n }\n}\n\n/**\n * An error handler used when no error handler was supplied\n * to the SafeSubscriber -- meaning no error handler was supplied\n * do the `subscribe` call on our observable.\n * @param err The error to handle\n */\nfunction defaultErrorHandler(err: any) {\n throw err;\n}\n\n/**\n * A handler for notifications that cannot be sent to a stopped subscriber.\n * @param notification The notification being sent\n * @param subscriber The stopped subscriber\n */\nfunction handleStoppedNotification(notification: ObservableNotification, subscriber: Subscriber) {\n const { onStoppedNotification } = config;\n onStoppedNotification && timeoutProvider.setTimeout(() => onStoppedNotification(notification, subscriber));\n}\n\n/**\n * The observer used as a stub for subscriptions where the user did not\n * pass any arguments to `subscribe`. Comes with the default error handling\n * behavior.\n */\nexport const EMPTY_OBSERVER: Readonly> & { closed: true } = {\n closed: true,\n next: noop,\n error: defaultErrorHandler,\n complete: noop,\n};\n", "/**\n * Symbol.observable or a string \"@@observable\". Used for interop\n *\n * @deprecated We will no longer be exporting this symbol in upcoming versions of RxJS.\n * Instead polyfill and use Symbol.observable directly *or* use https://www.npmjs.com/package/symbol-observable\n */\nexport const observable: string | symbol = (() => (typeof Symbol === 'function' && Symbol.observable) || '@@observable')();\n", "/**\n * This function takes one parameter and just returns it. Simply put,\n * this is like `(x: T): T => x`.\n *\n * ## Examples\n *\n * This is useful in some cases when using things like `mergeMap`\n *\n * ```ts\n * import { interval, take, map, range, mergeMap, identity } from 'rxjs';\n *\n * const source$ = interval(1000).pipe(take(5));\n *\n * const result$ = source$.pipe(\n * map(i => range(i)),\n * mergeMap(identity) // same as mergeMap(x => x)\n * );\n *\n * result$.subscribe({\n * next: console.log\n * });\n * ```\n *\n * Or when you want to selectively apply an operator\n *\n * ```ts\n * import { interval, take, identity } from 'rxjs';\n *\n * const shouldLimit = () => Math.random() < 0.5;\n *\n * const source$ = interval(1000);\n *\n * const result$ = source$.pipe(shouldLimit() ? take(5) : identity);\n *\n * result$.subscribe({\n * next: console.log\n * });\n * ```\n *\n * @param x Any value that is returned by this function\n * @returns The value passed as the first parameter to this function\n */\nexport function identity(x: T): T {\n return x;\n}\n", "import { identity } from './identity';\nimport { UnaryFunction } from '../types';\n\nexport function pipe(): typeof identity;\nexport function pipe(fn1: UnaryFunction): UnaryFunction;\nexport function pipe(fn1: UnaryFunction, fn2: UnaryFunction): UnaryFunction;\nexport function pipe(fn1: UnaryFunction, fn2: UnaryFunction, fn3: UnaryFunction): UnaryFunction;\nexport function pipe(\n fn1: UnaryFunction,\n fn2: UnaryFunction,\n fn3: UnaryFunction,\n fn4: UnaryFunction\n): UnaryFunction;\nexport function pipe(\n fn1: UnaryFunction,\n fn2: UnaryFunction,\n fn3: UnaryFunction,\n fn4: UnaryFunction,\n fn5: UnaryFunction\n): UnaryFunction;\nexport function pipe(\n fn1: UnaryFunction,\n fn2: UnaryFunction,\n fn3: UnaryFunction,\n fn4: UnaryFunction,\n fn5: UnaryFunction,\n fn6: UnaryFunction\n): UnaryFunction;\nexport function pipe(\n fn1: UnaryFunction,\n fn2: UnaryFunction,\n fn3: UnaryFunction,\n fn4: UnaryFunction,\n fn5: UnaryFunction,\n fn6: UnaryFunction,\n fn7: UnaryFunction\n): UnaryFunction;\nexport function pipe(\n fn1: UnaryFunction,\n fn2: UnaryFunction,\n fn3: UnaryFunction,\n fn4: UnaryFunction,\n fn5: UnaryFunction,\n fn6: UnaryFunction,\n fn7: UnaryFunction,\n fn8: UnaryFunction\n): UnaryFunction;\nexport function pipe(\n fn1: UnaryFunction,\n fn2: UnaryFunction,\n fn3: UnaryFunction,\n fn4: UnaryFunction,\n fn5: UnaryFunction,\n fn6: UnaryFunction,\n fn7: UnaryFunction,\n fn8: UnaryFunction,\n fn9: UnaryFunction\n): UnaryFunction;\nexport function pipe(\n fn1: UnaryFunction,\n fn2: UnaryFunction,\n fn3: UnaryFunction,\n fn4: UnaryFunction,\n fn5: UnaryFunction,\n fn6: UnaryFunction,\n fn7: UnaryFunction,\n fn8: UnaryFunction,\n fn9: UnaryFunction,\n ...fns: UnaryFunction[]\n): UnaryFunction;\n\n/**\n * pipe() can be called on one or more functions, each of which can take one argument (\"UnaryFunction\")\n * and uses it to return a value.\n * It returns a function that takes one argument, passes it to the first UnaryFunction, and then\n * passes the result to the next one, passes that result to the next one, and so on. \n */\nexport function pipe(...fns: Array>): UnaryFunction {\n return pipeFromArray(fns);\n}\n\n/** @internal */\nexport function pipeFromArray(fns: Array>): UnaryFunction {\n if (fns.length === 0) {\n return identity as UnaryFunction;\n }\n\n if (fns.length === 1) {\n return fns[0];\n }\n\n return function piped(input: T): R {\n return fns.reduce((prev: any, fn: UnaryFunction) => fn(prev), input as any);\n };\n}\n", "import { Operator } from './Operator';\nimport { SafeSubscriber, Subscriber } from './Subscriber';\nimport { isSubscription, Subscription } from './Subscription';\nimport { TeardownLogic, OperatorFunction, Subscribable, Observer } from './types';\nimport { observable as Symbol_observable } from './symbol/observable';\nimport { pipeFromArray } from './util/pipe';\nimport { config } from './config';\nimport { isFunction } from './util/isFunction';\nimport { errorContext } from './util/errorContext';\n\n/**\n * A representation of any set of values over any amount of time. This is the most basic building block\n * of RxJS.\n *\n * @class Observable\n */\nexport class Observable implements Subscribable {\n /**\n * @deprecated Internal implementation detail, do not use directly. Will be made internal in v8.\n */\n source: Observable | undefined;\n\n /**\n * @deprecated Internal implementation detail, do not use directly. Will be made internal in v8.\n */\n operator: Operator | undefined;\n\n /**\n * @constructor\n * @param {Function} subscribe the function that is called when the Observable is\n * initially subscribed to. This function is given a Subscriber, to which new values\n * can be `next`ed, or an `error` method can be called to raise an error, or\n * `complete` can be called to notify of a successful completion.\n */\n constructor(subscribe?: (this: Observable, subscriber: Subscriber) => TeardownLogic) {\n if (subscribe) {\n this._subscribe = subscribe;\n }\n }\n\n // HACK: Since TypeScript inherits static properties too, we have to\n // fight against TypeScript here so Subject can have a different static create signature\n /**\n * Creates a new Observable by calling the Observable constructor\n * @owner Observable\n * @method create\n * @param {Function} subscribe? the subscriber function to be passed to the Observable constructor\n * @return {Observable} a new observable\n * @nocollapse\n * @deprecated Use `new Observable()` instead. Will be removed in v8.\n */\n static create: (...args: any[]) => any = (subscribe?: (subscriber: Subscriber) => TeardownLogic) => {\n return new Observable(subscribe);\n };\n\n /**\n * Creates a new Observable, with this Observable instance as the source, and the passed\n * operator defined as the new observable's operator.\n * @method lift\n * @param operator the operator defining the operation to take on the observable\n * @return a new observable with the Operator applied\n * @deprecated Internal implementation detail, do not use directly. Will be made internal in v8.\n * If you have implemented an operator using `lift`, it is recommended that you create an\n * operator by simply returning `new Observable()` directly. See \"Creating new operators from\n * scratch\" section here: https://rxjs.dev/guide/operators\n */\n lift(operator?: Operator): Observable {\n const observable = new Observable();\n observable.source = this;\n observable.operator = operator;\n return observable;\n }\n\n subscribe(observerOrNext?: Partial> | ((value: T) => void)): Subscription;\n /** @deprecated Instead of passing separate callback arguments, use an observer argument. Signatures taking separate callback arguments will be removed in v8. Details: https://rxjs.dev/deprecations/subscribe-arguments */\n subscribe(next?: ((value: T) => void) | null, error?: ((error: any) => void) | null, complete?: (() => void) | null): Subscription;\n /**\n * Invokes an execution of an Observable and registers Observer handlers for notifications it will emit.\n *\n * Use it when you have all these Observables, but still nothing is happening.\n *\n * `subscribe` is not a regular operator, but a method that calls Observable's internal `subscribe` function. It\n * might be for example a function that you passed to Observable's constructor, but most of the time it is\n * a library implementation, which defines what will be emitted by an Observable, and when it be will emitted. This means\n * that calling `subscribe` is actually the moment when Observable starts its work, not when it is created, as it is often\n * the thought.\n *\n * Apart from starting the execution of an Observable, this method allows you to listen for values\n * that an Observable emits, as well as for when it completes or errors. You can achieve this in two\n * of the following ways.\n *\n * The first way is creating an object that implements {@link Observer} interface. It should have methods\n * defined by that interface, but note that it should be just a regular JavaScript object, which you can create\n * yourself in any way you want (ES6 class, classic function constructor, object literal etc.). In particular, do\n * not attempt to use any RxJS implementation details to create Observers - you don't need them. Remember also\n * that your object does not have to implement all methods. If you find yourself creating a method that doesn't\n * do anything, you can simply omit it. Note however, if the `error` method is not provided and an error happens,\n * it will be thrown asynchronously. Errors thrown asynchronously cannot be caught using `try`/`catch`. Instead,\n * use the {@link onUnhandledError} configuration option or use a runtime handler (like `window.onerror` or\n * `process.on('error)`) to be notified of unhandled errors. Because of this, it's recommended that you provide\n * an `error` method to avoid missing thrown errors.\n *\n * The second way is to give up on Observer object altogether and simply provide callback functions in place of its methods.\n * This means you can provide three functions as arguments to `subscribe`, where the first function is equivalent\n * of a `next` method, the second of an `error` method and the third of a `complete` method. Just as in case of an Observer,\n * if you do not need to listen for something, you can omit a function by passing `undefined` or `null`,\n * since `subscribe` recognizes these functions by where they were placed in function call. When it comes\n * to the `error` function, as with an Observer, if not provided, errors emitted by an Observable will be thrown asynchronously.\n *\n * You can, however, subscribe with no parameters at all. This may be the case where you're not interested in terminal events\n * and you also handled emissions internally by using operators (e.g. using `tap`).\n *\n * Whichever style of calling `subscribe` you use, in both cases it returns a Subscription object.\n * This object allows you to call `unsubscribe` on it, which in turn will stop the work that an Observable does and will clean\n * up all resources that an Observable used. Note that cancelling a subscription will not call `complete` callback\n * provided to `subscribe` function, which is reserved for a regular completion signal that comes from an Observable.\n *\n * Remember that callbacks provided to `subscribe` are not guaranteed to be called asynchronously.\n * It is an Observable itself that decides when these functions will be called. For example {@link of}\n * by default emits all its values synchronously. Always check documentation for how given Observable\n * will behave when subscribed and if its default behavior can be modified with a `scheduler`.\n *\n * #### Examples\n *\n * Subscribe with an {@link guide/observer Observer}\n *\n * ```ts\n * import { of } from 'rxjs';\n *\n * const sumObserver = {\n * sum: 0,\n * next(value) {\n * console.log('Adding: ' + value);\n * this.sum = this.sum + value;\n * },\n * error() {\n * // We actually could just remove this method,\n * // since we do not really care about errors right now.\n * },\n * complete() {\n * console.log('Sum equals: ' + this.sum);\n * }\n * };\n *\n * of(1, 2, 3) // Synchronously emits 1, 2, 3 and then completes.\n * .subscribe(sumObserver);\n *\n * // Logs:\n * // 'Adding: 1'\n * // 'Adding: 2'\n * // 'Adding: 3'\n * // 'Sum equals: 6'\n * ```\n *\n * Subscribe with functions ({@link deprecations/subscribe-arguments deprecated})\n *\n * ```ts\n * import { of } from 'rxjs'\n *\n * let sum = 0;\n *\n * of(1, 2, 3).subscribe(\n * value => {\n * console.log('Adding: ' + value);\n * sum = sum + value;\n * },\n * undefined,\n * () => console.log('Sum equals: ' + sum)\n * );\n *\n * // Logs:\n * // 'Adding: 1'\n * // 'Adding: 2'\n * // 'Adding: 3'\n * // 'Sum equals: 6'\n * ```\n *\n * Cancel a subscription\n *\n * ```ts\n * import { interval } from 'rxjs';\n *\n * const subscription = interval(1000).subscribe({\n * next(num) {\n * console.log(num)\n * },\n * complete() {\n * // Will not be called, even when cancelling subscription.\n * console.log('completed!');\n * }\n * });\n *\n * setTimeout(() => {\n * subscription.unsubscribe();\n * console.log('unsubscribed!');\n * }, 2500);\n *\n * // Logs:\n * // 0 after 1s\n * // 1 after 2s\n * // 'unsubscribed!' after 2.5s\n * ```\n *\n * @param {Observer|Function} observerOrNext (optional) Either an observer with methods to be called,\n * or the first of three possible handlers, which is the handler for each value emitted from the subscribed\n * Observable.\n * @param {Function} error (optional) A handler for a terminal event resulting from an error. If no error handler is provided,\n * the error will be thrown asynchronously as unhandled.\n * @param {Function} complete (optional) A handler for a terminal event resulting from successful completion.\n * @return {Subscription} a subscription reference to the registered handlers\n * @method subscribe\n */\n subscribe(\n observerOrNext?: Partial> | ((value: T) => void) | null,\n error?: ((error: any) => void) | null,\n complete?: (() => void) | null\n ): Subscription {\n const subscriber = isSubscriber(observerOrNext) ? observerOrNext : new SafeSubscriber(observerOrNext, error, complete);\n\n errorContext(() => {\n const { operator, source } = this;\n subscriber.add(\n operator\n ? // We're dealing with a subscription in the\n // operator chain to one of our lifted operators.\n operator.call(subscriber, source)\n : source\n ? // If `source` has a value, but `operator` does not, something that\n // had intimate knowledge of our API, like our `Subject`, must have\n // set it. We're going to just call `_subscribe` directly.\n this._subscribe(subscriber)\n : // In all other cases, we're likely wrapping a user-provided initializer\n // function, so we need to catch errors and handle them appropriately.\n this._trySubscribe(subscriber)\n );\n });\n\n return subscriber;\n }\n\n /** @internal */\n protected _trySubscribe(sink: Subscriber): TeardownLogic {\n try {\n return this._subscribe(sink);\n } catch (err) {\n // We don't need to return anything in this case,\n // because it's just going to try to `add()` to a subscription\n // above.\n sink.error(err);\n }\n }\n\n /**\n * Used as a NON-CANCELLABLE means of subscribing to an observable, for use with\n * APIs that expect promises, like `async/await`. You cannot unsubscribe from this.\n *\n * **WARNING**: Only use this with observables you *know* will complete. If the source\n * observable does not complete, you will end up with a promise that is hung up, and\n * potentially all of the state of an async function hanging out in memory. To avoid\n * this situation, look into adding something like {@link timeout}, {@link take},\n * {@link takeWhile}, or {@link takeUntil} amongst others.\n *\n * #### Example\n *\n * ```ts\n * import { interval, take } from 'rxjs';\n *\n * const source$ = interval(1000).pipe(take(4));\n *\n * async function getTotal() {\n * let total = 0;\n *\n * await source$.forEach(value => {\n * total += value;\n * console.log('observable -> ' + value);\n * });\n *\n * return total;\n * }\n *\n * getTotal().then(\n * total => console.log('Total: ' + total)\n * );\n *\n * // Expected:\n * // 'observable -> 0'\n * // 'observable -> 1'\n * // 'observable -> 2'\n * // 'observable -> 3'\n * // 'Total: 6'\n * ```\n *\n * @param next a handler for each value emitted by the observable\n * @return a promise that either resolves on observable completion or\n * rejects with the handled error\n */\n forEach(next: (value: T) => void): Promise;\n\n /**\n * @param next a handler for each value emitted by the observable\n * @param promiseCtor a constructor function used to instantiate the Promise\n * @return a promise that either resolves on observable completion or\n * rejects with the handled error\n * @deprecated Passing a Promise constructor will no longer be available\n * in upcoming versions of RxJS. This is because it adds weight to the library, for very\n * little benefit. If you need this functionality, it is recommended that you either\n * polyfill Promise, or you create an adapter to convert the returned native promise\n * to whatever promise implementation you wanted. Will be removed in v8.\n */\n forEach(next: (value: T) => void, promiseCtor: PromiseConstructorLike): Promise;\n\n forEach(next: (value: T) => void, promiseCtor?: PromiseConstructorLike): Promise {\n promiseCtor = getPromiseCtor(promiseCtor);\n\n return new promiseCtor((resolve, reject) => {\n const subscriber = new SafeSubscriber({\n next: (value) => {\n try {\n next(value);\n } catch (err) {\n reject(err);\n subscriber.unsubscribe();\n }\n },\n error: reject,\n complete: resolve,\n });\n this.subscribe(subscriber);\n }) as Promise;\n }\n\n /** @internal */\n protected _subscribe(subscriber: Subscriber): TeardownLogic {\n return this.source?.subscribe(subscriber);\n }\n\n /**\n * An interop point defined by the es7-observable spec https://github.com/zenparsing/es-observable\n * @method Symbol.observable\n * @return {Observable} this instance of the observable\n */\n [Symbol_observable]() {\n return this;\n }\n\n /* tslint:disable:max-line-length */\n pipe(): Observable;\n pipe(op1: OperatorFunction): Observable;\n pipe(op1: OperatorFunction, op2: OperatorFunction): Observable;\n pipe(op1: OperatorFunction, op2: OperatorFunction, op3: OperatorFunction): Observable;\n pipe(\n op1: OperatorFunction,\n op2: OperatorFunction,\n op3: OperatorFunction,\n op4: OperatorFunction\n ): Observable;\n pipe(\n op1: OperatorFunction,\n op2: OperatorFunction,\n op3: OperatorFunction,\n op4: OperatorFunction,\n op5: OperatorFunction\n ): Observable;\n pipe(\n op1: OperatorFunction,\n op2: OperatorFunction,\n op3: OperatorFunction,\n op4: OperatorFunction,\n op5: OperatorFunction,\n op6: OperatorFunction\n ): Observable;\n pipe(\n op1: OperatorFunction,\n op2: OperatorFunction,\n op3: OperatorFunction,\n op4: OperatorFunction,\n op5: OperatorFunction,\n op6: OperatorFunction,\n op7: OperatorFunction\n ): Observable;\n pipe(\n op1: OperatorFunction,\n op2: OperatorFunction,\n op3: OperatorFunction,\n op4: OperatorFunction,\n op5: OperatorFunction,\n op6: OperatorFunction,\n op7: OperatorFunction,\n op8: OperatorFunction\n ): Observable;\n pipe(\n op1: OperatorFunction,\n op2: OperatorFunction,\n op3: OperatorFunction,\n op4: OperatorFunction,\n op5: OperatorFunction,\n op6: OperatorFunction,\n op7: OperatorFunction,\n op8: OperatorFunction,\n op9: OperatorFunction\n ): Observable;\n pipe(\n op1: OperatorFunction,\n op2: OperatorFunction,\n op3: OperatorFunction,\n op4: OperatorFunction,\n op5: OperatorFunction,\n op6: OperatorFunction,\n op7: OperatorFunction,\n op8: OperatorFunction,\n op9: OperatorFunction,\n ...operations: OperatorFunction[]\n ): Observable;\n /* tslint:enable:max-line-length */\n\n /**\n * Used to stitch together functional operators into a chain.\n * @method pipe\n * @return {Observable} the Observable result of all of the operators having\n * been called in the order they were passed in.\n *\n * ## Example\n *\n * ```ts\n * import { interval, filter, map, scan } from 'rxjs';\n *\n * interval(1000)\n * .pipe(\n * filter(x => x % 2 === 0),\n * map(x => x + x),\n * scan((acc, x) => acc + x)\n * )\n * .subscribe(x => console.log(x));\n * ```\n */\n pipe(...operations: OperatorFunction[]): Observable {\n return pipeFromArray(operations)(this);\n }\n\n /* tslint:disable:max-line-length */\n /** @deprecated Replaced with {@link firstValueFrom} and {@link lastValueFrom}. Will be removed in v8. Details: https://rxjs.dev/deprecations/to-promise */\n toPromise(): Promise;\n /** @deprecated Replaced with {@link firstValueFrom} and {@link lastValueFrom}. Will be removed in v8. Details: https://rxjs.dev/deprecations/to-promise */\n toPromise(PromiseCtor: typeof Promise): Promise;\n /** @deprecated Replaced with {@link firstValueFrom} and {@link lastValueFrom}. Will be removed in v8. Details: https://rxjs.dev/deprecations/to-promise */\n toPromise(PromiseCtor: PromiseConstructorLike): Promise;\n /* tslint:enable:max-line-length */\n\n /**\n * Subscribe to this Observable and get a Promise resolving on\n * `complete` with the last emission (if any).\n *\n * **WARNING**: Only use this with observables you *know* will complete. If the source\n * observable does not complete, you will end up with a promise that is hung up, and\n * potentially all of the state of an async function hanging out in memory. To avoid\n * this situation, look into adding something like {@link timeout}, {@link take},\n * {@link takeWhile}, or {@link takeUntil} amongst others.\n *\n * @method toPromise\n * @param [promiseCtor] a constructor function used to instantiate\n * the Promise\n * @return A Promise that resolves with the last value emit, or\n * rejects on an error. If there were no emissions, Promise\n * resolves with undefined.\n * @deprecated Replaced with {@link firstValueFrom} and {@link lastValueFrom}. Will be removed in v8. Details: https://rxjs.dev/deprecations/to-promise\n */\n toPromise(promiseCtor?: PromiseConstructorLike): Promise {\n promiseCtor = getPromiseCtor(promiseCtor);\n\n return new promiseCtor((resolve, reject) => {\n let value: T | undefined;\n this.subscribe(\n (x: T) => (value = x),\n (err: any) => reject(err),\n () => resolve(value)\n );\n }) as Promise;\n }\n}\n\n/**\n * Decides between a passed promise constructor from consuming code,\n * A default configured promise constructor, and the native promise\n * constructor and returns it. If nothing can be found, it will throw\n * an error.\n * @param promiseCtor The optional promise constructor to passed by consuming code\n */\nfunction getPromiseCtor(promiseCtor: PromiseConstructorLike | undefined) {\n return promiseCtor ?? config.Promise ?? Promise;\n}\n\nfunction isObserver(value: any): value is Observer {\n return value && isFunction(value.next) && isFunction(value.error) && isFunction(value.complete);\n}\n\nfunction isSubscriber(value: any): value is Subscriber {\n return (value && value instanceof Subscriber) || (isObserver(value) && isSubscription(value));\n}\n", "import { Observable } from '../Observable';\nimport { Subscriber } from '../Subscriber';\nimport { OperatorFunction } from '../types';\nimport { isFunction } from './isFunction';\n\n/**\n * Used to determine if an object is an Observable with a lift function.\n */\nexport function hasLift(source: any): source is { lift: InstanceType['lift'] } {\n return isFunction(source?.lift);\n}\n\n/**\n * Creates an `OperatorFunction`. Used to define operators throughout the library in a concise way.\n * @param init The logic to connect the liftedSource to the subscriber at the moment of subscription.\n */\nexport function operate(\n init: (liftedSource: Observable, subscriber: Subscriber) => (() => void) | void\n): OperatorFunction {\n return (source: Observable) => {\n if (hasLift(source)) {\n return source.lift(function (this: Subscriber, liftedSource: Observable) {\n try {\n return init(liftedSource, this);\n } catch (err) {\n this.error(err);\n }\n });\n }\n throw new TypeError('Unable to lift unknown Observable type');\n };\n}\n", "import { Subscriber } from '../Subscriber';\n\n/**\n * Creates an instance of an `OperatorSubscriber`.\n * @param destination The downstream subscriber.\n * @param onNext Handles next values, only called if this subscriber is not stopped or closed. Any\n * error that occurs in this function is caught and sent to the `error` method of this subscriber.\n * @param onError Handles errors from the subscription, any errors that occur in this handler are caught\n * and send to the `destination` error handler.\n * @param onComplete Handles completion notification from the subscription. Any errors that occur in\n * this handler are sent to the `destination` error handler.\n * @param onFinalize Additional teardown logic here. This will only be called on teardown if the\n * subscriber itself is not already closed. This is called after all other teardown logic is executed.\n */\nexport function createOperatorSubscriber(\n destination: Subscriber,\n onNext?: (value: T) => void,\n onComplete?: () => void,\n onError?: (err: any) => void,\n onFinalize?: () => void\n): Subscriber {\n return new OperatorSubscriber(destination, onNext, onComplete, onError, onFinalize);\n}\n\n/**\n * A generic helper for allowing operators to be created with a Subscriber and\n * use closures to capture necessary state from the operator function itself.\n */\nexport class OperatorSubscriber extends Subscriber {\n /**\n * Creates an instance of an `OperatorSubscriber`.\n * @param destination The downstream subscriber.\n * @param onNext Handles next values, only called if this subscriber is not stopped or closed. Any\n * error that occurs in this function is caught and sent to the `error` method of this subscriber.\n * @param onError Handles errors from the subscription, any errors that occur in this handler are caught\n * and send to the `destination` error handler.\n * @param onComplete Handles completion notification from the subscription. Any errors that occur in\n * this handler are sent to the `destination` error handler.\n * @param onFinalize Additional finalization logic here. This will only be called on finalization if the\n * subscriber itself is not already closed. This is called after all other finalization logic is executed.\n * @param shouldUnsubscribe An optional check to see if an unsubscribe call should truly unsubscribe.\n * NOTE: This currently **ONLY** exists to support the strange behavior of {@link groupBy}, where unsubscription\n * to the resulting observable does not actually disconnect from the source if there are active subscriptions\n * to any grouped observable. (DO NOT EXPOSE OR USE EXTERNALLY!!!)\n */\n constructor(\n destination: Subscriber,\n onNext?: (value: T) => void,\n onComplete?: () => void,\n onError?: (err: any) => void,\n private onFinalize?: () => void,\n private shouldUnsubscribe?: () => boolean\n ) {\n // It's important - for performance reasons - that all of this class's\n // members are initialized and that they are always initialized in the same\n // order. This will ensure that all OperatorSubscriber instances have the\n // same hidden class in V8. This, in turn, will help keep the number of\n // hidden classes involved in property accesses within the base class as\n // low as possible. If the number of hidden classes involved exceeds four,\n // the property accesses will become megamorphic and performance penalties\n // will be incurred - i.e. inline caches won't be used.\n //\n // The reasons for ensuring all instances have the same hidden class are\n // further discussed in this blog post from Benedikt Meurer:\n // https://benediktmeurer.de/2018/03/23/impact-of-polymorphism-on-component-based-frameworks-like-react/\n super(destination);\n this._next = onNext\n ? function (this: OperatorSubscriber, value: T) {\n try {\n onNext(value);\n } catch (err) {\n destination.error(err);\n }\n }\n : super._next;\n this._error = onError\n ? function (this: OperatorSubscriber, err: any) {\n try {\n onError(err);\n } catch (err) {\n // Send any errors that occur down stream.\n destination.error(err);\n } finally {\n // Ensure finalization.\n this.unsubscribe();\n }\n }\n : super._error;\n this._complete = onComplete\n ? function (this: OperatorSubscriber) {\n try {\n onComplete();\n } catch (err) {\n // Send any errors that occur down stream.\n destination.error(err);\n } finally {\n // Ensure finalization.\n this.unsubscribe();\n }\n }\n : super._complete;\n }\n\n unsubscribe() {\n if (!this.shouldUnsubscribe || this.shouldUnsubscribe()) {\n const { closed } = this;\n super.unsubscribe();\n // Execute additional teardown if we have any and we didn't already do so.\n !closed && this.onFinalize?.();\n }\n }\n}\n", "import { Subscription } from '../Subscription';\n\ninterface AnimationFrameProvider {\n schedule(callback: FrameRequestCallback): Subscription;\n requestAnimationFrame: typeof requestAnimationFrame;\n cancelAnimationFrame: typeof cancelAnimationFrame;\n delegate:\n | {\n requestAnimationFrame: typeof requestAnimationFrame;\n cancelAnimationFrame: typeof cancelAnimationFrame;\n }\n | undefined;\n}\n\nexport const animationFrameProvider: AnimationFrameProvider = {\n // When accessing the delegate, use the variable rather than `this` so that\n // the functions can be called without being bound to the provider.\n schedule(callback) {\n let request = requestAnimationFrame;\n let cancel: typeof cancelAnimationFrame | undefined = cancelAnimationFrame;\n const { delegate } = animationFrameProvider;\n if (delegate) {\n request = delegate.requestAnimationFrame;\n cancel = delegate.cancelAnimationFrame;\n }\n const handle = request((timestamp) => {\n // Clear the cancel function. The request has been fulfilled, so\n // attempting to cancel the request upon unsubscription would be\n // pointless.\n cancel = undefined;\n callback(timestamp);\n });\n return new Subscription(() => cancel?.(handle));\n },\n requestAnimationFrame(...args) {\n const { delegate } = animationFrameProvider;\n return (delegate?.requestAnimationFrame || requestAnimationFrame)(...args);\n },\n cancelAnimationFrame(...args) {\n const { delegate } = animationFrameProvider;\n return (delegate?.cancelAnimationFrame || cancelAnimationFrame)(...args);\n },\n delegate: undefined,\n};\n", "import { createErrorClass } from './createErrorClass';\n\nexport interface ObjectUnsubscribedError extends Error {}\n\nexport interface ObjectUnsubscribedErrorCtor {\n /**\n * @deprecated Internal implementation detail. Do not construct error instances.\n * Cannot be tagged as internal: https://github.com/ReactiveX/rxjs/issues/6269\n */\n new (): ObjectUnsubscribedError;\n}\n\n/**\n * An error thrown when an action is invalid because the object has been\n * unsubscribed.\n *\n * @see {@link Subject}\n * @see {@link BehaviorSubject}\n *\n * @class ObjectUnsubscribedError\n */\nexport const ObjectUnsubscribedError: ObjectUnsubscribedErrorCtor = createErrorClass(\n (_super) =>\n function ObjectUnsubscribedErrorImpl(this: any) {\n _super(this);\n this.name = 'ObjectUnsubscribedError';\n this.message = 'object unsubscribed';\n }\n);\n", "import { Operator } from './Operator';\nimport { Observable } from './Observable';\nimport { Subscriber } from './Subscriber';\nimport { Subscription, EMPTY_SUBSCRIPTION } from './Subscription';\nimport { Observer, SubscriptionLike, TeardownLogic } from './types';\nimport { ObjectUnsubscribedError } from './util/ObjectUnsubscribedError';\nimport { arrRemove } from './util/arrRemove';\nimport { errorContext } from './util/errorContext';\n\n/**\n * A Subject is a special type of Observable that allows values to be\n * multicasted to many Observers. Subjects are like EventEmitters.\n *\n * Every Subject is an Observable and an Observer. You can subscribe to a\n * Subject, and you can call next to feed values as well as error and complete.\n */\nexport class Subject extends Observable implements SubscriptionLike {\n closed = false;\n\n private currentObservers: Observer[] | null = null;\n\n /** @deprecated Internal implementation detail, do not use directly. Will be made internal in v8. */\n observers: Observer[] = [];\n /** @deprecated Internal implementation detail, do not use directly. Will be made internal in v8. */\n isStopped = false;\n /** @deprecated Internal implementation detail, do not use directly. Will be made internal in v8. */\n hasError = false;\n /** @deprecated Internal implementation detail, do not use directly. Will be made internal in v8. */\n thrownError: any = null;\n\n /**\n * Creates a \"subject\" by basically gluing an observer to an observable.\n *\n * @nocollapse\n * @deprecated Recommended you do not use. Will be removed at some point in the future. Plans for replacement still under discussion.\n */\n static create: (...args: any[]) => any = (destination: Observer, source: Observable): AnonymousSubject => {\n return new AnonymousSubject(destination, source);\n };\n\n constructor() {\n // NOTE: This must be here to obscure Observable's constructor.\n super();\n }\n\n /** @deprecated Internal implementation detail, do not use directly. Will be made internal in v8. */\n lift(operator: Operator): Observable {\n const subject = new AnonymousSubject(this, this);\n subject.operator = operator as any;\n return subject as any;\n }\n\n /** @internal */\n protected _throwIfClosed() {\n if (this.closed) {\n throw new ObjectUnsubscribedError();\n }\n }\n\n next(value: T) {\n errorContext(() => {\n this._throwIfClosed();\n if (!this.isStopped) {\n if (!this.currentObservers) {\n this.currentObservers = Array.from(this.observers);\n }\n for (const observer of this.currentObservers) {\n observer.next(value);\n }\n }\n });\n }\n\n error(err: any) {\n errorContext(() => {\n this._throwIfClosed();\n if (!this.isStopped) {\n this.hasError = this.isStopped = true;\n this.thrownError = err;\n const { observers } = this;\n while (observers.length) {\n observers.shift()!.error(err);\n }\n }\n });\n }\n\n complete() {\n errorContext(() => {\n this._throwIfClosed();\n if (!this.isStopped) {\n this.isStopped = true;\n const { observers } = this;\n while (observers.length) {\n observers.shift()!.complete();\n }\n }\n });\n }\n\n unsubscribe() {\n this.isStopped = this.closed = true;\n this.observers = this.currentObservers = null!;\n }\n\n get observed() {\n return this.observers?.length > 0;\n }\n\n /** @internal */\n protected _trySubscribe(subscriber: Subscriber): TeardownLogic {\n this._throwIfClosed();\n return super._trySubscribe(subscriber);\n }\n\n /** @internal */\n protected _subscribe(subscriber: Subscriber): Subscription {\n this._throwIfClosed();\n this._checkFinalizedStatuses(subscriber);\n return this._innerSubscribe(subscriber);\n }\n\n /** @internal */\n protected _innerSubscribe(subscriber: Subscriber) {\n const { hasError, isStopped, observers } = this;\n if (hasError || isStopped) {\n return EMPTY_SUBSCRIPTION;\n }\n this.currentObservers = null;\n observers.push(subscriber);\n return new Subscription(() => {\n this.currentObservers = null;\n arrRemove(observers, subscriber);\n });\n }\n\n /** @internal */\n protected _checkFinalizedStatuses(subscriber: Subscriber) {\n const { hasError, thrownError, isStopped } = this;\n if (hasError) {\n subscriber.error(thrownError);\n } else if (isStopped) {\n subscriber.complete();\n }\n }\n\n /**\n * Creates a new Observable with this Subject as the source. You can do this\n * to create custom Observer-side logic of the Subject and conceal it from\n * code that uses the Observable.\n * @return {Observable} Observable that the Subject casts to\n */\n asObservable(): Observable {\n const observable: any = new Observable();\n observable.source = this;\n return observable;\n }\n}\n\n/**\n * @class AnonymousSubject\n */\nexport class AnonymousSubject extends Subject {\n constructor(\n /** @deprecated Internal implementation detail, do not use directly. Will be made internal in v8. */\n public destination?: Observer,\n source?: Observable\n ) {\n super();\n this.source = source;\n }\n\n next(value: T) {\n this.destination?.next?.(value);\n }\n\n error(err: any) {\n this.destination?.error?.(err);\n }\n\n complete() {\n this.destination?.complete?.();\n }\n\n /** @internal */\n protected _subscribe(subscriber: Subscriber): Subscription {\n return this.source?.subscribe(subscriber) ?? EMPTY_SUBSCRIPTION;\n }\n}\n", "import { TimestampProvider } from '../types';\n\ninterface DateTimestampProvider extends TimestampProvider {\n delegate: TimestampProvider | undefined;\n}\n\nexport const dateTimestampProvider: DateTimestampProvider = {\n now() {\n // Use the variable rather than `this` so that the function can be called\n // without being bound to the provider.\n return (dateTimestampProvider.delegate || Date).now();\n },\n delegate: undefined,\n};\n", "import { Subject } from './Subject';\nimport { TimestampProvider } from './types';\nimport { Subscriber } from './Subscriber';\nimport { Subscription } from './Subscription';\nimport { dateTimestampProvider } from './scheduler/dateTimestampProvider';\n\n/**\n * A variant of {@link Subject} that \"replays\" old values to new subscribers by emitting them when they first subscribe.\n *\n * `ReplaySubject` has an internal buffer that will store a specified number of values that it has observed. Like `Subject`,\n * `ReplaySubject` \"observes\" values by having them passed to its `next` method. When it observes a value, it will store that\n * value for a time determined by the configuration of the `ReplaySubject`, as passed to its constructor.\n *\n * When a new subscriber subscribes to the `ReplaySubject` instance, it will synchronously emit all values in its buffer in\n * a First-In-First-Out (FIFO) manner. The `ReplaySubject` will also complete, if it has observed completion; and it will\n * error if it has observed an error.\n *\n * There are two main configuration items to be concerned with:\n *\n * 1. `bufferSize` - This will determine how many items are stored in the buffer, defaults to infinite.\n * 2. `windowTime` - The amount of time to hold a value in the buffer before removing it from the buffer.\n *\n * Both configurations may exist simultaneously. So if you would like to buffer a maximum of 3 values, as long as the values\n * are less than 2 seconds old, you could do so with a `new ReplaySubject(3, 2000)`.\n *\n * ### Differences with BehaviorSubject\n *\n * `BehaviorSubject` is similar to `new ReplaySubject(1)`, with a couple of exceptions:\n *\n * 1. `BehaviorSubject` comes \"primed\" with a single value upon construction.\n * 2. `ReplaySubject` will replay values, even after observing an error, where `BehaviorSubject` will not.\n *\n * @see {@link Subject}\n * @see {@link BehaviorSubject}\n * @see {@link shareReplay}\n */\nexport class ReplaySubject extends Subject {\n private _buffer: (T | number)[] = [];\n private _infiniteTimeWindow = true;\n\n /**\n * @param bufferSize The size of the buffer to replay on subscription\n * @param windowTime The amount of time the buffered items will stay buffered\n * @param timestampProvider An object with a `now()` method that provides the current timestamp. This is used to\n * calculate the amount of time something has been buffered.\n */\n constructor(\n private _bufferSize = Infinity,\n private _windowTime = Infinity,\n private _timestampProvider: TimestampProvider = dateTimestampProvider\n ) {\n super();\n this._infiniteTimeWindow = _windowTime === Infinity;\n this._bufferSize = Math.max(1, _bufferSize);\n this._windowTime = Math.max(1, _windowTime);\n }\n\n next(value: T): void {\n const { isStopped, _buffer, _infiniteTimeWindow, _timestampProvider, _windowTime } = this;\n if (!isStopped) {\n _buffer.push(value);\n !_infiniteTimeWindow && _buffer.push(_timestampProvider.now() + _windowTime);\n }\n this._trimBuffer();\n super.next(value);\n }\n\n /** @internal */\n protected _subscribe(subscriber: Subscriber): Subscription {\n this._throwIfClosed();\n this._trimBuffer();\n\n const subscription = this._innerSubscribe(subscriber);\n\n const { _infiniteTimeWindow, _buffer } = this;\n // We use a copy here, so reentrant code does not mutate our array while we're\n // emitting it to a new subscriber.\n const copy = _buffer.slice();\n for (let i = 0; i < copy.length && !subscriber.closed; i += _infiniteTimeWindow ? 1 : 2) {\n subscriber.next(copy[i] as T);\n }\n\n this._checkFinalizedStatuses(subscriber);\n\n return subscription;\n }\n\n private _trimBuffer() {\n const { _bufferSize, _timestampProvider, _buffer, _infiniteTimeWindow } = this;\n // If we don't have an infinite buffer size, and we're over the length,\n // use splice to truncate the old buffer values off. Note that we have to\n // double the size for instances where we're not using an infinite time window\n // because we're storing the values and the timestamps in the same array.\n const adjustedBufferSize = (_infiniteTimeWindow ? 1 : 2) * _bufferSize;\n _bufferSize < Infinity && adjustedBufferSize < _buffer.length && _buffer.splice(0, _buffer.length - adjustedBufferSize);\n\n // Now, if we're not in an infinite time window, remove all values where the time is\n // older than what is allowed.\n if (!_infiniteTimeWindow) {\n const now = _timestampProvider.now();\n let last = 0;\n // Search the array for the first timestamp that isn't expired and\n // truncate the buffer up to that point.\n for (let i = 1; i < _buffer.length && (_buffer[i] as number) <= now; i += 2) {\n last = i;\n }\n last && _buffer.splice(0, last + 1);\n }\n }\n}\n", "import { Scheduler } from '../Scheduler';\nimport { Subscription } from '../Subscription';\nimport { SchedulerAction } from '../types';\n\n/**\n * A unit of work to be executed in a `scheduler`. An action is typically\n * created from within a {@link SchedulerLike} and an RxJS user does not need to concern\n * themselves about creating and manipulating an Action.\n *\n * ```ts\n * class Action extends Subscription {\n * new (scheduler: Scheduler, work: (state?: T) => void);\n * schedule(state?: T, delay: number = 0): Subscription;\n * }\n * ```\n *\n * @class Action\n */\nexport class Action extends Subscription {\n constructor(scheduler: Scheduler, work: (this: SchedulerAction, state?: T) => void) {\n super();\n }\n /**\n * Schedules this action on its parent {@link SchedulerLike} for execution. May be passed\n * some context object, `state`. May happen at some point in the future,\n * according to the `delay` parameter, if specified.\n * @param {T} [state] Some contextual data that the `work` function uses when\n * called by the Scheduler.\n * @param {number} [delay] Time to wait before executing the work, where the\n * time unit is implicit and defined by the Scheduler.\n * @return {void}\n */\n public schedule(state?: T, delay: number = 0): Subscription {\n return this;\n }\n}\n", "import type { TimerHandle } from './timerHandle';\ntype SetIntervalFunction = (handler: () => void, timeout?: number, ...args: any[]) => TimerHandle;\ntype ClearIntervalFunction = (handle: TimerHandle) => void;\n\ninterface IntervalProvider {\n setInterval: SetIntervalFunction;\n clearInterval: ClearIntervalFunction;\n delegate:\n | {\n setInterval: SetIntervalFunction;\n clearInterval: ClearIntervalFunction;\n }\n | undefined;\n}\n\nexport const intervalProvider: IntervalProvider = {\n // When accessing the delegate, use the variable rather than `this` so that\n // the functions can be called without being bound to the provider.\n setInterval(handler: () => void, timeout?: number, ...args) {\n const { delegate } = intervalProvider;\n if (delegate?.setInterval) {\n return delegate.setInterval(handler, timeout, ...args);\n }\n return setInterval(handler, timeout, ...args);\n },\n clearInterval(handle) {\n const { delegate } = intervalProvider;\n return (delegate?.clearInterval || clearInterval)(handle as any);\n },\n delegate: undefined,\n};\n", "import { Action } from './Action';\nimport { SchedulerAction } from '../types';\nimport { Subscription } from '../Subscription';\nimport { AsyncScheduler } from './AsyncScheduler';\nimport { intervalProvider } from './intervalProvider';\nimport { arrRemove } from '../util/arrRemove';\nimport { TimerHandle } from './timerHandle';\n\nexport class AsyncAction extends Action {\n public id: TimerHandle | undefined;\n public state?: T;\n // @ts-ignore: Property has no initializer and is not definitely assigned\n public delay: number;\n protected pending: boolean = false;\n\n constructor(protected scheduler: AsyncScheduler, protected work: (this: SchedulerAction, state?: T) => void) {\n super(scheduler, work);\n }\n\n public schedule(state?: T, delay: number = 0): Subscription {\n if (this.closed) {\n return this;\n }\n\n // Always replace the current state with the new state.\n this.state = state;\n\n const id = this.id;\n const scheduler = this.scheduler;\n\n //\n // Important implementation note:\n //\n // Actions only execute once by default, unless rescheduled from within the\n // scheduled callback. This allows us to implement single and repeat\n // actions via the same code path, without adding API surface area, as well\n // as mimic traditional recursion but across asynchronous boundaries.\n //\n // However, JS runtimes and timers distinguish between intervals achieved by\n // serial `setTimeout` calls vs. a single `setInterval` call. An interval of\n // serial `setTimeout` calls can be individually delayed, which delays\n // scheduling the next `setTimeout`, and so on. `setInterval` attempts to\n // guarantee the interval callback will be invoked more precisely to the\n // interval period, regardless of load.\n //\n // Therefore, we use `setInterval` to schedule single and repeat actions.\n // If the action reschedules itself with the same delay, the interval is not\n // canceled. If the action doesn't reschedule, or reschedules with a\n // different delay, the interval will be canceled after scheduled callback\n // execution.\n //\n if (id != null) {\n this.id = this.recycleAsyncId(scheduler, id, delay);\n }\n\n // Set the pending flag indicating that this action has been scheduled, or\n // has recursively rescheduled itself.\n this.pending = true;\n\n this.delay = delay;\n // If this action has already an async Id, don't request a new one.\n this.id = this.id ?? this.requestAsyncId(scheduler, this.id, delay);\n\n return this;\n }\n\n protected requestAsyncId(scheduler: AsyncScheduler, _id?: TimerHandle, delay: number = 0): TimerHandle {\n return intervalProvider.setInterval(scheduler.flush.bind(scheduler, this), delay);\n }\n\n protected recycleAsyncId(_scheduler: AsyncScheduler, id?: TimerHandle, delay: number | null = 0): TimerHandle | undefined {\n // If this action is rescheduled with the same delay time, don't clear the interval id.\n if (delay != null && this.delay === delay && this.pending === false) {\n return id;\n }\n // Otherwise, if the action's delay time is different from the current delay,\n // or the action has been rescheduled before it's executed, clear the interval id\n if (id != null) {\n intervalProvider.clearInterval(id);\n }\n\n return undefined;\n }\n\n /**\n * Immediately executes this action and the `work` it contains.\n * @return {any}\n */\n public execute(state: T, delay: number): any {\n if (this.closed) {\n return new Error('executing a cancelled action');\n }\n\n this.pending = false;\n const error = this._execute(state, delay);\n if (error) {\n return error;\n } else if (this.pending === false && this.id != null) {\n // Dequeue if the action didn't reschedule itself. Don't call\n // unsubscribe(), because the action could reschedule later.\n // For example:\n // ```\n // scheduler.schedule(function doWork(counter) {\n // /* ... I'm a busy worker bee ... */\n // var originalAction = this;\n // /* wait 100ms before rescheduling the action */\n // setTimeout(function () {\n // originalAction.schedule(counter + 1);\n // }, 100);\n // }, 1000);\n // ```\n this.id = this.recycleAsyncId(this.scheduler, this.id, null);\n }\n }\n\n protected _execute(state: T, _delay: number): any {\n let errored: boolean = false;\n let errorValue: any;\n try {\n this.work(state);\n } catch (e) {\n errored = true;\n // HACK: Since code elsewhere is relying on the \"truthiness\" of the\n // return here, we can't have it return \"\" or 0 or false.\n // TODO: Clean this up when we refactor schedulers mid-version-8 or so.\n errorValue = e ? e : new Error('Scheduled action threw falsy error');\n }\n if (errored) {\n this.unsubscribe();\n return errorValue;\n }\n }\n\n unsubscribe() {\n if (!this.closed) {\n const { id, scheduler } = this;\n const { actions } = scheduler;\n\n this.work = this.state = this.scheduler = null!;\n this.pending = false;\n\n arrRemove(actions, this);\n if (id != null) {\n this.id = this.recycleAsyncId(scheduler, id, null);\n }\n\n this.delay = null!;\n super.unsubscribe();\n }\n }\n}\n", "import { Action } from './scheduler/Action';\nimport { Subscription } from './Subscription';\nimport { SchedulerLike, SchedulerAction } from './types';\nimport { dateTimestampProvider } from './scheduler/dateTimestampProvider';\n\n/**\n * An execution context and a data structure to order tasks and schedule their\n * execution. Provides a notion of (potentially virtual) time, through the\n * `now()` getter method.\n *\n * Each unit of work in a Scheduler is called an `Action`.\n *\n * ```ts\n * class Scheduler {\n * now(): number;\n * schedule(work, delay?, state?): Subscription;\n * }\n * ```\n *\n * @class Scheduler\n * @deprecated Scheduler is an internal implementation detail of RxJS, and\n * should not be used directly. Rather, create your own class and implement\n * {@link SchedulerLike}. Will be made internal in v8.\n */\nexport class Scheduler implements SchedulerLike {\n public static now: () => number = dateTimestampProvider.now;\n\n constructor(private schedulerActionCtor: typeof Action, now: () => number = Scheduler.now) {\n this.now = now;\n }\n\n /**\n * A getter method that returns a number representing the current time\n * (at the time this function was called) according to the scheduler's own\n * internal clock.\n * @return {number} A number that represents the current time. May or may not\n * have a relation to wall-clock time. May or may not refer to a time unit\n * (e.g. milliseconds).\n */\n public now: () => number;\n\n /**\n * Schedules a function, `work`, for execution. May happen at some point in\n * the future, according to the `delay` parameter, if specified. May be passed\n * some context object, `state`, which will be passed to the `work` function.\n *\n * The given arguments will be processed an stored as an Action object in a\n * queue of actions.\n *\n * @param {function(state: ?T): ?Subscription} work A function representing a\n * task, or some unit of work to be executed by the Scheduler.\n * @param {number} [delay] Time to wait before executing the work, where the\n * time unit is implicit and defined by the Scheduler itself.\n * @param {T} [state] Some contextual data that the `work` function uses when\n * called by the Scheduler.\n * @return {Subscription} A subscription in order to be able to unsubscribe\n * the scheduled work.\n */\n public schedule(work: (this: SchedulerAction, state?: T) => void, delay: number = 0, state?: T): Subscription {\n return new this.schedulerActionCtor(this, work).schedule(state, delay);\n }\n}\n", "import { Scheduler } from '../Scheduler';\nimport { Action } from './Action';\nimport { AsyncAction } from './AsyncAction';\nimport { TimerHandle } from './timerHandle';\n\nexport class AsyncScheduler extends Scheduler {\n public actions: Array> = [];\n /**\n * A flag to indicate whether the Scheduler is currently executing a batch of\n * queued actions.\n * @type {boolean}\n * @internal\n */\n public _active: boolean = false;\n /**\n * An internal ID used to track the latest asynchronous task such as those\n * coming from `setTimeout`, `setInterval`, `requestAnimationFrame`, and\n * others.\n * @type {any}\n * @internal\n */\n public _scheduled: TimerHandle | undefined;\n\n constructor(SchedulerAction: typeof Action, now: () => number = Scheduler.now) {\n super(SchedulerAction, now);\n }\n\n public flush(action: AsyncAction): void {\n const { actions } = this;\n\n if (this._active) {\n actions.push(action);\n return;\n }\n\n let error: any;\n this._active = true;\n\n do {\n if ((error = action.execute(action.state, action.delay))) {\n break;\n }\n } while ((action = actions.shift()!)); // exhaust the scheduler queue\n\n this._active = false;\n\n if (error) {\n while ((action = actions.shift()!)) {\n action.unsubscribe();\n }\n throw error;\n }\n }\n}\n", "import { AsyncAction } from './AsyncAction';\nimport { AsyncScheduler } from './AsyncScheduler';\n\n/**\n *\n * Async Scheduler\n *\n * Schedule task as if you used setTimeout(task, duration)\n *\n * `async` scheduler schedules tasks asynchronously, by putting them on the JavaScript\n * event loop queue. It is best used to delay tasks in time or to schedule tasks repeating\n * in intervals.\n *\n * If you just want to \"defer\" task, that is to perform it right after currently\n * executing synchronous code ends (commonly achieved by `setTimeout(deferredTask, 0)`),\n * better choice will be the {@link asapScheduler} scheduler.\n *\n * ## Examples\n * Use async scheduler to delay task\n * ```ts\n * import { asyncScheduler } from 'rxjs';\n *\n * const task = () => console.log('it works!');\n *\n * asyncScheduler.schedule(task, 2000);\n *\n * // After 2 seconds logs:\n * // \"it works!\"\n * ```\n *\n * Use async scheduler to repeat task in intervals\n * ```ts\n * import { asyncScheduler } from 'rxjs';\n *\n * function task(state) {\n * console.log(state);\n * this.schedule(state + 1, 1000); // `this` references currently executing Action,\n * // which we reschedule with new state and delay\n * }\n *\n * asyncScheduler.schedule(task, 3000, 0);\n *\n * // Logs:\n * // 0 after 3s\n * // 1 after 4s\n * // 2 after 5s\n * // 3 after 6s\n * ```\n */\n\nexport const asyncScheduler = new AsyncScheduler(AsyncAction);\n\n/**\n * @deprecated Renamed to {@link asyncScheduler}. Will be removed in v8.\n */\nexport const async = asyncScheduler;\n", "import { AsyncAction } from './AsyncAction';\nimport { AnimationFrameScheduler } from './AnimationFrameScheduler';\nimport { SchedulerAction } from '../types';\nimport { animationFrameProvider } from './animationFrameProvider';\nimport { TimerHandle } from './timerHandle';\n\nexport class AnimationFrameAction extends AsyncAction {\n constructor(protected scheduler: AnimationFrameScheduler, protected work: (this: SchedulerAction, state?: T) => void) {\n super(scheduler, work);\n }\n\n protected requestAsyncId(scheduler: AnimationFrameScheduler, id?: TimerHandle, delay: number = 0): TimerHandle {\n // If delay is greater than 0, request as an async action.\n if (delay !== null && delay > 0) {\n return super.requestAsyncId(scheduler, id, delay);\n }\n // Push the action to the end of the scheduler queue.\n scheduler.actions.push(this);\n // If an animation frame has already been requested, don't request another\n // one. If an animation frame hasn't been requested yet, request one. Return\n // the current animation frame request id.\n return scheduler._scheduled || (scheduler._scheduled = animationFrameProvider.requestAnimationFrame(() => scheduler.flush(undefined)));\n }\n\n protected recycleAsyncId(scheduler: AnimationFrameScheduler, id?: TimerHandle, delay: number = 0): TimerHandle | undefined {\n // If delay exists and is greater than 0, or if the delay is null (the\n // action wasn't rescheduled) but was originally scheduled as an async\n // action, then recycle as an async action.\n if (delay != null ? delay > 0 : this.delay > 0) {\n return super.recycleAsyncId(scheduler, id, delay);\n }\n // If the scheduler queue has no remaining actions with the same async id,\n // cancel the requested animation frame and set the scheduled flag to\n // undefined so the next AnimationFrameAction will request its own.\n const { actions } = scheduler;\n if (id != null && actions[actions.length - 1]?.id !== id) {\n animationFrameProvider.cancelAnimationFrame(id as number);\n scheduler._scheduled = undefined;\n }\n // Return undefined so the action knows to request a new async id if it's rescheduled.\n return undefined;\n }\n}\n", "import { AsyncAction } from './AsyncAction';\nimport { AsyncScheduler } from './AsyncScheduler';\n\nexport class AnimationFrameScheduler extends AsyncScheduler {\n public flush(action?: AsyncAction): void {\n this._active = true;\n // The async id that effects a call to flush is stored in _scheduled.\n // Before executing an action, it's necessary to check the action's async\n // id to determine whether it's supposed to be executed in the current\n // flush.\n // Previous implementations of this method used a count to determine this,\n // but that was unsound, as actions that are unsubscribed - i.e. cancelled -\n // are removed from the actions array and that can shift actions that are\n // scheduled to be executed in a subsequent flush into positions at which\n // they are executed within the current flush.\n const flushId = this._scheduled;\n this._scheduled = undefined;\n\n const { actions } = this;\n let error: any;\n action = action || actions.shift()!;\n\n do {\n if ((error = action.execute(action.state, action.delay))) {\n break;\n }\n } while ((action = actions[0]) && action.id === flushId && actions.shift());\n\n this._active = false;\n\n if (error) {\n while ((action = actions[0]) && action.id === flushId && actions.shift()) {\n action.unsubscribe();\n }\n throw error;\n }\n }\n}\n", "import { AnimationFrameAction } from './AnimationFrameAction';\nimport { AnimationFrameScheduler } from './AnimationFrameScheduler';\n\n/**\n *\n * Animation Frame Scheduler\n *\n * Perform task when `window.requestAnimationFrame` would fire\n *\n * When `animationFrame` scheduler is used with delay, it will fall back to {@link asyncScheduler} scheduler\n * behaviour.\n *\n * Without delay, `animationFrame` scheduler can be used to create smooth browser animations.\n * It makes sure scheduled task will happen just before next browser content repaint,\n * thus performing animations as efficiently as possible.\n *\n * ## Example\n * Schedule div height animation\n * ```ts\n * // html:
\n * import { animationFrameScheduler } from 'rxjs';\n *\n * const div = document.querySelector('div');\n *\n * animationFrameScheduler.schedule(function(height) {\n * div.style.height = height + \"px\";\n *\n * this.schedule(height + 1); // `this` references currently executing Action,\n * // which we reschedule with new state\n * }, 0, 0);\n *\n * // You will see a div element growing in height\n * ```\n */\n\nexport const animationFrameScheduler = new AnimationFrameScheduler(AnimationFrameAction);\n\n/**\n * @deprecated Renamed to {@link animationFrameScheduler}. Will be removed in v8.\n */\nexport const animationFrame = animationFrameScheduler;\n", "import { Observable } from '../Observable';\nimport { SchedulerLike } from '../types';\n\n/**\n * A simple Observable that emits no items to the Observer and immediately\n * emits a complete notification.\n *\n * Just emits 'complete', and nothing else.\n *\n * ![](empty.png)\n *\n * A simple Observable that only emits the complete notification. It can be used\n * for composing with other Observables, such as in a {@link mergeMap}.\n *\n * ## Examples\n *\n * Log complete notification\n *\n * ```ts\n * import { EMPTY } from 'rxjs';\n *\n * EMPTY.subscribe({\n * next: () => console.log('Next'),\n * complete: () => console.log('Complete!')\n * });\n *\n * // Outputs\n * // Complete!\n * ```\n *\n * Emit the number 7, then complete\n *\n * ```ts\n * import { EMPTY, startWith } from 'rxjs';\n *\n * const result = EMPTY.pipe(startWith(7));\n * result.subscribe(x => console.log(x));\n *\n * // Outputs\n * // 7\n * ```\n *\n * Map and flatten only odd numbers to the sequence `'a'`, `'b'`, `'c'`\n *\n * ```ts\n * import { interval, mergeMap, of, EMPTY } from 'rxjs';\n *\n * const interval$ = interval(1000);\n * const result = interval$.pipe(\n * mergeMap(x => x % 2 === 1 ? of('a', 'b', 'c') : EMPTY),\n * );\n * result.subscribe(x => console.log(x));\n *\n * // Results in the following to the console:\n * // x is equal to the count on the interval, e.g. (0, 1, 2, 3, ...)\n * // x will occur every 1000ms\n * // if x % 2 is equal to 1, print a, b, c (each on its own)\n * // if x % 2 is not equal to 1, nothing will be output\n * ```\n *\n * @see {@link Observable}\n * @see {@link NEVER}\n * @see {@link of}\n * @see {@link throwError}\n */\nexport const EMPTY = new Observable((subscriber) => subscriber.complete());\n\n/**\n * @param scheduler A {@link SchedulerLike} to use for scheduling\n * the emission of the complete notification.\n * @deprecated Replaced with the {@link EMPTY} constant or {@link scheduled} (e.g. `scheduled([], scheduler)`). Will be removed in v8.\n */\nexport function empty(scheduler?: SchedulerLike) {\n return scheduler ? emptyScheduled(scheduler) : EMPTY;\n}\n\nfunction emptyScheduled(scheduler: SchedulerLike) {\n return new Observable((subscriber) => scheduler.schedule(() => subscriber.complete()));\n}\n", "import { SchedulerLike } from '../types';\nimport { isFunction } from './isFunction';\n\nexport function isScheduler(value: any): value is SchedulerLike {\n return value && isFunction(value.schedule);\n}\n", "import { SchedulerLike } from '../types';\nimport { isFunction } from './isFunction';\nimport { isScheduler } from './isScheduler';\n\nfunction last(arr: T[]): T | undefined {\n return arr[arr.length - 1];\n}\n\nexport function popResultSelector(args: any[]): ((...args: unknown[]) => unknown) | undefined {\n return isFunction(last(args)) ? args.pop() : undefined;\n}\n\nexport function popScheduler(args: any[]): SchedulerLike | undefined {\n return isScheduler(last(args)) ? args.pop() : undefined;\n}\n\nexport function popNumber(args: any[], defaultValue: number): number {\n return typeof last(args) === 'number' ? args.pop()! : defaultValue;\n}\n", "export const isArrayLike = ((x: any): x is ArrayLike => x && typeof x.length === 'number' && typeof x !== 'function');", "import { isFunction } from \"./isFunction\";\n\n/**\n * Tests to see if the object is \"thennable\".\n * @param value the object to test\n */\nexport function isPromise(value: any): value is PromiseLike {\n return isFunction(value?.then);\n}\n", "import { InteropObservable } from '../types';\nimport { observable as Symbol_observable } from '../symbol/observable';\nimport { isFunction } from './isFunction';\n\n/** Identifies an input as being Observable (but not necessary an Rx Observable) */\nexport function isInteropObservable(input: any): input is InteropObservable {\n return isFunction(input[Symbol_observable]);\n}\n", "import { isFunction } from './isFunction';\n\nexport function isAsyncIterable(obj: any): obj is AsyncIterable {\n return Symbol.asyncIterator && isFunction(obj?.[Symbol.asyncIterator]);\n}\n", "/**\n * Creates the TypeError to throw if an invalid object is passed to `from` or `scheduled`.\n * @param input The object that was passed.\n */\nexport function createInvalidObservableTypeError(input: any) {\n // TODO: We should create error codes that can be looked up, so this can be less verbose.\n return new TypeError(\n `You provided ${\n input !== null && typeof input === 'object' ? 'an invalid object' : `'${input}'`\n } where a stream was expected. You can provide an Observable, Promise, ReadableStream, Array, AsyncIterable, or Iterable.`\n );\n}\n", "export function getSymbolIterator(): symbol {\n if (typeof Symbol !== 'function' || !Symbol.iterator) {\n return '@@iterator' as any;\n }\n\n return Symbol.iterator;\n}\n\nexport const iterator = getSymbolIterator();\n", "import { iterator as Symbol_iterator } from '../symbol/iterator';\nimport { isFunction } from './isFunction';\n\n/** Identifies an input as being an Iterable */\nexport function isIterable(input: any): input is Iterable {\n return isFunction(input?.[Symbol_iterator]);\n}\n", "import { ReadableStreamLike } from '../types';\nimport { isFunction } from './isFunction';\n\nexport async function* readableStreamLikeToAsyncGenerator(readableStream: ReadableStreamLike): AsyncGenerator {\n const reader = readableStream.getReader();\n try {\n while (true) {\n const { value, done } = await reader.read();\n if (done) {\n return;\n }\n yield value!;\n }\n } finally {\n reader.releaseLock();\n }\n}\n\nexport function isReadableStreamLike(obj: any): obj is ReadableStreamLike {\n // We don't want to use instanceof checks because they would return\n // false for instances from another Realm, like an