Type-safe builders help you create complex objects step-by-step with clear rules. They make your code easier to read and safer by catching mistakes early.
Building blocks of type-safe builders in Kotlin
class Builder { fun part(block: PartBuilder.() -> Unit) { /*...*/ } fun build(): Result { /*...*/ } } class PartBuilder { fun setProperty(value: Any) { /*...*/ } } fun buildObject(block: Builder.() -> Unit): Result { val builder = Builder() builder.block() return builder.build() }
The builder class defines how to add parts and build the final object.
The block parameter uses a lambda with receiver to allow clean syntax inside the builder.
class MealBuilder { private val items = mutableListOf<String>() fun addItem(item: String) { items.add(item) } fun build() = items.joinToString(", ") } fun meal(block: MealBuilder.() -> Unit): String { val builder = MealBuilder() builder.block() return builder.build() }
val myMeal = meal { addItem("Burger") addItem("Fries") addItem("Soda") } println(myMeal)
This program builds a simple HTML page using type-safe builders for <html>, <head>, and <body> sections. It shows how to organize code clearly and safely.
class HtmlBuilder { private val children = mutableListOf<String>() fun head(block: HeadBuilder.() -> Unit) { val headBuilder = HeadBuilder() headBuilder.block() children.add("<head>${headBuilder.build()}</head>") } fun body(block: BodyBuilder.() -> Unit) { val bodyBuilder = BodyBuilder() bodyBuilder.block() children.add("<body>${bodyBuilder.build()}</body>") } fun build() = "<html>" + children.joinToString("") + "</html>" } class HeadBuilder { private val elements = mutableListOf<String>() fun title(text: String) { elements.add("<title>$text</title>") } fun build() = elements.joinToString("") } class BodyBuilder { private val elements = mutableListOf<String>() fun p(text: String) { elements.add("<p>$text</p>") } fun build() = elements.joinToString("") } fun html(block: HtmlBuilder.() -> Unit): String { val builder = HtmlBuilder() builder.block() return builder.build() } fun main() { val page = html { head { title("Welcome") } body { p("Hello, this is a type-safe builder example.") } } println(page) }
Type-safe builders use lambdas with receivers to create a clean and readable syntax.
They help prevent errors by limiting what can be called inside each builder block.
You can nest builders to represent complex structures like HTML or UI layouts.
Type-safe builders help build complex objects step-by-step with clear rules.
They use special functions and lambdas to make code easy to read and safe.
You can create nested builders to represent structured data like HTML.