Envoy와 Apache APISIX: Envoy Filter를 구현하는 또 다른 방법

API7.ai

December 16, 2020

Technology

Envoy 필터 구현 방법

Envoy 필터

Envoy는 현대적인 대규모 서비스 지향 아키텍처를 위해 설계된 L7 프록시 및 통신 버스입니다. 플러그 가능한 필터 체인 메커니즘을 통해 다양한 작업을 수행할 수 있는 필터를 작성하여 메인 서버에 삽입할 수 있습니다.

Envoy 필터

확장 방법

기존 필터가 사용자의 맞춤 요구 사항을 충족하지 못할 경우, Envoy를 확장해야 합니다. 기존 필터 체인을 기반으로 새로운 필터를 맞춤화하여 요구 사항을 충족시킬 수 있습니다.

개발자는 세 가지 방법으로 Envoy를 확장할 수 있습니다:

시작 난이도안정성개발 효율성배포 및 컴파일
C++높음안정적낮음컴파일 시간이 오래 걸림
Lua낮음안정적높음컴파일 없이 직접 배포 가능
WASM중간-높음불확실언어에 의존언어에 따라 컴파일 시간이 다름
  1. C++을 사용하여 확장

이 방법은 Envoy를 기반으로 직접 C++ 코드를 작성하여 기능을 강화합니다. 맞춤 필터를 구현한 후, 새로운 바이너리 파일을 다시 컴파일하여 업그레이드를 완료합니다. 이 방법에는 두 가지 문제가 있습니다:

  • C++ 언어에 제한되어 있어 시작 난이도가 높고 개발자가 부족합니다.
  • 배포, 운영, 유지보수 및 업그레이드의 복잡성이 증가합니다. Envoy는 점점 무거워지고, 모든 변경 사항마다 바이너리 파일을 다시 컴파일해야 하므로 반복 및 관리가 어렵습니다.
  1. Lua를 사용하여 확장

Lua는 애플리케이션에 내장되어 유연한 확장 및 맞춤 기능을 제공하기 위해 태어났으며, 널리 사용되고 있습니다.

Lua 필터는 요청 및 응답 프로세스에서 Lua 스크립트를 실행할 수 있게 합니다. 현재 지원되는 주요 기능은 다음과 같습니다: 요청 또는 응답 흐름에서 헤더, 본문, 트레일러 검사; 헤더 및 트레일러 수정; 전체 요청/응답 본문 검사를 위한 차단 및 버퍼링; 업스트림 호스트에 대한 비동기 HTTP 호출 수행; 직접 응답 수행 및 추가 필터 반복 건너뛰기 등.

현재 많은 사람들이 설정에서 직접 Lua 코드를 배포하지만, 이는 코드 조직 및 관리에 불리하며, 다른 사람들과 공유하여 생태계를 형성하기 어렵습니다.

  1. WASM 확장 사용

개발자는 자신의 프로그래밍 언어로 필터를 작성하고, 도구를 사용하여 WASM 형식으로 컴파일한 후 Envoy에 내장하여 실행할 수 있습니다.

현재 지원되는 언어가 적으며, 이러한 언어를 사용하여 확장하는 것은 여전히 간단하지 않습니다. 반면, 많은 사람들이 WASM에 대해 여전히 우려를 가지고 있어 직접 사용하지 않을 수 있습니다.

Apache APISIX 솔루션

위의 분석을 통해 Lua가 Envoy를 확장하는 데 매우 적합하며, 배우기 쉽고 개발 효율성이 매우 높다는 것을 알 수 있습니다. Envoy에 내장되어 있기 때문에 추가 네트워크 오버헤드가 없고 성능이 좋습니다.

Apache APISIX 커뮤니티는 Lua를 기반으로 한 자체 솔루션을 제안합니다. 이는 강력하고 유연한 기본 라이브러리를 제공하여 Apache APISIX의 모든 플러그인과 향후 개발될 플러그인이 Envoy에서 실행될 수 있도록 하는 것입니다. 개발자는 이 기본 라이브러리를 기반으로 자신만의 맞춤 플러그인을 개발할 수도 있습니다.

Apache APISIX는 동적, 실시간, 고성능 API 게이트웨이로, Nginx 라이브러리와 Lua를 기반으로 합니다. Apache APISIX는 로드 밸런싱, 동적 업스트림, 카나리 릴리스, 서킷 브레이커, 인증, 관찰 가능성 등 다양한 트래픽 관리 기능을 제공합니다.

예제

구체적인 코드와 실행 방법은 다음 저장소를 확인하세요: https://github.com/api7/envoy-apisix.

Envoy의 관련 설정은 다음과 같습니다:

필터 정의:

http_filters:
  - name: entry.lua
    typed_config:
      "@type": type.googleapis.com/envoy.extensions.filters.http.lua.v3.Lua
      source_codes:
        entry.lua:
          filename: /apisix/entry.lua

라우트에 필터를 활성화하고 메타데이터로 구성:

routes:
  - match:
      prefix: "/foo"
    route:
      cluster: web_service
    typed_per_filter_config:
      envoy.filters.http.lua:
        "@type": type.googleapis.com/envoy.extensions.filters.http.lua.v3.LuaPerRoute
        name: entry.lua
    metadata:
      filter_metadata:
        envoy.filters.http.lua:
          plugins:
            - name: uri-blocker
              conf:
                rejected_code: 403
                block_rules:
                  - root.exe
                  - root.m+

작동 방식

Envoy에 큰 변경을 가할 필요 없이, 공통 요구 사항에 적합한 몇 가지 최적화만 수행합니다.

플러그인 계층에 대해 플랫폼 차이를 차단합니다. 사용해야 하는 모든 인터페이스는 기본 프레임워크인 apisix.core에 추상화되어 있어 모든 플러그인이 Envoy와 Apache APISIX에서 동시에 실행될 수 있습니다.

아키텍처 다이어그램

이전 예제를 사용하여 플러그인이 어떻게 실행되는지 보여줍니다:

플러그인 작업 흐름

첫 번째 단계, 설정 읽기

메타데이터를 통해 각 라우트에서 실행해야 할 플러그인과 각 플러그인의 설정을 결정합니다. 예제에서는 /foo 접두사를 가진 라우트에 uri-blocker 플러그인을 설정하고, 플러그인의 차단 규칙과 차단이 필요할 때의 응답 상태를 설정했습니다.

두 번째 단계, 요청 파싱

클라이언트 요청 데이터를 ctx로 캡슐화하여 전체 프로세스에서 직접 사용할 수 있게 합니다.

세 번째 단계, 플러그인 실행

설정된 규칙과 얻은 uri를 매칭하여 이 요청을 차단해야 하는지 여부를 결정합니다. 차단이 필요하면 respond를 호출하여 직접 응답하고, 그렇지 않으면 통과시킵니다.

미래 전망

점점 더 많은 APISIX 플러그인이 Envoy에서 실행 가능해지고 있으며, 결국 모든 APISIX 플러그인(향후 개발될 플러그인 포함)이 Envoy에서 실행 가능해질 것입니다.

동시에, 우리는 Envoy 커뮤니티와 Lua 필터 방향으로 협력하여 Lua 필터를 최적화하고 개선하고, Envoy의 확장 능력을 강화하며, Envoy 확장의 난이도를 낮추기를 희망합니다.

Tags: