Merge branch 'develop' into feature/multiple-users-activation-permissions
This commit is contained in:
commit
c0aca32dd0
|
@ -1,3 +1,3 @@
|
||||||
[
|
[
|
||||||
inputs: ["mix.exs", "{config,lib,test}/**/*.{ex,exs}"]
|
inputs: ["mix.exs", "{config,lib,test}/**/*.{ex,exs}", "priv/repo/migrations/*.exs"]
|
||||||
]
|
]
|
||||||
|
|
|
@ -16,10 +16,10 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/).
|
||||||
- OAuth: support for hierarchical permissions / [Mastodon 2.4.3 OAuth permissions](https://docs.joinmastodon.org/api/permissions/)
|
- OAuth: support for hierarchical permissions / [Mastodon 2.4.3 OAuth permissions](https://docs.joinmastodon.org/api/permissions/)
|
||||||
- Authentication: Added rate limit for password-authorized actions / login existence checks
|
- Authentication: Added rate limit for password-authorized actions / login existence checks
|
||||||
- Metadata Link: Atom syndication Feed
|
- Metadata Link: Atom syndication Feed
|
||||||
|
- Mix task to re-count statuses for all users (`mix pleroma.count_statuses`)
|
||||||
- Admin API: `/users/:nickname/toggle_activation` endpoint is now deprecated in favor of: `/users/activate`, `/users/deactivate`, both accept `nicknames` array
|
- Admin API: `/users/:nickname/toggle_activation` endpoint is now deprecated in favor of: `/users/activate`, `/users/deactivate`, both accept `nicknames` array
|
||||||
- Admin API: `POST /api/pleroma/admin/users/:nickname/permission_group/:permission_group` / `DELETE /api/pleroma/admin/users/:nickname/permission_group/:permission_group` are deprecated in favor of: `POST /api/pleroma/admin/users/permission_group/:permission_group` / `DELETE /api/pleroma/admin/users/permission_group/:permission_group` (both accept `nicknames` array)
|
- Admin API: `POST /api/pleroma/admin/users/:nickname/permission_group/:permission_group` / `DELETE /api/pleroma/admin/users/:nickname/permission_group/:permission_group` are deprecated in favor of: `POST /api/pleroma/admin/users/permission_group/:permission_group` / `DELETE /api/pleroma/admin/users/permission_group/:permission_group` (both accept `nicknames` array)
|
||||||
|
|
||||||
|
|
||||||
### Changed
|
### Changed
|
||||||
- **Breaking:** Elixir >=1.8 is now required (was >= 1.7)
|
- **Breaking:** Elixir >=1.8 is now required (was >= 1.7)
|
||||||
- **Breaking:** Admin API: Return link alongside with token on password reset
|
- **Breaking:** Admin API: Return link alongside with token on password reset
|
||||||
|
@ -30,6 +30,7 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/).
|
||||||
- Admin API: Return link alongside with token on password reset
|
- Admin API: Return link alongside with token on password reset
|
||||||
- MRF (Simple Policy): Also use `:accept`/`:reject` on the actors rather than only their activities
|
- MRF (Simple Policy): Also use `:accept`/`:reject` on the actors rather than only their activities
|
||||||
- OStatus: Extract RSS functionality
|
- OStatus: Extract RSS functionality
|
||||||
|
- Mastodon API: Add `pleroma.direct_conversation_id` to the status endpoint (`GET /api/v1/statuses/:id`)
|
||||||
|
|
||||||
### Fixed
|
### Fixed
|
||||||
- Mastodon API: Fix private and direct statuses not being filtered out from the public timeline for an authenticated user (`GET /api/v1/timelines/public`)
|
- Mastodon API: Fix private and direct statuses not being filtered out from the public timeline for an authenticated user (`GET /api/v1/timelines/public`)
|
||||||
|
|
|
@ -0,0 +1,22 @@
|
||||||
|
defmodule Mix.Tasks.Pleroma.CountStatuses do
|
||||||
|
@shortdoc "Re-counts statuses for all users"
|
||||||
|
|
||||||
|
use Mix.Task
|
||||||
|
alias Pleroma.User
|
||||||
|
import Ecto.Query
|
||||||
|
|
||||||
|
def run([]) do
|
||||||
|
Mix.Pleroma.start_pleroma()
|
||||||
|
|
||||||
|
stream =
|
||||||
|
User
|
||||||
|
|> where(local: true)
|
||||||
|
|> Pleroma.Repo.stream()
|
||||||
|
|
||||||
|
Pleroma.Repo.transaction(fn ->
|
||||||
|
Enum.each(stream, &User.update_note_count/1)
|
||||||
|
end)
|
||||||
|
|
||||||
|
Mix.Pleroma.shell_info("Done")
|
||||||
|
end
|
||||||
|
end
|
|
@ -167,7 +167,11 @@ def create(%{assigns: %{user: _user}} = conn, %{"media_ids" => _} = params) do
|
||||||
def show(%{assigns: %{user: user}} = conn, %{"id" => id}) do
|
def show(%{assigns: %{user: user}} = conn, %{"id" => id}) do
|
||||||
with %Activity{} = activity <- Activity.get_by_id_with_object(id),
|
with %Activity{} = activity <- Activity.get_by_id_with_object(id),
|
||||||
true <- Visibility.visible_for_user?(activity, user) do
|
true <- Visibility.visible_for_user?(activity, user) do
|
||||||
try_render(conn, "show.json", activity: activity, for: user)
|
try_render(conn, "show.json",
|
||||||
|
activity: activity,
|
||||||
|
for: user,
|
||||||
|
with_direct_conversation_id: true
|
||||||
|
)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|
|
@ -3,14 +3,13 @@ defmodule Pleroma.Repo.Migrations.CreatePleroma.User do
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
create_if_not_exists table(:users) do
|
create_if_not_exists table(:users) do
|
||||||
add :email, :string
|
add(:email, :string)
|
||||||
add :password_hash, :string
|
add(:password_hash, :string)
|
||||||
add :name, :string
|
add(:name, :string)
|
||||||
add :nickname, :string
|
add(:nickname, :string)
|
||||||
add :bio, :string
|
add(:bio, :string)
|
||||||
|
|
||||||
timestamps()
|
timestamps()
|
||||||
end
|
end
|
||||||
|
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -3,12 +3,11 @@ defmodule Pleroma.Repo.Migrations.CreatePleroma.Activity do
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
create_if_not_exists table(:activities) do
|
create_if_not_exists table(:activities) do
|
||||||
add :data, :map
|
add(:data, :map)
|
||||||
|
|
||||||
timestamps()
|
timestamps()
|
||||||
end
|
end
|
||||||
|
|
||||||
create_if_not_exists index(:activities, [:data], using: :gin)
|
create_if_not_exists(index(:activities, [:data], using: :gin))
|
||||||
|
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -3,10 +3,9 @@ defmodule Pleroma.Repo.Migrations.CreatePleroma.Object do
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
create_if_not_exists table(:objects) do
|
create_if_not_exists table(:objects) do
|
||||||
add :data, :map
|
add(:data, :map)
|
||||||
|
|
||||||
timestamps()
|
timestamps()
|
||||||
end
|
end
|
||||||
|
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -3,7 +3,7 @@ defmodule Pleroma.Repo.Migrations.AddFollowingListToUsers do
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
alter table(:users) do
|
alter table(:users) do
|
||||||
add :following, :map
|
add(:following, :map)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -3,7 +3,7 @@ defmodule Pleroma.Repo.Migrations.AddApIdToUsers do
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
alter table(:users) do
|
alter table(:users) do
|
||||||
add :ap_id, :string
|
add(:ap_id, :string)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -2,6 +2,6 @@ defmodule Pleroma.Repo.Migrations.AddIndexToObjects do
|
||||||
use Ecto.Migration
|
use Ecto.Migration
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
create_if_not_exists index(:objects, [:data], using: :gin)
|
create_if_not_exists(index(:objects, [:data], using: :gin))
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -2,7 +2,7 @@ defmodule Pleroma.Repo.Migrations.AddUniqueIndexToEmailAndNickname do
|
||||||
use Ecto.Migration
|
use Ecto.Migration
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
create_if_not_exists unique_index(:users, [:email])
|
create_if_not_exists(unique_index(:users, [:email]))
|
||||||
create_if_not_exists unique_index(:users, [:nickname])
|
create_if_not_exists(unique_index(:users, [:nickname]))
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -3,7 +3,7 @@ defmodule Pleroma.Repo.Migrations.AddAvatarObjectToUsers do
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
alter table(:users) do
|
alter table(:users) do
|
||||||
add :avatar, :map
|
add(:avatar, :map)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -3,11 +3,11 @@ defmodule Pleroma.Repo.Migrations.CreateWebsubServerSubscription do
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
create_if_not_exists table(:websub_server_subscriptions) do
|
create_if_not_exists table(:websub_server_subscriptions) do
|
||||||
add :topic, :string
|
add(:topic, :string)
|
||||||
add :callback, :string
|
add(:callback, :string)
|
||||||
add :secret, :string
|
add(:secret, :string)
|
||||||
add :valid_until, :naive_datetime
|
add(:valid_until, :naive_datetime)
|
||||||
add :state, :string
|
add(:state, :string)
|
||||||
|
|
||||||
timestamps()
|
timestamps()
|
||||||
end
|
end
|
||||||
|
|
|
@ -3,8 +3,8 @@ defmodule Pleroma.Repo.Migrations.AddFieldsToUsers do
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
alter table(:users) do
|
alter table(:users) do
|
||||||
add :local, :boolean, default: true
|
add(:local, :boolean, default: true)
|
||||||
add :info, :map
|
add(:info, :map)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -3,11 +3,11 @@ defmodule Pleroma.Repo.Migrations.CreateWebsubClientSubscription do
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
create_if_not_exists table(:websub_client_subscriptions) do
|
create_if_not_exists table(:websub_client_subscriptions) do
|
||||||
add :topic, :string
|
add(:topic, :string)
|
||||||
add :secret, :string
|
add(:secret, :string)
|
||||||
add :valid_until, :naive_datetime_usec
|
add(:valid_until, :naive_datetime_usec)
|
||||||
add :state, :string
|
add(:state, :string)
|
||||||
add :subscribers, :map
|
add(:subscribers, :map)
|
||||||
|
|
||||||
timestamps()
|
timestamps()
|
||||||
end
|
end
|
||||||
|
|
|
@ -3,8 +3,8 @@ defmodule Pleroma.Repo.Migrations.AddUserAndHub do
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
alter table(:websub_client_subscriptions) do
|
alter table(:websub_client_subscriptions) do
|
||||||
add :hub, :string
|
add(:hub, :string)
|
||||||
add :user_id, references(:users)
|
add(:user_id, references(:users))
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -2,10 +2,16 @@ defmodule Pleroma.Repo.Migrations.AddIdContraintsToActivitiesAndObjectsPartTwo d
|
||||||
use Ecto.Migration
|
use Ecto.Migration
|
||||||
|
|
||||||
def up do
|
def up do
|
||||||
drop_if_exists index(:objects, ["(data->>\"id\")"], name: :objects_unique_apid_index)
|
drop_if_exists(index(:objects, ["(data->>\"id\")"], name: :objects_unique_apid_index))
|
||||||
drop_if_exists index(:activities, ["(data->>\"id\")"], name: :activities_unique_apid_index)
|
drop_if_exists(index(:activities, ["(data->>\"id\")"], name: :activities_unique_apid_index))
|
||||||
create_if_not_exists unique_index(:objects, ["(data->>'id')"], name: :objects_unique_apid_index)
|
|
||||||
create_if_not_exists unique_index(:activities, ["(data->>'id')"], name: :activities_unique_apid_index)
|
create_if_not_exists(
|
||||||
|
unique_index(:objects, ["(data->>'id')"], name: :objects_unique_apid_index)
|
||||||
|
)
|
||||||
|
|
||||||
|
create_if_not_exists(
|
||||||
|
unique_index(:activities, ["(data->>'id')"], name: :activities_unique_apid_index)
|
||||||
|
)
|
||||||
end
|
end
|
||||||
|
|
||||||
def down, do: :ok
|
def down, do: :ok
|
||||||
|
|
|
@ -3,9 +3,9 @@ defmodule Pleroma.Repo.Migrations.AddLocalFieldToActivities do
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
alter table(:activities) do
|
alter table(:activities) do
|
||||||
add :local, :boolean, default: true
|
add(:local, :boolean, default: true)
|
||||||
end
|
end
|
||||||
|
|
||||||
create_if_not_exists index(:activities, [:local])
|
create_if_not_exists(index(:activities, [:local]))
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -2,6 +2,6 @@ defmodule Pleroma.Repo.Migrations.AddUniqueIndexToAPID do
|
||||||
use Ecto.Migration
|
use Ecto.Migration
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
create_if_not_exists unique_index(:users, [:ap_id])
|
create_if_not_exists(unique_index(:users, [:ap_id]))
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -3,14 +3,13 @@ defmodule Pleroma.Repo.Migrations.LongerBios do
|
||||||
|
|
||||||
def up do
|
def up do
|
||||||
alter table(:users) do
|
alter table(:users) do
|
||||||
modify :bio, :text
|
modify(:bio, :text)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
def down do
|
def down do
|
||||||
alter table(:users) do
|
alter table(:users) do
|
||||||
modify :bio, :string
|
modify(:bio, :string)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
end
|
end
|
||||||
|
|
|
@ -2,6 +2,6 @@ defmodule Pleroma.Repo.Migrations.RemoveActivitiesIndex do
|
||||||
use Ecto.Migration
|
use Ecto.Migration
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
drop_if_exists index(:activities, [:data])
|
drop_if_exists(index(:activities, [:data]))
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -2,7 +2,16 @@ defmodule Pleroma.Repo.Migrations.AddObjectActivityIndexPartTwo do
|
||||||
use Ecto.Migration
|
use Ecto.Migration
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
drop_if_exists index(:objects, ["(data->'object'->>'id')", "(data->>'type')"], name: :activities_create_objects_index)
|
drop_if_exists(
|
||||||
create_if_not_exists index(:activities, ["(data->'object'->>'id')", "(data->>'type')"], name: :activities_create_objects_index)
|
index(:objects, ["(data->'object'->>'id')", "(data->>'type')"],
|
||||||
|
name: :activities_create_objects_index
|
||||||
|
)
|
||||||
|
)
|
||||||
|
|
||||||
|
create_if_not_exists(
|
||||||
|
index(:activities, ["(data->'object'->>'id')", "(data->>'type')"],
|
||||||
|
name: :activities_create_objects_index
|
||||||
|
)
|
||||||
|
)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -2,6 +2,8 @@ defmodule Pleroma.Repo.Migrations.AddActorIndexToActivity do
|
||||||
use Ecto.Migration
|
use Ecto.Migration
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
create_if_not_exists index(:activities, ["(data->>'actor')", "inserted_at desc"], name: :activities_actor_index)
|
create_if_not_exists(
|
||||||
|
index(:activities, ["(data->>'actor')", "inserted_at desc"], name: :activities_actor_index)
|
||||||
|
)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -3,13 +3,13 @@ defmodule Pleroma.Repo.Migrations.AddFollowerAddressToUser do
|
||||||
|
|
||||||
def up do
|
def up do
|
||||||
alter table(:users) do
|
alter table(:users) do
|
||||||
add :follower_address, :string, unique: true
|
add(:follower_address, :string, unique: true)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
def down do
|
def down do
|
||||||
alter table(:users) do
|
alter table(:users) do
|
||||||
remove :follower_address
|
remove(:follower_address)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -3,12 +3,12 @@ defmodule Pleroma.Repo.Migrations.AddMastodonApps do
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
create_if_not_exists table(:apps) do
|
create_if_not_exists table(:apps) do
|
||||||
add :client_name, :string
|
add(:client_name, :string)
|
||||||
add :redirect_uris, :string
|
add(:redirect_uris, :string)
|
||||||
add :scopes, :string
|
add(:scopes, :string)
|
||||||
add :website, :string
|
add(:website, :string)
|
||||||
add :client_id, :string
|
add(:client_id, :string)
|
||||||
add :client_secret, :string
|
add(:client_secret, :string)
|
||||||
|
|
||||||
timestamps()
|
timestamps()
|
||||||
end
|
end
|
||||||
|
|
|
@ -3,11 +3,11 @@ defmodule Pleroma.Repo.Migrations.CreateOAuthAuthorizations do
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
create_if_not_exists table(:oauth_authorizations) do
|
create_if_not_exists table(:oauth_authorizations) do
|
||||||
add :app_id, references(:apps)
|
add(:app_id, references(:apps))
|
||||||
add :user_id, references(:users)
|
add(:user_id, references(:users))
|
||||||
add :token, :string
|
add(:token, :string)
|
||||||
add :valid_until, :naive_datetime_usec
|
add(:valid_until, :naive_datetime_usec)
|
||||||
add :used, :boolean, default: false
|
add(:used, :boolean, default: false)
|
||||||
|
|
||||||
timestamps()
|
timestamps()
|
||||||
end
|
end
|
||||||
|
|
|
@ -3,11 +3,11 @@ defmodule Pleroma.Repo.Migrations.CreateOAuthToken do
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
create_if_not_exists table(:oauth_tokens) do
|
create_if_not_exists table(:oauth_tokens) do
|
||||||
add :app_id, references(:apps)
|
add(:app_id, references(:apps))
|
||||||
add :user_id, references(:users)
|
add(:user_id, references(:users))
|
||||||
add :token, :string
|
add(:token, :string)
|
||||||
add :refresh_token, :string
|
add(:refresh_token, :string)
|
||||||
add :valid_until, :naive_datetime_usec
|
add(:valid_until, :naive_datetime_usec)
|
||||||
|
|
||||||
timestamps()
|
timestamps()
|
||||||
end
|
end
|
||||||
|
|
|
@ -3,13 +3,13 @@ defmodule Pleroma.Repo.Migrations.CreateNotifications do
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
create_if_not_exists table(:notifications) do
|
create_if_not_exists table(:notifications) do
|
||||||
add :user_id, references(:users, on_delete: :delete_all)
|
add(:user_id, references(:users, on_delete: :delete_all))
|
||||||
add :activity_id, references(:activities, on_delete: :delete_all)
|
add(:activity_id, references(:activities, on_delete: :delete_all))
|
||||||
add :seen, :boolean, default: false
|
add(:seen, :boolean, default: false)
|
||||||
|
|
||||||
timestamps()
|
timestamps()
|
||||||
end
|
end
|
||||||
|
|
||||||
create_if_not_exists index(:notifications, [:user_id])
|
create_if_not_exists(index(:notifications, [:user_id]))
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -3,6 +3,11 @@ defmodule Pleroma.Repo.Migrations.AddContextIndex do
|
||||||
@disable_ddl_transaction true
|
@disable_ddl_transaction true
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
create index(:activities, ["(data->>'type')", "(data->>'context')"], name: :activities_context_index, concurrently: true)
|
create(
|
||||||
|
index(:activities, ["(data->>'type')", "(data->>'context')"],
|
||||||
|
name: :activities_context_index,
|
||||||
|
concurrently: true
|
||||||
|
)
|
||||||
|
)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -3,6 +3,12 @@ defmodule Pleroma.Repo.Migrations.AddFTSIndexToActivities do
|
||||||
@disable_ddl_transaction true
|
@disable_ddl_transaction true
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
create index(:activities, ["(to_tsvector('english', data->'object'->>'content'))"], concurrently: true, using: :gin, name: :activities_fts)
|
create(
|
||||||
|
index(:activities, ["(to_tsvector('english', data->'object'->>'content'))"],
|
||||||
|
concurrently: true,
|
||||||
|
using: :gin,
|
||||||
|
name: :activities_fts
|
||||||
|
)
|
||||||
|
)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -4,6 +4,12 @@ defmodule Pleroma.Repo.Migrations.AddTagIndex do
|
||||||
@disable_ddl_transaction true
|
@disable_ddl_transaction true
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
create index(:activities, ["(data #> '{\"object\",\"tag\"}')"], concurrently: true, using: :gin, name: :activities_tags)
|
create(
|
||||||
|
index(:activities, ["(data #> '{\"object\",\"tag\"}')"],
|
||||||
|
concurrently: true,
|
||||||
|
using: :gin,
|
||||||
|
name: :activities_tags
|
||||||
|
)
|
||||||
|
)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -3,9 +3,9 @@ defmodule Pleroma.Repo.Migrations.CreatePasswordResetTokens do
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
create_if_not_exists table(:password_reset_tokens) do
|
create_if_not_exists table(:password_reset_tokens) do
|
||||||
add :token, :string
|
add(:token, :string)
|
||||||
add :user_id, references(:users)
|
add(:user_id, references(:users))
|
||||||
add :used, :boolean, default: false
|
add(:used, :boolean, default: false)
|
||||||
|
|
||||||
timestamps()
|
timestamps()
|
||||||
end
|
end
|
||||||
|
|
|
@ -4,7 +4,17 @@ defmodule Pleroma.Repo.Migrations.AddSecondObjectIndexToActivty do
|
||||||
@disable_ddl_transaction true
|
@disable_ddl_transaction true
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
drop_if_exists index(:activities, ["(data->'object'->>'id')", "(data->>'type')"], name: :activities_create_objects_index)
|
drop_if_exists(
|
||||||
create index(:activities, ["(coalesce(data->'object'->>'id', data->>'object'))"], name: :activities_create_objects_index, concurrently: true)
|
index(:activities, ["(data->'object'->>'id')", "(data->>'type')"],
|
||||||
|
name: :activities_create_objects_index
|
||||||
|
)
|
||||||
|
)
|
||||||
|
|
||||||
|
create(
|
||||||
|
index(:activities, ["(coalesce(data->'object'->>'id', data->>'object'))"],
|
||||||
|
name: :activities_create_objects_index,
|
||||||
|
concurrently: true
|
||||||
|
)
|
||||||
|
)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -2,6 +2,6 @@ defmodule Pleroma.Repo.Migrations.DropObjectIndex do
|
||||||
use Ecto.Migration
|
use Ecto.Migration
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
drop_if_exists index(:objects, [:data], using: :gin)
|
drop_if_exists(index(:objects, [:data], using: :gin))
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -4,6 +4,11 @@ defmodule Pleroma.Repo.Migrations.AddObjectActorIndex do
|
||||||
@disable_ddl_transaction true
|
@disable_ddl_transaction true
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
create index(:objects, ["(data->>'actor')", "(data->>'type')"], concurrently: true, name: :objects_actor_type)
|
create(
|
||||||
|
index(:objects, ["(data->>'actor')", "(data->>'type')"],
|
||||||
|
concurrently: true,
|
||||||
|
name: :objects_actor_type
|
||||||
|
)
|
||||||
|
)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -5,16 +5,17 @@ defmodule Pleroma.Repo.Migrations.AddActorToActivity do
|
||||||
|
|
||||||
def up do
|
def up do
|
||||||
alter table(:activities) do
|
alter table(:activities) do
|
||||||
add :actor, :string
|
add(:actor, :string)
|
||||||
end
|
end
|
||||||
|
|
||||||
create index(:activities, [:actor, "id DESC NULLS LAST"], concurrently: true)
|
create(index(:activities, [:actor, "id DESC NULLS LAST"], concurrently: true))
|
||||||
end
|
end
|
||||||
|
|
||||||
def down do
|
def down do
|
||||||
drop_if_exists index(:activities, [:actor, "id DESC NULLS LAST"])
|
drop_if_exists(index(:activities, [:actor, "id DESC NULLS LAST"]))
|
||||||
|
|
||||||
alter table(:activities) do
|
alter table(:activities) do
|
||||||
remove :actor
|
remove(:actor)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -5,17 +5,19 @@ defmodule Pleroma.Repo.Migrations.FillActorField do
|
||||||
|
|
||||||
def up do
|
def up do
|
||||||
max = Repo.aggregate(Activity, :max, :id)
|
max = Repo.aggregate(Activity, :max, :id)
|
||||||
|
|
||||||
if max do
|
if max do
|
||||||
IO.puts("#{max} activities")
|
IO.puts("#{max} activities")
|
||||||
chunks = 0..(round(max / 10_000))
|
chunks = 0..round(max / 10_000)
|
||||||
|
|
||||||
Enum.each(chunks, fn (i) ->
|
Enum.each(chunks, fn i ->
|
||||||
min = i * 10_000
|
min = i * 10_000
|
||||||
max = min + 10_000
|
max = min + 10_000
|
||||||
|
|
||||||
execute("""
|
execute("""
|
||||||
update activities set actor = data->>'actor' where id > #{min} and id <= #{max};
|
update activities set actor = data->>'actor' where id > #{min} and id <= #{max};
|
||||||
""")
|
""")
|
||||||
|> IO.inspect
|
|> IO.inspect()
|
||||||
end)
|
end)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
@ -23,4 +25,3 @@ def up do
|
||||||
def down do
|
def down do
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|
|
@ -3,6 +3,6 @@ defmodule Pleroma.Repo.Migrations.AddSortIndexToActivities do
|
||||||
@disable_ddl_transaction true
|
@disable_ddl_transaction true
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
create index(:activities, ["id desc nulls last"], concurrently: true)
|
create(index(:activities, ["id desc nulls last"], concurrently: true))
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -2,6 +2,6 @@ defmodule Pleroma.Repo.Migrations.AddLocalIndexToUser do
|
||||||
use Ecto.Migration
|
use Ecto.Migration
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
create_if_not_exists index(:users, [:local])
|
create_if_not_exists(index(:users, [:local]))
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -3,9 +3,9 @@ defmodule Pleroma.Repo.Migrations.AddRecipientsToActivities do
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
alter table(:activities) do
|
alter table(:activities) do
|
||||||
add :recipients, {:array, :string}
|
add(:recipients, {:array, :string})
|
||||||
end
|
end
|
||||||
|
|
||||||
create_if_not_exists index(:activities, [:recipients], using: :gin)
|
create_if_not_exists(index(:activities, [:recipients], using: :gin))
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -4,17 +4,21 @@ defmodule Pleroma.Repo.Migrations.FillRecipientsInActivities do
|
||||||
|
|
||||||
def up do
|
def up do
|
||||||
max = Repo.aggregate(Activity, :max, :id)
|
max = Repo.aggregate(Activity, :max, :id)
|
||||||
|
|
||||||
if max do
|
if max do
|
||||||
IO.puts("#{max} activities")
|
IO.puts("#{max} activities")
|
||||||
chunks = 0..(round(max / 10_000))
|
chunks = 0..round(max / 10_000)
|
||||||
|
|
||||||
Enum.each(chunks, fn (i) ->
|
Enum.each(chunks, fn i ->
|
||||||
min = i * 10_000
|
min = i * 10_000
|
||||||
max = min + 10_000
|
max = min + 10_000
|
||||||
|
|
||||||
execute("""
|
execute("""
|
||||||
update activities set recipients = array(select jsonb_array_elements_text(data->'to')) where id > #{min} and id <= #{max};
|
update activities set recipients = array(select jsonb_array_elements_text(data->'to')) where id > #{
|
||||||
|
min
|
||||||
|
} and id <= #{max};
|
||||||
""")
|
""")
|
||||||
|> IO.inspect
|
|> IO.inspect()
|
||||||
end)
|
end)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -3,17 +3,18 @@ defmodule Pleroma.Repo.Migrations.MakeFollowingPostgresArray do
|
||||||
|
|
||||||
def up do
|
def up do
|
||||||
alter table(:users) do
|
alter table(:users) do
|
||||||
add :following_temp, {:array, :string}
|
add(:following_temp, {:array, :string})
|
||||||
end
|
end
|
||||||
|
|
||||||
execute """
|
execute("""
|
||||||
update users set following_temp = array(select jsonb_array_elements_text(following));
|
update users set following_temp = array(select jsonb_array_elements_text(following));
|
||||||
"""
|
""")
|
||||||
|
|
||||||
alter table(:users) do
|
alter table(:users) do
|
||||||
remove :following
|
remove(:following)
|
||||||
end
|
end
|
||||||
rename table(:users), :following_temp, to: :following
|
|
||||||
|
rename(table(:users), :following_temp, to: :following)
|
||||||
end
|
end
|
||||||
|
|
||||||
def down, do: :ok
|
def down, do: :ok
|
||||||
|
|
|
@ -3,7 +3,7 @@ defmodule Pleroma.Repo.Migrations.AddFollowerAddressIndexToUsers do
|
||||||
|
|
||||||
@disable_ddl_transaction true
|
@disable_ddl_transaction true
|
||||||
def change do
|
def change do
|
||||||
create index(:users, [:follower_address], concurrently: true)
|
create(index(:users, [:follower_address], concurrently: true))
|
||||||
create index(:users, [:following], concurrently: true, using: :gin)
|
create(index(:users, [:following], concurrently: true, using: :gin))
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -2,6 +2,6 @@ defmodule Pleroma.Repo.Migrations.DropLocalIndexOnActivities do
|
||||||
use Ecto.Migration
|
use Ecto.Migration
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
drop_if_exists index(:users, [:local])
|
drop_if_exists(index(:users, [:local]))
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -2,7 +2,7 @@ defmodule Pleroma.Repo.Migrations.ActuallyDropLocalIndex do
|
||||||
use Ecto.Migration
|
use Ecto.Migration
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
create_if_not_exists index(:users, [:local])
|
create_if_not_exists(index(:users, [:local]))
|
||||||
drop_if_exists index("activities", :local)
|
drop_if_exists(index("activities", :local))
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -3,13 +3,13 @@ defmodule Pleroma.Repo.Migrations.CreateLists do
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
create_if_not_exists table(:lists) do
|
create_if_not_exists table(:lists) do
|
||||||
add :user_id, references(:users, on_delete: :delete_all)
|
add(:user_id, references(:users, on_delete: :delete_all))
|
||||||
add :title, :string
|
add(:title, :string)
|
||||||
add :following, {:array, :string}
|
add(:following, {:array, :string})
|
||||||
|
|
||||||
timestamps()
|
timestamps()
|
||||||
end
|
end
|
||||||
|
|
||||||
create_if_not_exists index(:lists, [:user_id])
|
create_if_not_exists(index(:lists, [:user_id]))
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -3,7 +3,7 @@ defmodule Pleroma.Repo.Migrations.ModifyActivityIndex do
|
||||||
@disable_ddl_transaction true
|
@disable_ddl_transaction true
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
create index(:activities, ["id desc nulls last", "local"], concurrently: true)
|
create(index(:activities, ["id desc nulls last", "local"], concurrently: true))
|
||||||
drop_if_exists index(:activities, ["id desc nulls last"])
|
drop_if_exists(index(:activities, ["id desc nulls last"]))
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -4,8 +4,15 @@ defmodule Pleroma.Repo.Migrations.AddTrigramExtension do
|
||||||
|
|
||||||
def up do
|
def up do
|
||||||
Logger.warn("ATTENTION ATTENTION ATTENTION\n")
|
Logger.warn("ATTENTION ATTENTION ATTENTION\n")
|
||||||
Logger.warn("This will try to create the pg_trgm extension on your database. If your database user does NOT have the necessary rights, you will have to do it manually and re-run the migrations.\nYou can probably do this by running the following:\n")
|
|
||||||
Logger.warn("sudo -u postgres psql pleroma_dev -c \"create extension if not exists pg_trgm\"\n")
|
Logger.warn(
|
||||||
|
"This will try to create the pg_trgm extension on your database. If your database user does NOT have the necessary rights, you will have to do it manually and re-run the migrations.\nYou can probably do this by running the following:\n"
|
||||||
|
)
|
||||||
|
|
||||||
|
Logger.warn(
|
||||||
|
"sudo -u postgres psql pleroma_dev -c \"create extension if not exists pg_trgm\"\n"
|
||||||
|
)
|
||||||
|
|
||||||
execute("create extension if not exists pg_trgm")
|
execute("create extension if not exists pg_trgm")
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|
|
@ -2,6 +2,8 @@ defmodule Pleroma.Repo.Migrations.CreateUserTrigramIndex do
|
||||||
use Ecto.Migration
|
use Ecto.Migration
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
create_if_not_exists index(:users, ["(nickname || name) gist_trgm_ops"], name: :users_trigram_index, using: :gist)
|
create_if_not_exists(
|
||||||
|
index(:users, ["(nickname || name) gist_trgm_ops"], name: :users_trigram_index, using: :gist)
|
||||||
|
)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -2,6 +2,6 @@ defmodule Pleroma.Repo.Migrations.AddListFollowIndex do
|
||||||
use Ecto.Migration
|
use Ecto.Migration
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
create_if_not_exists index(:lists, [:following])
|
create_if_not_exists(index(:lists, [:following]))
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -3,6 +3,11 @@ defmodule Pleroma.Repo.Migrations.CreateApidHostExtractionIndex do
|
||||||
@disable_ddl_transaction true
|
@disable_ddl_transaction true
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
create index(:activities, ["(split_part(actor, '/', 3))"], concurrently: true, name: :activities_hosts)
|
create(
|
||||||
|
index(:activities, ["(split_part(actor, '/', 3))"],
|
||||||
|
concurrently: true,
|
||||||
|
name: :activities_hosts
|
||||||
|
)
|
||||||
|
)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -3,8 +3,8 @@ defmodule Pleroma.Repo.Migrations.CreateUserInviteTokens do
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
create_if_not_exists table(:user_invite_tokens) do
|
create_if_not_exists table(:user_invite_tokens) do
|
||||||
add :token, :string
|
add(:token, :string)
|
||||||
add :used, :boolean, default: false
|
add(:used, :boolean, default: false)
|
||||||
|
|
||||||
timestamps()
|
timestamps()
|
||||||
end
|
end
|
||||||
|
|
|
@ -3,6 +3,11 @@ defmodule Pleroma.Repo.Migrations.CreateActivitiesInReplyToIndex do
|
||||||
@disable_ddl_transaction true
|
@disable_ddl_transaction true
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
create index(:activities, ["(data->'object'->>'inReplyTo')"], concurrently: true, name: :activities_in_reply_to)
|
create(
|
||||||
|
index(:activities, ["(data->'object'->>'inReplyTo')"],
|
||||||
|
concurrently: true,
|
||||||
|
name: :activities_in_reply_to
|
||||||
|
)
|
||||||
|
)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -3,18 +3,21 @@ defmodule Pleroma.Repo.Migrations.CreateFilters do
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
create_if_not_exists table(:filters) do
|
create_if_not_exists table(:filters) do
|
||||||
add :user_id, references(:users, on_delete: :delete_all)
|
add(:user_id, references(:users, on_delete: :delete_all))
|
||||||
add :filter_id, :integer
|
add(:filter_id, :integer)
|
||||||
add :hide, :boolean
|
add(:hide, :boolean)
|
||||||
add :phrase, :string
|
add(:phrase, :string)
|
||||||
add :context, {:array, :string}
|
add(:context, {:array, :string})
|
||||||
add :expires_at, :utc_datetime
|
add(:expires_at, :utc_datetime)
|
||||||
add :whole_word, :boolean
|
add(:whole_word, :boolean)
|
||||||
|
|
||||||
timestamps()
|
timestamps()
|
||||||
end
|
end
|
||||||
|
|
||||||
create_if_not_exists index(:filters, [:user_id])
|
create_if_not_exists(index(:filters, [:user_id]))
|
||||||
create_if_not_exists index(:filters, [:phrase], where: "hide = true", name: :hided_phrases_index)
|
|
||||||
|
create_if_not_exists(
|
||||||
|
index(:filters, [:phrase], where: "hide = true", name: :hided_phrases_index)
|
||||||
|
)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -3,11 +3,11 @@ defmodule Pleroma.Repo.Migrations.AddRecipientsToAndCcFieldsToActivities do
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
alter table(:activities) do
|
alter table(:activities) do
|
||||||
add :recipients_to, {:array, :string}
|
add(:recipients_to, {:array, :string})
|
||||||
add :recipients_cc, {:array, :string}
|
add(:recipients_cc, {:array, :string})
|
||||||
end
|
end
|
||||||
|
|
||||||
create_if_not_exists index(:activities, [:recipients_to], using: :gin)
|
create_if_not_exists(index(:activities, [:recipients_to], using: :gin))
|
||||||
create_if_not_exists index(:activities, [:recipients_cc], using: :gin)
|
create_if_not_exists(index(:activities, [:recipients_cc], using: :gin))
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -2,7 +2,12 @@ defmodule Pleroma.Repo.Migrations.ActivitiesAddToCcIndices do
|
||||||
use Ecto.Migration
|
use Ecto.Migration
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
create_if_not_exists index(:activities, ["(data->'to')"], name: :activities_to_index, using: :gin)
|
create_if_not_exists(
|
||||||
create_if_not_exists index(:activities, ["(data->'cc')"], name: :activities_cc_index, using: :gin)
|
index(:activities, ["(data->'to')"], name: :activities_to_index, using: :gin)
|
||||||
|
)
|
||||||
|
|
||||||
|
create_if_not_exists(
|
||||||
|
index(:activities, ["(data->'cc')"], name: :activities_cc_index, using: :gin)
|
||||||
|
)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -3,15 +3,15 @@ defmodule Pleroma.Repo.Migrations.RemoveRecipientsToAndCcFieldsFromActivities do
|
||||||
|
|
||||||
def up do
|
def up do
|
||||||
alter table(:activities) do
|
alter table(:activities) do
|
||||||
remove :recipients_to
|
remove(:recipients_to)
|
||||||
remove :recipients_cc
|
remove(:recipients_cc)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
def down do
|
def down do
|
||||||
alter table(:activities) do
|
alter table(:activities) do
|
||||||
add :recipients_to, {:array, :string}
|
add(:recipients_to, {:array, :string})
|
||||||
add :recipients_cc, {:array, :string}
|
add(:recipients_cc, {:array, :string})
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -2,6 +2,8 @@ defmodule Pleroma.Repo.Migrations.UsersAddIsModeratorIndex do
|
||||||
use Ecto.Migration
|
use Ecto.Migration
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
create_if_not_exists index(:users, ["(info->'is_moderator')"], name: :users_is_moderator_index, using: :gin)
|
create_if_not_exists(
|
||||||
|
index(:users, ["(info->'is_moderator')"], name: :users_is_moderator_index, using: :gin)
|
||||||
|
)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -3,16 +3,16 @@ defmodule Pleroma.Repo.Migrations.CreatePushSubscriptions do
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
create_if_not_exists table("push_subscriptions") do
|
create_if_not_exists table("push_subscriptions") do
|
||||||
add :user_id, references("users", on_delete: :delete_all)
|
add(:user_id, references("users", on_delete: :delete_all))
|
||||||
add :token_id, references("oauth_tokens", on_delete: :delete_all)
|
add(:token_id, references("oauth_tokens", on_delete: :delete_all))
|
||||||
add :endpoint, :string
|
add(:endpoint, :string)
|
||||||
add :key_p256dh, :string
|
add(:key_p256dh, :string)
|
||||||
add :key_auth, :string
|
add(:key_auth, :string)
|
||||||
add :data, :map
|
add(:data, :map)
|
||||||
|
|
||||||
timestamps()
|
timestamps()
|
||||||
end
|
end
|
||||||
|
|
||||||
create_if_not_exists index("push_subscriptions", [:user_id, :token_id], unique: true)
|
create_if_not_exists(index("push_subscriptions", [:user_id, :token_id], unique: true))
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -3,7 +3,7 @@ defmodule Pleroma.Repo.Migrations.UsersAddLastRefreshedAt do
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
alter table(:users) do
|
alter table(:users) do
|
||||||
add :last_refreshed_at, :naive_datetime_usec
|
add(:last_refreshed_at, :naive_datetime_usec)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -3,9 +3,9 @@ defmodule Pleroma.Repo.Migrations.AddTagsToUsers do
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
alter table(:users) do
|
alter table(:users) do
|
||||||
add :tags, {:array, :string}
|
add(:tags, {:array, :string})
|
||||||
end
|
end
|
||||||
|
|
||||||
create_if_not_exists index(:users, [:tags], using: :gin)
|
create_if_not_exists(index(:users, [:tags], using: :gin))
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -3,7 +3,7 @@ defmodule Pleroma.Repo.Migrations.AddBookmarksToUsers do
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
alter table(:users) do
|
alter table(:users) do
|
||||||
add :bookmarks, {:array, :string}, null: false, default: []
|
add(:bookmarks, {:array, :string}, null: false, default: [])
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -16,32 +16,34 @@ def up do
|
||||||
# Old serial int ids are transformed to 128bits with extra padding.
|
# Old serial int ids are transformed to 128bits with extra padding.
|
||||||
# The application (in `Pleroma.FlakeId`) handles theses IDs properly as integers; to keep compatibility
|
# The application (in `Pleroma.FlakeId`) handles theses IDs properly as integers; to keep compatibility
|
||||||
# with previously issued ids.
|
# with previously issued ids.
|
||||||
#execute "update activities set external_id = CAST( LPAD( TO_HEX(id), 32, '0' ) AS uuid);"
|
# execute "update activities set external_id = CAST( LPAD( TO_HEX(id), 32, '0' ) AS uuid);"
|
||||||
#execute "update users set external_id = CAST( LPAD( TO_HEX(id), 32, '0' ) AS uuid);"
|
# execute "update users set external_id = CAST( LPAD( TO_HEX(id), 32, '0' ) AS uuid);"
|
||||||
|
|
||||||
clippy = start_clippy_heartbeats()
|
clippy = start_clippy_heartbeats()
|
||||||
|
|
||||||
# Lock both tables to avoid a running server to meddling with our transaction
|
# Lock both tables to avoid a running server to meddling with our transaction
|
||||||
execute "LOCK TABLE activities;"
|
execute("LOCK TABLE activities;")
|
||||||
execute "LOCK TABLE users;"
|
execute("LOCK TABLE users;")
|
||||||
|
|
||||||
execute """
|
execute("""
|
||||||
ALTER TABLE activities
|
ALTER TABLE activities
|
||||||
DROP CONSTRAINT activities_pkey CASCADE,
|
DROP CONSTRAINT activities_pkey CASCADE,
|
||||||
ALTER COLUMN id DROP default,
|
ALTER COLUMN id DROP default,
|
||||||
ALTER COLUMN id SET DATA TYPE uuid USING CAST( LPAD( TO_HEX(id), 32, '0' ) AS uuid),
|
ALTER COLUMN id SET DATA TYPE uuid USING CAST( LPAD( TO_HEX(id), 32, '0' ) AS uuid),
|
||||||
ADD PRIMARY KEY (id);
|
ADD PRIMARY KEY (id);
|
||||||
"""
|
""")
|
||||||
|
|
||||||
execute """
|
execute("""
|
||||||
ALTER TABLE users
|
ALTER TABLE users
|
||||||
DROP CONSTRAINT users_pkey CASCADE,
|
DROP CONSTRAINT users_pkey CASCADE,
|
||||||
ALTER COLUMN id DROP default,
|
ALTER COLUMN id DROP default,
|
||||||
ALTER COLUMN id SET DATA TYPE uuid USING CAST( LPAD( TO_HEX(id), 32, '0' ) AS uuid),
|
ALTER COLUMN id SET DATA TYPE uuid USING CAST( LPAD( TO_HEX(id), 32, '0' ) AS uuid),
|
||||||
ADD PRIMARY KEY (id);
|
ADD PRIMARY KEY (id);
|
||||||
"""
|
""")
|
||||||
|
|
||||||
execute "UPDATE users SET info = jsonb_set(info, '{pinned_activities}', array_to_json(ARRAY(select jsonb_array_elements_text(info->'pinned_activities')))::jsonb);"
|
execute(
|
||||||
|
"UPDATE users SET info = jsonb_set(info, '{pinned_activities}', array_to_json(ARRAY(select jsonb_array_elements_text(info->'pinned_activities')))::jsonb);"
|
||||||
|
)
|
||||||
|
|
||||||
# Fkeys:
|
# Fkeys:
|
||||||
# Activities - Referenced by:
|
# Activities - Referenced by:
|
||||||
|
@ -56,18 +58,19 @@ def up do
|
||||||
# TABLE "push_subscriptions" CONSTRAINT "push_subscriptions_user_id_fkey" FOREIGN KEY (user_id) REFERENCES users(id) ON DELETE CASCADE
|
# TABLE "push_subscriptions" CONSTRAINT "push_subscriptions_user_id_fkey" FOREIGN KEY (user_id) REFERENCES users(id) ON DELETE CASCADE
|
||||||
# TABLE "websub_client_subscriptions" CONSTRAINT "websub_client_subscriptions_user_id_fkey" FOREIGN KEY (user_id) REFERENCES users(id)
|
# TABLE "websub_client_subscriptions" CONSTRAINT "websub_client_subscriptions_user_id_fkey" FOREIGN KEY (user_id) REFERENCES users(id)
|
||||||
|
|
||||||
execute """
|
execute("""
|
||||||
ALTER TABLE notifications
|
ALTER TABLE notifications
|
||||||
ALTER COLUMN activity_id SET DATA TYPE uuid USING CAST( LPAD( TO_HEX(activity_id), 32, '0' ) AS uuid),
|
ALTER COLUMN activity_id SET DATA TYPE uuid USING CAST( LPAD( TO_HEX(activity_id), 32, '0' ) AS uuid),
|
||||||
ADD CONSTRAINT notifications_activity_id_fkey FOREIGN KEY (activity_id) REFERENCES activities(id) ON DELETE CASCADE;
|
ADD CONSTRAINT notifications_activity_id_fkey FOREIGN KEY (activity_id) REFERENCES activities(id) ON DELETE CASCADE;
|
||||||
"""
|
""")
|
||||||
|
|
||||||
for table <- ~w(notifications filters lists oauth_authorizations oauth_tokens password_reset_tokens push_subscriptions websub_client_subscriptions) do
|
for table <-
|
||||||
execute """
|
~w(notifications filters lists oauth_authorizations oauth_tokens password_reset_tokens push_subscriptions websub_client_subscriptions) do
|
||||||
|
execute("""
|
||||||
ALTER TABLE #{table}
|
ALTER TABLE #{table}
|
||||||
ALTER COLUMN user_id SET DATA TYPE uuid USING CAST( LPAD( TO_HEX(user_id), 32, '0' ) AS uuid),
|
ALTER COLUMN user_id SET DATA TYPE uuid USING CAST( LPAD( TO_HEX(user_id), 32, '0' ) AS uuid),
|
||||||
ADD CONSTRAINT #{table}_user_id_fkey FOREIGN KEY (user_id) REFERENCES users(id) ON DELETE CASCADE;
|
ADD CONSTRAINT #{table}_user_id_fkey FOREIGN KEY (user_id) REFERENCES users(id) ON DELETE CASCADE;
|
||||||
"""
|
""")
|
||||||
end
|
end
|
||||||
|
|
||||||
flush()
|
flush()
|
||||||
|
@ -78,41 +81,50 @@ def up do
|
||||||
def down, do: :ok
|
def down, do: :ok
|
||||||
|
|
||||||
defp start_clippy_heartbeats() do
|
defp start_clippy_heartbeats() do
|
||||||
count = from(a in "activities", select: count(a.id)) |> Repo.one!
|
count = from(a in "activities", select: count(a.id)) |> Repo.one!()
|
||||||
|
|
||||||
if count > 5000 do
|
if count > 5000 do
|
||||||
heartbeat_interval = :timer.minutes(2) + :timer.seconds(30)
|
heartbeat_interval = :timer.minutes(2) + :timer.seconds(30)
|
||||||
all_tips = Clippy.tips() ++ [
|
|
||||||
"The migration is still running, maybe it's time for another “tea”?",
|
|
||||||
"Happy rabbits practice a cute behavior known as a\n“binky:” they jump up in the air\nand twist\nand spin around!",
|
|
||||||
"Nothing and everything.\n\nI still work.",
|
|
||||||
"Pleroma runs on a Raspberry Pi!\n\n … but this migration will take forever if you\nactually run on a raspberry pi",
|
|
||||||
"Status? Stati? Post? Note? Toot?\nRepeat? Reboost? Boost? Retweet? Retoot??\n\nI-I'm confused.",
|
|
||||||
]
|
|
||||||
|
|
||||||
heartbeat = fn(heartbeat, runs, all_tips, tips) ->
|
all_tips =
|
||||||
tips = if Integer.is_even(runs) do
|
Clippy.tips() ++
|
||||||
tips = if tips == [], do: all_tips, else: tips
|
[
|
||||||
[tip | tips] = Enum.shuffle(tips)
|
"The migration is still running, maybe it's time for another “tea”?",
|
||||||
Clippy.puts(tip)
|
"Happy rabbits practice a cute behavior known as a\n“binky:” they jump up in the air\nand twist\nand spin around!",
|
||||||
tips
|
"Nothing and everything.\n\nI still work.",
|
||||||
else
|
"Pleroma runs on a Raspberry Pi!\n\n … but this migration will take forever if you\nactually run on a raspberry pi",
|
||||||
IO.puts "\n -- #{DateTime.to_string(DateTime.utc_now())} Migration still running, please wait…\n"
|
"Status? Stati? Post? Note? Toot?\nRepeat? Reboost? Boost? Retweet? Retoot??\n\nI-I'm confused."
|
||||||
tips
|
]
|
||||||
end
|
|
||||||
|
heartbeat = fn heartbeat, runs, all_tips, tips ->
|
||||||
|
tips =
|
||||||
|
if Integer.is_even(runs) do
|
||||||
|
tips = if tips == [], do: all_tips, else: tips
|
||||||
|
[tip | tips] = Enum.shuffle(tips)
|
||||||
|
Clippy.puts(tip)
|
||||||
|
tips
|
||||||
|
else
|
||||||
|
IO.puts(
|
||||||
|
"\n -- #{DateTime.to_string(DateTime.utc_now())} Migration still running, please wait…\n"
|
||||||
|
)
|
||||||
|
|
||||||
|
tips
|
||||||
|
end
|
||||||
|
|
||||||
:timer.sleep(heartbeat_interval)
|
:timer.sleep(heartbeat_interval)
|
||||||
heartbeat.(heartbeat, runs + 1, all_tips, tips)
|
heartbeat.(heartbeat, runs + 1, all_tips, tips)
|
||||||
end
|
end
|
||||||
|
|
||||||
Clippy.puts [
|
Clippy.puts([
|
||||||
[:red, :bright, "It looks like you are running an older instance!"],
|
[:red, :bright, "It looks like you are running an older instance!"],
|
||||||
[""],
|
[""],
|
||||||
[:bright, "This migration may take a long time", :reset, " -- so you probably should"],
|
[:bright, "This migration may take a long time", :reset, " -- so you probably should"],
|
||||||
["go drink a cofe, or a tea, or a beer, a whiskey, a vodka,"],
|
["go drink a cofe, or a tea, or a beer, a whiskey, a vodka,"],
|
||||||
["while it runs to deal with your temporary fediverse pause!"]
|
["while it runs to deal with your temporary fediverse pause!"]
|
||||||
]
|
])
|
||||||
|
|
||||||
:timer.sleep(heartbeat_interval)
|
:timer.sleep(heartbeat_interval)
|
||||||
spawn_link(fn() -> heartbeat.(heartbeat, 1, all_tips, []) end)
|
spawn_link(fn -> heartbeat.(heartbeat, 1, all_tips, []) end)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@ -120,8 +132,7 @@ defp stop_clippy_heartbeats(pid) do
|
||||||
if pid do
|
if pid do
|
||||||
Process.unlink(pid)
|
Process.unlink(pid)
|
||||||
Process.exit(pid, :kill)
|
Process.exit(pid, :kill)
|
||||||
Clippy.puts [[:green, :bright, "Hurray!!", "", "", "Migration completed!"]]
|
Clippy.puts([[:green, :bright, "Hurray!!", "", "", "Migration completed!"]])
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
end
|
end
|
||||||
|
|
|
@ -43,6 +43,8 @@ def down do
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
|
|
||||||
execute("drop function if exists activity_visibility(actor varchar, recipients varchar[], data jsonb)")
|
execute(
|
||||||
|
"drop function if exists activity_visibility(actor varchar, recipients varchar[], data jsonb)"
|
||||||
|
)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -2,16 +2,18 @@ defmodule Pleroma.Repo.Migrations.CreateUserFtsIndex do
|
||||||
use Ecto.Migration
|
use Ecto.Migration
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
create_if_not_exists index(
|
create_if_not_exists(
|
||||||
:users,
|
index(
|
||||||
[
|
:users,
|
||||||
"""
|
[
|
||||||
(setweight(to_tsvector('simple', regexp_replace(nickname, '\\W', ' ', 'g')), 'A') ||
|
"""
|
||||||
setweight(to_tsvector('simple', regexp_replace(coalesce(name, ''), '\\W', ' ', 'g')), 'B'))
|
(setweight(to_tsvector('simple', regexp_replace(nickname, '\\W', ' ', 'g')), 'A') ||
|
||||||
"""
|
setweight(to_tsvector('simple', regexp_replace(coalesce(name, ''), '\\W', ' ', 'g')), 'B'))
|
||||||
],
|
"""
|
||||||
name: :users_fts_index,
|
],
|
||||||
using: :gin
|
name: :users_fts_index,
|
||||||
)
|
using: :gin
|
||||||
|
)
|
||||||
|
)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -27,10 +27,8 @@ def up do
|
||||||
"""
|
"""
|
||||||
|
|
||||||
execute(definition)
|
execute(definition)
|
||||||
|
|
||||||
end
|
end
|
||||||
|
|
||||||
def down do
|
def down do
|
||||||
|
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -2,6 +2,8 @@ defmodule Pleroma.Repo.Migrations.UsersAddIsAdminIndex do
|
||||||
use Ecto.Migration
|
use Ecto.Migration
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
create_if_not_exists(index(:users, ["(info->'is_admin')"], name: :users_is_admin_index, using: :gin))
|
create_if_not_exists(
|
||||||
|
index(:users, ["(info->'is_admin')"], name: :users_is_admin_index, using: :gin)
|
||||||
|
)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -3,13 +3,13 @@ defmodule Pleroma.Repo.Migrations.CreateInstances do
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
create_if_not_exists table(:instances) do
|
create_if_not_exists table(:instances) do
|
||||||
add :host, :string
|
add(:host, :string)
|
||||||
add :unreachable_since, :naive_datetime_usec
|
add(:unreachable_since, :naive_datetime_usec)
|
||||||
|
|
||||||
timestamps()
|
timestamps()
|
||||||
end
|
end
|
||||||
|
|
||||||
create_if_not_exists unique_index(:instances, [:host])
|
create_if_not_exists(unique_index(:instances, [:host]))
|
||||||
create_if_not_exists index(:instances, [:unreachable_since])
|
create_if_not_exists(index(:instances, [:unreachable_since]))
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -27,11 +27,8 @@ def up do
|
||||||
"""
|
"""
|
||||||
|
|
||||||
execute(definition)
|
execute(definition)
|
||||||
|
|
||||||
end
|
end
|
||||||
|
|
||||||
def down do
|
def down do
|
||||||
|
|
||||||
end
|
end
|
||||||
|
|
||||||
end
|
end
|
||||||
|
|
|
@ -3,6 +3,12 @@ defmodule Pleroma.Repo.Migrations.AddActivitiesLikesIndex do
|
||||||
@disable_ddl_transaction true
|
@disable_ddl_transaction true
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
create index(:activities, ["((data #> '{\"object\",\"likes\"}'))"], concurrently: true, name: :activities_likes, using: :gin)
|
create(
|
||||||
|
index(:activities, ["((data #> '{\"object\",\"likes\"}'))"],
|
||||||
|
concurrently: true,
|
||||||
|
name: :activities_likes,
|
||||||
|
using: :gin
|
||||||
|
)
|
||||||
|
)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -2,9 +2,17 @@ defmodule Pleroma.Repo.Migrations.SplitHideNetwork do
|
||||||
use Ecto.Migration
|
use Ecto.Migration
|
||||||
|
|
||||||
def up do
|
def up do
|
||||||
execute("UPDATE users SET info = jsonb_set(info, '{hide_network}'::text[], 'false'::jsonb) WHERE NOT(info::jsonb ? 'hide_network') AND local")
|
execute(
|
||||||
execute("UPDATE users SET info = jsonb_set(info, '{hide_followings}'::text[], info->'hide_network') WHERE local")
|
"UPDATE users SET info = jsonb_set(info, '{hide_network}'::text[], 'false'::jsonb) WHERE NOT(info::jsonb ? 'hide_network') AND local"
|
||||||
execute("UPDATE users SET info = jsonb_set(info, '{hide_followers}'::text[], info->'hide_network') WHERE local")
|
)
|
||||||
|
|
||||||
|
execute(
|
||||||
|
"UPDATE users SET info = jsonb_set(info, '{hide_followings}'::text[], info->'hide_network') WHERE local"
|
||||||
|
)
|
||||||
|
|
||||||
|
execute(
|
||||||
|
"UPDATE users SET info = jsonb_set(info, '{hide_followers}'::text[], info->'hide_network') WHERE local"
|
||||||
|
)
|
||||||
end
|
end
|
||||||
|
|
||||||
def down do
|
def down do
|
||||||
|
|
|
@ -3,10 +3,10 @@ defmodule Pleroma.Repo.Migrations.CreateThreadMutes do
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
create_if_not_exists table(:thread_mutes) do
|
create_if_not_exists table(:thread_mutes) do
|
||||||
add :user_id, references(:users, type: :uuid, on_delete: :delete_all)
|
add(:user_id, references(:users, type: :uuid, on_delete: :delete_all))
|
||||||
add :context, :string
|
add(:context, :string)
|
||||||
end
|
end
|
||||||
|
|
||||||
create_if_not_exists unique_index(:thread_mutes, [:user_id, :context], name: :unique_index)
|
create_if_not_exists(unique_index(:thread_mutes, [:user_id, :context], name: :unique_index))
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -4,7 +4,7 @@ defmodule Pleroma.Repo.Migrations.AddScopeSToOAuthEntities do
|
||||||
def change do
|
def change do
|
||||||
for t <- [:oauth_authorizations, :oauth_tokens] do
|
for t <- [:oauth_authorizations, :oauth_tokens] do
|
||||||
alter table(t) do
|
alter table(t) do
|
||||||
add :scopes, {:array, :string}, default: [], null: false
|
add(:scopes, {:array, :string}, default: [], null: false)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -4,14 +4,20 @@ defmodule Pleroma.Repo.Migrations.ChangeAppsScopesToVarcharArray do
|
||||||
@alter_apps_scopes "ALTER TABLE apps ALTER COLUMN scopes"
|
@alter_apps_scopes "ALTER TABLE apps ALTER COLUMN scopes"
|
||||||
|
|
||||||
def up do
|
def up do
|
||||||
execute "#{@alter_apps_scopes} TYPE varchar(255)[] USING string_to_array(scopes, ',')::varchar(255)[];"
|
execute(
|
||||||
execute "#{@alter_apps_scopes} SET DEFAULT ARRAY[]::character varying[];"
|
"#{@alter_apps_scopes} TYPE varchar(255)[] USING string_to_array(scopes, ',')::varchar(255)[];"
|
||||||
execute "#{@alter_apps_scopes} SET NOT NULL;"
|
)
|
||||||
|
|
||||||
|
execute("#{@alter_apps_scopes} SET DEFAULT ARRAY[]::character varying[];")
|
||||||
|
execute("#{@alter_apps_scopes} SET NOT NULL;")
|
||||||
end
|
end
|
||||||
|
|
||||||
def down do
|
def down do
|
||||||
execute "#{@alter_apps_scopes} DROP NOT NULL;"
|
execute("#{@alter_apps_scopes} DROP NOT NULL;")
|
||||||
execute "#{@alter_apps_scopes} DROP DEFAULT;"
|
execute("#{@alter_apps_scopes} DROP DEFAULT;")
|
||||||
execute "#{@alter_apps_scopes} TYPE varchar(255) USING array_to_string(scopes, ',')::varchar(255);"
|
|
||||||
|
execute(
|
||||||
|
"#{@alter_apps_scopes} TYPE varchar(255) USING array_to_string(scopes, ',')::varchar(255);"
|
||||||
|
)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -3,7 +3,7 @@ defmodule Pleroma.Repo.Migrations.DataMigrationPopulateOAuthScopes do
|
||||||
|
|
||||||
def up do
|
def up do
|
||||||
for t <- [:oauth_authorizations, :oauth_tokens] do
|
for t <- [:oauth_authorizations, :oauth_tokens] do
|
||||||
execute "UPDATE #{t} SET scopes = apps.scopes FROM apps WHERE #{t}.app_id = apps.id;"
|
execute("UPDATE #{t} SET scopes = apps.scopes FROM apps WHERE #{t}.app_id = apps.id;")
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|
|
@ -3,7 +3,7 @@ defmodule Pleroma.Repo.Migrations.DataMigrationNormalizeScopes do
|
||||||
|
|
||||||
def up do
|
def up do
|
||||||
for t <- [:apps, :oauth_authorizations, :oauth_tokens] do
|
for t <- [:apps, :oauth_authorizations, :oauth_tokens] do
|
||||||
execute "UPDATE #{t} SET scopes = string_to_array(array_to_string(scopes, ' '), ' ');"
|
execute("UPDATE #{t} SET scopes = string_to_array(array_to_string(scopes, ' '), ' ');")
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|
|
@ -2,7 +2,7 @@ defmodule Pleroma.Repo.Migrations.AddDefaultTagsToUser do
|
||||||
use Ecto.Migration
|
use Ecto.Migration
|
||||||
|
|
||||||
def up do
|
def up do
|
||||||
execute "UPDATE users SET tags = array[]::varchar[] where tags IS NULL"
|
execute("UPDATE users SET tags = array[]::varchar[] where tags IS NULL")
|
||||||
end
|
end
|
||||||
|
|
||||||
def down, do: :noop
|
def down, do: :noop
|
||||||
|
|
|
@ -4,7 +4,7 @@ defmodule Pleroma.Repo.Migrations.UpdateUserNoteCounters do
|
||||||
@public "https://www.w3.org/ns/activitystreams#Public"
|
@public "https://www.w3.org/ns/activitystreams#Public"
|
||||||
|
|
||||||
def up do
|
def up do
|
||||||
execute """
|
execute("""
|
||||||
WITH public_note_count AS (
|
WITH public_note_count AS (
|
||||||
SELECT
|
SELECT
|
||||||
data->>'actor' AS actor,
|
data->>'actor' AS actor,
|
||||||
|
@ -19,11 +19,11 @@ def up do
|
||||||
SET "info" = jsonb_set(u.info, '{note_count}', o.count::varchar::jsonb, true)
|
SET "info" = jsonb_set(u.info, '{note_count}', o.count::varchar::jsonb, true)
|
||||||
FROM public_note_count AS o
|
FROM public_note_count AS o
|
||||||
WHERE u.ap_id = o.actor
|
WHERE u.ap_id = o.actor
|
||||||
"""
|
""")
|
||||||
end
|
end
|
||||||
|
|
||||||
def down do
|
def down do
|
||||||
execute """
|
execute("""
|
||||||
WITH public_note_count AS (
|
WITH public_note_count AS (
|
||||||
SELECT
|
SELECT
|
||||||
data->>'actor' AS actor,
|
data->>'actor' AS actor,
|
||||||
|
@ -36,6 +36,6 @@ def down do
|
||||||
SET "info" = jsonb_set(u.info, '{note_count}', o.count::varchar::jsonb, true)
|
SET "info" = jsonb_set(u.info, '{note_count}', o.count::varchar::jsonb, true)
|
||||||
FROM public_note_count AS o
|
FROM public_note_count AS o
|
||||||
WHERE u.ap_id = o.actor
|
WHERE u.ap_id = o.actor
|
||||||
"""
|
""")
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -3,16 +3,16 @@ defmodule Pleroma.Repo.Migrations.CreateRegistrations do
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
create_if_not_exists table(:registrations, primary_key: false) do
|
create_if_not_exists table(:registrations, primary_key: false) do
|
||||||
add :id, :uuid, primary_key: true
|
add(:id, :uuid, primary_key: true)
|
||||||
add :user_id, references(:users, type: :uuid, on_delete: :delete_all)
|
add(:user_id, references(:users, type: :uuid, on_delete: :delete_all))
|
||||||
add :provider, :string
|
add(:provider, :string)
|
||||||
add :uid, :string
|
add(:uid, :string)
|
||||||
add :info, :map, default: %{}
|
add(:info, :map, default: %{})
|
||||||
|
|
||||||
timestamps()
|
timestamps()
|
||||||
end
|
end
|
||||||
|
|
||||||
create_if_not_exists unique_index(:registrations, [:provider, :uid])
|
create_if_not_exists(unique_index(:registrations, [:provider, :uid]))
|
||||||
create_if_not_exists unique_index(:registrations, [:user_id, :provider, :uid])
|
create_if_not_exists(unique_index(:registrations, [:user_id, :provider, :uid]))
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -2,6 +2,6 @@ defmodule Pleroma.Repo.Migrations.CreateNotificationIdIndex do
|
||||||
use Ecto.Migration
|
use Ecto.Migration
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
create_if_not_exists index(:notifications, ["id desc nulls last"])
|
create_if_not_exists(index(:notifications, ["id desc nulls last"]))
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -3,6 +3,12 @@ defmodule Pleroma.Repo.Migrations.AddIndexOnSubscribers do
|
||||||
|
|
||||||
@disable_ddl_transaction true
|
@disable_ddl_transaction true
|
||||||
def change do
|
def change do
|
||||||
create index(:users, ["(info->'subscribers')"], name: :users_subscribers_index, using: :gin, concurrently: true)
|
create(
|
||||||
|
index(:users, ["(info->'subscribers')"],
|
||||||
|
name: :users_subscribers_index,
|
||||||
|
using: :gin,
|
||||||
|
concurrently: true
|
||||||
|
)
|
||||||
|
)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -19,8 +19,8 @@ def change do
|
||||||
timestamps()
|
timestamps()
|
||||||
end
|
end
|
||||||
|
|
||||||
create_if_not_exists index(:conversation_participations, [:conversation_id])
|
create_if_not_exists(index(:conversation_participations, [:conversation_id]))
|
||||||
create_if_not_exists unique_index(:conversation_participations, [:user_id, :conversation_id])
|
create_if_not_exists(unique_index(:conversation_participations, [:user_id, :conversation_id]))
|
||||||
create_if_not_exists unique_index(:conversations, [:ap_id])
|
create_if_not_exists(unique_index(:conversations, [:ap_id]))
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -2,6 +2,6 @@ defmodule Pleroma.Repo.Migrations.AddParticipationUpdatedAtIndex do
|
||||||
use Ecto.Migration
|
use Ecto.Migration
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
create_if_not_exists index(:conversation_participations, ["updated_at desc"])
|
create_if_not_exists(index(:conversation_participations, ["updated_at desc"]))
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -2,6 +2,8 @@ defmodule Pleroma.Repo.Migrations.AddIndexOnUserInfoDeactivated do
|
||||||
use Ecto.Migration
|
use Ecto.Migration
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
create_if_not_exists(index(:users, ["(info->'deactivated')"], name: :users_deactivated_index, using: :gin))
|
create_if_not_exists(
|
||||||
|
index(:users, ["(info->'deactivated')"], name: :users_deactivated_index, using: :gin)
|
||||||
|
)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -18,7 +18,7 @@ def up do
|
||||||
|> Enum.each(fn %{id: user_id, bookmarks: bookmarks} ->
|
|> Enum.each(fn %{id: user_id, bookmarks: bookmarks} ->
|
||||||
Enum.each(bookmarks, fn ap_id ->
|
Enum.each(bookmarks, fn ap_id ->
|
||||||
activity = Activity.get_create_by_object_ap_id(ap_id)
|
activity = Activity.get_create_by_object_ap_id(ap_id)
|
||||||
unless is_nil(activity), do: {:ok, _} = Bookmark.create(user_id, activity.id)
|
unless is_nil(activity), do: {:ok, _} = Bookmark.create(user_id, activity.id)
|
||||||
end)
|
end)
|
||||||
end)
|
end)
|
||||||
|
|
||||||
|
@ -29,7 +29,7 @@ def up do
|
||||||
|
|
||||||
def down do
|
def down do
|
||||||
alter table(:users) do
|
alter table(:users) do
|
||||||
add :bookmarks, {:array, :string}, null: false, default: []
|
add(:bookmarks, {:array, :string}, null: false, default: [])
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -2,7 +2,18 @@ defmodule Pleroma.Repo.Migrations.AddFTSIndexToObjects do
|
||||||
use Ecto.Migration
|
use Ecto.Migration
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
drop_if_exists index(:activities, ["(to_tsvector('english', data->'object'->>'content'))"], using: :gin, name: :activities_fts)
|
drop_if_exists(
|
||||||
create_if_not_exists index(:objects, ["(to_tsvector('english', data->>'content'))"], using: :gin, name: :objects_fts)
|
index(:activities, ["(to_tsvector('english', data->'object'->>'content'))"],
|
||||||
|
using: :gin,
|
||||||
|
name: :activities_fts
|
||||||
|
)
|
||||||
|
)
|
||||||
|
|
||||||
|
create_if_not_exists(
|
||||||
|
index(:objects, ["(to_tsvector('english', data->>'content'))"],
|
||||||
|
using: :gin,
|
||||||
|
name: :objects_fts
|
||||||
|
)
|
||||||
|
)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -2,18 +2,18 @@ defmodule Pleroma.Repo.Migrations.SetDefaultStateToReports do
|
||||||
use Ecto.Migration
|
use Ecto.Migration
|
||||||
|
|
||||||
def up do
|
def up do
|
||||||
execute """
|
execute("""
|
||||||
UPDATE activities AS a
|
UPDATE activities AS a
|
||||||
SET data = jsonb_set(data, '{state}', '"open"', true)
|
SET data = jsonb_set(data, '{state}', '"open"', true)
|
||||||
WHERE data->>'type' = 'Flag'
|
WHERE data->>'type' = 'Flag'
|
||||||
"""
|
""")
|
||||||
end
|
end
|
||||||
|
|
||||||
def down do
|
def down do
|
||||||
execute """
|
execute("""
|
||||||
UPDATE activities AS a
|
UPDATE activities AS a
|
||||||
SET data = data #- '{state}'
|
SET data = data #- '{state}'
|
||||||
WHERE data->>'type' = 'Flag'
|
WHERE data->>'type' = 'Flag'
|
||||||
"""
|
""")
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -3,13 +3,13 @@ defmodule Pleroma.Repo.Migrations.ChangeHideColumnInFilterTable do
|
||||||
|
|
||||||
def up do
|
def up do
|
||||||
alter table(:filters) do
|
alter table(:filters) do
|
||||||
modify :hide, :boolean, default: false
|
modify(:hide, :boolean, default: false)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
def down do
|
def down do
|
||||||
alter table(:filters) do
|
alter table(:filters) do
|
||||||
modify :hide, :boolean
|
modify(:hide, :boolean)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -2,6 +2,6 @@ defmodule Pleroma.Repo.Migrations.AddObjectInReplyToIndex do
|
||||||
use Ecto.Migration
|
use Ecto.Migration
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
create index(:objects, ["(data->>'inReplyTo')"], name: :objects_in_reply_to_index)
|
create(index(:objects, ["(data->>'inReplyTo')"], name: :objects_in_reply_to_index))
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -2,7 +2,10 @@ defmodule Pleroma.Repo.Migrations.AddTagIndexToObjects do
|
||||||
use Ecto.Migration
|
use Ecto.Migration
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
drop_if_exists index(:activities, ["(data #> '{\"object\",\"tag\"}')"], using: :gin, name: :activities_tags)
|
drop_if_exists(
|
||||||
create_if_not_exists index(:objects, ["(data->'tag')"], using: :gin, name: :objects_tags)
|
index(:activities, ["(data #> '{\"object\",\"tag\"}')"], using: :gin, name: :activities_tags)
|
||||||
|
)
|
||||||
|
|
||||||
|
create_if_not_exists(index(:objects, ["(data->'tag')"], using: :gin, name: :objects_tags))
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -3,6 +3,8 @@ defmodule Pleroma.Repo.Migrations.CopyMutedToMutedNotifications do
|
||||||
alias Pleroma.User
|
alias Pleroma.User
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
execute("update users set info = jsonb_set(info, '{muted_notifications}', info->'mutes', true) where local = true")
|
execute(
|
||||||
|
"update users set info = jsonb_set(info, '{muted_notifications}', info->'mutes', true) where local = true"
|
||||||
|
)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -7,7 +7,7 @@ def change do
|
||||||
add(:participation_id, references(:conversation_participations, on_delete: :delete_all))
|
add(:participation_id, references(:conversation_participations, on_delete: :delete_all))
|
||||||
end
|
end
|
||||||
|
|
||||||
create_if_not_exists index(:conversation_participation_recipient_ships, [:user_id])
|
create_if_not_exists(index(:conversation_participation_recipient_ships, [:user_id]))
|
||||||
create_if_not_exists index(:conversation_participation_recipient_ships, [:participation_id])
|
create_if_not_exists(index(:conversation_participation_recipient_ships, [:participation_id]))
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -2,6 +2,6 @@ defmodule Pleroma.Repo.Migrations.AddLikesIndexToObjects do
|
||||||
use Ecto.Migration
|
use Ecto.Migration
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
create_if_not_exists index(:objects, ["(data->'likes')"], using: :gin, name: :objects_likes)
|
create_if_not_exists(index(:objects, ["(data->'likes')"], using: :gin, name: :objects_likes))
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -6,7 +6,8 @@ def change do
|
||||||
add(:object_id, references(:objects, type: :id), null: false)
|
add(:object_id, references(:objects, type: :id), null: false)
|
||||||
add(:user_id, references(:users, type: :uuid, on_delete: :delete_all), null: false)
|
add(:user_id, references(:users, type: :uuid, on_delete: :delete_all), null: false)
|
||||||
end
|
end
|
||||||
create_if_not_exists index(:deliveries, :object_id, name: :deliveries_object_id)
|
|
||||||
|
create_if_not_exists(index(:deliveries, :object_id, name: :deliveries_object_id))
|
||||||
create_if_not_exists(unique_index(:deliveries, [:user_id, :object_id]))
|
create_if_not_exists(unique_index(:deliveries, [:user_id, :object_id]))
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -2,7 +2,6 @@ defmodule Pleroma.Repo.Migrations.DropSubscriptionIfExists do
|
||||||
use Ecto.Migration
|
use Ecto.Migration
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
|
|
||||||
end
|
end
|
||||||
|
|
||||||
def up do
|
def up do
|
||||||
|
@ -10,6 +9,7 @@ def up do
|
||||||
drop_if_exists(index(:subscription_notifications, ["id desc nulls last"]))
|
drop_if_exists(index(:subscription_notifications, ["id desc nulls last"]))
|
||||||
drop_if_exists(table(:subscription_notifications))
|
drop_if_exists(table(:subscription_notifications))
|
||||||
end
|
end
|
||||||
|
|
||||||
def down do
|
def down do
|
||||||
:ok
|
:ok
|
||||||
end
|
end
|
||||||
|
|
|
@ -3,7 +3,7 @@ defmodule Pleroma.Repo.Migrations.AddKeysColumn do
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
alter table("users") do
|
alter table("users") do
|
||||||
add_if_not_exists :keys, :text
|
add_if_not_exists(:keys, :text)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -2,6 +2,9 @@ defmodule Pleroma.Repo.Migrations.MoveKeysToSeparateColumn do
|
||||||
use Ecto.Migration
|
use Ecto.Migration
|
||||||
|
|
||||||
def change do
|
def change do
|
||||||
execute("update users set keys = info->>'keys' where local", "update users set info = jsonb_set(info, '{keys}'::text[], to_jsonb(keys)) where local")
|
execute(
|
||||||
|
"update users set keys = info->>'keys' where local",
|
||||||
|
"update users set info = jsonb_set(info, '{keys}'::text[], to_jsonb(keys)) where local"
|
||||||
|
)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -37,29 +37,60 @@ detect_branch() {
|
||||||
elif [ "$branch" = "" ]; then
|
elif [ "$branch" = "" ]; then
|
||||||
echo "master"
|
echo "master"
|
||||||
else
|
else
|
||||||
# Note: branch name in version is of SemVer format and may only contain [0-9a-zA-Z-] symbols —
|
# Note: branch name in version is of SemVer format and may only contain [0-9a-zA-Z-] symbols —
|
||||||
# if supporting releases for more branches, need to ensure they contain only these symbols.
|
# if supporting releases for more branches, need to ensure they contain only these symbols.
|
||||||
echo "Releases are built only for master and develop branches" >&2
|
echo "Releases are built only for master and develop branches" >&2
|
||||||
exit 1
|
exit 1
|
||||||
fi
|
fi
|
||||||
}
|
}
|
||||||
update() {
|
update() {
|
||||||
set -e
|
set -e
|
||||||
|
NO_RM=false
|
||||||
|
|
||||||
|
while echo "$1" | grep "^-" >/dev/null; do
|
||||||
|
case "$1" in
|
||||||
|
--zip-url)
|
||||||
|
FULL_URI="$2"
|
||||||
|
shift 2
|
||||||
|
;;
|
||||||
|
--no-rm)
|
||||||
|
NO_RM=true
|
||||||
|
shift
|
||||||
|
;;
|
||||||
|
--flavour)
|
||||||
|
FLAVOUR="$2"
|
||||||
|
shift 2
|
||||||
|
;;
|
||||||
|
--branch)
|
||||||
|
BRANCH="$2"
|
||||||
|
shift 2
|
||||||
|
;;
|
||||||
|
--tmp-dir)
|
||||||
|
TMP_DIR="$2"
|
||||||
|
shift 2
|
||||||
|
;;
|
||||||
|
-*)
|
||||||
|
echo "invalid option: $1" 1>&2
|
||||||
|
shift
|
||||||
|
;;
|
||||||
|
esac
|
||||||
|
done
|
||||||
|
|
||||||
RELEASE_ROOT=$(dirname "$SCRIPTPATH")
|
RELEASE_ROOT=$(dirname "$SCRIPTPATH")
|
||||||
uri="${PLEROMA_CTL_URI:-https://git.pleroma.social}"
|
uri="https://git.pleroma.social"
|
||||||
project_id="${PLEROMA_CTL_PROJECT_ID:-2}"
|
project_id="2"
|
||||||
project_branch="$(detect_branch)"
|
project_branch="${BRANCH:-$(detect_branch)}"
|
||||||
flavour="${PLEROMA_CTL_FLAVOUR:-$(detect_flavour)}"
|
flavour="${FLAVOUR:-$(detect_flavour)}"
|
||||||
echo "Detected flavour: $flavour"
|
tmp="${TMP_DIR:-/tmp}"
|
||||||
tmp="${PLEROMA_CTL_TMP_DIR:-/tmp}"
|
|
||||||
artifact="$tmp/pleroma.zip"
|
artifact="$tmp/pleroma.zip"
|
||||||
full_uri="${uri}/api/v4/projects/${project_id}/jobs/artifacts/${project_branch}/download?job=${flavour}"
|
full_uri="${FULL_URI:-${uri}/api/v4/projects/${project_id}/jobs/artifacts/${project_branch}/download?job=${flavour}}"
|
||||||
echo "Downloading the artifact from ${full_uri} to ${artifact}"
|
echo "Downloading the artifact from ${full_uri} to ${artifact}"
|
||||||
curl "$full_uri" -o "${artifact}"
|
curl "$full_uri" -o "${artifact}"
|
||||||
echo "Unpacking ${artifact} to ${tmp}"
|
echo "Unpacking ${artifact} to ${tmp}"
|
||||||
unzip -q "$artifact" -d "$tmp"
|
unzip -q "$artifact" -d "$tmp"
|
||||||
echo "Copying files over to $RELEASE_ROOT"
|
echo "Copying files over to $RELEASE_ROOT"
|
||||||
if [ "$1" != "--no-rm" ]; then
|
if [ "$NO_RM" = false ]; then
|
||||||
|
echo "Removing files from the previous release"
|
||||||
rm -r "${RELEASE_ROOT:-?}"/*
|
rm -r "${RELEASE_ROOT:-?}"/*
|
||||||
fi
|
fi
|
||||||
cp -rf "$tmp/release"/* "$RELEASE_ROOT"
|
cp -rf "$tmp/release"/* "$RELEASE_ROOT"
|
||||||
|
@ -86,36 +117,41 @@ if [ -z "$1" ] || [ "$1" = "help" ]; then
|
||||||
Rollback database migrations (needs to be done before downgrading)
|
Rollback database migrations (needs to be done before downgrading)
|
||||||
|
|
||||||
update [OPTIONS]
|
update [OPTIONS]
|
||||||
Update the instance using the latest CI artifact for the current branch.
|
Update the instance.
|
||||||
|
|
||||||
The only supported option is --no-rm, when set the script won't delete the whole directory, but
|
|
||||||
just force copy over files from the new release. This wastes more space, but may be useful if
|
|
||||||
some files are stored inside of the release directories (although you really shouldn't store them
|
|
||||||
there), or if you want to be able to quickly revert a broken update.
|
|
||||||
|
|
||||||
The script will try to detect your architecture and ABI and set a flavour automatically,
|
|
||||||
but if it is wrong, you can overwrite it by setting PLEROMA_CTL_FLAVOUR to the desired flavour.
|
|
||||||
|
|
||||||
By default the artifact will be downloaded from https://git.pleroma.social for pleroma/pleroma (project id: 2)
|
|
||||||
to /tmp/, you can overwrite these settings by setting PLEROMA_CTL_URI, PLEROMA_CTL_PROJECT_ID and PLEROMA_CTL_TMP_DIR
|
|
||||||
respectively.
|
|
||||||
|
|
||||||
|
Options:
|
||||||
|
--branch Update to a specified branch, instead of the latest version of the current one.
|
||||||
|
--flavour Update to a specified flavour (CPU architecture+libc), instead of the current one.
|
||||||
|
--zip-url Get the release from a specified url. If set, renders the previous 2 options inactive.
|
||||||
|
--no-rm Do not erase previous release's files.
|
||||||
|
--tmp-dir Download the temporary files to a specified directory.
|
||||||
|
|
||||||
and any mix tasks under Pleroma namespace, for example \`mix pleroma.user COMMAND\` is
|
and any mix tasks under Pleroma namespace, for example \`mix pleroma.user COMMAND\` is
|
||||||
equivalent to \`$(basename "$0") user COMMAND\`
|
equivalent to \`$(basename "$0") user COMMAND\`
|
||||||
|
|
||||||
By default pleroma_ctl will try calling into a running instance to execute non migration-related commands,
|
By default pleroma_ctl will try calling into a running instance to execute non migration-related commands,
|
||||||
if for some reason this is undesired, set PLEROMA_CTL_RPC_DISABLED environment variable
|
if for some reason this is undesired, set PLEROMA_CTL_RPC_DISABLED environment variable.
|
||||||
|
|
||||||
"
|
"
|
||||||
else
|
else
|
||||||
SCRIPT=$(readlink -f "$0")
|
SCRIPT=$(readlink -f "$0")
|
||||||
SCRIPTPATH=$(dirname "$SCRIPT")
|
SCRIPTPATH=$(dirname "$SCRIPT")
|
||||||
|
|
||||||
if [ "$1" = "update" ]; then
|
FULL_ARGS="$*"
|
||||||
update "$2"
|
|
||||||
elif [ "$1" = "migrate" ] || [ "$1" = "rollback" ] || [ "$1" = "create" ] || [ "$1 $2" = "instance gen" ] || [ -n "$PLEROMA_CTL_RPC_DISABLED" ]; then
|
ACTION="$1"
|
||||||
"$SCRIPTPATH"/pleroma eval 'Pleroma.ReleaseTasks.run("'"$*"'")'
|
shift
|
||||||
|
|
||||||
|
if [ "$(echo \"$1\" | grep \"^-\" >/dev/null)" = false ]; then
|
||||||
|
SUBACTION="$1"
|
||||||
|
shift
|
||||||
|
fi
|
||||||
|
|
||||||
|
if [ "$ACTION" = "update" ]; then
|
||||||
|
update "$@"
|
||||||
|
elif [ "$ACTION" = "migrate" ] || [ "$ACTION" = "rollback" ] || [ "$ACTION" = "create" ] || [ "$ACTION $SUBACTION" = "instance gen" ] || [ "$PLEROMA_CTL_RPC_DISABLED" = true ]; then
|
||||||
|
"$SCRIPTPATH"/pleroma eval 'Pleroma.ReleaseTasks.run("'"$FULL_ARGS"'")'
|
||||||
else
|
else
|
||||||
"$SCRIPTPATH"/pleroma rpc 'Pleroma.ReleaseTasks.run("'"$*"'")'
|
"$SCRIPTPATH"/pleroma rpc 'Pleroma.ReleaseTasks.run("'"$FULL_ARGS"'")'
|
||||||
fi
|
fi
|
||||||
fi
|
fi
|
||||||
|
|
|
@ -126,9 +126,25 @@ test "when association is not loaded" do
|
||||||
}
|
}
|
||||||
|
|
||||||
{:ok, local_activity} = Pleroma.Web.CommonAPI.post(user, %{"status" => "find me!"})
|
{:ok, local_activity} = Pleroma.Web.CommonAPI.post(user, %{"status" => "find me!"})
|
||||||
|
{:ok, japanese_activity} = Pleroma.Web.CommonAPI.post(user, %{"status" => "更新情報"})
|
||||||
{:ok, job} = Pleroma.Web.Federator.incoming_ap_doc(params)
|
{:ok, job} = Pleroma.Web.Federator.incoming_ap_doc(params)
|
||||||
{:ok, remote_activity} = ObanHelpers.perform(job)
|
{:ok, remote_activity} = ObanHelpers.perform(job)
|
||||||
%{local_activity: local_activity, remote_activity: remote_activity, user: user}
|
|
||||||
|
%{
|
||||||
|
japanese_activity: japanese_activity,
|
||||||
|
local_activity: local_activity,
|
||||||
|
remote_activity: remote_activity,
|
||||||
|
user: user
|
||||||
|
}
|
||||||
|
end
|
||||||
|
|
||||||
|
test "finds utf8 text in statuses", %{
|
||||||
|
japanese_activity: japanese_activity,
|
||||||
|
user: user
|
||||||
|
} do
|
||||||
|
activities = Activity.search(user, "更新情報")
|
||||||
|
|
||||||
|
assert [^japanese_activity] = activities
|
||||||
end
|
end
|
||||||
|
|
||||||
test "find local and remote statuses for authenticated users", %{
|
test "find local and remote statuses for authenticated users", %{
|
||||||
|
|
|
@ -0,0 +1,4 @@
|
||||||
|
<?xml version="1.0" encoding="UTF-8"?>
|
||||||
|
<XRD xmlns="http://docs.oasis-open.org/ns/xri/xrd-1.0">
|
||||||
|
<Link rel="lrdd" type="application/xrd+xml" template="https://mstdn.jp/.well-known/webfinger?resource={uri}"/>
|
||||||
|
</XRD>
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue