Swiftpack.co - omochi/CodegenKit as Swift Package

Swiftpack.co is a collection of thousands of indexed Swift packages. Search packages.
See all packages published by omochi.
omochi/CodegenKit 1.3.0
Swift code generation framework
⭐️ 13
🕓 5 weeks ago
.package(url: "https://github.com/omochi/CodegenKit.git", from: "1.3.0")

CodegenKit: Swift code generation framework

This is a framework for introducing code generation on your Swift project. You can do meta-programming like below.

Code becomes template as it is

Placeholders are defined by markers in Swift code as follows.

protocol TSDecl {}

extension TSDecl {
    // @codegen(as)
    // @end

Generated codes are inserted in area between markers.

Thus, CodegenKit doesn't use any specific template files. Instead, Swift source codes are used as a template.

Write code renderer in Swift

Write code renderer as follows.

import Foundation
import CodegenKit

struct Node {
    var stem: String
    var typeName: String

struct TSDeclRenderer: Renderer {
    var nodes: [Node] = [...]

    func isTarget(file: URL) -> Bool {
        file.lastPathComponent == "TSDecl.swift"

    func render(template: inout CodeTemplate, file: URL, on runner: CodegenRunner) throws {
        template["as"] = asCasts()

    func asCasts() -> String {
        let lines: [String] = nodes.map { (node) in
public var as\(node.stem.pascal): \(node.typeName)? { self as? \(node.typeName) }
        return lines.joined(separator: "\n")

Your source code are passed as CodeTemplate object. You can edit contents of placeholder via subscript.

Do code generation

After writing renderers, generate codes. Perform code generation with following command.

$ swift package codegen

Previous code will be edited as follows.

// TSDecl.swift
protocol TSDecl {}

extension TSDecl {
    // @codegen(as)
    public var asClass: TSClassDecl? { self as? TSClassDecl }
    public var asField: TSFieldDecl? { self as? TSFieldDecl }
    public var asFunction: TSFunctionDecl? { self as? TSFunctionDecl }
    public var asImport: TSImportDecl? { self as? TSImportDecl }
    public var asInterface: TSInterfaceDecl? { self as? TSInterfaceDecl }
    public var asMethod: TSMethodDecl? { self as? TSMethodDecl }
    public var asNamespace: TSNamespaceDecl? { self as? TSNamespaceDecl }
    public var asSourceFile: TSSourceFile? { self as? TSSourceFile }
    public var asType: TSTypeDecl? { self as? TSTypeDecl }
    public var asVar: TSVarDecl? { self as? TSVarDecl }
    // @end

Let's start and enjoy code generation! Please read this document for detailed setup instructions.



Stars: 13
Last commit: 5 weeks ago
jonrohan Something's broken? Yell at me @ptrpavlik. Praise and feedback (and money) is also welcome.

Release Notes

Upgrade SwiftSyntax 508 versions
5 weeks ago

Swiftpack is being maintained by Petr Pavlik | @ptrpavlik | @swiftpackco | API | Analytics