From e9d911241aaa74040895228b1a00ff825538f579 Mon Sep 17 00:00:00 2001 From: Brujo Benavides Date: Mon, 12 Jan 2015 09:46:17 -0300 Subject: [PATCH 1/3] [#185] First steps --- config/elvis-test.config | 6 +- config/elvis.config | 6 +- config/old/elvis-test-rule-config-list.config | 6 +- config/test.config | 6 +- src/elvis_project.erl | 88 +++++++++++++------ test/examples/Makefile.fail | 12 +-- test/examples/rebar.config.fail | 10 +-- test/project_SUITE.erl | 39 ++++++++ 8 files changed, 126 insertions(+), 47 deletions(-) diff --git a/config/elvis-test.config b/config/elvis-test.config index 78c2bc5..9a9aa85 100644 --- a/config/elvis-test.config +++ b/config/elvis-test.config @@ -30,11 +30,13 @@ }, #{dirs => ["."], filter => "Makefile", - rules => [{elvis_project, no_deps_master_erlang_mk, #{ignore => []}}] + rules => [{elvis_project, no_deps_master_erlang_mk, #{ignore => []}}, + {elvis_project, git_for_deps_erlang_mk, #{ignore => []}}] }, #{dirs => ["."], filter => "rebar.config", - rules => [{elvis_project, no_deps_master_rebar, #{ignore => []}}] + rules => [{elvis_project, no_deps_master_rebar, #{ignore => []}}, + {elvis_project, git_for_deps_rebar, #{ignore => []}}] }, #{dirs => ["."], filter => "elvis.config", diff --git a/config/elvis.config b/config/elvis.config index cf70ef8..d65c5a2 100644 --- a/config/elvis.config +++ b/config/elvis.config @@ -30,11 +30,13 @@ }, #{dirs => ["."], filter => "Makefile", - rules => [{elvis_project, no_deps_master_erlang_mk, #{ignore => [sync]}}] + rules => [{elvis_project, no_deps_master_erlang_mk, #{ignore => []}}, + {elvis_project, git_for_deps_erlang_mk, #{ignore => []}}] }, #{dirs => ["."], filter => "rebar.config", - rules => [{elvis_project, no_deps_master_rebar, #{ignore => []}}] + rules => [{elvis_project, no_deps_master_rebar, #{ignore => []}}, + {elvis_project, git_for_deps_rebar, #{ignore => []}}] }, #{dirs => ["."], filter => "elvis.config", diff --git a/config/old/elvis-test-rule-config-list.config b/config/old/elvis-test-rule-config-list.config index 913e597..c0864ae 100644 --- a/config/old/elvis-test-rule-config-list.config +++ b/config/old/elvis-test-rule-config-list.config @@ -29,11 +29,13 @@ }, #{dirs => ["."], filter => "Makefile", - rules => [{elvis_project, no_deps_master_erlang_mk, []}] + rules => [{elvis_project, no_deps_master_erlang_mk, #{ignore => []}}, + {elvis_project, git_for_deps_erlang_mk, #{ignore => []}}] }, #{dirs => ["."], filter => "rebar.config", - rules => [{elvis_project, no_deps_master_rebar, []}] + rules => [{elvis_project, no_deps_master_rebar, #{ignore => []}}, + {elvis_project, git_for_deps_rebar, #{ignore => []}}] }, #{dirs => ["."], filter => "elvis.config", diff --git a/config/test.config b/config/test.config index 8f88523..f2fa385 100644 --- a/config/test.config +++ b/config/test.config @@ -30,11 +30,13 @@ }, #{dirs => ["."], filter => "Makefile", - rules => [{elvis_project, no_deps_master_erlang_mk, #{ignore => []}}] + rules => [{elvis_project, no_deps_master_erlang_mk, #{ignore => []}}, + {elvis_project, git_for_deps_erlang_mk, #{ignore => []}}] }, #{dirs => ["."], filter => "rebar.config", - rules => [{elvis_project, no_deps_master_rebar, #{ignore => []}}] + rules => [{elvis_project, no_deps_master_rebar, #{ignore => []}}, + {elvis_project, git_for_deps_rebar, #{ignore => []}}] }, #{dirs => ["."], filter => "elvis.config", diff --git a/src/elvis_project.erl b/src/elvis_project.erl index eed4603..745cbd2 100644 --- a/src/elvis_project.erl +++ b/src/elvis_project.erl @@ -3,6 +3,8 @@ -export([ no_deps_master_erlang_mk/3, no_deps_master_rebar/3, + git_for_deps_erlang_mk/3, + git_for_deps_rebar/3, old_configuration_format/3 ]). @@ -11,6 +13,10 @@ "please change this to a tag, branch or specific " "commit."). +-define(DEP_NO_GIT, + "Dependency '~s' is not using git protocol, " + "please change this to something like `git://...`"). + -define(OLD_CONFIG_FORMAT, "The current Elvis configuration file has an outdated format. " "Please check Elvis's GitHub repository to find out what the " @@ -20,6 +26,28 @@ %% Rules %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +-spec git_for_deps_erlang_mk(elvis_config:config(), + elvis_file:file(), + [term()]) -> + [elvis_result:item()]. +git_for_deps_erlang_mk(_Config, Target, RuleConfig) -> + IgnoreDeps = maps:get(ignore, RuleConfig, []), + Deps = get_erlang_mk_deps(Target), + BadDeps = lists:filter(fun is_erlang_mk_not_git_dep/1, Deps), + lists:flatmap( + fun(Line) -> erlang_mk_dep_to_result(Line, IgnoreDeps) end, BadDeps). + +-spec git_for_deps_rebar(elvis_config:config(), + elvis_file:file(), + [term()]) -> + [elvis_result:item()]. +git_for_deps_rebar(_Config, Target, RuleConfig) -> + IgnoreDeps = maps:get(ignore, RuleConfig, []), + Deps = get_rebar_deps(Target), + BadDeps = lists:filter(fun is_rebar_not_git_dep/1, Deps), + lists:flatmap( + fun(Line) -> rebar_dep_to_result(Line, IgnoreDeps) end, BadDeps). + -spec no_deps_master_erlang_mk(elvis_config:config(), elvis_file:file(), [term()]) -> @@ -27,21 +55,9 @@ no_deps_master_erlang_mk(_Config, Target, RuleConfig) -> IgnoreDeps = maps:get(ignore, RuleConfig, []), Deps = get_erlang_mk_deps(Target), - DepsInMaster = lists:filter(fun is_erlang_mk_master_dep/1, Deps), - DepToResult = - fun(Line) -> - Opts = [{capture, all_but_first, binary}], - {match, [Name]} = re:run(Line, "dep_([^ ]*)", Opts), - NameAtom = binary_to_atom(Name, utf8), - case lists:member(NameAtom, IgnoreDeps) of - true -> - []; - false -> - [elvis_result:new(item, ?DEP_MASTER, [Name])] - end - end, - - lists:flatmap(DepToResult, DepsInMaster). + BadDeps = lists:filter(fun is_erlang_mk_master_dep/1, Deps), + lists:flatmap( + fun(Line) -> erlang_mk_dep_to_result(Line, IgnoreDeps) end, BadDeps). -spec no_deps_master_rebar(elvis_config:config(), elvis_file:file(), @@ -50,19 +66,9 @@ no_deps_master_erlang_mk(_Config, Target, RuleConfig) -> no_deps_master_rebar(_Config, Target, RuleConfig) -> IgnoreDeps = maps:get(ignore, RuleConfig, []), Deps = get_rebar_deps(Target), - DepsInMaster = lists:filter(fun is_rebar_master_dep/1, Deps), - - DepToResult = - fun({AppName, _, _}) -> - case lists:member(AppName, IgnoreDeps) of - true -> - []; - false -> - [elvis_result:new(item, ?DEP_MASTER, [AppName])] - end - end, - - lists:flatmap(DepToResult, DepsInMaster). + BadDeps = lists:filter(fun is_rebar_master_dep/1, Deps), + lists:flatmap( + fun(Line) -> rebar_dep_to_result(Line, IgnoreDeps) end, BadDeps). -spec old_configuration_format(elvis_config:config(), elvis_file:file(), @@ -106,6 +112,18 @@ is_rebar_master_dep({_AppName, _Vsn, {_SCM, _Location, {branch, "master"}}}) -> is_rebar_master_dep(_) -> false. +is_rebar_not_git_dep({_AppName, _Vsn, {_SCM, "git://" ++ _, _Branch}}) -> false; +is_rebar_not_git_dep(_) -> true. + +rebar_dep_to_result({AppName, _, _}, IgnoreDeps) -> + case lists:member(AppName, IgnoreDeps) of + true -> + []; + false -> + [elvis_result:new(item, ?DEP_MASTER, [AppName])] + end. + + %%% erlang.mk is_erlang_mk_master_dep(Line) -> @@ -114,12 +132,26 @@ is_erlang_mk_master_dep(Line) -> _ -> true end. +is_erlang_mk_not_git_dep(Line) -> + lager:alert("~p", [Line]), false. + get_erlang_mk_deps(File) -> {Src, _} = elvis_file:src(File), Lines = binary:split(Src, <<"\n">>, [global]), IsDepsLine = fun(Line) -> re:run(Line, "dep_", []) /= nomatch end, lists:filter(IsDepsLine, Lines). +erlang_mk_dep_to_result(Line, IgnoreDeps) -> + Opts = [{capture, all_but_first, binary}], + {match, [Name]} = re:run(Line, "dep_([^ ]*)", Opts), + NameAtom = binary_to_atom(Name, utf8), + case lists:member(NameAtom, IgnoreDeps) of + true -> + []; + false -> + [elvis_result:new(item, ?DEP_MASTER, [Name])] + end. + %% Old config is_old_config(ElvisConfig) -> diff --git a/test/examples/Makefile.fail b/test/examples/Makefile.fail index d4d4df6..cda9e96 100644 --- a/test/examples/Makefile.fail +++ b/test/examples/Makefile.fail @@ -4,13 +4,13 @@ DEPS = lager sync getopt jiffy ibrowse aleppo zipper TEST_DEPS = meck dep_lager = git https://github.com/basho/lager.git 2.0.3 -dep_sync = git https://github.com/rustyio/sync.git master -dep_getopt = git https://github.com/jcomellas/getopt v0.8.2 +dep_sync = git git@github.com:rustyio/sync.git master +dep_getopt = git git://github.com/jcomellas/getopt v0.8.2 dep_meck = git https://github.com/eproxus/meck master -dep_jiffy = git https://github.com/davisp/jiffy 0.11.3 -dep_ibrowse = git https://github.com/cmullaparthi/ibrowse v4.1.1 -dep_aleppo = git https://github.com/inaka/aleppo master -dep_zipper = git https://github.com/inaka/zipper 0.1.0 +dep_jiffy = git git://github.com/davisp/jiffy 0.11.3 +dep_ibrowse = git git://github.com/cmullaparthi/ibrowse v4.1.1 +dep_aleppo = git git://github.com/inaka/aleppo master +dep_zipper = git git://github.com/inaka/zipper 0.1.0 include erlang.mk diff --git a/test/examples/rebar.config.fail b/test/examples/rebar.config.fail index 0bfb0d2..95dbffa 100644 --- a/test/examples/rebar.config.fail +++ b/test/examples/rebar.config.fail @@ -21,12 +21,12 @@ {deps_dir, "deps"}. {deps, [ - {lager, "2.*", {git, "git@github.com:basho/lager.git", "2.0.0"}}, + {lager, "2.*", {git, "https://github.com/basho/lager.git", "2.0.0"}}, {getopt, "0.*", {git, "git@github.com:jcomellas/getopt.git", {branch, "master"}}}, - {meck, "0.*", {git, "git@github.com:eproxus/meck.git", "0.8.2"}}, - {jiffy, "0.*", {git, "git@github.com:davisp/jiffy.git", "0.11.3"}}, - {ibrowse, "4.*", {git, "git@github.com:cmullaparthi/ibrowse.git", "v4.1.1"}}, - {aleppo, "0.*", {git, "git@github.com:inaka/aleppo.git", "master"}} + {meck, "0.*", {git, "git://github.com/eproxus/meck.git", "0.8.2"}}, + {jiffy, "0.*", {git, "git://github.com/davisp/jiffy.git", "0.11.3"}}, + {ibrowse, "4.*", {git, "git://github.com/cmullaparthi/ibrowse.git", "v4.1.1"}}, + {aleppo, "0.*", {git, "git://github.com/inaka/aleppo.git", "master"}} ] }. {escript_name, "elvis"}. diff --git a/test/project_SUITE.erl b/test/project_SUITE.erl index 1bbe8cc..f7e7505 100644 --- a/test/project_SUITE.erl +++ b/test/project_SUITE.erl @@ -9,6 +9,8 @@ -export([ verify_no_deps_master_erlang_mk/1, verify_no_deps_master_rebar/1, + verify_git_for_deps_erlang_mk/1, + verify_git_for_deps_rebar/1, verify_old_config_format/1 ]). @@ -82,6 +84,43 @@ verify_no_deps_master_rebar(_Config) -> RuleConfig1 = #{ignore => [aleppo, getopt]}, [] = elvis_project:no_deps_master_rebar(ElvisConfig, File, RuleConfig1). + +-spec verify_git_for_deps_erlang_mk(config()) -> any(). +verify_git_for_deps_erlang_mk(_Config) -> + ElvisConfig = elvis_config:default(), + SrcDirs = elvis_config:dirs(ElvisConfig), + + Filename = "Makefile.fail", + {ok, File} = elvis_test_utils:find_file(SrcDirs, Filename), + + [_, _, _] = elvis_project:git_for_deps_erlang_mk(ElvisConfig, File, #{}), + + RuleConfig = #{ignore => [sync]}, + [_, _] = elvis_project:git_for_deps_erlang_mk(ElvisConfig, + File, + RuleConfig), + + RuleConfig1 = #{ignore => [sync, meck]}, + [_] = elvis_project:git_for_deps_erlang_mk(ElvisConfig, + File, + RuleConfig1). + +-spec verify_git_for_deps_rebar(config()) -> any(). +verify_git_for_deps_rebar(_Config) -> + ElvisConfig = elvis_config:default(), + SrcDirs = elvis_config:dirs(ElvisConfig), + + Filename = "rebar.config.fail", + {ok, File} = elvis_test_utils:find_file(SrcDirs, Filename), + + [_, _] = elvis_project:git_for_deps_rebar(ElvisConfig, File, #{}), + + RuleConfig = #{ignore => [aleppo]}, + [_] = elvis_project:git_for_deps_rebar(ElvisConfig, File, RuleConfig), + + RuleConfig1 = #{ignore => [aleppo, lager]}, + [] = elvis_project:git_for_deps_rebar(ElvisConfig, File, RuleConfig1). + -spec verify_old_config_format(config()) -> any(). verify_old_config_format(_Config) -> ElvisConfig = elvis_config:default(), From 50f38d651cd3659675178837358dcc4e7690601f Mon Sep 17 00:00:00 2001 From: Brujo Benavides Date: Mon, 12 Jan 2015 12:17:29 -0300 Subject: [PATCH 2/3] [#185] Code complete --- src/elvis_project.erl | 35 ++++++++++++++++++++++++++--------- test/project_SUITE.erl | 4 ++-- 2 files changed, 28 insertions(+), 11 deletions(-) diff --git a/src/elvis_project.erl b/src/elvis_project.erl index 745cbd2..246eb3e 100644 --- a/src/elvis_project.erl +++ b/src/elvis_project.erl @@ -35,7 +35,9 @@ git_for_deps_erlang_mk(_Config, Target, RuleConfig) -> Deps = get_erlang_mk_deps(Target), BadDeps = lists:filter(fun is_erlang_mk_not_git_dep/1, Deps), lists:flatmap( - fun(Line) -> erlang_mk_dep_to_result(Line, IgnoreDeps) end, BadDeps). + fun(Line) -> + erlang_mk_dep_to_result(Line, ?DEP_NO_GIT, IgnoreDeps) + end, BadDeps). -spec git_for_deps_rebar(elvis_config:config(), elvis_file:file(), @@ -46,7 +48,9 @@ git_for_deps_rebar(_Config, Target, RuleConfig) -> Deps = get_rebar_deps(Target), BadDeps = lists:filter(fun is_rebar_not_git_dep/1, Deps), lists:flatmap( - fun(Line) -> rebar_dep_to_result(Line, IgnoreDeps) end, BadDeps). + fun(Line) -> + rebar_dep_to_result(Line, ?DEP_NO_GIT, IgnoreDeps) + end, BadDeps). -spec no_deps_master_erlang_mk(elvis_config:config(), elvis_file:file(), @@ -57,7 +61,9 @@ no_deps_master_erlang_mk(_Config, Target, RuleConfig) -> Deps = get_erlang_mk_deps(Target), BadDeps = lists:filter(fun is_erlang_mk_master_dep/1, Deps), lists:flatmap( - fun(Line) -> erlang_mk_dep_to_result(Line, IgnoreDeps) end, BadDeps). + fun(Line) -> + erlang_mk_dep_to_result(Line, ?DEP_MASTER, IgnoreDeps) + end, BadDeps). -spec no_deps_master_rebar(elvis_config:config(), elvis_file:file(), @@ -68,7 +74,9 @@ no_deps_master_rebar(_Config, Target, RuleConfig) -> Deps = get_rebar_deps(Target), BadDeps = lists:filter(fun is_rebar_master_dep/1, Deps), lists:flatmap( - fun(Line) -> rebar_dep_to_result(Line, IgnoreDeps) end, BadDeps). + fun(Line) -> + rebar_dep_to_result(Line, ?DEP_MASTER, IgnoreDeps) + end, BadDeps). -spec old_configuration_format(elvis_config:config(), elvis_file:file(), @@ -115,12 +123,12 @@ is_rebar_master_dep(_) -> is_rebar_not_git_dep({_AppName, _Vsn, {_SCM, "git://" ++ _, _Branch}}) -> false; is_rebar_not_git_dep(_) -> true. -rebar_dep_to_result({AppName, _, _}, IgnoreDeps) -> +rebar_dep_to_result({AppName, _, _}, Message, IgnoreDeps) -> case lists:member(AppName, IgnoreDeps) of true -> []; false -> - [elvis_result:new(item, ?DEP_MASTER, [AppName])] + [elvis_result:new(item, Message, [AppName])] end. @@ -133,7 +141,16 @@ is_erlang_mk_master_dep(Line) -> end. is_erlang_mk_not_git_dep(Line) -> - lager:alert("~p", [Line]), false. + [_DepName, Dependency] = binary:split(Line, <<"=">>), + [Protocol, Url | _] = + [Part + || Part <- binary:split(Dependency, <<" ">>, [global, trim]) + , Part /= <<>>], + case {Protocol, Url} of + {<<"git">>, <<"git://", _/binary>>} -> false; + {<<"git">>, _} -> true; + {_NotGit, _} -> false + end. get_erlang_mk_deps(File) -> {Src, _} = elvis_file:src(File), @@ -141,7 +158,7 @@ get_erlang_mk_deps(File) -> IsDepsLine = fun(Line) -> re:run(Line, "dep_", []) /= nomatch end, lists:filter(IsDepsLine, Lines). -erlang_mk_dep_to_result(Line, IgnoreDeps) -> +erlang_mk_dep_to_result(Line, Message, IgnoreDeps) -> Opts = [{capture, all_but_first, binary}], {match, [Name]} = re:run(Line, "dep_([^ ]*)", Opts), NameAtom = binary_to_atom(Name, utf8), @@ -149,7 +166,7 @@ erlang_mk_dep_to_result(Line, IgnoreDeps) -> true -> []; false -> - [elvis_result:new(item, ?DEP_MASTER, [Name])] + [elvis_result:new(item, Message, [Name])] end. %% Old config diff --git a/test/project_SUITE.erl b/test/project_SUITE.erl index f7e7505..fe61179 100644 --- a/test/project_SUITE.erl +++ b/test/project_SUITE.erl @@ -115,10 +115,10 @@ verify_git_for_deps_rebar(_Config) -> [_, _] = elvis_project:git_for_deps_rebar(ElvisConfig, File, #{}), - RuleConfig = #{ignore => [aleppo]}, + RuleConfig = #{ignore => [getopt]}, [_] = elvis_project:git_for_deps_rebar(ElvisConfig, File, RuleConfig), - RuleConfig1 = #{ignore => [aleppo, lager]}, + RuleConfig1 = #{ignore => [getopt, lager]}, [] = elvis_project:git_for_deps_rebar(ElvisConfig, File, RuleConfig1). -spec verify_old_config_format(config()) -> any(). From eecc9cd03d75ae7b867fad6bf567cdf00378a3e0 Mon Sep 17 00:00:00 2001 From: Brujo Benavides Date: Mon, 12 Jan 2015 12:18:22 -0300 Subject: [PATCH 3/3] CHANGELOG --- CHANGELOG.md | 1 + 1 file changed, 1 insertion(+) diff --git a/CHANGELOG.md b/CHANGELOG.md index 09896c6..44838af 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -7,6 +7,7 @@ All notable changes to this project will be documented in this file. ### Added - [#195] elvis_webhook as an egithub_webhook +- [#185] Rule to enforce dependency url fetch protocol ### Deprecated