Skip to content

Commit 9abe0b9

Browse files
authored
Merge pull request #66636 from kirbyt/kirbyt/observation-docs-109798110
Observation reference documentation
2 parents d5c3018 + 367a7f6 commit 9abe0b9

File tree

3 files changed

+90
-0
lines changed

3 files changed

+90
-0
lines changed

stdlib/public/Observation/Sources/Observation/Observable.swift

Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10,11 +10,35 @@
1010
//===----------------------------------------------------------------------===//
1111

1212

13+
/// A type that emits notifications to observers when underlying data changes.
14+
///
15+
/// Conforming to this protocol signals to other APIs that the type supports
16+
/// observation. However, applying the `Observable` protocol by itself to a
17+
/// type doesn't add observation functionality to the type. Instead, always use
18+
/// the ``Observation/Observable-swift.macro`` macro when adding observation
19+
/// support to a type.
1320
@available(SwiftStdlib 5.9, *)
1421
@_marker public protocol Observable { }
1522

1623
#if $Macros && hasAttribute(attached)
1724

25+
/// Defines and implements conformance of the Observable protocol.
26+
///
27+
/// This macro adds observation support to a custom type and conforms the type
28+
/// to the ``Observation/Observable-swift.protocol`` protocol. For example, the
29+
/// following code applies the `Observable` macro to the type `Car` making it
30+
/// observable:
31+
///
32+
/// @Observable
33+
/// class Car {
34+
/// var name: String = ""
35+
/// var needsRepairs: Bool = false
36+
///
37+
/// init(name: String, needsRepairs: Bool = false) {
38+
/// self.name = name
39+
/// self.needsRepairs = needsRepairs
40+
/// }
41+
/// }
1842
@available(SwiftStdlib 5.9, *)
1943
#if OBSERVATION_SUPPORTS_PEER_MACROS
2044
@attached(member, names: named(_$observationRegistrar), named(access), named(withMutation))
@@ -26,6 +50,10 @@
2650
public macro Observable() =
2751
#externalMacro(module: "ObservationMacros", type: "ObservableMacro")
2852

53+
/// Synthesizes a property for accessors.
54+
///
55+
/// The ``Observation`` module uses this macro. Its use outside of the
56+
/// framework isn't necessary.
2957
@available(SwiftStdlib 5.9, *)
3058
@attached(accessor, names: named(init), named(get), named(set))
3159
#if OBSERVATION_SUPPORTS_PEER_MACROS
@@ -34,6 +62,11 @@ public macro Observable() =
3462
public macro ObservationTracked() =
3563
#externalMacro(module: "ObservationMacros", type: "ObservationTrackedMacro")
3664

65+
/// Disables observation tracking of a property.
66+
///
67+
/// By default, an object can observe any property of an observable type that
68+
/// is accessible to the observing object. To prevent observation of an
69+
/// accessible property, attach the `ObservationIgnored` macro to the property.
3770
@available(SwiftStdlib 5.9, *)
3871
@attached(accessor, names: named(willSet))
3972
public macro ObservationIgnored() =

stdlib/public/Observation/Sources/Observation/ObservationRegistrar.swift

Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,11 @@
99
//
1010
//===----------------------------------------------------------------------===//
1111

12+
/// Provides storage for tracking and access to data changes.
13+
///
14+
/// You don't need to create an instance of `ObservationRegistrar` when using
15+
/// the ``Observation/Observable-swift.macro`` macro to indicate observability
16+
/// of a type.
1217
@available(SwiftStdlib 5.9, *)
1318
public struct ObservationRegistrar: Sendable {
1419
struct State: @unchecked Sendable {
@@ -90,9 +95,20 @@ public struct ObservationRegistrar: Sendable {
9095

9196
let context = Context()
9297

98+
/// Creates an instance of the observation registrar.
99+
///
100+
/// You don't need to create an instance of
101+
/// ``Observation/ObservationRegistrar`` when using the
102+
/// ``Observation/Observable-swift.macro`` macro to indicate observably
103+
/// of a type.
93104
public init() {
94105
}
95106

107+
/// Registers access to a specific property for observation.
108+
///
109+
/// - Parameters:
110+
/// - subject: An instance of an observable type.
111+
/// - keyPath: The key path of an observed property.
96112
public func access<Subject: Observable, Member>(
97113
_ subject: Subject,
98114
keyPath: KeyPath<Subject, Member>
@@ -106,20 +122,37 @@ public struct ObservationRegistrar: Sendable {
106122
}
107123
}
108124

125+
/// A property observation called before setting the value of the subject.
126+
///
127+
/// - Parameters:
128+
/// - subject: An instance of an observable type.
129+
/// - keyPath: The key path of an observed property.
109130
public func willSet<Subject: Observable, Member>(
110131
_ subject: Subject,
111132
keyPath: KeyPath<Subject, Member>
112133
) {
113134
context.willSet(subject, keyPath: keyPath)
114135
}
115136

137+
/// A property observation called after setting the value of the subject.
138+
///
139+
/// - Parameters:
140+
/// - subject: An instance of an observable type.
141+
/// - keyPath: The key path of an observed property.
116142
public func didSet<Subject: Observable, Member>(
117143
_ subject: Subject,
118144
keyPath: KeyPath<Subject, Member>
119145
) {
120146

121147
}
122148

149+
/// Identifies mutations to the transactions registered for observers.
150+
///
151+
/// This method calls ``willset(_:keypath:)`` before the mutation. Then it
152+
/// calls ``didset(_:keypath:)`` after the mutation.
153+
/// - Parameters:
154+
/// - of: An instance of an observable type.
155+
/// - keyPath: The key path of an observed property.
123156
public func withMutation<Subject: Observable, Member, T>(
124157
of subject: Subject,
125158
keyPath: KeyPath<Subject, Member>,

stdlib/public/Observation/Sources/Observation/ObservationTracking.swift

Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -80,6 +80,30 @@ public struct ObservationTracking {
8080
}
8181
}
8282

83+
/// Tracks access to properties.
84+
///
85+
/// This method tracks access to any property within the `apply` closure, and
86+
/// informs the caller of value changes made to participating properties by way
87+
/// of the `onChange` closure. For example, the following code tracks changes
88+
/// to the name of cars, but it doesn't track changes to any other property of
89+
/// `Car`:
90+
///
91+
/// func render() {
92+
/// withObservationTracking {
93+
/// for car in cars {
94+
/// print(car.name)
95+
/// }
96+
/// } onChange: {
97+
/// print("Schedule renderer.")
98+
/// }
99+
/// }
100+
///
101+
/// - Parameters:
102+
/// - apply: A closure that contains properties to track.
103+
/// - onChange: The closure invoked when the value of a property changes.
104+
///
105+
/// - Returns: The value that the `apply` closure returns if it has a return
106+
/// value; otherwise, there is no return value.
83107
@available(SwiftStdlib 5.9, *)
84108
public func withObservationTracking<T>(
85109
_ apply: () -> T,

0 commit comments

Comments
 (0)