defmodule SimpleshopTheme.Media.Image do use Ecto.Schema import Ecto.Changeset @primary_key {:id, :binary_id, autogenerate: true} @foreign_key_type :binary_id schema "images" do field :image_type, :string field :filename, :string field :content_type, :string field :file_size, :integer field :data, :binary field :is_svg, :boolean, default: false field :svg_content, :string field :thumbnail_data, :binary timestamps(type: :utc_datetime) end @max_file_size 5_000_000 @doc false def changeset(image, attrs) do image |> cast(attrs, [:image_type, :filename, :content_type, :file_size, :data, :is_svg, :svg_content]) |> validate_required([:image_type, :filename, :content_type, :file_size, :data]) |> validate_inclusion(:image_type, ~w(logo header product)) |> validate_number(:file_size, less_than: @max_file_size) |> detect_svg() end defp detect_svg(changeset) do content_type = get_change(changeset, :content_type) if content_type == "image/svg+xml" or String.ends_with?(get_change(changeset, :filename) || "", ".svg") do changeset |> put_change(:is_svg, true) |> maybe_store_svg_content() else changeset end end defp maybe_store_svg_content(changeset) do case get_change(changeset, :data) do nil -> changeset svg_binary when is_binary(svg_binary) -> put_change(changeset, :svg_content, svg_binary) end end end