DataOptic
Optics make working with immutable state painless, but sometimes you may need to perform these immutable updates outside of global state created with createState
.
Examples range from updating React state created with useState
,
updating global state in a Redux reducer
or a Zustand action,
to manipulating your GraphQL cache directly with apollo-client.
A DataOptic
is an Optic that's not focused on global state, but simply on a plain immutable value that you want to produce new versions of.
It retains all of the benefits of the Optics API but without the state management part (no subscribe
method).
Usage
Call the focusOn
function to create a DataOptic from a plain value.
ts
import {focusOn } from "@optics/react";constuser = {name : "John Doe",contact : {address : {number : 1,street : "Rue de la paix",},},credits : {gold : {available : 10,blocked : 3 },silver : {available : 30,blocked : 7 },},};constuserOptic =focusOn (user );
ts
import {focusOn } from "@optics/react";constuser = {name : "John Doe",contact : {address : {number : 1,street : "Rue de la paix",},},credits : {gold : {available : 10,blocked : 3 },silver : {available : 30,blocked : 7 },},};constuserOptic =focusOn (user );
- Call
set
everytime you want to apply a modification where the optic is currently focused.
It returns a newDataOptic
focused on the updated value. - Call
get
to retrieve the final value that got all the previous updates applied to it.
ts
constupdatedUser =focusOn (user ).contact .address .number .set (10).credits .gold .available .set ((prev ) =>prev + 5).get ();
ts
constupdatedUser =focusOn (user ).contact .address .number .set (10).credits .gold .available .set ((prev ) =>prev + 5).get ();
It lets us update both the user's street number and his amount of available gold credits in a single expression.
ts
// updatedUser{name: "Vincent",contact: {mails: "foo@bar.com",address: {number: 10,street: "Rue de la paix",},},credits: {gold: { available: 15, blocked: 3 },silver: { available: 30, blocked: 7 },},};
ts
// updatedUser{name: "Vincent",contact: {mails: "foo@bar.com",address: {number: 10,street: "Rue de la paix",},},credits: {gold: { available: 15, blocked: 3 },silver: { available: 30, blocked: 7 },},};
@optics/data
The @optics/data
package only exports DataOptic
and the focusOn
function, without the rest of the API related to state management.
You can import this package if you are already invested in another state management solution and just want to use Optics to perform immutable updates.