changed
CHANGELOG.md
|
@@ -7,9 +7,24 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
|
7
7
|
|
8
8
|
## [Unreleased]
|
9
9
|
|
10
|
+ ## [0.1.1] - 2021-09-24
|
11
|
+
|
12
|
+ ### Fixed
|
13
|
+
|
14
|
+ - Validate short and long names properly. This also add better defaults depending
|
15
|
+ on which type of nodes PLDS is connecting to.
|
16
|
+
|
17
|
+ ### Changed
|
18
|
+
|
19
|
+ - The `--cookie` flag is now optional. By default it will use the one from
|
20
|
+ `Node.get_cookie()` when distribution is enabled.
|
21
|
+
|
22
|
+ ## [0.1.0] - 2021-09-22
|
23
|
+
|
10
24
|
### Added
|
11
25
|
|
12
26
|
- Initial release of PLDS.
|
13
27
|
|
14
|
- [Unreleased]: https://github.com/phoenixframework/plds/compare/v0.1.0...HEAD
|
28
|
+ [Unreleased]: https://github.com/phoenixframework/plds/compare/v0.1.1...HEAD
|
29
|
+ [0.1.1]: https://github.com/phoenixframework/plds/compare/v0.1.0...v0.1.1
|
15
30
|
[0.1.0]: https://github.com/phoenixframework/plds/releases/tag/v0.1.0
|
changed
README.md
|
@@ -1,5 +1,7 @@
|
1
1
|
# PLDS - Phoenix LiveDashboard Standalone
|
2
2
|
|
3
|
+ [](https://github.com/phoenixframework/plds/actions/workflows/ci.yml)
|
4
|
+
|
3
5
|
<!-- MDOC !-->
|
4
6
|
|
5
7
|
PLDS is a command line interface for [Phoenix LiveDashboard](https://github.com/phoenixframework/phoenix_live_dashboard)
|
|
@@ -47,6 +49,12 @@ The only one available today is:
|
47
49
|
- Ecto with extras - works for PostgreSQL databases.
|
48
50
|
- Broadway Dashboard - to inspect Broadway pipelines.
|
49
51
|
|
52
|
+ ## Disabled pages
|
53
|
+
|
54
|
+ Note that some pages will be disabled when using PLDS. "Metrics" page is disabled
|
55
|
+ because we can't tell which module is responsible for the data upfront.
|
56
|
+ "OS Data" page is enabled only if the node has the `os_mon` application running.
|
57
|
+
|
50
58
|
<!-- MDOC !-->
|
51
59
|
|
52
60
|
## Development
|
changed
hex_metadata.config
|
@@ -50,4 +50,4 @@
|
50
50
|
{<<"optional">>,false},
|
51
51
|
{<<"repository">>,<<"hexpm">>},
|
52
52
|
{<<"requirement">>,<<"~> 2.5">>}]]}.
|
53
|
- {<<"version">>,<<"0.1.0">>}.
|
53
|
+ {<<"version">>,<<"0.1.1">>}.
|
changed
lib/plds/application.ex
|
@@ -10,6 +10,7 @@ defmodule PLDS.Application do
|
10
10
|
@impl true
|
11
11
|
def start(_type, _args) do
|
12
12
|
ensure_distribution!()
|
13
|
+ validate_hostname_resolution!()
|
13
14
|
connect_to_nodes!()
|
14
15
|
|
15
16
|
children = [
|
|
@@ -26,17 +27,37 @@ defmodule PLDS.Application do
|
26
27
|
defp ensure_distribution! do
|
27
28
|
PLDS.Distribution.ensure_distribution!()
|
28
29
|
|
29
|
- cookie = Application.fetch_env!(:plds, :cookie)
|
30
|
- Node.set_cookie(cookie)
|
30
|
+ if cookie = Application.get_env(:plds, :cookie) do
|
31
|
+ Node.set_cookie(cookie)
|
32
|
+ end
|
31
33
|
end
|
32
34
|
else
|
33
35
|
defp ensure_distribution!, do: :noop
|
34
36
|
end
|
35
37
|
|
36
38
|
defp connect_to_nodes! do
|
37
|
- nodes = Application.get_env(:plds, :nodes_to_connect, [])
|
39
|
+ PLDS.Distribution.connect_to_nodes!()
|
40
|
+ end
|
38
41
|
|
39
|
- PLDS.Distribution.connect_to_nodes!(nodes)
|
42
|
+ # See https://github.com/livebook-dev/livebook/pull/303
|
43
|
+ defp validate_hostname_resolution!() do
|
44
|
+ unless PLDS.Utils.long_name?() do
|
45
|
+ hostname = PLDS.Utils.node_host() |> to_charlist()
|
46
|
+
|
47
|
+ if hostname != 'nohost' and :inet.gethostbyname(hostname) == {:error, :nxdomain} do
|
48
|
+ PLDS.Utils.abort!("""
|
49
|
+ your hostname "#{hostname}" does not resolve to any IP address, which indicates something wrong in your OS configuration.
|
50
|
+
|
51
|
+ Make sure your computer's name resolves locally or start PLDS using a long distribution name:
|
52
|
+
|
53
|
+ plds server --name [email protected]
|
54
|
+
|
55
|
+ If you are running it from source, do instead:
|
56
|
+
|
57
|
+ MIX_ENV=prod elixir --name [email protected] -S mix phx.server
|
58
|
+ """)
|
59
|
+ end
|
60
|
+ end
|
40
61
|
end
|
41
62
|
|
42
63
|
@impl true
|
changed
lib/plds/distribution.ex
|
@@ -41,21 +41,41 @@ defmodule PLDS.Distribution do
|
41
41
|
end
|
42
42
|
|
43
43
|
defp get_node_type_and_name do
|
44
|
- Application.get_env(:plds, :node) || {:shortnames, :plds}
|
44
|
+ Application.get_env(:plds, :node) || default_node_type_and_name()
|
45
|
+ end
|
46
|
+
|
47
|
+ # Choose for a short or long name based on connections.
|
48
|
+ def default_node_type_and_name do
|
49
|
+ if Enum.any?(nodes_to_connect(), &PLDS.Utils.long_name?(Atom.to_string(&1))) do
|
50
|
+ name = :"[email protected]"
|
51
|
+
|
52
|
+ print_warning(
|
53
|
+ "using long names because one of the nodes is long. Current name is #{inspect(name)}"
|
54
|
+ )
|
55
|
+
|
56
|
+ {:longnames, name}
|
57
|
+ else
|
58
|
+ {:shortnames, :plds}
|
59
|
+ end
|
60
|
+ end
|
61
|
+
|
62
|
+ defp print_warning(message) do
|
63
|
+ IO.puts(:stderr, IO.ANSI.format([:yellow, "[PLDS] " <> message]))
|
64
|
+ end
|
65
|
+
|
66
|
+ defp nodes_to_connect do
|
67
|
+ Application.get_env(:plds, :nodes_to_connect, [])
|
45
68
|
end
|
46
69
|
|
47
70
|
# Nodes can have long or short names.
|
48
|
- def connect_to_nodes!(nodes) do
|
49
|
- [_, host] =
|
50
|
- node()
|
51
|
- |> Atom.to_string()
|
52
|
- |> String.split("@")
|
71
|
+ def connect_to_nodes!(nodes \\ nodes_to_connect()) do
|
72
|
+ host = PLDS.Utils.node_host()
|
53
73
|
|
54
74
|
# We get the current node host as host for when connect
|
55
75
|
# only have shortnames
|
56
76
|
for name <- nodes do
|
57
77
|
name =
|
58
|
- if long_name?(name) do
|
78
|
+ if with_host?(name) do
|
59
79
|
name
|
60
80
|
else
|
61
81
|
:"#{name}@#{host}"
|
|
@@ -67,7 +87,7 @@ defmodule PLDS.Distribution do
|
67
87
|
:ok
|
68
88
|
end
|
69
89
|
|
70
|
- defp long_name?(name) do
|
90
|
+ defp with_host?(name) do
|
71
91
|
name
|
72
92
|
|> Atom.to_string()
|
73
93
|
|> String.contains?("@")
|
changed
lib/plds/utils.ex
|
@@ -40,4 +40,35 @@ defmodule PLDS.Utils do
|
40
40
|
raise "\nERROR!!! [PLDS] " <> message
|
41
41
|
end
|
42
42
|
end
|
43
|
+
|
44
|
+ @doc """
|
45
|
+ Check if this app is running with long name.
|
46
|
+ """
|
47
|
+ def long_name? do
|
48
|
+ node_host() =~ "."
|
49
|
+ end
|
50
|
+
|
51
|
+ @doc """
|
52
|
+ Similar to long_name?/0, but check the given name.
|
53
|
+ """
|
54
|
+ def long_name?(name) do
|
55
|
+ name =~ "@" and name =~ "."
|
56
|
+ end
|
57
|
+
|
58
|
+ @doc """
|
59
|
+ Check if the given name is a short name with host.
|
60
|
+ """
|
61
|
+ def short_name_with_host?(name) do
|
62
|
+ String.contains?(name, "@") && not String.contains?(name, ".")
|
63
|
+ end
|
64
|
+
|
65
|
+ @doc """
|
66
|
+ Returns the host part of a node.
|
67
|
+ """
|
68
|
+ @spec node_host() :: binary()
|
69
|
+ def node_host do
|
70
|
+ [_, host] = node() |> Atom.to_string() |> :binary.split("@")
|
71
|
+
|
72
|
+ host
|
73
|
+ end
|
43
74
|
end
|
changed
lib/plds_cli/server.ex
|
@@ -13,8 +13,12 @@ defmodule PLDSCli.Server do
|
13
13
|
|
14
14
|
-c, --connect One or more node names to connect.
|
15
15
|
You can specify more nodes by using this option multiple times.
|
16
|
- It accepts both short and long names.
|
16
|
+ It accepts both short and long names. For short names you can
|
17
|
+ omit the host. If you pass a long name, then PLDS will start
|
18
|
+ with a long name with host "127.0.0.1". You cannot use short
|
19
|
+ and long names together.
|
17
20
|
--cookie Sets a cookie for the app distributed node.
|
21
|
+ This is optional and defaults to `Node.get_cookie()`.
|
18
22
|
--ip The ip address to start the web application on, defaults to 127.0.0.1
|
19
23
|
Must be a valid IPv4 or IPv6 address.
|
20
24
|
--name Set a name for the app distributed node.
|
|
@@ -121,16 +125,55 @@ defmodule PLDSCli.Server do
|
121
125
|
c: :connect
|
122
126
|
]
|
123
127
|
|
124
|
- defp args_to_options(args) do
|
128
|
+ # TODO: add tests to the name/sname and connect validations
|
129
|
+ @doc false
|
130
|
+ def args_to_options(args) do
|
125
131
|
{opts, _} = OptionParser.parse!(args, strict: @switches, aliases: @aliases)
|
126
132
|
validate_options!(opts)
|
127
133
|
opts
|
128
134
|
end
|
129
135
|
|
130
136
|
defp validate_options!(opts) do
|
131
|
- if Keyword.has_key?(opts, :name) and Keyword.has_key?(opts, :sname) do
|
132
|
- raise "the provided --sname and --name options are mutually exclusive, please specify only one of them"
|
137
|
+ if Keyword.has_key?(opts, :name) do
|
138
|
+ validate_opts_for_name!(opts)
|
133
139
|
end
|
140
|
+
|
141
|
+ if Keyword.has_key?(opts, :sname) do
|
142
|
+ validate_opts_for_short_name!(opts)
|
143
|
+ end
|
144
|
+ end
|
145
|
+
|
146
|
+ defp validate_opts_for_name!(opts) do
|
147
|
+ cond do
|
148
|
+ Keyword.has_key?(opts, :sname) ->
|
149
|
+ raise "the provided --sname and --name options are mutually exclusive, please specify only one of them"
|
150
|
+
|
151
|
+ connecting_to_short_names_with_hosts?(opts) ->
|
152
|
+ raise "the provided connections should have long names because you specified the --name option"
|
153
|
+
|
154
|
+ not PLDS.Utils.long_name?(opts[:name]) ->
|
155
|
+ raise "the provided --name option should include the full host name"
|
156
|
+
|
157
|
+ true ->
|
158
|
+ :ok
|
159
|
+ end
|
160
|
+ end
|
161
|
+
|
162
|
+ defp validate_opts_for_short_name!(opts) do
|
163
|
+ has_full_names? =
|
164
|
+ opts
|
165
|
+ |> Keyword.take([:connect])
|
166
|
+ |> Enum.any?(fn {:connect, name} -> PLDS.Utils.long_name?(name) end)
|
167
|
+
|
168
|
+ if has_full_names? do
|
169
|
+ raise "the provided connections should have short names because you specified the --sname option"
|
170
|
+ end
|
171
|
+ end
|
172
|
+
|
173
|
+ defp connecting_to_short_names_with_hosts?(opts) do
|
174
|
+ opts
|
175
|
+ |> Keyword.take([:connect])
|
176
|
+ |> Enum.any?(fn {:connect, name} -> PLDS.Utils.short_name_with_host?(name) end)
|
134
177
|
end
|
135
178
|
|
136
179
|
defp opts_to_config([], config), do: config
|
changed
mix.exs
|
@@ -1,7 +1,7 @@
|
1
1
|
defmodule PLDS.MixProject do
|
2
2
|
use Mix.Project
|
3
3
|
|
4
|
- @version "0.1.0"
|
4
|
+ @version "0.1.1"
|
5
5
|
@description "CLI version of Phoenix LiveDashboard"
|
6
6
|
|
7
7
|
def project do
|