diff --git a/config/config.exs b/config/config.exs index 17674049a..abdf22eec 100644 --- a/config/config.exs +++ b/config/config.exs @@ -329,6 +329,7 @@ config :mobilizon, Mobilizon.Service.Notifier.Email, enabled: true config :mobilizon, Mobilizon.Service.Notifier.Push, enabled: true config :mobilizon, :exports, + path: "/var/lib/mobilizon/uploads/exports", formats: [ Mobilizon.Service.Export.Participants.CSV ] diff --git a/config/dev.exs b/config/dev.exs index d7a28a2ac..c78500a99 100644 --- a/config/dev.exs +++ b/config/dev.exs @@ -94,6 +94,8 @@ config :mobilizon, Mobilizon.Web.Auth.Guardian, config :mobilizon, Mobilizon.Web.Upload.Uploader.Local, uploads: "uploads" +config :mobilizon, :exports, path: "uploads/exports" + config :tz_world, data_dir: "_build/dev/lib/tz_world/priv" config :mobilizon, :anonymous, diff --git a/config/test.exs b/config/test.exs index c6338b88e..d0a4afa0a 100644 --- a/config/test.exs +++ b/config/test.exs @@ -60,6 +60,8 @@ config :mobilizon, Mobilizon.Web.Upload, filters: [], link_name: false config :mobilizon, Mobilizon.Web.Upload.Uploader.Local, uploads: "test/uploads" +config :mobilizon, :exports, path: "test/uploads/exports" + config :tz_world, data_dir: "_build/test/lib/tz_world/priv" config :tesla, Mobilizon.Service.HTTP.ActivityPub, diff --git a/lib/service/export/participants/common.ex b/lib/service/export/participants/common.ex index b1292b9c7..3512d0dc2 100644 --- a/lib/service/export/participants/common.ex +++ b/lib/service/export/participants/common.ex @@ -4,9 +4,9 @@ defmodule Mobilizon.Service.Export.Participants.Common do """ alias Mobilizon.Actors.Actor + alias Mobilizon.{Config, Export} alias Mobilizon.Events.Participant alias Mobilizon.Events.Participant.Metadata - alias Mobilizon.Export alias Mobilizon.Storage.Repo import Mobilizon.Web.Gettext, only: [gettext: 1] @@ -117,4 +117,13 @@ defmodule Mobilizon.Service.Export.Participants.Common do formats = Keyword.get(export_config, :formats, []) type in formats end + + @default_upload_path "uploads/exports/" + + @spec export_path(String.t()) :: String.t() + def export_path(extension) do + [:exports, :path] + |> Config.get(@default_upload_path) + |> Path.join(extension) + end end diff --git a/lib/service/export/participants/csv.ex b/lib/service/export/participants/csv.ex index 62cbdbb3f..b33fbb581 100644 --- a/lib/service/export/participants/csv.ex +++ b/lib/service/export/participants/csv.ex @@ -3,17 +3,21 @@ defmodule Mobilizon.Service.Export.Participants.CSV do Export a list of participants to CSV """ - alias Mobilizon.Events + alias Mobilizon.{Events, Export} alias Mobilizon.Events.Event - alias Mobilizon.Export alias Mobilizon.Storage.Repo alias Mobilizon.Web.Gettext import Mobilizon.Web.Gettext, only: [gettext: 2] import Mobilizon.Service.Export.Participants.Common, - only: [save_upload: 5, columns: 0, to_list: 1, clean_exports: 2, export_enabled?: 1] - - @upload_path "uploads/exports/csv/" + only: [ + save_upload: 5, + columns: 0, + to_list: 1, + clean_exports: 2, + export_enabled?: 1, + export_path: 1 + ] @extension "csv" @@ -26,7 +30,7 @@ defmodule Mobilizon.Service.Export.Participants.CSV do def export(%Event{id: event_id} = event, options \\ []) do if ready?() do filename = "#{ShortUUID.encode!(Ecto.UUID.generate())}.csv" - full_path = @upload_path <> filename + full_path = Path.join([export_path(@extension), filename]) file = File.open!(full_path, [:write, :utf8]) @@ -80,7 +84,7 @@ defmodule Mobilizon.Service.Export.Participants.CSV do """ @spec clean_exports :: :ok def clean_exports do - clean_exports("csv", @upload_path) + clean_exports("csv", export_path(@extension)) end @spec dependencies_ok? :: boolean diff --git a/lib/service/export/participants/ods.ex b/lib/service/export/participants/ods.ex index e6eb6c4c9..ef73d25fe 100644 --- a/lib/service/export/participants/ods.ex +++ b/lib/service/export/participants/ods.ex @@ -10,9 +10,14 @@ defmodule Mobilizon.Service.Export.Participants.ODS do import Mobilizon.Web.Gettext, only: [gettext: 2] import Mobilizon.Service.Export.Participants.Common, - only: [save_upload: 5, to_list: 1, clean_exports: 2, columns: 0, export_enabled?: 1] - - @upload_path "uploads/exports/ods/" + only: [ + save_upload: 5, + to_list: 1, + clean_exports: 2, + columns: 0, + export_enabled?: 1, + export_path: 1 + ] @extension "ods" @@ -25,7 +30,7 @@ defmodule Mobilizon.Service.Export.Participants.ODS do def export(%Event{id: event_id} = event, options \\ []) do if ready?() do filename = "#{ShortUUID.encode!(Ecto.UUID.generate())}.ods" - full_path = @upload_path <> filename + full_path = Path.join([export_path(@extension), filename]) case Repo.transaction( fn -> @@ -84,7 +89,7 @@ defmodule Mobilizon.Service.Export.Participants.ODS do """ @spec clean_exports :: :ok def clean_exports do - clean_exports("ods", @upload_path) + clean_exports(@extension, export_path(@extension)) end @spec dependencies_ok? :: boolean diff --git a/lib/service/export/participants/pdf.ex b/lib/service/export/participants/pdf.ex index 3d488e6c5..a51e3a08e 100644 --- a/lib/service/export/participants/pdf.ex +++ b/lib/service/export/participants/pdf.ex @@ -12,9 +12,14 @@ defmodule Mobilizon.Service.Export.Participants.PDF do import Mobilizon.Web.Gettext, only: [gettext: 2] import Mobilizon.Service.Export.Participants.Common, - only: [save_upload: 5, columns: 0, to_list: 1, clean_exports: 2, export_enabled?: 1] - - @upload_path "uploads/exports/pdf/" + only: [ + save_upload: 5, + columns: 0, + to_list: 1, + clean_exports: 2, + export_enabled?: 1, + export_path: 1 + ] @extension "pdf" @@ -27,7 +32,7 @@ defmodule Mobilizon.Service.Export.Participants.PDF do def export(%Event{id: event_id} = event, options \\ []) do if ready?() do filename = "#{ShortUUID.encode!(Ecto.UUID.generate())}.pdf" - full_path = @upload_path <> filename + full_path = Path.join([export_path(@extension), filename]) case Repo.transaction( fn -> @@ -98,7 +103,7 @@ defmodule Mobilizon.Service.Export.Participants.PDF do """ @spec clean_exports :: :ok def clean_exports do - clean_exports("pdf", @upload_path) + clean_exports(@extension, export_path(@extension)) end @spec dependencies_ok? :: boolean diff --git a/lib/web/controllers/export_controller.ex b/lib/web/controllers/export_controller.ex index e0d01867a..ce937b68d 100644 --- a/lib/web/controllers/export_controller.ex +++ b/lib/web/controllers/export_controller.ex @@ -6,7 +6,7 @@ defmodule Mobilizon.Web.ExportController do plug(:put_layout, false) action_fallback(Mobilizon.Web.FallbackController) alias Mobilizon.Export - import Mobilizon.Service.Export.Participants.Common, only: [enabled_formats: 0] + import Mobilizon.Service.Export.Participants.Common, only: [enabled_formats: 0, export_path: 1] import Mobilizon.Web.Gettext, only: [dgettext: 3] # sobelow_skip ["Traversal.SendDownload"] @@ -15,7 +15,7 @@ defmodule Mobilizon.Web.ExportController do if format in enabled_formats() do case Export.get_export(file, "event_participants", format) do %Export{file_name: file_name, file_path: file_path} -> - local_path = "uploads/exports/#{format}/#{file_path}" + local_path = Path.join(export_path(format), file_path) # We're using encode: false to disable escaping the filename with URI.encode_www_form/1 # but it may introduce an security issue if the event title wasn't properly sanitized # https://github.com/phoenixframework/phoenix/pull/3344