diff --git a/lib/pleroma/config/config_db.ex b/lib/pleroma/config/config_db.ex index 6d48e0300..93b02370c 100644 --- a/lib/pleroma/config/config_db.ex +++ b/lib/pleroma/config/config_db.ex @@ -16,6 +16,7 @@ defmodule Pleroma.ConfigDB do field(:key, :string) field(:group, :string) field(:value, :binary) + field(:db, {:array, :string}, virtual: true, default: []) timestamps() end @@ -61,6 +62,22 @@ def update(%ConfigDB{} = config, %{value: value}) do |> Repo.update() end + @spec get_db_keys(ConfigDB.t()) :: [String.t()] + def get_db_keys(%ConfigDB{} = config) do + config.value + |> ConfigDB.from_binary() + |> get_db_keys(config.key) + end + + @spec get_db_keys(keyword() | any()) :: [String.t()] + def get_db_keys(value, key) do + if Keyword.keyword?(value) do + value |> Keyword.keys() |> Enum.map(&convert(&1)) + else + [convert(key)] + end + end + @full_key_update [ {:pleroma, :ecto_repos}, {:pleroma, :assets}, @@ -317,7 +334,7 @@ defp do_transform_string(value) do @spec is_module_name?(String.t()) :: boolean() def is_module_name?(string) do - Regex.match?(~r/^(Pleroma|Phoenix|Tesla|Quack)\./, string) or + Regex.match?(~r/^(Pleroma|Phoenix|Tesla|Quack|Ueberauth)\./, string) or string in ["Oban", "Ueberauth", "ExSyslogger"] end end diff --git a/lib/pleroma/config/holder.ex b/lib/pleroma/config/holder.ex index 0d9cfef66..7436df1a7 100644 --- a/lib/pleroma/config/holder.ex +++ b/lib/pleroma/config/holder.ex @@ -15,8 +15,8 @@ def load(path), do: Config.Reader.read!(path) # support for Elixir less than 1.9 @spec load() :: map() def load do - {config, _paths} = load("config/config.exs") - {env_config, _paths} = load("config/#{Mix.env()}.exs") + config = load("config/config.exs") + env_config = load("config/#{Mix.env()}.exs") Mix.Config.merge(config, env_config) end diff --git a/lib/pleroma/config/transfer_task.ex b/lib/pleroma/config/transfer_task.ex index 70b51cb4d..6e651c48b 100644 --- a/lib/pleroma/config/transfer_task.ex +++ b/lib/pleroma/config/transfer_task.ex @@ -66,7 +66,9 @@ defp update_env(setting) do rescue e -> Logger.warn( - "updating env causes error, key: #{inspect(setting.key)}, error: #{inspect(e)}" + "updating env causes error, group: #{inspect(setting.group)}, key: #{ + inspect(setting.key) + }, value: #{inspect(ConfigDB.from_binary(setting.value))}, error: #{inspect(e)}" ) nil diff --git a/lib/pleroma/web/admin_api/admin_api_controller.ex b/lib/pleroma/web/admin_api/admin_api_controller.ex index cc93c2309..7572a6b65 100644 --- a/lib/pleroma/web/admin_api/admin_api_controller.ex +++ b/lib/pleroma/web/admin_api/admin_api_controller.ex @@ -827,15 +827,11 @@ def config_show(conn, _params) do merged = Pleroma.Config.Holder.config() |> DeepMerge.deep_merge(configs) - |> Enum.map(fn {group, value} -> - Enum.map(value, fn {key, value} -> + |> Enum.map(fn {group, values} -> + Enum.map(values, fn {key, value} -> db = if configs[group][key] do - if Keyword.keyword?(value) do - Keyword.keys(value) |> Enum.map(fn key -> ConfigDB.convert(key) end) - else - ConfigDB.convert(key) - end + ConfigDB.get_db_keys(value, key) end setting = %{ @@ -871,6 +867,9 @@ def config_update(conn, %{"configs" => configs}) do end end) |> Enum.reject(&is_nil(&1)) + |> Enum.map(fn config -> + Map.put(config, :db, ConfigDB.get_db_keys(config)) + end) Pleroma.Config.TransferTask.load_and_update_env() diff --git a/lib/pleroma/web/admin_api/views/config_view.ex b/lib/pleroma/web/admin_api/views/config_view.ex index 72b042ab7..23d97e847 100644 --- a/lib/pleroma/web/admin_api/views/config_view.ex +++ b/lib/pleroma/web/admin_api/views/config_view.ex @@ -12,10 +12,16 @@ def render("index.json", %{configs: configs}) do end def render("show.json", %{config: config}) do - %{ + map = %{ key: config.key, group: config.group, value: Pleroma.ConfigDB.from_binary_with_convert(config.value) } + + if config.db != [] do + Map.put(map, :db, config.db) + else + map + end end end diff --git a/test/config/transfer_task_test.exs b/test/config/transfer_task_test.exs index c3c4ef674..37bea20a3 100644 --- a/test/config/transfer_task_test.exs +++ b/test/config/transfer_task_test.exs @@ -86,6 +86,6 @@ test "non existing atom" do assert ExUnit.CaptureLog.capture_log(fn -> Pleroma.Config.TransferTask.start_link([]) end) =~ - "updating env causes error, key: \":undefined_atom_key\", error: %ArgumentError{message: \"argument error\"}" + "updating env causes error, group: \":pleroma\", key: \":undefined_atom_key\", value: [live: 2, com: 3], error: %ArgumentError{message: \"argument error\"}" end end diff --git a/test/web/admin_api/admin_api_controller_test.exs b/test/web/admin_api/admin_api_controller_test.exs index 0206f23d6..2a0261b0e 100644 --- a/test/web/admin_api/admin_api_controller_test.exs +++ b/test/web/admin_api/admin_api_controller_test.exs @@ -1936,7 +1936,7 @@ test "merged default setting with db settings", %{conn: conn} do |> ConfigDB.convert() Enum.each(received_configs, fn %{"value" => value, "db" => db} -> - assert db in [config1.key, config2.key, db_keys] + assert db in [[config1.key], [config2.key], db_keys] assert value in [ ConfigDB.from_binary_with_convert(config1.value), @@ -1985,7 +1985,7 @@ test "create new config setting in db", %{conn: conn} do %{group: ":pleroma", key: ":key1", value: "value1"}, %{ group: ":ueberauth", - key: "Ueberauth.Strategy.Twitter.OAuth", + key: "Ueberauth", value: [%{"tuple" => [":consumer_secret", "aaaa"]}] }, %{ @@ -2025,12 +2025,14 @@ test "create new config setting in db", %{conn: conn} do %{ "group" => ":pleroma", "key" => ":key1", - "value" => "value1" + "value" => "value1", + "db" => [":key1"] }, %{ "group" => ":ueberauth", - "key" => "Ueberauth.Strategy.Twitter.OAuth", - "value" => [%{"tuple" => [":consumer_secret", "aaaa"]}] + "key" => "Ueberauth", + "value" => [%{"tuple" => [":consumer_secret", "aaaa"]}], + "db" => [":consumer_secret"] }, %{ "group" => ":pleroma", @@ -2041,7 +2043,8 @@ test "create new config setting in db", %{conn: conn} do %{":nested_22" => "nested_value222"}, %{":nested_33" => %{":nested_44" => "nested_444"}} ] - } + }, + "db" => [":key2"] }, %{ "group" => ":pleroma", @@ -2049,17 +2052,20 @@ test "create new config setting in db", %{conn: conn} do "value" => [ %{"nested_3" => ":nested_3", "nested_33" => "nested_33"}, %{"nested_4" => true} - ] + ], + "db" => [":key3"] }, %{ "group" => ":pleroma", "key" => ":key4", - "value" => %{"endpoint" => "https://example.com", ":nested_5" => ":upload"} + "value" => %{"endpoint" => "https://example.com", ":nested_5" => ":upload"}, + "db" => [":key4"] }, %{ "group" => ":idna", "key" => ":key5", - "value" => %{"tuple" => ["string", "Pleroma.Captcha.NotReal", []]} + "value" => %{"tuple" => ["string", "Pleroma.Captcha.NotReal", []]}, + "db" => [":key5"] } ] } @@ -2121,12 +2127,23 @@ test "save config setting without key", %{conn: conn} do assert json_response(conn, 200) == %{ "configs" => [ - %{"group" => ":quack", "key" => ":level", "value" => ":info"}, - %{"group" => ":quack", "key" => ":meta", "value" => [":none"]}, + %{ + "group" => ":quack", + "key" => ":level", + "value" => ":info", + "db" => [":level"] + }, + %{ + "group" => ":quack", + "key" => ":meta", + "value" => [":none"], + "db" => [":meta"] + }, %{ "group" => ":quack", "key" => ":webhook_url", - "value" => "https://hooks.slack.com/services/KEY" + "value" => "https://hooks.slack.com/services/KEY", + "db" => [":webhook_url"] } ] } @@ -2155,7 +2172,8 @@ test "saving config with partial update", %{conn: conn} do %{"tuple" => [":key1", 1]}, %{"tuple" => [":key2", 2]}, %{"tuple" => [":key3", 3]} - ] + ], + "db" => [":key1", ":key2", ":key3"] } ] } @@ -2205,7 +2223,8 @@ test "saving config with nested merge", %{conn: conn} do ] ] } - ] + ], + "db" => [":key1", ":key3", ":key2"] } ] } @@ -2242,7 +2261,8 @@ test "saving special atoms", %{conn: conn} do [%{"tuple" => [":versions", [":tlsv1", ":tlsv1.1", ":tlsv1.2"]]}] ] } - ] + ], + "db" => [":ssl_options"] } ] } @@ -2282,7 +2302,8 @@ test "saving full setting if value is in full_key_update list", %{conn: conn} do "value" => [ ":console", %{"tuple" => ["ExSyslogger", ":ex_syslogger"]} - ] + ], + "db" => [":backends"] } ] } @@ -2318,7 +2339,8 @@ test "saving full setting if value is not keyword", %{conn: conn} do %{ "group" => ":tesla", "key" => ":adapter", - "value" => "Tesla.Adapter.Httpc" + "value" => "Tesla.Adapter.Httpc", + "db" => [":adapter"] } ] } @@ -2351,7 +2373,8 @@ test "update config setting & delete", %{conn: conn} do %{ "group" => ":pleroma", "key" => config1.key, - "value" => "another_value" + "value" => "another_value", + "db" => [":keyaa1"] } ] } @@ -2384,7 +2407,11 @@ test "common config example", %{conn: conn} do %{"tuple" => [":name", "Pleroma"]} ] }, - %{"group" => ":tesla", "key" => ":adapter", "value" => "Tesla.Adapter.Httpc"} + %{ + "group" => ":tesla", + "key" => ":adapter", + "value" => "Tesla.Adapter.Httpc" + } ] }) @@ -2408,9 +2435,27 @@ test "common config example", %{conn: conn} do %{"tuple" => [":regex3", "~r/https:\\/\\/example.com/i"]}, %{"tuple" => [":regex4", "~r/https:\\/\\/example.com/s"]}, %{"tuple" => [":name", "Pleroma"]} + ], + "db" => [ + ":enabled", + ":method", + ":seconds_valid", + ":path", + ":key1", + ":partial_chain", + ":regex1", + ":regex2", + ":regex3", + ":regex4", + ":name" ] }, - %{"group" => ":tesla", "key" => ":adapter", "value" => "Tesla.Adapter.Httpc"} + %{ + "group" => ":tesla", + "key" => ":adapter", + "value" => "Tesla.Adapter.Httpc", + "db" => [":adapter"] + } ] } end @@ -2540,7 +2585,8 @@ test "tuples with more than two values", %{conn: conn} do ] ] } - ] + ], + "db" => [":http"] } ] } @@ -2602,7 +2648,8 @@ test "settings with nesting map", %{conn: conn} do } ] } - ] + ], + "db" => [":key2", ":key3"] } ] } @@ -2626,7 +2673,8 @@ test "value as map", %{conn: conn} do %{ "group" => ":pleroma", "key" => ":key1", - "value" => %{"key" => "some_val"} + "value" => %{"key" => "some_val"}, + "db" => [":key1"] } ] } @@ -2665,6 +2713,15 @@ test "queues key as atom", %{conn: conn} do %{"tuple" => [":transmogrifier", 20]}, %{"tuple" => [":scheduled_activities", 10]}, %{"tuple" => [":background", 5]} + ], + "db" => [ + ":federator_incoming", + ":federator_outgoing", + ":web_push", + ":mailer", + ":transmogrifier", + ":scheduled_activities", + ":background" ] } ] @@ -2695,7 +2752,8 @@ test "delete part of settings by atom subkeys", %{conn: conn} do %{ "group" => ":pleroma", "key" => ":keyaa1", - "value" => [%{"tuple" => [":subkey2", "val2"]}] + "value" => [%{"tuple" => [":subkey2", "val2"]}], + "db" => [":subkey2"] } ] } @@ -2724,7 +2782,8 @@ test "proxy tuple localhost", %{conn: conn} do "value" => [ %{"tuple" => [":proxy_url", %{"tuple" => [":socks5", "localhost", 1234]}]}, %{"tuple" => [":send_user_agent", false]} - ] + ], + "db" => [":proxy_url", ":send_user_agent"] } ] } @@ -2753,7 +2812,8 @@ test "proxy tuple domain", %{conn: conn} do "value" => [ %{"tuple" => [":proxy_url", %{"tuple" => [":socks5", "domain.com", 1234]}]}, %{"tuple" => [":send_user_agent", false]} - ] + ], + "db" => [":proxy_url", ":send_user_agent"] } ] } @@ -2782,7 +2842,8 @@ test "proxy tuple ip", %{conn: conn} do "value" => [ %{"tuple" => [":proxy_url", %{"tuple" => [":socks5", "127.0.0.1", 1234]}]}, %{"tuple" => [":send_user_agent", false]} - ] + ], + "db" => [":proxy_url", ":send_user_agent"] } ] }