Policy#

Ресурс Policy позволяет настраивать такие функции, как контроль доступа и ограничение скорости; их можно добавить к вашим ресурсам VirtualServer и VirtualServerRoute.

Он реализован как пользовательский ресурс.

Это справочная документация по ресурсу Policy.

Предварительные требования#

Политики работают совместно с ресурсами VirtualServer и VirtualServerRoute, которые необходимо создавать отдельно.

Спецификация Policy#

Ниже приведен пример политики, которая разрешает доступ клиентам из подсети 10.0.0.0/8 и запрещает доступ любым другим:

apiVersion: k8s.angie.software/v1
kind: Policy
metadata:
  name: allow-localhost
spec:
  accessControl:
    allow:
    - 10.0.0.0/8

Поле

Описание

Тип

Обязательно

AccessControl

Политика контроля доступа, основанная на IP-адресе клиента.

AccessControl

Нет

ingressClassName

Указывает, какой экземпляр ANIC должен обрабатывать ресурс Policy.

string

Нет

rateLimit

Политика ограничения скорости управляет скоростью обработки запросов по определенному ключу.

ref:rateLimit

Нет

basicAuth

Политика базовой аутентификации настраивает в Angie аутентификацию клиентских запросов с использованием базовой аутентификации HTTP по учетным данным.

BasicAuth

Нет

ingressMTLS

Политика IngressMTLS настраивает проверку сертификата клиента.

IngressMTLS

Нет

egressMTLS

Политика EgressMTLS настраивает аутентификацию и проверку сертификата апстрима.

EgressMTLS

Нет

Примечание

Политика должна включать в себя ровно одно значение.

AccessControl#

Политика контроля доступа настраивает в Angie отклонение или принятие запросов от клиентов с указанными IP-адресами и подсетями.

Например, следующая политика разрешает доступ клиентам из подсети 10.0.0.0/8 и запрещает доступ любым другим:

accessControl:
  allow:
  - 10.0.0.0/8

Напротив, приведенная ниже политика делает обратное: запрещает доступ клиентам с 10.0.0.0/8 и разрешает доступ любым другим клиентам:

accessControl:
  deny:
  - 10.0.0.0/8

Примечание

Функция реализована с использованием модуля Angie http_access. Политика контроля доступа ANIC поддерживает либо разрешающие, либо запрещающие правила, но не оба вида сразу (в отличие от модуля).

Поле

Описание

Тип

Обязательно

allow

Разрешает доступ для указанных сетей или адресов. Например, 192.168.1.1 или 10.1.1.0/16.

[]string

Нет

deny

Запрещает доступ для указанных сетей или адресов. Например, 192.168.1.1 или 10.1.1.0/16.

[]string

Нет

AccessControl должен включать либо allow, либо deny.

Поведение слияния AccessControl#

Ресурс VirtualServer или VirtualServerRoute может ссылаться на несколько политик контроля доступа. Например, здесь мы ссылаемся на две политики, в каждой из которых настроен список разрешений:

policies:
  - name: allow-policy-one
  - name: allow-policy-two

Когда вы ссылаетесь на несколько политик контроля доступа, ANIC объединит их содержимое в один список разрешений или запретов.

Ссылки как на разрешающие, так и на запрещающие политики, как показано в примере ниже, не поддерживаются. Если указаны ссылки как на разрешающие, так и на запрещающие списки, ANIC использует только политики разрешающих списков.

policies:
  - name: deny-policy
  - name: allow-policy-one
  - name: allow-policy-two

RateLimit#

Политика ограничения скорости настраивает в Angie ограничение скорости обработки запросов.

Например, следующая политика ограничит все последующие запросы, поступающие с одного IP-адреса, при превышении скорости в 10 запросов в секунду:

rateLimit:
  rate: 10r/s
  zoneSize: 10M
  key: ${binary_remote_addr}

Примечание

Функция реализована с использованием модуля Angie http_limit_req_module.

Поле

Описание

Тип

Обязательно

rate

Допустимая скорость запросов. Скорость указывается в запросах в секунду (r/s) или запросах в минуту (r/m).

string

Да

key

Ключ, к которому применяется ограничение скорости. Может содержать текст, переменные или их комбинацию. Переменные должны заключены в ${}. Например: ${binary_remote_addr}. Допустимые переменные: $binary_remote_addr, $request_uri, $url, $http_, $args, $arg_, $cookie_.

string

Да

zoneSize

Размер зоны разделяемой памяти. Допускаются только положительные значения. Допустимые суффиксы - k или m; если суффикс не задан, предполагается k.

string

Да

delay

Указывает предел, при достижении которого избыточные запросы становятся отложенными. Если этот параметр не задан, задерживаются все избыточные запросы.

int

Нет

noDelay

Отключает задержку избыточных запросов при ограничении количества запросов. Имеет приоритет над delay, если заданы оба параметра.

bool

Нет

burst

Избыточные запросы задерживаются до тех пор, пока их количество не превысит размер burst, после чего запрос завершается с ошибкой.

int

Нет

dryRun

Включает режим сухого прогона. В этом режиме ограничение скорости фактически не применяется, но количество избыточных запросов учитывается, как обычно, в зоне разделяемой памяти.

bool

Нет

logLevel

Устанавливает желаемый уровень ведения журнала для случаев, когда сервер отказывается обрабатывать запросы из-за превышения скорости или задерживает обработку запросов. Допустимые значения: info, notice, warn или error. Значение по умолчанию - error.

string

Нет

rejectCode

Задает код состояния, возвращаемый в ответ на отклоненные запросы. Значение должно попадать в диапазон 400..599. Значение по умолчанию - 503.

int

Нет

Для каждой политики, на которую ссылается VirtualServer или его VirtualServerRoute, ANIC сгенерирует единую зону ограничения скорости, определенную директивой http_limit_req. Если два ресурса VirtualServer ссылаются на одну и ту же политику, ANIC сгенерирует две разные зоны ограничения скорости, по одной на каждый VirtualServer.

Поведение слияния RateLimit#

Ресурс VirtualServer или VirtualServerRoute может ссылаться на несколько политик ограничения скорости. Например, здесь мы ссылаемся на две политики:

policies:
  - name: rate-limit-policy-one
  - name: rate-limit-policy-two

Когда вы ссылаетесь на несколько политик ограничения скорости, ANIC настроит в Angie использование всех указанных ограничений скорости. Если определено несколько политик, каждая дополнительная политика наследует параметры dryRun, LogLevel и rejectCode из первой политики, на которую идет ссылка (rate-limit-policy-one в примере выше).

BasicAuth#

Настраивает в Angie аутентификацию клиентских запросов при помощи базовой схемы аутентификации HTTP.

Например, следующая политика будет отклонять все запросы, которые не содержат действительную комбинацию имени пользователя и пароля в заголовке HTTP Authentication

basicAuth:
  secret: htpasswd-secret
  realm: "My API"

Примечание

Функция реализована с использованием модуля Angie http_auth_basic.

Поле

Описание

Тип

Обязательно

secret

Имя секрета Kubernetes, в котором хранится конфигурация Htpasswd. Он должен находиться в том же пространстве имен, что и ресурс Policy. Секрет должен иметь тип angie.software/htpasswd, а конфигурация должна храниться в секрете по ключу htpasswd; в противном случае секрет будет отклонен как недействительный.

string

Да

realm

Область для базовой аутентификации.

string

Нет

Поведение слияния BasicAuth#

Ресурс VirtualServer или VirtualServerRoute может ссылаться на несколько политик базовой аутентификации. При этом будет применяться только одна из них. Все последующие ссылки будут проигнорированы. Например, здесь мы ссылаемся на две политики:

policies:
  - name: basic-auth-policy-one
  - name: basic-auth-policy-two

В этом примере ANIC будет использовать конфигурацию из первой ссылки на политику «basic-auth-policy-one» и игнорирует «basic-auth-policy-two».

IngressMTLS#

Политика IngressMTLS настраивает проверку сертификата клиента.

Например, следующая политика будет проверять сертификат клиента, используя сертификат Центра Сертификации, указанный в ingress-mtls-secret:

ingressMTLS:
  clientCertSecret: ingress-mtls-secret
  verifyClient: "on"
  verifyDepth: 1

Ниже приведен пример ingress-mtls-secret типа angie.software/ca

kind: Secret
metadata:
  name: ingress-mtls-secret
apiVersion: v1
type: angie.software/ca
data:
  ca.crt: <base64encoded-certificate>

У ресурса VirtualServer, который ссылается на политику IngressMTLS, должно быть следующие настройки:

Если эти условия нарушены, Angie будет отправлять клиентам код состояния 500.

Вы можете передавать сведения о сертификате клиента, включая сам сертификат, серверам апстрима. Например:

action:
  proxy:
    upstream: webapp
    requestHeaders:
      set:
        - name: client-cert-subj-dn
          value: ${ssl_client_s_dn} # subject DN
        - name: client-cert
          value: ${ssl_client_escaped_cert} # клиентский сертификат в формате PEM (urlencoded)

Мы используем параметр requestHeaders в Action.Proxy для задания значений двух заголовков, которые Angie будет передавать серверам апстрима. См. список встроенных переменных, поддерживаемых модулем http_ssl, которые вы можете использовать для передачи сведений о сертификате клиента.

Примечание

Функция реализована с использованием модуля Angie http_ssl.

Использование списка отзыва сертификатов#

Политика IngressMTLS поддерживает настройку списка CRL для политики. Это можно сделать одним из двух способов.

Примечание

Одновременно можно использовать только один из этих параметров конфигурации.

  1. Добавление в тип секрета angie.software/caполя ca.crl, которое содержит список отзыва сертификатов в кодировке base64. Пример YAML:

    kind: Secret
    metadata:
      name: ingress-mtls-secret
    apiVersion: v1
    type: angie.software/ca
    data:
      ca.crt: <base64encoded-certificate>
      ca.crl: <base64encoded-crl>
    
  2. Добавление поля crlFileName с именем CRL-файла в спецификацию политики IngressMTLS.

    Примечание

    Этот параметр конфигурации следует использовать только при наличии CRL-файла размером более 1 МБ; в противном случае рекомендуется использовать для управления CRL тип секрета angie.software/ca.

    Пример YAML:

    apiVersion: k8s.angie.software/v1
    kind: Policy
    metadata:
      name: ingress-mtls-policy
    spec:
    ingressMTLS:
        clientCertSecret: ingress-mtls-secret
        crlFileName: webapp.crl
        verifyClient: "on"
        verifyDepth: 1
    

Предупреждение

При настройке CRL с помощью поля ingressMTLS.crlFileName следует учитывать дополнительный контекст:

  1. ANIC ожидает, что CRL, в данном случае webapp.crl, будет находиться в каталоге /etc/angie/secrets. Для развертывания ANIC необходимо будет добавить точку подключения тома. Добавьте свой CRL в каталог /etc/angie/secrets.

  2. При обновлении содержимого списка CRL (например, был отозван новый сертификат) Angie необходимо перезагрузить, чтобы отразились последние изменения. В зависимости от вашей среды для этого может потребоваться обновить имя списка CRL и применить это обновление к политике ingress-mtls.yaml, чтобы Angie получил последнюю версию CRL.

Обратитесь к документации Kubernetes по томам, чтобы найти наилучшую реализацию для вашей среды.

Поле

Описание

Тип

Обязательно

clientCertSecret

Имя секрета Kubernetes, в котором хранится сертификат центра сертификации. Он должен находиться в том же пространстве имен, что и ресурс Policy. Секрет должен иметь тип angie.software/ca, а конфигурация должна храниться в секрете по ключу ca.crt; в противном случае секрет будет отклонен как недействительный.

string

Да

verifyClient

Верификация для клиента. Допустимые значения: "on", "off", "optional", "optional_no_ca". Значение по умолчанию - "on".

string

Нет

verifyDepth

Устанавливает глубину проверки в цепочке клиентских сертификатов. Значение по умолчанию равно 1.

int

Нет

crlFileName

Имя файла списка отзыва сертификатов. ANIC будет искать этот файл в каталоге /etc/angie/secrets

string

Нет

Поведение слияния IngressMTLS#

Ресурс VirtualServer может ссылаться только на одну политику IngressMTLS. Все последующие ссылки будут проигнорированы. Например, здесь мы ссылаемся на две политики:

policies:
  - name: ingress-mtls-policy-one
  - name: ingress-mtls-policy-two

В этом примере ANIC будет использовать конфигурацию из первой ссылки на политику ingress-mtls-policy-one и игнорирует ingress-mtls-policy-two.

EgressMTLS#

EgressMTLS настраивает аутентификацию и проверку сертификатов для апстримов.

Например, следующая политика будет использовать egress-mtls-secret для аутентификации в приложении апстрима и egress-trusted-ca-secret для проверки сертификата приложения:

egressMTLS:
  tlsSecret: egress-mtls-secret
  trustedCertSecret: egress-trusted-ca-secret
  verifyServer: on
  verifyDepth: 2

Примечание

Функция реализована с использованием модуля Angie http_proxy.

Поле

Описание

Тип

Обязательно

tlsSecret

Имя секрета файла Kubernetes, в котором хранятся сертификат и ключ TLS. Он должен находиться в том же пространстве имен, что и ресурс Policy. Секрет должен иметь тип kubernetes.io/tls, сертификат - храниться в секрете под ключом tls.crt, а ключ - как tls.key; в противном случае секрет будет отклонен как недействительный.

string

Нет

trustedCertSecret

Имя секрета Kubernetes, в котором хранится сертификат центра сертификации. Он должен находиться в том же пространстве имен, что и ресурс Policy. Секрет должен иметь тип angie.software/ca, а конфигурация должна храниться в секрете по ключу ca.crt; в противном случае секрет будет отклонен как недействительный.

string

Нет

verifyServer

Включает проверку сертификата HTTPS-сервера апстрима.

bool

Нет

verifyDepth

Устанавливает глубину проверки в цепочке сертификатов проксируемого HTTPS-сервера. Значение по умолчанию равно 1.

int

Нет

sessionReuse

Позволяет повторно использовать SSL-сеансы к апстримам. Значение по умолчанию равно true.

bool

Нет

serverName

Позволяет передавать имя сервера через расширение SNI.

bool

Нет

sslName

Позволяет переопределить имя сервера, используемое для проверки сертификата HTTPS-сервера апстрима.

string

Нет

ciphers

Указывает разрешенные шифры для запросов к HTTPS-серверу апстрима. Значение по умолчанию - DEFAULT.

string

Нет

protocols

Задает протоколы для запросов к HTTPS-серверу апстрима. Значение по умолчанию - TLSv1, TLSv1.1, TLSv1.2.

string

Нет

Поведение слияния EgressMTLS#

Ресурс VirtualServer или VirtualServerRoute может ссылаться на несколько политик EgressMTLS. При этом будет применяться только одна из них. Все последующие ссылки будут проигнорированы. Например, здесь мы ссылаемся на две политики:

policies:
  - name: egress-mtls-policy-one
  - name: egress-mtls-policy-two

В этом примере ANIC будет использовать конфигурацию из первой ссылки на политику egress-mtls-policy-one и игнорирует egress-mtls-policy-two.

Применение политик#

Политики можно применять как к ресурсам VirtualServer, так и к VirtualServerRoute. Например:

- VirtualServer:
    apiVersion: k8s.angie.software/v1
    kind: VirtualServer
    metadata:
      name: cafe
      namespace: cafe
    spec:
      host: cafe.example.com
      tls:
        secret: cafe-secret
      policies: # spec policies
        - name: policy1
    upstreams:
      - name: coffee
        service: coffee-svc
        port: 80
    routes:
      - path: /tea
        policies: # route policies
        - name: policy2
          namespace: cafe
          route: tea/tea
      - path: /coffee
        policies: # route policies
          - name: policy3
            namespace: cafe
        action:
          pass: coffee

В случае VirtualServer политику можно применить:

  • для всех маршрутов (политики спецификации)

  • к определенному маршруту (политики маршрутов)

    Политики маршрутов имеют приоритет над политиками спецификации того же типа. Если в примере выше тип политик policy-1 и policy-3 - AccessControl, то для запросов к cafe.example.com/coffee Angie применит policy-3.

    Переопределение обеспечивается Angie: политики спецификации реализуются в контексте конфигурации server, а политики маршрутов реализуются в контексте location. В результате приоритет в рамках одного типа имеют политики маршрутов.

  • Ресурс VirtualServerRoute, на который ссылается указанный выше VirtualServer:

    apiVersion: k8s.angie.software/v1
    kind: VirtualServerRoute
    metadata:
      name: tea
      namespace: tea
    spec:
      host: cafe.example.com
      upstreams:
        - name: tea
          service: tea-svc
          port: 80
      subroutes: # subroute policies
        - path: /tea
          policies:
          - name: policy4
            namespace: tea
          action:
            pass: tea
    

    В VirtualServerRoute можно применить политику к вложенному маршруту (политики вложенных маршрутов).

    Политики вложенных маршрутов имеют приоритет над политиками спецификации того же типа. В приведенном выше примере, если тип политик policy-1 (в VirtualServer) и policy-4 - AccessControl, то для запросов к cafe.example.com/tea Angie будет применять policy-4. Как и в случае с VirtualServer, переопределение обеспечивается средствами Angie.

    Политики вложенных маршрутов всегда имеют приоритет над политиками маршрутов независимо от типа. Например, политика policy-2 в маршруте VirtualServer будет проигнорирована на вложенном маршруте /tea, поскольку у того есть свои собственные политики (в нашем случае это только policy4). Если бы у вложенного маршрута не было политик, то была бы применена policy-2. Это переопределение выполняет ANIC - контекст location для вложенного маршрута будет содержать либо политики маршрута, либо политики вложенного маршрута, но не то и другое вместе.

Недопустимые политики#

Angie будет рассматривать политику как недействительную, если выполняется одно из следующих условий:

  • Политика не проходит всестороннюю валидацию.

  • Политика отсутствует в кластере.

  • Политика не соответствует требованиям, предъявляемым к ее конкретному типу. Например, политика ingressMTLS требует, чтобы в VirtualServer было включено завершение TLS.

В случае недопустимой политики Angie возвращает код состояния 500 для клиентских запросов со следующими правилами:

  • Если на политику ссылается маршрут VirtualServer или вложенный маршрут VirtualServerRoute, Angie будет возвращать код состояния 500 для запросов к URI такого маршрута.

  • Если ссылка на политику задана в спецификации VirtualServer, Angie будет возвращать код состояния 500 для запросов ко всем URI этого VirtualServer.

Если политика недействительна, VirtualServer или VirtualServerRoute будет иметь статус с предупреждением о состоянии и сообщением, объясняющим, почему политика не была признана недействительной.

Валидация#

Для ресурса Policy доступны два типа валидации:

  • Структурная валидация с помощью kubectl и сервера Kubernetes API.

  • Всесторонняя валидация с помощью ANIC.

Структурная валидация#

Пользовательское определение ресурса для Policy включает структурную схему OpenAPI, которая описывает тип каждого поля ресурса.

Если вы попытаетесь создать (или обновить) ресурс, который нарушает структурную схему (например, использует строковое значение вместо массива строк в поле allow), то kubectl и сервер Kubernetes API отклонят ресурс.

  • Пример проверки kubectl:

    kubectl apply -f access-control-policy-allow.yaml
    
    error: error validating "access-control-policy-allow.yaml": error validating data: ValidationError(Policy.spec.accessControl.allow): invalid type for software.angie.k8s.v1.Policy.spec.accessControl.allow: got "string", expected "array"; if you choose to ignore these errors, turn validation off with --validate=false
    
  • Пример проверки сервера Kubernetes API:

    kubectl apply -f access-control-policy-allow.yaml --validate=false
    
    The Policy "webapp-policy" is invalid: spec.accessControl.allow: Invalid value: "string": spec.accessControl.allow in body must be of type array: "string"
    

Если ресурс прошел структурную валидацию, выполняется всесторонняя валидация ANIC.

Всесторонняя валидация#

ANIC проверяет поля ресурса Policy. Если ресурс недопустим, ANIC отклонит его. Ресурс останется в кластере, но ANIC будет игнорировать его.

Можно использовать kubectl, чтобы проверить, успешно ли ANIC применил конфигурацию Policy. Для политики mypolicy мы можем запустить:

kubectl describe pol mypolicy

. . .
Events:
  Type    Reason          Age   From                      Message
-----
Normal  AddedOrUpdated  11s   angie-ingress-controller  Policy default/mypolicy was added or updated

Обратите внимание, что раздел «События» (Events) включает событие Normal с причиной AddedOrUpdated, которое информирует нас о том, что конфигурация была успешно применена.

Если вы создадите недопустимый ресурс, ANIC отклонит его и выдаст событие Rejected. Например, если вы создадите политику mypolicy с недопустимым IP-адресом 10.0.0. в поле allow, то вы получите:

kubectl describe policy mypolicy
. . .
Events:
  Type     Reason    Age   From                      Message
-----
Warning  Rejected  7s    angie-ingress-controller  Policy default/mypolicy is invalid and was rejected: spec.accessControl.allow[0]: Invalid value: "10.0.0.": must be a CIDR or IP

Обратите внимание, что раздел «События» (Events) включает предупреждающее событие с указанием причины отклонения.

Кроме того, эта информация также доступна в поле status ресурса Policy. Обратите внимание на раздел «Статус» (Status) политики:

kubectl describe pol mypolicy

. . .
Status:
  Message:  Policy default/mypolicy is invalid and was rejected: spec.accessControl.allow[0]: Invalid value: "10.0.0.": must be a CIDR or IP
  Reason:   Rejected
  State:    Invalid

Примечание

Если вы сделаете существующий ресурс недействительным, ANIC отклонит его.