summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorLuis Rascão <luis.rascao@gmail.com>2016-03-18 15:06:09 +0000
committerLuis Rascão <luis.rascao@gmail.com>2016-03-18 15:06:09 +0000
commit88b67f3a5c635eb00d33d47281d58b7f1b03093c (patch)
tree774fe5904ceca628b7cbe876bd767864299ec766
parent384af7ef191b8b3f52b212f6b7f02ace786ba2a9 (diff)
parent16bc8f77254d58913748e3d878b48be290a5fa89 (diff)
downloadrebar-88b67f3a5c635eb00d33d47281d58b7f1b03093c.tar.gz
Merge pull request #594 from matwey/cache_load_save
Introduce REBAR_VSN_CACHE_FILE env variable to load/save vsn cache
-rw-r--r--inttest/vsn_cache/main.erl13
-rw-r--r--inttest/vsn_cache/vsn_cache_rt.erl90
-rw-r--r--src/rebar.erl3
-rw-r--r--src/rebar_core.erl2
-rw-r--r--src/rebar_utils.erl22
5 files changed, 127 insertions, 3 deletions
diff --git a/inttest/vsn_cache/main.erl b/inttest/vsn_cache/main.erl
new file mode 100644
index 0000000..67b6465
--- /dev/null
+++ b/inttest/vsn_cache/main.erl
@@ -0,0 +1,13 @@
+-module(main).
+-behaviour(application).
+
+-export([start/0,start/1,start/2,stop/1]).
+
+start() ->
+ start(permanent).
+start(_Restart) ->
+ ok.
+start(_Type,_Args) ->
+ ok.
+stop(_State) ->
+ ok.
diff --git a/inttest/vsn_cache/vsn_cache_rt.erl b/inttest/vsn_cache/vsn_cache_rt.erl
new file mode 100644
index 0000000..b482888
--- /dev/null
+++ b/inttest/vsn_cache/vsn_cache_rt.erl
@@ -0,0 +1,90 @@
+%% -*- erlang-indent-level: 4;indent-tabs-mode: nil -*-
+%% ex: ts=4 sw=4 et
+-module(vsn_cache_rt).
+
+-compile(export_all).
+
+setup([Target]) ->
+ retest_utils:load_module(filename:join(Target, "inttest_utils.erl")),
+ ok.
+
+files() ->
+ [
+ %% Cache save check
+ {create, "save/src/save.app.src", app(save, [main])},
+ {create, "save/vsn_cache_file", ""},
+ {copy, "main.erl", "save/src/main.erl"},
+
+ %% Cache load check
+ {create, "load/src/load.app.src", app(load, [main])},
+ {copy, "main.erl", "load/src/main.erl"}
+ ] ++ inttest_utils:rebar_setup().
+
+apply_cmds([], _Params) ->
+ ok;
+apply_cmds([Cmd | Rest], Params) ->
+ io:format("Running: ~s (~p)\n", [Cmd, Params]),
+ {ok, _} = retest_sh:run(Cmd, Params),
+ apply_cmds(Rest, Params).
+
+run_save(Dir) ->
+ GitCmds = ["git init",
+ "git add -A",
+ "git config user.email 'vsn_cache@example.com'",
+ "git config user.name 'vsn_cache'",
+ "git commit -a -m \"Initial Commit\""],
+ AppDir = filename:join(Dir, "save"),
+ EbinDir = filename:join(AppDir, "ebin"),
+ AppFile = filename:join(EbinDir, "save.app"),
+ VsnCacheFile = filename:join(AppDir, "vsn_cache_file"),
+ Env = [{"REBAR_VSN_CACHE_FILE", VsnCacheFile}],
+
+ %% Initialize test git repository
+ ok = apply_cmds(GitCmds, [{dir, AppDir}]),
+ %% Compile test project with vsn cache enabled
+ {ok, _} = retest_sh:run("../rebar -v compile", [{env, Env}, {dir, AppDir}]),
+ %% Vsn cache file has an entry
+ {ok, [{{git, AppDir}, Hash}]} = file:consult(VsnCacheFile),
+ %% This vsn entry must coincide with entry from ebin/save.app
+ {ok, [{application, save, PropList}]} = file:consult(AppFile),
+ Hash = proplists:get_value(vsn, PropList),
+ ok.
+
+run_load(Dir) ->
+ AppDir = filename:join(Dir, "load"),
+ EbinDir = filename:join(AppDir, "ebin"),
+ AppFile = filename:join(EbinDir, "load.app"),
+ VsnCacheFile = filename:join(AppDir, "vsn_cache_file"),
+ Hash = "deadbeef",
+ CacheEntries = [{{git, AppDir}, Hash}],
+ Env = [{"REBAR_VSN_CACHE_FILE", VsnCacheFile}],
+
+ %% Initialize dummy vsn cache file
+ vsn_cache_file(VsnCacheFile, CacheEntries),
+ %% Compile test project with vsn cache enabled
+ {ok, _} = retest_sh:run("../rebar -v compile", [{env, Env}, {dir, AppDir}]),
+ %% This vsn entry in cache file must coincide with entry in ebin/load.app
+ {ok, [{application, load, PropList}]} = file:consult(AppFile),
+ Hash = proplists:get_value(vsn, PropList),
+ ok.
+
+run(Dir) ->
+ run_save(Dir),
+ run_load(Dir),
+ ok.
+
+%%
+%% Generate the contents of a simple .app file
+%%
+app(Name, Modules) ->
+ App = {application, Name,
+ [{description, atom_to_list(Name)},
+ {vsn, git},
+ {modules, Modules},
+ {registered, []},
+ {applications, [kernel, stdlib]}]},
+ io_lib:format("~p.\n", [App]).
+
+vsn_cache_file(Name, Entries) ->
+ file:write_file(Name,
+ [io_lib:format("~p.~n", [X]) || X <- Entries]).
diff --git a/src/rebar.erl b/src/rebar.erl
index 888f80d..5a809d2 100644
--- a/src/rebar.erl
+++ b/src/rebar.erl
@@ -143,7 +143,7 @@ init_config({Options, _NonOptArgs}) ->
%% Keep track of how many operations we do, so we can detect bad commands
BaseConfig1 = rebar_config:set_xconf(BaseConfig, operations, 0),
%% Initialize vsn cache
- rebar_config:set_xconf(BaseConfig1, vsn_cache, dict:new()).
+ rebar_utils:init_vsn_cache(BaseConfig1).
init_config1(BaseConfig) ->
%% Determine the location of the rebar executable; important for pulling
@@ -288,6 +288,7 @@ help() ->
?CONSOLE(
"Environment variables:~n"
" REBAR_DEPS_PREFER_LIBS to look for dependecies in system libs prior fetching.~n"
+ " REBAR_VSN_CACHE_FILE to load vsn cache from and save to specified file.~n"
"~n", []).
%%
diff --git a/src/rebar_core.erl b/src/rebar_core.erl
index 0650430..6cc8d38 100644
--- a/src/rebar_core.erl
+++ b/src/rebar_core.erl
@@ -106,7 +106,7 @@ process_commands([Command | Rest], ParentConfig) ->
ParentConfig2),
%% Wipe out vsn cache to avoid invalid hits when
%% dependencies are updated
- rebar_config:set_xconf(ParentConfig3, vsn_cache, dict:new())
+ rebar_utils:init_vsn_cache(ParentConfig3)
catch
throw:rebar_abort ->
case rebar_config:get_xconf(ParentConfig1, keep_going, false) of
diff --git a/src/rebar_utils.erl b/src/rebar_utils.erl
index 1fb5419..c3ebfe5 100644
--- a/src/rebar_utils.erl
+++ b/src/rebar_utils.erl
@@ -67,7 +67,9 @@
processing_base_dir/1,
processing_base_dir/2,
patch_env/2,
- cleanup_code_path/1
+ cleanup_code_path/1,
+ init_vsn_cache/1,
+ save_vsn_cache/1
]).
%% for internal use only
@@ -268,6 +270,23 @@ expand_env_variable(InStr, VarName, RawVarValue) ->
re:replace(InStr, RegEx, [VarValue, "\\2"], ReOpts)
end.
+init_vsn_cache(Config) ->
+ init_vsn_cache(Config, os:getenv("REBAR_VSN_CACHE_FILE")).
+init_vsn_cache(Config, false) ->
+ rebar_config:set_xconf(Config, vsn_cache, dict:new());
+init_vsn_cache(Config, CacheFile) ->
+ {ok, CacheList} = file:consult(CacheFile),
+ CacheDict = dict:from_list(CacheList),
+ rebar_config:set_xconf(Config, vsn_cache, CacheDict).
+
+save_vsn_cache(Config) ->
+ save_vsn_cache(Config, os:getenv("REBAR_VSN_CACHE_FILE")).
+save_vsn_cache(_Config, false) ->
+ ok;
+save_vsn_cache(Config, CacheFile) ->
+ file:write_file(CacheFile,
+ [io_lib:format("~p.~n", [X]) || X <- dict:to_list(rebar_config:get_xconf(Config, vsn_cache))]).
+
vcs_vsn(Config, Vsn, Dir) ->
Key = {Vsn, Dir},
Cache = rebar_config:get_xconf(Config, vsn_cache),
@@ -276,6 +295,7 @@ vcs_vsn(Config, Vsn, Dir) ->
VsnString = vcs_vsn_1(Vsn, Dir),
Cache1 = dict:store(Key, VsnString, Cache),
Config1 = rebar_config:set_xconf(Config, vsn_cache, Cache1),
+ save_vsn_cache(Config1),
{Config1, VsnString};
{ok, VsnString} ->
{Config, VsnString}