# Julia workflow

**URL:** <https://discourse.julialang.org/t/julia-workflow/21993>\
**Category:** New to Julia\
**Created:** [March 18, 2019, 9:11am UTC](https://discourse.julialang.org/t/julia-workflow/21993 "2019-03-18T09:11:31Z")\
**Posts on this page:** 12\
**Page:** 1

<div class="post-metadata">

**Author:** ![HenrikM](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/henrikm/32/17975_2.png) [@HenrikM](https://discourse.julialang.org/u/HenrikM)\
**Post date:** [March 18, 2019, 9:11am UTC](https://discourse.julialang.org/t/julia-workflow/21993/1 "2019-03-18T09:11:31Z")

</div>

This is a bit of a soft/vague question, but I am struggling to find a good, informal, workflow for my budding Julia development. I’m probably just tripping over my own preconceptions, please point me in the right direction.

Let’s say I want to use [Revise.jl](https://github.com/timholy/Revise.jl). It seems I have to put my code in a [Module](https://docs.julialang.org/en/v1/manual/modules/) to make it work. The Julia documentations [Workflow Tips](https://docs.julialang.org/en/v1/manual/workflow-tips/) suggest using `include`, but that does no seems to sync with Revise. To be able to load the module, it seems easiest to put it in a [Package](https://julialang.github.io/Pkg.jl/v1/). The package documentation talks about [projects](https://julialang.github.io/Pkg.jl/v1/environments/#Creating-your-own-projects-1), but I’m not quite sure what the distinctions are. To have local packages, it seems I have to [create git repositories](https://julialang.github.io/Pkg.jl/v1/managing-packages/#Adding-a-local-package-1) for them.

Walking down this road, it seems to me that Module = Package = (magic directory structure) ≈ Project = git repo. But that can’t be right. And surely Julia development is not cemented on git?

Are there any blogs or tutorials on how to manage a small julia project? Currently just a few own local modules, lots of editing and restructuring going on. How to organically grow a project from one file to many modules? How should I structure my directories/modules/packages, the whole lot!

Thank you for your help!

---

<div class="post-metadata">

**Author:** ![cserteGT3](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/csertegt3/32/8283_2.png) [@cserteGT3](https://discourse.julialang.org/u/cserteGT3)\
**Post date:** [March 18, 2019, 10:10am UTC](https://discourse.julialang.org/t/julia-workflow/21993/2 "2019-03-18T10:10:02Z")

</div>

> [@HenrikM](#):
>
> Let’s say I want to use [Revise.jl](https://github.com/timholy/Revise.jl). It seems I have to put my code in a [Module](https://docs.julialang.org/en/v1/manual/modules/) to make it work. The Julia documentations [Workflow Tips](https://docs.julialang.org/en/v1/manual/workflow-tips/) suggest using `include`, but that does no seems to sync with Revise.

I think you could go with the [REPL workflow](https://docs.julialang.org/en/v1/manual/workflow-tips/#A-basic-editor/REPL-workflow-1) with Revise, the only change you should do (in the `Tst.jl` file):

```julia
using Revise
includet("Tmp.jl")

```

That way you can develop your code in the `Tmp` module and test it in the `tst.jl`.  
At least that’s how I do it, hope it helps.  
(Edit: fix typo)

---

<div class="post-metadata">

**Author:** ![HenrikM](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/henrikm/32/17975_2.png) [@HenrikM](https://discourse.julialang.org/u/HenrikM)\
**Post date:** [March 18, 2019, 10:22am UTC](https://discourse.julialang.org/t/julia-workflow/21993/3 "2019-03-18T10:22:50Z")

</div>

Are you using `Revise` at all? My understanding is that you shouldn’t have to use `include` at all, you just go:

```julia
using Revise
using Tmp

```

and then changes to `Tmp` are automagically propagated to the REPL. That is how I am using `Revise`.

---

<div class="post-metadata">

**Author:** ![cserteGT3](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/csertegt3/32/8283_2.png) [@cserteGT3](https://discourse.julialang.org/u/cserteGT3)\
**Post date:** [March 18, 2019, 11:45am UTC](https://discourse.julialang.org/t/julia-workflow/21993/4 "2019-03-18T11:45:21Z")

</div>

It could be that I misunderstood Revise’s docs.  
This is how I use it (using the REPL workflow example):  
`Tmp.jl`:

```julia
module Tmp
export say_hello

say_hello() = println("Hello!")

# your other definitions here
end

```

then in `Tst.jl`:

```julia
using Revise
includet("Tmp.jl")
using .Tmp

say_hello()
# say_hello()

# your other test code here

```

It’s working for me. But it could be that after `using Revise` the use of `includet()` is redundant, as the `Tmp` module is will be tracked by `Revise` after the `using` statement.

Also sorry for not answering directly your questions, I misinterpreted something.

---

<div class="post-metadata">

**Author:** ![mauro3](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/mauro3/32/292_2.png) [@mauro3](https://discourse.julialang.org/u/mauro3)\
**Post date:** [March 18, 2019, 11:53am UTC](https://discourse.julialang.org/t/julia-workflow/21993/5 "2019-03-18T11:53:29Z")

</div>

My understanding is that revise tracks things on the LOAD\_PATH automatically. But if it is elsewhere `includet` is needed.

---

<div class="post-metadata">

**Author:** ![e3c6](https://avatars.discourse-cdn.com/v4/letter/e/e79b87/32.png) [@e3c6](https://discourse.julialang.org/u/e3c6)\
**Post date:** [March 18, 2019, 1:30pm UTC](https://discourse.julialang.org/t/julia-workflow/21993/6 "2019-03-18T13:30:27Z")

</div>

Unfortunately `Revise.jl` doesn’t handle changes in type definitions.  
I would like to know if there is a better workflow to handle these kind of changes.

---

<div class="post-metadata">

**Author:** ![jonathanBieler](https://avatars.discourse-cdn.com/v4/letter/j/82dd89/32.png) [@jonathanBieler](https://discourse.julialang.org/u/jonathanBieler)\
**Post date:** [March 18, 2019, 4:01pm UTC](https://discourse.julialang.org/t/julia-workflow/21993/7 "2019-03-18T16:01:26Z")

</div>

Personally I make modules only when it makes sense to. That is when I have a clearly defined and atomic set of features that I want to reuse often. Otherwise, I make scripts that use modules and often load (via `include`) a “library script” (a file that contains mostly functions).

Basically all code starts in a script at the global scope, if it’s useful it goes into a “library script”, and if that is really useful it ends up in a package.

For reloading type definitions I often just search and replace the type name (adding a version number to it).

Note that you can also reload a module (including type definitions) just using `include` or with plain code if you don’t use exports for testing:

```julia
module Foo
    bar(x) = 2x
    struct MyStruct
        x
    end
end

Foo.bar(2)
Foo.MyStruct(1)

```

I usually start my modules like that and then move them to a package. A package is a special directory structure (Foo/src/Foo.jl) containing a module `Foo` and added to your environment via the package manager. They don’t require git.

---

<div class="post-metadata">

**Author:** ![Tamas\_Papp](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/tamas_papp/32/25949_2.png) [@Tamas\_Papp](https://discourse.julialang.org/u/Tamas_Papp)\
**Post date:** [March 18, 2019, 5:19pm UTC](https://discourse.julialang.org/t/julia-workflow/21993/8 "2019-03-18T17:19:03Z")

</div>

> [@HenrikM](#):
>
> And surely Julia development is not cemented on git?

It isn’t, but since git gives so many benefits for so little extra overhead, people tend to use it.

What I usually do is

1. make a small project for everything (using [skeleton.jl](https://github.com/tpapp/skeleton.jl) — disclaimer: I am the author, and there are other fine solutions),

2. `pkg> activate that/project` when I am working on it,

3. enable Revise.jl automatically at startup.

For things I use & develop regularly, I `pkg> dev`.

> [@HenrikM](#):
>
> The package documentation talks about [projects](https://julialang.github.io/Pkg.jl/v1/environments/#Creating-your-own-projects-1), but I’m not quite sure what the distinctions are.

See the definitions [here](https://julialang.github.io/Pkg.jl/dev/glossary/).

---

<div class="post-metadata">

**Author:** ![HenrikM](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/henrikm/32/17975_2.png) [@HenrikM](https://discourse.julialang.org/u/HenrikM)\
**Post date:** [March 18, 2019, 9:06pm UTC](https://discourse.julialang.org/t/julia-workflow/21993/9 "2019-03-18T21:06:19Z")

</div>

Thank you for your answer! I also found your blog and blogpost: [My Julia workflow](https://tpapp.github.io/post/julia-workflow/), and I realised that I have much to learn from you.

One follow-up question: Why do I have to `pkg> activate` every time I want to run anything from the project? Isn’t all the waltzing with `Manifest.toml` and `Project.toml` enough? Or putting it in a different way, what variable does the `activate` update and how does it enable julia to find my code? I thought the `activate` was only for `Pkg` and that code loading relied on the `.toml` files.

For example, in a newly created directory `TestProj`:

```julia
] activate .
] generate TestMod
] develop --local TestMod
> using TestMod

```

This works and gives me a false sense of having set up a working environment. But if I exit and re-enter julia:

```julia
> using TestMod
ERROR: ArgumentError: Package TestMod not found in current path:
- Run `import Pkg; Pkg.add("TestMod")` to install the TestMod package.

```

I have to `] activate .` again merely for `using` to work, even if no `Pkg` managing actions are to take place.

I apologise for the long post, I’m just trying to expose my thinking so that you people can point out the flaws in it.

---

<div class="post-metadata">

**Author:** ![Tamas\_Papp](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/tamas_papp/32/25949_2.png) [@Tamas\_Papp](https://discourse.julialang.org/u/Tamas_Papp)\
**Post date:** [March 19, 2019, 7:31am UTC](https://discourse.julialang.org/t/julia-workflow/21993/10 "2019-03-19T07:31:20Z")

</div>

> [@HenrikM](#):
>
> Or putting it in a different way, what variable does the `activate` update and how does it enable julia to find my code?

It changes the [active environment](https://julialang.github.io/Pkg.jl/dev/getting-started/#Getting-Started-with-Environments-1) (again, please do read the Pkg docs, they clarify a lot).

To give an example, suppose I am working on code for a research paper. It will not be used by anything else, but uses quite a few packages. I also want to commit the `Manifest.toml`, so that I can always rely on a consistent and tested environment, and upgrade on demand (eg I run it on a remote server so I want it to be rock-solid).

So I generate a package skeleton in `~/research/CodeForPaper`. This is not in my global environment.

Whenever I want to work on it, I `pkg> activate ~/research/CodeForPaper`. I occasionally `pkg> up` then, which updates _this_ environment. After testing I commit to the repo. Otherwise it does not interfere with anything, and is practically “invisible” unless I activate it.

---

<div class="post-metadata">

**Author:** ![HenrikM](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/henrikm/32/17975_2.png) [@HenrikM](https://discourse.julialang.org/u/HenrikM)\
**Post date:** [March 19, 2019, 7:41am UTC](https://discourse.julialang.org/t/julia-workflow/21993/11 "2019-03-19T07:41:53Z")

</div>

Thank you for your patiens. I have read the Pkg docs but probably misunderstood them. The sentence

> You may have noticed the (v1.1) in the REPL prompt. This lets us know v1.1 is the active environment. The active environment is the environment that will be modified by Pkg commands such as add, rm and update.

gives me the impression that the “active environment is the environment that will be **modified by Pkg commands** such as add, rm and update”. Apparently the active environment is also the environment that determines what packages are loaded. I thought the `toml`-files had something to do with that. [Project environments](https://docs.julialang.org/en/v1/manual/code-loading/#Project-environments-1):

> A project environment is determined by a directory containing a project file called Project.toml, and optionally a manifest file called Manifest.toml.

Now feel that these files are just dead in the water until I activate the project. Is that correct?

---

<div class="post-metadata">

**Author:** ![Tamas\_Papp](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/tamas_papp/32/25949_2.png) [@Tamas\_Papp](https://discourse.julialang.org/u/Tamas_Papp)\
**Post date:** [March 19, 2019, 8:06am UTC](https://discourse.julialang.org/t/julia-workflow/21993/12 "2019-03-19T08:06:20Z")

</div>

> [@HenrikM](#):
>
> Now feel that these files are just dead in the water until I activate the project. Is that correct?

More or less (except for resolving the dependency graph if necessary, if I understand correctly), except for [stacked ones](https://docs.julialang.org/en/v1/manual/code-loading/#Environment-stacks-1) (but I would not worry about that at the moment).
