Why embedded reports expose data: a breakdown of signed embedding
A public report link is a quick way to show analytics and the shortest path to data leaks from dashboards. The URL does not check who opened it: it lingers in browser history, in forwarded email, in proxy logs, and in search engine indexes. Once sent to a shared chat, it serves up an export with margin, customer base, or sales dynamics.
Shared accounts produce the same result by a different route. When a department uses a single login, dashboard permissions stop restricting anything: everyone sees all reports, and logs keep only an impersonal entry.
In such a scheme, access to analytics cannot be segmented by role, region, or customer, and during incident investigation it is unclear who exactly opened the data.
Signed access (signed embedding) closes both gaps. The application server generates a report link at request time, adds a signature with a secret key, and user parameters — identifier, role, filters over their data.
The analytics platform verifies the signature, serves only the permitted slice, and does not store your users' passwords.
Metabase supports this mode out of the box: the signature lives for minutes, filters are applied on the application side, so a forwarded link will not open someone else's data. We explain how it works and what needs to be configured.
What embedding analytics into a product interface gives
The first thing noticed after embedding is that reporting moves inside the product. The user does not leave for an external analytics tool or keep a second tab open: they view the needed slice where they work with tickets, invoices, or orders.
This also changes behavior — people turn to numbers at the moment of decision, not once a week after a reminder.
The technical foundation is provided by signed embedding: the product server generates a signed token that embeds the user identifier, the set of filters available to them, and the time to live.
The signature is verified on the analytics service side, so parameters cannot be substituted in the browser. Row-level data segregation is set by the same token — the customer sees only their own slices, and this does not require a separate dashboard copy for each one.
Single sign-on removes an entire class of access incidents. Accounts do not proliferate across tools, permissions are inherited from the product, and when an employee leaves or changes role, access is closed with one operation.
This is exactly what should be checked: how many times per period accesses are created and revoked manually.
The reduction in manual exports is measured simply: the share of “send me the report” requests to support and the share of slices still assembled in spreadsheets.
When the needed dataset is built in the interface in a couple of seconds, the analyst stops being an intermediary between data and decisions, and the customer receives analytics as part of the product, not as a separate service on request.
Analytics embedding methods: where signed embedding is needed
The choice between report embedding methods is determined not by developer convenience, but by whom we give data to and how dynamic the filters are. A public dashboard lives at a permanent link and does not know who opened it.
A persistent embedded session shows everyone the same picture inside the interface. A signed report link (signed embedding) is generated on the application side for a specific user and carries filters within itself.
| Option | When it fits | Limitations |
|---|---|---|
| Public dashboard | Open reporting, demos, showcases without personal data | No access segregation, filters are hardcoded into the dashboard itself |
| Persistent embedded session | Internal portal where everyone views the same aggregates | One permission set for all, parameters cannot be set on the fly |
| Signed report link | Customer portals, datasets for a specific user or counterparty | Signature is calculated by the server, link TTL must be limited |
What is behind the choice
The public option saves time at the start, but each new dataset requires manually editing the dashboard, and a leaked link equals leaked data.
An embedded session solves the appearance issue but not the permissions issue: if a filter needs to be inserted from the account, it does not get there.
A signed link solves the task differently — the application calculates the parameters itself, signs them with a secret, and returns a ready URL, while the analytics server verifies the signature and does not allow values in the request to be substituted.
That is why this mode is adopted where reporting is seen by external users, not only employees. Next, we explain how this scheme is assembled and what to provide for when migrating from public access.
Work stages: from source audit to production deployment
Embedding analytics into a product starts not with charts but with a data inventory: if a metric is calculated differently in two places, the embedded report will replicate the discrepancy at the same speed as it is viewed.
-
Data source audit. We verify where the numbers come from: table schema, refresh frequency, time zones, aggregation rules. The result is a metric map and a list of discrepancies that we close before embedding.
-
Access scheme. We define what the customer, manager, and administrator see: mapping product roles to report groups and row-level filters by account identifier.
-
Signed embedding setup. In Metabase, the signature is assembled on the server, the secret key does not get into the markup; we embed filtering parameters and the link TTL so that another account cannot open a neighbor's data.
-
Embedding into the interface. The report URL and parameters come from the backend, loading and error states are handled by product tools, and permissions are checked before rendering.
-
Testing on staging. We run scenarios: guest without a session, someone else's identifier, expired signature, unavailable source. We measure report opening time and behavior during failures.
-
Production deployment and handover of policies. The report update procedure, signing key rotation, actions when the source is unavailable — we record these in a document that remains with your team.
Each stage ends with a verifiable artifact: a metric map, permission scheme, report configuration, test run results. This makes the path from “the dashboard opens” to “the metrics can be trusted” predictable.
What we hand over: configurations, schemes, and policies
Signed embedding ends not with launching a dashboard but with a package of artifacts: using them, your team can change reports, roles, and filters without contacting us. Everything is stored in the repository next to the application code and goes through review together with it.
- Connection configurations — environment, data source, list of embedded dashboards, signing key, and its rotation procedure.
- Integration scheme — how the application assembles the signed request, where user permissions are checked, and what happens on failure.
- Access policies — mapping application roles to filters in reports: who sees which data rows.
- Analytics documentation — models, sources, refresh schedules, and the owner of each data mart.
- Support guide — typical failures: expired signature, empty filter, unavailable source — and the procedure for each.
- Change policy — how to add a dashboard or parameter without breaking already embedded views.
We separately record the “role — dashboard — filter” matrix: it removes most questions during acceptance. We conduct the handover on a demo environment — your team adds a report and changes permissions themselves, and we verify the result and update the documentation as needed.
Case study: reduced the share of dashboard access failures
The client is a platform with a customer portal: each customer has their own analytics, and dashboards must open directly in the interface, without a second login.
Initially, reporting lived in a separate Metabase environment: a manager manually created an account, configured permissions, and sent the customer a login in a separate email.
Granting access took from several hours to two days, and support received repetitive requests — “the dashboard does not open,” “it asks for a password again,” “I see another customer's metrics.”
We moved embedding to signed embedding: the application server generates a signed token that embeds the customer identifier, their role, a set of filters, and a short TTL so the link cannot be forwarded and reused.
The dashboard is served inside the portal without a login and password, and parameters cannot be forged via the address bar — the signature is verified on the analytics service side, and any edit invalidates the token.
Metrics before and after
| Metric | Before | After |
|---|---|---|
| Granting access to a new customer | from several hours to two days | automatically upon login to the portal |
| Share of support requests about access | about two thirds of all requests | isolated ones related to role configuration |
| Access failures: expired password, someone else's profile | reproduced constantly | do not occur by design |
| Onboarding a new customer | manual work by a manager in the admin panel | one entry in the configuration |
What this achieved
The flow of access requests collapsed: support stopped being an intermediary between the customer and analytics, and managers no longer had to keep track of who was granted what.
Permissions are now inherited from the role in the application, so when a plan changes or a customer is disconnected, the set of visible dashboards changes with the same action, without manual synchronization.
How does a signed link differ from a public one?
A public link contains no signature: the URL itself is the access. The server serves data to anyone who opens it, and its lifetime is determined only by when someone remembers to disable it.
There is no user binding: if parameters exist at all, they are directly in the URL, and they are easy to substitute.
A signed link (Metabase signed embedding) is a token for a specific user and a specific dashboard. Inside are the dashboard identifier, a set of access parameters, and the expiration time; a private-key signature prevents them from being substituted in the address bar.
We set the TTL explicitly: from a minute for a one-off export to several hours for a working screen.
Access revocation is the main difference in practice. A public link can only be disabled entirely, and everyone to whom you gave it loses access at once; you cannot revoke access for a single recipient specifically.
A signature has two levers: a short TTL and key rotation — invalidating the key extinguishes all issued tokens at once.
A short TTL and rotation close the leak but do not replace server-side permission checks. The signature confirms that the parameters were issued by our backend, not that the user is entitled to exactly these rows.
Therefore, we put a minimal set of filters in the token, and access to each dashboard is still verified on the server before data is served.
Technical concerns and limitations of the approach
Concerns around signed embedding are usually the same: whether data access will open through someone else's interface, whether each customer will see only their own rows, and what will happen to analytics when a dashboard built in Metabase starts living separately from the application.
It works like this: the signature is generated on the application server, not in the browser, so the secret never leaves the backend. And exactly what goes into the signature — dashboard identifier, customer filters, TTL — determines the security of the embedding.
Will the customer tweak parameters in the address bar and see someone else's data?
The signature is calculated over the entire set of parameters: changing the dashboard, filter, or TTL makes it invalid, and the analytics server rejects the request.
Data filtering is set on our side at the moment the link is issued, and only what we explicitly allow remains editable.
Will the link be forwarded to a third party?
A signed link lives for minutes and is tied to specific parameters — after the TTL expires, the server returns a failure, not data. If necessary, we bind issuance to the user's session in the application, and the link does not work in isolation from authorization.
Who is responsible for dashboards after launch, and what does the approach not cover?
The dashboard is edited in the analytics tool itself, without an application release: charts change, slices are added, formulas are refined. Changes affecting filtering go through approval — the rest are made without review.
The limitation is honest: the approach covers viewing and filtering ready-made reports but does not replace the analytics interface — ad-hoc queries and heavy exports remain in the tool itself.
Let's discuss your analytics embedding task
To come back with an estimate for the embedding project rather than generalities, we need your environment: where analytics lives, who views it, and by what attribute data is divided between users. Below is what we will need from you as input. With this set, we assemble a work plan and implementation timeline without follow-up rounds.
- A list of dashboards and the questions they answer: which metrics the manager views, and which the customer views in the portal.
- Access model: list of roles, visibility rules, whether there is customer segregation and by which field the dataset is sliced.
- Data sources: where the marts come from, how often they refresh, and the acceptable delay between an event and the chart.
- Authorization in the application: where the session is issued and at what point it is convenient to generate the signed token (signed embedding) taking user permissions into account.
- Embedding locations: a separate analytics section, customer card, admin tab — taking layout and responsive design into account.
- Environments and operations: how many environments, who the owner is, how we update dashboards, and what we do when the key changes.
In response, you receive the input data composition with gaps that need to be closed, an authorization flow diagram, a policy for key rotation and access revocation, a stage-by-stage work plan, and an implementation timeline with checkpoints.
Describe the task — which product, which users, and by what date the result is needed. We will come back with an estimate and a plan.







