[{"data":1,"prerenderedAt":-1},["ShallowReactive",2],{"project-6899":3},{"id":4,"name":5,"fullName":6,"owner":7,"repo":5,"description":8,"homepage":9,"htmlUrl":9,"language":10,"languages":9,"totalLinesOfCode":9,"stars":11,"forks":12,"watchers":13,"openIssues":14,"contributorsCount":15,"subscribersCount":15,"size":15,"stars1d":16,"stars7d":16,"stars30d":16,"stars90d":15,"forks30d":15,"starsTrendScore":17,"compositeScore":18,"rankGlobal":9,"rankLanguage":9,"license":19,"archived":20,"fork":20,"defaultBranch":21,"hasWiki":22,"hasPages":20,"topics":23,"createdAt":9,"pushedAt":9,"updatedAt":24,"readmeContent":25,"aiSummary":26,"trendingCount":15,"starSnapshotCount":15,"syncStatus":27,"lastSyncTime":28,"discoverSource":29},6899,"Bond","DeclarativeHub\u002FBond","DeclarativeHub","A Swift binding framework",null,"Swift",4204,352,89,44,0,1,3,62.24,"MIT License",false,"master",true,[],"2026-06-12 04:00:30","# Bond, Swift Bond\n\n[![Platform](https:\u002F\u002Fimg.shields.io\u002Fcocoapods\u002Fp\u002FBond.svg?style=flat)](http:\u002F\u002Fcocoadocs.org\u002Fdocsets\u002FBond\u002F)\n[![CI Status](https:\u002F\u002Ftravis-ci.org\u002FDeclarativeHub\u002FBond.svg?branch=master)](https:\u002F\u002Ftravis-ci.org\u002FDeclarativeHub\u002FBond)\n[![Twitter](https:\u002F\u002Fimg.shields.io\u002Fbadge\u002Ftwitter-@srdanrasic-red.svg?style=flat)](https:\u002F\u002Ftwitter.com\u002Fsrdanrasic)\n\n\u003Cbr>\n\n**Update: Bond 7 has been released!** Check out [the migration guide](Documentation\u002FMigration.md) to learn more about the update.\n\nBond is a Swift binding framework that takes binding concepts to a whole new level. It's simple, powerful, type-safe and multi-paradigm - just like Swift.\n\nBond is built on top of ReactiveKit and bridges the gap between the reactive and imperative paradigms. You can use it as a standalone framework to simplify your state changes with bindings and reactive data sources, but you can also use it with ReactiveKit to complement your reactive data flows with bindings, reactive delegates and reactive data sources.\n\nBond is a backbone of the [Binder Architecture](https:\u002F\u002Fgithub.com\u002FDeclarativeHub\u002FTheBinderArchitecture) - a preferred architecture to be used with the framework.\n\n## Why use Bond?\n\nSay that you would like to do something when text of a text field changes. Well, you could setup the *target-action* mechanism between your objects and go through all that target-action selector registration pain, or you could simply use Bond and do this:\n\n```swift\ntextField.reactive.text.observeNext { text in\n    print(text)\n}\n```\n\nNow, instead of printing what the user has typed, you can _bind_ it to a label:\n\n```swift\ntextField.reactive.text.bind(to: label.reactive.text)\n```\n\nBecause binding to a label text property is so common, you can even do:\n\n```swift\ntextField.reactive.text.bind(to: label)\n```\n\nThat one line establishes a binding between the text field's text property and label's text property. In effect, whenever user makes a change to the text field, that change will automatically be propagated to the label.\n\nMore often than not, direct binding is not enough. Usually you need to transform input is some way, like prepending a greeting to a name. As Bond is backed by [ReactiveKit](https:\u002F\u002Fgithub.com\u002FDeclarativeHub\u002FReactiveKit) it has full confidence in functional paradigm.\n\n```swift\ntextField.reactive.text\n  .map { \"Hi \" + $0 }\n  .bind(to: label)\n```\n\nWhenever a change occurs in the text field, new value will be transformed by the closure and propagated to the label.\n\nNotice how we have used `reactive.text` property of the text field. It is an observable representation of the `text` property provided by Bond framework. There are many other extensions like that one for various UIKit components. They are all placed within the `.reactive` proxy.\n\nFor example, to observe button events do:\n\n```swift\nbutton.reactive.controlEvents(.touchUpInside)\n  .observeNext { e in\n    print(\"Button tapped.\")\n  }\n```\n\nHandling `touchUpInside` event is used so frequently that Bond comes with the extension just for that event:\n\n```swift\nbutton.reactive.tap\n  .observeNext {\n    print(\"Button tapped.\")\n  }  \n```\n\nYou can use any ReactiveKit operators to transform or combine signals. Following snippet depicts how values of two text fields can be reduced to a boolean value and applied to button's enabled property.\n\n```swift\ncombineLatest(emailField.reactive.text, passField.reactive.text) { email, pass in\n    return email.length > 0 && pass.length > 0\n  }\n  .bind(to: button.reactive.isEnabled)\n```\n\nWhenever user types something into any of these text fields, expression will be evaluated and button state updated.\n\nBond's power is not, however, in coupling various UI components, but in the binding of the business logic layer (i.e. Service or View Model) to the View layer and vice-versa. Here is how one could bind user's number of followers property of the model to the label.\n\n```swift\nviewModel.numberOfFollowers\n  .map { \"\\($0)\" }\n  .bind(to: label)\n```\n\nPoint here is not in the simplicity of a value assignment to the text property of a label, but in the creation of a binding which automatically updates label text property whenever the number of followers change.\n\nBond also supports two way bindings. Here is an example of how you could keep username text field and username property of your View Model in sync (whenever any of them change, other one will be updated too):\n\n```swift\nviewModel.username\n  .bidirectionalBind(to: usernameTextField.reactive.text)\n```\n\nBond is also great for observing various different events and asynchronous tasks. For example, you could observe a notification like this:\n\n```swift\nNotificationCenter.default.reactive.notification(\"MyNotification\")\n  .observeNext { notification in\n    print(\"Got \\(notification)\")\n  }\n  .dispose(in: bag)\n```\n\nLet me give you one last example. Say you have an array of repositories you would like to display in a collection view. For each repository you have a name and its owner's profile photo. Of course, photo is not immediately available as it has to be downloaded, but once you get it, you want it to appear in collection view's cell. Additionally, when user does 'pull down to refresh' and your array gets new repositories, you want those in collection view too.\n\nSo how do you proceed? Well, instead of implementing a data source object, observing photo downloads with KVO and manually updating the collection view with new items, with Bond you can do all that in just few lines:\n\n```swift\nrepositories.bind(to: collectionView) { array, indexPath, collectionView in\n  let cell = collectionView.dequeueReusableCell(withReuseIdentifier: \"Cell\", for: indexPath) as! RepositoryCell\n  let repository = array[indexPath.item]\n\n  repository.name\n    .bind(to: cell.nameLabel)\n    .dispose(in: cell.onReuseBag)\n\n  repository.photo\n    .bind(to: cell.avatarImageView)\n    .dispose(in: cell.onReuseBag)\n\n  return cell\n}\n```\n\nYes, that's right!\n\n## Reactive Extensions\n\nBond is all about bindings and other reactive extensions. To learn more about how bindings work and how to create your own bindings check out [the documentation on bindings](Documentation\u002FBindings.md).\n\nIf you are interested in what bindings and extensions are supported, just start typing `.reactive.` on any UIKit or AppKit object and you will get the list of available extensions. You can also skim over the [source files](https:\u002F\u002Fgithub.com\u002FDeclarativeHub\u002FBond\u002Ftree\u002Fmaster\u002FSources\u002FBond\u002FUIKit) to get an overview.\n\n## Observable Collections\n\nWhen working with arrays usually we need to know how exactly did an array change. New elements could have been inserted into the array and old ones deleted or updated. Bond provides mechanisms for observing such fine-grained changes.\n\nFor example, Bond provides you with a `(Mutable)ObservableArray` type that can be used to generate and observe fine-grained changes.\n\n```swift\nlet names = MutableObservableArray([\"Steve\", \"Tim\"])\n\n...\n\nnames.observeNext { e in\n  print(\"array: \\(e.collection), diff: \\(e.diff), patch: \\(e.patch)\")\n}\n```\n\nYou work with the observable array like you would work with the array it encapsulates.\n\n```swift\nnames.append(\"John\") \u002F\u002F prints: array: [\"Steve\", \"Tim\", \"John\"], diff: Inserts: [2], patch: [I(John, at: 2)]\nnames.removeLast()   \u002F\u002F prints: array: [\"Steve\", \"Tim\"], diff: Deletes: [2], patch: [D(at: 2)]\nnames[1] = \"Mark\"    \u002F\u002F prints: array: [\"Steve\", \"Mark\"], diff: Updates: [1], patch: [U(at: 1, newElement: Mark)]\n```\n\nPeek into [observable collections documentation](Documentation\u002FObservableCollections.md) to learn more about observable collections.\n\n## Data Source Signals\n\nObservable collections and other data source signals enable us to build powerful UI bindings. For example, an observable array can be bound to a collection view just like this:\n\n```swift\nnames.bind(to: collectionView, cellType: UserCell.self) { (cell, name) in\n    cell.titleLabel.text = name\n}\n```\n\nNo need to implement data source objects and do everything manually. Check out [documentation on the data source signals](Documentation\u002FDataSourceSignals.md) to learn more about them and about table or collection view bindings. \n\n## Protocol Proxies\n\nBond provides `NSObject` extensions that make it easy to convert delegate method calls into signal. The extensions are built on top of ObjC runtime and enable you to intercept delegate method invocations and convert them into signal events.\n\nBond uses protocol proxies to implement table and collection view bindings and to provide signals like `tableView.reactive.selectedRowIndexPath`. Check out [the protocol proxies documentation](Documentation\u002FProtocolProxies.md) to learn more.\n\n## Community Extensions\n\nMake sure to check out [Extensions directory](Extensions). It contains extensions that make Bond easy to use with other frameworks and libraries, like Realm. \n\nIf you have an extensions that makes your favourite framework work with Bond and you'd like to share it with everyone, we'd be more than happy to accept your PR. \n\n## Requirements\n\n* iOS 8.0+ \u002F macOS 10.11+ \u002F tvOS 9.0+\n* Swift 4.2\n\n## Communication\n\n* If you'd like to ask a question, open an issue.\n* If you found a bug, open an issue.\n* If you have a feature request, open an issue.\n* If you want to contribute, submit a pull request (include unit tests).\n\n## Installation\n\n### Carthage\n\n1. Add the following to your *Cartfile*:\n \n    ```\n    github \"DeclarativeHub\u002FBond\"\n    ```\n \n2. Run `carthage update`\n3. Add the framework as described in [Carthage Readme](https:\u002F\u002Fgithub.com\u002FCarthage\u002FCarthage#adding-frameworks-to-an-application)\n\n### Accio\n\n1. Add the following to your Package.swift:\n\n    ```swift\n    .package(url: \"https:\u002F\u002Fgithub.com\u002FDeclarativeHub\u002FBond.git\", .upToNextMajor(from: \"7.4.1\")),\n    ```\n\n2. Next, add `Bond` to your App targets dependencies like so:\n\n    ```swift\n    .target(\n        name: \"App\",\n        dependencies: [\n            \"Bond\",\n        ]\n    ),\n    ```\n\n3. Then run `accio update`.\n\n### CocoaPods\n\n1. Add the following to your *Podfile*:\n  \n    ```\n    pod 'Bond'\n    ```\n  \n2. Run `pod install`.\n\n## License\n\nThe MIT License (MIT)\n\nCopyright (c) 2015-2019 Srdan Rasic (@srdanrasic)\n\nPermission is hereby granted, free of charge, to any person obtaining a copy\nof this software and associated documentation files (the \"Software\"), to deal\nin the Software without restriction, including without limitation the rights\nto use, copy, modify, merge, publish, distribute, sublicense, and\u002For sell\ncopies of the Software, and to permit persons to whom the Software is\nfurnished to do so, subject to the following conditions:\n\nThe above copyright notice and this permission notice shall be included in\nall copies or substantial portions of the Software.\n\nTHE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR\nIMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,\nFITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE\nAUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER\nLIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,\nOUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN\nTHE SOFTWARE.\n","Bond 是一个 Swift 绑定框架，旨在简化界面元素与数据模型之间的连接。它基于 ReactiveKit 构建，支持声明式编程风格，同时保持了 Swift 的简洁性和类型安全性。通过 Bond，开发者可以轻松地将文本框、按钮等 UI 控件的状态变化绑定到视图或其他数据源上，实现双向数据流的自动更新。此外，Bond 还提供了丰富的转换操作，允许对绑定的数据进行处理后再显示。这个框架非常适合需要频繁更新 UI 以反映数据变化的应用场景，如表单验证、实时数据显示等。",2,"2026-06-11 03:09:28","top_language"]