{"id":23141336,"url":"https://github.com/robotpajamas/swiftyteeth","last_synced_at":"2025-08-17T13:31:44.421Z","repository":{"id":46718256,"uuid":"67143390","full_name":"RobotPajamas/SwiftyTeeth","owner":"RobotPajamas","description":"A simple, lightweight library intended to take away some of the cruft and tediousness of using CoreBluetooth","archived":false,"fork":false,"pushed_at":"2024-02-27T13:59:54.000Z","size":326,"stargazers_count":23,"open_issues_count":22,"forks_count":8,"subscribers_count":1,"default_branch":"master","last_synced_at":"2025-04-05T07:33:04.321Z","etag":null,"topics":["bluetooth","bluetooth-low-energy","corebluetooth","ios","swift"],"latest_commit_sha":null,"homepage":"","language":"Swift","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"apache-2.0","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/RobotPajamas.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null}},"created_at":"2016-09-01T15:26:46.000Z","updated_at":"2024-07-11T12:28:49.000Z","dependencies_parsed_at":"2023-11-17T15:02:47.896Z","dependency_job_id":null,"html_url":"https://github.com/RobotPajamas/SwiftyTeeth","commit_stats":null,"previous_names":[],"tags_count":13,"template":false,"template_full_name":null,"purl":"pkg:github/RobotPajamas/SwiftyTeeth","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/RobotPajamas%2FSwiftyTeeth","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/RobotPajamas%2FSwiftyTeeth/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/RobotPajamas%2FSwiftyTeeth/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/RobotPajamas%2FSwiftyTeeth/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/RobotPajamas","download_url":"https://codeload.github.com/RobotPajamas/SwiftyTeeth/tar.gz/refs/heads/master","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/RobotPajamas%2FSwiftyTeeth/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":270856561,"owners_count":24657688,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","status":"online","status_checked_at":"2025-08-17T02:00:09.016Z","response_time":129,"last_error":null,"robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":true,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["bluetooth","bluetooth-low-energy","corebluetooth","ios","swift"],"created_at":"2024-12-17T14:13:30.062Z","updated_at":"2025-08-17T13:31:44.136Z","avatar_url":"https://github.com/RobotPajamas.png","language":"Swift","funding_links":[],"categories":[],"sub_categories":[],"readme":"# SwiftyTeeth\n\n## What is SwiftyTeeth?\n\nSwiftyTeeth is a simple, lightweight library intended to take away some of the cruft and tediousness of using iOS BLE. It replaces CoreBluetooth's protocols and delegates with a callback-based pattern, and handles much of the code overhead associated with handling connections, discovery, reads/writes, and notifications. It is a spiritually similar library to Android's [Blueteeth](https://github.com/RobotPajamas/Blueteeth).\n\nBoth libraries were originally inspired by the simplicity and ease-of-use of [LGBluetooth](https://github.com/l0gg3r/LGBluetooth).\n\n## High-Level\n\nThe motivation for this library was to provide an alternate (ideally - simpler) API than what iOS offers in CoreBluetooth to reduce complexity and code overhead. Another motivator was to provide an API that might make more sense 'practically' than CoreBluetooth's API, which exposes underlying implementation-specifics rather than abstracting them away.\n\nFor instance, with BLE devices, you connect to a peripheral, but in CoreBluetooth - you call connect on a manager singleton to connect to a peripheral, which makes sense for implementation-specifics (as there is only 1 Bluetooth radio which needs to manage all connections), but not semantically. In SwiftyTeeth, the 'Device' object has the connect method, the caller 'connects to a device', rather than the caller 'asks a singleton to connect to a device on it's behalf'.\n\n## Usage\n\nScan for BLE devices using SwiftyTeeth with a 1 second timeout:\n\n\tSwiftyTeeth.shared.scan(for: 1) { devices in\n            self.devices = devices\n            self.tableView.reloadData()\n        }\n\n\nAlternatively, you could use the SwiftyTeethable protocol in an extension:\n\n\textension DeviceListViewController: SwiftyTeethable {\n\t    func scanTapped() {\n\t        swiftyTeeth.scan(for: 1) { devices in\n\t            self.devices = devices\n\t            self.tableView.reloadData()\n\t        }\n\t    }\n\t}\n\n\nInitiate a connection using a SwiftyTeeth.Device:\n \n\tdevice?.connect(complete: { isConnected in\n\t\tprint(\"Is device connected? \\(isConnected == true)\")\n    })\n\n\nDiscover Bluetooth services and characteristics:\n \n\tself.device?.discoverServices(complete: { services, error in\n        services.forEach({\n            print(\"Discovering characteristics for service: \\($0.uuid.uuidString)\")\n            self.device?.discoverCharacteristics(for: $0, complete: { service, characteristics, error in\n                characteristics.forEach({\n                    print(\"App: Discovered characteristic: \\($0.uuid.uuidString) in \\(service.uuid.uuidString)\")\n                })\n                \n                if service == services.last {\n                    print(\"App: All services/characteristics discovered\")\n                }\n            })\n        })\n    })\n\n\nWrite to a connected SwiftyTeeth.Device:\n\n\tlet command = Data(bytes: [0x01])\n    device?.write(data: command, to: characteristic, in: service, complete: { error in\n        print(\"Write with response successful? \\(error == nil)\")\n    })\n\n\nRead from a connected SwiftyTeeth.Device:\n \n    device?.read(from: characteristic, in: service, complete: { data, error in\n        print(\"Read value: \\(data?.base64EncodedString())\")\n    })\n\n\nSubscribe to notifications from a connected SwiftyTeeth.Device:\n\n\tdevice?.subscribe(to: characteristic, in: service, complete: { data, error in\n        print(\"Subscribed value: \\(data?.base64EncodedString())\")\n    })\n\nCheck out the sample app in `SwiftyTeeth Sample/` to see the API in action. \n\n## Future Directions\n\n### Better Error handling\n\nError handling in a BLE library is always tricky - but generally they should be fully asynchronous. In addition, having clear and concise error conditions, alongside seamless retries is crucial.\n\n### Queues\n\nAs mentioned in [the Blueteeth post](http://www.sureshjoshi.com/mobile/bluetooth-bluetooths-blueteeth/), Callback Hell (or rightward drift) sucks, but that hasn't yet been solved in this library. The current usage for chaining calls is still, unfortunately, callbacks in callbacks.\n\n### MacOS\n\nCoreBluetooth is also available on MacOS, so once completed and compiled correctly - there is no reason that it couldn't be used directly on a Mac, rather than only from iOS devices.\n\n### SwiftyTeeth as a Peripheral\n\nFor the purposes of testing and debugging, being able to use a Mac as a demo-peripheral has immense value. CoreBluetooth supports central and peripheral modes of operation, so this would be a great (and useful) extension.\n\n### Reactive Everything!\n\nNow that this library is released and progressively becoming more stable, the next step in the process is to create Reactive bindings (RxSwift bindings specifically). They will be created in a separate repo, so that there isn't a forced, heavy dependency on the Rx framework in any app that just wants to use SwiftyTeeth.\n\n\n## Requirements\n\n* iOS 10+\n* Swift 5+\n* XCode 10+\n\n## Download\n\n### CocoaPods\n\nCurrently, you can use the master or develop branches and git directly until the API has stabilized.\n\n\tplatform :ios, '9.0'\n\tuse_frameworks!\n\n    pod 'SwiftyTeeth', :git =\u003e 'https://github.com/RobotPajamas/SwiftyTeeth.git', :branch =\u003e 'master'\n\n### Carthage\n\nInstructions coming soon.\n\n## Issues\n\nPlease report all bugs or feature requests to: https://github.com/RobotPajamas/SwiftyTeeth/issues\n\n## Swifty Community\n\nOther iOS-centric Bluetooth libraries.\n\n* [RxSwiftyTeeth](https://github.com/RobotPajamas/RxSwiftyTeeth)\n* [BluetoothKit](https://github.com/rhummelmose/BluetoothKit)\n* [Bluetonium](https://github.com/e-sites/Bluetonium)\n* [RxBluetoothKit](https://github.com/Polidea/RxBluetoothKit)\n* [BlueCap](https://github.com/troystribling/BlueCap)\n* [Swift-LightBlue](https://github.com/Pluto-Y/Swift-LightBlue)\n* [PromiseKit/CoreBluetooth](https://github.com/PromiseKit/CoreBluetooth)\n* [RedBearLab](https://github.com/RedBearLab/iOS)\n* [SwiftyBluetooth](https://github.com/tehjord/SwiftyBluetooth)\n* [LGBluetooth](https://github.com/LGBluetooth/LGBluetooth)\n* [RZBluetooth](https://github.com/Raizlabs/RZBluetooth)\n\n## License\n\nThe Apache License (Apache)\n\n    Copyright (c) 2019 Robot Pajamas\n\n    Licensed under the Apache License, Version 2.0 (the \"License\");\n    you may not use this file except in compliance with the License.\n    You may obtain a copy of the License at\n\n    http://www.apache.org/licenses/LICENSE-2.0\n\n    THE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR\n    IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,\n    FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE\n    AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER\n    LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,\n    OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE\n    SOFTWARE.\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Frobotpajamas%2Fswiftyteeth","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Frobotpajamas%2Fswiftyteeth","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Frobotpajamas%2Fswiftyteeth/lists"}