util_controller.ex 4.94 KB
Newer Older
1
# Pleroma: A lightweight social networking server
Haelwenn's avatar
Haelwenn committed
2
# Copyright © 2017-2021 Pleroma Authors <https://pleroma.social/>
3 4
# SPDX-License-Identifier: AGPL-3.0-only

dtluna's avatar
dtluna committed
5 6
defmodule Pleroma.Web.TwitterAPI.UtilController do
  use Pleroma.Web, :controller
7

eal's avatar
eal committed
8
  require Logger
9

Maksim's avatar
Maksim committed
10
  alias Pleroma.Config
Haelwenn's avatar
Haelwenn committed
11
  alias Pleroma.Emoji
Maksim's avatar
Maksim committed
12
  alias Pleroma.Healthcheck
13
  alias Pleroma.User
Haelwenn's avatar
Haelwenn committed
14
  alias Pleroma.Web.CommonAPI
15
  alias Pleroma.Web.Plugs.OAuthScopesPlug
Haelwenn's avatar
Haelwenn committed
16
  alias Pleroma.Web.WebFinger
Roger Braun's avatar
Roger Braun committed
17

Haelwenn's avatar
Haelwenn committed
18
  plug(Pleroma.Web.ApiSpec.CastAndValidate when action != :remote_subscribe)
19
  plug(Pleroma.Web.Plugs.FederatingPlug when action == :remote_subscribe)
20

21 22 23 24
  plug(
    OAuthScopesPlug,
    %{scopes: ["write:accounts"]}
    when action in [
25
           :change_email,
26 27 28 29 30 31 32
           :change_password,
           :delete_account,
           :update_notificaton_settings,
           :disable_account
         ]
  )

Haelwenn's avatar
Haelwenn committed
33
  defdelegate open_api_operation(action), to: Pleroma.Web.ApiSpec.TwitterUtilOperation
34

eal's avatar
eal committed
35
  def remote_subscribe(conn, %{"nickname" => nick, "profile" => _}) do
Maksim's avatar
Maksim committed
36 37
    with %User{} = user <- User.get_cached_by_nickname(nick),
         avatar = User.avatar_url(user) do
eal's avatar
eal committed
38 39 40
      conn
      |> render("subscribe.html", %{nickname: nick, avatar: avatar, error: false})
    else
lain's avatar
lain committed
41 42 43 44 45 46
      _e ->
        render(conn, "subscribe.html", %{
          nickname: nick,
          avatar: nil,
          error: "Could not find user"
        })
eal's avatar
eal committed
47 48
    end
  end
lain's avatar
lain committed
49

eal's avatar
eal committed
50 51 52 53 54 55 56
  def remote_subscribe(conn, %{"user" => %{"nickname" => nick, "profile" => profile}}) do
    with {:ok, %{"subscribe_address" => template}} <- WebFinger.finger(profile),
         %User{ap_id: ap_id} <- User.get_cached_by_nickname(nick) do
      conn
      |> Phoenix.Controller.redirect(external: String.replace(template, "{uri}", ap_id))
    else
      _e ->
lain's avatar
lain committed
57 58 59 60 61
        render(conn, "subscribe.html", %{
          nickname: nick,
          avatar: nil,
          error: "Something went wrong."
        })
eal's avatar
eal committed
62 63 64
    end
  end

lain's avatar
lain committed
65
  def frontend_configurations(conn, _params) do
66
    render(conn, "frontend_configurations.json")
lain's avatar
lain committed
67 68
  end

eal's avatar
eal committed
69
  def emoji(conn, _params) do
70
    emoji =
Maksim's avatar
Maksim committed
71 72
      Enum.reduce(Emoji.get_all(), %{}, fn {code, %Emoji{file: file, tags: tags}}, acc ->
        Map.put(acc, code, %{image_url: file, tags: tags})
73 74 75
      end)

    json(conn, emoji)
eal's avatar
eal committed
76
  end
eal's avatar
eal committed
77

78 79 80 81
  def update_notificaton_settings(%{assigns: %{user: user}} = conn, params) do
    with {:ok, _} <- User.update_notification_settings(user, params) do
      json(conn, %{status: "success"})
    end
eal's avatar
eal committed
82
  end
eal's avatar
eal committed
83

84 85
  def change_password(%{assigns: %{user: user}, body_params: body_params} = conn, %{}) do
    case CommonAPI.Utils.confirm_current_password(user, body_params.password) do
86 87 88
      {:ok, user} ->
        with {:ok, _user} <-
               User.reset_password(user, %{
89 90
                 password: body_params.new_password,
                 password_confirmation: body_params.new_password_confirmation
91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106
               }) do
          json(conn, %{status: "success"})
        else
          {:error, changeset} ->
            {_, {error, _}} = Enum.at(changeset.errors, 0)
            json(conn, %{error: "New password #{error}."})

          _ ->
            json(conn, %{error: "Unable to change password."})
        end

      {:error, msg} ->
        json(conn, %{error: msg})
    end
  end

107 108
  def change_email(%{assigns: %{user: user}, body_params: body_params} = conn, %{}) do
    case CommonAPI.Utils.confirm_current_password(user, body_params.password) do
minibikini's avatar
minibikini committed
109
      {:ok, user} ->
110
        with {:ok, _user} <- User.change_email(user, body_params.email) do
minibikini's avatar
minibikini committed
111 112 113 114 115 116 117 118 119 120 121 122 123 124 125
          json(conn, %{status: "success"})
        else
          {:error, changeset} ->
            {_, {error, _}} = Enum.at(changeset.errors, 0)
            json(conn, %{error: "Email #{error}."})

          _ ->
            json(conn, %{error: "Unable to change email."})
        end

      {:error, msg} ->
        json(conn, %{error: msg})
    end
  end

126
  def delete_account(%{assigns: %{user: user}} = conn, params) do
Haelwenn's avatar
Haelwenn committed
127
    password = params[:password] || ""
128 129

    case CommonAPI.Utils.confirm_current_password(user, password) do
130
      {:ok, user} ->
131
        User.delete(user)
132
        json(conn, %{status: "success"})
133 134 135 136 137

      {:error, msg} ->
        json(conn, %{error: msg})
    end
  end
138

139
  def disable_account(%{assigns: %{user: user}} = conn, params) do
Haelwenn's avatar
Haelwenn committed
140
    case CommonAPI.Utils.confirm_current_password(user, params[:password]) do
141
      {:ok, user} ->
142
        User.set_activation_async(user, false)
143 144 145 146 147 148 149
        json(conn, %{status: "success"})

      {:error, msg} ->
        json(conn, %{error: msg})
    end
  end

150 151 152
  def captcha(conn, _params) do
    json(conn, Pleroma.Captcha.new())
  end
153 154

  def healthcheck(conn, _params) do
Maksim's avatar
Maksim committed
155 156 157 158 159 160
    with true <- Config.get([:instance, :healthcheck]),
         %{healthy: true} = info <- Healthcheck.system_info() do
      json(conn, info)
    else
      %{healthy: false} = info ->
        service_unavailable(conn, info)
161

Maksim's avatar
Maksim committed
162 163 164 165
      _ ->
        service_unavailable(conn, %{})
    end
  end
166

Maksim's avatar
Maksim committed
167 168 169 170
  defp service_unavailable(conn, info) do
    conn
    |> put_status(:service_unavailable)
    |> json(info)
171
  end
dtluna's avatar
dtluna committed
172
end