Vuex-module-decorators: How should I use the VuexModule constructor to implement an abstract store

Created on 12 Aug 2020  路  1Comment  路  Source: championswimmer/vuex-module-decorators

Hi there.

I'm trying to set up my modules to extend an AbstractStore class that implements basic actions and mutations for simple CRUD operations. Whereas the children of AbstractStore implement their respective state, getters and any other actions/mutations that are unique to them.

To implement this I'm passing an endpoint string to its constructor, which is then used in the HTTP requests. Here's a rough example of how I'm trying to implement this:

// store.ts

import { VuexModule, Module, Mutation, Action } from 'vuex-module-decorators'
import { $axios } from '~/utils/api'

@Module({
  stateFactory: true,
  namespaced: true
})
export default abstract class AbstractStore extends VuexModule {

  endpoint: string

  // common state

  constructor(endpoint: string) {
    super() // This displays an error
    this.endpoint = endpoint
  }

  // CRUD Mutations

  @Action
  async create() {
    try {
      const data = this.getProperties
      const response = await $axios.$post(this.endpoint, data)
      this.CREATE(response.data)
    } catch (error) {
      console.error(error)
    }
  }

  @Action
  async read(id: number) {
    try {
      const response = await $axios.$get(this.endpoint + `/${id}`)
      this.READ(response.data)
    } catch (error) {
      console.error(error)
    }
  }

  @Action
  async update() {
    try {
      const data = this.getProperties
      const response = await $axios.$put(this.endpoint + `/${data.id}`, data)
      this.CREATE(response.data)
    } catch (error) {
      console.error(error)
    }
  }

  @Action 
  async delete(id: number) {
    try {
      await $axios.$delete(this.endpoint + `/${id}`)
      this.DELETE(id)
    } catch (error) {
      console.error(error)
    }
  }

  abstract get getProperties(): any
}
// users.ts

import { Module, Mutation, Action } from 'vuex-module-decorators'
import { $axios } from '~/utils/api'
import AbstractStore from './store'

const endpoint = '/api/users'

@Module({
  stateFactory: true,
  namespaced: true
})
export default class UsersStore extends AbstractStore {

  // user state

  constructor() {
    super(endpoint)
  }

  // Other Mutations and Actions

  get getProperties(): any {
    return {
      // package up the user state
    }
  }
}



md5-b4c9141ce3aebedcd7eacd4c9221a891



Expected 1 arguments, but got 0. ts(2554)
vuexmodule.d.ts(16, 17): An argument for 'module' was not provided.

So what should I pass to super to make this work? Can this implementation even work as I want it to? Would love some insight, thanks!

Most helpful comment

Hello,

I had very similar problem.
Each of the Vuex store modules expect the parent module as argument.

Simply in AbstractStore define constructor like:

constructor(module: Mod<ThisType<any>, any>, endpoint: string) {
  super(module);
  this.endpoint = endpoint
}

and in UsersStore

constructor(module: Mod<ThisType<any>, any>) {
  super(module, endpoint);
}

Let us know if it work.

>All comments

Hello,

I had very similar problem.
Each of the Vuex store modules expect the parent module as argument.

Simply in AbstractStore define constructor like:

constructor(module: Mod<ThisType<any>, any>, endpoint: string) {
  super(module);
  this.endpoint = endpoint
}

and in UsersStore

constructor(module: Mod<ThisType<any>, any>) {
  super(module, endpoint);
}

Let us know if it work.

Was this page helpful?
0 / 5 - 0 ratings

Related issues

blainehansen picture blainehansen  路  4Comments

stevefan1999-personal picture stevefan1999-personal  路  5Comments

davidmoshal picture davidmoshal  路  6Comments

Akumzy picture Akumzy  路  5Comments

MagnusJohansson picture MagnusJohansson  路  5Comments