Skip to content

Commit 905fcfa

Browse files
committed
dynamic_modules: add examples for network & listener modules
Signed-off-by: Rohit Agrawal <rohit.agrawal@databricks.com>
1 parent db78e3f commit 905fcfa

12 files changed

Lines changed: 2676 additions & 16 deletions

go/gosdk/abi.go

Lines changed: 13 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -22,11 +22,15 @@ typedef enum {
2222
envoy_dynamic_module_type_http_header_type_ResponseTrailer = 3,
2323
} envoy_dynamic_module_type_http_header_type;
2424
25+
// envoy_dynamic_module_type_envoy_buffer is a struct representing a buffer owned by Envoy.
26+
// Uses const char* because this receives data FROM Envoy.
2527
typedef struct {
26-
uintptr_t ptr;
28+
const char* ptr;
2729
size_t length;
2830
} envoy_dynamic_module_type_envoy_buffer;
2931
32+
// envoy_dynamic_module_type_module_buffer is a struct representing a buffer owned by the module.
33+
// Uses uintptr_t because this sends data TO Envoy.
3034
typedef struct {
3135
uintptr_t ptr;
3236
size_t length;
@@ -85,8 +89,7 @@ size_t envoy_dynamic_module_callback_http_get_body_chunks_size(
8589
int body_type);
8690
8791
#cgo noescape envoy_dynamic_module_callback_http_send_response
88-
// Uncomment once https://github.com/envoyproxy/envoy/pull/39206 is merged.
89-
// #cgo nocallback envoy_dynamic_module_callback_http_send_response
92+
#cgo nocallback envoy_dynamic_module_callback_http_send_response
9093
void envoy_dynamic_module_callback_http_send_response(
9194
uintptr_t filter_envoy_ptr, uint32_t status_code,
9295
uintptr_t headers_vector, size_t headers_vector_size,
@@ -164,13 +167,11 @@ func envoy_dynamic_module_on_program_init() uintptr {
164167
//export envoy_dynamic_module_on_http_filter_config_new
165168
func envoy_dynamic_module_on_http_filter_config_new(
166169
_ uintptr,
167-
namePtr *C.char,
168-
nameSize C.size_t,
169-
configPtr *C.char,
170-
configSize C.size_t,
170+
nameBuffer C.envoy_dynamic_module_type_envoy_buffer,
171+
configBuffer C.envoy_dynamic_module_type_envoy_buffer,
171172
) uintptr {
172-
name := C.GoStringN(namePtr, C.int(nameSize))
173-
config := C.GoBytes(unsafe.Pointer(configPtr), C.int(configSize))
173+
name := C.GoStringN(nameBuffer.ptr, C.int(nameBuffer.length))
174+
config := C.GoBytes(unsafe.Pointer(configBuffer.ptr), C.int(configBuffer.length))
174175
filterConfig := NewHttpFilterConfig(name, config)
175176
if filterConfig == nil {
176177
return 0
@@ -389,7 +390,7 @@ func (e envoyFilter) GetRequestHeader(key string) (string, bool) {
389390
return "", false
390391
}
391392

392-
result := unsafe.Slice((*byte)(unsafe.Pointer(uintptr(resultBuf.ptr))), resultBuf.length)
393+
result := unsafe.Slice((*byte)(unsafe.Pointer(resultBuf.ptr)), resultBuf.length)
393394
runtime.KeepAlive(key)
394395
return string(result), true
395396
}
@@ -415,7 +416,7 @@ func (e envoyFilter) GetResponseHeader(key string) (string, bool) {
415416
return "", false
416417
}
417418

418-
result := unsafe.Slice((*byte)(unsafe.Pointer(uintptr(resultBuf.ptr))), resultBuf.length)
419+
result := unsafe.Slice((*byte)(unsafe.Pointer(resultBuf.ptr)), resultBuf.length)
419420
runtime.KeepAlive(key)
420421
return string(result), true
421422
}
@@ -563,7 +564,7 @@ func (e envoyFilter) getStringAttribute(id int) string {
563564
if !ret {
564565
return ""
565566
}
566-
return string(unsafe.Slice((*byte)(unsafe.Pointer(uintptr(result.ptr))), result.length)) // Copy the result to a Go string.
567+
return string(unsafe.Slice((*byte)(unsafe.Pointer(result.ptr)), result.length)) // Copy the result to a Go string.
567568
}
568569

569570
// GetRequestHeaders implements EnvoyHttpFilter.

rust/Cargo.lock

Lines changed: 1 addition & 1 deletion
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

rust/Cargo.toml

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,3 @@
1-
21
[package]
32
name = "envoy-proxy-dynamic-modules-rust-sdk-examples"
43
version = "0.1.0"
@@ -17,7 +16,8 @@ matchers = "0.2.0"
1716
[dev-dependencies]
1817
tempfile = "3.16.0"
1918

19+
# Main library - HTTP filters (backward compatible)
2020
[lib]
2121
name = "rust_module"
2222
path = "src/lib.rs"
23-
crate-type = ["cdylib"]
23+
crate-type = ["cdylib", "rlib"]

rust/src/http_zero_copy_regex_waf.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -126,7 +126,7 @@ mod tests {
126126
#[test]
127127
/// This demonstrates how to write a test without Envoy using a mock provided by the SDK.
128128
fn test_filter() {
129-
let mut filter_config = FilterConfig::new("Hello [Ww].+").unwrap();
129+
let filter_config = FilterConfig::new("Hello [Ww].+").unwrap();
130130
let mut envoy_filter = MockEnvoyHttpFilter::new();
131131
let mut filter: Box<dyn HttpFilter<MockEnvoyHttpFilter>> =
132132
filter_config.new_http_filter(&mut envoy_filter);

rust/src/lib.rs

Lines changed: 53 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,65 @@
1+
//! Envoy Dynamic Modules Rust SDK Examples
2+
//!
3+
//! This crate contains example implementations of Envoy dynamic modules using the Rust SDK.
4+
//!
5+
//! # HTTP Filters
6+
//!
7+
//! The main library exports HTTP filter examples that work with `declare_init_functions!`:
8+
//! - `passthrough` - A minimal filter that passes all data through unchanged.
9+
//! - `access_logger` - Logs request/response information.
10+
//! - `random_auth` - Randomly rejects requests (for testing).
11+
//! - `zero_copy_regex_waf` - Zero-copy regex-based WAF filter.
12+
//! - `header_mutation` - Adds/removes/modifies headers.
13+
//! - `metrics` - Collects request/response metrics.
14+
//!
15+
//! # Network Filters
16+
//!
17+
//! Network filter examples are provided as public modules. To use them, create a separate
18+
//! crate that includes this library and uses `declare_network_filter_init_functions!` with
19+
//! the module's `new_filter_config` function.
20+
//!
21+
//! Available network filters:
22+
//! - [`network_echo`] - Echoes data back to the client.
23+
//! - [`network_rate_limiter`] - Limits concurrent connections.
24+
//! - [`network_protocol_logger`] - Logs protocol information.
25+
//! - [`network_redis`] - Redis RESP protocol parser and command filter.
26+
//!
27+
//! # Listener Filters
28+
//!
29+
//! Listener filter examples are provided as public modules. To use them, create a separate
30+
//! crate that includes this library and uses `declare_listener_filter_init_functions!` with
31+
//! the module's `new_filter_config` function.
32+
//!
33+
//! Available listener filters:
34+
//! - [`listener_ip_allowlist`] - IP allowlist/blocklist filter.
35+
//! - [`listener_tls_detector`] - TLS protocol detection filter.
36+
//! - [`listener_sni_router`] - SNI-based routing filter.
37+
138
use envoy_proxy_dynamic_modules_rust_sdk::*;
239

40+
// HTTP filter examples.
341
mod http_access_logger;
442
mod http_header_mutation;
543
mod http_metrics;
644
mod http_passthrough;
745
mod http_random_auth;
846
mod http_zero_copy_regex_waf;
947

48+
// Network filter examples.
49+
// These modules can be used to create standalone network filter cdylibs.
50+
// See each module's documentation for usage instructions.
51+
pub mod network_echo;
52+
pub mod network_protocol_logger;
53+
pub mod network_rate_limiter;
54+
pub mod network_redis;
55+
56+
// Listener filter examples.
57+
// These modules can be used to create standalone listener filter cdylibs.
58+
// See each module's documentation for usage instructions.
59+
pub mod listener_ip_allowlist;
60+
pub mod listener_sni_router;
61+
pub mod listener_tls_detector;
62+
1063
declare_init_functions!(init, new_http_filter_config_fn);
1164

1265
/// This implements the [`envoy_proxy_dynamic_modules_rust_sdk::ProgramInitFunction`].

0 commit comments

Comments
 (0)