Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Namespaces using parent module functions when loading #391

Closed
bvssvni opened this issue Oct 1, 2016 · 1 comment
Closed

Namespaces using parent module functions when loading #391

bvssvni opened this issue Oct 1, 2016 · 1 comment

Comments

@bvssvni
Copy link
Member

bvssvni commented Oct 1, 2016

Related to #388.

Currently all functions in Dyon live in the same namespace. This is because we try to use dynamic modules as a way of organizing code, with the ability to control and swap dependencies. However, it leads to problems when you try to reuse code across projects, because two external functions from two different projects can collide.

This is an idea for adding support for namespaces, but keeping dynamic modules as the way code is organized.

Call parent module functions

Instead of loading source from files, the namespaces are functions in the parent module that gets called upon loading:

// Calls `fn input() -> res[any]` in parent module when loading.
// Imports `press_args` and `release_args` into the prelude for this module.
// An error is reported if the loading fails.
use input::{press_args, release_args}

fn main() {
    ...
    // Function is imported into prelude.
    a := press_args()
    ...
}

This is equivalent to the following loader script:

fn main() {
    // Load `input` module using external function `input`.
    input := unwrap(input())
    // Load the main program using `input` as import.
    main := unwrap(load(source: "src/main.dyon", imports: [input]))
    // Run program.
    call(main, "main", [])
}

With imports the loader script can be reduced to:

fn main() {
    main := unwrap(load("src/main.dyon"))
    call(main, "main", [])
}

When not using a loader script, the function that returns the module can be an external function.

Global imports

Global imports can be supported:

// Import everything.
use input::*

fn main() {
    ...
    a := press_args()
    ...
}

Renaming

One can also rename imports:

use input::press_args as press

fn main() {
    ...
    a := press()
    ...
}

Loading from source

In the loader script, one can define a module that is loaded from source:

input() = load("src/input.dyon")

One can also use current objects to reuse a loaded module:

input() ~ mut modules = {
    if !has(modules, "input") { modules.input := load("src/input.dyon") }
    clone(modules.input)
}
@bvssvni
Copy link
Member Author

bvssvni commented Jun 16, 2018

Closed in favor of #434

@bvssvni bvssvni closed this as completed Jun 16, 2018
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

1 participant