Skip to content

Conversation

anferbui
Copy link
Contributor

Bug/issue #, if applicable: N/A

Summary

After #1249, we ended up with three implementations of isBeta which are equivalent:

  • NavigatorIndexableRenderMetadataRepresentation 1
  • OutOfProcessReferenceResolver.ResolvedInformation 2
  • LinkDestinationSummary 3

This adds an extension to Array<AvailabilityRenderItem> which defines a property isBeta with the same logic.

This will eliminate the possibility that these 3 implementations will inadvertently become out of sync with each other. The logic remains that an item is in beta if all platforms are marked as beta.

There is still at least one more place in the code-base which determines beta status 4, but that remains hard to merge at the moment.

Dependencies

N/A

Testing

No functional changes, verified by checking that unit tests still pass.

Checklist

Make sure you check off the following items. If they cannot be completed, provide a reason.

  • [ ] Added tests (No change in functionality)
  • Ran the ./bin/test script and it succeeded
  • Updated documentation if necessary

Adds an extension to `Array<AvailabilityRenderItem>` which defines a property `isBeta` with the same logic currently defined in 3 separate locations:
- `NavigatorIndexableRenderMetadataRepresentation` [1]
- `OutOfProcessReferenceResolver.ResolvedInformation` [2]
- `LinkDestinationSummary` [3]

This will eliminate the possibility that these 3 implementations will inadvertently become out of sync with each other. The logic remains that an item is in beta if all platforms are marked as beta.

There is still at least one more place in the code-base which determines beta status [4], but that remains hard to merge at the moment.

[1]: https://github.com/swiftlang/swift-docc/blob/1c54e106f5c9a92a69225492b1a89c934677ae58/Sources/SwiftDocC/Indexing/Navigator/RenderNode%2BNavigatorIndex.swift#L126-L134
[2]: https://github.com/swiftlang/swift-docc/blob/1c54e106f5c9a92a69225492b1a89c934677ae58/Sources/SwiftDocC/Infrastructure/External%20Data/OutOfProcessReferenceResolver.swift#L592-L598
[3]: https://github.com/swiftlang/swift-docc/blob/1c54e106f5c9a92a69225492b1a89c934677ae58/Sources/SwiftDocC/Infrastructure/Link%20Resolution/ExternalPathHierarchyResolver.swift#L186-L192
[4]: https://github.com/swiftlang/swift-docc/blob/1c54e106f5c9a92a69225492b1a89c934677ae58/Sources/SwiftDocC/Model/Rendering/DocumentationContentRenderer.swift#L210
Removes the duplicate implementations and delegates to the `Array<AvailabilityRenderItem>` extension instead.
@anferbui anferbui added the code cleanup Code cleanup *without* user facing changes label Sep 15, 2025
@anferbui
Copy link
Contributor Author

@swift-ci please test

Copy link
Contributor

@d-ronnqvist d-ronnqvist left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I feel like the name isBeta makes for a strange call site because it's conceptually not a property of the array but of its elements. There's also the ambiguity in the name of what it means to be "in beta". This PR worsens that issue by making the ambiguous API available to more internal code.

I also don't think this very mild code repetition is much of an issue, so we could leave it as is.

Comment on lines +183 to +187
guard !self.isEmpty else {
return false
}

return self.allSatisfy { $0.isBeta == true }
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

FYI: you can write this in a single expression as

Suggested change
guard !self.isEmpty else {
return false
}
return self.allSatisfy { $0.isBeta == true }
contains(where: { $0.isBeta != true })

///
/// - Returns: `true` if all platforms in the array are in beta; `false` if the array is empty or if any
/// platform is not in beta.
var isBeta: Bool {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think this name looks a bit strange at the call site because the array isn't "in beta" rather it's the containing elements that are.

Also, this name has some ambiguity as to what it means for a collection of platforms to be in beta. This is explained in the documentation but if this behavior was clarified in the symbol name it would avoid this ambiguity all together.

Suggested change
var isBeta: Bool {
var allAreInBeta: Bool {

Comment on lines +175 to +178
/// This computed property centralizes the beta determination logic to avoid code duplication across multiple
/// components that need to check whether a symbol is in beta based on its platform availability.
/// `NavigatorIndexableRenderMetadataRepresentation`, `OutOfProcessReferenceResolver.ResolvedInformation` and `LinkDestinationSummary` all store an array of ``AvailabilityRenderItem`` and need to determine beta status based on platform availability,
/// so it is convenient to de-duplicate the shared logic here.
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This type of comment is about the implementation and isn't all that relevant to the user of the API.

Suggested change
/// This computed property centralizes the beta determination logic to avoid code duplication across multiple
/// components that need to check whether a symbol is in beta based on its platform availability.
/// `NavigatorIndexableRenderMetadataRepresentation`, `OutOfProcessReferenceResolver.ResolvedInformation` and `LinkDestinationSummary` all store an array of ``AvailabilityRenderItem`` and need to determine beta status based on platform availability,
/// so it is convenient to de-duplicate the shared logic here.

Comment on lines +179 to +181
///
/// - Returns: `true` if all platforms in the array are in beta; `false` if the array is empty or if any
/// platform is not in beta.
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Simple properties like this one don't need a returns section.

Suggested change
///
/// - Returns: `true` if all platforms in the array are in beta; `false` if the array is empty or if any
/// platform is not in beta.

}

extension Array where Array.Element == AvailabilityRenderItem {
/// Determines whether all platforms in the array are in beta.
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is a verb phrase ("determines") but properties is more commonly described by nouns.

We could either change this to a function (func allAreInBeta() -> Bool) to go better with the verb phrase or change this to a noun phrase. For example:

Suggested change
/// Determines whether all platforms in the array are in beta.
/// A Boolean value that determines whether all platforms in the array are in beta.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That said, with a simple and clean name like allAreInBeta I don't know if this needs any documentation at all as an internal API.

}
}

extension Array where Array.Element == AvailabilityRenderItem {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

FIY: this can be expressed more simply as

Suggested change
extension Array where Array.Element == AvailabilityRenderItem {
extension Array<AvailabilityRenderItem> {

Comment on lines +170 to +173
/// This property returns `true` if every availability item in the array has its `isBeta` property set to `true`,
/// indicating that the symbol is introduced in a beta version across all platforms. If the array is empty,
/// this property returns `false`, as an item with no platform availability information is not considered
/// to be in beta.
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If this behavior is clarified in the API then this documentation can be simplified to only covering the empty behavior.

Also, there's no need to wrap documentation to a fixed column width.

Suggested change
/// This property returns `true` if every availability item in the array has its `isBeta` property set to `true`,
/// indicating that the symbol is introduced in a beta version across all platforms. If the array is empty,
/// this property returns `false`, as an item with no platform availability information is not considered
/// to be in beta.
/// If the array is empty, this value is `false`. A symbol without any platform availability information isn't considered to be in beta.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
code cleanup Code cleanup *without* user facing changes
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants