best-practicesUpdated 2025

ROI Tracking with utm_id: Complete Guide to GA4 ROAS

Track return on ad spend (ROAS) for LinkedIn, TikTok, and all paid campaigns in GA4 using utm_id cost import.

8 min readbest-practices

You're spending $50,000/month across LinkedIn, TikTok, Pinterest, and Reddit ads. When your CEO asks "What's our return on ad spend?", you open GA4 and see:

LinkedIn:

  • Revenue: $85,000 ✅
  • Cost: $0.00 ❌
  • ROAS: N/A ❌

TikTok:

  • Revenue: $62,000 ✅
  • Cost: $0.00 ❌
  • ROAS: N/A ❌

You know these campaigns are driving revenue, but you can't prove they're profitable because GA4 has no cost data.

The solution: utm_id + cost data import = full ROI visibility in GA4.

This guide shows you how to track ROAS, CPA, and profitability for every paid campaign—all within GA4's native reporting interface.

🚨 Not sure what's breaking your tracking?

Run a free 60-second audit to check all 40+ ways UTM tracking can fail.

Scan Your Campaigns Free

✓ No credit card ✓ See results instantly

The ROI Tracking Problem

Why GA4 Doesn't Have Your Cost Data

Auto-tagged platforms (Google Ads, Facebook, Microsoft) automatically send cost data to GA4. You see ROAS without any setup.

Non-auto-tagged platforms (LinkedIn, TikTok, Pinterest, Twitter, Reddit, Taboola, etc.) don't share cost data with GA4. You must manually import it.

Without cost import:

  • ✅ GA4 tracks sessions, conversions, revenue
  • ❌ GA4 doesn't know ad spend
  • ❌ Can't calculate ROAS (Revenue / Ad Spend)
  • ❌ Can't calculate CPA (Ad Spend / Conversions)
  • ❌ Can't determine campaign profitability

With cost import (via utm_id):

  • ✅ GA4 tracks sessions, conversions, revenue
  • GA4 knows ad spend (you imported it)
  • ROAS calculated automatically (Revenue / Cost)
  • CPA calculated automatically (Cost / Conversions)
  • Profitability visible (Revenue - Cost = Profit)

How utm_id Enables ROI Tracking

The Complete Flow

Step 1: Add utm_id to campaign URLs

Code
LinkedIn ad:
https://yoursite.com/demo?utm_id=LI-2025-01-DEMO&utm_source=linkedin&utm_medium=cpc&utm_campaign=product-demo

Step 2: GA4 captures utm_id with every session

When users click, GA4 stores:

  • Campaign ID: LI-2025-01-DEMO
  • Sessions, conversions, revenue

Step 3: Export cost data from ad platform

LinkedIn Ads → Campaign Manager → Performance → Export

  • Daily cost for Campaign ID 123456789

Step 4: Create cost CSV with matching Campaign ID

Csv
Date,Campaign ID,Cost
20250101,LI-2025-01-DEMO,987.50
20250102,LI-2025-01-DEMO,1024.80
20250103,LI-2025-01-DEMO,956.30

Step 5: Upload to GA4 Data Import

GA4 → Admin → Data import → Cost data → Upload CSV

Step 6: GA4 matches utm_id to cost

GA4 takes Campaign ID from CSV and matches to Campaign ID from traffic (utm_id parameter).

Step 7: ROI metrics appear in reports

GA4 → Reports → Advertising → Campaign performance

Now you see:

  • Cost (imported from CSV)
  • ROAS (Revenue ÷ Cost)
  • CPA (Cost ÷ Conversions)

Real Example: $50k/Month Multi-Platform ROI

Client: E-commerce brand Channels: LinkedIn ($25k/month), TikTok ($20k/month), Pinterest ($5k/month) Problem: No ROI visibility in GA4 before utm_id implementation

Before utm_id (No Cost Data)

What GA4 showed:

CampaignSessionsConversionsRevenue
LinkedIn - Product Demo4,000120$60,000
TikTok - Brand Awareness12,000240$72,000
Pinterest - Shopping2,00060$18,000

Total: 18,000 sessions, 420 conversions, $150,000 revenue

Questions they couldn't answer:

  • Which channel has best ROAS?
  • Should we increase LinkedIn or TikTok budget?
  • Is Pinterest worth the $5k/month?
  • What's our blended ROAS across channels?

After utm_id + Cost Import

Campaign URLs updated:

Code
LinkedIn:
?utm_id=LI-2025-01-DEMO&utm_source=linkedin&utm_medium=cpc&utm_campaign=product-demo

TikTok:
?utm_id=TT-2025-01-BRAND&utm_source=tiktok&utm_medium=cpc&utm_campaign=brand-awareness

Pinterest:
?utm_id=PIN-2025-01-SHOP&utm_source=pinterest&utm_medium=cpc&utm_campaign=shopping

Cost CSV uploaded:

Csv
Date,Campaign ID,Cost
20250101,LI-2025-01-DEMO,833.33
20250101,TT-2025-01-BRAND,666.67
20250101,PIN-2025-01-SHOP,166.67
(... daily costs for 30 days)

What GA4 now shows:

CampaignSessionsConversionsRevenueCostROASCPA
LinkedIn4,000120$60,000$25,0002.4x$208
TikTok12,000240$72,000$20,0003.6x$83
Pinterest2,00060$18,000$5,0003.6x$83
Total18,000420$150,000$50,0003.0x$119

Insights Revealed

Discovery #1: TikTok and Pinterest had same ROAS (3.6x)

  • Both outperforming LinkedIn (2.4x)
  • Should prioritize TikTok/Pinterest budget increases

Discovery #2: LinkedIn had lowest ROAS but highest CPA

  • $208 cost per acquisition (2.5x more expensive than TikTok/Pinterest)
  • Needed creative refresh or better targeting

Discovery #3: Pinterest ROI matched TikTok despite 4x less spend

  • Untapped opportunity
  • Immediate budget increase from $5k to $15k/month

Actions Taken (Based on Data)

Budget reallocation:

  • LinkedIn: $25k → $15k (-40%)
  • TikTok: $20k → $25k (+25%)
  • Pinterest: $5k → $15k (+200%)
  • Total budget: $50k (unchanged)

Result after 2 months:

  • Total revenue: $150k → $210k (+40%)
  • Blended ROAS: 3.0x → 4.2x (+40%)
  • LinkedIn ROAS improved to 3.0x (creative refresh worked)

This was only possible because utm_id enabled cost import.

😰 Is this your only tracking issue?

This is just 1 of 40+ ways UTM tracking breaks. Most marketing teams have 8-12 critical issues they don't know about.

• 94% of sites have UTM errors

• Average: $8,400/month in wasted ad spend

• Fix time: 15 minutes with our report

✓ Connects directly to GA4 (read-only, secure)

✓ Scans 90 days of data in 2 minutes

✓ Prioritizes issues by revenue impact

✓ Shows exact sessions affected

Get Your Free Audit Report

GA4 ROI Reports with Cost Data

Once you've imported cost via utm_id, these reports become available:

Report 1: Campaign Performance (Primary ROI View)

Location: GA4 → Reports → Advertising → Campaign performance

Metrics shown:

  • Sessions
  • Conversions
  • Cost ← Imported via utm_id
  • ROAS ← Revenue / Cost
  • CPA ← Cost / Conversions
  • Revenue
  • Purchase revenue

How to use it:

  1. Sort by ROAS descending
  2. Identify high-performing campaigns (ROAS > target)
  3. Scale high-ROAS campaigns
  4. Pause or optimize low-ROAS campaigns

Report 2: Source/Medium ROI Comparison

Location: GA4 → Reports → Acquisition → Traffic acquisition

Filter: Add filter "Session medium" = "cpc" (paid traffic only)

Metrics:

  • Sessions
  • Conversions
  • Cost
  • ROAS

View by: Session source / medium

Example output:

Source / MediumSessionsConversionsCostROAS
linkedin / cpc4,000120$25,0002.4x
tiktok / cpc12,000240$20,0003.6x
pinterest / cpc2,00060$5,0003.6x

How to use it:

  • Compare platform-level performance
  • Decide channel budget allocation

Report 3: Explore - ROI Deep Dive

Location: GA4 → Explore → Free form

Dimensions:

  • Campaign ID (utm_id)
  • Campaign name
  • Source / Medium
  • Date

Metrics:

  • Sessions
  • Conversions
  • Conversion rate
  • Cost
  • Revenue
  • ROAS
  • Profit ← Create calculated metric (Revenue - Cost)

Custom calculated metric: Profit

GA4 → Explore → Create calculated metric:

Code
Name: Profit
Formula: Revenue - Cost

Now you can see actual profit per campaign, not just ROAS.

Report 4: Time-Series ROI Trend

Location: GA4 → Explore → Line chart

Setup:

  • X-axis: Date (daily or weekly)
  • Y-axis: ROAS
  • Breakdown: Campaign ID

Use case: See how ROAS changes over time for each campaign

  • Identify campaigns with declining ROAS (need optimization)
  • Spot campaigns with improving ROAS (scale these)

Advanced: Profitability Analysis

ROAS is good, but profit is better. GA4 can calculate profit if you know your margins.

Scenario: 40% Margin Business

Your business:

  • Product cost: 60% of sale price
  • Margin: 40%

Example:

  • Sale: $100
  • Cost of goods: $60
  • Gross profit: $40

To calculate true ROI:

Code
Profit = (Revenue × Margin) - Ad Spend
ROI % = (Profit / Ad Spend) × 100

GA4 Calculated Metric: True Profit

Create in GA4 Explore:

Code
Name: Gross Profit
Formula: (Revenue * 0.40) - Cost

(Where 0.40 = your margin percentage)

Example with LinkedIn campaign:

  • Revenue: $60,000
  • Cost: $25,000
  • ROAS: 2.4x (looks okay)

But true profitability:

  • Gross profit: ($60,000 × 0.40) - $25,000 = $24,000 - $25,000 = -$1,000
  • The campaign is losing money!

ROAS > 1.0x doesn't guarantee profitability if you have product costs.

Breakeven ROAS Calculator

Formula:

Code
Breakeven ROAS = 1 / Margin

Example (40% margin):
Breakeven ROAS = 1 / 0.40 = 2.5x

Interpretation:

  • ROAS < 2.5x → Losing money
  • ROAS = 2.5x → Breaking even
  • ROAS > 2.5x → Profitable

In our LinkedIn example:

  • ROAS: 2.4x
  • Breakeven: 2.5x
  • Result: Losing $1,000

Action: Optimize LinkedIn campaign to reach 2.5x+ ROAS or pause.

Common ROI Metrics Explained

ROAS (Return on Ad Spend)

Formula:

Code
ROAS = Revenue / Cost

Example:

  • Revenue: $72,000
  • Cost: $20,000
  • ROAS: $72,000 / $20,000 = 3.6x

Interpretation: For every $1 spent, you get $3.60 back.

Good ROAS depends on your margin:

  • High margin (70%+): ROAS > 1.5x is good
  • Medium margin (40-50%): ROAS > 2.5x needed
  • Low margin (20-30%): ROAS > 4.0x required

CPA (Cost Per Acquisition)

Formula:

Code
CPA = Cost / Conversions

Example:

  • Cost: $20,000
  • Conversions: 240
  • CPA: $20,000 / 240 = $83.33

Interpretation: You're paying $83.33 to acquire each customer.

Use case: Compare CPA across channels to find most efficient acquisition source.

ROI (Return on Investment)

Formula:

Code
ROI % = ((Revenue - Cost) / Cost) × 100

Example:

  • Revenue: $72,000
  • Cost: $20,000
  • ROI: (($72,000 - $20,000) / $20,000) × 100 = 260%

Interpretation: You made 260% return (2.6x profit) on your investment.

ROAS vs ROI:

  • ROAS: 3.6x (includes cost in denominator)
  • ROI: 260% (profit / cost)
  • Both measure similar thing, different formats

CPC (Cost Per Click)

Formula:

Code
CPC = Cost / Sessions

Example:

  • Cost: $20,000
  • Sessions: 12,000
  • CPC: $20,000 / 12,000 = $1.67

Interpretation: Each click costs $1.67.

Use case: Identify expensive traffic sources (high CPC) that may need optimization.

Troubleshooting ROI Tracking

Issue: Cost Shows $0.00 Even After Upload

Possible causes:

Cause 1: utm_id mismatch

  • URL utm_id: LI-2025-01-DEMO
  • CSV Campaign ID: linkedin-demo-jan (doesn't match!)

Fix: Ensure exact match (case-sensitive)

Cause 2: Date range mismatch

  • GA4 report: Jan 1-15
  • CSV data: Jan 16-31 (no overlap)

Fix: Upload CSV covering full date range

Cause 3: Processing delay

  • Cost data takes 24-48 hours to appear

Fix: Wait, then check again

Issue: ROAS Looks Impossibly High

Example: ROAS = 50x (seems too good to be true)

Possible causes:

Cause 1: Missing days in CSV

  • CSV only has 5 days of cost
  • GA4 has 30 days of revenue
  • ROAS artificially inflated

Fix: Upload complete cost data for full period

Cause 2: Cost data too low

  • CSV has $500 cost
  • Platform actually charged $5,000
  • Decimal point error or missing row

Fix: Verify cost data matches platform billing

Issue: Conversions Tracked But No Revenue

Problem: CPA shows correctly but ROAS = N/A

Cause: GA4 isn't capturing purchase revenue

Fix:

  1. Verify e-commerce tracking is set up
  2. Check purchase events include value parameter
  3. GA4 → Reports → Monetization → Ecommerce purchases (verify revenue flows)

Prevention & Maintenance

Monthly ROI Review Checklist

Week 1: Upload cost data CSV for previous month ✅ Week 1: Verify cost appears in GA4 Advertising reports ✅ Week 2: Review ROAS by campaign ✅ Week 2: Identify campaigns below breakeven ROAS ✅ Week 3: Optimize or pause low-ROAS campaigns ✅ Week 3: Increase budget for high-ROAS campaigns ✅ Week 4: Document changes and set new ROAS targets

Automation Options

Manual CSV uploads work but take time. Consider automation if spending $10k+/month:

Option 1: Third-party tools

  • Supermetrics ($99/month) - Auto-syncs cost daily
  • Windsor.ai ($49/month) - Connects 50+ platforms
  • Funnel.io ($299/month) - Enterprise solution

Option 2: Custom API integration

  • Use GA4 Data Import API
  • Schedule daily script to pull cost from ad platforms
  • Auto-format and upload to GA4

Option 3: Google Sheets + Apps Script

  • Weekly manual paste of cost data into Sheet
  • Apps Script auto-formats and uploads to GA4
  • Semi-automated middle ground

✅ Fixed this issue? Great! Now check the other 39...

You just fixed one tracking issue. But are your Google Ads doubling sessions? Is Facebook attribution broken? Are internal links overwriting campaigns?

Connects to GA4 (read-only, OAuth secured)

Scans 90 days of traffic in 2 minutes

Prioritizes by revenue impact

Free forever for monthly audits

Run Complete UTM Audit (Free Forever)

Join 2,847 marketers fixing their tracking daily

FAQ

What's a good ROAS target?

Depends on your margin. Use this formula:

Code
Minimum ROAS = 1 / Margin

Examples:
- 50% margin → Minimum ROAS = 2.0x
- 40% margin → Minimum ROAS = 2.5x
- 30% margin → Minimum ROAS = 3.3x
- 20% margin → Minimum ROAS = 5.0x

Anything below minimum ROAS = losing money.

Can I track ROI for organic channels (email, social)?

You can track conversions and revenue, but "ROAS" doesn't apply (no ad cost per click).

Alternative metrics:

  • Conversion rate
  • Revenue per session
  • Total revenue
  • Customer lifetime value

How do I compare paid vs organic ROI?

For paid channels: ROAS (Revenue / Ad Cost)

For organic channels: ROI based on production cost:

Code
Email ROI = Revenue / ESP Cost
Content ROI = Revenue / Content Production Cost
SEO ROI = Revenue / SEO Tool/Agency Cost

Not apples-to-apples, but helps with budget allocation.

What if I run campaigns across multiple platforms?

Option 1: Blended ROAS (combine all platforms)

Code
Total Revenue / Total Cost = Blended ROAS

Option 2: Per-platform ROAS (GA4 Traffic Acquisition report)

  • Compare LinkedIn vs TikTok vs Pinterest
  • Allocate budget to best performers

Should I include agency fees in cost data?

Yes, for true ROI. Include:

  • Platform ad spend ✅
  • Agency management fees ✅
  • Creative production costs ✅

Total cost should reflect everything you paid to run that campaign.

Can I import historical cost data?

Yes! GA4 allows up to 90 days of backdated cost import.

Csv
Date,Campaign ID,Cost
20241015,LI-2024-Q4,850.00  ← 86 days ago, works!

Limitation: Can't import data older than 90 days.

Conclusion

ROI tracking with utm_id in 5 steps:

  1. Add utm_id to campaign URLs (LinkedIn, TikTok, Pinterest, etc.)
  2. Upload cost data CSV to GA4 Data Import
  3. Wait 24-48 hours for processing
  4. Check GA4 Advertising reports (cost, ROAS, CPA now visible)
  5. Optimize based on data (scale high-ROAS, pause low-ROAS campaigns)

Once set up, you'll have complete ROI visibility:

  • ROAS by campaign
  • CPA by channel
  • Profitability analysis
  • Data-driven budget decisions

No more guessing which campaigns are profitable. utm_id + cost import = full transparency.


Related: GA4 Cost Import Setup Guide (Step-by-Step)

UTM

Get Your Free Audit in 60 Seconds

Connect GA4, run the scan, and see exactly where tracking is leaking budget. No credit card required.

Trusted by growth teams and agencies to keep attribution clean.