Git Product home page Git Product logo

ngrx-wieder's People

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

ngrx-wieder's Issues

[Immer] An immer producer returned a new value *and* modified its draft

Scenario

In a complex application I implement some type of spreadsheet. On initialization I create the table and add a row, something like that:

newState = {
        ...newState,
        table: {
          ...newState.table,
          rows: [newRow]
        }
      };

Where "newRow" was created before. If I keep this code block, an error occurs (see below). If I remove it, the error disappears. After a lot of testing I'm out of new ideas. Could this be a bug in ngrx-wieder?

Further information

Error message

ERROR Error: [Immer] An immer producer returned a new value *and* modified its draft. Either return a new value *or* modify the draft.
    at n (immer.esm.js:1:216)
    at P (immer.esm.js:1:2508)
    at produce (immer.esm.js:1:16338)
    at reducer (ngrx-wieder.mjs:52:27)
    at ngrx-wieder.mjs:196:35
    at ngrx-store.mjs:374:20
    at combination (ngrx-store.mjs:329:37)
    at ngrx-store.mjs:994:27
    at ngrx-store.mjs:362:20
    at computeNextEntry (ngrx-store-devtools.mjs:457:21)

ngrx-wieder/fesm2020/ngrx-wieder.mjs:52:27

const create = (initialState, ons, config, segmenter) => {
    const map = {};
    for (const on of ons) {
        for (const type of on.types) {
            if (map[type]) {
                const existingReducer = map[type];
                map[type] = (state, action) => on.reducer(existingReducer(state, action), action);
            }
            else {
                map[type] = on.reducer;
            }
        }
    }
    const reducer = ((state = initialState, action, listener) => {
        const r = map[action.type];
        if (r) {
            return produce(state, (draft) => r(draft, action), listener);   // <------------------- ERROR HERE?
        }
        return state;
    });
    return wrap(reducer, config, segmenter);
};

I searched for this error message on Google and found this: https://stackoverflow.com/questions/60806105/error-an-immer-producer-returned-a-new-value-and-modified-its-draft-either-r

Does it have something to do with the definition of anonymous functions by any chance?

System

  • Angular 15.1.2
  • Immer 9.0.12 (same issue with 9.0.19)
  • ngrx-wieder 10.0.2
  • ngrx/store 15.2.1

History to contain only the changes made to the state

I have a project with a lot of data in my store, and it is too expensive to make a complete copy for each action.

Can we think of a history that only contains changes made to the store? Without having a copy for each action?

I would be interested to work on this project

angular 13 support

Hey @nilsmehlhorn, was looking with interest at this library and am wondering whether you still plan to keep it up to date?

I did some testing locally and was able to get it working with angular 13, I can tidy things up and open a pr if you want, but was basically wondering first of all if the project is still alive.

Thanks :)

Import default "produce" breaks jest tests

When running unit tests using jest it breaks the build.

Screenshot 2023-01-03 at 17 51 00

This is related with the way that produce is imported.
You are importing produce as:

import produce, { enablePatches, applyPatches } from 'immer';

When I believe it should be

import { produce, enablePatches, applyPatches } from 'immer';

The following conversation describes in more detail the issue:
immerjs/immer#992

History not filling

Hi,

I'm working on a somewhat legacy project I managed to update to Angular 11 and introduced immer + wieder.

Unfortunately my code does not work as expected.

This is my reducer file (shortened)

export interface IDashboardState extends UndoRedoState {
  dashboards: DashboardModel[]
  currentDashboardId: string | undefined
}

export const initialState: IDashboardState = {
  dashboards: [],
  currentDashboardId: undefined,
  ...initialUndoRedoState
}

const undoableActions = [
  DashboardActions.updateWidget,
  DashboardActions.addWidgetToDashboard,
  DashboardActions.removeWidgetFromDashboard
]

const { createUndoRedoReducer } = undoRedo({ allowedActionTypes: undoableActions.map(a => a.type) })

export const dashboardReducer = createUndoRedoReducer(
  initialState,
  produceOn(DashboardActions.addWidgetToDashboard, (state, action) => {
    const dashboardIdx = state.dashboards.findIndex(d => d.id === action.dashboardId)
    if (dashboardIdx >= 0) {
      state.dashboards[dashboardIdx].widgets.push(action.widget)
    }
    return state
  }),
)

One thing that confuses me, is that I have to return the state, even though I use "produceOn":

TS2345: Argument of type '(state: WritableDraft<IDashboardState>, action: { dashboards: DashboardModel[]; } & TypedAction<"[ProjectEffects] Set Dashboards"> & { ...; }) => void' is not assignable to parameter of type 'ProduceOnReducer<void, [ActionCreator<"[ProjectEffects] Set Dashboards", (props: { dashboards: DashboardModel[]; }) => { dashboards: DashboardModel[]; } & TypedAction<"[ProjectEffects] Set Dashboards">>], void>'.   Types of parameters 'state' and 'state' are incompatible.     Type 'void' is not assignable to type 'WritableDraft<IDashboardState>'.

The other, more problematic thing is that I can't undo anything. I debugged the history within the state and found out, that it is an empty object even after dispatching multiple allowed actions.

These are the versions:

"@angular/core": "11.2.14"
"immer": "9.0.12",
"ngrx-immer": "1.0.3",
"ngrx-wieder": "6.0.2",

What might be the problem and how could I fix it?

Best regards

Migrate to Angular & NgRx 9

Upgrading to Angular 9 should be hassle-free since the library is barely using any framework API.

Upgrading to NgRx 9, however, we have to deal with some changes to support createReducer and the on function which are used in companion to replace switch statements inside reducers.

The reducer from the example application would look along the lines of this (without immer.js):

const reducer = createReducer(
  initialState,
  on(addTodo, state => ...),
  on(toggleTodo, state => ...)
  ...
)

timdeschryver/ngrx-etc provides a replacement for on, called mutableOn which wraps the produce function from immer.

My first idea involves passing the patch listener to an extended version of mutableOn. This requires a factory function for the reducer in order to keep the API for undoRedo somewhat similar:

const reducerFactory = (listener) => createReducer(
  initialState,
  mutableOn(addTodo, (state, next) => ..., listener),
  mutableOn(toggleTodo, (state, next) => ..., listener)
  ...

However, this seems inconvenient. It'd be more convenient to turn things around and provide the required functions while hooking them into an instance of undeRedo beforehand:

const {produceOn, wrapReducer} = undoRedo(config);
const reducer = wrapReducer(createReducer(
  initialState,
  produceOn(addTodo, (state, next) => ...),
  produceOn(toggleTodo, (state, next) => ...)
  ...
))

Implementation would follow something like this:

const undoRedo = (config) => {
  /* vars for patches */
  const produceOn = (action, producer) => /* similar to mutableOn, but store patches */
  const wrapReducer = (reducer) => (state, action) {
    /* access patches like before */
  }
  return {produceOn, wrapReducer}
}

Error with ngrx 11

Following the documentation to setup ngrx-wieder, I'm getting this errors:

Error: node_modules/ngrx-wieder/lib/produce-on.d.ts:2:10 - error TS2724: '"../../@ngrx/store/ngrx-store"' has no exported member named 'On'. Did you mean 'on'?

2 import { On } from '@ngrx/store';
~~

Error: node_modules/ngrx-wieder/lib/undo-redo.reducer.d.ts:1:33 - error TS2724: '"../../@ngrx/store/ngrx-store"' has no exported member named 'On'. Did you mean 'on'?

1 import { Action, ActionReducer, On } from "@ngrx/store";

Seems that the name of ngrx's On has changed to lower-case on...

I'm using:

"@ngrx/store": "^11.0.1",
"immer": "^9.0.1",
"ngrx-wieder": "^5.0.0",
"rxjs": "~6.6.6",

Implementing with lazy-loaded feature modules

Hey @nilsmehlhorn!

This library is awesome. I'm wondering how I go about implementing this across multiple lazy-loaded feature modules. Does the library support such a configuration like this:

StoreModule.forRoot(appReducer),
StoreModule.forFeature('feature-a', featureAReducers),
StoreModule.forFeature('feature-b', featureBReducers);
StoreModule.forFeature('feature-c', featureCReducers);

It seems that the provided example simply invokes the undoRedo({ ... }) in the app reducer. Would I invoke undoRedo({ undoActionType: 'UNDO_FEATURE_A', redoActionType: 'REDO_FEATURE_A', }) in each featureReducer and modify the config?

Second, having this functionality would appear to split the undoRedo patching into separate state slices, making a global undoRedo not possible or much more difficult to implement? This seems very similar to the segmentationOverride option in the config.

I will experiment with some different configurations and report back. Any help is appreciated!

Feature request: actions for enable/disable undo & redo

Description of the feature

As soon as undo & redo is disabled, the history stops growing and the UNDO and REDO actions do not have any effect. After the undo&redo was re-enabled the undo function reverts the state to the state before the deactivation.

Problem

There are situations where you want to enable/disable undo&redo. For example: I'm currently working on an app that allows an combination of manual and automatic processing of data. While the user does changes to the data (manual processing) the undo & redo shoud be enabled. As soon as the user triggers the automatic processing, he shouldn't be able to do undo & redo as long as the automatic processing is running.

Workaround

I'm currently using a workaround: As long as undo&redo is disabled, these actions are not triggered. But the problem is, that the automatic process uses the same actions that are allowed to be redone/undone. That means the history keeps growing although it shouldn't. That's why I call the CLEAR action after each time an allowed-action type was called while the undo & redo is disabled. The disadvantage of this workaround is that I lost the whole history.

Suggestion

It would be nice if there are any actions to enable/disable redo & undo. For example: 'ENABLE' and 'DISABLE'
Does this makes sense?

AOT error from Angular 'ngrx-wieder' contains deep imports into

Warning: Entry point 'ngrx-wieder' contains deep imports into 'C:/msweb/sign-studio/node_modules/@ngrx/store/src/models'. This is probably not a problem, but may cause the compilation of entry points to be out of order.
Compiling @angular/core : es2015 as esm2015

CRUD operations support

In a case where all the changes (CRUD ops) done by user are persisted, how to do undo/redo in this case? - can you please provide any sample code?

Feature Module it's not working

I'm trying to use this library but the state it's not showing properly. I put in a feature module and did not work. Please can u help resolve this issue?

installation of 4.0.2 failed

Problem:

npm install --save ngrx-wieder@latest
npm ERR! code ERESOLVE
npm ERR! ERESOLVE unable to resolve dependency tree
npm ERR! 
npm ERR! While resolving: [email protected]
npm ERR! Found: @angular/[email protected]
npm ERR! node_modules/@angular/common
npm ERR!   @angular/common@"11.0.4" from the root project
npm ERR! 
npm ERR! Could not resolve dependency:
npm ERR! peer @angular/common@"^10.0.0" from [email protected]
npm ERR! node_modules/ngrx-wieder
npm ERR!   ngrx-wieder@"4.0.2" from the root project
npm ERR! 
npm ERR! Fix the upstream dependency conflict, or retry
npm ERR! this command with --force, or --legacy-peer-deps
npm ERR! to accept an incorrect (and potentially broken) dependency resolution.
npm ERR! 
npm ERR! See /Users/julian/.npm/eresolve-report.txt for a full report.

npm ERR! A complete log of this run can be found in:
npm ERR!     /Users/julian/.npm/_logs/2021-02-16T11_29_57_157Z-debug.log

Comment

I'm already using Angular 11, but since [email protected] worked with Angular 11, I thorught 4.0.2 would work, too.

Can I use PatchListener with Class?

Change state todos to an Class instance, then can't get undoredo stack from ngrx-wi`eder

// app.state.ts
export class Todos {
  list: Todo[] = [
    {id: id(), text: 'Travel', checked: true},
    {id: id(), text: 'Relax', checked: false},
    {id: id(), text: 'Work', checked: false}
  ]

  addTodo(id, text) {
    this.list.push(new Todo(id, text))
  }
}

export const initial: State = {
  todos: new Todos()
}

// app.reducer.ts
 case addTodo.type:
        // next.todos.push({id: id(), text: action.text, checked: false})
        next.todos.addTodo(id(), action.text)

I think immer just shallow copy the instance object, when I add new todo, actually change in the deep todos.list array. Do you have some idea ? Thank you.

6.0.2 version dependency on Angular 11

When I try to install the 6.0.2 version this error occurs when intalling the dependecies

npm ERR! ERESOLVE unable to resolve dependency tree
npm ERR! 
npm ERR! While resolving: [email protected]
npm ERR! Found: @angular/[email protected]
npm ERR! node_modules/@angular/common
npm ERR!   @angular/common@"~12.1.2" from the root project
npm ERR! 
npm ERR! Could not resolve dependency:
npm ERR! peer @angular/common@"^11.0.0" from [email protected]
npm ERR! node_modules/ngrx-wieder
npm ERR!   ngrx-wieder@"6.0.2" from the root project
npm ERR! 
npm ERR! Fix the upstream dependency conflict, or retry
npm ERR! this command with --force, or --legacy-peer-deps
npm ERR! to accept an incorrect (and potentially broken) dependency resolution.
npm ERR! 
npm ERR! See /home/digob/.npm/eresolve-report.txt for a full report.

npm ERR! A complete log of this run can be found in:
npm ERR!     /home/digob/.npm/_logs/2021-07-15T20_03_14_190Z-debug.log```

Feature Request / Question - Possibility to see differences of Undo / Redo within an Effect

Hi Nils,

I'm fairly new to the whole concept of ngrx, immer.js and wieder.js so sorry in advance if this does not really concern wieder.js and can be solved otherwise.
I'd like to access the changes reversed or re-reapplied in an ngrx effect in order to reflect the undone/redone changes within a database. Reapplying the whole context would be possible, but a huge performance impact when there's only one object that needs to be adjusted.

Is there a possiblity that the Undo/Redo actions can put out the applied changes to an effect or that these differences can be accessed somehow?

Can't install version 3.1.x with angular 9.1.x and npm 7.x

Hi, while trying to install the library (version 3.1.1) into an angular 9.1.x application I'm getting this error:

npm ERR! code ERESOLVE
npm ERR! ERESOLVE unable to resolve dependency tree
npm ERR! 
npm ERR! While resolving: [email protected]
npm ERR! Found: @angular/[email protected]
npm ERR! node_modules/@angular/common
npm ERR!   @angular/common@"9.1.13" from the root project
npm ERR! 
npm ERR! Could not resolve dependency:
npm ERR! peer @angular/common@"^8.0.1 - ^9.0.7" from [email protected]
npm ERR! node_modules/ngrx-wieder
npm ERR!   ngrx-wieder@"3.1.1" from the root project
npm ERR! 
npm ERR! Fix the upstream dependency conflict, or retry
npm ERR! this command with --force, or --legacy-peer-deps
npm ERR! to accept an incorrect (and potentially broken) dependency resolution.
npm ERR! 
npm ERR! See /home/menecats/.npm/eresolve-report.txt for a full report.

npm ERR! A complete log of this run can be found in:
npm ERR!     /home/menecats/.npm/_logs/2021-08-25T10_47_23_851Z-debug.log

This error only appears in npm 7.x (currently i'm using 7.21.0) as they've changed the peer dependency management strategy.
I've installed the library with the --legacy-peer-deps and it works as intended.
Can you please update the peer dependency for @angular/common to support also angular 9.1 directly with npm 7?

Thanks

Using createUndoRedoReducer with StoreModule.forFeature doesn't work

I followed the installation guide created a reducer for a feature instead of root and it didn't work, not getting any errors as well other than the one below, which is just error because the state doesn't get initialized and the selectors are trying to access the data.(ngrx-wieder tries to access the store as well and fails).

Doing nothing fancy here, just trying to create a reducer and use it with StoreModule.forFeature('databoard', undoableRedcucer)

If I use createReducer from ngrx/store It works fine.

error-handler.service.ts:23 Error: TypeError: Cannot read property 'histories' of undefined
    at ngrx-wieder.js:88
    at reducer (databoard.reducer.ts:289)
    at ngrx-store.js:290
    at combination (ngrx-store.js:245)
    at ngrx-store.js:752
    at ngrx-store.js:752
    at ngrx-store.js:278
    at computeNextEntry (ngrx-store-devtools.js:426)
    at recomputeStates (ngrx-store-devtools.js:460)
    at ngrx-store-devtools.js:734

ngrx-store.js:695 @ngrx/store: The feature name "databoard" does not exist in the state, therefore createFeatureSelector cannot access it.  Be sure it is imported in a loaded module using StoreModule.forRoot('databoard', ...) or StoreModule.forFeature('databoard', ...).  If the default state is intended to be undefined, as is the case with router state, this development-only warning message can be ignored.
(anonymous) @ ngrx-store.js:695
(anonymous) @ ngrx-store.js:571
defaultStateFn @ ngrx-store.js:571

databoard.reducer.ts:319 selectorState undefined
error-handler.service.ts:23 Error: TypeError: Cannot read property 'histories' of undefined
    at ngrx-wieder.js:88
    at reducer (databoard.reducer.ts:289)
    at ngrx-store.js:290
    at combination (ngrx-store.js:245)
    at ngrx-store.js:752
    at ngrx-store.js:752
    at ngrx-store.js:278
    at ngrx-store-devtools.js:737
    at Array.map (<anonymous>)
    at ngrx-store-devtools.js:737

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.