func mergeDeclaration()

in Sources/SwiftDocC/Semantics/Symbol/Symbol.swift [308:362]


    func mergeDeclaration(mergingDeclaration: SymbolGraph.Symbol.DeclarationFragments, identifier: String, symbolAvailability: SymbolGraph.Symbol.Availability?, selector: UnifiedSymbolGraph.Selector) throws {
        let trait = DocumentationDataVariantsTrait(interfaceLanguage: selector.interfaceLanguage)
        let platformName = selector.platform

        if let platformName = platformName,
            let existingKey = declarationVariants[trait]?.first(
                where: { pair in
                    return pair.value.declarationFragments == mergingDeclaration.declarationFragments
                }
            )?.key
        {
            guard !existingKey.contains(nil) else {
                throw DocumentationContext.ContextError.unexpectedEmptyPlatformName(identifier)
            }

            let platform = PlatformName(operatingSystemName: platformName)
            if !existingKey.contains(platform) {
                // Matches one of the existing declarations, append to the existing key.
                let currentDeclaration = declarationVariants[trait]?.removeValue(forKey: existingKey)!
                declarationVariants[trait]?[existingKey + [platform]] = currentDeclaration
            }
        } else {
            // Add new declaration
            if let name = platformName {
                declarationVariants[trait]?[[PlatformName.init(operatingSystemName: name)]] = mergingDeclaration
            } else {
                declarationVariants[trait]?[[nil]] = mergingDeclaration
            }
        }

        // Merge the new symbol with the existing availability. If a value already exist, only override if it's for this platform.
        if let symbolAvailability = symbolAvailability,
            symbolAvailability.availability.isEmpty == false || availabilityVariants[trait]?.availability.isEmpty == false // Nothing to merge if both are empty
        {
            var items = availabilityVariants[trait]?.availability ?? []

            // Add all the domains that don't already have availability information
            for availability in symbolAvailability.availability {
                guard !items.contains(where: { $0.domain?.rawValue == availability.domain?.rawValue }) else { continue }
                items.append(availability)
            }

            // Override the availability for all domains that apply to this platform
            if let modulePlatformName = platformName.map(PlatformName.init) {
                let symbolAvailabilityForPlatform = symbolAvailability.filterItems(thatApplyTo: modulePlatformName)

                for availability in symbolAvailabilityForPlatform.availability {
                    items.removeAll(where: { $0.domain?.rawValue == availability.domain?.rawValue })
                    items.append(availability)
                }
            }

            availabilityVariants[trait] = SymbolGraph.Symbol.Availability(availability: items)
        }
    }