Router macros for the ingest endpoint and the dashboard.
defmodule MyAppWeb.Router do
use MyAppWeb, :router
import Pixelex.Router
# the browser's way in: POST /px/e, GET /px/px.gif, GET /px/pixelex.js
pixelex_ingest "/px"
scope "/admin" do
pipe_through [:browser, :require_admin]
pixelex_dashboard "/analytics"
pixelex_settings "/analytics/settings"
end
endThe ingest endpoint takes no pipeline
pixelex_ingest/2 deliberately forwards outside the :browser pipeline.
Session fetching, flash and CSRF protection are all wrong here: the
endpoint is called by a beacon on pages the visitor is not signed in to,
and a CSRF token would have to be embedded in the tracker for every page,
which is not protection, it is ceremony. What actually bounds it is the
per-site event allowlist, the consent gate, bot filtering and the rate
limiter — see Pixelex.Plug.Ingest.
The dashboard takes yours
pixelex_dashboard/2 mounts a LiveView and inherits whatever pipeline it
is scoped inside. It has no authentication of its own. Put it behind
yours. A site's full traffic, sources and funnels are not public data, and
a library that shipped its own auth would be a second login for you to
maintain and a first one for an attacker to find.
Summary
Functions
Mount the dashboard at path.
Mount the ingest endpoint at path.
Mount the settings screen at path.
Functions
Mount the dashboard at path.
Options
:site_id— pin the dashboard to one site. Omitted, it reads?site=and defaults to the request host.:on_mount— extraon_mounthooks, for your own authorisation.:live_session_name— defaults to:pixelex_dashboard.
Mount the ingest endpoint at path.
Configure the tracker to match with
config :pixelex, ingest_path: "/px" — the path is configurable precisely
because a fixed, well-known one is what ends up on a filter list.
Mount the settings screen at path.
Where a tenant pastes their own pixel ids and access tokens and presses
Test. Same options as pixelex_dashboard/2.
It writes. The dashboard leaking ?site= shows the wrong numbers; this
one edits the wrong tenant's ad credentials. On a path-based multi-tenant
app, pin :site_id or pass an :on_mount that checks the current user
against the site they asked for. On a custom-domain product the host is
already the tenant and the default is right.
scope "/admin" do
pipe_through [:browser, :require_admin]
pixelex_dashboard "/analytics"
pixelex_settings "/analytics/settings"
end