or run

npx @tessl/cli init
Log in

Version

Tile

Overview

Evals

Files

Files

docs

annotations.mdbuiltins.mddescriptors.mdencoding.mdindex.mdmodules.mdserializers.md

annotations.mddocs/

0

# Serialization Annotations

1

2

Comprehensive reference for all kotlinx.serialization annotations that control serialization behavior.

3

4

## Core Annotations

5

6

### @Serializable

7

8

The primary annotation that marks a class as serializable and instructs the compiler plugin to generate a serializer.

9

10

```kotlin

11

@MustBeDocumented

12

@Target(AnnotationTarget.PROPERTY, AnnotationTarget.CLASS, AnnotationTarget.TYPE)

13

public annotation class Serializable(

14

val with: KClass<out KSerializer<*>> = KSerializer::class

15

)

16

```

17

{ .api }

18

19

**Usage:**

20

21

```javascript

22

// Basic serializable class

23

@Serializable

24

class User {

25

constructor(name, age) {

26

this.name = name;

27

this.age = age;

28

}

29

}

30

31

// With custom serializer

32

@Serializable(UserCustomSerializer::class)

33

class User {

34

constructor(name, age) {

35

this.name = name;

36

this.age = age;

37

}

38

}

39

```

40

41

**Parameters:**

42

- `with`: Specifies a custom serializer class to use instead of the generated one

43

44

### @SerialName

45

46

Overrides the default name used in the serialized form for classes or properties.

47

48

```kotlin

49

@MustBeDocumented

50

@Target(AnnotationTarget.PROPERTY, AnnotationTarget.CLASS)

51

public annotation class SerialName(val value: String)

52

```

53

{ .api }

54

55

**Usage:**

56

57

```javascript

58

@Serializable

59

@SerialName("UserProfile")

60

class User {

61

@SerialName("user_name")

62

name;

63

64

@SerialName("user_age")

65

age;

66

67

constructor(name, age) {

68

this.name = name;

69

this.age = age;

70

}

71

}

72

73

// Serialized as: {"user_name": "John", "user_age": 30}

74

```

75

76

## Field Control Annotations

77

78

### @Required

79

80

Marks a property as required during deserialization, even if it has a default value.

81

82

```kotlin

83

@SerialInfo

84

@Target(AnnotationTarget.PROPERTY)

85

annotation class Required

86

```

87

{ .api }

88

89

**Usage:**

90

91

```javascript

92

@Serializable

93

class Config {

94

@Required

95

apiKey = "default"; // Must be present in JSON even though it has default

96

97

timeout = 5000; // Optional, will use default if missing

98

99

constructor(apiKey = "default", timeout = 5000) {

100

this.apiKey = apiKey;

101

this.timeout = timeout;

102

}

103

}

104

105

// This will throw MissingFieldException:

106

// {"timeout": 10000} // Missing required apiKey

107

108

// This works:

109

// {"apiKey": "abc123", "timeout": 10000}

110

```

111

112

### @Transient

113

114

Excludes a property from serialization entirely.

115

116

```kotlin

117

@Target(AnnotationTarget.PROPERTY)

118

annotation class Transient

119

```

120

{ .api }

121

122

**Usage:**

123

124

```javascript

125

@Serializable

126

class User {

127

name;

128

age;

129

130

@Transient

131

password; // Never serialized

132

133

@Transient

134

temporaryData; // Runtime-only data

135

136

constructor(name, age, password = null, temporaryData = null) {

137

this.name = name;

138

this.age = age;

139

this.password = password;

140

this.temporaryData = temporaryData;

141

}

142

}

143

144

// Only serializes: {"name": "John", "age": 30}

145

```

146

147

### @EncodeDefault

148

149

Controls serialization of properties with default values (Experimental API).

150

151

```kotlin

152

@ExperimentalSerializationApi

153

@SerialInfo

154

@Target(AnnotationTarget.PROPERTY, AnnotationTarget.CLASS)

155

annotation class EncodeDefault(val mode: Mode = Mode.ALWAYS) {

156

enum class Mode { ALWAYS, NEVER }

157

}

158

```

159

{ .api }

160

161

**Usage:**

162

163

```javascript

164

@Serializable

165

class Settings {

166

@EncodeDefault(EncodeDefault.Mode.ALWAYS)

167

theme = "dark"; // Always included, even when default

168

169

@EncodeDefault(EncodeDefault.Mode.NEVER)

170

debug = false; // Never included when it's the default value

171

172

language = "en"; // Format-dependent behavior

173

174

constructor(theme = "dark", debug = false, language = "en") {

175

this.theme = theme;

176

this.debug = debug;

177

this.language = language;

178

}

179

}

180

```

181

182

## Contextual Serialization Annotations

183

184

### @Contextual

185

186

Instructs the plugin to use contextual serializer lookup for this property.

187

188

```kotlin

189

@Target(AnnotationTarget.PROPERTY, AnnotationTarget.TYPE)

190

annotation class Contextual

191

```

192

{ .api }

193

194

**Usage:**

195

196

```javascript

197

@Serializable

198

class Event {

199

name;

200

201

@Contextual

202

timestamp; // Serializer looked up from SerializersModule at runtime

203

204

constructor(name, timestamp) {

205

this.name = name;

206

this.timestamp = timestamp;

207

}

208

}

209

210

// Configure contextual serializer in module

211

const module = SerializersModule {

212

contextual(Date, DateSerializer)

213

};

214

```

215

216

### @UseContextualSerialization

217

218

File-level annotation that enables contextual serialization for specified classes.

219

220

```kotlin

221

@Target(AnnotationTarget.FILE)

222

annotation class UseContextualSerialization(

223

vararg val forClasses: KClass<*>

224

)

225

```

226

{ .api }

227

228

**Usage:**

229

230

```javascript

231

@file:UseContextualSerialization(Date::class, BigDecimal::class)

232

233

// Now all Date and BigDecimal properties automatically use contextual lookup

234

@Serializable

235

class Transaction {

236

timestamp; // Automatically contextual (Date)

237

amount; // Automatically contextual (BigDecimal)

238

239

constructor(timestamp, amount) {

240

this.timestamp = timestamp;

241

this.amount = amount;

242

}

243

}

244

```

245

246

### @UseSerializers

247

248

File-level annotation to add serializers to the resolving process.

249

250

```kotlin

251

@Target(AnnotationTarget.FILE)

252

annotation class UseSerializers(

253

vararg val serializerClasses: KClass<out KSerializer<*>>

254

)

255

```

256

{ .api }

257

258

**Usage:**

259

260

```javascript

261

@file:UseSerializers(DateSerializer::class, UUIDSerializer::class)

262

263

// These serializers are now available for automatic resolution

264

@Serializable

265

class Document {

266

id; // Will use UUIDSerializer if id is UUID

267

createdAt; // Will use DateSerializer if createdAt is Date

268

269

constructor(id, createdAt) {

270

this.id = id;

271

this.createdAt = createdAt;

272

}

273

}

274

```

275

276

## Polymorphic Serialization

277

278

### @Polymorphic

279

280

Instructs the plugin to use polymorphic serialization for this property.

281

282

```kotlin

283

@Target(AnnotationTarget.PROPERTY, AnnotationTarget.TYPE)

284

annotation class Polymorphic

285

```

286

{ .api }

287

288

**Usage:**

289

290

```javascript

291

@Serializable

292

abstract class Shape {

293

abstract area;

294

}

295

296

@Serializable

297

class Circle extends Shape {

298

constructor(radius) {

299

super();

300

this.radius = radius;

301

this.area = Math.PI * radius * radius;

302

}

303

}

304

305

@Serializable

306

class Rectangle extends Shape {

307

constructor(width, height) {

308

super();

309

this.width = width;

310

this.height = height;

311

this.area = width * height;

312

}

313

}

314

315

@Serializable

316

class Drawing {

317

@Polymorphic

318

shapes; // Array of Shape - actual type determined at runtime

319

320

constructor(shapes) {

321

this.shapes = shapes;

322

}

323

}

324

```

325

326

## Experimental Annotations

327

328

### @MetaSerializable

329

330

Meta-annotation for creating custom serializable annotations (Experimental).

331

332

```kotlin

333

@ExperimentalSerializationApi

334

@Target(AnnotationTarget.ANNOTATION_CLASS)

335

annotation class MetaSerializable

336

```

337

{ .api }

338

339

**Usage:**

340

341

```javascript

342

@MetaSerializable

343

@Target(AnnotationTarget.CLASS)

344

annotation class JsonSerializable

345

346

// Custom annotation that implies @Serializable

347

@JsonSerializable

348

class User {

349

constructor(name) {

350

this.name = name;

351

}

352

}

353

```

354

355

### @Serializer

356

357

Instructs the plugin to create a serializer for the specified class (Experimental).

358

359

```kotlin

360

@ExperimentalSerializationApi

361

@Target(AnnotationTarget.CLASS)

362

annotation class Serializer(val forClass: KClass<*>)

363

```

364

{ .api }

365

366

**Usage:**

367

368

```javascript

369

// Generate serializer for external class you can't modify

370

@Serializer(ExternalLibraryClass::class)

371

object ExternalClassSerializer : KSerializer<ExternalLibraryClass> {

372

// Implementation generated by plugin

373

}

374

```

375

376

### @KeepGeneratedSerializer

377

378

Keeps the generated serializer accessible when a custom serializer is specified (Experimental).

379

380

```kotlin

381

@ExperimentalSerializationApi

382

@Target(AnnotationTarget.CLASS)

383

annotation class KeepGeneratedSerializer

384

```

385

{ .api }

386

387

**Usage:**

388

389

```javascript

390

@Serializable(CustomUserSerializer::class)

391

@KeepGeneratedSerializer

392

class User {

393

constructor(name, age) {

394

this.name = name;

395

this.age = age;

396

}

397

398

// Both CustomUserSerializer and generated serializer are available

399

static generatedSerializer = /* generated serializer */;

400

}

401

402

// Access both serializers

403

const customSer = User.serializer(); // Returns CustomUserSerializer

404

const generatedSer = User.generatedSerializer; // Returns generated serializer

405

```

406

407

## Meta-Annotations

408

409

### @SerialInfo

410

411

Base meta-annotation for all serialization-related annotations.

412

413

```kotlin

414

@ExperimentalSerializationApi

415

@Target(AnnotationTarget.ANNOTATION_CLASS)

416

annotation class SerialInfo

417

```

418

{ .api }

419

420

### @InheritableSerialInfo

421

422

Meta-annotation for annotations that should be inherited by subclasses.

423

424

```kotlin

425

@ExperimentalSerializationApi

426

@Target(AnnotationTarget.ANNOTATION_CLASS)

427

annotation class InheritableSerialInfo

428

```

429

{ .api }

430

431

**Usage:**

432

433

```javascript

434

@InheritableSerialInfo

435

@Target(AnnotationTarget.CLASS)

436

annotation class ApiVersion(val version: String)

437

438

@ApiVersion("v1")

439

@Serializable

440

abstract class BaseEntity {

441

id;

442

}

443

444

// Inherits @ApiVersion("v1") annotation

445

@Serializable

446

class User extends BaseEntity {

447

constructor(id, name) {

448

super();

449

this.id = id;

450

this.name = name;

451

}

452

}

453

```

454

455

## Annotation Combinations

456

457

Annotations can be combined for sophisticated serialization control:

458

459

```javascript

460

@Serializable

461

class UserProfile {

462

@SerialName("user_id")

463

@Required

464

id; // Custom name and always required

465

466

@SerialName("display_name")

467

name; // Custom name, optional

468

469

@Transient

470

password; // Never serialized

471

472

@Contextual

473

@SerialName("last_login")

474

lastLogin; // Custom name with contextual serializer

475

476

@EncodeDefault(EncodeDefault.Mode.NEVER)

477

theme = "default"; // Don't encode when default

478

479

constructor(id, name, password = null, lastLogin = null, theme = "default") {

480

this.id = id;

481

this.name = name;

482

this.password = password;

483

this.lastLogin = lastLogin;

484

this.theme = theme;

485

}

486

}

487

```

488

489

## JavaScript-Specific Notes

490

491

### Enum Annotations

492

493

On JavaScript, enum classes require explicit `@Serializable` annotation:

494

495

```javascript

496

@Serializable

497

enum class Status {

498

ACTIVE, INACTIVE, PENDING

499

}

500

501

@Serializable

502

class Task {

503

status; // Status enum

504

505

constructor(status) {

506

this.status = status;

507

}

508

}

509

```

510

511

### Type Safety

512

513

TypeScript provides compile-time validation of annotation usage:

514

515

```typescript

516

interface SerializableClass {

517

// Ensures proper annotation usage at compile time

518

readonly serializer: () => KSerializer<this>;

519

}

520

521

@Serializable

522

class User implements SerializableClass {

523

// TypeScript enforces correct implementation

524

}

525

```

526

527

All annotations work consistently across different serialization formats (JSON, ProtoBuf, CBOR, etc.), providing format-independent serialization control.