Proto 0.2.1
This commit is contained in:
parent
0b52119b3d
commit
2508b17637
@ -1 +1 @@
|
|||||||
0.2.0
|
0.2.1
|
||||||
|
|||||||
@ -1,6 +1,6 @@
|
|||||||
{application,zx,
|
{application,zx,
|
||||||
[{description,"Zomp client program"},
|
[{description,"Zomp client program"},
|
||||||
{vsn,"0.2.0"},
|
{vsn,"0.2.1"},
|
||||||
{applications,[stdlib,kernel]},
|
{applications,[stdlib,kernel]},
|
||||||
{modules,[zx,zx_auth,zx_conn,zx_conn_sup,zx_daemon,zx_key,
|
{modules,[zx,zx_auth,zx_conn,zx_conn_sup,zx_daemon,zx_key,
|
||||||
zx_lib,zx_local,zx_net,zx_peer,zx_peer_man,
|
zx_lib,zx_local,zx_net,zx_peer,zx_peer_man,
|
||||||
@ -24,7 +24,7 @@
|
|||||||
%%% @end
|
%%% @end
|
||||||
|
|
||||||
-module(zx).
|
-module(zx).
|
||||||
-vsn("0.2.0").
|
-vsn("0.2.1").
|
||||||
-behavior(application).
|
-behavior(application).
|
||||||
-author("Craig Everett <zxq9@zxq9.com>").
|
-author("Craig Everett <zxq9@zxq9.com>").
|
||||||
-copyright("Craig Everett <zxq9@zxq9.com>").
|
-copyright("Craig Everett <zxq9@zxq9.com>").
|
||||||
@ -42,7 +42,7 @@
|
|||||||
key_data/0, key_bin/0, key_id/0, key_name/0,
|
key_data/0, key_bin/0, key_id/0, key_name/0,
|
||||||
user_id/0, user_name/0, contact_info/0, user_data/0,
|
user_id/0, user_name/0, contact_info/0, user_data/0,
|
||||||
lower0_9/0, label/0,
|
lower0_9/0, label/0,
|
||||||
package_meta/0, ss_tag/0, search_tag/0,
|
package_meta/0, ss_tag/0, search_tag/0, description/0, package_type/0,
|
||||||
outcome/0]).
|
outcome/0]).
|
||||||
|
|
||||||
-include("zx_logger.hrl").
|
-include("zx_logger.hrl").
|
||||||
@ -78,12 +78,33 @@
|
|||||||
-type lower0_9() :: [$a..$z | $0..$9 | $_].
|
-type lower0_9() :: [$a..$z | $0..$9 | $_].
|
||||||
-type label() :: [$a..$z | $0..$9 | $_ | $- | $.].
|
-type label() :: [$a..$z | $0..$9 | $_ | $- | $.].
|
||||||
-type package_meta() :: #{package_id := package_id(),
|
-type package_meta() :: #{package_id := package_id(),
|
||||||
search_tags := [search_tag()],
|
name := string(),
|
||||||
|
desc := string(),
|
||||||
|
author := string(),
|
||||||
|
a_email := string(),
|
||||||
|
copyright := string(),
|
||||||
|
c_email := string(),
|
||||||
|
ws_url := string(),
|
||||||
|
repo_url := string(),
|
||||||
|
prefix := string(),
|
||||||
|
tags := [search_tag()],
|
||||||
deps := [package_id()],
|
deps := [package_id()],
|
||||||
type := app | lib}.
|
type := package_type()}.
|
||||||
-type ss_tag() :: {serial(), calendar:timestamp()}.
|
-type ss_tag() :: {serial(), calendar:timestamp()}.
|
||||||
-type search_tag() :: string().
|
-type search_tag() :: string().
|
||||||
|
|
||||||
|
-type description() :: {description,
|
||||||
|
PackageID :: package_id(),
|
||||||
|
DisplayName :: string(),
|
||||||
|
Type :: package_type(),
|
||||||
|
Desc :: string(),
|
||||||
|
Author :: string(),
|
||||||
|
AEmail :: string(),
|
||||||
|
WebURL :: string(),
|
||||||
|
RepoURL :: string(),
|
||||||
|
Tags :: [zx:search_tag()]}.
|
||||||
|
-type package_type() :: app | lib | gui | cli.
|
||||||
|
|
||||||
-type outcome() :: ok
|
-type outcome() :: ok
|
||||||
| {error, Reason :: term()}
|
| {error, Reason :: term()}
|
||||||
| {error, Code :: non_neg_integer()}
|
| {error, Code :: non_neg_integer()}
|
||||||
@ -114,6 +135,8 @@ do(["help", "dev"]) ->
|
|||||||
done(help(dev));
|
done(help(dev));
|
||||||
do(["help", "sysop"]) ->
|
do(["help", "sysop"]) ->
|
||||||
done(help(sysop));
|
done(help(sysop));
|
||||||
|
do(["--version"]) ->
|
||||||
|
done(version());
|
||||||
do(["run", PackageString | ArgV]) ->
|
do(["run", PackageString | ArgV]) ->
|
||||||
ok = zx_daemon:connect(),
|
ok = zx_daemon:connect(),
|
||||||
not_done(run(PackageString, ArgV));
|
not_done(run(PackageString, ArgV));
|
||||||
@ -128,6 +151,9 @@ do(["list", "versions", PackageName]) ->
|
|||||||
do(["latest", PackageString]) ->
|
do(["latest", PackageString]) ->
|
||||||
ok = zx_daemon:connect(),
|
ok = zx_daemon:connect(),
|
||||||
done(zx_local:latest(PackageString));
|
done(zx_local:latest(PackageString));
|
||||||
|
do(["describe", PackageString]) ->
|
||||||
|
ok = zx_daemon:connect(),
|
||||||
|
done(zx_local:describe(PackageString));
|
||||||
do(["upgrade"]) ->
|
do(["upgrade"]) ->
|
||||||
ok = zx_daemon:connect(),
|
ok = zx_daemon:connect(),
|
||||||
done(upgrade());
|
done(upgrade());
|
||||||
@ -185,6 +211,8 @@ do(["set", "version", VersionString]) ->
|
|||||||
do(["provides", Module]) ->
|
do(["provides", Module]) ->
|
||||||
ok = zx_daemon:connect(),
|
ok = zx_daemon:connect(),
|
||||||
done(zx_local:provides(Module));
|
done(zx_local:provides(Module));
|
||||||
|
do(["update", "meta"]) ->
|
||||||
|
done(zx_local:update_meta());
|
||||||
do(["update", ".app"]) ->
|
do(["update", ".app"]) ->
|
||||||
done(zx_local:update_app_file());
|
done(zx_local:update_app_file());
|
||||||
do(["package"]) ->
|
do(["package"]) ->
|
||||||
@ -481,7 +509,7 @@ list() ->
|
|||||||
|
|
||||||
list(Realm) ->
|
list(Realm) ->
|
||||||
{ok, ID} = zx_daemon:list(Realm),
|
{ok, ID} = zx_daemon:list(Realm),
|
||||||
wait_result(ID).
|
zx_daemon:wait_result(ID).
|
||||||
|
|
||||||
|
|
||||||
-spec list(realm(), name()) -> Result
|
-spec list(realm(), name()) -> Result
|
||||||
@ -507,7 +535,7 @@ list(Realm, Name) ->
|
|||||||
|
|
||||||
list(Realm, Name, Version) ->
|
list(Realm, Name, Version) ->
|
||||||
{ok, ID} = zx_daemon:list(Realm, Name, Version),
|
{ok, ID} = zx_daemon:list(Realm, Name, Version),
|
||||||
wait_result(ID).
|
zx_daemon:wait_result(ID).
|
||||||
|
|
||||||
|
|
||||||
-spec latest(package_id()) -> Result
|
-spec latest(package_id()) -> Result
|
||||||
@ -521,7 +549,7 @@ list(Realm, Name, Version) ->
|
|||||||
|
|
||||||
latest(PackageID) ->
|
latest(PackageID) ->
|
||||||
{ok, ID} = zx_daemon:latest(PackageID),
|
{ok, ID} = zx_daemon:latest(PackageID),
|
||||||
wait_result(ID).
|
zx_daemon:wait_result(ID).
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
@ -620,7 +648,7 @@ resolve_version(PackageID = {_, _, {X, Y, Z}})
|
|||||||
end;
|
end;
|
||||||
resolve_version(PackageID = {Realm, Name, _}) ->
|
resolve_version(PackageID = {Realm, Name, _}) ->
|
||||||
{ok, ID} = zx_daemon:latest(PackageID),
|
{ok, ID} = zx_daemon:latest(PackageID),
|
||||||
case wait_result(ID) of
|
case zx_daemon:wait_result(ID) of
|
||||||
{ok, Latest} -> resolve_version({Realm, Name, Latest});
|
{ok, Latest} -> resolve_version({Realm, Name, Latest});
|
||||||
Error -> Error
|
Error -> Error
|
||||||
end.
|
end.
|
||||||
@ -722,7 +750,7 @@ upgrade() ->
|
|||||||
{ok, PackageString} = zx_lib:package_string(PackageID),
|
{ok, PackageString} = zx_lib:package_string(PackageID),
|
||||||
ok = tell("Current version: ~s~n", [PackageString]),
|
ok = tell("Current version: ~s~n", [PackageString]),
|
||||||
{ok, ID} = zx_daemon:latest({Realm, Name}),
|
{ok, ID} = zx_daemon:latest({Realm, Name}),
|
||||||
case wait_result(ID) of
|
case zx_daemon:wait_result(ID) of
|
||||||
{ok, Current} ->
|
{ok, Current} ->
|
||||||
tell("Running latest version.~n");
|
tell("Running latest version.~n");
|
||||||
{ok, Latest} when Latest > Current ->
|
{ok, Latest} when Latest > Current ->
|
||||||
@ -812,13 +840,6 @@ ensure_all_started(AppMod) ->
|
|||||||
end.
|
end.
|
||||||
|
|
||||||
|
|
||||||
wait_result(ID) ->
|
|
||||||
receive
|
|
||||||
{result, ID, Result} -> Result
|
|
||||||
after 5000 -> {error, timeout}
|
|
||||||
end.
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
%%% Usage
|
%%% Usage
|
||||||
|
|
||||||
@ -849,6 +870,7 @@ usage_user() ->
|
|||||||
" zx list packages Realm~n"
|
" zx list packages Realm~n"
|
||||||
" zx list versions PackageID~n"
|
" zx list versions PackageID~n"
|
||||||
" zx latest PackageID~n"
|
" zx latest PackageID~n"
|
||||||
|
" zx describe Package~n"
|
||||||
" zx upgrade~n"
|
" zx upgrade~n"
|
||||||
" zx import realm RealmFile~n"
|
" zx import realm RealmFile~n"
|
||||||
" zx drop realm Realm~n"
|
" zx drop realm Realm~n"
|
||||||
@ -869,6 +891,7 @@ usage_dev() ->
|
|||||||
" zx verup Level~n"
|
" zx verup Level~n"
|
||||||
" zx set version Version~n"
|
" zx set version Version~n"
|
||||||
" zx provides Module~n"
|
" zx provides Module~n"
|
||||||
|
" zx update meta~n"
|
||||||
" zx update .app~n"
|
" zx update .app~n"
|
||||||
" zx package [Path]~n"
|
" zx package [Path]~n"
|
||||||
" zx submit ZSP~n"
|
" zx submit ZSP~n"
|
||||||
@ -922,3 +945,7 @@ usage_spec() ->
|
|||||||
" ZSP :: Path to a .zsp file (Zomp Source Package).~n"
|
" ZSP :: Path to a .zsp file (Zomp Source Package).~n"
|
||||||
" ZPUF :: Path to a .zpuf file (Zomp Public User File).~n"
|
" ZPUF :: Path to a .zpuf file (Zomp Public User File).~n"
|
||||||
" ZDUF :: Path to a .zduf file (Zomp DANGEROUS User File).~n".
|
" ZDUF :: Path to a .zduf file (Zomp DANGEROUS User File).~n".
|
||||||
|
|
||||||
|
|
||||||
|
version() ->
|
||||||
|
io:format("zx ~ts~n", [os:getenv("ZX_VERSION")]).
|
||||||
@ -9,7 +9,7 @@
|
|||||||
%%% @end
|
%%% @end
|
||||||
|
|
||||||
-module(zx_auth).
|
-module(zx_auth).
|
||||||
-vsn("0.2.0").
|
-vsn("0.2.1").
|
||||||
-author("Craig Everett <zxq9@zxq9.com>").
|
-author("Craig Everett <zxq9@zxq9.com>").
|
||||||
-copyright("Craig Everett <zxq9@zxq9.com>").
|
-copyright("Craig Everett <zxq9@zxq9.com>").
|
||||||
-license("GPL-3.0").
|
-license("GPL-3.0").
|
||||||
@ -7,7 +7,7 @@
|
|||||||
%%% @end
|
%%% @end
|
||||||
|
|
||||||
-module(zx_conn).
|
-module(zx_conn).
|
||||||
-vsn("0.2.0").
|
-vsn("0.2.1").
|
||||||
-author("Craig Everett <zxq9@zxq9.com>").
|
-author("Craig Everett <zxq9@zxq9.com>").
|
||||||
-copyright("Craig Everett <zxq9@zxq9.com>").
|
-copyright("Craig Everett <zxq9@zxq9.com>").
|
||||||
-license("GPL-3.0").
|
-license("GPL-3.0").
|
||||||
@ -5,7 +5,7 @@
|
|||||||
%%% @end
|
%%% @end
|
||||||
|
|
||||||
-module(zx_conn_sup).
|
-module(zx_conn_sup).
|
||||||
-vsn("0.2.0").
|
-vsn("0.2.1").
|
||||||
-behavior(supervisor).
|
-behavior(supervisor).
|
||||||
-author("Craig Everett <zxq9@zxq9.com>").
|
-author("Craig Everett <zxq9@zxq9.com>").
|
||||||
-copyright("Craig Everett <zxq9@zxq9.com>").
|
-copyright("Craig Everett <zxq9@zxq9.com>").
|
||||||
@ -138,7 +138,7 @@
|
|||||||
%%% @end
|
%%% @end
|
||||||
|
|
||||||
-module(zx_daemon).
|
-module(zx_daemon).
|
||||||
-vsn("0.2.0").
|
-vsn("0.2.1").
|
||||||
-behavior(gen_server).
|
-behavior(gen_server).
|
||||||
-author("Craig Everett <zxq9@zxq9.com>").
|
-author("Craig Everett <zxq9@zxq9.com>").
|
||||||
-copyright("Craig Everett <zxq9@zxq9.com>").
|
-copyright("Craig Everett <zxq9@zxq9.com>").
|
||||||
@ -148,9 +148,10 @@
|
|||||||
-export([pass_meta/3, argv/0,
|
-export([pass_meta/3, argv/0,
|
||||||
subscribe/1, unsubscribe/1,
|
subscribe/1, unsubscribe/1,
|
||||||
list/0, list/1, list/2, list/3, latest/1,
|
list/0, list/1, list/2, list/3, latest/1,
|
||||||
provides/2, list_deps/1,
|
describe/1, provides/2, list_deps/1,
|
||||||
list_sysops/1,
|
list_sysops/1,
|
||||||
fetch/1, install/1, build/1]).
|
fetch/1, install/1, build/1,
|
||||||
|
wait_result/1, wait_results/1]).
|
||||||
-export([register_key/2, get_key/2, keybin/2,
|
-export([register_key/2, get_key/2, keybin/2,
|
||||||
find_keypair/1, have_key/2, list_keys/2]).
|
find_keypair/1, have_key/2, list_keys/2]).
|
||||||
-export([report/1, result/2, notify/2]).
|
-export([report/1, result/2, notify/2]).
|
||||||
@ -271,6 +272,7 @@
|
|||||||
| {list, zx:realm(), zx:name(), zx:version()}
|
| {list, zx:realm(), zx:name(), zx:version()}
|
||||||
| {latest, zx:realm(), zx:name()}
|
| {latest, zx:realm(), zx:name()}
|
||||||
| {latest, zx:realm(), zx:name(), zx:version()}
|
| {latest, zx:realm(), zx:name(), zx:version()}
|
||||||
|
| {describe, zx:realm(), zx:name()}
|
||||||
| {provides, zx:realm(), string()}
|
| {provides, zx:realm(), string()}
|
||||||
| {list_deps, zx:realm(), zx:name(), zx:version()}
|
| {list_deps, zx:realm(), zx:name(), zx:version()}
|
||||||
| {list_sysops, zx:realm()}
|
| {list_sysops, zx:realm()}
|
||||||
@ -292,6 +294,7 @@
|
|||||||
| package_list()
|
| package_list()
|
||||||
| version_list()
|
| version_list()
|
||||||
| latest_result()
|
| latest_result()
|
||||||
|
| desc_result()
|
||||||
| fetch_result()
|
| fetch_result()
|
||||||
| key_result()}.
|
| key_result()}.
|
||||||
|
|
||||||
@ -308,6 +311,11 @@
|
|||||||
| bad_package
|
| bad_package
|
||||||
| bad_version
|
| bad_version
|
||||||
| timeout}.
|
| timeout}.
|
||||||
|
-type desc_result() :: {ok, zx:description()}
|
||||||
|
| {error, bad_realm
|
||||||
|
| bad_package
|
||||||
|
| bad_version
|
||||||
|
| timeout}.
|
||||||
-type fetch_result() :: {hops, non_neg_integer()}
|
-type fetch_result() :: {hops, non_neg_integer()}
|
||||||
| {done, zx:package_id()}
|
| {done, zx:package_id()}
|
||||||
| {error, bad_realm
|
| {error, bad_realm
|
||||||
@ -473,6 +481,14 @@ latest({Realm, Name, Version}) ->
|
|||||||
request({latest, Realm, Name, Version}).
|
request({latest, Realm, Name, Version}).
|
||||||
|
|
||||||
|
|
||||||
|
-spec describe(Package) -> {ok, RequestID}
|
||||||
|
when Package :: zx:package(),
|
||||||
|
RequestID :: integer().
|
||||||
|
|
||||||
|
describe({Realm, Name}) ->
|
||||||
|
request({describe, Realm, Name}).
|
||||||
|
|
||||||
|
|
||||||
-spec provides(Realm, Module) -> {ok, RequestID}
|
-spec provides(Realm, Module) -> {ok, RequestID}
|
||||||
when Realm :: zx:realm(),
|
when Realm :: zx:realm(),
|
||||||
Module :: string(),
|
Module :: string(),
|
||||||
@ -521,6 +537,59 @@ build(PackageID) ->
|
|||||||
gen_server:call(?MODULE, {build, PackageID}).
|
gen_server:call(?MODULE, {build, PackageID}).
|
||||||
|
|
||||||
|
|
||||||
|
-spec wait_result(ID) -> Result
|
||||||
|
when ID :: id(),
|
||||||
|
Result :: {ok, term()}
|
||||||
|
| {error, Reason},
|
||||||
|
Reason :: bad_realm
|
||||||
|
| bad_package
|
||||||
|
| bad_version
|
||||||
|
| timeout
|
||||||
|
| network
|
||||||
|
| {unexpected, Message :: string()}.
|
||||||
|
|
||||||
|
wait_result(ID) ->
|
||||||
|
receive
|
||||||
|
{result, ID, Result} -> Result;
|
||||||
|
Message -> {error, {unexpected, Message}}
|
||||||
|
after 5000 -> {error, timeout}
|
||||||
|
end.
|
||||||
|
|
||||||
|
|
||||||
|
-spec wait_results(IDs) -> Outcome
|
||||||
|
when IDs :: [id()],
|
||||||
|
Outcome :: {ok, [Result]}
|
||||||
|
| {error, Unexpected, [Result]}
|
||||||
|
| {error, Reason},
|
||||||
|
Result :: {id(), term()},
|
||||||
|
Unexpected :: {unexpected, {result, id(), term()}},
|
||||||
|
Reason :: bad_realm
|
||||||
|
| bad_package
|
||||||
|
| bad_version
|
||||||
|
| timeout
|
||||||
|
| network
|
||||||
|
| {unexpected, Message :: string()}.
|
||||||
|
|
||||||
|
|
||||||
|
wait_results(IDs) ->
|
||||||
|
wait_results(IDs, []).
|
||||||
|
|
||||||
|
wait_results([], Results) ->
|
||||||
|
{ok, Results};
|
||||||
|
wait_results(IDs, Results) ->
|
||||||
|
receive
|
||||||
|
{result, ID, Result} ->
|
||||||
|
case lists:member(ID, IDs) of
|
||||||
|
true -> wait_results(lists:delete(ID, IDs), [{ID, Result} | Results]);
|
||||||
|
false -> {error, {unexpected, {result, ID, Result}}, Results}
|
||||||
|
end;
|
||||||
|
Message ->
|
||||||
|
{error, {unexpected, Message}}
|
||||||
|
after 5000 ->
|
||||||
|
{error, timeout}
|
||||||
|
end.
|
||||||
|
|
||||||
|
|
||||||
-spec add_mirror(zx:host()) -> ok.
|
-spec add_mirror(zx:host()) -> ok.
|
||||||
|
|
||||||
add_mirror(Host) ->
|
add_mirror(Host) ->
|
||||||
@ -1304,6 +1373,7 @@ local_request(R, {list, N}) -> zomp_realm:list(R, N);
|
|||||||
local_request(R, {list, N, V}) -> zomp_realm:list(R, {N, V});
|
local_request(R, {list, N, V}) -> zomp_realm:list(R, {N, V});
|
||||||
local_request(R, {latest, N}) -> zomp_realm:latest(R, N);
|
local_request(R, {latest, N}) -> zomp_realm:latest(R, N);
|
||||||
local_request(R, {latest, N, V}) -> zomp_realm:latest(R, {N, V});
|
local_request(R, {latest, N, V}) -> zomp_realm:latest(R, {N, V});
|
||||||
|
local_request(R, {describe, N}) -> zomp_realm:describe(R, N);
|
||||||
local_request(R, {provides, M}) -> zomp_realm:provides(R, M);
|
local_request(R, {provides, M}) -> zomp_realm:provides(R, M);
|
||||||
local_request(R, {list_deps, N, V}) -> zomp_realm:list_deps(R, {N, V});
|
local_request(R, {list_deps, N, V}) -> zomp_realm:list_deps(R, {N, V});
|
||||||
local_request(R, {list_sysops}) -> zomp_realm:list_sysops(R).
|
local_request(R, {list_sysops}) -> zomp_realm:list_sysops(R).
|
||||||
@ -8,7 +8,7 @@
|
|||||||
%%% @end
|
%%% @end
|
||||||
|
|
||||||
-module(zx_key).
|
-module(zx_key).
|
||||||
-vsn("0.2.0").
|
-vsn("0.2.1").
|
||||||
-author("Craig Everett <zxq9@zxq9.com>").
|
-author("Craig Everett <zxq9@zxq9.com>").
|
||||||
-copyright("Craig Everett <zxq9@zxq9.com>").
|
-copyright("Craig Everett <zxq9@zxq9.com>").
|
||||||
-license("GPL-3.0").
|
-license("GPL-3.0").
|
||||||
@ -10,7 +10,7 @@
|
|||||||
%%% @end
|
%%% @end
|
||||||
|
|
||||||
-module(zx_lib).
|
-module(zx_lib).
|
||||||
-vsn("0.2.0").
|
-vsn("0.2.1").
|
||||||
-author("Craig Everett <zxq9@zxq9.com>").
|
-author("Craig Everett <zxq9@zxq9.com>").
|
||||||
-copyright("Craig Everett <zxq9@zxq9.com>").
|
-copyright("Craig Everett <zxq9@zxq9.com>").
|
||||||
-license("GPL-3.0").
|
-license("GPL-3.0").
|
||||||
@ -6,25 +6,27 @@
|
|||||||
%%% @end
|
%%% @end
|
||||||
|
|
||||||
-module(zx_local).
|
-module(zx_local).
|
||||||
-vsn("0.2.0").
|
-vsn("0.2.1").
|
||||||
-author("Craig Everett <zxq9@zxq9.com>").
|
-author("Craig Everett <zxq9@zxq9.com>").
|
||||||
-copyright("Craig Everett <zxq9@zxq9.com>").
|
-copyright("Craig Everett <zxq9@zxq9.com>").
|
||||||
-license("GPL-3.0").
|
-license("GPL-3.0").
|
||||||
|
|
||||||
-export([initialize/0, set_version/1,
|
-export([initialize/0, set_version/1,
|
||||||
list_realms/0, list_packages/1, list_versions/1,
|
list_realms/0, list_packages/1, list_versions/1,
|
||||||
latest/1, provides/1,
|
latest/1, describe/1, provides/1,
|
||||||
list_keys/0, list_sysops/1,
|
list_keys/0, list_sysops/1,
|
||||||
set_dep/1, list_deps/0, list_deps/1, drop_dep/1, verup/1, package/1,
|
set_dep/1, list_deps/0, list_deps/1, drop_dep/1, verup/1, package/1,
|
||||||
update_app_file/0,
|
update_meta/0, update_app_file/0,
|
||||||
import_realm/1, drop_realm/1, logpath/2,
|
import_realm/1, drop_realm/1, logpath/2,
|
||||||
set_timeout/1, add_mirror/0, drop_mirror/0,
|
set_timeout/1,
|
||||||
|
add_mirror/0, add_mirror/1, add_mirror/2,
|
||||||
|
drop_mirror/0, drop_mirror/1, drop_mirror/2,
|
||||||
create_project/0,
|
create_project/0,
|
||||||
grow_a_pair/0, grow_a_pair/2, drop_key/1,
|
grow_a_pair/0, grow_a_pair/2, drop_key/1,
|
||||||
create_user/0, create_userfile/0, export_user/0, import_user/1,
|
create_user/0, create_userfile/0, export_user/0, import_user/1,
|
||||||
create_realm/0, create_realmfile/0, create_realmfile/1]).
|
create_realm/0, create_realmfile/0, create_realmfile/1]).
|
||||||
|
|
||||||
-export([select_realm/0, create_user/1, select_private_key/1]).
|
-export([create_user/1, select_private_key/1]).
|
||||||
|
|
||||||
-include("zx_logger.hrl").
|
-include("zx_logger.hrl").
|
||||||
|
|
||||||
@ -50,7 +52,6 @@
|
|||||||
desc = none :: none | string(),
|
desc = none :: none | string(),
|
||||||
repo_url = none :: none | string(),
|
repo_url = none :: none | string(),
|
||||||
ws_url = none :: none | string(),
|
ws_url = none :: none | string(),
|
||||||
url = none :: none | string(),
|
|
||||||
id = none :: none | zx:package_id() | zx:name(),
|
id = none :: none | zx:package_id() | zx:name(),
|
||||||
prefix = none :: none | zx:lower0_9(),
|
prefix = none :: none | zx:lower0_9(),
|
||||||
appmod = none :: none | zx:lower0_9(),
|
appmod = none :: none | zx:lower0_9(),
|
||||||
@ -59,7 +60,9 @@
|
|||||||
a_email = none :: none | string(),
|
a_email = none :: none | string(),
|
||||||
copyright = none :: none | string(),
|
copyright = none :: none | string(),
|
||||||
c_email = none :: none | string(),
|
c_email = none :: none | string(),
|
||||||
deps = [] :: [zx:package_id()]}).
|
deps = [] :: [zx:package_id()],
|
||||||
|
tags = [] :: [string()],
|
||||||
|
file_exts = [] :: [string()]}).
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
@ -447,6 +450,170 @@ initialize_app_file({_, Name, Version}, AppMod, Type, Desc) ->
|
|||||||
zx_lib:write_terms(AppFile, [AppProfile]).
|
zx_lib:write_terms(AppFile, [AppProfile]).
|
||||||
|
|
||||||
|
|
||||||
|
-spec update_meta() -> zx:outcome().
|
||||||
|
|
||||||
|
update_meta() ->
|
||||||
|
case zx_lib:read_project_meta() of
|
||||||
|
{ok, Data} -> update_meta(Data);
|
||||||
|
Error -> Error
|
||||||
|
end.
|
||||||
|
|
||||||
|
update_meta(Data = #{package_id := {_, Name, _}}) ->
|
||||||
|
P = #project{name = maps:get(name, Data, Name),
|
||||||
|
author = maps:get(author, Data, ""),
|
||||||
|
a_email = maps:get(a_email, Data, ""),
|
||||||
|
copyright = maps:get(copyright, Data, ""),
|
||||||
|
c_email = maps:get(c_email, Data, ""),
|
||||||
|
repo_url = maps:get(repo_url, Data, ""),
|
||||||
|
ws_url = maps:get(ws_url, Data, ""),
|
||||||
|
desc = maps:get(desc, Data, ""),
|
||||||
|
tags = sets:from_list(maps:get(tags, Data, [])),
|
||||||
|
file_exts = sets:from_list(maps:get(file_exts, Data, []))},
|
||||||
|
update_meta(Data, P).
|
||||||
|
|
||||||
|
update_meta(Data = #{type := gui},
|
||||||
|
P = #project{name = Name,
|
||||||
|
author = Author,
|
||||||
|
a_email = AEmail,
|
||||||
|
copyright = CR,
|
||||||
|
c_email = CEmail,
|
||||||
|
repo_url = RepoURL,
|
||||||
|
ws_url = WebURL,
|
||||||
|
desc = Desc,
|
||||||
|
tags = Tags,
|
||||||
|
file_exts = Exts}) ->
|
||||||
|
Instructions =
|
||||||
|
"~nDESCRIPTION DATA~n"
|
||||||
|
"[ 1] Project Name : ~ts~n"
|
||||||
|
"[ 2] Author : ~ts~n"
|
||||||
|
"[ 3] Author's Email : ~ts~n"
|
||||||
|
"[ 4] Copyright Holder : ~ts~n"
|
||||||
|
"[ 5] Copyright Holder's Email : ~ts~n"
|
||||||
|
"[ 6] Repo URL : ~ts~n"
|
||||||
|
"[ 7] Website URL : ~ts~n"
|
||||||
|
"[ 8] Description : ~ts~n"
|
||||||
|
"[ 9] Search Tags : ~tp~n"
|
||||||
|
"[10] File associations : ~tp~n"
|
||||||
|
"Press a number to select something to change, or [ENTER] to continue.~n",
|
||||||
|
ok = io:format(Instructions,
|
||||||
|
[Name,
|
||||||
|
Author, AEmail, CR, CEmail,
|
||||||
|
RepoURL, WebURL,
|
||||||
|
Desc, sets:to_list(Tags), sets:to_list(Exts)]),
|
||||||
|
case zx_tty:get_input() of
|
||||||
|
"1" ->
|
||||||
|
update_meta(Data, P#project{name = ask_project_name()});
|
||||||
|
"2" ->
|
||||||
|
{A, E} = ask_author(),
|
||||||
|
update_meta(Data, P#project{author = A, a_email = E});
|
||||||
|
"3" ->
|
||||||
|
update_meta(Data, P#project{a_email = ask_email_optional()});
|
||||||
|
"4" ->
|
||||||
|
{C, E} = ask_copyright(),
|
||||||
|
update_meta(Data, P#project{copyright = C, c_email = E});
|
||||||
|
"5" ->
|
||||||
|
update_meta(Data, P#project{c_email = ask_email_optional()});
|
||||||
|
"6" ->
|
||||||
|
update_meta(Data, P#project{repo_url = ask_url(repo)});
|
||||||
|
"7" ->
|
||||||
|
update_meta(Data, P#project{ws_url = ask_url(website)});
|
||||||
|
"8" ->
|
||||||
|
update_meta(Data, P#project{desc = ask_description()});
|
||||||
|
"9" ->
|
||||||
|
update_meta(Data, P#project{tags = edit_tags(Tags)});
|
||||||
|
"10" ->
|
||||||
|
update_meta(Data, P#project{file_exts = edit_exts(Exts)});
|
||||||
|
"" ->
|
||||||
|
finalize_meta(Data, P);
|
||||||
|
_ ->
|
||||||
|
ok = zx_tty:derp(),
|
||||||
|
update_meta(Data, P)
|
||||||
|
end;
|
||||||
|
update_meta(Data,
|
||||||
|
P = #project{name = Name,
|
||||||
|
author = Author,
|
||||||
|
a_email = AEmail,
|
||||||
|
copyright = CR,
|
||||||
|
c_email = CEmail,
|
||||||
|
repo_url = RepoURL,
|
||||||
|
ws_url = WebURL,
|
||||||
|
desc = Desc,
|
||||||
|
tags = Tags}) ->
|
||||||
|
Instructions =
|
||||||
|
"~nDESCRIPTION DATA~n"
|
||||||
|
"[1] Project Name : ~ts~n"
|
||||||
|
"[2] Author : ~ts~n"
|
||||||
|
"[3] Author's Email : ~ts~n"
|
||||||
|
"[4] Copyright Holder : ~ts~n"
|
||||||
|
"[5] Copyright Holder's Email : ~ts~n"
|
||||||
|
"[6] Repo URL : ~ts~n"
|
||||||
|
"[7] Website URL : ~ts~n"
|
||||||
|
"[8] Description : ~ts~n"
|
||||||
|
"[9] Search Tags : ~tp~n"
|
||||||
|
"Press a number to select something to change, or [ENTER] to continue.~n",
|
||||||
|
ok = io:format(Instructions,
|
||||||
|
[Name,
|
||||||
|
Author, AEmail, CR, CEmail,
|
||||||
|
RepoURL, WebURL,
|
||||||
|
Desc, sets:to_list(Tags)]),
|
||||||
|
case zx_tty:get_input() of
|
||||||
|
"1" ->
|
||||||
|
update_meta(Data, P#project{name = ask_project_name()});
|
||||||
|
"2" ->
|
||||||
|
{A, E} = ask_author(),
|
||||||
|
update_meta(Data, P#project{author = A, a_email = E});
|
||||||
|
"3" ->
|
||||||
|
update_meta(Data, P#project{a_email = ask_email_optional()});
|
||||||
|
"4" ->
|
||||||
|
{C, E} = ask_copyright(),
|
||||||
|
update_meta(Data, P#project{copyright = C, c_email = E});
|
||||||
|
"5" ->
|
||||||
|
update_meta(Data, P#project{c_email = ask_email_optional()});
|
||||||
|
"6" ->
|
||||||
|
update_meta(Data, P#project{repo_url = ask_url(repo)});
|
||||||
|
"7" ->
|
||||||
|
update_meta(Data, P#project{ws_url = ask_url(website)});
|
||||||
|
"8" ->
|
||||||
|
update_meta(Data, P#project{desc = ask_description()});
|
||||||
|
"9" ->
|
||||||
|
update_meta(Data, P#project{tags = edit_tags(Tags)});
|
||||||
|
"" ->
|
||||||
|
finalize_meta(Data, P);
|
||||||
|
_ ->
|
||||||
|
ok = zx_tty:derp(),
|
||||||
|
update_meta(Data, P)
|
||||||
|
end.
|
||||||
|
|
||||||
|
finalize_meta(Data = #{type := Type},
|
||||||
|
#project{name = Name,
|
||||||
|
author = Author,
|
||||||
|
a_email = AEmail,
|
||||||
|
copyright = CR,
|
||||||
|
c_email = CEmail,
|
||||||
|
repo_url = RepoURL,
|
||||||
|
ws_url = WebURL,
|
||||||
|
desc = Desc,
|
||||||
|
tags = Tags,
|
||||||
|
file_exts = Exts}) ->
|
||||||
|
Updated = Data#{name => Name,
|
||||||
|
author => Author,
|
||||||
|
a_email => AEmail,
|
||||||
|
copyright => CR,
|
||||||
|
c_email => CEmail,
|
||||||
|
repo_url => RepoURL,
|
||||||
|
ws_url => WebURL,
|
||||||
|
desc => Desc,
|
||||||
|
tags => sets:to_list(Tags),
|
||||||
|
file_exts => sets:to_list(Exts)},
|
||||||
|
NewData =
|
||||||
|
case Type == gui of
|
||||||
|
true -> Updated;
|
||||||
|
false -> maps:remove(file_exts, Updated)
|
||||||
|
end,
|
||||||
|
ok = zx_lib:write_project_meta(NewData),
|
||||||
|
update_app_file(NewData).
|
||||||
|
|
||||||
|
|
||||||
-spec update_app_file() -> zx:outcome().
|
-spec update_app_file() -> zx:outcome().
|
||||||
|
|
||||||
update_app_file() ->
|
update_app_file() ->
|
||||||
@ -457,6 +624,7 @@ update_app_file() ->
|
|||||||
|
|
||||||
update_app_file(Meta) ->
|
update_app_file(Meta) ->
|
||||||
{_, Name, Version} = maps:get(package_id, Meta),
|
{_, Name, Version} = maps:get(package_id, Meta),
|
||||||
|
Desc = maps:get(desc, Meta, ""),
|
||||||
{ok, VersionString} = zx_lib:version_to_string(Version),
|
{ok, VersionString} = zx_lib:version_to_string(Version),
|
||||||
AppName = list_to_atom(Name),
|
AppName = list_to_atom(Name),
|
||||||
AppFile = filename:join("ebin", Name ++ ".app"),
|
AppFile = filename:join("ebin", Name ++ ".app"),
|
||||||
@ -474,7 +642,7 @@ update_app_file(Meta) ->
|
|||||||
end,
|
end,
|
||||||
Grep = "grep -oP '^-module\\(\\K[^)]+' src/* | cut -d: -f2",
|
Grep = "grep -oP '^-module\\(\\K[^)]+' src/* | cut -d: -f2",
|
||||||
Modules = [list_to_atom(M) || M <- string:lexemes(os:cmd(Grep), "\n")],
|
Modules = [list_to_atom(M) || M <- string:lexemes(os:cmd(Grep), "\n")],
|
||||||
Properties = [{vsn, VersionString}, {modules, Modules}],
|
Properties = [{description, Desc}, {vsn, VersionString}, {modules, Modules}],
|
||||||
Store = fun(T, L) -> lists:keystore(element(1, T), 1, L, T) end,
|
Store = fun(T, L) -> lists:keystore(element(1, T), 1, L, T) end,
|
||||||
AppData = lists:foldl(Store, RawAppData, Properties),
|
AppData = lists:foldl(Store, RawAppData, Properties),
|
||||||
AppProfile = {application, AppName, AppData},
|
AppProfile = {application, AppName, AppData},
|
||||||
@ -525,7 +693,7 @@ update_version(Realm, Name, OldVersion, NewVersion, OldMeta) ->
|
|||||||
ok = update_app_vsn(Name, NewVersion),
|
ok = update_app_vsn(Name, NewVersion),
|
||||||
{ok, OldVS} = zx_lib:version_to_string(OldVersion),
|
{ok, OldVS} = zx_lib:version_to_string(OldVersion),
|
||||||
{ok, NewVS} = zx_lib:version_to_string(NewVersion),
|
{ok, NewVS} = zx_lib:version_to_string(NewVersion),
|
||||||
tell("Version changed from ~s to ~s~n.", [OldVS, NewVS]);
|
tell("Version changed from ~s to ~s.~n", [OldVS, NewVS]);
|
||||||
Error ->
|
Error ->
|
||||||
ok = tell(error, "Write to zomp.meta failed with: ~160tp", [Error]),
|
ok = tell(error, "Write to zomp.meta failed with: ~160tp", [Error]),
|
||||||
Error
|
Error
|
||||||
@ -550,7 +718,7 @@ list_realms() ->
|
|||||||
|
|
||||||
list_packages(Realm) ->
|
list_packages(Realm) ->
|
||||||
{ok, ID} = zx_daemon:list(Realm),
|
{ok, ID} = zx_daemon:list(Realm),
|
||||||
case wait_result(ID) of
|
case zx_daemon:wait_result(ID) of
|
||||||
{ok, []} -> tell(error, "No packages available.~n");
|
{ok, []} -> tell(error, "No packages available.~n");
|
||||||
{ok, Packages} -> lists:foreach(print_package(Realm), Packages);
|
{ok, Packages} -> lists:foreach(print_package(Realm), Packages);
|
||||||
{error, bad_realm} -> {error, "Unconfigured realm or bad realm name.", 22};
|
{error, bad_realm} -> {error, "Unconfigured realm or bad realm name.", 22};
|
||||||
@ -576,7 +744,7 @@ list_versions(PackageString) ->
|
|||||||
|
|
||||||
list_versions2({Realm, Name, Version}) ->
|
list_versions2({Realm, Name, Version}) ->
|
||||||
{ok, ID} = zx_daemon:list(Realm, Name, Version),
|
{ok, ID} = zx_daemon:list(Realm, Name, Version),
|
||||||
case wait_result(ID) of
|
case zx_daemon:wait_result(ID) of
|
||||||
{ok, []} -> tell(error, "No versions available.~n");
|
{ok, []} -> tell(error, "No versions available.~n");
|
||||||
{ok, Versions} -> lists:foreach(fun print_version/1, Versions);
|
{ok, Versions} -> lists:foreach(fun print_version/1, Versions);
|
||||||
{error, bad_realm} -> {error, "Bad realm name.", 22};
|
{error, bad_realm} -> {error, "Bad realm name.", 22};
|
||||||
@ -600,12 +768,51 @@ latest(PackageString) ->
|
|||||||
|
|
||||||
latest2(PackageID) ->
|
latest2(PackageID) ->
|
||||||
{ok, ID} = zx_daemon:latest(PackageID),
|
{ok, ID} = zx_daemon:latest(PackageID),
|
||||||
case wait_result(ID) of
|
case zx_daemon:wait_result(ID) of
|
||||||
{ok, Version} -> print_version(Version);
|
{ok, Version} -> print_version(Version);
|
||||||
Error -> Error
|
Error -> Error
|
||||||
end.
|
end.
|
||||||
|
|
||||||
|
|
||||||
|
-spec describe(PackageString :: string()) -> zx:outcome().
|
||||||
|
|
||||||
|
describe(PackageString) ->
|
||||||
|
case zx_lib:package_id(PackageString) of
|
||||||
|
{ok, {Realm, Name, _}} -> describe2({Realm, Name});
|
||||||
|
{error, invalid_package_string} -> {error, "Invalid package name.", 22}
|
||||||
|
end.
|
||||||
|
|
||||||
|
describe2(Package) ->
|
||||||
|
{ok, ID} = zx_daemon:describe(Package),
|
||||||
|
case zx_daemon:wait_result(ID) of
|
||||||
|
{ok, Description} -> describe3(Description);
|
||||||
|
{error, bad_realm} -> {error, "Unconfigured realm or bad realm name.", 22};
|
||||||
|
{error, timeout} -> {error, "Request timed out.", 62};
|
||||||
|
{error, network} -> {error, "Network problem connecting to realm.", 101}
|
||||||
|
end.
|
||||||
|
|
||||||
|
describe3({description,
|
||||||
|
PackageID, DName, Type, Desc, Author, AEmail, WebURL, RepoURL, Tags}) ->
|
||||||
|
{ok, PackageString} = zx_lib:package_string(PackageID),
|
||||||
|
AuthorString =
|
||||||
|
case {Author, AEmail} of
|
||||||
|
{"", ""} -> "";
|
||||||
|
_ -> copyright_holder(Author, AEmail)
|
||||||
|
end,
|
||||||
|
Format =
|
||||||
|
"~n"
|
||||||
|
"Package : ~ts~n"
|
||||||
|
"Name : ~ts~n"
|
||||||
|
"Type : ~tp~n"
|
||||||
|
"Desc : ~ts~n"
|
||||||
|
"Author : ~ts~n"
|
||||||
|
"Web : ~ts~n"
|
||||||
|
"Repo : ~ts~n"
|
||||||
|
"Tags : ~tp~n",
|
||||||
|
io:format(Format,
|
||||||
|
[PackageString, DName, Type, Desc, AuthorString, WebURL, RepoURL, Tags]).
|
||||||
|
|
||||||
|
|
||||||
-spec provides(Module :: string()) -> zx:outcome().
|
-spec provides(Module :: string()) -> zx:outcome().
|
||||||
|
|
||||||
provides(Module) ->
|
provides(Module) ->
|
||||||
@ -616,7 +823,7 @@ provides(Module) ->
|
|||||||
ID
|
ID
|
||||||
end,
|
end,
|
||||||
IDs = [MakeRequest(R) || R <- Realms],
|
IDs = [MakeRequest(R) || R <- Realms],
|
||||||
case wait_results(IDs) of
|
case zx_daemon:wait_results(IDs) of
|
||||||
{ok, Results} ->
|
{ok, Results} ->
|
||||||
Packages = lists:append([R || {_, {ok, R}} <- Results]),
|
Packages = lists:append([R || {_, {ok, R}} <- Results]),
|
||||||
lists:foreach(fun print_packages/1, Packages);
|
lists:foreach(fun print_packages/1, Packages);
|
||||||
@ -632,10 +839,10 @@ print_packages(PackageID) ->
|
|||||||
-spec list_keys() -> zx:outcome().
|
-spec list_keys() -> zx:outcome().
|
||||||
|
|
||||||
list_keys() ->
|
list_keys() ->
|
||||||
Realm = select_realm(),
|
{ok, Realm} = pick_realm(),
|
||||||
UserName = select_user(Realm),
|
UserName = select_user(Realm),
|
||||||
{ok, ID} = zx_daemon:list_keys({Realm, UserName}),
|
{ok, ID} = zx_daemon:list_keys({Realm, UserName}),
|
||||||
case wait_result(ID) of
|
case zx_daemon:wait_result(ID) of
|
||||||
{ok, RemoteKeys} ->
|
{ok, RemoteKeys} ->
|
||||||
Print = fun(KN) -> io:format("~ts~n", [KN]) end,
|
Print = fun(KN) -> io:format("~ts~n", [KN]) end,
|
||||||
lists:foreach(Print, RemoteKeys);
|
lists:foreach(Print, RemoteKeys);
|
||||||
@ -648,7 +855,7 @@ list_keys() ->
|
|||||||
|
|
||||||
list_sysops(Realm) ->
|
list_sysops(Realm) ->
|
||||||
{ok, ID} = zx_daemon:list_sysops(Realm),
|
{ok, ID} = zx_daemon:list_sysops(Realm),
|
||||||
case wait_result(ID) of
|
case zx_daemon:wait_result(ID) of
|
||||||
{ok, Sysops} -> lists:foreach(fun zx_lib:print_user/1, Sysops);
|
{ok, Sysops} -> lists:foreach(fun zx_lib:print_user/1, Sysops);
|
||||||
Error -> Error
|
Error -> Error
|
||||||
end.
|
end.
|
||||||
@ -790,7 +997,7 @@ list_deps(PackageString) ->
|
|||||||
|
|
||||||
list_deps2(PackageID) ->
|
list_deps2(PackageID) ->
|
||||||
{ok, ID} = zx_daemon:list_deps(PackageID),
|
{ok, ID} = zx_daemon:list_deps(PackageID),
|
||||||
case wait_result(ID) of
|
case zx_daemon:wait_result(ID) of
|
||||||
{ok, Deps} -> lists:foreach(fun print_package_id/1, Deps);
|
{ok, Deps} -> lists:foreach(fun print_package_id/1, Deps);
|
||||||
Error -> Error
|
Error -> Error
|
||||||
end.
|
end.
|
||||||
@ -1515,7 +1722,7 @@ ask_module() ->
|
|||||||
|
|
||||||
package_exists({Realm, Package, _}) ->
|
package_exists({Realm, Package, _}) ->
|
||||||
{ok, ID} = zx_daemon:list(Realm),
|
{ok, ID} = zx_daemon:list(Realm),
|
||||||
case wait_result(ID) of
|
case zx_daemon:wait_result(ID) of
|
||||||
{ok, Packages} -> lists:member(Package, Packages);
|
{ok, Packages} -> lists:member(Package, Packages);
|
||||||
_ -> maybe
|
_ -> maybe
|
||||||
end.
|
end.
|
||||||
@ -1526,8 +1733,8 @@ package_exists({Realm, Package, _}) ->
|
|||||||
%% Execute the key generation procedure for 16k RSA keys once and then terminate.
|
%% Execute the key generation procedure for 16k RSA keys once and then terminate.
|
||||||
|
|
||||||
grow_a_pair() ->
|
grow_a_pair() ->
|
||||||
case select_realm() of
|
case pick_realm() of
|
||||||
error -> {error, "No realms configured.", 61};
|
{error, no_realms} -> {error, "No realms configured.", 61};
|
||||||
Realm -> grow_a_pair(Realm)
|
Realm -> grow_a_pair(Realm)
|
||||||
end.
|
end.
|
||||||
|
|
||||||
@ -1756,7 +1963,7 @@ prompt_port_number(Current) ->
|
|||||||
|
|
||||||
ask_url(realm) ->
|
ask_url(realm) ->
|
||||||
Message =
|
Message =
|
||||||
"~nURL~n"
|
"~nREALM COMMUNITY URL~n"
|
||||||
"Most public realms have a website, IRC channel, or similar location where its "
|
"Most public realms have a website, IRC channel, or similar location where its "
|
||||||
"community (or customers) communicate. If you have such a URL enter it here.~n"
|
"community (or customers) communicate. If you have such a URL enter it here.~n"
|
||||||
"NOTE: No checking is performed on the input here. Confuse your users at "
|
"NOTE: No checking is performed on the input here. Confuse your users at "
|
||||||
@ -1765,7 +1972,7 @@ ask_url(realm) ->
|
|||||||
zx_tty:get_input(Message);
|
zx_tty:get_input(Message);
|
||||||
ask_url(repo) ->
|
ask_url(repo) ->
|
||||||
Message =
|
Message =
|
||||||
"~nURL~n"
|
"~nPROJECT REPO URL~n"
|
||||||
"Most projects have a hosted repo URL (gitlab, github, SF, self hosted, etc).~n"
|
"Most projects have a hosted repo URL (gitlab, github, SF, self hosted, etc).~n"
|
||||||
"If you have such a URL enter it here.~n"
|
"If you have such a URL enter it here.~n"
|
||||||
"NOTE: No checking is performed on the input here. Confuse your users at "
|
"NOTE: No checking is performed on the input here. Confuse your users at "
|
||||||
@ -1774,7 +1981,7 @@ ask_url(repo) ->
|
|||||||
zx_tty:get_input(Message);
|
zx_tty:get_input(Message);
|
||||||
ask_url(website) ->
|
ask_url(website) ->
|
||||||
Message =
|
Message =
|
||||||
"~nURL~n"
|
"~nPROJECT WEBSITE URL~n"
|
||||||
"Many project, particularly GUI applications, have a public website where "
|
"Many project, particularly GUI applications, have a public website where "
|
||||||
"documentation, user forums, etc. are hosted.~n"
|
"documentation, user forums, etc. are hosted.~n"
|
||||||
"If you have such a URL enter it here.~n"
|
"If you have such a URL enter it here.~n"
|
||||||
@ -1898,8 +2105,8 @@ store_user(#user_data{realm = Realm,
|
|||||||
-spec create_userfile() -> ok.
|
-spec create_userfile() -> ok.
|
||||||
|
|
||||||
create_userfile() ->
|
create_userfile() ->
|
||||||
case select_realm() of
|
case pick_realm() of
|
||||||
error -> {error, "No realms configured.", 61};
|
{error, no_realms} -> {error, "No realms configured.", 61};
|
||||||
Realm -> create_userfile(Realm)
|
Realm -> create_userfile(Realm)
|
||||||
end.
|
end.
|
||||||
|
|
||||||
@ -1937,8 +2144,8 @@ create_userfile(Realm, UserName) ->
|
|||||||
-spec export_user() -> ok.
|
-spec export_user() -> ok.
|
||||||
|
|
||||||
export_user() ->
|
export_user() ->
|
||||||
case select_realm() of
|
case pick_realm() of
|
||||||
error -> {error, "No realms configured.", 61};
|
{error, no_realms} -> {error, "No realms configured.", 61};
|
||||||
Realm -> export_user(Realm)
|
Realm -> export_user(Realm)
|
||||||
end.
|
end.
|
||||||
|
|
||||||
@ -2040,10 +2247,12 @@ pick_realm() ->
|
|||||||
[] ->
|
[] ->
|
||||||
ok = tell(warning, "No realms configured! Exiting..."),
|
ok = tell(warning, "No realms configured! Exiting..."),
|
||||||
{error, no_realms};
|
{error, no_realms};
|
||||||
|
[Realm] ->
|
||||||
|
ok = tell("Realm ~ts selected.", [Realm]),
|
||||||
|
{ok, Realm};
|
||||||
Realms ->
|
Realms ->
|
||||||
ok = io:format("Select a realm:~n"),
|
ok = io:format("Select a realm:~n"),
|
||||||
Options = lists:zip(Realms, Realms),
|
Realm = zx_tty:select_string(Realms),
|
||||||
Realm = zx_tty:select(Options),
|
|
||||||
{ok, Realm}
|
{ok, Realm}
|
||||||
end.
|
end.
|
||||||
|
|
||||||
@ -2233,6 +2442,61 @@ ask_description() ->
|
|||||||
unicode:characters_to_list(String, utf8).
|
unicode:characters_to_list(String, utf8).
|
||||||
|
|
||||||
|
|
||||||
|
-spec edit_tags(Set) -> NewSet
|
||||||
|
when Set :: sets:set(string()),
|
||||||
|
NewSet :: sets:set(string()).
|
||||||
|
|
||||||
|
edit_tags(Set) ->
|
||||||
|
ok = io:format("CURRENT TAGS:~n~tp~n", [sets:to_list(Set)]),
|
||||||
|
Options =
|
||||||
|
[{"Add a tag", 1},
|
||||||
|
{"Remove a tag", 2},
|
||||||
|
{"Return", 3}],
|
||||||
|
case zx_tty:select(Options) of
|
||||||
|
1 ->
|
||||||
|
New = string:lowercase(zx_tty:get_input("~nEnter a new tag~n")),
|
||||||
|
edit_tags(sets:add_element(New, Set));
|
||||||
|
2 ->
|
||||||
|
edit_tags(rem_item(Set));
|
||||||
|
3 ->
|
||||||
|
Set
|
||||||
|
end.
|
||||||
|
|
||||||
|
|
||||||
|
-spec edit_exts(Set) -> NewSet
|
||||||
|
when Set :: sets:set(string()),
|
||||||
|
NewSet :: sets:set(string()).
|
||||||
|
|
||||||
|
edit_exts(Set) ->
|
||||||
|
ok = io:format("CURRENT ASSOCIATED FILE EXTENSIONS:~n~tp~n", [sets:to_list(Set)]),
|
||||||
|
Options =
|
||||||
|
[{"Add a tag", 1},
|
||||||
|
{"Remove a tag", 2},
|
||||||
|
{"Return", 3}],
|
||||||
|
case zx_tty:select(Options) of
|
||||||
|
1 ->
|
||||||
|
New = dotify(string:lowercase(zx_tty:get_input("~nEnter a new tag~n"))),
|
||||||
|
edit_tags(sets:add_element(New, Set));
|
||||||
|
2 ->
|
||||||
|
edit_tags(rem_item(Set));
|
||||||
|
3 ->
|
||||||
|
Set
|
||||||
|
end.
|
||||||
|
|
||||||
|
dotify(S) ->
|
||||||
|
Chars = lists:seq($a, $z) ++ lists:seq($0, $9),
|
||||||
|
{_, T} = string:take(S, Chars, true),
|
||||||
|
{H, _} = string:take(T, Chars, false),
|
||||||
|
[$. | H].
|
||||||
|
|
||||||
|
|
||||||
|
rem_item(Set) ->
|
||||||
|
ok = io:format("~nSelect an item to drop.~n"),
|
||||||
|
Picked = zx_tty:select_string(sets:to_list(Set)),
|
||||||
|
sets:del_element(Picked, Set).
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
-spec realm_exists(zx:realm()) -> boolean().
|
-spec realm_exists(zx:realm()) -> boolean().
|
||||||
%% @private
|
%% @private
|
||||||
%% Checks for remnants of a realm.
|
%% Checks for remnants of a realm.
|
||||||
@ -2260,7 +2524,7 @@ make_realm_dirs(Realm) ->
|
|||||||
-spec create_realmfile() -> ok.
|
-spec create_realmfile() -> ok.
|
||||||
|
|
||||||
create_realmfile() ->
|
create_realmfile() ->
|
||||||
Realm = select_realm(),
|
{ok, Realm} = pick_realm(),
|
||||||
create_realmfile(Realm).
|
create_realmfile(Realm).
|
||||||
|
|
||||||
|
|
||||||
@ -2329,7 +2593,7 @@ logpath(_, Ago) when Ago < 1 ->
|
|||||||
set_timeout(String) ->
|
set_timeout(String) ->
|
||||||
case string:to_integer(String) of
|
case string:to_integer(String) of
|
||||||
{Value, ""} when Value > 0 ->
|
{Value, ""} when Value > 0 ->
|
||||||
zx_sys_conf:save(zx_sys_conf:timeout(Value, zx_sys_conf:load()));
|
zx_daemon:conf(timeout, Value);
|
||||||
_ ->
|
_ ->
|
||||||
{error, "Enter a positive integer. Common values are 3, 5 and 10.", 22}
|
{error, "Enter a positive integer. Common values are 3, 5 and 10.", 22}
|
||||||
end.
|
end.
|
||||||
@ -2357,6 +2621,33 @@ add_mirror() ->
|
|||||||
zx_daemon:add_mirror({Host, Port}).
|
zx_daemon:add_mirror({Host, Port}).
|
||||||
|
|
||||||
|
|
||||||
|
-spec add_mirror(Address) -> zx:outcome()
|
||||||
|
when Address :: string().
|
||||||
|
|
||||||
|
add_mirror(Address) ->
|
||||||
|
add_mirror(Address, "11311").
|
||||||
|
|
||||||
|
|
||||||
|
-spec add_mirror(Address, PortString) -> zx:outcome()
|
||||||
|
when Address :: string(),
|
||||||
|
PortString :: string().
|
||||||
|
|
||||||
|
add_mirror(Address, PortString) ->
|
||||||
|
Host = parse_maybe_address(Address),
|
||||||
|
try
|
||||||
|
case list_to_integer(PortString) of
|
||||||
|
Port when 16#ffff >= Port, Port > 0 ->
|
||||||
|
zx_daemon:add_mirror({Host, Port});
|
||||||
|
Illegal ->
|
||||||
|
F = "Provided port number ~w is out of bound (1~65535).",
|
||||||
|
Message = io_lib:format(F, [Illegal]),
|
||||||
|
{error, Message}
|
||||||
|
end
|
||||||
|
catch error:badarg ->
|
||||||
|
{error, "Provided port value is not a port number."}
|
||||||
|
end.
|
||||||
|
|
||||||
|
|
||||||
-spec drop_mirror() -> ok.
|
-spec drop_mirror() -> ok.
|
||||||
|
|
||||||
drop_mirror() ->
|
drop_mirror() ->
|
||||||
@ -2375,13 +2666,30 @@ drop_mirror() ->
|
|||||||
end.
|
end.
|
||||||
|
|
||||||
|
|
||||||
-spec select_realm() -> {ok, zx:realm()} | error.
|
-spec drop_mirror(Address) -> zx:outcome()
|
||||||
|
when Address :: string().
|
||||||
|
|
||||||
select_realm() ->
|
drop_mirror(Address) ->
|
||||||
case zx_lib:list_realms() of
|
drop_mirror(Address, "11311").
|
||||||
[] -> error;
|
|
||||||
[Realm] -> Realm;
|
|
||||||
Realms -> zx_tty:select_string(Realms)
|
-spec drop_mirror(Address, PortString) -> zx:outcome()
|
||||||
|
when Address :: string(),
|
||||||
|
PortString :: string().
|
||||||
|
|
||||||
|
drop_mirror(Address, PortString) ->
|
||||||
|
Host = parse_maybe_address(Address),
|
||||||
|
try
|
||||||
|
case list_to_integer(PortString) of
|
||||||
|
Port when 16#ffff >= Port, Port > 0 ->
|
||||||
|
zx_daemon:drop_mirror({Host, Port});
|
||||||
|
Illegal ->
|
||||||
|
F = "Provided port number ~w is out of bound (1~65535).",
|
||||||
|
Message = io_lib:format(F, [Illegal]),
|
||||||
|
{error, Message}
|
||||||
|
end
|
||||||
|
catch error:badarg ->
|
||||||
|
{error, "Provided port value is not a port number."}
|
||||||
end.
|
end.
|
||||||
|
|
||||||
|
|
||||||
@ -2424,33 +2732,3 @@ select_private_key2(Realm, [KeyName | Rest]) ->
|
|||||||
end;
|
end;
|
||||||
select_private_key2(_, []) ->
|
select_private_key2(_, []) ->
|
||||||
error.
|
error.
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
%%% Utility Functions
|
|
||||||
|
|
||||||
wait_result(ID) ->
|
|
||||||
receive
|
|
||||||
{result, ID, Result} -> Result;
|
|
||||||
Message -> {error, {unexpected, Message}}
|
|
||||||
after 5000 -> {error, timeout}
|
|
||||||
end.
|
|
||||||
|
|
||||||
|
|
||||||
wait_results(IDs) ->
|
|
||||||
wait_results(IDs, []).
|
|
||||||
|
|
||||||
wait_results([], Results) ->
|
|
||||||
{ok, Results};
|
|
||||||
wait_results(IDs, Results) ->
|
|
||||||
receive
|
|
||||||
{result, ID, Result} ->
|
|
||||||
case lists:member(ID, IDs) of
|
|
||||||
true -> wait_results(lists:delete(ID, IDs), [{ID, Result} | Results]);
|
|
||||||
false -> {error, {unexpected, {result, ID, Result}}, Results}
|
|
||||||
end;
|
|
||||||
Message ->
|
|
||||||
{error, {unexpected, Message}}
|
|
||||||
after 5000 ->
|
|
||||||
{error, timeout}
|
|
||||||
end.
|
|
||||||
@ -5,7 +5,7 @@
|
|||||||
%%% @end
|
%%% @end
|
||||||
|
|
||||||
-module(zx_net).
|
-module(zx_net).
|
||||||
-vsn("0.2.0").
|
-vsn("0.2.1").
|
||||||
-author("Craig Everett <zxq9@zxq9.com>").
|
-author("Craig Everett <zxq9@zxq9.com>").
|
||||||
-copyright("Craig Everett <zxq9@zxq9.com>").
|
-copyright("Craig Everett <zxq9@zxq9.com>").
|
||||||
-license("GPL-3.0").
|
-license("GPL-3.0").
|
||||||
@ -8,7 +8,7 @@
|
|||||||
%%% @end
|
%%% @end
|
||||||
|
|
||||||
-module(zx_peer).
|
-module(zx_peer).
|
||||||
-vsn("0.2.0").
|
-vsn("0.2.1").
|
||||||
-author("Craig Everett <zxq9@zxq9.com>").
|
-author("Craig Everett <zxq9@zxq9.com>").
|
||||||
-copyright("Craig Everett <zxq9@zxq9.com>").
|
-copyright("Craig Everett <zxq9@zxq9.com>").
|
||||||
-license("GPL-3.0").
|
-license("GPL-3.0").
|
||||||
@ -9,7 +9,7 @@
|
|||||||
%%% @end
|
%%% @end
|
||||||
|
|
||||||
-module(zx_peer_man).
|
-module(zx_peer_man).
|
||||||
-vsn("0.2.0").
|
-vsn("0.2.1").
|
||||||
-behavior(gen_server).
|
-behavior(gen_server).
|
||||||
-author("Craig Everett <zxq9@zxq9.com>").
|
-author("Craig Everett <zxq9@zxq9.com>").
|
||||||
-copyright("Craig Everett <zxq9@zxq9.com>").
|
-copyright("Craig Everett <zxq9@zxq9.com>").
|
||||||
@ -6,7 +6,7 @@
|
|||||||
%%% @end
|
%%% @end
|
||||||
|
|
||||||
-module(zx_peer_sup).
|
-module(zx_peer_sup).
|
||||||
-vsn("0.2.0").
|
-vsn("0.2.1").
|
||||||
-behaviour(supervisor).
|
-behaviour(supervisor).
|
||||||
-author("Craig Everett <zxq9@zxq9.com>").
|
-author("Craig Everett <zxq9@zxq9.com>").
|
||||||
-copyright("Craig Everett <zxq9@zxq9.com>").
|
-copyright("Craig Everett <zxq9@zxq9.com>").
|
||||||
@ -10,7 +10,7 @@
|
|||||||
%%% @end
|
%%% @end
|
||||||
|
|
||||||
-module(zx_peers).
|
-module(zx_peers).
|
||||||
-vsn("0.2.0").
|
-vsn("0.2.1").
|
||||||
-behavior(supervisor).
|
-behavior(supervisor).
|
||||||
-author("Craig Everett <zxq9@zxq9.com>").
|
-author("Craig Everett <zxq9@zxq9.com>").
|
||||||
-copyright("Craig Everett <zxq9@zxq9.com>").
|
-copyright("Craig Everett <zxq9@zxq9.com>").
|
||||||
@ -5,7 +5,7 @@
|
|||||||
%%% @end
|
%%% @end
|
||||||
|
|
||||||
-module(zx_proxy).
|
-module(zx_proxy).
|
||||||
-vsn("0.2.0").
|
-vsn("0.2.1").
|
||||||
-author("Craig Everett <zxq9@zxq9.com>").
|
-author("Craig Everett <zxq9@zxq9.com>").
|
||||||
-copyright("Craig Everett <zxq9@zxq9.com>").
|
-copyright("Craig Everett <zxq9@zxq9.com>").
|
||||||
-license("GPL-3.0").
|
-license("GPL-3.0").
|
||||||
@ -5,7 +5,7 @@
|
|||||||
%%% @end
|
%%% @end
|
||||||
|
|
||||||
-module(zx_sup).
|
-module(zx_sup).
|
||||||
-vsn("0.2.0").
|
-vsn("0.2.1").
|
||||||
-behavior(supervisor).
|
-behavior(supervisor).
|
||||||
-author("Craig Everett <zxq9@zxq9.com>").
|
-author("Craig Everett <zxq9@zxq9.com>").
|
||||||
-copyright("Craig Everett <zxq9@zxq9.com>").
|
-copyright("Craig Everett <zxq9@zxq9.com>").
|
||||||
@ -1,12 +1,12 @@
|
|||||||
%%% @doc
|
%%% @doc
|
||||||
%%% ZX TTY
|
%%% ZX TTY
|
||||||
%%%
|
%%%
|
||||||
%%% This module lets other parts of ZX interact (very clumsily) with the user via a text
|
%%% This module lets other parts of ZX interact (clumsily) with the user via a text
|
||||||
%%% interface. Hopefully this will never be called on Windows.
|
%%% interface. Hopefully this will never be called on Windows.
|
||||||
%%% @end
|
%%% @end
|
||||||
|
|
||||||
-module(zx_tty).
|
-module(zx_tty).
|
||||||
-vsn("0.2.0").
|
-vsn("0.2.1").
|
||||||
-author("Craig Everett <zxq9@zxq9.com>").
|
-author("Craig Everett <zxq9@zxq9.com>").
|
||||||
-copyright("Craig Everett <zxq9@zxq9.com>").
|
-copyright("Craig Everett <zxq9@zxq9.com>").
|
||||||
-license("GPL-3.0").
|
-license("GPL-3.0").
|
||||||
@ -7,7 +7,7 @@
|
|||||||
%%% @end
|
%%% @end
|
||||||
|
|
||||||
-module(zx_zsp).
|
-module(zx_zsp).
|
||||||
-vsn("0.2.0").
|
-vsn("0.2.1").
|
||||||
-author("Craig Everett <zxq9@zxq9.com>").
|
-author("Craig Everett <zxq9@zxq9.com>").
|
||||||
-copyright("Craig Everett <zxq9@zxq9.com>").
|
-copyright("Craig Everett <zxq9@zxq9.com>").
|
||||||
-license("GPL-3.0").
|
-license("GPL-3.0").
|
||||||
@ -26,6 +26,12 @@
|
|||||||
|
|
||||||
-type meta() :: {PackageID :: zx:package_id(),
|
-type meta() :: {PackageID :: zx:package_id(),
|
||||||
KeyName :: zx:key_name(),
|
KeyName :: zx:key_name(),
|
||||||
|
DisplayName :: string(),
|
||||||
|
Desc :: string(),
|
||||||
|
Author :: string(),
|
||||||
|
AEmail :: string(),
|
||||||
|
WebURL :: string(),
|
||||||
|
RepoURL :: string(),
|
||||||
Tags :: [string()],
|
Tags :: [string()],
|
||||||
Deps :: [zx:package_id()],
|
Deps :: [zx:package_id()],
|
||||||
Modules :: [string()]}.
|
Modules :: [string()]}.
|
||||||
@ -71,9 +77,20 @@ pack3(TargetDir, PackageID, Meta, {KeyName, Key}, ZspFile) ->
|
|||||||
ok = erl_tar:create(TarGzPath, Targets, [compressed]),
|
ok = erl_tar:create(TarGzPath, Targets, [compressed]),
|
||||||
{ok, TgzBin} = file:read_file(TarGzPath),
|
{ok, TgzBin} = file:read_file(TarGzPath),
|
||||||
ok = file:delete(TarGzPath),
|
ok = file:delete(TarGzPath),
|
||||||
Tags = maps:get(tags, Meta, []),
|
MetaData =
|
||||||
Deps = maps:get(deps, Meta, []),
|
{PackageID,
|
||||||
MetaBin = term_to_binary({PackageID, KeyName, Tags, Deps, Modules}),
|
KeyName,
|
||||||
|
maps:get(name, Meta, Name),
|
||||||
|
maps:get(type, Meta),
|
||||||
|
maps:get(desc, Meta, ""),
|
||||||
|
maps:get(author, Meta, ""),
|
||||||
|
maps:get(a_email, Meta, ""),
|
||||||
|
maps:get(ws_url, Meta, ""),
|
||||||
|
maps:get(repo_url, Meta, ""),
|
||||||
|
maps:get(tags, Meta, []),
|
||||||
|
maps:get(deps, Meta, []),
|
||||||
|
Modules},
|
||||||
|
MetaBin = term_to_binary(MetaData),
|
||||||
MetaSize = byte_size(MetaBin),
|
MetaSize = byte_size(MetaBin),
|
||||||
SignMe = <<MetaSize:24, MetaBin:MetaSize/binary, TgzBin/binary>>,
|
SignMe = <<MetaSize:24, MetaBin:MetaSize/binary, TgzBin/binary>>,
|
||||||
Sig = public_key:sign(SignMe, sha512, Key),
|
Sig = public_key:sign(SignMe, sha512, Key),
|
||||||
@ -1,5 +1,5 @@
|
|||||||
{deps,[]}.
|
{deps,[]}.
|
||||||
{package_id,{"otpr","zx",{0,2,0}}}.
|
{package_id,{"otpr","zx",{0,2,1}}}.
|
||||||
{prefix,"zx_"}.
|
{prefix,"zx_"}.
|
||||||
{tags,[]}.
|
{tags,[]}.
|
||||||
{type,app}.
|
{type,app}.
|
||||||
Loading…
x
Reference in New Issue
Block a user