Magai

How to Use AI for Client Reporting That Holds Up

How to use AI for client reporting: turn an export into a monthly narrative, check it against the data, and catch what the model gets wrong.

By Dustin W. StoutPublished 20 min read
A desk with a printed monthly report and a pencil, the start of using AI for client reporting

Six client reports are due Friday, and you are still copying numbers out of an export.

The numbers aren't the hard part. The export already has them. The hard part is the page that says what moved, why it moved, and what you will do about it.

Here is how to use AI for client reporting: put the client's export and rules in one thread, make the model check the data before it writes a word, tell it what the data can't know, and have a second reader check the draft before the client sees it.

That last step is the one that gets skipped on a Friday.

A model writes a wrong paragraph exactly as smoothly as a right one. When a tracking problem looks like a performance problem, you get a confident, well written explanation of the performance problem. The client believes it because it reads well.

So treat the model as a fast junior analyst who has never met the client. Quick, tireless, and missing everything you didn't hand over.

This post follows one monthly report from export to send. The client is Harbor & Pine, a made up outdoor gear store, and its owner is Dana. The export is a sample with one tracking problem planted in it.

Every prompt below was run on that export, with only the file contents and earlier replies left out of the code blocks. The replies are quoted from those runs, including the parts that went wrong.

How to use AI for client reporting starts with one thread per client

The first mistake happens before any prompt. It's the wrong client's brief in the wrong thread.

You have six clients, each with a voice and a banned word list. Put them all in one chat and one client's rules leak into another client's report. It only has to happen once.

So make a folder in Magai for each client, and start a new thread in it every month. Everything about Harbor & Pine lives in that folder. Nothing about anyone else does. (More on how agencies set this up is on the marketing agencies page.)

Then upload the files into the thread. This is the capability the whole job leans on.

What you want is the model reading the client's own export, in a thread that already holds the client's rules. Not a blank chat that has no idea which client it's writing for, or what you promised them last month.

A model working from your uploaded export is working from your numbers. A model working from memory is working from marketing in general.

Here is the part of the sample export the report is built on:

Channel August sessions September sessions August revenue September revenue
Organic Search 18,400 20,100 $27,810 $32,470
Paid Search 9,200 9,500 $23,460 $23,375
Paid Social 12,600 7,800 $14,175 $9,360
Email 5,100 5,400 $19,975 $26,730
Direct 7,300 10,470 $10,530 $11,790
Referral 2,900 3,100 $2,320 $2,635
Total 55,500 56,370 $98,270 $106,360

The real file has more columns. The paid rows also carry ad spend and the clicks the ad platform counted, and that is deliberate, as the next step shows. A second file, weekly.csv, breaks four things out by week: Paid Social sessions and clicks, Direct sessions, and email revenue. A monthly total hides when something broke. A weekly one shows the week.

The brief is the last file, and it's the one that makes the report sound like your agency and not like a model. Here is the Harbor & Pine brief:

CLIENT BRIEF: Harbor & Pine Outfitters (sample client)
Owner: Dana Whitfield. Online store selling camping and trail gear.
Agency: Fieldhouse Digital. Report goes to Dana by email on the first Friday of the month.
Goals for September 2026: online revenue of $105,000. Blended paid ROAS (paid search plus paid social revenue divided by ad spend) of at least 2.5.
Voice: plain and warm, like a trusted neighbor who happens to know the numbers. Short sentences. No hype.
Never use these words: skyrocket, game-changing, crushing it, leverage, synergy, stellar.
Always say 'online revenue', never 'sales'. Show percent changes to one decimal. Name the dollar amount first, then the percent.
Dana is not a marketer. Explain any metric the first time it appears.

Each line earns its place. The goal numbers give the model something to measure against. The banned words get checked by hand at the end, because a list is an instruction and not a guarantee. "Online revenue, never sales" is the kind of rule a client cares about and no model will guess. The last line is why ROAS, which is revenue divided by ad spend, gets a definition the first time it appears.

Magai never uses what you put in a thread to train any model, from any provider on the platform. Read your client contracts anyway, because what you may upload is a promise between you and them.

If uploading a file into a thread is new to you, the lesson planning walkthrough does it with a reading passage instead of a spreadsheet.

Two printed export pages side by side on a desk with a pencil about to circle one row, the start of AI client reporting

Make it check the export before it writes a word

Here is what skipping this step looks like. The first prompt in the thread was the lazy one:

Write the September monthly report narrative for Dana. Cover what moved, why, and what we do next. Keep it under 350 words.

The reply was tidy. It opened with Dana's name, used none of the banned words, and got every figure in the first paragraph right. September online revenue was $106,360, up $8,090 from August and $1,360 over goal.

The problem sat in the third paragraph: "Social accounted for the decline: its revenue fell $4,815 (34.0%)." That is a verdict, written in the voice of someone who knows. The same reply told Dana that blended paid ROAS was 2.3 against a goal of 2.5.

To its credit, the model flagged the gap between ad clicks and site sessions a paragraph later. But a client reads the verdict first. The report said Paid Social failed, and the export doesn't support that.

Now the same files with the check first. Pick a model from the picker in Magai, or type /Claude at the start of the message, and send this:

I'm writing the September report for this client. Before any writing, check the data. List what you see in each file, check whether the numbers agree with each other, and flag anything that looks like a tracking or data problem rather than a real change in performance. Do not write the report yet.

The last line matters most. Without it, the model checks the data in one paragraph and then writes the report anyway.

The reply split by file and did the arithmetic first. Totals agreed across both files, and it gave the August to September change for every channel, dollars before percents, which is the order the brief asked for. Then it raised its flags:

Paid Social sessions fell by 4,800 (38.1%), while its platform clicks fell by only 200 (1.6%).

It also did the part a person skips on a Thursday. On the weekly file it divided sessions by clicks for each week. Week one came out at 98.3%. The remaining weeks sat between 48.3% and 52.7%. Something broke between the first week of September and the second, and in a real account that's the line where you open the ad platform.

It refused to guess why. It listed a change in how clicks become measured sessions, a tracking or attribution problem, and a real change after the click, then said:

The file alone cannot distinguish among these.

It also noticed that the blank ad spend cells on the unpaid channels looked like "not applicable" and not zero, which matters the moment someone averages the column.

Four questions belong in every version of this prompt. The model covered all four unprompted, but write them down so a tired Thursday doesn't depend on it:

  1. Do the totals agree between files?
  2. Are blank cells blanks or zeros?
  3. Do related measures move together, like ad clicks and site sessions, or spend and clicks?
  4. Did one channel fall while another rose by a similar amount?

One detail for later. The check ran on the same model that went on to write the draft. That matters in the second reader step.

Tell it what the data can't know, then ask what moved

The export doesn't know about your sale. It doesn't know you changed a URL template on September 8, either. You do, so the next message carries it.

What the files don't show, from me:
1. We sent a flash sale email on Sept 12 (20% off, ran Sept 12 to 14).
2. On Sept 8 we changed the URL template on the paid social ads. I have not yet confirmed the UTM tags carried over.
3. Paid search had no changes in September. Organic: we published four new trail guides in late August.

Now explain what moved and why. Make a table of the five biggest movements in online revenue, in dollars first and then percent. For each one, label the explanation as CONFIRMED BY THE DATA, LIKELY, or UNKNOWN, and say what we would check to confirm it. Do not assume anything I haven't told you.

The last sentence matters, and so do the three labels. A model asked why revenue moved tends to give you a reason for every row, because a row with no reason looks unfinished. The labels give it a way to say it doesn't know.

Here is the table it came back with, shortened:

Channel Change in online revenue Label What it said to check
Email up $6,755 (33.8%) LIKELY Email revenue for Sept 8 to 14 was $9,600, but the files can't isolate the sale. Check the campaign report for orders that used the discount.
Paid Social down $4,815 (34.0%) UNKNOWN Sessions fell 38.1% while platform clicks fell 1.6%. The URL change could be related, but nothing confirms the tags were lost. Check the ad URLs.
Organic Search up $4,660 (16.8%) LIKELY The four trail guides may have contributed. Check organic revenue by landing page.
Direct up $1,260 (12.0%) UNKNOWN Missing paid social tags could shift visits into Direct, but that is unconfirmed. Compare source reports before and after Sept 8.
Referral up $315 (13.6%) UNKNOWN The files show the increase and not the cause. Check the referring sites.

Marking Paid Social UNKNOWN was the right call. The prompt said the tags were unconfirmed, and the model didn't promote that suspicion to a fact. It also left Paid Search out of the table, because Paid Search moved by $85 and Referral, at $315, was the fifth biggest.

One slip. The prompt asked for a table, and the reply opened with "Dana," as if it were writing the letter. Once a model knows who the reader is, it can start writing to them before you ask. That's harmless here and annoying in the next step, so notice it.

One more prompt belongs in this step, because the mistake it prevents survives longest in client reports. Conversion rate is a percentage, so a change in it can be read two ways. Harbor & Pine's went from 2.12% in August to 2.19% in September. That is 0.07 percentage points, and it is also a 3.1% relative increase. Both are true. Only one belongs in front of Dana without a label.

Wikipedia's entry on the percentage point puts the difference plainly: moving from 40 percent to 44 percent is 4 percentage points, and a 10 percent increase in the quantity measured. Ask for it in the right unit:

Did the store's conversion rate improve in September? Conversion rate is purchases divided by sessions. Give me the number for both months and the change, in one short paragraph for a client who is not a marketer.

The model held up, answering "an improvement of 0.07 percentage points". Add a line to the brief anyway: changes in a rate are reported in percentage points. A rule in the brief is cheaper than checking every month.

A trail signpost at a fork in a misty forest with two blank arrows, standing for the cause behind a number

Go and look at the one thing it marked unknown

This step belongs to you, not the model.

Open the ad platform and read the ad URLs. In the sample, the answer is set in advance: since the September 8 change, two of the four paid social ad sets have been running without UTM tags. In your account, this is the part where you find out.

UTM tags are the labels on a link that tell Analytics where a visit came from. Google's help page on campaign URLs says to always include three of them: utm_source, utm_medium and utm_campaign. Strip them and Analytics sorts the visit by whatever it can see about where the visitor came from.

Google's default channel group definitions spell out where that lands. A visit counts as Direct when the source is exactly "(direct)" and the medium is "(not set)" or "(none)". The same table sends a visit to Organic Social when the source matches a known social site. So untagged clicks can surface in Direct or in Organic Social, depending on whether the app passed along a referrer. The sample puts them in Direct.

That one URL change probably explains the three odd things in the export. Paid Social sessions fall while clicks stay flat. Direct rises. And blended paid ROAS drops below the 2.5 goal, even though not a dollar of spend moved.

Now tell the thread what you found:

UPDATE from me: I checked the paid social ads. Since the Sept 8 template change, two of the four ad sets have been running without UTM tags. Their visits are landing in Direct. I can't say how many, so don't put a number on it.

Look at the last sentence. A model will happily estimate the split if you leave it room. Any number it produces is a guess, and the client will read it as a measurement.

The thread is where this earns its keep. The model doesn't need the files pasted again, or the check, or the labeled table. They're all above it in the conversation, along with your update.

Write the narrative in the client's voice

Now the report. The prompt names the structure, the length, and what the model may and may not claim:

Now write the September report narrative for Dana. Three sections with plain headings: What moved, Why, What we do next. Under 400 words. Use only CONFIRMED and LIKELY explanations from our work, and mark what is a likely explanation in plain words. Do not say paid social failed. Do not put a number on how much Direct traffic came from paid social.

The two "do not" lines come straight from the earlier steps. The lazy run said Paid Social failed, and the Direct split is the one number nobody could measure. Every report has its own pair, the claim you must not make and the number you can't size. Write them into the prompt before the model gets the chance.

The reply came to 268 words. The "Why" section opened like this:

Confirmed: Two of the four Paid Social ad sets have been running without tracking tags since the Sept. 8 URL change. Their visits are being counted as Direct.

The model did what it was told. It kept the unknowns out of the report, marked the likely explanations as likely, said nothing about Paid Social failing, and put no number on the Direct split. The voice held too. It said "online revenue" every time and never "sales", and a search of the reply for the six banned words found none. Do that search by hand every month. It takes ten seconds.

Two lines were wrong in spirit and right in arithmetic. The "What moved" section listed "Paid Social fell $4,815 (34.0%)" with no caveat. And it said blended paid ROAS "was 2.31x, below the 2.5x goal", flat, as a fact about the ads.

Those are the two lines Dana will remember. The model had the information to fix both, and the draft didn't connect the missing tags to the ROAS number.

You could catch this by eye. After the sixth report on a Friday afternoon, you might not.

Hands holding a printed two page client letter beside a stack of plain envelopes

Give the draft to a second reader that has never seen it

A first draft needs an editor, and the model that wrote it is a poor one. It reads its own work the way you read your own email: for what you meant.

So start a second pass. In Magai, you can switch models in the same thread and the conversation comes with you: the files, the check, the update, the draft. Switch to /GPT or /Gemini for this step, because a different model doesn't share the first one's habits.

The run for this post used the same model for the draft and the second read, and it still caught what's below. A different model is a stronger reader, and Claude and ChatGPT fail in different directions, which is the point of using two.

You are the second reader. Check every number and every claim in the draft above against the two files and against what the owner told us. Make a table: the claim as written, what the files show, and PASS, FIX or UNSUPPORTED. Then list anything a reader would take away that the numbers don't support, even if each number is right.

The last sentence is the useful one. Each number in a report can be right while the report is wrong. Here is what came back on the lines that mattered, shortened:

What the draft said What the second reader found Verdict
Blended paid ROAS was 2.31x, below the 2.5x goal The arithmetic is right, but the missing tags may understate paid revenue, so the line reads like a miss FIX
Paid Social "visits" fell by 4,800 The file reports sessions, not visits FIX
The missing tags explain the gap between clicks and sessions Clicks and sessions are different measures, so the tags can't be said to explain the gap FIX
Online revenue was up $8,090 (8.2%) Matches the files PASS
Organic Search rose $4,660 (16.8%) Matches the files PASS
Trail guides may have contributed to organic growth The timing fits, but nothing in the files connects them UNSUPPORTED
The $105,000 goal Not found in the files UNSUPPORTED

The big catch was the ROAS line. The second reader said the arithmetic was right and the line was still wrong, because missing tags may make reported paid revenue understate what the ads earned. That is exactly the sentence a client reads as "the ads got worse".

It also caught "visits" where the files say sessions. Small, until Dana asks what a visit is and you've used two words for the same thing.

Two flags were the prompt's fault. The $105,000 goal came back UNSUPPORTED, and so did the phrase "online revenue", because the column is called revenue_usd. Both facts live in the brief, and the run's prompt left the brief out. A second reader knows only what's in front of it. In a Magai thread the brief is already there, which is one more reason to keep a thread per client.

It also overreached once. It marked the line saying the email promotion likely contributed as FIX, because the files don't prove the promotion caused the lift. The draft had said "likely", so keep it. A second reader that never lets anything through is as useless as one that lets everything through.

A 2025 paper on table reasoning, Formula-R1, opens by saying language models "still struggle with accurate numerical reasoning over tabular data". The arithmetic in these runs was right. The framing is where a model slips, and a second read is where you catch it.

A colleague leaning over a desk pointing a pen at a printed page of charts, the second reader at work

Fix the draft, then check five numbers yourself

You might think three more prompts after the draft eat the time you saved. They do eat some. Each one is a pasted paragraph, and the report you skip them for is the one you rewrite on Monday after Dana calls.

Take the findings you agree with and paste them back as instructions. Leave out the ones you don't.

A second reader found these problems:
- The paid ROAS line says we missed the 2.5 goal, but the missing tags mean paid social revenue is probably undercounted. A reader will think the ads got worse.
- The draft says visits where the files say sessions.
- The draft implies the missing tags explain the gap between clicks and sessions. Clicks and sessions are different measures, so say only that the tags are a likely reason the channel totals moved.

Rewrite the report. Same three headings, under 400 words, same voice rules. Put the ROAS number in its honest frame: what the report shows, why it is probably low, and what we will do to find out.

The rewrite came to 293 words with no banned words. The ROAS paragraph now reads:

The report shows 2.31x, below the 2.5x goal and down from 2.65x in August. But this is likely low: missing tracking tags may have sent paid social activity, and its online revenue, into Direct. So this number is not a dependable read of actual paid performance.

That paragraph gives Dana the number, says why it is probably low, and doesn't pretend to know more than it does.

Then comes a step that is yours alone. Open the export and check five numbers against the source: total online revenue, the comparison to goal, blended ROAS, and the two movements Dana will ask about first, Email and Paid Social. It takes three minutes.

A second reader lowers the odds of an error. It doesn't take your name off the report.

Keep the draft, the findings and the rewrite in the same thread. If Dana asks next month why the ROAS line was framed that way, the reasoning is sitting in the conversation, and you don't have to rebuild it from memory.

Turn what we do next into tasks someone owns

A report that ends on "we'll keep an eye on it" isn't finished. The last section of the job is the one that says what the agency does next, and it should be a list with owners and dates.

Turn the 'What we do next' section into a task list. A table with four columns: the task, who owns it (Fieldhouse Digital or Dana), the date it is due, and the one check that tells us it is done. Today is Friday, October 2, 2026. Only tasks that follow from the report. Keep each task to one line.

Here are three of the five rows it returned:

Task Owner Due Done when
Fix tracking tags on the two affected Paid Social ad sets Fieldhouse Digital October 5, 2026 All four ad sets show their sessions and online revenue under Paid Social
Recalculate blended paid ROAS with the corrected data Fieldhouse Digital October 6, 2026 The updated calculation uses the corrected channel totals
Track the next email promotion and trail guide content separately Fieldhouse Digital November 6, 2026 The next report shows online revenue separately for each

The order is right: fix the tags, then recalculate ROAS.

Two things need your hand. It gave every task to Fieldhouse Digital, so Dana has nothing to do, and a report that asks nothing of the client reads like an invoice. If the next step needs her approval, say so. It also listed "Keep Paid Search unchanged" as a task, which is a decision and not a task, and one of its "done when" checks, that Direct no longer includes sessions from the affected ad sets, isn't something you can look at and verify. Cut the first. Rewrite the second as a check you can run, like comparing Direct sessions in the week after the fix with the weeks before it.

The dates are the model's suggestions, built from the Friday date in the prompt. They're yours to change.

Put the table at the foot of the report, under "What we do next", and name the first task in the opening line of the email you send with it. Dana should know what you're doing about the tags before she scrolls to find out.

Save the setup so next month starts at step three

Everything you typed in the steps above is the same next month. Type it once and save it.

Agents in Magai are reusable instructions that run on any model, so the rules travel with you whichever model writes or reads. Here are the instructions for a reporting agent, built from what went wrong above:

You are the reporting analyst for Fieldhouse Digital. For every client report:
1. Read the client brief first. Follow its voice and banned words exactly.
2. Check the export before writing. Totals must agree across files. Blank cells are not zeros. Related measures, like ad clicks and site sessions, should move together. Flag any channel that falls while another rises by a similar amount.
3. Label every explanation CONFIRMED BY THE DATA, LIKELY or UNKNOWN. Never promote a likely or unknown explanation to a fact.
4. Report changes in a rate, like conversion rate, in percentage points.
5. Never estimate a number the files don't contain.
6. Write the report in three sections: What moved, Why, What we do next.
Do not write a report until the data check is done and the owner has answered the unknowns.

Paste that into a new agent and the habits are no longer yours to remember. If you haven't built one before, how to build an AI agent without code walks through it.

Upload last month's report into the new thread along with the export, and the model can see how you described things before. A claim you dropped last month doesn't sneak back in.

If your exports land in Google Drive, connect it. Magai connects 150+ third party apps, Drive and Gmail among them, directly to agents, so the agent works from the file in the folder and not from a download you've renamed three times.

A scheduled task can run the check prompt on a day you choose, so the flags are waiting when you sit down. Six clients is six checks you didn't start by hand. More on AI for marketing teams is in the marketing archive.

A finished desk on a Friday afternoon with a closed laptop and one day circled on a calendar

Next month, you start a new thread in Harbor & Pine's folder, upload the new export, and type one line:

Run the data check on the new export and stop there.

Then go and look at the unknowns. That part was always yours.

Friday still has six reports due. This time, none of them start with a copy and paste.

Open Magai, make the client's folder, and run the check first.

More in Marketing