mobx-state-tree
mobx-state-tree copied to clipboard
Typing "self" when splitting actions into multiple files
- [ X ] I've checked documentation and searched for existing issues
- [ X ] I tried the spectrum channel
To better organize my code I'd like to put some action definitions in multiple files. An issue arises with typing "self" when doing this. For example:
File1.ts
import OtherActions from "./file2"
export const MyModel = t.model({foo: t.string}).actions(self => ({
typeOfSelfIsFineHere(){
....
}
})).actions(OtherActions)
File2.ts
import {MyModel} from "./file1"
//TS error 2502 'self' is referenced directly or indirectly in its own type annotation
export default (self: Instance<typeof MyModel>) => ({
typeOfSelfIsErrorHere(){
....
}
})
I'm unable to provide the proper type for "self" when trying to write actions in a separate file because it results in a circular type definition. Any thoughts on how to work around this?
Spectrum question link: https://spectrum.chat/mobx-state-tree/general/typing-self-when-splitting-actions-into-multiple-files~7ab0ccdb-24b2-49bb-a8c0-8462d3aac07e
+1 I have the same problem when I tried move actions and views to separated files.
In your case, you can break the type in two (this works exactly the same technically), and grab the type of the partial type:
File 1
import OtherActions from "./file2"
export const MyBaseModel = t.model({foo: t.string}).actions(self => ({
typeOfSelfIsFineHere(){
....
}
}))
export const MyModel = MyBaseModel.actions(OtherActions)
File 2
import {MyBaseModel} from "./file1"
export default (self: Instance<typeof MyBaseModel>) => ({
typeOfSelfIsErrorHere(){
....
}
})
See also the readme section: https://github.com/mobxjs/mobx-state-tree#typing-self-in-actions-and-views
Now over a year later I've got an 8k line file making up my root MST store and I'm finally getting to attempting splitting it into smaller chunks. Everything has stayed in one file so far because it's easier, but it's starting to be a drain on editor performance.
The technique above works but it gets a bit messy when actions depend upon each other. Any action that calls another action must either be in the same file or yet another name needs to be introduced to hold the state of the partially built store. Unfortunately I don't really see any way around this, anybody have ideas?
This solved my problem (I believe).
File1.ts
import OtherActions from "./file2"
export const MyModel = t.model({foo: t.string}).actions(self => ({
typeOfSelfIsFineHere(){
....
}
})).actions(OtherActions)
File2.ts
export default <T extends IStateTreeNode>(mstInstance: T) => {
const self = mstInstance as unknown as Instance<typeof MyModel>
return {
typeOfSelfIsErrorHere() {
// do something
},
}
}
Hey folks,
This MobX-State-Tree issue is pretty old, and looks like there were some satisfactory answers already.
I'm gonna go ahead and close this out. Thanks for your time!