Developers working with Ktor must enforce explicit authentication, rigorous input validation, and secure cryptographic and session management practices across client and server boundaries. The framework provides flexible building blocks for routing, serialization, and connection handling, but does not enforce secure defaults for tokens, session storage, or path resolution out of the box. Security-sensitive surfaces include authentication providers, static content routing, URL parsers, and client engine configurations, all of which must be configured to fail closed upon validation failures or malformed inputs.
Essential implementation rules
Configure Mandatory Validation and Handlers for Authentication Providers
Always supply mandatory validation functions, signature verifiers, and claim checks for basic, digest, API key, and JWT authentication blocks to ensure missing or invalid credentials properly trigger unauthenticated challenge responses. Set up explicit fallback blocks on OAuth providers and return null when credentials fail validation requirements.
Protect Routing Endpoints and Avoid Loose SkipWhen Conditions
Enclose all sensitive routes and WebSocket connection handshakes within authenticate blocks referencing valid providers to reject unauthenticated requests before executing route logic. Avoid relying on loose request parameters inside skipWhen conditions; instead, define public routes entirely outside authentication routing blocks.
Enforce Strict TLS Transport, Hostname Verification, and Mutual TLS
Rely on Ktor’s built-in hostname verification functions to strictly validate domain labels, ignore trailing dots, and reject overly broad wildcards. Configure explicit key stores, trust managers for mutual TLS, and default server trust challenge handling to prevent certificate bypasses.
Validate Incoming Request Payloads and Configure RequestValidation
Install the RequestValidation plugin and define rules using validate<T> or filter blocks to enforce strict input boundaries and type constraints. Pair this with StatusPages to catch validation exceptions and return appropriate HTTP error responses.
Prevent Directory Traversal Using Static Content Routing
Utilize Ktor’s built-in static content DSL functions such as staticFiles, staticResources, and staticFileSystem, or call call.resolveResource(), to automatically validate request paths, block parent directory relative paths (..), URL-encoded dots, and backslashes.
Enforce Server-Side Session Storage and Secure Cookie Flags
Supply a server-side SessionStorage implementation when configuring sessions containing sensitive user data, and set cookie.secure = true and cookie.httpOnly = true. Explicitly clear server session state using call.sessions.clear<SessionType>() and invalidate client session cookies with maxAge = -1 on logout.
Use Secure Cryptographic Algorithms, Nonces, and Disable Backward Compatibility
Specify strong algorithms like DigestAlgorithm.SHA_256 for HTTP Digest authentication instead of legacy defaults. Keep backwardCompatibleRead set to false in session encryption transformers after migration, and utilize generateNonceBlocking() to create secure random tokens.
Configure CSRF Protection and Origin Validation Rules
Explicitly configure allowed origins, host matching rules, or header validation checks using allowOrigin, originMatchesHost, or checkHeader within the CSRF plugin block to protect state-modifying endpoints such as POST or PUT.
Neutralize Special Characters in LDAP and URL Inputs
Pass dynamic user input strings through ldapEscape before constructing query filters or Distinguished Names. Use parseUrl() instead of direct Url constructor calls when processing untrusted URL strings to handle malformed specifications safely.
Enforce Resource Exhaustion Limits on WebSockets, Redirects, and Queries
Set explicit maximum frame sizes on WebSocket sessions using maxFrameSize, bound automatic redirect loops by configuring maxSendCount on the HttpSend plugin, and specify an explicit limit parameter when manually parsing raw query strings.
Sanitize Sensitive Headers and Configuration Bindings
Use sanitizeHeader when configuring the Logging plugin to redact sensitive headers like Authorization or custom API keys before writing to log files. Ensure configuration files avoid recursive reference loops and that all referenced environment variables are defined prior to application launch.
Supply Matching Delegates and Enforce Protocol Integrity in Engine Configurations
When configuring a custom NSURLSession for the Darwin client engine using usePreconfiguredSession, supply both the session and its matching KtorNSURLSessionDelegate instance to prevent initialization exceptions. Validate server responses for expected HTTP status codes and content types when establishing server-sent events streams.
ktor: All Security Cards
Approximately 4,892 tokens
On this card
Category: api contract misuse
Supply Matching Delegates When Configuring Custom NSURLSession in Darwin Engine
Use when
Configuring a custom NSURLSession for the Ktor Darwin client engine using DarwinClientEngineConfig.usePreconfiguredSession.
Secure rules
Rule 1: Always supply both the custom NSURLSession and its matching KtorNSURLSessionDelegate instance to prevent initialization exceptions and broken request handling.
When configuring a custom NSURLSession using DarwinClientEngineConfig.usePreconfiguredSession, you must provide the session along with its corresponding KtorNSURLSessionDelegate instance. Passing a session without its matching delegate causes an IllegalArgumentException at initialization and disrupts Ktor’s internal pipeline and delegation mechanism for network events and authentication challenges.
Implement Mandatory Validation and Fallback Handlers for Authentication Providers
Use when
When configuring authentication plugins such as basic, digest, API key, and OAuth in Ktor applications to verify credentials and handle failures.
Secure rules
Rule 1: Configure mandatory validation functions and return null when credentials fail verification checks.
Always supply validate functions and digest providers for basic, digest, and API key authentication blocks so missing or invalid credentials properly trigger unauthenticated challenge responses.
Rule 2: Configure explicit fallback handlers for OAuth authentication flows to process errors gracefully.
Set up explicit fallback blocks on OAuth authentication providers to handle authorization errors or failed token exchanges safely without exposing internal exceptions.
Protect Routing Endpoints and WebSocket Handshakes with Authentication Blocks
Use when
When securing HTTP routes, API key protected endpoints, or WebSocket connection handshakes in Ktor applications.
Secure rules
Rule 1: Enclose protected routes and WebSocket endpoints within authenticate blocks referencing valid providers.
Wrap all sensitive routes and WebSocket connections inside an authenticate block to ensure that unauthenticated requests are rejected before executing route logic.
install(Authentication) { apiKey("api-key") { validate { key -> if (key == "valid-key") UserIdPrincipal("user") else null } }}routing { authenticate("api-key") { get("/authenticated") { val principal = call.principal<UserIdPrincipal>() call.respond(principal!!) } }}
Category: configuration source integrity
Prevent configuration failure by validating structural integrity and environment bindings
Use when
When loading configuration files and setting environment properties in Ktor applications.
Secure rules
Rule 1: Avoid recursive reference loops in YAML configuration files.
Ensure self-referencing property aliases in YAML configurations do not introduce circular references, as Ktor’s YamlConfig will raise an ApplicationConfigurationException to block invalid configuration loading.
Rule 2: Ensure all referenced environment variables are defined prior to application launch.
Verify that all environment variables referenced in YAML configuration files are explicitly defined in the runtime environment to prevent initialization failures when YamlConfig fails fast.
ktor: deployment: port: $PORT
Rule 3: Safely read optional properties and deserialize typed configurations from ApplicationConfig.
Use propertyOrNull to access optional key-value properties or getAs to map typed configuration objects safely instead of throwing unhandled exceptions.
val config = MapApplicationConfig( "host" to "0.0.0.0", "port" to "8080")val salt: String? = config.propertyOrNull("auth.salt")?.getString()val rootConfig: RootConfig? = config.getAs<RootConfig>()
Rule 4: Ensure all dynamically referenced dependency factory functions and classes are publicly accessible.
Verify that functions and classes loaded via external application configuration files are publicly accessible to avoid DependencyInjectionException during dependency injection initialization.
fun createBankService(): BankService = BankServiceImpl()
Category: cryptography
Use secure cryptographic algorithms and parameters for encryption and token generation
Use when
When configuring cryptographic mechanisms such as HTTP digest authentication, session encryption transformers, and random nonce generation within Ktor applications.
Avoid legacy MD5 defaults in HTTP Digest authentication by specifying strong algorithms like DigestAlgorithm.SHA_256 or DigestAlgorithm.SHA_512_256 to prevent collision and offline cracking attacks.
Rule 2: Disable session encryption backward compatibility after migration
Keep backwardCompatibleRead set to false in SessionTransportTransformerEncrypt during normal operations to prevent older payload formats and legacy cryptographic signature layouts from being accepted.
Rule 3: Generate cryptographically secure nonces using Ktor utilities
Utilize generateNonceBlocking() or generateNonce() to generate secure random strings, session identifiers, and tokens across platforms to prevent predictable values.
Configure Origin and Header Validation in Ktor CSRF Plugin
Use when
When implementing cross-site request forgery protection for state-changing HTTP requests using Ktor’s CSRF plugin.
Secure rules
Rule 1: Explicitly configure allowed origins and header validation rules when installing the CSRF plugin to prevent rejecting valid production requests or leaving endpoints vulnerable.
Use allowOrigin, originMatchesHost, or checkHeader within the CSRF plugin configuration block to validate incoming state-changing requests. Ensure proper predicate checks or trusted origins are defined to protect state-modifying endpoints such as POST or PUT while safely ignoring safe methods.
Prevent directory traversal by using Ktor static content routing and resource resolution APIs
Use when
Serving static files, directories, or embedded classpath resources from user-supplied paths or URL parameters.
Secure rules
Rule 1: Use built-in static content DSL and resource resolution functions to automatically validate request paths and prevent directory traversal.
Utilize Ktor’s built-in static content DSL such as staticFiles, staticResources, and staticFileSystem, or call call.resolveResource() to serve files safely. These functions automatically validate request paths, block parent directory relative paths (..), URL-encoded dots (%2e%2e), or backslashes, and ensure that path traversal attempts cannot escape the defined static root directory.
When constructing dynamic LDAP queries or Distinguished Names using untrusted user inputs in Ktor server applications.
Secure rules
Rule 1: Neutralize special LDAP characters in user-supplied strings before building query filters or Distinguished Names.
Pass all dynamic user input strings through ldapEscape to ensure meta-characters are safely escaped and interpreter syntax neutralization is maintained.
val safeUsername = ldapEscape(userInput)val userDn = "cn=$safeUsername,ou=users,dc=example,dc=com"
Category: input contract definition
Validate incoming request payloads with RequestValidation and StatusPages
Use when
When validating incoming request bodies and handling malformed input data in Ktor applications.
Secure rules
Rule 1: Configure Ktor request validation rules to reject malformed input payloads before application processing.
Install the RequestValidation plugin and define rules using validate<T> or filter blocks to enforce strict input boundaries and type constraints. Pair this with StatusPages to catch RequestValidationException and return an appropriate HTTP error response.
install(RequestValidation) { validate<String> { body -> if (!body.startsWith("+")) { ValidationResult.Invalid("String must start with '+'") } else { ValidationResult.Valid } }}install(StatusPages) { exception<RequestValidationException> { call, cause -> call.respond(HttpStatusCode.BadRequest, cause.reasons.joinToString(", ")) }}
Category: input interpretation safety
Canonicalize and parse untrusted URL and header strings safely
Use when
When validating, parsing, or normalizing untrusted URL strings, authentication headers, or cookie values to ensure security decisions rely on unambiguous interpretations.
Secure rules
Rule 1: Use parseUrl instead of direct Url constructor calls when processing untrusted URL strings.
Invoke parseUrl() to evaluate untrusted or user-supplied URL inputs. This approach gracefully returns null when encountering malformed specifications or invalid encoding, preventing uncaught runtime exceptions and potential parsing bypasses during input validation.
Rule 2: Normalize internationalized and multi-byte domain names using Ktor URL builders.
Convert URLs containing internationalized domain names or non-ASCII characters using Ktor’s Url builder and toNSUrl(). This ensures Punycode encoding is applied correctly to hostnames and percent-encoding is applied to query parameters before native platform calls.
val safeUrl = Url("http://привет.привет/echo_query?привет")val nsUrl = safeUrl.toNSUrl()
Rule 3: Encode cookie values instead of using RAW encoding
Do not render data that may contain untrusted characters with CookieEncoding.RAW. Use CookieEncoding.URI_ENCODING, which is also Ktor’s default, so the cookie value is encoded when the Set-Cookie header is rendered. Treat values returned by parseServerSetCookieHeader as decoded application data rather than as sanitized header text.
Enforce Protocol and Content-Type Validation in SSE and WebSocket Sessions
Use when
Developing client applications using Ktor HTTP, SSE, or WebSocket engines where protocol framing, content types, and connection state must be strictly enforced.
Secure rules
Rule 1: Validate that server responses enforce expected HTTP status codes and content types when establishing server-sent events streams.
Catch SSEClientException when initializing SSE sessions to handle invalid content types or non-200 responses properly rather than parsing incorrect payloads.
Rule 2: Avoid bypassing TLS certificate validation in production client configurations.
Do not use custom authentication challenge handlers that automatically trust any server certificate without evaluation. Use standard default handling for server trust challenges to allow the operating system to perform full certificate chain validation.
Enforce Frame Size Limits on WebSockets and Bounded Redirections in Ktor Clients
Use when
Configuring Ktor client plugins such as WebSockets and HttpRedirect to handle remote network streams and untrusted server interactions safely.
Secure rules
Rule 1: Configure explicit maximum frame sizes on WebSocket sessions to prevent memory exhaustion.
When installing the WebSockets plugin in the Ktor client, set maxFrameSize to an appropriate threshold to prevent malicious or malfunctioning remote endpoints from sending oversized frames that consume excessive heap memory.
val client = HttpClient { install(WebSockets) { maxFrameSize = 1024 * 1024 // Set maximum frame size to 1MB }}
Rule 2: Bound automatic redirect loops in HTTP client configurations
When automatic redirect handling is enabled (the default, or via the HttpRedirect plugin), bound the number of requests that may be sent during a single call—including those caused by redirects—by configuring maxSendCount on the always-installed HttpSend plugin. Exceeding the limit throws SendCountExceedException so that cyclic redirect responses fail fast rather than consuming memory and network resources indefinitely. The default value is 20.
Rule 3: Specify an explicit limit parameter when parsing raw query strings.
When parsing raw query strings manually using parseQueryString, specify an explicit limit parameter to cap the maximum number of query key-value pairs processed and avoid high memory consumption.
val parameters = parseQueryString(rawQuery, startIndex = 0, limit = 100)
Category: secret handling
Sanitize Sensitive Headers During Client Logging
Use when
Configuring client logging for Ktor HTTP requests and responses that contain sensitive authentication headers or tokens.
Secure rules
Rule 1: Sanitize sensitive HTTP headers to prevent credential leakage into log files.
When configuring the Logging plugin with header or full logging levels, use sanitizeHeader to redact sensitive headers like Authorization or custom secret headers before they are written to logs.
Avoid Authentication Bypass via Loose SkipWhen Conditions
Use when
When configuring authentication providers and routing paths where certain requests need to be treated as public or excluded from authentication requirements.
Secure rules
Rule 1: Avoid relying on skipWhen conditions with untrusted request parameters to bypass authentication checks.
Do not use loose or untrusted request inputs such as request URIs or headers inside skipWhen conditions within authentication provider configurations because this can bypass authentication completely. Instead, define public routes entirely outside the authenticate routing DSL block.
Clear session state and invalidate cookies securely on logout
Use when
Handling user logout actions and terminating active session states in Ktor server applications.
Secure rules
Rule 1: Explicitly clear server-side session state and invalidate client session cookies during user logout.
Always clear session state explicitly using call.sessions.clear<SessionType>() when executing logout actions, and ensure session cookie configurations correctly preserve security flags while handling termination. When invalidating cookies via call.response.cookies.append, supply maxAge = -1 or 0 alongside matching domain and path attributes so the browser successfully drops the token.
Enforce secure transport attributes and server-side storage for sensitive session cookies
Use when
Configuring session storage backends, cookie flags, and secure transport mechanisms.
Secure rules
Rule 1: Configure server-side session storage and enforce strict secure flags on session cookies to prevent exposure.
Supply a server-side SessionStorage implementation when configuring sessions containing sensitive user data so that only a random identifier is sent to the client. Set cookie.secure = true and appropriate SameSite policies to restrict transmission to encrypted connections and prevent interception or cross-site leakage.
Validate session identifiers and authenticate session principals on incoming requests
Use when
Processing incoming requests and verifying session authenticity in protected routes.
Secure rules
Rule 1: Verify that session lookup and authentication hooks successfully resolve valid, non-null session principals.
Configure session authentication with an explicit validate block that checks session validity, and always check for null when fetching session data via call.sessions.get<T>(). Unrecognized or expired session identifiers should immediately trigger invalidation or return unauthorized responses.
install(Sessions) { cookie<UserSession>("SESSION_ID", storage)}routing { get("/protected") { val session = call.sessions.get<UserSession>() if (session == null) { call.respond(HttpStatusCode.Unauthorized, "Invalid or expired session") return@get } call.respondText("Welcome, ${session.userId}") }}
Supply Matching Delegates When Configuring Custom NSURLSession in Darwin Engine
Approximately 260 tokens
Use when
Configuring a custom NSURLSession for the Ktor Darwin client engine using DarwinClientEngineConfig.usePreconfiguredSession.
Secure rules
Rule 1: Always supply both the custom NSURLSession and its matching KtorNSURLSessionDelegate instance to prevent initialization exceptions and broken request handling.
When configuring a custom NSURLSession using DarwinClientEngineConfig.usePreconfiguredSession, you must provide the session along with its corresponding KtorNSURLSessionDelegate instance. Passing a session without its matching delegate causes an IllegalArgumentException at initialization and disrupts Ktor’s internal pipeline and delegation mechanism for network events and authentication challenges.
Implement Mandatory Validation and Fallback Handlers for Authentication Providers
Use when
When configuring authentication plugins such as basic, digest, API key, and OAuth in Ktor applications to verify credentials and handle failures.
Secure rules
Rule 1: Configure mandatory validation functions and return null when credentials fail verification checks.
Always supply validate functions and digest providers for basic, digest, and API key authentication blocks so missing or invalid credentials properly trigger unauthenticated challenge responses.
Rule 2: Configure explicit fallback handlers for OAuth authentication flows to process errors gracefully.
Set up explicit fallback blocks on OAuth authentication providers to handle authorization errors or failed token exchanges safely without exposing internal exceptions.
Protect Routing Endpoints and WebSocket Handshakes with Authentication Blocks
Use when
When securing HTTP routes, API key protected endpoints, or WebSocket connection handshakes in Ktor applications.
Secure rules
Rule 1: Enclose protected routes and WebSocket endpoints within authenticate blocks referencing valid providers.
Wrap all sensitive routes and WebSocket connections inside an authenticate block to ensure that unauthenticated requests are rejected before executing route logic.
install(Authentication) { apiKey("api-key") { validate { key -> if (key == "valid-key") UserIdPrincipal("user") else null } }}routing { authenticate("api-key") { get("/authenticated") { val principal = call.principal<UserIdPrincipal>() call.respond(principal!!) } }}
Prevent configuration failure by validating structural integrity and environment bindings
Approximately 392 tokens
Use when
When loading configuration files and setting environment properties in Ktor applications.
Secure rules
Rule 1: Avoid recursive reference loops in YAML configuration files.
Ensure self-referencing property aliases in YAML configurations do not introduce circular references, as Ktor’s YamlConfig will raise an ApplicationConfigurationException to block invalid configuration loading.
Rule 2: Ensure all referenced environment variables are defined prior to application launch.
Verify that all environment variables referenced in YAML configuration files are explicitly defined in the runtime environment to prevent initialization failures when YamlConfig fails fast.
ktor: deployment: port: $PORT
Rule 3: Safely read optional properties and deserialize typed configurations from ApplicationConfig.
Use propertyOrNull to access optional key-value properties or getAs to map typed configuration objects safely instead of throwing unhandled exceptions.
val config = MapApplicationConfig( "host" to "0.0.0.0", "port" to "8080")val salt: String? = config.propertyOrNull("auth.salt")?.getString()val rootConfig: RootConfig? = config.getAs<RootConfig>()
Rule 4: Ensure all dynamically referenced dependency factory functions and classes are publicly accessible.
Verify that functions and classes loaded via external application configuration files are publicly accessible to avoid DependencyInjectionException during dependency injection initialization.
fun createBankService(): BankService = BankServiceImpl()
Use secure cryptographic algorithms and parameters for encryption and token generation
Approximately 452 tokens
Use when
When configuring cryptographic mechanisms such as HTTP digest authentication, session encryption transformers, and random nonce generation within Ktor applications.
Avoid legacy MD5 defaults in HTTP Digest authentication by specifying strong algorithms like DigestAlgorithm.SHA_256 or DigestAlgorithm.SHA_512_256 to prevent collision and offline cracking attacks.
Rule 2: Disable session encryption backward compatibility after migration
Keep backwardCompatibleRead set to false in SessionTransportTransformerEncrypt during normal operations to prevent older payload formats and legacy cryptographic signature layouts from being accepted.
Rule 3: Generate cryptographically secure nonces using Ktor utilities
Utilize generateNonceBlocking() or generateNonce() to generate secure random strings, session identifiers, and tokens across platforms to prevent predictable values.
Configure Origin and Header Validation in Ktor CSRF Plugin
Approximately 220 tokens
Use when
When implementing cross-site request forgery protection for state-changing HTTP requests using Ktor’s CSRF plugin.
Secure rules
Rule 1: Explicitly configure allowed origins and header validation rules when installing the CSRF plugin to prevent rejecting valid production requests or leaving endpoints vulnerable.
Use allowOrigin, originMatchesHost, or checkHeader within the CSRF plugin configuration block to validate incoming state-changing requests. Ensure proper predicate checks or trusted origins are defined to protect state-modifying endpoints such as POST or PUT while safely ignoring safe methods.
Prevent directory traversal by using Ktor static content routing and resource resolution APIs
Approximately 208 tokens
Use when
Serving static files, directories, or embedded classpath resources from user-supplied paths or URL parameters.
Secure rules
Rule 1: Use built-in static content DSL and resource resolution functions to automatically validate request paths and prevent directory traversal.
Utilize Ktor’s built-in static content DSL such as staticFiles, staticResources, and staticFileSystem, or call call.resolveResource() to serve files safely. These functions automatically validate request paths, block parent directory relative paths (..), URL-encoded dots (%2e%2e), or backslashes, and ensure that path traversal attempts cannot escape the defined static root directory.
When constructing dynamic LDAP queries or Distinguished Names using untrusted user inputs in Ktor server applications.
Secure rules
Rule 1: Neutralize special LDAP characters in user-supplied strings before building query filters or Distinguished Names.
Pass all dynamic user input strings through ldapEscape to ensure meta-characters are safely escaped and interpreter syntax neutralization is maintained.
val safeUsername = ldapEscape(userInput)val userDn = "cn=$safeUsername,ou=users,dc=example,dc=com"
Validate incoming request payloads with RequestValidation and StatusPages
Approximately 229 tokens
Use when
When validating incoming request bodies and handling malformed input data in Ktor applications.
Secure rules
Rule 1: Configure Ktor request validation rules to reject malformed input payloads before application processing.
Install the RequestValidation plugin and define rules using validate<T> or filter blocks to enforce strict input boundaries and type constraints. Pair this with StatusPages to catch RequestValidationException and return an appropriate HTTP error response.
install(RequestValidation) { validate<String> { body -> if (!body.startsWith("+")) { ValidationResult.Invalid("String must start with '+'") } else { ValidationResult.Valid } }}install(StatusPages) { exception<RequestValidationException> { call, cause -> call.respond(HttpStatusCode.BadRequest, cause.reasons.joinToString(", ")) }}
Canonicalize and parse untrusted URL and header strings safely
Approximately 504 tokens
Use when
When validating, parsing, or normalizing untrusted URL strings, authentication headers, or cookie values to ensure security decisions rely on unambiguous interpretations.
Secure rules
Rule 1: Use parseUrl instead of direct Url constructor calls when processing untrusted URL strings.
Invoke parseUrl() to evaluate untrusted or user-supplied URL inputs. This approach gracefully returns null when encountering malformed specifications or invalid encoding, preventing uncaught runtime exceptions and potential parsing bypasses during input validation.
Rule 2: Normalize internationalized and multi-byte domain names using Ktor URL builders.
Convert URLs containing internationalized domain names or non-ASCII characters using Ktor’s Url builder and toNSUrl(). This ensures Punycode encoding is applied correctly to hostnames and percent-encoding is applied to query parameters before native platform calls.
val safeUrl = Url("http://привет.привет/echo_query?привет")val nsUrl = safeUrl.toNSUrl()
Rule 3: Encode cookie values instead of using RAW encoding
Do not render data that may contain untrusted characters with CookieEncoding.RAW. Use CookieEncoding.URI_ENCODING, which is also Ktor’s default, so the cookie value is encoded when the Set-Cookie header is rendered. Treat values returned by parseServerSetCookieHeader as decoded application data rather than as sanitized header text.
Enforce Protocol and Content-Type Validation in SSE and WebSocket Sessions
Approximately 301 tokens
Use when
Developing client applications using Ktor HTTP, SSE, or WebSocket engines where protocol framing, content types, and connection state must be strictly enforced.
Secure rules
Rule 1: Validate that server responses enforce expected HTTP status codes and content types when establishing server-sent events streams.
Catch SSEClientException when initializing SSE sessions to handle invalid content types or non-200 responses properly rather than parsing incorrect payloads.
Rule 2: Avoid bypassing TLS certificate validation in production client configurations.
Do not use custom authentication challenge handlers that automatically trust any server certificate without evaluation. Use standard default handling for server trust challenges to allow the operating system to perform full certificate chain validation.
Enforce Frame Size Limits on WebSockets and Bounded Redirections in Ktor Clients
Approximately 404 tokens
Use when
Configuring Ktor client plugins such as WebSockets and HttpRedirect to handle remote network streams and untrusted server interactions safely.
Secure rules
Rule 1: Configure explicit maximum frame sizes on WebSocket sessions to prevent memory exhaustion.
When installing the WebSockets plugin in the Ktor client, set maxFrameSize to an appropriate threshold to prevent malicious or malfunctioning remote endpoints from sending oversized frames that consume excessive heap memory.
val client = HttpClient { install(WebSockets) { maxFrameSize = 1024 * 1024 // Set maximum frame size to 1MB }}
Rule 2: Bound automatic redirect loops in HTTP client configurations
When automatic redirect handling is enabled (the default, or via the HttpRedirect plugin), bound the number of requests that may be sent during a single call—including those caused by redirects—by configuring maxSendCount on the always-installed HttpSend plugin. Exceeding the limit throws SendCountExceedException so that cyclic redirect responses fail fast rather than consuming memory and network resources indefinitely. The default value is 20.
Rule 3: Specify an explicit limit parameter when parsing raw query strings.
When parsing raw query strings manually using parseQueryString, specify an explicit limit parameter to cap the maximum number of query key-value pairs processed and avoid high memory consumption.
val parameters = parseQueryString(rawQuery, startIndex = 0, limit = 100)
Sanitize Sensitive Headers During Client Logging
Approximately 198 tokens
Use when
Configuring client logging for Ktor HTTP requests and responses that contain sensitive authentication headers or tokens.
Secure rules
Rule 1: Sanitize sensitive HTTP headers to prevent credential leakage into log files.
When configuring the Logging plugin with header or full logging levels, use sanitizeHeader to redact sensitive headers like Authorization or custom secret headers before they are written to logs.
Avoid Authentication Bypass via Loose SkipWhen Conditions
Approximately 194 tokens
Use when
When configuring authentication providers and routing paths where certain requests need to be treated as public or excluded from authentication requirements.
Secure rules
Rule 1: Avoid relying on skipWhen conditions with untrusted request parameters to bypass authentication checks.
Do not use loose or untrusted request inputs such as request URIs or headers inside skipWhen conditions within authentication provider configurations because this can bypass authentication completely. Instead, define public routes entirely outside the authenticate routing DSL block.
Clear session state and invalidate cookies securely on logout
Approximately 560 tokens
Use when
Handling user logout actions and terminating active session states in Ktor server applications.
Secure rules
Rule 1: Explicitly clear server-side session state and invalidate client session cookies during user logout.
Always clear session state explicitly using call.sessions.clear<SessionType>() when executing logout actions, and ensure session cookie configurations correctly preserve security flags while handling termination. When invalidating cookies via call.response.cookies.append, supply maxAge = -1 or 0 alongside matching domain and path attributes so the browser successfully drops the token.
Enforce secure transport attributes and server-side storage for sensitive session cookies
Use when
Configuring session storage backends, cookie flags, and secure transport mechanisms.
Secure rules
Rule 1: Configure server-side session storage and enforce strict secure flags on session cookies to prevent exposure.
Supply a server-side SessionStorage implementation when configuring sessions containing sensitive user data so that only a random identifier is sent to the client. Set cookie.secure = true and appropriate SameSite policies to restrict transmission to encrypted connections and prevent interception or cross-site leakage.
Validate session identifiers and authenticate session principals on incoming requests
Use when
Processing incoming requests and verifying session authenticity in protected routes.
Secure rules
Rule 1: Verify that session lookup and authentication hooks successfully resolve valid, non-null session principals.
Configure session authentication with an explicit validate block that checks session validity, and always check for null when fetching session data via call.sessions.get<T>(). Unrecognized or expired session identifiers should immediately trigger invalidation or return unauthorized responses.
install(Sessions) { cookie<UserSession>("SESSION_ID", storage)}routing { get("/protected") { val session = call.sessions.get<UserSession>() if (session == null) { call.respond(HttpStatusCode.Unauthorized, "Invalid or expired session") return@get } call.respondText("Welcome, ${session.userId}") }}