https://github.com/nslogmeng/swift-service
A lightweight, zero-dependency, type-safe dependency injection framework for modern Swift.
https://github.com/nslogmeng/swift-service
dependency dependency-injection ioc-container ios ios-development service-locator spm swift swift-concurrency swift-package-manager swift6 swiftui
Last synced: 4 months ago
JSON representation
A lightweight, zero-dependency, type-safe dependency injection framework for modern Swift.
- Host: GitHub
- URL: https://github.com/nslogmeng/swift-service
- Owner: nslogmeng
- License: mit
- Created: 2025-08-18T17:20:11.000Z (10 months ago)
- Default Branch: main
- Last Pushed: 2026-01-16T15:44:02.000Z (5 months ago)
- Last Synced: 2026-01-16T20:36:08.179Z (5 months ago)
- Topics: dependency, dependency-injection, ioc-container, ios, ios-development, service-locator, spm, swift, swift-concurrency, swift-package-manager, swift6, swiftui
- Language: Swift
- Homepage: https://nslogmeng.github.io/swift-service/documentation/service/?utm_source=github&utm_medium=referral&utm_campaign=service-github&utm_content=repo-about
- Size: 2.32 MB
- Stars: 4
- Watchers: 0
- Forks: 0
- Open Issues: 0
-
Metadata Files:
- Readme: README.md
- License: LICENSE
Awesome Lists containing this project
README
# Service
[](https://swiftpackageindex.com/nslogmeng/swift-service)
[](https://swiftpackageindex.com/nslogmeng/swift-service)
[](https://github.com/nslogmeng/swift-service/actions/workflows/build.yml)
[](https://github.com/nslogmeng/swift-service/actions/workflows/test.yml)
[](https://nslogmeng.github.io/swift-service/documentation/service/?utm_source=github&utm_medium=referral&utm_campaign=service-github&utm_content=readme-badge)
[](https://deepwiki.com/nslogmeng/swift-service)
A lightweight, zero-dependency, type-safe dependency injection framework designed for modern Swift projects.
Inspired by [Swinject](https://github.com/Swinject/Swinject) and [swift-dependencies](https://github.com/pointfreeco/swift-dependencies), Service leverages modern Swift features for simple, robust dependency injection. **Extremely easy to learn** with familiar register/resolve patterns, elegant dependency injection through property wrappers.
## ✨ Core Features
- **🚀 Modern Swift**: Uses property wrappers, TaskLocal, and concurrency primitives, fully leverages modern Swift features
- **🎯 Simple API, Ready to Use**: Use `@Service` property wrapper, no manual dependency passing needed, cleaner code
- **📦 Zero Dependencies, Lightweight**: No third-party dependencies, adds no burden to your project, perfect for any Swift project
- **🔒 Type-Safe, Compile-Time Checked**: Leverages Swift's type system to catch errors at compile time
- **⚡ Thread-Safe, Concurrency-Friendly**: Built-in thread safety guarantees, perfect support for Swift 6 concurrency model
- **🌍 Environment Isolation, Test-Friendly**: Task-level environment switching based on TaskLocal, easily swap dependencies in tests
- **🎨 MainActor Support**: Dedicated `@MainService` API for SwiftUI view models and UI components
- **🔍 Automatic Circular Dependency Detection**: Runtime detection of circular dependencies with clear error messages
- **🧩 Modular Assembly**: Organize service registrations through ServiceAssembly pattern for clearer code structure
## 📦 Installation
Add to your `Package.swift`:
```swift
dependencies: [
.package(url: "https://github.com/nslogmeng/swift-service", .upToNextMajor(from: "1.0.0"))
],
targets: [
.target(
name: "MyProject",
dependencies: [
.product(name: "Service", package: "swift-service"),
]
)
]
```
## 🚀 Quick Start
Get started with Service in just three steps:
### 1. Register Services
```swift
import Service
// Register a service (supports both protocols and concrete types)
ServiceEnv.current.register(DatabaseProtocol.self) {
DatabaseService(connectionString: "sqlite://app.db")
}
```
### 2. Inject Dependencies
Use the `@Service` property wrapper to automatically resolve dependencies:
```swift
struct UserRepository {
@Service
var database: DatabaseProtocol
func fetchUser(id: String) -> User? {
return database.findUser(id: id)
}
}
```
### 3. Use Services
```swift
let repository = UserRepository()
let user = repository.fetchUser(id: "123")
// database is automatically injected, no manual passing needed!
```
### 🎨 SwiftUI View Model Support
```swift
// Register MainActor service
ServiceEnv.current.registerMain(UserViewModel.self) {
UserViewModel()
}
// Use @MainService in your views
struct UserView: View {
@MainService
var viewModel: UserViewModel
var body: some View {
Text(viewModel.userName)
}
}
```
### 🧪 Test Environment Switching
```swift
// Switch to test environment in tests
await ServiceEnv.$current.withValue(.test) {
// Register mock services for testing
ServiceEnv.current.register(DatabaseProtocol.self) {
MockDatabase()
}
// All service resolutions use test environment
let repository = UserRepository()
// Test with mock database...
}
```
## 📚 Documentation
For comprehensive documentation, tutorials, and examples, see the [Service Documentation](https://nslogmeng.github.io/swift-service/documentation/service/?utm_source=github&utm_medium=referral&utm_campaign=service-github&utm_content=readme-docs).
### Topics
#### Essentials
- **[Getting Started](https://nslogmeng.github.io/swift-service/documentation/service/gettingstarted/?utm_source=github&utm_medium=referral&utm_campaign=service-github&utm_content=readme-docs)** - Quick setup guide
- **[Basic Usage](https://nslogmeng.github.io/swift-service/documentation/service/basicusage/?utm_source=github&utm_medium=referral&utm_campaign=service-github&utm_content=readme-docs)** - Core patterns and examples
- **[Service Environments](https://nslogmeng.github.io/swift-service/documentation/service/serviceenvironments/?utm_source=github&utm_medium=referral&utm_campaign=service-github&utm_content=readme-docs)** - Managing different service configurations
#### Advanced Topics
- **[MainActor Services](https://nslogmeng.github.io/swift-service/documentation/service/mainactorservices/?utm_source=github&utm_medium=referral&utm_campaign=service-github&utm_content=readme-docs)** - Working with UI components
- **[Service Assembly](https://nslogmeng.github.io/swift-service/documentation/service/serviceassembly/?utm_source=github&utm_medium=referral&utm_campaign=service-github&utm_content=readme-docs)** - Organizing service registrations
- **[Circular Dependencies](https://nslogmeng.github.io/swift-service/documentation/service/circulardependencies/?utm_source=github&utm_medium=referral&utm_campaign=service-github&utm_content=readme-docs)** - Understanding and avoiding circular dependencies
- **[Resetting Services](https://nslogmeng.github.io/swift-service/documentation/service/resettingservices/?utm_source=github&utm_medium=referral&utm_campaign=service-github&utm_content=readme-docs)** - Clearing caches and resetting service environments
#### Examples
- **[Real-World Examples](https://nslogmeng.github.io/swift-service/documentation/service/realworldexamples/?utm_source=github&utm_medium=referral&utm_campaign=service-github&utm_content=readme-docs)** - Practical use cases
#### Deep Dive
- **[Understanding Service](https://nslogmeng.github.io/swift-service/documentation/service/understandingservice/?utm_source=github&utm_medium=referral&utm_campaign=service-github&utm_content=readme-docs)** - Deep dive into architecture
- **[Concurrency Model](https://nslogmeng.github.io/swift-service/documentation/service/concurrencymodel/?utm_source=github&utm_medium=referral&utm_campaign=service-github&utm_content=readme-docs)** - Understanding Service's concurrency model
## 💡 Why Service?
### 🎯 Extremely Easy to Learn
If you're familiar with traditional dependency injection patterns (like Swinject), Service will feel very familiar. With property wrappers, you don't even need to manually pass dependencies:
```swift
// Traditional way: need to manually pass dependencies
class UserService {
init(database: DatabaseProtocol, logger: LoggerProtocol) { ... }
}
let service = UserService(database: db, logger: logger)
// Service way: automatic injection, cleaner code
class UserService {
@Service var database: DatabaseProtocol
@Service var logger: LoggerProtocol
}
let service = UserService() // Dependencies automatically injected!
```
### 🚀 Built for Modern Swift
- **Swift 6 Concurrency Model**: Perfect support for `Sendable` and `@MainActor`, with dedicated APIs for UI services
- **TaskLocal Environment Isolation**: Task-based environment switching, no need to modify global state in tests
- **Property Wrappers**: Leverages modern Swift features for elegant dependency injection
### 🛡️ Safe and Reliable
- **Compile-Time Type Checking**: Leverages Swift's type system to catch errors at compile time
- **Thread Safety Guarantees**: Built-in locking mechanism, supports concurrent access
- **Circular Dependency Detection**: Automatic runtime detection and reporting of circular dependencies
### 📦 Lightweight, Zero Burden
- **Zero Dependencies**: No third-party dependencies, won't add complexity to your project
- **Minimal Runtime Cost**: Efficient implementation with minimal impact on app performance
- **Wide Applicability**: Perfect for SwiftUI apps, server-side Swift, command-line tools, and any Swift project
### 🧩 Flexible and Powerful
- **Multiple Registration Methods**: Supports factory functions, direct instances, and ServiceKey protocol
- **Modular Assembly**: Organize service registrations through ServiceAssembly for clearer code structure
- **Environment Isolation**: Production, development, and test environments are completely isolated
## 📄 License
This project is licensed under the MIT License. See the [LICENSE](./LICENSE) file for details.