Storehouse.File (Storehouse v0.2.0)

Copy Markdown View Source

A stored file: what Storehouse.store/2 gives, and what an app keeps in its records (or a document's data) to show and serve it again.

  • :key - its key in the store (Storehouse.key/2).
  • :url - its URL, from the store.
  • :name - the client's file name, for display only (Storehouse.clean_name/1).
  • :content_type - the type its bytes prove (Storehouse.Check).
  • :bytes - its size.
  • :width and :height - an image's, as a browser draws it (turned as a JPEG's EXIF says), or nil.
  • :checksum - the SHA-256 of its bytes, in Base64 (as S3's x-amz-checksum-sha256): the store checked it as it took the file, and Storehouse.checksum/1 gives it of a copy, to compare. nil for a file uploaded straight to a store that keeps none (Storehouse.verify_upload/2).
  • :preview - the URL of a smaller image of it (a thumbnail, a PDF's first page, a video's poster), when the app made one, or nil.
  • :metadata - the app's own (Storehouse.Metadata): a caption, a credit. %{} when there is none.
  • :analysis - what the analysis steps made of the file (Storehouse.Analyzer), by step name, each a Storehouse.Analysis. %{} when none ran.

In JSON

A file encodes as JSON (JSON.Encoder on Elixir 1.18 and later, and Jason.Encoder when Jason is there) with its fields and metadata, but not its analysis: what a file's EXIF says can hold where a photo was taken. to_map/2 chooses what goes.

Summary

Functions

What the analysis step step made of the file (Storehouse.Analysis), or nil when it has not run.

What the analysis step step read from the file, when it ran and did not fail or skip it: its result, else nil.

Whether the file is an image (PNG, JPEG, GIF or WebP).

Merges metadata into the file's own (Storehouse.Metadata.merge/2): a caption a person entered, a credit. It is normalized first (Storehouse.Metadata.normalize/1), and refused with {:error, {:invalid_metadata, path}} when it holds what JSON does not.

The file as a map with string keys, for JSON: its fields and metadata, without its analysis unless asked.

Types

t()

@type t() :: %Storehouse.File{
  analysis: %{required(String.t()) => Storehouse.Analysis.t()},
  bytes: non_neg_integer(),
  checksum: String.t() | nil,
  content_type: String.t(),
  height: pos_integer() | nil,
  key: Storehouse.Adapter.key(),
  metadata: map(),
  name: String.t(),
  preview: String.t() | nil,
  url: String.t(),
  width: pos_integer() | nil
}

Functions

analysis(file, step)

@spec analysis(t(), String.t() | atom()) :: Storehouse.Analysis.t() | nil

What the analysis step step made of the file (Storehouse.Analysis), or nil when it has not run.

analyzed(file, step)

@spec analyzed(t(), String.t() | atom()) :: map() | nil

What the analysis step step read from the file, when it ran and did not fail or skip it: its result, else nil.

Examples

iex> file = %Storehouse.File{key: "a.pdf", url: "/a.pdf", name: "a.pdf", content_type: "application/pdf", bytes: 1}
iex> file = Storehouse.File.put_analysis(file, "pages", Storehouse.Analysis.ok(%{"pages" => 12}))
iex> Storehouse.File.analyzed(file, :pages)
%{"pages" => 12}

image?(file)

@spec image?(t()) :: boolean()

Whether the file is an image (PNG, JPEG, GIF or WebP).

put_metadata(file, metadata)

@spec put_metadata(t(), map()) :: {:ok, t()} | {:error, {:invalid_metadata, list()}}

Merges metadata into the file's own (Storehouse.Metadata.merge/2): a caption a person entered, a credit. It is normalized first (Storehouse.Metadata.normalize/1), and refused with {:error, {:invalid_metadata, path}} when it holds what JSON does not.

Examples

iex> file = %Storehouse.File{key: "a.png", url: "/a.png", name: "a.png", content_type: "image/png", bytes: 1}
iex> {:ok, file} = Storehouse.File.put_metadata(file, %{caption: "The quay"})
iex> {:ok, file} = Storehouse.File.put_metadata(file, %{credit: "Ana"})
iex> file.metadata
%{"caption" => "The quay", "credit" => "Ana"}

to_map(file, opts \\ [])

@spec to_map(t(), keyword()) :: map()

The file as a map with string keys, for JSON: its fields and metadata, without its analysis unless asked.

  • :only - the fields to give, of [:key, :url, :name, :content_type, :bytes, :width, :height, :checksum, :preview, :metadata]. The default is all of them.
  • :analysis - the analysis steps to give, under "analysis": a list of their names, or true for every one. The default is none.

Examples

iex> file = %Storehouse.File{key: "a.png", url: "/a.png", name: "a.png", content_type: "image/png", bytes: 1, metadata: %{"caption" => "Hi"}}
iex> Storehouse.File.to_map(file, only: [:url, :metadata])
%{"url" => "/a.png", "metadata" => %{"caption" => "Hi"}}