Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion src/cli.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ import * as cliModule from './cli';
import {
resolveCopilotApiKey,
resolveCopilotApiRouting,
testHelpers as copilotApiResolverTestHelpers,
copilotApiResolverTestHelpers,
} from './copilot-api-resolver';
import { redactSecrets } from './redact-secrets';

Expand Down
2 changes: 1 addition & 1 deletion src/container-lifecycle.ts
Original file line number Diff line number Diff line change
Expand Up @@ -466,4 +466,4 @@ function resetAgentExternallyKilled(): void {

/** @internal Exposed only for unit tests — not part of the public API. */
// ts-prune-ignore-next
export const testHelpers = { isAgentExternallyKilled, resetAgentExternallyKilled };
export const containerLifecycleTestHelpers = { isAgentExternallyKilled, resetAgentExternallyKilled };
4 changes: 2 additions & 2 deletions src/copilot-api-resolver.test.ts
Original file line number Diff line number Diff line change
@@ -1,13 +1,13 @@
import {
resolveCopilotApiKey,
resolveCopilotApiRouting,
testHelpers,
copilotApiResolverTestHelpers,
} from './copilot-api-resolver';

const {
deriveCopilotApiTargetFromProviderBaseUrl,
deriveCopilotApiBasePathFromProviderBaseUrl,
} = testHelpers;
} = copilotApiResolverTestHelpers;

describe('resolveCopilotApiKey', () => {
it('should return COPILOT_API_KEY when set', () => {
Expand Down
2 changes: 1 addition & 1 deletion src/copilot-api-resolver.ts
Original file line number Diff line number Diff line change
Expand Up @@ -85,7 +85,7 @@ export function resolveCopilotApiRouting(

/** @internal Exposed only for unit tests — not part of the public API. */
// ts-prune-ignore-next
export const testHelpers = {
export const copilotApiResolverTestHelpers = {
deriveCopilotApiTargetFromProviderBaseUrl,
deriveCopilotApiBasePathFromProviderBaseUrl,
};
12 changes: 6 additions & 6 deletions src/docker-manager-lifecycle.test.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import { startContainers, runAgentCommand, fastKillAgentContainer, setAwfDockerHost, stopContainers, getLocalDockerEnv } from './docker-manager';
import { testHelpers as lifecycleTestHelpers } from './container-lifecycle';
import { containerLifecycleTestHelpers } from './container-lifecycle';
import { AGENT_CONTAINER_NAME } from './constants';
import { logger } from './logger';
import * as fs from 'fs';
Expand Down Expand Up @@ -371,7 +371,7 @@ describe('docker-manager lifecycle', () => {
describe('fastKillAgentContainer', () => {
beforeEach(() => {
jest.clearAllMocks();
lifecycleTestHelpers.resetAgentExternallyKilled();
containerLifecycleTestHelpers.resetAgentExternallyKilled();
});

it('should call docker stop with default 3-second timeout', async () => {
Expand Down Expand Up @@ -407,16 +407,16 @@ describe('docker-manager lifecycle', () => {
it('should set the externally-killed flag', async () => {
mockExecaFn.mockResolvedValueOnce({ stdout: '', stderr: '', exitCode: 0 } as any);

expect(lifecycleTestHelpers.isAgentExternallyKilled()).toBe(false);
expect(containerLifecycleTestHelpers.isAgentExternallyKilled()).toBe(false);
await fastKillAgentContainer();
expect(lifecycleTestHelpers.isAgentExternallyKilled()).toBe(true);
expect(containerLifecycleTestHelpers.isAgentExternallyKilled()).toBe(true);
});

it('should set the externally-killed flag even when docker stop fails', async () => {
mockExecaFn.mockRejectedValueOnce(new Error('docker not found'));

await fastKillAgentContainer();
expect(lifecycleTestHelpers.isAgentExternallyKilled()).toBe(true);
expect(containerLifecycleTestHelpers.isAgentExternallyKilled()).toBe(true);
});
});

Expand Down Expand Up @@ -512,7 +512,7 @@ describe('docker-manager lifecycle', () => {
beforeEach(() => {
testDir = fs.mkdtempSync(path.join(os.tmpdir(), 'awf-test-'));
jest.clearAllMocks();
lifecycleTestHelpers.resetAgentExternallyKilled();
containerLifecycleTestHelpers.resetAgentExternallyKilled();
});

afterEach(() => {
Expand Down
22 changes: 11 additions & 11 deletions src/docker-manager-utils.test.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import {
testHelpers,
hostEnvTestHelpers,
getSafeHostUid,
getSafeHostGid,
getRealUserHome,
Expand Down Expand Up @@ -33,31 +33,31 @@ describe('docker-manager utilities', () => {
describe('subnetsOverlap', () => {

it('should detect overlapping subnets with same CIDR', () => {
expect(testHelpers.subnetsOverlap('172.30.0.0/24', '172.30.0.0/24')).toBe(true);
expect(hostEnvTestHelpers.subnetsOverlap('172.30.0.0/24', '172.30.0.0/24')).toBe(true);
});

it('should detect non-overlapping subnets', () => {
expect(testHelpers.subnetsOverlap('172.30.0.0/24', '172.31.0.0/24')).toBe(false);
expect(testHelpers.subnetsOverlap('192.168.1.0/24', '192.168.2.0/24')).toBe(false);
expect(hostEnvTestHelpers.subnetsOverlap('172.30.0.0/24', '172.31.0.0/24')).toBe(false);
expect(hostEnvTestHelpers.subnetsOverlap('192.168.1.0/24', '192.168.2.0/24')).toBe(false);
});

it('should detect when smaller subnet is inside larger subnet', () => {
expect(testHelpers.subnetsOverlap('172.16.0.0/16', '172.16.5.0/24')).toBe(true);
expect(testHelpers.subnetsOverlap('172.16.5.0/24', '172.16.0.0/16')).toBe(true);
expect(hostEnvTestHelpers.subnetsOverlap('172.16.0.0/16', '172.16.5.0/24')).toBe(true);
expect(hostEnvTestHelpers.subnetsOverlap('172.16.5.0/24', '172.16.0.0/16')).toBe(true);
});

it('should detect partial overlap', () => {
expect(testHelpers.subnetsOverlap('172.30.0.0/23', '172.30.1.0/24')).toBe(true);
expect(hostEnvTestHelpers.subnetsOverlap('172.30.0.0/23', '172.30.1.0/24')).toBe(true);
});

it('should handle Docker default bridge network', () => {
expect(testHelpers.subnetsOverlap('172.17.0.0/16', '172.17.5.0/24')).toBe(true);
expect(testHelpers.subnetsOverlap('172.17.0.0/16', '172.18.0.0/16')).toBe(false);
expect(hostEnvTestHelpers.subnetsOverlap('172.17.0.0/16', '172.17.5.0/24')).toBe(true);
expect(hostEnvTestHelpers.subnetsOverlap('172.17.0.0/16', '172.18.0.0/16')).toBe(false);
});

it('should handle /32 (single host) networks', () => {
expect(testHelpers.subnetsOverlap('192.168.1.1/32', '192.168.1.1/32')).toBe(true);
expect(testHelpers.subnetsOverlap('192.168.1.1/32', '192.168.1.2/32')).toBe(false);
expect(hostEnvTestHelpers.subnetsOverlap('192.168.1.1/32', '192.168.1.1/32')).toBe(true);
expect(hostEnvTestHelpers.subnetsOverlap('192.168.1.1/32', '192.168.1.2/32')).toBe(false);
});
});

Expand Down
2 changes: 1 addition & 1 deletion src/host-env.ts
Original file line number Diff line number Diff line change
Expand Up @@ -49,7 +49,7 @@ function subnetsOverlap(subnet1: string, subnet2: string): boolean {

/** @internal Exposed only for unit tests — not part of the public API. */
// ts-prune-ignore-next
export const testHelpers = { subnetsOverlap };
export const hostEnvTestHelpers = { subnetsOverlap };

/**
* SSL configuration for Docker Compose (when SSL Bump is enabled)
Expand Down
4 changes: 2 additions & 2 deletions src/host-iptables-cleanup.test.ts
Original file line number Diff line number Diff line change
@@ -1,9 +1,9 @@
import { execaResult, mockedExeca, setupHostIptablesTestSuite } from './test-helpers/host-iptables-test-setup';
import { cleanupHostIptables, setupHostIptables } from './host-iptables';
import { testHelpers } from './host-iptables-shared';
import { iptablesSharedTestHelpers } from './host-iptables-shared';

describe('host-iptables (cleanup)', () => {
setupHostIptablesTestSuite(testHelpers.resetIpv6State);
setupHostIptablesTestSuite(iptablesSharedTestHelpers.resetIpv6State);

describe('cleanupHostIptables', () => {
it('should flush and delete both FW_WRAPPER and FW_WRAPPER_V6 chains', async () => {
Expand Down
4 changes: 2 additions & 2 deletions src/host-iptables-doh.test.ts
Original file line number Diff line number Diff line change
@@ -1,9 +1,9 @@
import { execaResult, mockedExeca, setupHostIptablesTestSuite } from './test-helpers/host-iptables-test-setup';
import { setupHostIptables } from './host-iptables';
import { testHelpers } from './host-iptables-shared';
import { iptablesSharedTestHelpers } from './host-iptables-shared';

describe('host-iptables (doh)', () => {
setupHostIptablesTestSuite(testHelpers.resetIpv6State);
setupHostIptablesTestSuite(iptablesSharedTestHelpers.resetIpv6State);

describe('setupHostIptables with DoH proxy', () => {
it('should add HTTPS ACCEPT rule for DoH proxy when dohProxyIp is provided', async () => {
Expand Down
4 changes: 2 additions & 2 deletions src/host-iptables-host-access.test.ts
Original file line number Diff line number Diff line change
@@ -1,9 +1,9 @@
import { mockedExeca, setupDefaultIptablesMocks, setupHostIptablesTestSuite } from './test-helpers/host-iptables-test-setup';
import { HostAccessConfig, setupHostIptables } from './host-iptables';
import { testHelpers } from './host-iptables-shared';
import { iptablesSharedTestHelpers } from './host-iptables-shared';

describe('host-iptables (host access)', () => {
setupHostIptablesTestSuite(testHelpers.resetIpv6State);
setupHostIptablesTestSuite(iptablesSharedTestHelpers.resetIpv6State);

describe('setupHostIptables with host access', () => {
it('should add gateway ACCEPT rules when hostAccess is enabled', async () => {
Expand Down
8 changes: 4 additions & 4 deletions src/host-iptables-network.test.ts
Original file line number Diff line number Diff line change
@@ -1,12 +1,12 @@
import { execaResult, mockedExeca, setupHostIptablesTestSuite } from './test-helpers/host-iptables-test-setup';
import { testHelpers as networkTestHelpers } from './host-iptables-network';
import { iptablesNetworkTestHelpers } from './host-iptables-network';
import { ensureFirewallNetwork } from './host-iptables';
import { testHelpers } from './host-iptables-shared';
import { iptablesSharedTestHelpers } from './host-iptables-shared';

const { cleanupFirewallNetwork } = networkTestHelpers;
const { cleanupFirewallNetwork } = iptablesNetworkTestHelpers;

describe('host-iptables (network)', () => {
setupHostIptablesTestSuite(testHelpers.resetIpv6State);
setupHostIptablesTestSuite(iptablesSharedTestHelpers.resetIpv6State);

describe('ensureFirewallNetwork', () => {
it('should return network config when network already exists', async () => {
Expand Down
2 changes: 1 addition & 1 deletion src/host-iptables-network.ts
Original file line number Diff line number Diff line change
Expand Up @@ -64,4 +64,4 @@ async function cleanupFirewallNetwork(): Promise<void> {
}

/** @internal Exposed for testing only */
export const testHelpers = { cleanupFirewallNetwork };
export const iptablesNetworkTestHelpers = { cleanupFirewallNetwork };
4 changes: 2 additions & 2 deletions src/host-iptables-setup.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,13 +2,13 @@ import { API_PROXY_PORTS } from './types';
import { execaError, execaResult, mockedExeca, setupDefaultIptablesMocks, setupHostIptablesTestSuite } from './test-helpers/host-iptables-test-setup';
import { isValidPortSpec } from './host-iptables-rules';
import { setupHostIptables } from './host-iptables';
import { testHelpers } from './host-iptables-shared';
import { iptablesSharedTestHelpers } from './host-iptables-shared';

// setupHostIptables intentionally allows the inclusive min:max API proxy port window.
const apiProxyPortRange = `${Math.min(...Object.values(API_PROXY_PORTS))}:${Math.max(...Object.values(API_PROXY_PORTS))}`;

describe('host-iptables (setup)', () => {
setupHostIptablesTestSuite(testHelpers.resetIpv6State);
setupHostIptablesTestSuite(iptablesSharedTestHelpers.resetIpv6State);

describe('setupHostIptables', () => {
it('should throw error if iptables permission denied', async () => {
Expand Down
4 changes: 2 additions & 2 deletions src/host-iptables-shared.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -7,12 +7,12 @@ import {
getDockerBridgeGateway,
getNetworkBridgeName,
isIp6tablesAvailable,
testHelpers,
iptablesSharedTestHelpers,
} from './host-iptables-shared';
import { logger } from './logger';

describe('host-iptables-shared', () => {
setupHostIptablesTestSuite(testHelpers.resetIpv6State);
setupHostIptablesTestSuite(iptablesSharedTestHelpers.resetIpv6State);

describe('cleanupChain', () => {
it('removes matching DOCKER-USER references in reverse order before deleting the chain', async () => {
Expand Down
2 changes: 1 addition & 1 deletion src/host-iptables-shared.ts
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@ function resetIpv6State(): void {

/** @internal Exposed only for unit tests — not part of the public API. */
// ts-prune-ignore-next
export const testHelpers = { resetIpv6State };
export const iptablesSharedTestHelpers = { resetIpv6State };

/**
* Gets the bridge interface name for the firewall network
Expand Down
10 changes: 5 additions & 5 deletions src/logs/log-discovery.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ import * as os from 'os';
import {
discoverLogSources,
selectMostRecent,
testHelpers,
logDiscoveryTestHelpers,
validateSource,
listLogSources,
} from './log-discovery';
Expand Down Expand Up @@ -42,7 +42,7 @@ describe('log-discovery', () => {
it('should return true when container is running', async () => {
mockedExeca.mockResolvedValue({ stdout: 'awf-squid', stderr: '' } as never);

const result = await testHelpers.isContainerRunning('awf-squid');
const result = await logDiscoveryTestHelpers.isContainerRunning('awf-squid');

expect(result).toBe(true);
expect(mockedExeca).toHaveBeenCalledWith('docker', [
Expand All @@ -57,23 +57,23 @@ describe('log-discovery', () => {
it('should return false when container is not running', async () => {
mockedExeca.mockResolvedValue({ stdout: '', stderr: '' } as never);

const result = await testHelpers.isContainerRunning('awf-squid');
const result = await logDiscoveryTestHelpers.isContainerRunning('awf-squid');

expect(result).toBe(false);
});

it('should return false when container name does not match exactly', async () => {
mockedExeca.mockResolvedValue({ stdout: 'awf-squid-old', stderr: '' } as never);

const result = await testHelpers.isContainerRunning('awf-squid');
const result = await logDiscoveryTestHelpers.isContainerRunning('awf-squid');

expect(result).toBe(false);
});

it('should return false when docker command fails', async () => {
mockedExeca.mockRejectedValue(new Error('Docker not available'));

const result = await testHelpers.isContainerRunning('awf-squid');
const result = await logDiscoveryTestHelpers.isContainerRunning('awf-squid');

expect(result).toBe(false);
});
Expand Down
2 changes: 1 addition & 1 deletion src/logs/log-discovery.ts
Original file line number Diff line number Diff line change
Expand Up @@ -165,7 +165,7 @@ async function isContainerRunning(containerName: string): Promise<boolean> {

/** @internal Exposed only for unit tests — not part of the public API. */
// ts-prune-ignore-next
export const testHelpers = { isContainerRunning };
export const logDiscoveryTestHelpers = { isContainerRunning };

/**
* Validates and creates a LogSource from a user-specified path or "running" keyword
Expand Down
Loading