A New, Modern Reactive State Management Library for Swift and SwiftUI (The iOS implementation of Recoil)

Overview

RecoilSwift

RecoilSwift is a lightweight & reactive swift state management library. RecoilSwift is a SwiftUI implementation of recoil.js which powered by Facebook.

Recoil is an alternate option to replace of the Redux(reswift) or MVVM.

Version License Platform

What is recoil

Recoil

Requirements

  • iOS 13+
  • Xcode 12.4+

NOTE: Currently this library only support for SwiftUI, UIKit is not available. But it planned.

In recent release, we re-implement this library with react hooks pattern which making the usage of this lib is more similar with official way.

Installation

  1. In Xcode, open your project and navigate to FileSwift PackagesAdd Package Dependency...
  2. Paste the repository URL (https://github.com/hollyoops/RecoilSwift.git) and click Next.
  3. For Rules, select Branch (with branch set to master).
  4. Click Finish.

RecoilSwift is available through CocoaPods. To install it, simply add the following line to your Podfile:

pod 'RecoilSwift'

State Management Data Flow

    ← ← ← ← ← ← ← ← ← atoms ← ← ← ← ← ← ← ←
    ↓                                     ↑ 
    ↓                                     ↑
selectors                       set / writeable selectors 
    ↓                                     ↑ 
    ↓                                     ↑                                               
    → → → → → → → view(hooks) → → → → → → →

<img src="image.png" width="700" height="378"/>

Basic Usage

Create Atom / Selector:

// Create a Atom
let allBooksState = atom { [Book]() }

// Create readonly Selector
let currentBooksSelector = selector { get -> [Book] in
    let books = get(allBooksState)
    if let category = get(selectedCategoryState) {
        return books.filter { $0.category == category }
    }
    return books
}

// Create parameterized selector 
let someSelector = selectorFamily { (id: String, get: ReadonlyContext) -> AnyPublisher<[String], Error> in
    // Do some logic in here with id
}

Use Atom / Selector in SwiftUI

Because the useRecoilXXX series API is based on Hooks. so it should follow all the rule of hooks

struct YourView: RecoilView { // You have to implement the RecoilView protocol
    var hookBody: some View { 
     let currentBooks = useRecoilValue(currentBooksSelector)

     let allBooks = useRecoilState(allBooksStore)

     let loadable = useRecoilValueLoadable(fetchRemoteDataByID(someID))
      // Your UI Code
    }
}

Advance Usage

Async task

let fetchRemoteDataById = selectorFamily { (id: String, get: ReadonlyContext) -> AnyPublisher<[String], Error> in
      Deferred {
        Future { promise in
              // Do some logic in here with id
        }
    }.eraseToAnyPublisher()
}

// In some function
func someView() -> some View {
    HookScope { // when your view is not implement with RecoilView, you have to use `HookScope`
        let id = useRecoilValue(selectedCategoryState)
        let loadable = useRecoilValueLoadable(fetchRemoteDataById(id))
        
        // This body will be render after task completed
        return VStack {
            // while loading
            if loadable.isLoading {
                ProgressView()
            }

            // when error
            if let err = loadable.error {
                errorView(err)
            }

            // when data fulfill
            if let names = loadable.data {
                dataView(allBook: names, onRetry: loadable.retry)
            }
        }
    }
}

Documentation

API Reference

TODOs

  • [feature]Add refresh for loadable
  • [performance]Fix circular reference for selector
  • [performance]Caches value for selector
  • [feature]Make UIKit compatible

Reference:

You might also like...
ReSwift is a Redux-like implementation of the unidirectional data flow architecture in Swift.
ReSwift is a Redux-like implementation of the unidirectional data flow architecture in Swift.

ReSwift is a Redux-like implementation of the unidirectional data flow architecture in Swift. ReSwift helps you to separate three important concerns of your app's components.

When is a lightweight implementation of Promises in Swift
When is a lightweight implementation of Promises in Swift

Description When is a lightweight implementation of Promises in Swift. It doesn't include any helper functions for iOS and OSX and it's intentional, t

📬 A lightweight implementation of an observable sequence that you can subscribe to.
📬 A lightweight implementation of an observable sequence that you can subscribe to.

Features Lightweight Observable is a simple implementation of an observable sequence that you can subscribe to. The framework is designed to be minima

Open source implementation of Apple's Combine framework for processing values over time.
Open source implementation of Apple's Combine framework for processing values over time.

OpenCombine Open-source implementation of Apple's Combine framework for processing values over time. The main goal of this project is to provide a com

A Swift based Future/Promises Library for IOS and OS X.

FutureKit for Swift A Swift based Future/Promises Library for IOS and OS X. Note - The latest FutureKit is works 3.0 For Swift 2.x compatibility use v

A micro-library for creating and observing events.

Signals Signals is a library for creating and observing events. It replaces delegates, actions and NSNotificationCenter with something much more power

SwiftUI-compatible framework for building browser apps with WebAssembly and native apps for other platforms
SwiftUI-compatible framework for building browser apps with WebAssembly and native apps for other platforms

SwiftUI-compatible framework for building browser apps with WebAssembly At the moment Tokamak implements a very basic subset of SwiftUI. Its DOM rende

SwiftUI-compatible framework for building browser apps with WebAssembly and native apps for other platforms
SwiftUI-compatible framework for building browser apps with WebAssembly and native apps for other platforms

SwiftUI-compatible framework for building browser apps with WebAssembly At the moment Tokamak implements a very basic subset of SwiftUI. Its DOM rende

Define and chain Closures with Inputs and Outputs

Closure Define and chain Closures with Inputs and Outputs Examples No Scoped State let noStateCount = ClosureString, String { text in String(repea

Owner
Holly Li
Holly Li
A simple and predictable state management library inspired by Flux + Elm + Redux.

A simple and predictable state management library inspired by Flux + Elm + Redux. Flywheel is built on top of Corotuines using the concepts of structured concurrency. At the core, lies the State Machine which is based on actor model.

Abhi Muktheeswarar 35 Dec 29, 2022
Predictable state management for SwiftUI applications.

SwiftDux Predictable state management for SwiftUI applications. SwiftDux is a state container inspired by Redux and built on top of Combine and SwiftU

Steven Lambion 148 Jul 4, 2022
A library for reactive and unidirectional Swift applications

ReactorKit is a framework for a reactive and unidirectional Swift application architecture. This repository introduces the basic concept of ReactorKit

ReactorKit 2.5k Dec 28, 2022
Reactive extensions to Cocoa frameworks, built on top of ReactiveSwift.

ReactiveSwift offers composable, declarative and flexible primitives that are built around the grand concept of streams of values over time. These primitives can be used to uniformly represent common Cocoa and generic programming patterns that are fundamentally an act of observation.

null 20k Jan 3, 2023
RxXRepository: reactive extension for XRepository

RxXRepository is reactive extension for XRepository. This extension allows imple

Sashko Potapov 1 Jan 6, 2022
VueFlux is the architecture to manage state with unidirectional data flow for Swift, inspired by Vuex and Flux.

Unidirectional State Management Architecture for Swift - Inspired by Vuex and Flux Introduction VueFlux is the architecture to manage state with unidi

Ryo Aoyama 324 Dec 17, 2022
Modern thread-safe and type-safe key-value observing for Swift and Objective-C

Now Archived and Forked PMKVObserver will not be maintained in this repository going forward. Please use, create issues on, and make PRs to the fork o

Postmates Inc. 708 Jun 29, 2022
Swift Apps in a Swoosh! A modern framework for creating iOS apps, inspired by Redux.

Katana is a modern Swift framework for writing iOS applications' business logic that are testable and easy to reason about. Katana is strongly inspire

Bending Spoons 2.2k Jan 1, 2023
Bond is a Swift binding framework that takes binding concepts to a whole new level.

Bond, Swift Bond Update: Bond 7 has been released! Check out the migration guide to learn more about the update. Bond is a Swift binding framework tha

Declarative Hub 4.2k Jan 5, 2023
Very simple Observable and Publisher implementation for iOS apps.

Very simple Observable and Publisher implementation for iOS apps.

Igor Kulman 7 Jun 11, 2022