Create and Manage Links

Purpose and Scope

Links are the primary resource in Dub: a link combines a destination URL with a short domain and slug, and then becomes the object marketers inspect, share, filter, and optimize. This guide explains the day-to-day management loop for links: create a link, find it again, inspect its performance, update organization or tracking settings, and delete or archive it when it is no longer needed. The supplied source evidence centers on the dashboard analytics layer, so the page emphasizes how the dashboard turns link records into operational decisions while also reflecting the official API terminology for create and bulk-create workflows.

A useful link-management workflow has two halves. The first half is mutation: creating links with a URL, optional domain, optional key, and related settings; later updating, deleting, or performing bulk actions. The second half is observation: knowing which links have clicks, leads, sales, folders, tags, and URL groupings so the right links are selected for follow-up work. Dub’s dashboard analytics page and link analytics badge make that observation loop visible, while the API provides the programmable surface for creating and managing links at workspace scope. Sources: apps/web/app/app.dub.co/(dashboard)/[slug]/links/analytics/page.tsx, apps/web/ui/links/link-analytics-badge.tsx

Relevant Source Files

  • apps/web/app/app.dub.co/(dashboard)/[slug]/links/analytics/client.tsx — wraps analytics content with workspace loading and event-limit gating so link analysis only renders when the workspace is ready and allowed to view it.
  • apps/web/app/app.dub.co/(dashboard)/[slug]/links/analytics/page.tsx — defines the dashboard route content for the workspace Analytics page and renders the shared analytics UI inside page chrome.
  • apps/web/ui/analytics/top-links.tsx — implements the “top links” analytics card, including link, folder, tag, base URL, and full URL groupings plus query-string filters for selected resources.
  • apps/web/ui/links/link-analytics-badge.tsx — renders per-link click, lead, and sales indicators and links users into filtered link analytics for a specific link.
  • apps/web/lib/analytics/types.ts — defines analytics filter and response types, including the linkId filter used to scope analytics to one or more links.
  • apps/web/lib/analytics/utils/index.ts — re-exports analytics utilities for query-string editing, CSV conversion, export formatting, interval data, and plan-aware date ranges.

Start by deciding whether the link is a one-off dashboard action, a repeated API operation, or part of a bulk import or campaign setup. In the official API surface, POST /links creates one link for the authenticated workspace. The request body includes url for the destination, domain when the link should use a specific short domain, key when the slug should be explicit, and keyLength when Dub should generate a slug of a chosen length. If no domain is provided, the API documentation describes falling back to the workspace primary domain, or dub.sh when the workspace has no domains.

After links exist, use analytics to decide what to retrieve, update, or remove. The workspace analytics page renders an Analytics component inside a page titled “Analytics,” wrapped in React Suspense with a layout loader. That means link management is not treated as a disconnected list operation; it is part of the workspace reporting experience. Users can move from a link row or badge into analytics filtered to that link, compare top links against folders and tags, and then return to the management surface with evidence about what should change. Sources: apps/web/app/app.dub.co/(dashboard)/[slug]/links/analytics/page.tsx, apps/web/ui/analytics/top-links.tsx

For bulk campaign operations, the official docs describe POST /links/bulk as a way to create up to 100 links for the authenticated workspace. That fits the same resource model as single-link creation but changes the operational shape: each item in the request array carries link fields such as url, domain, key, and keyLength. The supplied official help article also describes dashboard bulk actions for selected links, including tagging, moving to a folder, enabling or disabling conversion tracking, archiving, and deleting. Treat bulk operations as campaign-level changes where consistency and review matter more than speed alone.

Dashboard Analytics as the Management Workspace

The TopLinks component shows how the dashboard helps users find the right links to manage. It has two primary tabs: links and urls. The links tab can group results by individual links, folders, or tags; the urls tab can group by base URLs or full URLs. Each subtab maps to an analytics groupBy option such as top_links, top_folders, top_link_tags, top_base_urls, or top_urls. This is important for link management because the same campaign may need to be managed by short link, folder, tag, or destination URL depending on the task. Sources: apps/web/ui/analytics/top-links.tsx, apps/web/lib/analytics/types.ts

Filtering is handled through query parameters rather than hidden component state alone. TopLinks computes a filter key from the current subtab: linkId for links, folderId for folders, tagId for tags, and url for base URLs. When a user applies selected values, the component writes comma-separated values into the URL query string; when the filter is cleared, it deletes that parameter. This design makes filtered analytics shareable, navigable, and compatible with browser history, which is especially useful when a teammate needs to review the same set of links before a bulk update or deletion. Sources: apps/web/ui/analytics/top-links.tsx

The analytics type definitions make the filter contract explicit. AnalyticsFilters and EventsFilters both allow linkId to be either a plain string or a parsed filter, and include workspace-aware fields such as workspaceId and dataAvailableFrom. Event filters also preserve structural fields like event, page, limit, and sortBy, while allowing optional metadata inclusion. These types connect the dashboard’s link-selection behavior to the analytics query layer, so a “manage this link” interaction can become a precise analytics request rather than a broad workspace report. Sources: apps/web/lib/analytics/types.ts

The LinkAnalyticsBadge component is the per-link signal that links management and attribution together. It receives a link record without the user field and extracts domain, key, trackConversion, clicks, leads, and saleAmount. Every link can show clicks, but leads and sales are conditionally displayed when conversion tracking is enabled or when lead or sale data exists. This means a link can remain simple when it only needs click reporting, while conversion-oriented links surface richer performance data in the same management context. Sources: apps/web/ui/links/link-analytics-badge.tsx

On mobile, the badge links directly to /{slug}/links/analytics?linkId={link.id}, giving users a compact path from a link row to filtered analytics. On larger screens, it renders a tooltip with formatted counts, currency for sales, and the last-clicked timestamp when present. The component also integrates dashboard sharing through useShareDashboardModal, using the link’s domain and key. This is not merely decorative UI: it gives operators a quick decision point before changing a link, sharing its dashboard, or investigating why a link has no recent activity. Sources: apps/web/ui/links/link-analytics-badge.tsx

Permissions are part of safe link management. LinkAnalyticsBadge calls useCheckFolderPermission with the link’s folderId and the permission string folders.links.write. That indicates management capability can depend on the folder that contains the link, not only the workspace as a whole. When designing dashboard or automation workflows around updates and deletes, account for folder-scoped authorization: a user may be able to inspect analytics while not being allowed to edit every link in the filtered set. Sources: apps/web/ui/links/link-analytics-badge.tsx

API and Automation Reference

The official Links API describes POST /links for creating a single link in the authenticated workspace and POST /links/bulk for creating up to 100 links at once. The create payload includes url, domain, key, and keyLength, with url acting as the destination and domain plus key defining the short URL when supplied. Bulk creation uses an array of similar link objects. The official bulk-create snippet also notes that webhook events are not currently sent for bulk link creation, so downstream systems should not assume a webhook fan-out for that path.

TaskPublic surfacePractical notes
Create one linkPOST /linksUse for interactive creation, single automation events, or when each link needs immediate handling.
Create many linksPOST /links/bulkUse for campaign setup batches of up to 100 links; do not rely on webhook events for bulk creation based on the supplied official docs.
Inspect performanceDashboard analytics filtered by linkId, folderId, tagId, or urlUse the top-links card and link analytics badges to decide what needs editing or cleanup.
Update organizationDashboard bulk actions or API update flowsTags, folders, conversion tracking, archive state, and deletion are presented as bulk-management concepts in the official help evidence.
Share reportingLink dashboard sharing modalThe badge integrates sharing for a link’s domain and key.

The repository evidence supplied for this page does not include the CLI command implementation, so use the CLI as an automation convenience around the same link resource model rather than treating it as a separate kind of object. In practice, keep parity between dashboard, API, and CLI workflows: the same destination URL, short domain, key, folder or tag organization, and conversion-tracking intent should be recognizable no matter which interface created the link. For exact command syntax, pair this guide with the CLI reference page so operational scripts use the current binary behavior.

Operational Guardrails and Next Steps

Before updating or deleting links, narrow the set with analytics filters and confirm the selected grouping matches the job. A tag-level view is useful when campaign taxonomy is wrong; a folder-level view is better when ownership or permissions are the issue; a full-URL view is useful when many short links point to the same destination. Because the dashboard stores active filters in the query string, you can share the review state with another teammate before applying bulk changes. Sources: apps/web/ui/analytics/top-links.tsx, apps/web/lib/analytics/utils/index.ts

Also check workspace-level constraints before relying on analytics as part of a management flow. AnalyticsClient loads workspace state, shows a layout loader while that state is pending, and renders a workspace exceeded-events screen when the workspace has exceeded event limits, except for the pro-plan events-page case captured in the component condition. This means link records may still exist while analytics views are unavailable or gated. Build operator runbooks so mutation actions and analytics interpretation are not confused when a workspace is over its event allowance. Sources: apps/web/app/app.dub.co/(dashboard)/[slug]/links/analytics/client.tsx

Next, read the Links API overview for the full generated endpoint family, the bulk operations page for high-volume changes, and the CLI workflows page for command-line syntax. If your link-management work is driven by performance reporting, continue with the analytics overview and conversion tracking events pages so clicks, leads, sales, and sale amounts are interpreted consistently before links are changed or removed.