Useful methods to define and manage PostgreSQL views in Ecto.
Inspired by scenic library for ActiveRecord (RoR)
If available in Hex, the package can be installed
by adding ecto_vista
to your list of dependencies in mix.exs
:
def deps do
[
{:ecto_vista, "~> 0.2.0"}
]
end
- Add
ecto_vista
to your list of dependencies inmix.exs
and run:
mix deps.get
- Generate your migration for the view, put the view definition like the one below
inside
change
orup
method:
execute("""
CREATE MATERIALIZED VIEW catalog_v1 AS
SELECT c.*, count(p.id) AS product_count
FROM categories c
LEFT JOIN products p ON c.id = p.category_id
GROUP BY c.id
;
""")
- Use
EctoVista
module in your Ecto schema:
def App.Catalog do
use Ecto.Schema
use EctoVista,
repo: App.Repo
table_name: "catalog"
schema @table_name do
field(:name, :string)
field(:product_count, :integer)
end
end
The @table_name
will be defined in macro as {table_name}_v{version}
(version is 1 by default)
This naming convention facilitates 0-downtime view updates and will be handled automagically in future versions.
If you need to update the view, generate a new migration and then just update the version number in the schema definition:
def App.Catalog do
use Ecto.Schema
use EctoVista,
repo: App.Repo
table_name: "catalog"
version: 2
...
end
- Don't forget to refresh your materialized view to see data:
iex> Catalog.refresh
:ok
- Support
Model.refresh
callback in Ecto.Schema for Materialized Views - Implement automatic view versioning for a model
- Support
create view
callback in Ecto.Migration
- Support all options to refresh and create views
- Implement automatic view versioning for migration
Documentation can be generated with ExDoc and published on HexDocs. Once published, the docs can be found at https://hexdocs.pm/ecto_vista.
The source code is under the Apache 2 License.