diff options
Diffstat (limited to 'lib/mix/tasks')
| -rw-r--r-- | lib/mix/tasks/pleroma/config.ex | 49 | ||||
| -rw-r--r-- | lib/mix/tasks/pleroma/database.ex | 31 | 
2 files changed, 66 insertions, 14 deletions
| diff --git a/lib/mix/tasks/pleroma/config.ex b/lib/mix/tasks/pleroma/config.ex index 1962154b9..22502a522 100644 --- a/lib/mix/tasks/pleroma/config.ex +++ b/lib/mix/tasks/pleroma/config.ex @@ -27,7 +27,7 @@ defmodule Mix.Tasks.Pleroma.Config do        {opts, _} =          OptionParser.parse!(options, -          strict: [env: :string, delete: :boolean], +          strict: [env: :string, delete: :boolean, path: :string],            aliases: [d: :delete]          ) @@ -259,18 +259,43 @@ defmodule Mix.Tasks.Pleroma.Config do    defp migrate_from_db(opts) do      env = opts[:env] || Pleroma.Config.get(:env) +    filename = "#{env}.exported_from_db.secret.exs" +      config_path = -      if Pleroma.Config.get(:release) do -        :config_path -        |> Pleroma.Config.get() -        |> Path.dirname() -      else -        "config" +      cond do +        opts[:path] -> +          opts[:path] + +        Pleroma.Config.get(:release) -> +          :config_path +          |> Pleroma.Config.get() +          |> Path.dirname() + +        true -> +          "config"        end -      |> Path.join("#{env}.exported_from_db.secret.exs") +      |> Path.join(filename) -    file = File.open!(config_path, [:write, :utf8]) +    with {:ok, file} <- File.open(config_path, [:write, :utf8]) do +      write_config(file, config_path, opts) +      shell_info("Database configuration settings have been exported to #{config_path}") +    else +      _ -> +        shell_error("Impossible to save settings to this directory #{Path.dirname(config_path)}") +        tmp_config_path = Path.join(System.tmp_dir!(), filename) +        file = File.open!(tmp_config_path) + +        shell_info( +          "Saving database configuration settings to #{tmp_config_path}. Copy it to the #{ +            Path.dirname(config_path) +          } manually." +        ) +        write_config(file, tmp_config_path, opts) +    end +  end + +  defp write_config(file, path, opts) do      IO.write(file, config_header())      ConfigDB @@ -278,11 +303,7 @@ defmodule Mix.Tasks.Pleroma.Config do      |> Enum.each(&write_and_delete(&1, file, opts[:delete]))      :ok = File.close(file) -    System.cmd("mix", ["format", config_path]) - -    shell_info( -      "Database configuration settings have been exported to config/#{env}.exported_from_db.secret.exs" -    ) +    System.cmd("mix", ["format", path])    end    if Code.ensure_loaded?(Config.Reader) do diff --git a/lib/mix/tasks/pleroma/database.ex b/lib/mix/tasks/pleroma/database.ex index 2403ed581..e7f4b67a4 100644 --- a/lib/mix/tasks/pleroma/database.ex +++ b/lib/mix/tasks/pleroma/database.ex @@ -8,10 +8,13 @@ defmodule Mix.Tasks.Pleroma.Database do    alias Pleroma.Object    alias Pleroma.Repo    alias Pleroma.User +    require Logger    require Pleroma.Constants +    import Ecto.Query    import Mix.Pleroma +    use Mix.Task    @shortdoc "A collection of database related tasks" @@ -214,4 +217,32 @@ defmodule Mix.Tasks.Pleroma.Database do        shell_info('Done.')      end    end + +  # Rolls back a specific migration (leaving subsequent migrations applied). +  # WARNING: imposes a risk of unrecoverable data loss — proceed at your own responsibility. +  # Based on https://stackoverflow.com/a/53825840 +  def run(["rollback", version]) do +    prompt = "SEVERE WARNING: this operation may result in unrecoverable data loss. Continue?" + +    if shell_prompt(prompt, "n") in ~w(Yn Y y) do +      {_, result, _} = +        Ecto.Migrator.with_repo(Pleroma.Repo, fn repo -> +          version = String.to_integer(version) +          re = ~r/^#{version}_.*\.exs/ +          path = Ecto.Migrator.migrations_path(repo) + +          with {_, "" <> file} <- {:find, Enum.find(File.ls!(path), &String.match?(&1, re))}, +               {_, [{mod, _} | _]} <- {:compile, Code.compile_file(Path.join(path, file))}, +               {_, :ok} <- {:rollback, Ecto.Migrator.down(repo, version, mod)} do +            {:ok, "Reversed migration: #{file}"} +          else +            {:find, _} -> {:error, "No migration found with version prefix: #{version}"} +            {:compile, e} -> {:error, "Problem compiling migration module: #{inspect(e)}"} +            {:rollback, e} -> {:error, "Problem reversing migration: #{inspect(e)}"} +          end +        end) + +      shell_info(inspect(result)) +    end +  end  end | 
