effekt-lang / effekt-lang/effekt

Module System

Open
#30 2 comments 0 reactions 1 assignee Claimed by @anfark View on GitHub
feature requires-design
Dominant language
Scala
Stars
469
Forks
41
Avg merge
1d 16h
Merged PRs (30d)
23

Description

We want a module system for Effekt. At first we should focus on a simple and clear basis on which we then build interesting extensions.

# Properties

Some features we might want are:

1. A "hello effekt" project should "just work". No configuration required.
2. It should be possible to define modules locally, in a file, and then gradually move parts to different files.
3. Separate compilation should be possible

# Idea

We look at [namespaces in Flix](https://doc.flix.dev/namespaces/) and objects as modules in Scala for inspiration.

We already have interfaces so a first step would be to make the following work:

```
interface A {
def f(): Unit
}

def A = new A {
def f() = ()
}

def main() = {
A.f()
}
```

The second step is to introduce sugar for the above:

```
module A {
def f(): Unit = ()
}

def main() = {
A.f()
}
```

We add syntactic sugar with keyword `module`. It introduces the same name on the type level and on the term level.

# Nested modules

As a next step we make the following work:

```
interface B {
def f(): Unit
}

interface A {
def B : B
}

def A = new A {
def B = new B {
def f() = ()
}
}

def main() = {
A.B.f()
}
```

As a final step we make the `module` sugar work within modules.

# Interaction with Files

Files are completely orthogonal to modules. There is a keyword `include` that copy-pastes the content of the given file at this position. Each file with a certain path is only copied once. The order is topologically sorted.

# Opening modules

Unsupported

# Type members

Also see #68.

Consider:

```
module Http {
type Request { Get(url: String) }
def send(r: Request): Unit = ...
}

def getExample(): Http.Request = Http.Get("example.com")

def main() = Http.send(getExample())
```

Could this be sugar for:

```
interface Http[R] {
def send(r: R): Unit
}

type Request { Get(url: String) }

def Http = new Http[Request] {
def send(r: Request): Unit = ...
}

def getExample(): Request = Get("example.com")

def main() = Http.send(getExample())
```

Does this always work?

Contributor guide

No contributing guide indexed for this repository

Assessment

This issue has not been assessed yet.

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.