Advice on structuring ReScript project?

Let’s say I have a Stack module type, and I have a ListStack implementation and a VariantStack implementation.

I want the ListStack to have type Stack (so does VariantStack). If I structure it in one file, it becomes like this

module type Stack = {
   // ...
}

module VariantStack: Stack = {
  // ...
}

module ListStack: Stack = {
  // ...
}

But what if I want to separate it into different files? I am thinking something like this:

  • Stack.resi
  • ListStack.res
  • VariantStack.res

But I realized that I can’t have the module type annotation without making it nested. i.e,

// ListStack.res
module ListStack: Stack = {
}

If I want to use it, it becomes ListStack.ListStack. How do I get around this? Sorry if my question is very beginner.

Well, you could go:

// ListStack.res
module __ListStack: Stack = {
}

include __ListStack

But do you need it at all? Unlike records, modules in ReScript are structurally typed, so if it walks like a duck…

The only thing the annotation probably gets you is that if your implementation doesn’t match the Stack spec, type checking will fail earlier than, say, passing unannotaded ListStack to a functor expecting Stack.

2 Likes

Interfaces in ReScript are used solely to hide things. Or abstract details away, if you will. Interfaces do not add any information, they only remove it from outside view.

It can also be handy to ensure that an implementation conforms to some interface though, and a module type can be useful to avoid duplicating interface code. Using a module type makes sense here if you want to ensure that you can swap one implementation out for the other without compilation errors, but it’s not strictly necessary.

To do so in a separate file you can simply add an interface file (.resi) and include the module type in it:

// Collections.res
module type Stack = {
  // ...
}
// ListStack.resi
include Collections.Stack
2 Likes

Ohh interesting approach. Thank you

But do you need it at all? Unlike records, modules in ReScript are structurally typed, so if it walks like a duck…

I did not know this to be the case. Interesting. Thanks

Thank you, I didn’t know you can do it like this.