14
14
import Foundation
15
15
16
16
/// Inject a service at the first use of the property
17
- @propertyWrapper public final class LazyInjectService < Service> : Equatable , Identifiable {
17
+ @propertyWrapper public final class LazyInjectService < Service> : Equatable , Identifiable , @unchecked Sendable {
18
+ private let semaphore = DispatchSemaphore ( value: 1 )
19
+
20
+ var service : Service ?
21
+
18
22
/// Identifiable
19
23
///
20
24
/// Something to link the identity of this property wrapper to the underlying Service type.
@@ -38,12 +42,9 @@ import Foundation
38
42
"""
39
43
}
40
44
41
- /// Store the resolved service
42
- var service : Service ?
43
-
44
- public var container : SimpleResolvable
45
- public var customTypeIdentifier : String ?
46
- public var factoryParameters : [ String : Any ] ?
45
+ public let container : SimpleResolvable
46
+ public let customTypeIdentifier : String ?
47
+ public let factoryParameters : [ String : Any ] ?
47
48
48
49
public init ( customTypeIdentifier: String ? = nil ,
49
50
factoryParameters: [ String : Any ] ? = nil ,
@@ -55,16 +56,20 @@ import Foundation
55
56
56
57
public var wrappedValue : Service {
57
58
get {
59
+ semaphore. wait ( )
60
+ defer { semaphore. signal ( ) }
61
+
58
62
if let service {
59
63
return service
60
64
}
61
65
62
66
do {
63
- service = try container. resolve ( type: Service . self,
64
- forCustomTypeIdentifier: customTypeIdentifier,
65
- factoryParameters: factoryParameters,
66
- resolver: container)
67
- return service!
67
+ let resolvedService = try container. resolve ( type: Service . self,
68
+ forCustomTypeIdentifier: customTypeIdentifier,
69
+ factoryParameters: factoryParameters,
70
+ resolver: container)
71
+ service = resolvedService
72
+ return resolvedService
68
73
} catch {
69
74
fatalError ( " DI fatal error : \( error) " )
70
75
}
0 commit comments