Creating Links
Learn how to create powerful short links with platform-specific routing, attribution tracking, and UTM parameters.
Overview
LinkForty links are more than just URL shorteners. Each link can:
- Route users to different destinations based on their device (iOS, Android, Web)
- Track clicks and app installs with configurable attribution windows
- Include UTM parameters for campaign tracking
- Apply targeting rules (geographic, language, device)
- Generate QR codes for offline-to-online attribution
- Include social preview tags for rich link sharing
- Be served from your own branded domain instead of the shared LinkForty domain
Before creating links, you must first create a template. Templates define default settings for your links, such as domain, UTM parameters, and platform-specific URLs.
See Link Templates to create your first template.
Creating Your First Link
Via Dashboard
Step 1: Navigate to Links Page
- Log in to your LinkForty dashboard
- Click "Links" in the left sidebar
- Click the "Create Link" button (top right)
Step 2: Select a Template
Template (required)
Select from dropdown: e.g., "Default Template" or "Instagram Campaign"
When you select a template, its default settings will automatically pre-populate the form fields in the Advanced Options section. You can use these defaults as-is, or override any value you want to customize for this specific link.
Templates provide default settings for your link, including:
- Platform URLs - iOS App Store, Android Play Store, and Web fallback URLs
- Attribution Window - How long clicks remain valid for attribution
- UTM Parameters - Campaign tracking parameters
- Targeting Rules - Geographic, language, and device targeting
Step 3: Fill in Basic Information
Original URL (required)
https://example.com/products/wireless-headphones
This is where users will be sent if no platform-specific URL matches.
Title (optional, recommended)
Wireless Headphones - Spring Sale
Internal reference for your team. Not visible to users.
Description (optional)
Q2 2024 Instagram campaign for new wireless headphones launch
Helps organize and search for links later.
Step 4: Configure Platform-Specific URLs
Route users based on their device.
If your selected template has default platform URLs configured, these fields will be automatically filled. You can leave them as-is to use the template defaults, or enter different values to override them for this specific link.
iOS URL (optional)
https://apps.apple.com/app/your-store/id123456789
When clicked on iPhone/iPad, users see App Store.
Android URL (optional)
https://play.google.com/store/apps/details?id=com.yourstore
When clicked on Android, users see Google Play.
Web Fallback URL (optional)
https://example.com/products/wireless-headphones?platform=web
Destination for desktop/laptop users. Falls back to Original URL if empty.
Step 5: Set Attribution Window
Choose how long clicks remain valid for attribution:
| Window | Use Case | Conversion Rate |
|---|---|---|
| 1 hour | Immediate actions, privacy-focused | 5-10% |
| 24 hours | Direct response campaigns | 15-25% |
| 72 hours | Short promotional campaigns | 25-35% |
| 168 hours (7 days) | Industry standard, balanced | 35-50% |
| 336 hours (14 days) | Retargeting campaigns | 40-55% |
| 720 hours (30 days) | Brand awareness | 45-60% |
| 2160 hours (90 days) | Long consideration cycles | 50-70% |
Recommendation: Start with 7 days (168 hours) for most campaigns.
How it works:
- User clicks your link at 10:00 AM on Monday
- Link creates a fingerprint and stores it
- User installs your app at 3:00 PM on Wednesday (65 hours later)
- SDK checks for matching fingerprint within attribution window
- If match found (65h < 168h), install is attributed to your link
Step 6: Add UTM Parameters (optional)
Track campaign performance:
{
"utm_source": "instagram",
"utm_medium": "social",
"utm_campaign": "spring-sale-2024",
"utm_term": "wireless-headphones",
"utm_content": "carousel-ad-1"
}
These parameters are automatically appended to your destination URLs:
https://example.com/products/wireless-headphones?utm_source=instagram&utm_medium=social&utm_campaign=spring-sale-2024
Step 7: Custom Short Code (optional)
By default, LinkForty generates random codes like abc123. You can customize:
Custom Code: spring-sale
Generated Link: https://lnk.forty.com/spring-sale
Requirements:
- 4-30 characters
- Alphanumeric only (a-z, A-Z, 0-9, hyphens, underscores)
- Must be unique
Step 8: Set Expiration (optional)
Make links expire after a specific date:
Expires At: 2024-03-31 23:59:59
After expiration the link stops resolving. See Link Settings for exactly what a visitor sees.
Step 9: Create Link
Click "Create Link" button. Your link is instantly live:
https://lnk.forty.com/abc123
Creating Links via API
Authentication
Get your API key from Settings → API Keys.
export LINKFORTY_API_KEY="your-api-key-here"
Basic Link Creation
curl -X POST https://api.linkforty.com/api/links \
-H "Authorization: Bearer $LINKFORTY_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"templateId": "550e8400-e29b-41d4-a716-446655440000",
"originalUrl": "https://example.com/product/123",
"title": "Product 123 Campaign",
"iosUrl": "https://apps.apple.com/app/id123456789",
"androidUrl": "https://play.google.com/store/apps/details?id=com.app",
"attributionWindowHours": 168,
"utmParameters": {
"source": "facebook",
"medium": "cpc",
"campaign": "summer-2024"
}
}'
Response:
{
"id": "link_abc123xyz",
"short_code": "abc123",
"short_url": "https://lnk.forty.com/abc123",
"original_url": "https://example.com/product/123",
"ios_url": "https://apps.apple.com/app/id123456789",
"android_url": "https://play.google.com/store/apps/details?id=com.app",
"attribution_window_hours": 168,
"utm_parameters": {
"source": "facebook",
"medium": "cpc",
"campaign": "summer-2024"
},
"created_at": "2024-01-15T10:30:00Z",
"is_active": true
}
With Custom Short Code
curl -X POST https://api.linkforty.com/api/links \
-H "Authorization: Bearer $LINKFORTY_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"templateId": "550e8400-e29b-41d4-a716-446655440000",
"originalUrl": "https://example.com/sale",
"customCode": "summer-sale",
"attributionWindowHours": 336
}'
Generates: https://lnk.forty.com/summer-sale
With Targeting Rules
curl -X POST https://api.linkforty.com/api/links \
-H "Authorization: Bearer $LINKFORTY_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"templateId": "550e8400-e29b-41d4-a716-446655440000",
"originalUrl": "https://example.com/product/123",
"targetingRules": {
"countries": ["US", "CA", "GB"],
"languages": ["en"],
"devices": ["ios", "android"]
}
}'
With Expiration
curl -X POST https://api.linkforty.com/api/links \
-H "Authorization: Bearer $LINKFORTY_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"templateId": "550e8400-e29b-41d4-a716-446655440000",
"originalUrl": "https://example.com/flash-sale",
"expiresAt": "2024-12-31T23:59:59Z"
}'
Using Link Templates
Templates speed up link creation by pre-filling common settings.
Creating a Template
Via Dashboard:
- Go to Settings → Link Templates
- Click "Create Template"
- Fill in defaults:
- iOS URL:
https://apps.apple.com/app/id123456789 - Android URL:
https://play.google.com/store/apps/details?id=com.app - Attribution Window: 168 hours
- UTM Medium:
social
- iOS URL:
- Click "Save Template"
Via API:
curl -X POST https://api.linkforty.com/api/templates \
-H "Authorization: Bearer $LINKFORTY_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"name": "Social Media Default",
"iosUrl": "https://apps.apple.com/app/id123456789",
"androidUrl": "https://play.google.com/store/apps/details?id=com.app",
"attributionWindowHours": 168,
"utmParameters": {
"medium": "social"
}
}'
Using a Template
When creating links, select your template. Only fill in unique fields:
curl -X POST https://api.linkforty.com/api/links \
-H "Authorization: Bearer $LINKFORTY_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"templateId": "550e8400-e29b-41d4-a716-446655440000",
"originalUrl": "https://example.com/new-product",
"utmParameters": {
"source": "instagram",
"campaign": "launch-week"
}
}'
Template fills: iosUrl, androidUrl, attributionWindowHours, utm_medium: "social"
You override: utm_source, utm_campaign
See Link Templates Guide for more details.
Best Practices
1. Always Use Platform-Specific URLs
Bad:
{
"originalUrl": "https://example.com/product"
}
Good:
{
"originalUrl": "https://example.com/product",
"iosUrl": "https://apps.apple.com/app/id123",
"androidUrl": "https://play.google.com/store/apps/details?id=com.app",
"webFallbackUrl": "https://example.com/product?platform=web"
}
Why: Improves attribution accuracy by 3-5x. Users on mobile without app installed go to store instead of dead-end web page.
2. Use Descriptive Titles
Bad:
Title: Link 1
Good:
Title: Instagram Story - Summer Sale - Wireless Headphones
Why: Easier to find links later. Team knows what campaign it's for.
3. Match Attribution Window to Campaign Type
| Campaign Type | Recommended Window |
|---|---|
| Flash sales (24h) | 24-72 hours |
| Product launches | 7-14 days |
| Brand awareness | 14-30 days |
| Referral programs | 30-90 days |
| Content marketing | 7-30 days |
| Retargeting | 14-30 days |
4. Consistent UTM Naming
Create a naming convention and stick to it:
{
"utm_source": "instagram", // lowercase, platform name
"utm_medium": "social", // lowercase, channel type
"utm_campaign": "spring-2024", // lowercase-with-dashes, semantic
"utm_term": "headphones", // lowercase, product category
"utm_content": "carousel-1" // lowercase-with-dashes, creative variant
}
5. Use Custom Codes for Memorable Links
For marketing materials:
https://lnk.forty.com/spring-sale
For print/QR codes:
https://lnk.forty.com/menu
For referrals:
https://lnk.forty.com/john-referral
6. Set Expiration for Limited Campaigns
Always set expiration for:
- Flash sales
- Event promotions
- Limited-time offers
- Seasonal campaigns
Example:
{
"title": "Black Friday 2024",
"expiresAt": "2024-11-30T23:59:59Z"
}
Link Settings
Three per-link settings that apply after the link is created, and behave in ways that are easy to be surprised by.
Expiration Date
Set expiresAt to have a link stop working after a given moment:
curl -X PATCH https://api.linkforty.com/api/links/link_abc123xyz \
-H "Authorization: Bearer $LINKFORTY_API_KEY" \
-H "Content-Type: application/json" \
-d '{"expiresAt": "2026-03-31T23:59:59Z"}'
To remove an expiration date, send null explicitly — omitting the field leaves the existing date in place:
{ "expiresAt": null }
What a visitor sees. An expired link responds exactly as though it never existed: 404, with no indication that it was ever a real link. There is no "this link has expired" page. That is deliberate — an expired-link page would confirm to anyone probing short codes that a given code was once valid.
A job runs at the top of every hour and deactivates links whose expiry has passed. A link can therefore keep resolving for up to an hour after the timestamp you set. Set the expiry an hour early if the cut-off has to be exact.
Click-ID Passthrough
When enabled, the redirect appends an lf_click parameter carrying the ID of that specific click to the destination URL:
Destination configured: https://example.com/spring-sale
Visitor is sent to: https://example.com/spring-sale?lf_click=3f9a1c2e-...
That value is the primary key of the click event in your analytics. Handing it to the landing page lets a downstream tool — your own analytics, a data warehouse, a CRM — join a session on your site back to the exact click that produced it, rather than guessing from timestamps.
Only web destinations are touched. The parameter is added to HTTP and HTTPS destinations only. A custom-scheme destination (myapp://…) is left exactly as configured, as is any destination that cannot be parsed as an absolute URL.
lf_click is a reserved parameter nameDo not use lf_click for your own purposes on a destination URL. When passthrough is on, LinkForty sets this key and will overwrite a value you put there yourself.
Turn it off for signature-sensitive destinations. Anything that validates its own query string — S3 presigned URLs, signed CDN links, payment callbacks — will reject the request once an extra parameter is appended. Set appendClickId to false on those links:
{ "appendClickId": false }
The default differs between Cloud and self-hosted:
| Deployment | Default |
|---|---|
| LinkForty Cloud | On — new links append lf_click unless you opt out |
| Self-hosted (Core) | Off — opt in per link |
If you run both, do not assume a link behaves the same way in each.
Custom Domain
A link can be issued on any verified domain in your workspace rather than the default one, chosen when you create or edit it. See Custom Domains for adding and verifying them.
Advanced Features
Deep Link Parameters
Pass custom data to your app after install:
{
"originalUrl": "https://example.com/product/123?deeplink_param=value",
"iosUrl": "https://apps.apple.com/app/id123",
"androidUrl": "https://play.google.com/store/apps/details?id=com.app"
}
After user installs and opens app:
const deepLinkData = await LinkForty.getInstallData();
// Returns: { deeplink_param: "value" }
// Navigate to specific product
navigateToProduct(deepLinkData.deeplink_param);
Social Preview Tags
Add Open Graph tags for rich previews. These are per-link overrides — they take priority over your workspace's share card, so set them only when this specific link needs a different card:
curl -X POST https://api.linkforty.com/api/links \
-H "Authorization: Bearer $LINKFORTY_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"templateId": "550e8400-e29b-41d4-a716-446655440000",
"originalUrl": "https://example.com/product/123",
"socialPreview": {
"title": "Wireless Headphones - 50% Off",
"description": "Premium noise-cancelling headphones. Limited time offer.",
"imageUrl": "https://example.com/images/headphones-og.jpg"
}
}'
When shared on social media, shows:
- Image preview
- Custom title
- Custom description
See the Create Link API reference for all available social preview fields.
Troubleshooting
Link Returns 404
Cause: Short code doesn't exist or link was deleted.
Solution:
- Check if link exists: GET
/api/links/:shortCode - Verify link is active:
is_active: true - Check expiration:
expires_atis null or future date
Link Not Redirecting to Correct Platform
Cause: Platform detection issue.
Solution:
- Test user-agent detection:
curl -A "Mozilla/5.0 (iPhone; CPU iPhone OS 14_0 like Mac OS X)" \
https://lnk.forty.com/abc123 - Verify iOS/Android URLs are set
- Check targeting rules aren't blocking
Attribution Not Working
Cause: SDK not initialized or fingerprint mismatch.
Solution:
- Verify SDK is initialized:
LinkForty.init() - Check attribution window hasn't expired
- Confirm user clicked link before installing
- Test on real device (simulators may fail fingerprint matching)
See the Deferred Deep Linking guide for troubleshooting fingerprint matching issues.
Next Steps
- Link Templates - Create reusable templates
- Bulk Operations - Create and manage links in bulk via API
- QR Codes - Generate QR codes for offline attribution
- SDK Integration - Set up mobile SDK
- Analytics - Track link performance