SuperAPI AI Directory

accessorysetupkit

Agents & models

View repository

Updated 10-16 05:52

About this skill

AccessorySetupKit

Discover and pair Bluetooth and Wi-Fi accessories with privacy-preserving iOS 18+ system pickers. ASAccessorySession eliminates the need for broad system Bluetooth authorization prompts. After user authorization, hand off communication to CoreBluetooth or NetworkExtension.

Contents

  • Setup & Entitlements
  • Discovery Descriptors
  • Session Activation & Picker
  • Transport Handoff
  • Common Mistakes
  • Review Checklist
  • References

Setup & Entitlements

Add matching configuration keys to Info.plist:

Key Type Purpose
NSAccessorySetupSupports [String] Required. Contains Bluetooth and/or WiFi
NSAccessorySetupBluetoothServices [String] Service UUIDs discovered by the app
NSAccessorySetupBluetoothNames [String] Accessory name substrings to match
NSAccessorySetupBluetoothCompanyIdentifiers [String] Two-byte Bluetooth company identifiers

The Bluetooth-specific Info.plist values must strictly match the rules in ASDiscoveryDescriptor. If an accessory matches a descriptor not declared in Info.plist, the app crashes at runtime.

No user Bluetooth permission prompt is triggered; CBCentralManager transitions to poweredOn once at least one accessory is authorized via AccessorySetupKit.

Discovery Descriptors

Define matching criteria for scanning nearby hardware:

import AccessorySetupKit
import CoreBluetooth

// Bluetooth Descriptor
var btDescriptor = ASDiscoveryDescriptor()
btDescriptor.bluetoothServiceUUID = CBUUID(string: "12345678-1234-1234-1234-123456789ABC")
btDescriptor.bluetoothNameSubstring = "SmartSensor"
btDescriptor.bluetoothRange = .immediate // Only nearby devices

// Wi-Fi Descriptor (provide either ssid OR ssidPrefix, not both)
var wifiDescriptor = ASDiscoveryDescriptor()
wifiDescriptor.ssidPrefix = "SmartSensor-"

Session Activation & Picker

Activate an ASAccessorySession and present the system picker:

import AccessorySetupKit

final class AccessoryCoordinator {
    let session = ASAccessorySession()

    func start() {
        session.activate(on: .main) { [weak self] event in
            switch event.eventType {
            case .accessoryAdded, .accessoryChanged:
                if let accessory = event.accessory {
                    self?.handleAuthorizedAccessory(accessory)
                }
            case .accessoryRemoved:
                self?.handleRemovedAccessory(event.accessory)
            case .sessionReset:
                self?.session.activate(on: .main, eventHandler: { _ in })
            @unknown default:
                break
            }
        }
    }

    func presentPicker(descriptor: ASDiscoveryDescriptor) {
        let displayItem = ASPickerDisplayItem(
            name: "Smart Sensor",
            productImage: UIImage(named: "sensor")!,
            descriptor: descriptor
        )
        session.showPicker(for: [displayItem]) { error in
            if let error { print("Picker failed: \(error)") }
        }
    }
}

Transport Handoff

After the user selects an accessory in the system picker:

  • Bluetooth: Retrieve the peripheral using CBCentralManager.retrievePeripherals(withIdentifiers: [accessory.bluetoothIdentifier]). Do not run general scans.
  • Wi-Fi: Connect to the authorized Wi-Fi network using NetworkExtension (NEHotspotConfigurationManager).

Common Mistakes

  • Undeclared Info.plist properties: Any UUID, name, or company ID used in an ASDiscoveryDescriptor must be declared in Info.plist or the app crashes.
  • Setting both ssid and ssidPrefix: Wi-Fi descriptors must set either ssid or ssidPrefix, never both.
  • Triggering general CoreBluetooth scans: AccessorySetupKit apps should never call scanForPeripherals(); retrieve authorized peripherals by identifier.
  • Ignoring .sessionReset: The system can invalidate sessions during daemon restarts; recreate or reactivate the session upon .sessionReset.
  • Assuming immediate connection: Picker completion indicates authorization, not active connection. Initiate the connection via CoreBluetooth after handoff.

Review Checklist

  • NSAccessorySetupSupports declared in Info.plist with Bluetooth / WiFi
  • All descriptor UUIDs, names, and company IDs declared in Info.plist
  • Wi-Fi descriptor specifies either ssid or ssidPrefix, not both
  • Peripherals retrieved via retrievePeripherals(withIdentifiers:) without scanning
  • Session events handled for .accessoryAdded, .accessoryRemoved, and .sessionReset

References