Skip to main content

Documentation Index

Fetch the complete documentation index at: https://docs.myme.so/llms.txt

Use this file to discover all available pages before exploring further.

Typed domain models

Every core type has a generated typed wrapper: CoreNote, CoreBookmark, CoreTask, CoreHighlight, CoreEvent, CoreMedia and its eight subtypes, CoreEntity / CoreEntityPerson / CoreEntityPlace, CoreFile / CoreFileImage / CoreFileAudio / CoreFileVideo. 21 in total. Each wrapper conforms to the MarfaItem protocol — typeIdentifier, a failable init?(from: Item) that validates the type string and required fields, typed property accessors, and toProperties() for creating new items.
let item = try await client.items.get(id: noteId)

guard let note = CoreNote(from: item) else {
  throw UnexpectedType()
}

print(note.body)           // typed String — required
print(note.title ?? "")    // typed String? — optional
print(note.version)        // from MarfaItem default accessors

// To create a new item from a domain type:
let newItem = try await client.items.create(
  CreateItemInput(type: CoreNote.typeIdentifier, properties: note.toProperties())
)
Subtype-aware: CoreMediaArticle(from: item) returns nil unless item.type == "core.media.article". Required fields are non-optional (CoreMediaArticle.title, .body); optional fields surface as T?.

Custom-type codegen

Apps that register their own types (myapp.booking, myapp.user, …) can generate Swift wrappers in the same shape as CoreNote and friends. The generated structs conform to MarfaItem, expose typed property accessors, a failable init?(from: Item), and toProperties() for round-trip with client.items.create / update. Parent fields are flat-inlined, so a myapp.booking extending core.note exposes body, title, and the booking-specific fields on the same struct.

1. Configure

Drop a marfa-codegen.json at your repo root:
{
  "schema": 1,
  "source": { "mode": "local", "directory": "MarfaTypes" },
  "output": { "directory": "Sources/MyApp/MarfaTypes/Generated", "accessLevel": "public" },
  "types": { "include": ["myapp.*"] }
}
Drop one <type.id>.json file per type under MarfaTypes/:
{
  "id": "myapp.booking",
  "parent": "core.note",
  "version": 1,
  "fields": {
    "start_at": { "type": "string", "format": "datetime" },
    "party_size": { "type": "integer" }
  },
  "required": ["start_at"]
}
For "mode": "live", replace directory with cacheDirectory and let the sync executable populate the cache from GET /types.

2. Generate

Three entry points:
# SwiftPM command plugin — sandboxed, one shot.
swift package --allow-writing-to-package-directory generate-marfa-custom-types

# Same plugin, but pull schemas from a live server first.
swift package --allow-writing-to-package-directory --allow-network-connections all \
  generate-marfa-custom-types --sync

# Executables — CI-friendly, no sandbox prompts.
swift run codegen-custom-types
MARFA_API_URL= MARFA_API_KEY= swift run sync-custom-types
The --sync flow and sync-custom-types executable both call GET /types, so MARFA_API_KEY must carry the list_types permission. Pure-local codegen needs no credentials. core.* ids are always excluded from generation regardless of include/exclude globs — core wrappers ship with the SDK, so a misconfigured glob can’t clobber them.

3. Use the generated types

import SwiftUI
import MarfaSDK

struct BookingDetail: View {
  let item: Item

  var body: some View {
    if let booking = MyappBooking(from: item) {
      VStack(alignment: .leading) {
        Text(booking.title ?? "Untitled")
        Text(booking.startAt)
        Text("Party of \(booking.partySize ?? 0)")
      }
    } else {
      Text("Not a booking")
    }
  }
}

let created = try await client.items.create(
  CreateItemInput(
    type: MyappBooking.typeIdentifier,
    properties: [
      "start_at": .string("2026-05-01T18:00:00Z"),
      "party_size": .int(4),
      "body": .string("Dinner with J and S"),
    ]
  )
)

4. Keep generated files fresh

Commit the generated files. Add a freshness check to CI so a schema drift fails the build instead of going unnoticed:
- run: |
    swift run codegen-custom-types
    git diff --exit-code -- Sources/MyApp/MarfaTypes/Generated