Obsidian

0.3.0

🔮 Swift library providing natural language extensions and a reactive messaging framework.
beeauvin/obsidian

What's New

v0.3.0

2025-09-18T01:10:04Z

Prose

Sable is/was a separate library for thread safe message passing between actors. Both being OSS exports from a larger application project as it becomes relevant to polish/export them. Changes happen rapidly there though and reflecting them to both libraries has become untenable for me. So despite my best intentions to keep smaller, separate, packages I have decided to merge them into one monorepo style. For Obsidian, this means it now has an additional exported library ObsidianFlow. 🖤

Features, Fixes & Enhancements

  • [BREAKING] Feature: Swift build tools has been updated to 6.1 from 6.0.
  • [BREAKING] Refactor: The deprecated Result.catching method has been removed, replaced with Result.Catching.
  • Feature: Migrated the Sable project into Obsidian as ObsidianFlow.
  • Docs: Did a large documentation refresh and moved things around to be easier to find/parse.
  • Docs: Updated SPI config to generate documentation for all libraries.

What's Changed

  • deps(swift): [breaking] upgrade swift tools to 6.1 by @beeauvin in #28
  • feat(flow): migrate sable to obsidian by @beeauvin in #29
  • refactor(core): [breaking] remove deprecated lowercase result.catching by @beeauvin in #30
  • chore(release): v0.3.0 by @beeauvin in #31
  • docs(package): update swift package index to include all by @beeauvin in #32

Full Changelog: v0.2.2...v0.3.0

🔮 Obsidian

tests codecov

🔮 Obsidian is a comprehensive Swift 6+ utility library designed around the principle that code should be both functional and beautiful. It provides natural language interfaces for Swift's foundation types alongside a complete reactive messaging framework. From elegant Optional and Result extensions to thread-safe event-driven systems, Obsidian transforms how you write Swift code - making it read like prose while delivering powerful, type-safe functionality.

Modules

Obsidian is organized into focused modules, each addressing specific aspects of Swift development:

Natural language extensions for Optional and Result types with seamless conversion between them. Transform how you work with Swift's fundamental types using expressive, readable methods like otherwise, transform, when, and transmute.

Protocols for consistent interfaces across types: Uniquable for UUID-based identification, Namable for consistent naming, Describable for textual descriptions, and Representable for combined representation.

A comprehensive reactive messaging framework providing type-safe messaging primitives with Pulses, Channels, and Streams. Built for Swift's actor system with natural language APIs and immutable message design.

Obsidian (Umbrella Module)

The main module that imports and exposes Core, Foundation, and Flow modules. Import Obsidian to access all Obsidian features: utilities, protocols, and reactive messaging.

Getting Started

Installation

Add Obsidian to your Swift package dependencies:

dependencies: [
    .package(url: "https://github.com/beeauvin/obsidian.git", upToNextMinor: "0.3.0")
]

Basic Usage

Import Obsidian to access all features:

import Obsidian  // Imports Foundation utilities and Flow framework

For Flow-specific functionality, you can also import individual modules:

import ObsidianFlow  // Just the reactive messaging framework
import ObsidianCore  // Just the utility extensions

Quick Start

import Obsidian

// Use natural language Optional extensions
let username: String? = get_username()
let display_name = username.otherwise("Guest")

// Chain Result operations for robust error handling
let user_data = await Result<Data, Error>.Catching {
    try await api.fetch_user_data()
}.transform { data in
    try JSONDecoder().decode(User.self, from: data)
}.otherwise { DefaultUser() }

// Create reactive message flows
struct UserAction: Pulsable {
    let action: String
    let timestamp: Date
}

let action_channel = Channel { pulse in
    await process_user_action(pulse.data)
}

let action_pulse = Pulse(UserAction(action: "login", timestamp: Date()))
    .priority(.high)
    .tagged("user", "auth")

await action_channel.send(action_pulse)

For comprehensive examples and real-world usage patterns, see examples.md.

Documentation

Contributing

Contributions are welcome! Please read our design philosophy to understand Obsidian's core principles and intentional design decisions. The key consideration for contributions is alignment with these principles while enhancing the developer experience.

See the contributing guide for detailed guidelines.

License

🔮 Obsidian is available under the Mozilla Public License 2.0.

A copy of the MPLv2 is included in the license.md file for convenience.

Description

  • Swift Tools 6.1.0
View More Packages from this Author

Dependencies

  • None
Last updated: Mon Oct 27 2025 11:45:01 GMT-0900 (Hawaii-Aleutian Daylight Time)