testenv

package
v1.6.2 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Jan 26, 2026 License: Apache-2.0 Imports: 43 Imported by: 0

Documentation

Index

Constants

View Source
const (
	GENEVEPort       = 6081
	GENEVEVersion    = 0
	GENEVEProtoEther = 0x6558 // Transparent Ethernet Bridging (inner Ethernet frame)
	GENEVEProtoIPv4  = 0x0800 // IPv4 inner packet
	AWSGWLBOptClass  = 0x0108 // AWS GWLB option class
)

GENEVE protocol constants

View Source
const (
	DefaultEventuallyTimeout  = 15 * time.Second
	DefaultEventuallyInterval = 500 * time.Millisecond
	DefaultBlockedTimeout     = 2 * time.Second
)

Default timeouts for connection assertions

Variables

This section is empty.

Functions

func AssertCertificateIsValid

func AssertCertificateIsValid(t testing.TB, r *require.Assertions, a *assert.Assertions, certPath string)

AssertCertificateIsValid asserts basic certificate validity (not expired, not future).

func AssertCertificateValidity

func AssertCertificateValidity(t testing.TB, r *require.Assertions, a *assert.Assertions, certPath string, description string)

AssertCertificateValidity asserts that a certificate file is valid with default options.

func AssertCertificateValidityWithOptions

func AssertCertificateValidityWithOptions(t testing.TB, r *require.Assertions, a *assert.Assertions, certPath string, description string, opts CertificateValidityOptions)

AssertCertificateValidityWithOptions asserts that a certificate file is valid with custom options.

func AssertConnectionBlocked

func AssertConnectionBlocked(t testing.TB, r *require.Assertions, client *Client, ip string, port int, msgAndArgs ...interface{})

AssertConnectionBlocked asserts that a connection to ip:port is blocked (times out or errors).

func AssertConnectionBlockedWithTimeout

func AssertConnectionBlockedWithTimeout(t testing.TB, r *require.Assertions, client *Client, ip string, port int, timeout time.Duration, msgAndArgs ...interface{})

AssertConnectionBlockedWithTimeout asserts that a connection is blocked with custom timeout.

func AssertConnectionSucceeds

func AssertConnectionSucceeds(t testing.TB, r *require.Assertions, client *Client, ip string, port int, msgAndArgs ...interface{})

AssertConnectionSucceeds asserts that a connection to ip:port succeeds immediately.

func AssertDNSResolution

func AssertDNSResolution(t testing.TB, r *require.Assertions, client *Client, tn *TestNetwork, hostname string, msgAndArgs ...interface{})

AssertDNSResolution asserts that DNS resolution succeeds for the given hostname.

func AssertDNSResolutionFails

func AssertDNSResolutionFails(t testing.TB, r *require.Assertions, client *Client, tn *TestNetwork, hostname string, msgAndArgs ...interface{})

AssertDNSResolutionFails asserts that DNS resolution fails for the given hostname.

func AssertEventuallyConnects

func AssertEventuallyConnects(t testing.TB, r *require.Assertions, client *Client, ip string, port int, msgAndArgs ...interface{})

AssertEventuallyConnects asserts that a connection to ip:port eventually succeeds.

func AssertEventuallyConnectsWithTimeout

func AssertEventuallyConnectsWithTimeout(t testing.TB, r *require.Assertions, client *Client, ip string, port int, timeout, interval time.Duration, msgAndArgs ...interface{})

AssertEventuallyConnectsWithTimeout asserts that a connection eventually succeeds with custom timeout.

func AssertEventuallyDNSResolves

func AssertEventuallyDNSResolves(t testing.TB, r *require.Assertions, client *Client, tn *TestNetwork, hostname string, msgAndArgs ...interface{})

AssertEventuallyDNSResolves asserts that DNS resolution eventually succeeds.

func AssertEventuallyFileExists

func AssertEventuallyFileExists(t testing.TB, r *require.Assertions, path string, msgAndArgs ...interface{})

AssertEventuallyFileExists asserts that a file eventually exists at the given path.

func AssertFileExists

func AssertFileExists(t testing.TB, r *require.Assertions, path string, msgAndArgs ...interface{})

AssertFileExists asserts that a file exists at the given path.

func AssertFilePermissions

func AssertFilePermissions(t testing.TB, r *require.Assertions, path string, expectedMode os.FileMode, description string)

AssertFilePermissions asserts that a file exists and has the expected permissions.

func AssertHTTPBodyContains

func AssertHTTPBodyContains(t testing.TB, a *assert.Assertions, resp *HTTPResponse, expected string, msgAndArgs ...interface{})

AssertHTTPBodyContains asserts that an HTTP response body contains the expected string.

func AssertHTTPStatus

func AssertHTTPStatus(t testing.TB, r *require.Assertions, resp *HTTPResponse, expectedStatus int, msgAndArgs ...interface{})

AssertHTTPStatus asserts that an HTTP response has the expected status code.

func CaptureTracePipeSync added in v1.6.1

func CaptureTracePipeSync(duration time.Duration) string

CaptureTracePipeSync captures trace_pipe for a duration and returns the output

func CheckHealthEndpoint

func CheckHealthEndpoint(ip string, port int) (int, error)

CheckHealthEndpoint verifies health endpoint HTTP status code Used by all cloud lifecycle tests to verify /health endpoint behavior

func CheckNodeHealth

func CheckNodeHealth(testNet *TestNetwork) bool

CheckNodeHealth checks if a Neuwerk node is healthy by querying its /readyz endpoint. Returns true if the node responds with HTTP 200, false otherwise.

func CleanupStaleBPFMaps

func CleanupStaleBPFMaps()

CleanupStaleBPFMaps removes any leftover BPF maps from previous test runs. This is critical for preventing memory leaks when tests are interrupted (Ctrl+C) or fail before cleanup. BPF maps are pinned to /sys/fs/bpf/ and persist in kernel memory even after the process exits.

Integration tests use reduced map sizes (~5MB per instance vs ~600MB production), but leftover maps can still accumulate if tests are interrupted.

func CleanupTestNamespaces added in v1.6.1

func CleanupTestNamespaces(t *testing.T, env *K8sTestEnv)

CleanupTestNamespaces removes all test namespaces (test-ns-* prefix) from the Kind cluster. This is best-effort cleanup - failures are logged but don't fail the test. Cleanup happens both at test start and end to handle interrupted tests.

func ConnectNeuwerkToKind added in v1.6.1

func ConnectNeuwerkToKind(t *testing.T, testNet *TestNetwork, kindEnv *K8sTestEnv) (net.IP, error)

ConnectNeuwerkToKind creates a veth pair to connect the neuwerk namespace to the Kind Docker network. This allows neuwerk to reach the Kind API server at its Docker network IP. The function: 1. Creates a veth pair 2. Attaches one end to the Kind Docker bridge (in the host namespace) 3. Moves the other end to the neuwerk namespace 4. Assigns an IP address from the Kind subnet to the veth in the neuwerk namespace 5. Adds a route for the Kind subnet via this interface

Returns the IP address assigned to the veth in the neuwerk namespace.

func CreateNamespaceInKind added in v1.6.1

func CreateNamespaceInKind(t *testing.T, env *K8sTestEnv, name string)

CreateNamespaceInKind creates a namespace in the Kind cluster.

func DeleteNamespaceInKind added in v1.6.1

func DeleteNamespaceInKind(t *testing.T, env *K8sTestEnv, name string)

DeleteNamespaceInKind deletes a namespace from the Kind cluster.

func DumpFlowStateEntries added in v1.6.2

func DumpFlowStateEntries(flowStateMap *ebpf.Map, limit int) ([]struct {
	Key      bpf.FlowKey
	Metadata bpf.FlowMetadata
}, error)

DumpFlowStateEntries iterates over all entries in the flow_state map and returns them. Useful for debugging when expected entries aren't found.

func DumpNetworkState added in v1.6.1

func DumpNetworkState(tn *TestNetwork)

DumpNetworkState dumps the network state for a TestNetwork to stdout

func ExecInNS

func ExecInNS(ns netns.NsHandle, fn func() error) error

ExecInNS executes a function in a specific network namespace This is a shared utility function used across the testenv package

func ExecInNSWithOutput added in v1.6.1

func ExecInNSWithOutput(nsName string, cmdName string, args ...string) (string, error)

ExecInNSWithOutput runs a command in a namespace and returns output

func FlowKeyToString added in v1.6.2

func FlowKeyToString(k *bpf.FlowKey) string

FlowKeyToString returns a human-readable representation of a flow key.

func FlowStateToString added in v1.6.2

func FlowStateToString(m *bpf.FlowMetadata) string

FlowStateToString returns a human-readable representation of flow metadata.

func GenerateTestNamespace added in v1.6.1

func GenerateTestNamespace() string

GenerateTestNamespace generates a unique namespace name for test isolation. Uses time-based suffix to prevent collisions across parallel tests.

func GetAllGCPNodeIPs

func GetAllGCPNodeIPs(ctx context.Context, projectID, zone, clusterName string) ([]string, error)

GetAllGCPNodeIPs returns all Neuwerk instance IPs in the cluster

func GetAllGCPNodeNames

func GetAllGCPNodeNames(ctx context.Context, projectID, zone, clusterName string) ([]string, error)

GetAllGCPNodeNames returns all Neuwerk instance names in the cluster

func GetCertificateSerial

func GetCertificateSerial(t testing.TB, r *require.Assertions, certPath string) string

GetCertificateSerial reads a certificate and returns its serial number as a string.

func GetGCPBackendHealth

func GetGCPBackendHealth(ctx context.Context, projectID, region, backendServiceName string) ([]string, error)

GetGCPBackendHealth queries backend service health status

func GetGCPInstanceNameByIP

func GetGCPInstanceNameByIP(ctx context.Context, projectID, zone, ip string) (string, error)

GetGCPInstanceNameByIP retrieves instance name from internal IP

func GetGCPManagementIP

func GetGCPManagementIP(ctx context.Context, projectID, zone, instanceName string) (string, error)

GetGCPManagementIP retrieves Neuwerk instance internal IP via gcloud

func PolicyFixture

func PolicyFixture(name string) string

PolicyFixture returns the path to a policy fixture file.

func RunTcpdumpInNS added in v1.6.1

func RunTcpdumpInNS(nsName, ifName string, duration time.Duration) string

RunTcpdumpInNS runs tcpdump in a network namespace for a duration

func StartNeuwerkWithClient

func StartNeuwerkWithClient(t testing.TB, tn *TestNetwork, policyFile string) (*NeuwerkInstance, *Client)

StartNeuwerkWithClient starts Neuwerk with the given options and returns both the instance and a pre-configured client for the test network. The client is automatically configured with the root token for API authentication.

func StartNeuwerkWithClientAndOptions

func StartNeuwerkWithClientAndOptions(t testing.TB, tn *TestNetwork, opts NeuwerkOptions) (*NeuwerkInstance, *Client)

StartNeuwerkWithClientAndOptions starts Neuwerk with extended options and returns both the instance and a pre-configured client. The client is automatically configured with the root token for API authentication.

func TestPublicKeyFile

func TestPublicKeyFile() string

TestPublicKeyFile returns the path to the test public key file

func WaitForFlowState added in v1.6.2

func WaitForFlowState(
	flowStateMap *ebpf.Map,
	srcIP, dstIP net.IP,
	srcPort, dstPort uint16,
	protocol uint8,
	timeout time.Duration,
	pollInterval time.Duration,
) (*bpf.FlowMetadata, error)

WaitForFlowState polls for a flow_state entry with retries. Returns the flow metadata if found within the timeout, or an error.

func WaitForGCPBackendHealthy

func WaitForGCPBackendHealthy(ctx context.Context, projectID, region, backendServiceName string, timeout time.Duration) error

WaitForGCPBackendHealthy polls backend service until at least one backend is healthy

Types

type AzureClient

type AzureClient struct {
	// contains filtered or unexported fields
}

AzureClient wraps Azure SDK clients for testing

func NewAzureClient

func NewAzureClient(ctx context.Context, subscriptionID, resourceGroup string) (*AzureClient, error)

NewAzureClient creates Azure SDK client using Workload Identity

func (*AzureClient) ExecuteRemoteCommand

func (c *AzureClient) ExecuteRemoteCommand(ctx context.Context, vmName, command string) (string, error)

ExecuteRemoteCommand runs command on Azure VM via Run Command (Azure equivalent of SSM)

func (*AzureClient) GetAzureVMIPs

func (c *AzureClient) GetAzureVMIPs(ctx context.Context, clusterName string) ([]string, error)

GetAzureVMIPs returns private IPs for all VMs with cluster-name tag

func (*AzureClient) GetAzureVMNames

func (c *AzureClient) GetAzureVMNames(ctx context.Context, clusterName string) ([]string, error)

GetAzureVMNames returns VM names for all VMs with cluster-name tag

func (*AzureClient) GetGWLBBackendHealth

func (c *AzureClient) GetGWLBBackendHealth(ctx context.Context, lbName, backendPoolName string) (map[string]string, error)

GetGWLBBackendHealth returns health status of GWLB backend pool targets

func (*AzureClient) GetNodeStatsViaRunCommand

func (c *AzureClient) GetNodeStatsViaRunCommand(ctx context.Context, vmName, rootToken string) (map[string]interface{}, error)

GetNodeStatsViaRunCommand gets node stats by executing curl via Azure Run Command

func (*AzureClient) GetVMByName

func (c *AzureClient) GetVMByName(ctx context.Context, vmName string) (*armcompute.VirtualMachine, error)

GetVMByName retrieves a VM by name for status checks

func (*AzureClient) StopVM

func (c *AzureClient) StopVM(ctx context.Context, vmName string) error

StopVM stops an Azure VM (for multi-node failover testing)

func (*AzureClient) WaitForGWLBHealthy

func (c *AzureClient) WaitForGWLBHealthy(ctx context.Context, lbName, backendPoolName string, timeout time.Duration) error

WaitForGWLBHealthy polls until all backends are healthy or timeout

func (*AzureClient) WaitForVMRunning

func (c *AzureClient) WaitForVMRunning(ctx context.Context, vmName string, timeout time.Duration) error

WaitForVMRunning polls until VM is in running state

type CertificateValidityOptions

type CertificateValidityOptions struct {
	MinValidityDuration time.Duration
	MaxValidityDuration time.Duration
	BackdateTolerance   time.Duration
}

CertificateValidityOptions configures certificate validity checks.

func DefaultCertificateValidityOptions

func DefaultCertificateValidityOptions() CertificateValidityOptions

DefaultCertificateValidityOptions returns sensible defaults for certificate validation.

type Client

type Client struct {
	// contains filtered or unexported fields
}

Client represents a test client in a network namespace

func NewClient

func NewClient(ns netns.NsHandle, clientIP net.IP) *Client

NewClient creates a new test client

func (*Client) Connect

func (c *Client) Connect(addr string) error

Connect attempts to connect to the specified address

func (*Client) ConnectWithTimeout

func (c *Client) ConnectWithTimeout(addr string, timeout time.Duration) error

ConnectWithTimeout attempts to connect with a custom timeout

func (*Client) GetIP

func (c *Client) GetIP() net.IP

GetIP returns the client's IP address

func (*Client) HTTPDelete

func (c *Client) HTTPDelete(url string) (*HTTPResponse, error)

HTTPDelete performs an HTTP DELETE request from within the client's namespace Uses raw TCP connection to avoid Go HTTP client goroutine namespace issues

func (*Client) HTTPGet

func (c *Client) HTTPGet(url string) (*HTTPResponse, error)

HTTPGet performs an HTTP GET request from within the client's namespace Uses raw TCP connection to avoid Go HTTP client goroutine namespace issues

func (*Client) HTTPPost

func (c *Client) HTTPPost(url, contentType string, body []byte) (*HTTPResponse, error)

HTTPPost performs an HTTP POST request from within the client's namespace Uses raw TCP connection to avoid Go HTTP client goroutine namespace issues

func (*Client) HTTPPut

func (c *Client) HTTPPut(url, contentType string, body []byte) (*HTTPResponse, error)

HTTPPut performs an HTTP PUT request from within the client's namespace Uses raw TCP connection to avoid Go HTTP client goroutine namespace issues

func (*Client) Ping

func (c *Client) Ping(ip string) error

Ping sends an ICMP ping (simplified - just tries to connect)

func (*Client) ResolveDNS

func (c *Client) ResolveDNS(hostname string) error

ResolveDNS resolves a hostname using the system resolver

func (*Client) ResolveDNSWithServer

func (c *Client) ResolveDNSWithServer(hostname, dnsServer string) error

ResolveDNSWithServer resolves a hostname using a specific DNS server Uses miekg/dns directly to avoid goroutine/namespace issues with net.Resolver

func (*Client) SSEConnect

func (c *Client) SSEConnect(url string) (*SSEConnection, *HTTPResponse, error)

SSEConnect establishes an SSE connection to the specified URL Returns the connection and initial response headers for verification

func (*Client) SetAuthToken

func (c *Client) SetAuthToken(token string)

SetAuthToken sets the JWT token for API authentication. The token will be included as Authorization: Bearer <token> in all HTTP requests.

func (*Client) TriggerReconcile

func (c *Client) TriggerReconcile(apiBaseURL string) error

TriggerReconcile calls the /api/v1/reconcile endpoint to trigger immediate BPF map sync

type DNSRecords

type DNSRecords map[string][]string

DNSRecords is a map of hostname to IP addresses for mock DNS configuration.

type DebugCapture added in v1.6.1

type DebugCapture struct {
	// contains filtered or unexported fields
}

DebugCapture collects debugging information during test execution. It captures BPF trace_pipe output, tcpdump packets, and network state.

func StartDebugCapture added in v1.6.1

func StartDebugCapture(t testing.TB, tn *TestNetwork) *DebugCapture

StartDebugCapture begins capturing debug information for the test. Call Stop() or use t.Cleanup to stop capturing and print results.

func (*DebugCapture) DumpAll added in v1.6.1

func (dc *DebugCapture) DumpAll()

DumpAll prints all captured debug information

func (*DebugCapture) GetTcpdumpEgress added in v1.6.1

func (dc *DebugCapture) GetTcpdumpEgress() string

GetTcpdumpEgress returns the captured egress interface tcpdump output

func (*DebugCapture) GetTcpdumpIngress added in v1.6.1

func (dc *DebugCapture) GetTcpdumpIngress() string

GetTcpdumpIngress returns the captured ingress interface tcpdump output

func (*DebugCapture) GetTcpdumpUpstream added in v1.6.1

func (dc *DebugCapture) GetTcpdumpUpstream() string

GetTcpdumpUpstream returns the captured upstream interface tcpdump output

func (*DebugCapture) GetTracePipe added in v1.6.1

func (dc *DebugCapture) GetTracePipe() string

GetTracePipe returns the captured trace_pipe output

func (*DebugCapture) Stop added in v1.6.1

func (dc *DebugCapture) Stop()

Stop stops all capture processes

type FlowStateExpectation added in v1.6.2

type FlowStateExpectation struct {
	// TunnelType is the expected tunnel type (TUNNEL_MODE_NONE, TUNNEL_MODE_VXLAN, etc.)
	TunnelType uint8
	// ExpectVNI indicates whether VNI should be populated
	ExpectVNI bool
	// ExpectedVNI is the expected VNI value (only checked if ExpectVNI is true)
	ExpectedVNI uint32
	// ExpectOuterIPs indicates whether outer IP headers should be populated (VXLAN/GENEVE)
	ExpectOuterIPs bool
	// ExpectNATFields indicates whether NAT fields should be populated (GCP ILB mode)
	ExpectNATFields bool
}

FlowStateExpectation defines what to expect in flow_state map entries

func GetExpectationForMode added in v1.6.2

func GetExpectationForMode(config TestModeConfig) FlowStateExpectation

GetExpectationForMode returns the expected flow_state contents for a given network mode.

type FlowStateVerificationResult added in v1.6.2

type FlowStateVerificationResult struct {
	// Found indicates whether a flow_state entry was found
	Found bool
	// Metadata contains the actual flow metadata (if found)
	Metadata *bpf.FlowMetadata
	// Errors contains any verification failures
	Errors []string
}

FlowStateVerificationResult contains the result of flow_state verification

func VerifyFlowState added in v1.6.2

func VerifyFlowState(
	flowStateMap *ebpf.Map,
	srcIP, dstIP net.IP,
	srcPort, dstPort uint16,
	protocol uint8,
	expectation FlowStateExpectation,
) (*FlowStateVerificationResult, error)

VerifyFlowState looks up a flow_state entry and verifies it matches expectations. Returns the verification result including the actual metadata if found.

func (*FlowStateVerificationResult) IsValid added in v1.6.2

func (r *FlowStateVerificationResult) IsValid() bool

IsValid returns true if verification passed with no errors

type GCPDiscoveryOutput

type GCPDiscoveryOutput struct {
	ProducerVPCID        string `json:"producer_vpc_id"`
	ConsumerVPCID        string `json:"consumer_vpc_id"`
	BackendServiceID     string `json:"backend_service_id"`
	ConsumerInstanceName string `json:"consumer_instance_name"`
	ProjectID            string `json:"gcp_project_id"`
	Region               string `json:"gcp_region"`
	Zone                 string `json:"gcp_zone"`
}

GCPDiscoveryOutput holds Terraform output values for GCP

func DiscoverGCPInfrastructure

func DiscoverGCPInfrastructure(ctx context.Context, terraformDir string) (*GCPDiscoveryOutput, error)

DiscoverGCPInfrastructure queries Terraform outputs for GCP resources

type GENEVEClient

type GENEVEClient struct {
	// contains filtered or unexported fields
}

GENEVEClient can send GENEVE-encapsulated traffic for testing

func NewGENEVEClient

func NewGENEVEClient(ns netns.NsHandle, clientIP, tunnelSrcIP, tunnelDstIP net.IP, tunnelDstPort uint16, vni uint32) *GENEVEClient

NewGENEVEClient creates a new GENEVE test client

func (*GENEVEClient) ConnectViaGENEVE

func (c *GENEVEClient) ConnectViaGENEVE(innerDstIP string, innerDstPort int) error

ConnectViaGENEVE sends a GENEVE-encapsulated TCP SYN to test policy enforcement The inner packet is a TCP connection to the specified address Returns nil if the connection succeeds (traffic allowed), error if blocked

type HTTPResponse

type HTTPResponse struct {
	StatusCode int
	Body       []byte
}

HTTPResponse wraps the response from an HTTP request

type K8sTestEnv added in v1.6.1

type K8sTestEnv struct {
	KindClusterName string
	Kubeconfig      string // Raw kubeconfig content
	Clientset       *kubernetes.Clientset
	RESTConfig      *rest.Config

	// Integration API fields (extracted from kubeconfig for API requests)
	Endpoint    string // API server endpoint (e.g., https://172.18.0.2:6443)
	CACert      string // CA certificate in PEM format
	BearerToken string // Service account token for API authentication

	// Kind Docker network information (for connecting test namespaces)
	KindBridgeName string     // Docker bridge interface name (e.g., br-e91313def726)
	KindSubnet     *net.IPNet // Kind network subnet (e.g., 172.18.0.0/16)
	KindGateway    net.IP     // Kind network gateway (e.g., 172.18.0.1)
	ControlPlaneIP net.IP     // Kind control plane IP (e.g., 172.18.0.2)
}

K8sTestEnv represents a Kind cluster test environment

func SetupKindCluster added in v1.6.1

func SetupKindCluster(t *testing.T) *K8sTestEnv

SetupKindCluster creates or reuses a Kind cluster for testing. The cluster persists across test runs to avoid 30s+ startup per test. Uses a singleton pattern to support parallel tests safely.

Note: Namespace cleanup is NOT done via t.Cleanup() to support parallel tests. Stale namespaces from previous test runs are cleaned up at the START of tests.

Manual cleanup (if needed):

kind delete cluster --name neuwerk-test

type MockDNSServer

type MockDNSServer struct {
	// contains filtered or unexported fields
}

MockDNSServer provides controlled DNS responses for testing

func NewMockDNSServer

func NewMockDNSServer(ip string, port int) *MockDNSServer

NewMockDNSServer creates a new mock DNS server

func NewMockDNSServerInNS

func NewMockDNSServerInNS(ns netns.NsHandle, ip string, port int) *MockDNSServer

NewMockDNSServerInNS creates a new mock DNS server that runs in a specific namespace

func StartMockDNS

func StartMockDNS(t testing.TB, tn *TestNetwork, records DNSRecords) *MockDNSServer

StartMockDNS creates, configures, and starts a mock DNS server in the given namespace. It registers cleanup automatically and returns the started server.

func StartMockDNSMultiNode

func StartMockDNSMultiNode(t testing.TB, tn *TestNetwork, records DNSRecords) *MockDNSServer

StartMockDNSMultiNode creates a mock DNS server for multi-node setups. It binds to 0.0.0.0 to be accessible from all nodes.

func (*MockDNSServer) AddRecord

func (m *MockDNSServer) AddRecord(hostname string, ips []string)

AddRecord adds a DNS A record mapping hostname to IP addresses

func (*MockDNSServer) GetListenAddr

func (m *MockDNSServer) GetListenAddr() string

GetListenAddr returns the listen address of the DNS server

func (*MockDNSServer) RemoveRecord

func (m *MockDNSServer) RemoveRecord(hostname string)

RemoveRecord removes a DNS record

func (*MockDNSServer) SetDelay

func (m *MockDNSServer) SetDelay(d time.Duration)

SetDelay sets the response delay to simulate latency

func (*MockDNSServer) Start

func (m *MockDNSServer) Start() error

Start starts the DNS server

func (*MockDNSServer) Stop

func (m *MockDNSServer) Stop()

Stop stops the DNS server

type MockHTTPServer

type MockHTTPServer struct {
	// contains filtered or unexported fields
}

MockHTTPServer provides a simple HTTP server for testing

func NewMockHTTPServer

func NewMockHTTPServer(ns netns.NsHandle, ip net.IP, port int) *MockHTTPServer

NewMockHTTPServer creates a new mock HTTP server

func StartMockHTTPServer

func StartMockHTTPServer(t testing.TB, tn *TestNetwork, ip string, port int) *MockHTTPServer

StartMockHTTPServer creates and starts a mock HTTP server in the given namespace. It registers cleanup automatically and returns the started server.

func (*MockHTTPServer) GetListenAddr

func (m *MockHTTPServer) GetListenAddr() string

GetListenAddr returns the listen address

func (*MockHTTPServer) Start

func (m *MockHTTPServer) Start() error

Start starts the HTTP server in the specified namespace

func (*MockHTTPServer) Stop

func (m *MockHTTPServer) Stop() error

Stop stops the HTTP server

type NetworkMode added in v1.6.2

type NetworkMode int

NetworkMode represents the network deployment mode

const (
	// NetworkModeGCPILB represents GCP ILB mode (no tunnel, BPF-native NAT)
	NetworkModeGCPILB NetworkMode = iota
	// NetworkModeAzureGWLB represents Azure GWLB mode (VXLAN encapsulation)
	NetworkModeAzureGWLB
)

type NeuwerkInstance

type NeuwerkInstance struct {
	Cmd      *exec.Cmd
	PID      int
	Config   string
	TestNet  *TestNetwork
	StopChan chan struct{}
	DoneChan chan error
	Peers    []string

	APIURL        string          // API base URL (e.g., "10.100.1.10:3000") for HTTP requests
	PrivateKey    interface{}     // *rsa.PrivateKey for JWT signing
	RootToken     string          // Root admin token derived from bootstrap token
	BPFCollection *bpf.Collection // BPF map collection for test verification
	// contains filtered or unexported fields
}

NeuwerkInstance represents a running Neuwerk instance in a test environment

func StartNeuwerk

func StartNeuwerk(t interface{ Cleanup(func()) }, testNet *TestNetwork, policyFileOrOpts interface{}) (*NeuwerkInstance, error)

StartNeuwerk starts a Neuwerk instance in the test network Supports both old signature (policyFile string) and new signature (NeuwerkOptions)

func StartNeuwerkHA

func StartNeuwerkHA(t interface{ Cleanup(func()) }, testNet *TestNetwork, policyFile string, peers []string, licenseFiles *TestLicenseFiles) (*NeuwerkInstance, error)

StartNeuwerkHA starts a Neuwerk instance in HA mode with peers licenseFiles must be provided for HA mode to work (pass nil for non-HA tests)

func StartNeuwerkVXLAN

func StartNeuwerkVXLAN(t interface{ Cleanup(func()) }, testNet *TestNetwork, policyFile string, peers []string, licenseFiles *TestLicenseFiles) (*NeuwerkInstance, error)

StartNeuwerkVXLAN starts a Neuwerk instance in HA mode with VXLAN tunnel mode enabled. This is used for testing VXLAN encapsulation/decapsulation with policy enforcement.

func (*NeuwerkInstance) GetBPFCollection added in v1.6.1

func (ni *NeuwerkInstance) GetBPFCollection() *bpf.Collection

GetBPFCollection returns the BPF map collection for test verification. Returns nil if BPF maps are not loaded yet.

func (*NeuwerkInstance) GetBpffsPath

func (ni *NeuwerkInstance) GetBpffsPath() string

GetBpffsPath returns the bpffs path for this instance.

func (*NeuwerkInstance) GetRootToken

func (ni *NeuwerkInstance) GetRootToken() string

GetRootToken returns the root admin JWT token for API authentication. Returns empty string if token derivation failed.

func (*NeuwerkInstance) GetStorageDir

func (ni *NeuwerkInstance) GetStorageDir() string

GetStorageDir returns the storage directory path for this instance. Used when restarting a node to preserve state.

func (*NeuwerkInstance) IsRunning

func (ni *NeuwerkInstance) IsRunning() bool

IsRunning checks if the instance is still running

func (*NeuwerkInstance) Stop

func (ni *NeuwerkInstance) Stop() error

Stop stops the Neuwerk instance and cleans up all resources

func (*NeuwerkInstance) StopForRestart

func (ni *NeuwerkInstance) StopForRestart() error

StopForRestart stops the Neuwerk instance but preserves storage for restart. Use this when testing node restart scenarios where state should be preserved.

func (*NeuwerkInstance) WaitForReady

func (ni *NeuwerkInstance) WaitForReady(timeout time.Duration) error

WaitForReady polls the /readyz endpoint until it returns HTTP 200 or timeout

type NeuwerkOptions

type NeuwerkOptions struct {
	PolicyFile         string        // Path to policy YAML file
	Peers              []string      // List of peer addresses for HA mode
	LicenseFile        string        // Path to license file (required for HA mode)
	PublicKeyFile      string        // Path to license public key file (for test licenses)
	BootstrapTokenFile string        // Path to bootstrap token file (enables TLS)
	CertDir            string        // Certificate storage directory (default /var/lib/neuwerk/certs)
	RaftBindAddr       string        // Raft listener address for bootstrap (e.g., "10.100.1.10:7000")
	OIDCConfigFile     string        // Path to OIDC configuration file for SSO (optional)
	StorageDir         string        // Existing storage directory to reuse (for restart scenarios)
	SkipBootstrap      bool          // Skip TLS bootstrap (certificates already exist from previous run)
	TunnelMode         string        // Tunnel protocol mode: "geneve" (AWS), "vxlan" (Azure), or "" (none)
	EnableAuth         bool          // Enable authentication (JWT required for API calls)
	GracePeriod        time.Duration // K8s pod IP removal grace period (default: 30s, use 2-3s for tests)
	RateLimitWindow    time.Duration // Rate limit window for auth endpoints (default: 60s, use 5s for tests)
}

NeuwerkOptions holds configuration for starting a Neuwerk instance

type SSEConnection

type SSEConnection struct {
	// contains filtered or unexported fields
}

SSEConnection represents a Server-Sent Events connection

func (*SSEConnection) Close

func (s *SSEConnection) Close() error

Close closes the SSE connection

func (*SSEConnection) ReadEvent

func (s *SSEConnection) ReadEvent(timeout time.Duration) (*SSEEvent, error)

ReadEvent reads the next SSE event from the connection Returns the event data or error (including timeout)

type SSEEvent

type SSEEvent struct {
	Data string
}

SSEEvent represents a parsed SSE event

type TestLicenseFiles

type TestLicenseFiles struct {
	LicenseFile   string
	PublicKeyFile string
}

TestLicenseFiles contains paths to both the license file and public key file

func CreateHALicenseFiles

func CreateHALicenseFiles(t interface{ Cleanup(func()) }) (*TestLicenseFiles, error)

CreateHALicenseFiles returns paths to HA-enabled test license files This is a compatibility wrapper - no longer generates keys at runtime

func CreateLicenseFilesWithoutHA

func CreateLicenseFilesWithoutHA(t interface{ Cleanup(func()) }) (*TestLicenseFiles, error)

CreateLicenseFilesWithoutHA returns paths to license files without HA feature This is a compatibility wrapper - no longer generates keys at runtime

func LoadAllFeaturesLicenseFiles

func LoadAllFeaturesLicenseFiles() *TestLicenseFiles

LoadAllFeaturesLicenseFiles returns paths to a license with all features enabled

func LoadExpiredLicenseFiles

func LoadExpiredLicenseFiles() *TestLicenseFiles

LoadExpiredLicenseFiles returns paths to an expired license (30 days ago)

func LoadExpiredLongAgoLicenseFiles

func LoadExpiredLongAgoLicenseFiles() *TestLicenseFiles

LoadExpiredLongAgoLicenseFiles returns paths to a license expired 1 year ago

func LoadExpiresSoonLicenseFiles

func LoadExpiresSoonLicenseFiles() *TestLicenseFiles

LoadExpiresSoonLicenseFiles returns paths to a license expiring in 3 days

func LoadGracePeriodLicenseFiles

func LoadGracePeriodLicenseFiles() *TestLicenseFiles

LoadGracePeriodLicenseFiles returns paths to a license in grace period (expired 5 days ago)

func LoadHALicenseFiles

func LoadHALicenseFiles() *TestLicenseFiles

LoadHALicenseFiles returns paths to a valid HA-enabled test license

func LoadKubernetesOnlyLicenseFiles

func LoadKubernetesOnlyLicenseFiles() *TestLicenseFiles

LoadKubernetesOnlyLicenseFiles returns paths to a license with only Kubernetes feature

func LoadNoHALicenseFiles

func LoadNoHALicenseFiles() *TestLicenseFiles

LoadNoHALicenseFiles returns paths to a license without HA feature

func LoadSingleNodeLicenseFiles

func LoadSingleNodeLicenseFiles() *TestLicenseFiles

LoadSingleNodeLicenseFiles returns paths to a license limited to 1 node

func LoadThreeNodeLicenseFiles

func LoadThreeNodeLicenseFiles() *TestLicenseFiles

LoadThreeNodeLicenseFiles returns paths to a license limited to 3 nodes

func LoadTrialLicenseFiles

func LoadTrialLicenseFiles() *TestLicenseFiles

LoadTrialLicenseFiles returns paths to a 14-day trial license

type TestModeConfig added in v1.6.2

type TestModeConfig struct {
	Mode        NetworkMode
	TunnelMode  string // "" for GCP ILB, "vxlan" for Azure GWLB
	VXLANPort   uint16 // VXLAN destination port (10800 for internal, 10801 for external)
	VXLANVNI    uint32 // VXLAN Network Identifier
	Description string // Human-readable description
}

TestModeConfig holds configuration for a specific network mode test

type TestNetwork

type TestNetwork struct {
	// Network namespaces
	NeuwerkNS  netns.NsHandle
	ClientNS   netns.NsHandle
	UpstreamNS netns.NsHandle

	// Network namespace names (for nsenter)
	NeuwerkNSName  string
	ClientNSName   string
	UpstreamNSName string

	// veth pairs
	NeuwerkIngressVeth *netlink.Veth
	NeuwerkEgressVeth  *netlink.Veth
	ClientVeth         *netlink.Veth
	UpstreamVeth       *netlink.Veth

	// IP addresses
	NeuwerkIngressIP net.IP
	NeuwerkEgressIP  net.IP
	ClientIP         net.IP
	UpstreamIP       net.IP

	// BPF filesystem mount point
	BPFFSPath string

	// Management bridge name (for multi-node HA tests)
	ManagementBridgeName string
	// contains filtered or unexported fields
}

TestNetwork represents an isolated test network using network namespaces

func SetupMultiNode

func SetupMultiNode(t interface{ Cleanup(func()) }, nodeCount int) []*TestNetwork

SetupMultiNode creates isolated network environments for multi-node HA tests

func SetupMultiNodeWithCleanup

func SetupMultiNodeWithCleanup(t testing.TB, nodeCount int) []*TestNetwork

SetupMultiNodeWithCleanup creates multiple test networks and registers cleanup automatically.

func SetupSingleNode

func SetupSingleNode(t interface{ Cleanup(func()) }) *TestNetwork

SetupSingleNode creates an isolated network environment for single-node tests Returns the test network and registers cleanup function

func SetupSingleNodeWithCleanup

func SetupSingleNodeWithCleanup(t testing.TB) *TestNetwork

SetupSingleNodeWithCleanup creates a test network and registers cleanup automatically. This is the recommended way to create a single-node test environment.

func (*TestNetwork) APIBaseURL

func (tn *TestNetwork) APIBaseURL() string

APIBaseURL returns the base URL for the Neuwerk API (HTTP on port 3000).

func (*TestNetwork) APIBaseURLHTTPS

func (tn *TestNetwork) APIBaseURLHTTPS() string

APIBaseURLHTTPS returns the base URL for the Neuwerk API over HTTPS (port 8443).

func (*TestNetwork) Cleanup

func (tn *TestNetwork) Cleanup()

Cleanup removes all network namespaces and resources

func (*TestNetwork) DNSServerAddr

func (tn *TestNetwork) DNSServerAddr() string

DNSServerAddr returns the address of the DNS server (Neuwerk ingress IP on port 53).

func (*TestNetwork) GetClientNS

func (tn *TestNetwork) GetClientNS() netns.NsHandle

GetClientNS returns the client namespace handle

func (*TestNetwork) GetNeuwerkNS

func (tn *TestNetwork) GetNeuwerkNS() netns.NsHandle

GetNeuwerkNS returns the Neuwerk namespace handle

func (*TestNetwork) GetUpstreamNS

func (tn *TestNetwork) GetUpstreamNS() netns.NsHandle

GetUpstreamNS returns the upstream namespace handle

func (*TestNetwork) HealthURL

func (tn *TestNetwork) HealthURL() string

HealthURL returns the URL for the health endpoint.

func (*TestNetwork) MetricsURL

func (tn *TestNetwork) MetricsURL() string

MetricsURL returns the URL for the metrics endpoint.

func (*TestNetwork) NATSAddr

func (tn *TestNetwork) NATSAddr() string

NATSAddr returns the address of the NATS server (Neuwerk ingress IP on port 3320).

func (*TestNetwork) RaftAddr

func (tn *TestNetwork) RaftAddr() string

RaftAddr returns the address for Raft communication (Neuwerk ingress IP on port 3322).

type VXLANClient

type VXLANClient struct {
	// contains filtered or unexported fields
}

VXLANClient can send VXLAN-encapsulated traffic for testing

func NewVXLANClient

func NewVXLANClient(ns netns.NsHandle, clientIP, tunnelSrcIP, tunnelDstIP net.IP, tunnelDstPort uint16, vni uint32) *VXLANClient

NewVXLANClient creates a new VXLAN test client

func (*VXLANClient) ConnectViaVXLAN

func (c *VXLANClient) ConnectViaVXLAN(innerDstIP string, innerDstPort int) error

ConnectViaVXLAN sends a VXLAN-encapsulated TCP SYN to test policy enforcement The inner packet is a TCP connection to the specified address Returns nil if the connection succeeds (traffic allowed), error if blocked

type VXLANPacket

type VXLANPacket struct {
	Timestamp time.Time
	VNI       int
	SourceIP  string
	DestIP    string
}

VXLANPacket represents a captured VXLAN packet

type VXLANValidator

type VXLANValidator struct {
	// contains filtered or unexported fields
}

VXLANValidator provides VXLAN packet inspection helpers

func NewVXLANValidator

func NewVXLANValidator(client *AzureClient) *VXLANValidator

func (*VXLANValidator) CaptureVXLANPackets

func (v *VXLANValidator) CaptureVXLANPackets(ctx context.Context, vmName string, port int, duration time.Duration) ([]VXLANPacket, error)

CaptureVXLANPackets captures VXLAN packets on specified port using tcpdump

func (*VXLANValidator) VerifyVXLANEncapsulation

func (v *VXLANValidator) VerifyVXLANEncapsulation(ctx context.Context, vmName string) error

VerifyVXLANEncapsulation validates VXLAN traffic exists on both tunnels

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL