Skip to main content
Version: 1.x

Configuration Reference

Praman uses a Zod-validated configuration system. All fields have defaults — an empty {} is valid.

Config File​

Create praman.config.ts in your project root:

import { defineConfig } from 'playwright-praman';

export default defineConfig({
logLevel: 'info',
ui5WaitTimeout: 30_000,
controlDiscoveryTimeout: 10_000,
interactionStrategy: 'ui5-native',
discoveryStrategies: ['direct-id', 'recordreplay'],
auth: {
strategy: 'basic',
baseUrl: process.env.SAP_CLOUD_BASE_URL!,
username: process.env.SAP_CLOUD_USERNAME!,
password: process.env.SAP_CLOUD_PASSWORD!,
client: '100',
language: 'EN',
},
ai: {
provider: 'azure-openai',
apiKey: process.env.AZURE_OPENAI_KEY,
endpoint: process.env.AZURE_OPENAI_ENDPOINT,
deployment: 'gpt-4o',
},
telemetry: {
openTelemetry: true,
exporter: 'otlp',
endpoint: 'http://localhost:4318',
serviceName: 'sap-e2e-tests',
metrics: true,
},
});

Top-Level Options​

FieldTypeDefaultDescription
logLevel'error' | 'warn' | 'info' | 'debug' | 'verbose''info'Pino log level
ui5WaitTimeoutnumber30_000Max ms to wait for UI5 stability
controlDiscoveryTimeoutnumber10_000Max ms for control discovery
interactionStrategy'ui5-native' | 'dom-first' | 'opa5''ui5-native'How to interact with controls
discoveryStrategiesstring[]['direct-id', 'recordreplay']Ordered strategy chain
skipStabilityWaitbooleanfalseSkip waitForUI5Stable(), use brief DOM settle
preferVisibleControlsbooleantruePrefer visible controls over hidden ones
ignoreAutoWaitUrlsstring[][]Additional URL patterns to block (WalkMe, analytics)
skipPostFillWaitbooleanfalseSkip automatic waitForUI5() after fill() calls

Auth Sub-Schema​

FieldTypeDefaultDescription
strategy'btp-saml' | 'basic' | 'office365' | 'custom''basic'Authentication strategy
baseUrlstring (URL)requiredSAP system base URL
usernamestring—Login username
passwordstring—Login password
clientstring'100'SAP client number
languagestring'EN'SAP logon language

AI Sub-Schema​

FieldTypeDefaultDescription
provider'azure-openai' | 'openai' | 'anthropic''azure-openai'LLM provider
apiKeystring—OpenAI / Azure OpenAI API key
anthropicApiKeystring—Anthropic API key (separate for security)
modelstring—Model name (e.g., 'gpt-4o', 'claude-sonnet-4-6')
temperaturenumber0.3LLM temperature (0-2)
maxTokensnumber—Max tokens per response
endpointstring (URL)—Azure OpenAI resource endpoint
deploymentstring—Azure OpenAI deployment name
apiVersionstring—Azure API version

Telemetry Sub-Schema​

Telemetry is disabled by default with zero overhead. See Telemetry Setup for the full guide.

FieldTypeDefaultDescription
openTelemetrybooleanfalseEnable OpenTelemetry tracing
exporter'otlp' | 'azure-monitor' | 'jaeger''otlp'Trace exporter
endpointstring (URL)—OTLP/Jaeger endpoint URL (required when enabled)
serviceNamestring'playwright-praman'Service name in traces
protocol'http' | 'grpc''http'OTel transport protocol
metricsbooleanfalseEnable metric counters and histograms
batchTimeoutnumber5000Span batch export timeout (ms)
maxQueueSizenumber2048Max queued spans before dropping
resourceAttributesRecord<string, string>{}Additional OTel resource attributes
connectionStringstring—Azure Monitor connection string (required for Azure)

Selectors Sub-Schema​

FieldTypeDefaultDescription
defaultTimeoutnumber10_000Default selector timeout (ms)
preferVisibleControlsbooleantruePrefer visible controls
skipStabilityWaitbooleanfalseSkip stability wait for selectors

OPA5 Sub-Schema​

FieldTypeDefaultDescription
interactionTimeoutnumber5_000OPA5 interaction timeout (ms)
autoWaitbooleantrueAuto-wait for OPA5 readiness
debugbooleanfalseEnable OPA5 debug mode

Timeout Precedence​

When multiple timeout values could apply, Praman uses this precedence (highest first):

  1. Per-call options — ui5.control({ id: 'x' }, { timeout: 5000 })
  2. Top-level config — controlDiscoveryTimeout: 10000
  3. Selectors section — selectors.defaultTimeout: 10000 (fallback if top-level not set)
  4. Built-in default — 10,000ms

We recommend using only controlDiscoveryTimeout at the top level. selectors.defaultTimeout exists for backward compatibility and will be removed in a future major version.

For details on the 3-tier stability wait system, see Stability & Timing.

Environment Variable Overrides​

Top-level config fields can be overridden via environment variables:

Environment VariableConfig Field
PRAMAN_LOG_LEVELlogLevel
PRAMAN_UI5_WAIT_TIMEOUTui5WaitTimeout
PRAMAN_CONTROL_DISCOVERY_TIMEOUTcontrolDiscoveryTimeout
PRAMAN_INTERACTION_STRATEGYinteractionStrategy
PRAMAN_SKIP_STABILITY_WAITskipStabilityWait

General config precedence (highest to lowest):

  1. Per-call options (e.g., ui5.control({ ... }, { timeout: 5000 }))
  2. Environment variable overrides
  3. Environment-specific config (via defineConfig second argument)
  4. Top-level config
  5. Schema defaults

Multi-Environment Configuration​

defineConfig() accepts an optional second parameter for environment-specific overrides:

// praman.config.ts
import { defineConfig } from 'playwright-praman';

export default defineConfig(
{
logLevel: 'info',
auth: {
strategy: 'form',
baseUrl: 'https://dev.example.com',
},
},
{
ci: {
logLevel: 'error',
auth: {
strategy: 'basic',
baseUrl: 'https://ci.example.com',
},
},
staging: {
auth: {
baseUrl: 'https://staging.example.com',
},
},
},
);

Set PRAMAN_ENV or NODE_ENV to select the environment. PRAMAN_ENV takes precedence over NODE_ENV. When neither is set, the base config is used unchanged.

# Use CI config
PRAMAN_ENV=ci npx playwright test

# Falls back to NODE_ENV
NODE_ENV=staging npx playwright test
Shallow merge

Environment overrides are shallow-merged. For nested objects like auth, provide the complete sub-object in the override.

Complete playwright.config.ts Example​

import { defineConfig, devices } from '@playwright/test';

export default defineConfig({
testDir: './tests/e2e',
timeout: 120_000,
expect: { timeout: 10_000 },
fullyParallel: false,
retries: 1,
workers: 1,
reporter: [
['html', { open: 'never' }],
['playwright-praman/reporters', { type: 'compliance', outputDir: 'reports' }],
],
use: {
baseURL: process.env.SAP_CLOUD_BASE_URL,
trace: 'on-first-retry',
screenshot: 'only-on-failure',
video: 'retain-on-failure',
},
projects: [
{
name: 'setup',
testMatch: /auth-setup\.ts/,
teardown: 'teardown',
},
{
name: 'teardown',
testMatch: /auth-teardown\.ts/,
},
{
name: 'chromium',
dependencies: ['setup'],
use: {
...devices['Desktop Chrome'],
storageState: '.auth/sap-session.json',
},
},
],
});

Validation​

Config is validated with Zod at load time. Invalid config fails fast:

import { loadConfig } from 'playwright-praman';

const config = await loadConfig();
// Throws ConfigError with ERR_CONFIG_INVALID if schema fails
// Returns Readonly<PramanConfig> — deeply frozen, mutation throws