# `Sekisho.LiveView`
[🔗](https://github.com/hattoriai/sekisho/blob/v0.1.0-dev/lib/sekisho/live_view.ex#L2)

Permissions in LiveView: events checked before your `handle_event/3`
runs, and pages that lose their access while they are open.

Add the hook to a `live_session`, after the one that sets the scope:

    live_session :app,
      on_mount: [
        {MyAppWeb.UserAuth, :require_authenticated},
        {Sekisho.LiveView, MyApp.Permissions}
      ] do
      live "/documents/:id", DocumentLive
    end

Then, in `mount/3`, say what the page needs, and which events take
which permission on which assign:

    def mount(%{"id" => id}, _session, socket) do
      document = Docs.get_document!(socket.assigns.current_scope, id)

      {:ok,
       socket
       |> assign(document: document)
       |> Sekisho.LiveView.watch(:read, document)
       |> Sekisho.LiveView.authorize_events(%{
         "save" => {:update, :document},
         "delete" => {:delete, :document}
       })}
    end

An event of the map is refused when the scope does not have its
permission on the assign (a flash, and your `handle_event/3` is not
called). When access to a watched record is revoked (a grant taken
away, a role changed, a membership of your own tables:
`MyApp.Permissions.changed/0`), the page goes away with a flash: to
`"/"`, or where `:revoked_to` says.

It needs `:pubsub` in `use Sekisho`.

## Options

`{Sekisho.LiveView, {MyApp.Permissions, opts}}`:

  * `:scope` — the assign of the scope (`:current_scope`).
  * `:revoked_to` — where a page goes when its access is revoked (`"/"`).
  * `:revoked` — its flash (`"You no longer have access to this page."`).
  * `:denied` — the flash of a refused event (`"You are not allowed to do that."`).

Flashes are your words: pass translated ones (Gettext) here.

# `authorize_events`

```elixir
@spec authorize_events(Phoenix.LiveView.Socket.t(), %{
  required(String.t()) =&gt; {atom(), atom()}
}) ::
  Phoenix.LiveView.Socket.t()
```

Events checked before `handle_event/3`: `%{"delete" => {:delete,
:document}}` takes `:delete` on `@document`.

# `watch`

```elixir
@spec watch(Phoenix.LiveView.Socket.t(), atom(), struct()) ::
  Phoenix.LiveView.Socket.t()
```

The page needs the permission on the record: when it loses it, it goes away.

---

*Consult [api-reference.md](api-reference.md) for complete listing*
