summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorFred Hebert <mononcqc@ferd.ca>2017-08-15 11:20:28 -0400
committerFred Hebert <mononcqc@ferd.ca>2017-08-15 12:15:09 -0400
commitbc2f06220003499ac998f519c9eb595a0e957e15 (patch)
tree46744378d60e1e40a842419840d9c924abe2b44e
parent9c4e40d5b93c83f853be84685242d264b0892115 (diff)
Fix ordering of overlays and overlay vars in Relx
Specifically, this impacts profiles. It appears that relx as a whole requires its configuration to be merged in one tuple order (New takes precedence over Old), whereas the overlays require the opposite (Old takes precedence over New) since the operation order on disk is important to work well. This patch reorders overlay values such that the overlay of a profile takes place *after* the basic overlay, ensuring that the profile actions take place after the basic ones; this allows profiles to properly overwrite files as expected (see #1609) This is done while adequately maintaining the order of operations that were required as part of #1563 Overlay vars of profiles are also checked to be working fine, along with a test. This fixes #1247 and #1609
-rw-r--r--src/rebar_opts.erl6
-rw-r--r--test/rebar_release_SUITE.erl40
2 files changed, 38 insertions, 8 deletions
diff --git a/src/rebar_opts.erl b/src/rebar_opts.erl
index 8863b4c..b7156b2 100644
--- a/src/rebar_opts.erl
+++ b/src/rebar_opts.erl
@@ -132,7 +132,11 @@ merge_opt(mib_first_files, Value, Value) ->
merge_opt(mib_first_files, NewValue, OldValue) ->
OldValue ++ NewValue;
merge_opt(relx, NewValue, OldValue) ->
- rebar_utils:tup_umerge(OldValue, NewValue);
+ Partition = fun(C) -> is_tuple(C) andalso element(1, C) =:= overlay end,
+ {NewOverlays, NewOther} = lists:partition(Partition, NewValue),
+ {OldOverlays, OldOther} = lists:partition(Partition, OldValue),
+ rebar_utils:tup_umerge(NewOverlays, OldOverlays)
+ ++ rebar_utils:tup_umerge(OldOther, NewOther);
merge_opt(Key, NewValue, OldValue)
when Key == erl_opts; Key == eunit_compile_opts; Key == ct_compile_opts ->
merge_erl_opts(lists:reverse(OldValue), NewValue);
diff --git a/test/rebar_release_SUITE.erl b/test/rebar_release_SUITE.erl
index e41339b..1bcc61e 100644
--- a/test/rebar_release_SUITE.erl
+++ b/test/rebar_release_SUITE.erl
@@ -200,13 +200,34 @@ profile_overlays(Config) ->
AppDir = ?config(apps, Config),
Name = ?config(name, Config),
Vsn = "1.0.0",
+ file:write_file(filename:join(AppDir, "dev.file"), "dev.\n"),
+ file:write_file(filename:join(AppDir, "prod.file"), "prod.\n"),
+ file:write_file(filename:join(AppDir, "dev.vars"), "{env, \"dev\"}.\n"),
+ file:write_file(filename:join(AppDir, "prod.vars"), "{env, \"prod\"}.\n"),
{ok, RebarConfig} =
- file:consult(rebar_test_utils:create_config(AppDir,
- [{relx, [{release, {list_to_atom(Name), Vsn},
- [list_to_atom(Name)]},
- {overlay, [{mkdir, "randomdir"}]},
- {lib_dirs, [AppDir]}]},
- {profiles, [{prod, [{relx, [{overlay, [{mkdir, "otherrandomdir"}]}]}]}]}])),
+ file:consult(rebar_test_utils:create_config(AppDir,
+ %% Paths are relative, but to cwd in relx, not the project root as
+ %% seen by rebar3 (in non-test cases, they're the same).
+ %% Work around by being explicit.
+ [{relx, [{release, {list_to_atom(Name), Vsn},
+ [list_to_atom(Name)]},
+ {overlay_vars, filename:join(AppDir, "dev.vars")},
+ {overlay, [{mkdir, "randomdir"},
+ {copy, filename:join(AppDir,"./dev.file"), "profile.file"},
+ {copy, filename:join(AppDir,"./dev.file"), "{{env}}.file"},
+ {chmod, 8#00770, "profile.file"}]},
+ {lib_dirs, [AppDir]}]},
+ {profiles, [{prod,
+ [{relx, [
+ {overlay_vars, filename:join(AppDir, "prod.vars")},
+ {overlay, [{mkdir, "otherrandomdir"},
+ {copy, filename:join(AppDir, "./prod.file"), "{{env}}.file"},
+ {copy, filename:join(AppDir, "./prod.file"), "profile.file"},
+ {chmod, 8#00770, "profile.file"}]}
+
+ ]}]
+ }]}
+ ])),
ReleaseDir = filename:join([AppDir, "./_build/prod/rel/", Name]),
@@ -216,7 +237,12 @@ profile_overlays(Config) ->
{ok, [{release, list_to_atom(Name), Vsn, false},
{dir, filename:join(ReleaseDir, "otherrandomdir")},
{dir, filename:join(ReleaseDir, "randomdir")}]}
- ).
+ ),
+ ?assertMatch({ok,[prod]},
+ file:consult(filename:join(ReleaseDir, "profile.file"))),
+ ?assertMatch({ok,[prod]},
+ file:consult(filename:join(ReleaseDir, "prod.file"))),
+ ok.
profile_overlay_merge (_Config) ->
% when profile and relx overlays both exist, the profile overlays should be