[#923] Merge remote-tracking branch 'remotes/upstream/develop' into twitter_oauth
# Conflicts: # mix.exs
This commit is contained in:
commit
590c935d95
|
@ -1,9 +1,5 @@
|
||||||
image: elixir:1.8.1
|
image: elixir:1.8.1
|
||||||
|
|
||||||
services:
|
|
||||||
- name: postgres:9.6.2
|
|
||||||
command: ["postgres", "-c", "fsync=off", "-c", "synchronous_commit=off", "-c", "full_page_writes=off"]
|
|
||||||
|
|
||||||
variables:
|
variables:
|
||||||
POSTGRES_DB: pleroma_test
|
POSTGRES_DB: pleroma_test
|
||||||
POSTGRES_USER: postgres
|
POSTGRES_USER: postgres
|
||||||
|
@ -17,58 +13,60 @@ cache:
|
||||||
- deps
|
- deps
|
||||||
- _build
|
- _build
|
||||||
stages:
|
stages:
|
||||||
- lint
|
- build
|
||||||
- test
|
- test
|
||||||
- analysis
|
- deploy
|
||||||
- docs_build
|
|
||||||
- docs_deploy
|
|
||||||
|
|
||||||
before_script:
|
before_script:
|
||||||
- mix local.hex --force
|
- mix local.hex --force
|
||||||
- mix local.rebar --force
|
- mix local.rebar --force
|
||||||
|
|
||||||
|
build:
|
||||||
|
stage: build
|
||||||
|
script:
|
||||||
- mix deps.get
|
- mix deps.get
|
||||||
- mix compile --force
|
- mix compile --force
|
||||||
- mix ecto.create
|
|
||||||
- mix ecto.migrate
|
|
||||||
|
|
||||||
lint:
|
docs-build:
|
||||||
stage: lint
|
stage: build
|
||||||
script:
|
|
||||||
- mix format --check-formatted
|
|
||||||
|
|
||||||
unit-testing:
|
|
||||||
stage: test
|
|
||||||
script:
|
|
||||||
- mix test --trace --preload-modules
|
|
||||||
|
|
||||||
analysis:
|
|
||||||
stage: analysis
|
|
||||||
script:
|
|
||||||
- mix credo --strict --only=warnings,todo,fixme,consistency,readability
|
|
||||||
|
|
||||||
docs_build:
|
|
||||||
stage: docs_build
|
|
||||||
services:
|
|
||||||
only:
|
only:
|
||||||
- master@pleroma/pleroma
|
- master@pleroma/pleroma
|
||||||
- develop@pleroma/pleroma
|
- develop@pleroma/pleroma
|
||||||
variables:
|
variables:
|
||||||
MIX_ENV: dev
|
MIX_ENV: dev
|
||||||
before_script:
|
script:
|
||||||
- mix local.hex --force
|
|
||||||
- mix local.rebar --force
|
|
||||||
- mix deps.get
|
- mix deps.get
|
||||||
- mix compile
|
- mix compile
|
||||||
script:
|
|
||||||
- mix docs
|
- mix docs
|
||||||
artifacts:
|
artifacts:
|
||||||
paths:
|
paths:
|
||||||
- priv/static/doc
|
- priv/static/doc
|
||||||
|
|
||||||
docs_deploy:
|
unit-testing:
|
||||||
stage: docs_deploy
|
stage: test
|
||||||
image: alpine:3.9
|
|
||||||
services:
|
services:
|
||||||
|
- name: postgres:9.6.2
|
||||||
|
command: ["postgres", "-c", "fsync=off", "-c", "synchronous_commit=off", "-c", "full_page_writes=off"]
|
||||||
|
script:
|
||||||
|
- mix ecto.create
|
||||||
|
- mix ecto.migrate
|
||||||
|
- mix test --trace --preload-modules
|
||||||
|
|
||||||
|
lint:
|
||||||
|
stage: test
|
||||||
|
script:
|
||||||
|
- mix format --check-formatted
|
||||||
|
|
||||||
|
analysis:
|
||||||
|
stage: test
|
||||||
|
script:
|
||||||
|
- mix deps.get
|
||||||
|
- mix credo --strict --only=warnings,todo,fixme,consistency,readability
|
||||||
|
|
||||||
|
|
||||||
|
docs-deploy:
|
||||||
|
stage: deploy
|
||||||
|
image: alpine:3.9
|
||||||
only:
|
only:
|
||||||
- master@pleroma/pleroma
|
- master@pleroma/pleroma
|
||||||
- develop@pleroma/pleroma
|
- develop@pleroma/pleroma
|
||||||
|
|
10
README.md
10
README.md
|
@ -1,14 +1,16 @@
|
||||||
# Pleroma
|
# Pleroma
|
||||||
|
|
||||||
|
**Note**: This readme as well as complete documentation is also availible at <https://docs-develop.pleroma.social>
|
||||||
|
|
||||||
## About Pleroma
|
## About Pleroma
|
||||||
|
|
||||||
Pleroma is a microblogging server software that can federate (= exchange messages with) other servers that support the same federation standards (OStatus and ActivityPub). What that means is that you can host a server for yourself or your friends and stay in control of your online identity, but still exchange messages with people on larger servers. Pleroma will federate with all servers that implement either OStatus or ActivityPub, like Friendica, GNU Social, Hubzilla, Mastodon, Misskey, Peertube, and Pixelfed.
|
Pleroma is a microblogging server software that can federate (= exchange messages with) other servers that support the same federation standards (OStatus and ActivityPub). What that means is that you can host a server for yourself or your friends and stay in control of your online identity, but still exchange messages with people on larger servers. Pleroma will federate with all servers that implement either OStatus or ActivityPub, like Friendica, GNU Social, Hubzilla, Mastodon, Misskey, Peertube, and Pixelfed.
|
||||||
|
|
||||||
Pleroma is written in Elixir, high-performance and can run on small devices like a Raspberry Pi.
|
Pleroma is written in Elixir, high-performance and can run on small devices like a Raspberry Pi.
|
||||||
|
|
||||||
For clients it supports both the [GNU Social API with Qvitter extensions](https://twitter-api.readthedocs.io/en/latest/index.html) and the [Mastodon client API](https://github.com/tootsuite/documentation/blob/master/Using-the-API/API.md).
|
For clients it supports both the [GNU Social API with Qvitter extensions](https://twitter-api.readthedocs.io/en/latest/index.html) and the [Mastodon client API](https://docs.joinmastodon.org/api/guidelines/).
|
||||||
|
|
||||||
- [Client Applications for Pleroma](docs/Clients.md)
|
- [Client Applications for Pleroma](https://docs-develop.pleroma.social/clients.html)
|
||||||
|
|
||||||
No release has been made yet, but several servers have been online for months already. If you want to run your own server, feel free to contact us at @lain@pleroma.soykaf.com or in our dev chat at #pleroma on freenode or via matrix at <https://matrix.heldscal.la/#/room/#freenode_#pleroma:matrix.org>.
|
No release has been made yet, but several servers have been online for months already. If you want to run your own server, feel free to contact us at @lain@pleroma.soykaf.com or in our dev chat at #pleroma on freenode or via matrix at <https://matrix.heldscal.la/#/room/#freenode_#pleroma:matrix.org>.
|
||||||
|
|
||||||
|
@ -28,7 +30,7 @@ While we don’t provide docker files, other people have written very good ones.
|
||||||
|
|
||||||
* Run `mix deps.get` to install elixir dependencies.
|
* Run `mix deps.get` to install elixir dependencies.
|
||||||
* Run `mix pleroma.instance gen`. This will ask you questions about your instance and generate a configuration file in `config/generated_config.exs`. Check that and copy it to either `config/dev.secret.exs` or `config/prod.secret.exs`. It will also create a `config/setup_db.psql`, which you should run as the PostgreSQL superuser (i.e., `sudo -u postgres psql -f config/setup_db.psql`). It will create the database, user, and password you gave `mix pleroma.gen.instance` earlier, as well as set up the necessary extensions in the database. PostgreSQL superuser privileges are only needed for this step.
|
* Run `mix pleroma.instance gen`. This will ask you questions about your instance and generate a configuration file in `config/generated_config.exs`. Check that and copy it to either `config/dev.secret.exs` or `config/prod.secret.exs`. It will also create a `config/setup_db.psql`, which you should run as the PostgreSQL superuser (i.e., `sudo -u postgres psql -f config/setup_db.psql`). It will create the database, user, and password you gave `mix pleroma.gen.instance` earlier, as well as set up the necessary extensions in the database. PostgreSQL superuser privileges are only needed for this step.
|
||||||
* For these next steps, the default will be to run pleroma using the dev configuration file, `config/dev.secret.exs`. To run them using the prod config file, prefix each command at the shell with `MIX_ENV=prod`. For example: `MIX_ENV=prod mix phx.server`. Documentation for the config can be found at [`docs/config.md`](docs/config.md) in the repository, or at the "Configuration" page on <https://docs.pleroma.social>
|
* For these next steps, the default will be to run pleroma using the dev configuration file, `config/dev.secret.exs`. To run them using the prod config file, prefix each command at the shell with `MIX_ENV=prod`. For example: `MIX_ENV=prod mix phx.server`. Documentation for the config can be found at [`docs/config.md`](docs/config.md) in the repository, or at the "Configuration" page on <https://docs-develop.pleroma.social/config.html>
|
||||||
* Run `mix ecto.migrate` to run the database migrations. You will have to do this again after certain updates.
|
* Run `mix ecto.migrate` to run the database migrations. You will have to do this again after certain updates.
|
||||||
* You can check if your instance is configured correctly by running it with `mix phx.server` and checking the instance info endpoint at `/api/v1/instance`. If it shows your uri, name and email correctly, you are configured correctly. If it shows something like `localhost:4000`, your configuration is probably wrong, unless you are running a local development setup.
|
* You can check if your instance is configured correctly by running it with `mix phx.server` and checking the instance info endpoint at `/api/v1/instance`. If it shows your uri, name and email correctly, you are configured correctly. If it shows something like `localhost:4000`, your configuration is probably wrong, unless you are running a local development setup.
|
||||||
* The common and convenient way for adding HTTPS is by using Nginx as a reverse proxy. You can look at example Nginx configuration in `installation/pleroma.nginx`. If you need TLS/SSL certificates for HTTPS, you can look get some for free with letsencrypt: <https://letsencrypt.org/>. The simplest way to obtain and install a certificate is to use [Certbot.](https://certbot.eff.org) Depending on your specific setup, certbot may be able to get a certificate and configure your web server automatically.
|
* The common and convenient way for adding HTTPS is by using Nginx as a reverse proxy. You can look at example Nginx configuration in `installation/pleroma.nginx`. If you need TLS/SSL certificates for HTTPS, you can look get some for free with letsencrypt: <https://letsencrypt.org/>. The simplest way to obtain and install a certificate is to use [Certbot.](https://certbot.eff.org) Depending on your specific setup, certbot may be able to get a certificate and configure your web server automatically.
|
||||||
|
@ -66,7 +68,7 @@ This is useful for running Pleroma inside Tor or I2P.
|
||||||
|
|
||||||
## Customization and contribution
|
## Customization and contribution
|
||||||
|
|
||||||
The [Pleroma Wiki](https://git.pleroma.social/pleroma/pleroma/wikis/home) offers manuals and guides on how to further customize your instance to your liking and how you can contribute to the project.
|
The [Pleroma Documentation](https://docs-develop.pleroma.social/readme.html) offers manuals and guides on how to further customize your instance to your liking and how you can contribute to the project.
|
||||||
|
|
||||||
## Troubleshooting
|
## Troubleshooting
|
||||||
|
|
||||||
|
|
|
@ -396,6 +396,8 @@
|
||||||
oauth_consumer_strategies: oauth_consumer_strategies,
|
oauth_consumer_strategies: oauth_consumer_strategies,
|
||||||
oauth_consumer_enabled: oauth_consumer_strategies != []
|
oauth_consumer_enabled: oauth_consumer_strategies != []
|
||||||
|
|
||||||
|
config :pleroma, Pleroma.Mailer, adapter: Swoosh.Adapters.Sendmail
|
||||||
|
|
||||||
# Import environment specific config. This must remain at the bottom
|
# Import environment specific config. This must remain at the bottom
|
||||||
# of this file so it overrides the configuration defined above.
|
# of this file so it overrides the configuration defined above.
|
||||||
import_config "#{Mix.env()}.exs"
|
import_config "#{Mix.env()}.exs"
|
||||||
|
|
|
@ -1,4 +1,6 @@
|
||||||
# Backup your instance
|
# Backup/Restore your instance
|
||||||
|
|
||||||
|
## Backup
|
||||||
|
|
||||||
1. Stop the Pleroma service.
|
1. Stop the Pleroma service.
|
||||||
2. Go to the working directory of Pleroma (default is `/opt/pleroma`)
|
2. Go to the working directory of Pleroma (default is `/opt/pleroma`)
|
||||||
|
@ -6,7 +8,7 @@
|
||||||
4. Copy `pleroma.pgdump`, `config/prod.secret.exs` and the `uploads` folder to your backup destination. If you have other modifications, copy those changes too.
|
4. Copy `pleroma.pgdump`, `config/prod.secret.exs` and the `uploads` folder to your backup destination. If you have other modifications, copy those changes too.
|
||||||
5. Restart the Pleroma service.
|
5. Restart the Pleroma service.
|
||||||
|
|
||||||
## Restore your instance
|
## Restore
|
||||||
|
|
||||||
1. Stop the Pleroma service.
|
1. Stop the Pleroma service.
|
||||||
2. Go to the working directory of Pleroma (default is `/opt/pleroma`)
|
2. Go to the working directory of Pleroma (default is `/opt/pleroma`)
|
||||||
|
|
|
@ -1,9 +1,9 @@
|
||||||
# Updating your instance
|
# Updating your instance
|
||||||
1. Stop the Pleroma service.
|
1. Go to the working directory of Pleroma (default is `/opt/pleroma`)
|
||||||
2. Go to the working directory of Pleroma (default is `/opt/pleroma`)
|
2. Run `git pull`. This pulls the latest changes from upstream.
|
||||||
3. Run `git pull`. This pulls the latest changes from upstream.
|
3. Run `mix deps.get`. This pulls in any new dependencies.
|
||||||
4. Run `mix deps.get`. This pulls in any new dependencies.
|
4. Stop the Pleroma service.
|
||||||
5. Run `mix ecto.migrate`[^1]. This task performs database migrations, if there were any.
|
5. Run `mix ecto.migrate`[^1]. This task performs database migrations, if there were any.
|
||||||
6. Restart the Pleroma service.
|
6. Start the Pleroma service.
|
||||||
|
|
||||||
[^1]: Prefix with `MIX_ENV=prod` to run it using the production config file.
|
[^1]: Prefix with `MIX_ENV=prod` to run it using the production config file.
|
||||||
|
|
|
@ -193,6 +193,44 @@ This section is used to configure Pleroma-FE, unless ``:managed_config`` in ``:i
|
||||||
* `port`: Port to bind to
|
* `port`: Port to bind to
|
||||||
* `dstport`: Port advertised in urls (optional, defaults to `port`)
|
* `dstport`: Port advertised in urls (optional, defaults to `port`)
|
||||||
|
|
||||||
|
## Pleroma.Web.Endpoint
|
||||||
|
`Phoenix` endpoint configuration, all configuration options can be viewed [here](https://hexdocs.pm/phoenix/Phoenix.Endpoint.html#module-dynamic-configuration), only common options are listed here
|
||||||
|
* `http` - a list containing http protocol configuration, all configuration options can be viewed [here](https://hexdocs.pm/plug_cowboy/Plug.Cowboy.html#module-options), only common options are listed here
|
||||||
|
- `ip` - a tuple consisting of 4 integers
|
||||||
|
- `port`
|
||||||
|
* `url` - a list containing the configuration for generating urls, accepts
|
||||||
|
- `host` - the host without the scheme and a post (e.g `example.com`, not `https://example.com:2020`)
|
||||||
|
- `scheme` - e.g `http`, `https`
|
||||||
|
- `port`
|
||||||
|
- `path`
|
||||||
|
|
||||||
|
|
||||||
|
**Important note**: if you modify anything inside these lists, default `config.exs` values will be overwritten, which may result in breakage, to make sure this does not happen please copy the default value for the list from `config.exs` and modify/add only what you need
|
||||||
|
|
||||||
|
Example:
|
||||||
|
```elixir
|
||||||
|
config :pleroma, Pleroma.Web.Endpoint,
|
||||||
|
url: [host: "example.com", port: 2020, scheme: "https"],
|
||||||
|
http: [
|
||||||
|
# start copied from config.exs
|
||||||
|
dispatch: [
|
||||||
|
{:_,
|
||||||
|
[
|
||||||
|
{"/api/v1/streaming", Pleroma.Web.MastodonAPI.WebsocketHandler, []},
|
||||||
|
{"/websocket", Phoenix.Endpoint.CowboyWebSocket,
|
||||||
|
{Phoenix.Transports.WebSocket,
|
||||||
|
{Pleroma.Web.Endpoint, Pleroma.Web.UserSocket, websocket_config}}},
|
||||||
|
{:_, Phoenix.Endpoint.Cowboy2Handler, {Pleroma.Web.Endpoint, []}}
|
||||||
|
]}
|
||||||
|
# end copied from config.exs
|
||||||
|
],
|
||||||
|
port: 8080,
|
||||||
|
ip: {127, 0, 0, 1}
|
||||||
|
]
|
||||||
|
```
|
||||||
|
|
||||||
|
This will make Pleroma listen on `127.0.0.1` port `8080` and generate urls starting with `https://example.com:2020`
|
||||||
|
|
||||||
## :activitypub
|
## :activitypub
|
||||||
* ``accept_blocks``: Whether to accept incoming block activities from other instances
|
* ``accept_blocks``: Whether to accept incoming block activities from other instances
|
||||||
* ``unfollow_blocked``: Whether blocks result in people getting unfollowed
|
* ``unfollow_blocked``: Whether blocks result in people getting unfollowed
|
||||||
|
|
|
@ -1,7 +0,0 @@
|
||||||
# How to change the port or IP Pleroma listens to
|
|
||||||
To change the port or IP Pleroma listens to, head over to your generated config inside the Pleroma folder at config/prod.secret.exs and edit the following according to your needs.
|
|
||||||
```
|
|
||||||
config :pleroma, Pleroma.Web.Endpoint,
|
|
||||||
[...]
|
|
||||||
http: [ip: {127, 0, 0, 1}, port: 4000]
|
|
||||||
```
|
|
|
@ -1,11 +1,11 @@
|
||||||
# Introduction to Pleroma
|
# Introduction to Pleroma
|
||||||
**What is Pleroma?**
|
## What is Pleroma?
|
||||||
Pleroma is a federated social networking platform, compatible with GNU social, Mastodon and other OStatus and ActivityPub implementations. It is free software licensed under the AGPLv3.
|
Pleroma is a federated social networking platform, compatible with GNU social, Mastodon and other OStatus and ActivityPub implementations. It is free software licensed under the AGPLv3.
|
||||||
It actually consists of two components: a backend, named simply Pleroma, and a user-facing frontend, named Pleroma-FE. It also includes the Mastodon frontend, if that's your thing.
|
It actually consists of two components: a backend, named simply Pleroma, and a user-facing frontend, named Pleroma-FE. It also includes the Mastodon frontend, if that's your thing.
|
||||||
It's part of what we call the fediverse, a federated network of instances which speak common protocols and can communicate with each other.
|
It's part of what we call the fediverse, a federated network of instances which speak common protocols and can communicate with each other.
|
||||||
One account on a instance is enough to talk to the entire fediverse!
|
One account on a instance is enough to talk to the entire fediverse!
|
||||||
|
|
||||||
**How can I use it?**
|
## How can I use it?
|
||||||
|
|
||||||
Pleroma instances are already widely deployed, a list can be found here:
|
Pleroma instances are already widely deployed, a list can be found here:
|
||||||
http://distsn.org/pleroma-instances.html
|
http://distsn.org/pleroma-instances.html
|
||||||
|
@ -14,14 +14,14 @@ If you don't feel like joining an existing instance, but instead prefer to deplo
|
||||||
Installation instructions can be found here:
|
Installation instructions can be found here:
|
||||||
[main Pleroma wiki](/)
|
[main Pleroma wiki](/)
|
||||||
|
|
||||||
**I got an account, now what?**
|
## I got an account, now what?
|
||||||
Great! Now you can explore the fediverse!
|
Great! Now you can explore the fediverse!
|
||||||
- Open the login page for your Pleroma instance (for ex. https://pleroma.soykaf.com) and login with your username and password.
|
- Open the login page for your Pleroma instance (for ex. https://pleroma.soykaf.com) and login with your username and password.
|
||||||
(If you don't have one yet, click on Register) :slightly_smiling_face:
|
(If you don't have one yet, click on Register) :slightly_smiling_face:
|
||||||
|
|
||||||
At this point you will have two columns in front of you.
|
At this point you will have two columns in front of you.
|
||||||
|
|
||||||
***left column***
|
### Left column
|
||||||
- first block: here you can see your avatar, your nickname a bio, and statistics (Statuses, Following, Followers).
|
- first block: here you can see your avatar, your nickname a bio, and statistics (Statuses, Following, Followers).
|
||||||
Under that you have a text form which allows you to post new statuses. The icon on the left is for uploading media files and attach them to your post. The number under the text form is a character counter, every instance can have a different character limit (the default is 5000).
|
Under that you have a text form which allows you to post new statuses. The icon on the left is for uploading media files and attach them to your post. The number under the text form is a character counter, every instance can have a different character limit (the default is 5000).
|
||||||
If you want to mention someone, type @ + name of the person. A drop-down menu will help you in finding the right person. :slight_smile:
|
If you want to mention someone, type @ + name of the person. A drop-down menu will help you in finding the right person. :slight_smile:
|
||||||
|
@ -37,7 +37,7 @@ To post your status, simply press Submit.
|
||||||
|
|
||||||
- fourth block: This is the Notifications block, here you will get notified whenever somebody mentions you, follows you, repeats or favorites one of your statuses.
|
- fourth block: This is the Notifications block, here you will get notified whenever somebody mentions you, follows you, repeats or favorites one of your statuses.
|
||||||
|
|
||||||
***right column***
|
### Right column
|
||||||
This is where the interesting stuff happens! :slight_smile:
|
This is where the interesting stuff happens! :slight_smile:
|
||||||
Depending on the timeline you will see different statuses, but each status has a standard structure:
|
Depending on the timeline you will see different statuses, but each status has a standard structure:
|
||||||
- Icon + name + link to profile. An optional left-arrow if it's a reply to another status (hovering will reveal the replied-to status).
|
- Icon + name + link to profile. An optional left-arrow if it's a reply to another status (hovering will reveal the replied-to status).
|
||||||
|
@ -46,7 +46,7 @@ Depending on the timeline you will see different statuses, but each status has a
|
||||||
- The text of the status, including mentions. If you click on a mention, it will automatically open the profile page of that person.
|
- The text of the status, including mentions. If you click on a mention, it will automatically open the profile page of that person.
|
||||||
- Four buttons (left to right): Reply, Repeat, Favorite, Delete.
|
- Four buttons (left to right): Reply, Repeat, Favorite, Delete.
|
||||||
|
|
||||||
**Mastodon interface**
|
## Mastodon interface
|
||||||
If the Pleroma interface isn't your thing, or you're just trying something new but you want to keep using the familiar Mastodon interface, we got that too! :smile:
|
If the Pleroma interface isn't your thing, or you're just trying something new but you want to keep using the familiar Mastodon interface, we got that too! :smile:
|
||||||
Just add a "/web" after your instance url (for ex. https://pleroma.soycaf.com/web) and you'll end on the Mastodon web interface, but with a Pleroma backend! MAGIC! :fireworks:
|
Just add a "/web" after your instance url (for ex. https://pleroma.soycaf.com/web) and you'll end on the Mastodon web interface, but with a Pleroma backend! MAGIC! :fireworks:
|
||||||
For more information on the Mastodon interface, please look here:
|
For more information on the Mastodon interface, please look here:
|
||||||
|
|
|
@ -233,6 +233,7 @@ defmodule Pleroma.Web.Router do
|
||||||
get("/accounts/search", MastodonAPIController, :account_search)
|
get("/accounts/search", MastodonAPIController, :account_search)
|
||||||
|
|
||||||
get("/accounts/:id/lists", MastodonAPIController, :account_lists)
|
get("/accounts/:id/lists", MastodonAPIController, :account_lists)
|
||||||
|
get("/accounts/:id/identity_proofs", MastodonAPIController, :empty_array)
|
||||||
|
|
||||||
get("/follow_requests", MastodonAPIController, :follow_requests)
|
get("/follow_requests", MastodonAPIController, :follow_requests)
|
||||||
get("/blocks", MastodonAPIController, :blocks)
|
get("/blocks", MastodonAPIController, :blocks)
|
||||||
|
|
Loading…
Reference in New Issue