Skip to content
Eric Merritt edited this page Feb 12, 2012 · 2 revisions

Understanding the Sinan Config File sinan.config

At first glance the sinan.config file can be a little confusing. You see a config tuple in the file that looks like this:

{build_dir, "_build"}.

That makes sense, its a simple tuple key value pair. Then you see something like this:

{types, [{task, release},
        {release, b}], [{a, load}]}.

You think to yourself Wah? Its a bit disconcerting but don't worry. We are going to explain it in detail in this article.

You can think of a config entry as a key value pair like our first example:

 {build_dir, "_build"}.

This is a global config entry that applies to the entire project. However, you can specialize that config, basically restrict the entry to only apply to parts of the project, to specific tasks, specific releases, etc. That's what that middle element we saw in our second example is all about.

{types, [{task, release},
        {release, b}], [{a, load}]}.

The middle list (and it must always be a list) is a list specializers. In this case the specializer [{task, release}, {release, b}] indicates that this config value {types, [{a, load}]} applies only to the release task and only when release b is being built.

Config Specializers

There are four specializers available to specialize a config entry. These areas of specialization are.

  1. Task Name; {task, <task-name>}
  2. Release Name; {release, <release-name>}
  3. App Name; {app, <app-name>}
  4. Module Name; {module, <module-name>}

Lets look at an example of a config entry that we can heavily specialize. We will start at the broadest (unspecialized) and then specialize it down to the narrowest specialization. We will look at the compile_args entry used by build. That's a configuration that could, realistically, be specialized down to a very fine level.

Lets say that we wanted to turn on debug_info for every module in the project. In that case we would simple have a global, unspecialized config entry

{compile_args, [debug_info]}.

We have two releases in our project. Release A and Release B and now we want debug_info to only apply to Release B. We would then specialize our config entry to Release B.

{compile_args, [{release, b}], [debug_info]}.

Lets say we wanted to specialize it even further. We want to specialize it to just the foo app in release B. We could do that by adding an app specializer as follows:

{compile_args, [{app, foo}
                {release, b}], [debug_info]}.

Now debug info only applies to app foo in Release B. What happens if we leave off the release specializer?

{compile_args, [{app, foo}], [debug_info]}.

Then it will (of course) apply to app foo in any of the releases in the project.

What if we want to turn on debug_info for a single module bar in app foo in Release B?

{compile_args, [{module, bar},
                {app, foo}
                {release, b}], [debug_info]}.

Now our compile_args entry will only apply to module bar in app foo in Release B.

You wont use it very often, but you can specialize on a task as well. Lets say that we had two tasks in sinan, task build and task super. Both take a compile_argsentry, but we want our compile_args to apply only to task build. We would then add a task specializer as follows:

{compile_args, [{task, build},
                {module, bar},
                {app, foo}
                {release, b}], [debug_info]}.

One thing that you can not do is have two specializers of the same type. If you specialize a config differently you must have two config entries. For example, you could not do:

{compile_args, [{task, build},
                {module, bar},
                {app, foo}
                {release, b}
                {release, a}], [debug_info]}.

Notice that there is a Release A and Release B. This simply will not work. What you must do is provide two config entries one for Release A and another for Release B.

Conclusion

Specializers are a way to control how a configuration entry applies during a sinan build. If you don't need them you can more or less ignore them. If you do, the let you control the configuration of a build to a very fine level.