easy-peasy icon indicating copy to clipboard operation
easy-peasy copied to clipboard

Why destucting properties causing TypeScript error

Open 1alexvash opened this issue 4 years ago • 4 comments

I have the following code

import { createStore, action } from "easy-peasy";

import { Action } from "easy-peasy";

export type Task = {
  name: string;
  description: string;
};
export interface StoreModel {
  todos: Task[];
  addTodo: Action<StoreModel, Task>;
}

const defaultTodos = [
  {
    name: "First task",
    description: "",
  },
  {
    name: "Second task",
    description: "",
  },
  {
    name: "Third task",
    description: "",
  },
];

const store = createStore<StoreModel>({
  todos: defaultTodos,
  addTodo: action((state, payload) => {
    state.todos.push(payload);
  }),
});

export default store;

I want to separate state and actions into separate folders, as I used to do with regular javascript to simplify logic, but it causes an error

const state = {
  todos: defaultTodos,
};

const actions = {
  addTodo: action((state, payload) => {
    state.todos.push(payload);
  }),
};

const store = createStore<StoreModel>({
  ...state,
  ...actions,
});

export default store;

image

1alexvash avatar Aug 28 '21 15:08 1alexvash

I have rewritten my code to this version, and now I can destruct those properties

import { createStore, action, State } from "easy-peasy";

interface StoreModel {
  fruits: string[];
}

const store = createStore({
  fruits: ["🍎", "🍊", "🍇"],
  addFruit: action((state: State<StoreModel>, payload) => {
    state.fruits.push(payload);
  }),
});

export default store;

Can anyone tell me if this is correct TypeScript typing?

1alexvash avatar Aug 29 '21 15:08 1alexvash

Also, I have rewritten it like this:

import { createStore, action, State, Action } from "easy-peasy";

interface StoreModel {
  fruits: string[];
  addFruit: Action<StoreModel, string>;
}

const store = createStore<StoreModel>({
  fruits: ["🍎", "🍊", "🍇"],
  addFruit: action((state, payload) => {
    state.fruits.push(payload);
  }),
});

export default store;

It does work, but I destruct actions into a separate folder. I'm not sure what is the right way to approach TS typings

1alexvash avatar Aug 29 '21 15:08 1alexvash

I have a similar code in my codebase and it works. The only difference is that I define some types. Maybe this works for you.

type Task = {
  name: string,
  description: string
}

type State = {
  todos: Task[]
}

type Actions = {
  addTodo: Action<StoreModel, Task>
}

type StoreModel = State & Actions

... 

const state: State = {
  todos: defaultTodos,
};

const actions: Actions = {
  addTodo: action((state, payload) => {
    state.todos.push(payload);
  }),
};

const store = createStore<StoreModel>({
  ...state,
  ...actions,
});

export default store;

You can use interfaces too. I'm more used to types.

viczaca avatar Sep 07 '21 16:09 viczaca

@1alexvash can you try this;

import type { State, Actions } from 'easy-peasy';

const state: State<StoreModel> = {
  todos: defaultTodos,
};

const actions: Actions<StoreModel> = {
  addTodo: action((state, payload) => {
    state.todos.push(payload);
  }),
};

const store = createStore<StoreModel>({
  ...state,
  ...actions,
});

export default store;

ctrlplusb avatar Sep 15 '22 14:09 ctrlplusb