1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88
|
# Extending `Calendar.RecurrenceRule.End`
* Proposal: SF-0010
* Author(s): Hristo Staykov <hstaykov@apple.com>
* Review Manager: [Tina Liu](https://github.com/itingliu)
* Status: **Implemented**
* Bugs: <rdar://134294130&136704624>
* Implementation: [apple/swift-foundation#888](https://github.com/apple/swift-foundation/pull/888)
* Previous Proposal: [SF-0009](0009-calendar-recurrence-rule.md)
## Revision history
* **v1** Initial version
* **v2** Added `CustomStringConvertible` conformance to `Calendar.RecurrenceRule.End`.
* **v3** Renamed `count` to `occurrences`
* **v4** Made `Calendar.RecurrenceRule` conform to `Hashable`
## Introduction
In [SF-0009](0009-calendar-recurrence-rule.md) we introduced Calendar.RecurrenceRule API. In this API, we represent the end of a recurrence rule with the struct `Calendar.RecurrenceRule.End`:
```swift
/// When a recurring event stops recurring
public struct End: Sendable, Equatable {
/// The event stops repeating after a given number of times
/// - Parameter count: how many times to repeat the event, including
/// the first occurrence. `count` must be greater
/// than `0`
public static func afterOccurrences(_ count: Int) -> Self
/// The event stops repeating after a given date
/// - Parameter date: the date on which the event may last occur. No
/// further occurrences will be found after that
public static func afterDate(_ date: Date) -> Self
/// The event repeats indefinitely
public static var never: Self
}
```
This is de-facto an enum, but it was declared as struct to be future-proof. However, the original API only allowed construction of the recurrence rule end, but does not allow any introspection afterwards. This proposal adds a few properties to `Calendar.RecurrenceRule.End` to remedy this.
Additionally, we add `CustomStringConvertible` conformance to the struct. Previously, implementation details would be leaked when printing (`End(_guts: Foundation.Calendar.RecurrenceRule.End.(unknown context at $1a0a00afc)._End.never)`).
Lastly, we also make `Calendar.RecurrenceRule` and its subtypes conform to `Hashable`
## Detailed design
```swift
public extension Calendar.RecurrenceRule.End {
/// At most many times the event may occur
/// This value is set when the struct was initialized with `.afterOccurrences()`
@available(FoundationPreview 6.0.2, *)
public var occurrences: Int? { get }
/// The latest date when the event may occur
/// This value is set when the struct was initialized with `.afterDate()`
@available(FoundationPreview 6.0.2, *)
public var date: Date? { get }
}
@available(FoundationPreview 6.0.2, *)
public extension Calendar.RecurrenceRule.End: CustomStringConvertible {
public var description: String {
switch self._guts {
case .never: "Never"
case .afterDate(let date): "After \(date)"
case .afterOccurrences(let n): "After \(n) occurrences"
}
}
}
@available(FoundationPreview 6.0.2, *)
public extension Calendar.RecurrenceRule: Hashable { }
@available(FoundationPreview 6.0.2, *)
public extension Calendar.RecurrenceRule.End: Hashable { }
@available(FoundationPreview 6.0.2, *)
public extension Calendar.RecurrenceRule.Month: Hashable { }
@available(FoundationPreview 6.0.2, *)
public extension Calendar.RecurrenceRule.Weekday: Hashable { }
```
## Impact on existing code
None.
|