1
0
Fork 0
mirror of https://github.com/processone/ejabberd synced 2025-10-06 03:50:15 +02:00

Cleanup ext_mod and fix compilation path

This commit is contained in:
Christophe Romain 2016-12-07 09:27:21 +01:00
parent a681874f67
commit 8a7ea85a7e
2 changed files with 82 additions and 104 deletions

View file

@ -29,11 +29,13 @@
-author("Christophe Romain <christophe.romain@process-one.net>"). -author("Christophe Romain <christophe.romain@process-one.net>").
-export([start/0, stop/0, update/0, check/1, -export([start/0, stop/0, update/0, check/1,
available_command/0, available/0, available/1, available_command/0, available/0, available/1,
installed_command/0, installed/0, installed/1, installed_command/0, installed/0, installed/1,
install/1, uninstall/1, upgrade/0, upgrade/1, install/1, uninstall/1, upgrade/0, upgrade/1,
add_sources/2, del_sources/1, modules_dir/0, add_sources/2, del_sources/1, modules_dir/0,
config_dir/0, opt_type/1, get_commands_spec/0]). config_dir/0, opt_type/1, get_commands_spec/0]).
-export([compile_erlang_file/2, compile_elixir_file/2]).
-include("ejabberd_commands.hrl"). -include("ejabberd_commands.hrl").
-include("logger.hrl"). -include("logger.hrl").
@ -341,14 +343,17 @@ copy(From, To) ->
SubTo = filename:join(To, F), SubTo = filename:join(To, F),
copy(SubFrom, SubTo) copy(SubFrom, SubTo)
end, end,
lists:foldl(fun({ok, C2}, {ok, C1}) -> {ok, C1+C2}; lists:foldl(fun(ok, ok) -> ok;
({ok, _}, Error) -> Error; (ok, Error) -> Error;
(Error, _) -> Error (Error, _) -> Error
end, {ok, 0}, end, ok,
[Copy(filename:basename(X)) || X<-filelib:wildcard(From++"/*")]); [Copy(filename:basename(X)) || X<-filelib:wildcard(From++"/*")]);
false -> false ->
filelib:ensure_dir(To), filelib:ensure_dir(To),
file:copy(From, To) case file:copy(From, To) of
{ok, _} -> ok;
Error -> Error
end
end. end.
delete_path(Path) -> delete_path(Path) ->
@ -461,19 +466,15 @@ compile_and_install(Module, Spec) ->
LibDir = module_lib_dir(Module), LibDir = module_lib_dir(Module),
case filelib:is_dir(SrcDir) of case filelib:is_dir(SrcDir) of
true -> true ->
{ok, Dir} = file:get_cwd(), case compile_deps(SrcDir) of
file:set_cwd(SrcDir),
Result = case compile_deps(Module, Spec, LibDir) of
ok -> ok ->
case compile(Module, Spec, LibDir) of case compile(SrcDir) of
ok -> install(Module, Spec, LibDir); ok -> install(Module, Spec, SrcDir, LibDir);
Error -> Error Error -> Error
end; end;
Error -> Error ->
Error Error
end, end;
file:set_cwd(Dir),
Result;
false -> false ->
Path = proplists:get_value(url, Spec, ""), Path = proplists:get_value(url, Spec, ""),
case add_sources(Module, Path) of case add_sources(Module, Path) of
@ -482,79 +483,54 @@ compile_and_install(Module, Spec) ->
end end
end. end.
compile_deps(_Module, _Spec, DestDir) -> compile_deps(LibDir) ->
case filelib:is_dir("deps") of Deps = filename:join(LibDir, "deps"),
true -> ok; case filelib:is_dir(Deps) of
false -> fetch_rebar_deps() true -> ok; % assume deps are included
false -> fetch_rebar_deps(LibDir)
end, end,
Ebin = filename:join(DestDir, "ebin"), Rs = [compile(Dep) || Dep <- filelib:wildcard(filename:join(Deps, "*"))],
filelib:ensure_dir(filename:join(Ebin, ".")), compile_result(Rs).
Result = lists:foldl(fun(Dep, Acc) ->
Inc = filename:join(Dep, "include"),
Lib = filename:join(Dep, "lib"),
Src = filename:join(Dep, "src"),
Options = [verbose, report_errors, report_warnings,
{outdir, Ebin}, {i, Inc}],
[file:copy(App, Ebin) || App <- filelib:wildcard(Src++"/*.app")],
%% Compile erlang files compile(LibDir) ->
Acc1 = Acc ++ [case compile:file(File, Options) of Bin = filename:join(LibDir, "ebin"),
{ok, _} -> ok; Inc = filename:join(LibDir, "include"),
{ok, _, _} -> ok; Lib = filename:join(LibDir, "lib"),
{ok, _, _, _} -> ok; Src = filename:join(LibDir, "src"),
error -> {error, {compilation_failed, File}}; Options = [{outdir, Bin}, {i, Inc} | compile_options()],
Error -> Error filelib:ensure_dir(filename:join(Bin, ".")),
end [copy(App, Bin) || App <- filelib:wildcard(Src++"/*.app")],
|| File <- filelib:wildcard(Src++"/*.erl")], Er = [compile_erlang_file(Bin, File, Options)
|| File <- filelib:wildcard(Src++"/*.erl")],
Ex = [compile_elixir_file(Bin, File)
|| File <- filelib:wildcard(Lib ++ "/*.ex")],
compile_result(Er++Ex).
%% Compile elixir files compile_result(Results) ->
Acc1 ++ [case compile_elixir_file(Ebin, File) of
{ok, _} -> ok;
{error, File} -> {error, {compilation_failed, File}}
end
|| File <- filelib:wildcard(Lib ++ "/*.ex")]
end, [], filelib:wildcard("deps/*")),
case lists:dropwhile( case lists:dropwhile(
fun(ok) -> true; fun({ok, _}) -> true;
(_) -> false (_) -> false
end, Result) of end, Results) of
[] -> ok; [] -> ok;
[Error|_] -> Error [Error|_] -> Error
end. end.
compile(_Module, _Spec, DestDir) -> compile_options() ->
Ebin = filename:join(DestDir, "ebin"), [verbose, report_errors, report_warnings]
filelib:ensure_dir(filename:join(Ebin, ".")), ++ [{i, filename:join(code:lib_dir(App), "include")}
Includes = [{i, filename:join(code:lib_dir(App), "include")} || App <- [fast_xml, xmpp, ejabberd]].
|| App <- [fast_xml, xmpp, ejabberd]],
Options = [verbose, report_errors, report_warnings,
{outdir, Ebin}, {i, "include"} | Includes],
[file:copy(App, Ebin) || App <- filelib:wildcard("src/*.app")],
%% Compile erlang files compile_erlang_file(Dest, File) ->
Result = [case compile:file(File, Options) of compile_erlang_file(Dest, File, compile_options()).
{ok, _} -> ok;
{ok, _, _} -> ok;
{ok, _, _, _} -> ok;
error -> {error, {compilation_failed, File}};
Error -> Error
end
|| File <- filelib:wildcard("src/*.erl")],
%% Compile elixir files compile_erlang_file(Dest, File, ErlOptions) ->
Result1 = Result ++ [case compile_elixir_file(Ebin, File) of Options = [{outdir, Dest} | ErlOptions],
{ok, _} -> ok; case compile:file(File, Options) of
{error, File} -> {error, {compilation_failed, File}} {ok, Module} -> {ok, Module};
end {ok, Module, _} -> {ok, Module};
|| File <- filelib:wildcard("lib/*.ex")], {ok, Module, _, _} -> {ok, Module};
error -> {error, {compilation_failed, File}};
case lists:dropwhile( {error, E, W} -> {error, {compilation_failed, File, E, W}}
fun(ok) -> true;
(_) -> false
end, Result1) of
[] -> ok;
[Error|_] -> Error
end. end.
compile_elixir_file(Dest, File) when is_list(Dest) and is_list(File) -> compile_elixir_file(Dest, File) when is_list(Dest) and is_list(File) ->
@ -564,13 +540,15 @@ compile_elixir_file(Dest, File) ->
try 'Elixir.Kernel.ParallelCompiler':files_to_path([File], Dest, []) of try 'Elixir.Kernel.ParallelCompiler':files_to_path([File], Dest, []) of
[Module] -> {ok, Module} [Module] -> {ok, Module}
catch catch
_ -> {error, File} _ -> {error, {compilation_failed, File}}
end. end.
install(Module, Spec, DestDir) -> install(Module, Spec, SrcDir, LibDir) ->
Errors = lists:dropwhile(fun({_, {ok, _}}) -> true; {ok, CurDir} = file:get_cwd(),
file:set_cwd(SrcDir),
Errors = lists:dropwhile(fun({_, ok}) -> true;
(_) -> false (_) -> false
end, [{File, copy(File, filename:join(DestDir, File))} end, [{File, copy(File, filename:join(LibDir, File))}
|| File <- filelib:wildcard("{ebin,priv,conf,include}/**")]), || File <- filelib:wildcard("{ebin,priv,conf,include}/**")]),
Result = case Errors of Result = case Errors of
[{F, {error, E}}|_] -> [{F, {error, E}}|_] ->
@ -578,25 +556,28 @@ install(Module, Spec, DestDir) ->
[] -> [] ->
SpecPath = proplists:get_value(path, Spec), SpecPath = proplists:get_value(path, Spec),
SpecFile = filename:flatten([Module, ".spec"]), SpecFile = filename:flatten([Module, ".spec"]),
copy(filename:join(SpecPath, SpecFile), filename:join(DestDir, SpecFile)) copy(filename:join(SpecPath, SpecFile), filename:join(LibDir, SpecFile))
end, end,
case Result of file:set_cwd(CurDir),
{ok, _} -> ok; Result.
Error -> Error
end.
%% -- minimalist rebar spec parser, only support git %% -- minimalist rebar spec parser, only support git
fetch_rebar_deps() -> fetch_rebar_deps(SrcDir) ->
case rebar_deps("rebar.config")++rebar_deps("rebar.config.script") of case rebar_deps(filename:join(SrcDir, "rebar.config"))
++ rebar_deps(filename:join(SrcDir, "rebar.config.script")) of
[] -> [] ->
ok; ok;
Deps -> Deps ->
{ok, CurDir} = file:get_cwd(),
file:set_cwd(SrcDir),
filelib:ensure_dir(filename:join("deps", ".")), filelib:ensure_dir(filename:join("deps", ".")),
lists:foreach(fun({_App, Cmd}) -> lists:foreach(fun({_App, Cmd}) ->
os:cmd("cd deps; "++Cmd++"; cd ..") os:cmd("cd deps; "++Cmd++"; cd ..")
end, Deps) end, Deps),
file:set_cwd(CurDir)
end. end.
rebar_deps(Script) -> rebar_deps(Script) ->
case file:script(Script) of case file:script(Script) of
{ok, Config} when is_list(Config) -> {ok, Config} when is_list(Config) ->
@ -637,7 +618,7 @@ format({Key, Val}) -> % TODO: improve Yaml parsing
opt_type(allow_contrib_modules) -> opt_type(allow_contrib_modules) ->
fun (false) -> false; fun (false) -> false;
(no) -> false; (no) -> false;
(_) -> true (_) -> true
end; end;
opt_type(_) -> [allow_contrib_modules]. opt_type(_) -> [allow_contrib_modules].

View file

@ -643,17 +643,14 @@ get_commands_spec() ->
%%% %%%
compile(File) -> compile(File) ->
Includes = [{i, filename:join(code:lib_dir(App), "include")}
|| App <- [fast_xml, xmpp, ejabberd]],
Ebin = filename:join(code:lib_dir(ejabberd), "ebin"), Ebin = filename:join(code:lib_dir(ejabberd), "ebin"),
case compile:file(File, [{outdir, Ebin}|Includes]) of case ext_mod:compile_erlang_file(Ebin, File) of
error -> error; {ok, Module} ->
{error, _, _} -> error; code:purge(Module),
OK -> code:load_file(Module),
[ok, ModuleName | _] = tuple_to_list(OK), ok;
code:purge(ModuleName), _ ->
code:load_file(ModuleName), error
ok
end. end.
get_cookie() -> get_cookie() ->