0
# Compression Conditions
1
2
Compression conditions determine when responses should be compressed based on content type, size, and custom predicates. Conditions can be applied globally to all encoders or specifically to individual encoders.
3
4
## Condition Interface
5
6
```kotlin { .api }
7
interface ConditionsHolderBuilder {
8
val conditions: MutableList<ApplicationCall.(OutgoingContent) -> Boolean>
9
}
10
```
11
12
Both `CompressionConfig` and `CompressionEncoderBuilder` implement this interface, allowing conditions at both global and per-encoder levels.
13
14
## Built-in Condition Functions
15
16
### Custom Predicates
17
18
```kotlin { .api }
19
fun ConditionsHolderBuilder.condition(predicate: ApplicationCall.(OutgoingContent) -> Boolean)
20
```
21
22
Add custom logic to determine when compression should be applied:
23
24
```kotlin
25
install(Compression) {
26
// Global condition - applies to all encoders
27
condition { call, content ->
28
// Only compress responses for specific routes
29
call.request.uri.startsWith("/api/")
30
}
31
32
gzip {
33
// Encoder-specific condition
34
condition { call, content ->
35
// Don't compress responses for mobile clients
36
call.request.headers["User-Agent"]?.contains("Mobile") != true
37
}
38
}
39
}
40
```
41
42
### Minimum Size
43
44
```kotlin { .api }
45
fun ConditionsHolderBuilder.minimumSize(minSize: Long)
46
```
47
48
Only compress content that meets the minimum size threshold:
49
50
```kotlin
51
install(Compression) {
52
// Global minimum size
53
minimumSize(1024) // Only compress responses >= 1KB
54
55
gzip {
56
// Override for gzip - compress smaller JSON responses
57
minimumSize(200)
58
matchContentType(ContentType.Application.Json)
59
}
60
}
61
```
62
63
### Content Type Matching
64
65
```kotlin { .api }
66
fun ConditionsHolderBuilder.matchContentType(vararg mimeTypes: ContentType)
67
```
68
69
Only compress responses with matching content types:
70
71
```kotlin
72
install(Compression) {
73
matchContentType(
74
ContentType.Text.Plain,
75
ContentType.Text.Html,
76
ContentType.Application.Json,
77
ContentType.Application.JavaScript
78
)
79
}
80
```
81
82
### Content Type Exclusion
83
84
```kotlin { .api }
85
fun ConditionsHolderBuilder.excludeContentType(vararg mimeTypes: ContentType)
86
```
87
88
Exclude specific content types from compression:
89
90
```kotlin
91
install(Compression) {
92
// Exclude media files and streams
93
excludeContentType(
94
ContentType.Video.Any,
95
ContentType.Image.Any,
96
ContentType.Audio.Any,
97
ContentType.Text.EventStream,
98
ContentType.MultiPart.Any
99
)
100
}
101
```
102
103
## Default Conditions
104
105
When no conditions are explicitly configured, the plugin applies sensible defaults:
106
107
```kotlin
108
// Default exclusions applied automatically
109
excludeContentType(
110
ContentType.Video.Any,
111
ContentType.Image.JPEG,
112
ContentType.Image.PNG,
113
ContentType.Audio.Any,
114
ContentType.MultiPart.Any,
115
ContentType.Text.EventStream
116
)
117
minimumSize(200) // DEFAULT_MINIMAL_COMPRESSION_SIZE
118
```
119
120
## Condition Evaluation
121
122
Conditions are evaluated in the following order:
123
124
1. **Global conditions** (on `CompressionConfig`) - must all return `true`
125
2. **Encoder-specific conditions** (on `CompressionEncoderBuilder`) - must all return `true`
126
3. **Built-in checks** - content not already encoded, not SSE response, etc.
127
128
If any condition returns `false`, compression is skipped for that request.
129
130
## Advanced Condition Examples
131
132
### Dynamic Content Type Checking
133
134
```kotlin
135
install(Compression) {
136
condition { call, content ->
137
val contentType = content.contentType ?:
138
call.response.headers[HttpHeaders.ContentType]?.let { ContentType.parse(it) }
139
140
contentType?.let {
141
it.match(ContentType.Application.Json) ||
142
it.match(ContentType.Text.Any)
143
} ?: false
144
}
145
}
146
```
147
148
### Request Header Based Conditions
149
150
```kotlin
151
install(Compression) {
152
condition { call, _ ->
153
// Only compress for API versions that support it
154
val apiVersion = call.request.headers["API-Version"]
155
apiVersion != null && apiVersion >= "2.0"
156
}
157
158
condition { call, _ ->
159
// Skip compression for debug requests
160
call.request.queryParameters["debug"] != "true"
161
}
162
}
163
```
164
165
### Response Size Based Logic
166
167
```kotlin
168
install(Compression) {
169
condition { _, content ->
170
when (val length = content.contentLength) {
171
null -> true // Unknown length - allow compression
172
in 0..100 -> false // Too small
173
in 101..1000 -> content.contentType?.match(ContentType.Application.Json) == true
174
else -> true // Large content - always compress
175
}
176
}
177
}
178
```
179
180
## Condition Interaction
181
182
When both global and encoder-specific conditions are present:
183
184
```kotlin
185
install(Compression) {
186
// Global: must be JSON or text
187
matchContentType(ContentType.Application.Json, ContentType.Text.Any)
188
minimumSize(100)
189
190
gzip {
191
// Additional encoder requirement: minimum 500 bytes for gzip
192
minimumSize(500)
193
// Inherits global content type matching
194
}
195
196
deflate {
197
// Uses global conditions only (JSON/text, >= 100 bytes)
198
}
199
}
200
```
201
202
In this example:
203
- `deflate` compresses JSON/text >= 100 bytes
204
- `gzip` compresses JSON/text >= 500 bytes (more restrictive)