Swiftpack.co is a collection of thousands of indexed Swift packages. Search packages.
nayanda1/Impose
Impose
Impose is a simple dependency injection library for Swift
Requirements
- Swift 5.0 or higher
- iOS 9.3 or higher
Installation
Cocoapods
Impose is available through CocoaPods. To install it, simply add the following line to your Podfile:
pod 'Impose'
Swift Package Manager
First, create a Package.swift file and add this github url. It should look like:
dependencies: [
.package(url: "https://github.com/nayanda1/Impose.git", from: "1.2.0")
]
Then run swift build to build the dependency before you use it
Author
Nayanda Haberty, nayanda1@outlook.com
License
Impose is available under the MIT license. See the LICENSE file for more info.
Basic Usage
Impose is very easy to use and straightforward, all you need to do is provide some provider for dependency:
Imposer.impose(for: Dependency.self, SomeDependency())
and then use it in some of your class using property wrapper or using global function
class InjectedByPropertyWrapper {
@Injected var dependency: Dependency
...
...
}
class InjectedByInit {
var dependency: Dependency
init(dependency: Dependency = inject()) {
self.dependency = dependency
}
}
the provider is autoClosure type, so you can do something like this:
Imposer.impose(for: Dependency.self) {
dependency: SomeDependency = .init()
dependency.doSomeSetup()
return dependency
}
the provider automatically just create one instance only (singleton). If you want the provider to create new instance for every injection, you can just pass option:
Imposer.impose(for: Dependency.self, option: .alwaysNew, SomeDependency())
or if you want to set it to singleton explicitly:
Imposer.impose(for: Dependency.self, option: .singleton, SomeDependency())
Don't forget that it will throw uncatchable Error if the provider is not registered yet. If you want to catch the error manually, just use tryInject
instead:
class InjectedByInit {
var dependency: Dependency
init(dependency: Dependency? = nil) {
do {
self.dependency = dependency ?? try tryInject()
} catch {
self.dependency = DefaultDependency()
}
}
}
Optional Inject
Sometimes you just don't want your app to be throwing error because of failure in dependency injection. At those cases, just use @UnforceInjected
attribute or unforceInject
function. It will return nil if injection fail:
```swift
class InjectedByPropertyWrapper {
@UnforceInjected var dependency: Dependency?
...
...
}
class InjectedByInit {
var dependency: Dependency
init(dependency: Dependency? = unforceInject()) {
self.dependency = dependency
}
}
No Match Rules
If the Imposer did not found exact type registered but multiple compatible type, it will use the nearest one to the requested type.
protocol Dependency {
...
...
}
class MyDependency: Dependency {
...
...
}
class YourDependency: MyDependency {
...
...
}
class OurDependency: YourDependency {
...
...
}
and you register your dependency like this:
Imposer.impose(for: Dependency.self, MyDependency())
Imposer.impose(for: YourDependency.self, YourDependency())
Imposer.impose(for: OurDependency.self, OurDependency())
then the result will be:
class InjectedByPropertyWrapper {
@Injected var thisWillBeMyDependency: Dependency
@Injected var thisWillBeYourDependency: MyDependency
@Injected var thisWillBeYourDependencyToo: YourDependency
@Injected var thisWillBeOurDependency: OurDependency
...
...
}
class InjectedByInit {
var thisWillBeMyDependency: Dependency
var thisWillBeYourDependency: MyDependency
var thisWillBeYourDependencyToo: YourDependency
var thisWillBeOurDependency: OurDependency
init(thisWillBeMyDependency: Dependency = inject(),
thisWillBeYourDependency: MyDependency = inject(),
thisWillBeYourDependencyToo: YourDependency = inject(),
thisWillBeOurDependency: OurDependency = inject()) {
self.thisWillBeMyDependency = thisWillBeMyDependency
self.thisWillBeYourDependency = thisWillBeYourDependency
self.thisWillBeYourDependencyToo = thisWillBeYourDependencyToo
self.thisWillBeOurDependency = thisWillBeOurDependency
}
}
If you prefer the furthest type registered, then you can pass rules into propertyWrapper or inject function like this:
class InjectedByPropertyWrapper {
@Injected(ifNoMatchUse: .furthestType)
var thisWillBeMyDependency: Dependency
@Injected(ifNoMatchUse: .furthestType)
var thisWillBeOurDependency: MyDependency
@Injected(ifNoMatchUse: .furthestType)
var thisWillBeYourDependency: YourDependency
@Injected(ifNoMatchUse: .furthestType)
var thisWillBeOurDependencyToo: OurDependency
...
...
}
class InjectedByInit {
var thisWillBeMyDependency: Dependency
var thisWillBeOurDependency: MyDependency
var thisWillBeYourDependency: YourDependency
var thisWillBeOurDependencyToo: OurDependency
init(thisWillBeMyDependency: Dependency = inject(ifNoMatchUse: .furthestType),
thisWillBeOurDependency: MyDependency = inject(ifNoMatchUse: .furthestType),
thisWillBeYourDependency: YourDependency = inject(ifNoMatchUse: .furthestType),
thisWillBeOurDependencyToo: OurDependency = inject(ifNoMatchUse: .furthestType)) {
self.thisWillBeMyDependency = thisWillBeMyDependency
self.thisWillBeOurDependency = thisWillBeOurDependency
self.thisWillBeYourDependency = thisWillBeYourDependency
self.thisWillBeOurDependencyToo = thisWillBeOurDependencyToo
}
}
Github
link |
Stars: 3 |
Last commit: 1 week ago |
You may find interesting
Dependencies
Releases
Revert foldering - 2021-02-19T08:09:04
- Revert foldering
- Added macOS, tvOS target
- Added existing unit test to SPM