How to build a finance dashboard with OpenAI Codex
Stop paying monthly software fees just to view your own business numbers. Download our ready-to-use finance dashboard, and let OpenAI Codex customize it for you. Simply talk to the AI in plain English to connect your spreadsheet export, choose your currency, and get clear financial charts in minutes, no coding required.
OpenAI Codex
$ Build a finance dashboard: a validating CSV import with a rejects table, server-side jobs computing daily revenue, expense, cash-flow and receivables figures on accrual and cash bases, FX conversion with imputed rates flagged, KPI cards and charts, DSO, and row-level security over a multi-company model with admin and viewer roles.
- Parser reviewed against a real export
- Policies read as SQL before they run
- Ready for your review
What a finance dashboard actually is
A very short list of numbers somebody is going to act on. Everything difficult about building one sits between the export you start with and the figure on the card, and none of it is the chart.
The screen is deceptively simple: revenue, expenses, profit, cash, what you are owed: five numbers an owner reads in four seconds. A whole software category exists to produce them because each is a conclusion, and the path from raw records to conclusion has half a dozen places to go quietly wrong.
Start with where the numbers live. They are in an accounting system, and what you can get out is an export: invoices, payments, expenses and bank lines, in whatever shape that system felt like. Between that file and the dashboard, something has to decide what counts as revenue, on which date, in which currency, and what to do with the rows that will not parse. Those decisions are the product. The chart is the last five per cent.
What makes it different from most small applications is that being approximately right is not a rounding error, it is a wrong decision. Nobody re-plans hiring because a task board is stale. People do because a cash-flow chart said the quarter was fine. Hence the time this build spends on provenance: which rows produced this figure, on what basis, at which rate, and how you would check.
The import is the application
Exporting data from your accounting software is usually frustrating: column names change, dates look messy, and numbers get mixed up. We built the complex data-cleaning rules into this template for you. When you upload your export, the system automatically organizes the numbers, flags any missing data, and keeps your charts accurate.
Two bases, and they are not the same business
Accrual counts an invoice the day you send it. Cash counts it the day the money lands. For any business with payment terms those are two genuinely different pictures of the same month, and the gap between them is the thing receivables exist to measure. Decide which one your dashboard means, put it in a setting, and compute both if anybody will ever ask.
A forecast is a claim, and it needs a label
Every dashboard in this category eventually draws a line to the right of today. That line is not data, and whether it came from arithmetic on your history or a model asked to be plausible changes what somebody may do with it. The screen should say which, because the person reading it is deciding whether to hire.
How much the numbers are trusted today
~40%
of CFOs "do not completely trust the accuracy of their organization’s financial data", in a survey of over 1,300 senior finance people across seven countries published in January 2024 by BlackLine, a company that sells software for closing the books, so read it as interested research rather than neutral. Two things make it worth quoting anyway: the sample is large and named, and the number is about trust rather than tooling. A dashboard nobody believes is a slower spreadsheet.
BlackLine survey (Censuswide, 1,300+ respondents), published January 2024 · checked survey published January 2024
The parts every finance dashboard is built from
Five of these six are invisible on screen, and they are where the build time and the credibility both live. The first is where most projects fail.
An import that survives a real export
Your accounting system will hand you a file, and that file will disappoint you: a column renamed since last quarter, dates in two formats, a currency symbol glued to an amount, a negative in brackets, blank rows where somebody added a total. A parser that copes is half of it. The half that decides whether anybody trusts the result is what happens to the rows that fail: kept in a table you can look at, with the reason and the line number, rather than silently missing from a chart. Every finance person’s first question about a dashboard is "does this include everything", and a reject list is the only honest answer.
Instant analytics with no waiting time
If a website has to recalculate thousands of sales lines every time you click a page, it will freeze and load slowly. Our template automatically summarizes your daily totals in the background. That means your charts load instantly, even if you have years of sales data.
Accrual or cash, decided in a setting
The same month is two different businesses depending on whether you count an invoice when it was sent or when it was paid. Neither is more correct. They answer different questions. Put the choice in a settings row rather than the code, compute both if anybody will ask, and label the screen. A profit figure with no basis beside it is a number in search of an argument.
One currency to read, several to record
The moment you invoice abroad you have two problems and only one is obvious. The obvious one is converting into a base currency you can add up. The subtle one is that markets close, so for weekends, holidays and the day you happened to bill there may be no rate. Carrying the last known rate forward is the standard answer. The part worth building properly is marking the rows where you did it, so a converted total can say which part of itself was estimated. That flag costs an afternoon and settles every awkward conversation about a number being slightly off.
Receivables, because that is where trouble shows first
Profit is an opinion about a period. Being owed money is a fact about today. Ageing buckets and days-sales-outstanding are the two figures here that predict rather than report. A business whose average wait moves from thirty-four days to fifty-one has a problem two months before the cash-flow chart shows it. Build the ageing from invoice dates and payments rather than a status field somebody has to remember to update.
Control Who Can Edit vs. Who Can Only View
You don’t want team members or investors accidentally editing your financial records. This template comes with pre-set user roles: Admins can upload spreadsheets and change settings, while Viewers look at charts and download reports. The import, the figures jobs and the settings refuse anyone who is not an admin. If you run multiple businesses, each business’s data is kept completely separate and private.
Own the dashboard or rent a view of your own numbers
The five products below barely charge per person. Four advertise unlimited users. What they meter is the shape of your business: a second company, a fourth dashboard, a fifth data feed, one business open at a time. Work out which you outgrow first, because that is what you are buying.
Build your own
An app you own has no meter on any of that. Your second company is a row, your ninth dashboard is a route, and the figures behind them are already in your database, and with an AI coding tool writing the import, the daily jobs and the permission rules, that build is weeks rather than quarters.
- A second or fifth company is a row in a table rather than a plan tier
- A ninth dashboard costs a route and an afternoon, not an upgrade
- Every invoice, payment and expense is in your own database, queryable without an export request
- What counts as revenue, and on which basis, is your definition to write down
- Two businesses open at once, because nothing is stopping you
- No tier gets restructured under you, and no feature moves behind an upgrade you have not agreed to
Rent the reporting layer
Fathom · Klipfolio · Databox · LivePlan · JiravWhat renting buys is the part this template deliberately does not attempt. Live connections into the systems your numbers already live in, rather than a file you export. Consolidation across entities. Benchmarking against other companies. Client-ready branded report packs. On the accountant-facing products, a review workflow built for signing things off.
- Live connectors into your accounting system, so nobody exports anything. This template reads a CSV you give it
- Consolidation across several entities, with the eliminations that makes necessary
- Benchmarking your figures against other companies, which needs data you do not have
- Branded, client-ready report packs, and on two of these a workflow for reviewing and signing them off
- Somebody else’s problem when your accounting system changes a field name
- Four of the five advertise unlimited users, so what you are billed for is companies, dashboards or data feeds
First because it states the meter more plainly than anybody: you buy companies, and "Unlimited users" is listed as an included feature beside the price. That combination is the whole argument of this table: what is rationed is the entity, not the seat. The included list is also a fair summary of what this template does not do: "Group benchmarking", "Multi-currency consolidations", "Unlimited brandable reports". Prices are quoted in Australian dollars because that is the currency its page served us. Converting them ourselves would be inventing a figure.
fathomhq.com · checked August 2026
The strangest meter in the set to explain to somebody about to build their own, which is why it is here: the ladder is how many dashboards you may keep. Users are unlimited on all four tiers, and what else moves up is how often the data refreshes: four hours, one hour, fifteen minutes, then up-to-the-minute. Hold that beside a build you own, where a fourth dashboard is a new route and the refresh rate is however often you run the job. Its trial is 14 days with no card, described as "almost unlimited access to Klips".
klipfolio.com · checked August 2026
The generous-looking free tier that a finance dashboard outgrows immediately, and a third kind of meter. Free gives you "3 data sources included", "1 user" and "1 Dashboards & reports". The paid tiers hand back unlimited users and dashboards and then charge per feed. Do the count first: revenue, expenses, invoices, payments and exchange rates is five feeds before you reach a bank. The annual figures on the page are $768, $1,908 and $4,788.
databox.com · checked August 2026
The cheapest row by a wide margin, and included for a limit that is not a price. Its page says you can "Create as many companies as you like in LivePlan. However, only one company can be active at a time." For a founder with one business that is a non-issue. For anybody with a group, a side venture or clients it is the whole decision. Both tiers include five contributors and unlimited guests, another reminder that seats are not what this market charges for.
liveplan.com · checked August 2026
Here for what it does not tell you. Both figures are floors rather than prices, neither is stated as per user, per entity or per anything, and both route to a demo request rather than a checkout. That is normal in this part of the market and worth naming, because it is the practical difference between this table’s two columns: one you can budget from a web page, the other starts with a call. No per-seat or per-company reading is invented here, because the page does not support one.
jirav.com · checked August 2026
Rule of thumb: if the numbers must arrive automatically rather than through a file, if several entities need consolidating, if a client expects a branded pack with a review trail, or if somebody would rather ring a supplier than read a query, rent. If what you want is your own five numbers, defined the way your business defines them, in a currency you chose, with a bill that does not move when you open a second company, that is the half worth owning. One honest note either way, from the same survey as the figure above: 68% of those senior finance people said manual work leaves their organisation vulnerable to decision-making errors. Building the dashboard does not fix that by itself. It fixes it on the day you stop maintaining the spreadsheet beside it.
Why build with Codex
Most software looks simple from the outside, but almost all of the actual work is invisible: a database, logins, permission checks, forms that validate what people type, and dozens of screens that read and write records. Doing that by hand means knowing the whole stack cold, so weeks pass before the first feature a customer would notice actually works.
Codex closes that gap by working the way a developer would, just faster. The whole workflow becomes a simple loop:
Describe
Tell Codex what you want, in plain language.
Build
It edits the real project files, backend and auth and UI, rather than replying in a chat.
Check
Run the app yourself and confirm the change works.
Repeat
Describe the next change.
None of that loop needs a computer-science background, which is why one person can take an idea to a working app over a handful of focused sessions.
Three hard partshandled for you
The data model, authentication, and access rules are the pieces that make software like this genuinely hard to build alone. Describe them and Codex scaffolds all three, leaving mostly screens to build on top.
Any language is the interface
There’s no code to write, and no requirement to describe it in English. Ask for a new field, a renamed step, or an AI summary in whatever language you think in, and Codex implements it.
Local files it edits directly
Codex works on the project on your own disk rather than a copy somewhere else, so what it changes is exactly what you see when you run the app. Point it at the handful of files that matter and it stays fast and focused.
Pay a developer, or do it with AI
The only line in either column that is not optional is the model behind the forecast. The rest is a database plan and hosting, and both start free.
Hire a developer
Custom build, from scratch- Developer
- ~$12k-$49k
- Supabase (backend)
- Free tier · $25/mo (Pro plan)*
- Hosting
- $0 free tier
- AI model (the forecast)
- Usage-based - the one line here that is not optional
- Build time
- ~245 hrs of their work
~$12k-$49k to build, then from $25/mo plus model usage
Our ~245-hour estimate, priced at the rates in the survey linked below: senior US developers at $100-$150+ an hour, and agencies charging 20-40% above the freelancers they bid against, which is what makes $50/hr and $200/hr the honest ends. The distribution matters more than the total: roughly a third of those hours are the import and the jobs turning records into daily figures, and another slice is the permission model. Where somebody has quoted for "a dashboard", check what they assumed about the file your accounting system actually produces.
Build it with Codex
From scratch, with Codex- Codex
- ~$20/month (Plus) to ~$200/month (Pro)
- Backend (Supabase)
- Free tier · $25/month (Pro plan)*
- Hosting
- $0 on a free tier
- Your time
- ~116 hrs
~$20-$200/month while you build, then whichever plan you keep using
Codex itself is free to install. The cost sits in the ChatGPT plan behind it, or in API usage if you sign in with a key instead. Plus, around $20/month, covers a template import or a short build. A from-scratch build that runs for weeks usually needs Pro’s top usage-multiplier tier instead, which lands around $100 to $200 a month. The fee doesn’t shrink when you start from a template the way a per-hour developer bill would: the template changes how many of the hours in the estimator above you actually spend, not which ChatGPT plan you’re paying for.
* Two free-tier lines matter here, and neither is the one people check. The 500 MB database is enough for years of records, because financial data is small. What bites is the pause: a free project stops after a week of inactivity, and a dashboard read monthly is exactly the sort that goes quiet for a week. Pro, from $25/mo, ends the pause, keeps a daily backup for 7 days, and lifts egress to 250 GB (then $0.09 per GB) and file storage to 100 GB (then $0.0213 per GB), the second being where imported files accumulate.
Either way the dashboard is yours, and the only running costs are the database tier and whatever the forecast spends on a model. The difference between the columns is who does the work: pay someone up front, or describe what you want and build it yourself.
Prices and rates from supabase.com, developex.com and learn.chatgpt.com, checked August 2026.
Decide before you build
Six things to settle in writing first. Each is a definition somebody will later argue with, and far cheaper to write down now than to change once a figure has been in a board pack.
Where the numbers come from, and in what shape
Export a real month out of your accounting system before you plan anything else, and open the file. Its column names, its date format, how it writes a credit note. That is the specification for the hardest part of this build. If the answer is several systems, decide whether they arrive as separate imports or get merged first: different schemas.
Accrual, cash, or both
Write down which question your dashboard answers: what we earned, or what we banked. Most businesses with payment terms want both eventually, and the honest version of both is a setting plus two computed sets of figures. It changes which date every aggregation groups by, so decide before the jobs are written.
Your base currency, and what a missing rate means
Pick the currency you think in, then handle the awkward half: markets close, so some transaction dates have no rate. Carrying the last known rate forward is a good answer. Decide whether a total built on a carried-forward rate may look identical to one that was not. When somebody queries a figure, that is a two-minute answer or an afternoon.
Who may read, who may write, and how many businesses
A finance dashboard has readers who must not be able to change anything, which makes two roles the minimum. Then the bigger question: one company, or several? If several, keeping one set of books entirely invisible to another is the project’s most important rule, and it belongs in the database rather than a screen.
What each of your five numbers actually means
Revenue net or gross of refunds. Whether an intercompany invoice counts. Whether a deposit is revenue when taken. What sits above the line in your margin. Your AI tool cannot answer those, but written down they become a specification it can build exactly, and a note for whoever disputes a figure later.
Whether a forecast may be a guess
Something here will eventually draw a line past today, so decide in advance what that line may be. A projection from your own history (a trend, a seasonal average, a run rate) can be explained and checked. One a language model produced because it looked plausible cannot, and looks exactly as confident. The fix is a label on the chart.
Comparing your build options
The hours in this build collect in a parser and a set of policies, and where you start decides how much of your attention they take. Three routes to the same product below: every line written by hand, a UI kit that stops at a KPI card, or Codex working task by task on the real source. The fourth is not on the chart. The template has already spent these ~116 hours and ships the result.
The charts are a fortnight. What takes the quarter is everything behind them: getting an export out of your accounting system to parse cleanly, deciding what to do with the forty rows that do not, turning invoices and payments into daily totals on two different accounting bases, converting six currencies on days the rate is missing, and making sure the person who should only be reading cannot write. None of that appears on screen, and all of it decides whether the screen is true.
A kit hands you a dashboard shell, KPI cards and a chart library, which is genuinely most of the pixels and almost none of the work. Nothing in it knows what an invoice is, that revenue means two different numbers depending on a setting, that a rate was carried forward from Friday, or which company the person signing in belongs to. Every figure the cards display is still yours to derive.
Hand Codex a task and it edits the real files (a migration, the parser, a job that computes a figure, a policy) from the terminal, from your editor, or as a cloud run you collect later. The task list above it, unchanged, arriving as diffs that sit and wait for you to say yes, which on a build where the output is a number is the review you want.
Estimate your exact build timeframe
Plenty of businesses need less than this. If you invoice in one currency, or nobody but you will ever sign in, untick those rows and watch the estimate fall.
Your estimate
116 hrs
start to finish
Based on the 6 of 6 features you’ve selected, plus ~26h of groundwork. Toggle any on the left to watch the number move, and open the groundwork row to untick what you have already, such as a database that is already running or going live if you are only building a mock-up for now.
A rough estimate, not a quote. Real time depends on how much you customize and how clean your data is.
Let’s set up the tools you need
Before step 01, four things go on your computer. It takes about 15 minutes in total, and none of it is coding. Three are ordinary installers, and the fourth is a ChatGPT plan with Codex access switched on. After that, you build by describing what you want in plain language.
OpenAI Codex
Your main AI assistant. The app itself costs nothing and installs with a single command from OpenAI, then runs in your Terminal. What it costs to use is the next card: every request spends the usage allowance on your ChatGPT plan, and the free plan’s allowance is small enough that a build of this size stops early. Codex is also built into an extension for popular code editors and into the ChatGPT desktop app, which can hand a longer task off to Codex cloud to keep running in an isolated environment while you do something else.
Install Codex CLIChatGPT plan
Codex is technically included on the free ChatGPT plan too, but Free’s usage is the tightest of any tier. OpenAI doesn’t publish Free’s own cap, only that every paid tier gets a larger multiple of it, so treat Free as a way to try Codex rather than to build with it. ChatGPT Plus, around $20/month, is the realistic starting point, and a long, from-scratch build tends to need the top ChatGPT Pro tier, priced by usage multiplier at roughly $100 to $200/month. Codex can also run on pay-as-you-go API billing instead of a ChatGPT plan, if you’d rather pay per token than hold a subscription.
Compare ChatGPT plansNode.js engine
The engine that runs your app on your own computer. You never have to learn how it works: download the version marked LTS (the most stable one), install it, and forget about it.
Download Node.js (LTS)Supabase (database)
Where your project keeps its data. Install it, then sign in once by running supabase login. Words like migrations and row-level security turn up later in the guide, and Codex writes those parts for you.
Install Supabase CLINothing here is worth memorizing. These four just need to exist on your machine. From step 01 on, you say what you want and Codex runs the commands.
Build your finance dashboard, one Codex task at a time
Describe a task. Codex writes the files and runs the commands. The order below front-loads the two places a diff can read perfectly and still be wrong: a parser that quietly discards rows it cannot understand, and a policy set that looks complete until one editable column turns out to decide everything. Both get a task to themselves, and both are worth reading slowly.
- 01
Write AGENTS.md before there is any code to contradict it
Codex re-reads that file at the start of every task you hand over, which makes it the cheapest place to put the two rules this build depends on.
PromptSet up the projectStart by writing an AGENTS.md at the project root: the stack is React 18, Vite, TypeScript, Tailwind, and the Supabase JS client, and this project is a finance dashboard. Fix the vocabulary (company, invoice, payment, expense, bank line, daily figure, basis, base currency, rate, reject, role) and record two standing constraints. First: every figure shown is derived from records, on a stated accounting basis and at a stated rate, and anything carried forward or estimated stays flagged all the way to the card. No figure is ever hardcoded or produced by something the screen cannot explain. Second: every row belongs to a company, the company a person belongs to is what every access rule resolves to, and it is therefore never a value that person may change. You load that file automatically at the start of every later task. Then scaffold the project: a typed Supabase client under src/lib reading VITE_SUPABASE_URL and the publishable key (the sb_publishable_… key that replaced the older anon key) from .env, with .env confirmed present in .gitignore. Start the dev server once to prove it boots.
The second constraint is the one worth writing down rather than saying. It is a sentence about one column that will not be re-derived from context five tasks later, and on a multi-company finance application it is the difference between a permission model and the appearance of one.
- 02
One task for the schema, with the company on every table
Nothing depends on this yet, so it is cheap to get wrong and cheap to throw away, which is exactly why it is worth reading the SQL rather than the summary of it.
PromptModel the company and the recordsOne task, the data model, with no authentication and a company reference on every table from the start. Supabase migrations for: companies. Profiles linking an account to a company. Customers and vendors. Invoices with an issue date, a due date, an amount, a currency and a customer. Payments against invoices with their own date. Expenses with a date, an amount, a currency, a vendor and a category, plus my own category table. Vendor bills for payables. Bank lines with a date, an amount and a direction. An exchange-rate table keyed by currency and date with a flag for real or carried-forward. A per-company settings table holding the accounting basis, base currency, timezone and whether future dates are allowed. Add empty daily-figure tables for revenue, expenses, cash flow, receivables and payables, by company and date. Show me the SQL before you run it, then seed two companies with deliberately awkward data: one invoicing in three currencies, one with invoices paid sixty days late.
Read the rate table and the settings table hardest in that diff. Whether a rate is keyed per currency per day, and whether the basis lives per company rather than globally, are the two decisions every later task is written against, and both are cheap now and expensive once five jobs read them.
- 03
Give the parser its own task, and hand it your real file
Export a real month out of your accounting system first. What Codex needs is not a description of your file, it is the file.
PromptImport a real fileOne task, the import. A real CSV export from my accounting system is in the project. Read it first and report what you found before writing anything: column names, date format, how negatives and credit notes are written, total rows at the bottom, and anything you cannot map to my schema. Then build it: a private bucket restricted to CSV and scoped so a person reaches only their own folder, and a server-side function that parses an upload, validates every row (required fields present, dates parseable and inside a stated period, amounts numeric, currency known, no duplicate of an existing record), inserts what passes and writes every failure to a rejects table with the line number and the reason. No row is dropped silently. In the diff, mark every judgement call you made about my file’s format, because those are the lines I want to read first. Then run it and give me the accepted count, the full reject list, and the sum of accepted invoice amounts.
That instruction to mark the judgement calls is the review. A parser is nothing but small decisions about somebody else’s formatting, and a short list of them beats reading three hundred lines looking, particularly the decision about a row it only half understood.
- 04
One task for the figures, and read the SQL that computes them
The task that decides whether this dashboard is worth pointing at a decision. Ask for the jobs and their SQL before either runs, and judge them on which records they include.
PromptCompute the daily figuresOne task, the figures: server-side jobs, each rebuilding a period I name rather than appending, and not queries in a screen. Revenue from invoices by issue date for accrual and from payments by their own date for cash, computed both ways. Expenses by date and category. Cash flow as inflows and outflows from payments and bank lines with a running balance. Receivables and payables outstanding, bucketed by how overdue, plus days-sales-outstanding. Convert every amount into my base currency at the rate for that record’s own date. Where no rate exists, carry the last real rate forward, mark the figure as partly estimated, and never overwrite a real rate. Show me the SQL before you run it, and be explicit about two things I want to read rather than infer: how you group by date across timezones, and how a partial payment against an invoice affects both bases. Then print the working for one month: which records fed each figure, on which basis, how many conversions used a carried-forward rate, and both totals side by side.
Read the partial-payment handling character by character. It is the commonest source of a finance dashboard that is subtly wrong for a quarter, because on a tidy month where everything is paid in full both bases agree and the bug is invisible.
- 05
Tighten the permission boundary, then read every policy
Sign-in, and the rules standing between one company’s books and everybody else. This is a task to run Codex on a shorter leash than you would for an ordinary edit.
PromptAdd auth, roles, and the access rulesNarrow your permissions for this task before starting it. Everything here touches authentication. Wire in Supabase Auth for email-and-password sign-up, login, logout, a persisted session, and a profile row per account carrying its company. Add a role enum of 'admin' and 'viewer' in a roles table kept off the account record, plus a SECURITY DEFINER role-check function. Then row-level security on every table, with two things done deliberately. One: every policy scopes rows to the person’s company, and the profile update policy carries an explicit WITH CHECK forbidding a change to which company it points at. Which row you may edit and what that row may become are different questions, and this column is what every other policy resolves to. Two: any admin-only policy calls the role check in its condition rather than only in its name, which matters most on the roles table itself, since a viewer who can write it is an admin. Beyond that: only an admin writes records, changes settings or triggers the jobs. A viewer reads everything and writes nothing. Each server-side function re-checks the role itself, since they run with a key that bypasses these policies. Show me every policy as SQL before it runs, then prove five things as a signed-in account: the other company’s invoices are unreachable, its computed figures are unreachable, a viewer cannot insert an expense, a viewer cannot change the base currency, and an account cannot move its own profile to another company.
Ask Codex to list which tables and operations it actually covered, then check that list against your own schema rather than assuming it came out complete. The tables forgotten here are the dull ones (the rejects table and the audit log) and both hold the same figures as the tables everybody remembered.
- 06Destination
Send the pages to a cloud run, then reconcile a month yourself
The pages and the exports are tightly specified and self-contained, which makes them fair to hand off. The reconciliation at the end is the opposite kind of work, and it catches what reading a diff never will.
PromptBuild the pages, the forecast, and reconcileTwo pieces, the first contained enough to run unsupervised. First, the pages, all reading the computed figures rather than raw records: an overview of KPI cards. Revenue with filters that drill to the rows behind a total. Expenses by category. Profitability with the margin definition beside it. Cash flow with a running balance. Receivables and payables with ageing buckets and days-sales-outstanding. A reports page with downloadable profit-and-loss, cash-flow and expense packs as PDF and CSV. Show the accounting basis and base currency on every page, mark any total that used a carried-forward rate, and add audit triggers on invoices, payments and expenses recording old and new values. Second, the forecast, reviewed rather than delegated: twelve months projected from my own figures with a trend and a month-of-year seasonal factor, the method and months fitted named on the chart, and any model restricted to a sentence of commentary that cannot change a number. When both are merged, reconcile with me: one real month, your revenue, expense and cash figures beside the same three from my accounting system, every difference accounted for, including whatever is in the rejects table.
Do not send the forecast to a cloud run with the pages. Its output is a claim about the future rather than a restatement of the past, and the difference between a projection you can defend and a plausible line somebody will hire against is a couple of lines you want to have read.
Role-Based Access Control (Admin vs. Viewer)
A dashboard is useless if anyone can overwrite the data. Our codebase includes a pre-configured role-based permission system out of the box. Admins can upload CSVs, reconcile data, and adjust settings. Viewers read the charts and export reports, and the import, the figures jobs and the settings refuse them. Furthermore, if you manage multiple entities or clients, the database architecture ensures data is strictly siloed: one client can never see another’s books.
Let the auth service do the passwords
Sign-up, sign-in, sessions and password resets belong to whatever auth service ships with your database. A hand-rolled one that is wrong is wrong silently. Add one thing here: a second factor for anybody who can import or correct figures. The account that can rewrite what last quarter earned deserves more than a password.
Everything hangs off a company, and that is the whole model
The template puts a company on every row and writes almost every access rule as "does this row belong to the company the person asking belongs to". One function answers "which company is this", and every policy leans on it, which makes that function and the column it reads the most load-bearing lines in the project. Right, and the whole dashboard is correctly partitioned. Wrong once, and it is not partitioned at all.
Constrain what a row may become, not only which row you may edit
The rule to take away from this section. An update rule normally answers "may I edit this row?". It also has to answer "what may this row become?", and leaving the second half out lets somebody edit a row they legitimately own into something they should not reach. That matters most on the record saying which company a person belongs to, because it is the answer every other rule depends on. Say explicitly that the company on it may not change, and check it on the way in as well as out.
A rule named after a role has to actually check the role
The other rule worth carrying away. It is easy to write a permission whose name says "admins only" and whose condition only says "same company": the name reads correctly, the tests pass, and the restriction does not exist. Read your own rules with the names covered up and check each condition against what it should prevent. On a finance dashboard what this protects is the table of who is an admin, and a viewer who can edit that table is an admin.
92 live policies, because forty tables each need their own answer
The migrations carry 95 row-level security statements, three of which replace an earlier rule rather than adding one, so 92 are live, and almost none of the count is a history of revisions. The number is structural, not anxious: every raw table, every figures table, the settings, the roles, the audit log and the reject list each need their own answer for reading and for writing. It is also the honest measure of why this part of the build takes a fifth of the estimate.
Two roles, and the reason the boring one matters
Admin and viewer is all a single business needs, and the interesting half is the viewer: reads every figure, exports a report, changes nothing. The value of the role is entirely in what it cannot do, so test it that way: sign in as a viewer and try to import, to change the base currency, to edit the roles table. A viewer who manages any of the three is not a viewer.
Some work has to outrank the person who asked for it
Importing a file, rebuilding a month of figures and filling gaps in a rate table each touch far more rows than the person triggering them should be able to write directly. The template gives that work eight server-side functions running with a key that bypasses the ordinary rules, correct, and exactly why each has to check for itself that the caller is an admin first. A function that skips that check is a public endpoint that can rewrite last quarter.
The import bucket, done the careful way
A pattern to copy rather than a caveat: uploaded files go into a private bucket, capped in size, restricted to spreadsheet types, and scoped so each person reaches only their own folder. That is what you want, because an accounting export is a list of your customers and what they pay you. If you change one thing, do not make it public to "fix" a link. Generate a short-lived signed URL instead.
Keep the rows you rejected
When the import refuses a row, the refusal is data. The template writes those to their own table with the reason, and it belongs in this section rather than a usability one because of what silence would mean: a chart quietly missing forty invoices is a wrong number presented with total confidence. A visible reject list is the first thing to check after any import.
Log who changed which figure, and to what
The three tables that hold money (invoices, payments, expenses) carry triggers writing every insert, update and delete into an audit log with the old and new values. That is not paperwork, it is the answer to the only question that matters after a discrepancy: what did this number used to be, and who changed it. Keep the log readable to the business and writable by nothing.
Where the model key lives, and what the forecast is allowed to see
The forecast calls a hosted model, so a provider key exists, and it belongs on the server and nowhere else. Never in the app your team downloads. Then the question people skip: decide what is allowed to leave. Monthly totals are one thing. A customer list with what each owes is another. Send the smallest summary that can answer the question and write down what it contains, because "we send our finances to a third party" is a sentence somebody will eventually ask you to explain.
On the free tier, one copy is all there is
No backup is taken of your imported records, your settings or a single computed figure. Daily backups, kept for a week, start on Supabase Pro at $25/mo. Worth doing before the first month you reconcile: the imported records can be rebuilt from your accounting system, which is a comfort right up until you remember the corrections you made by hand afterwards cannot.
Review the access rules (row-level security policies) on every table. For each one, tell me in simple terms who can view, add, edit, and delete records, confirm that people can only reach their own data while the right roles can reach more, and flag anything left open that shouldn’t be.
Paste this before launch so Codex checks nobody can see data they shouldn’t.
One rule outranks the rest here: the database service key and the model provider key belong on the server only: never in the app your colleagues download, and never in a repository. Either one that gets out is burned: replace it the same day, and check the audit log for what was done with it in the meantime.
What speeds the build, and what slows it
Speeds the build
- An AGENTS.md file at your project root: Codex reads it automatically before every task, so you never have to remind it
- Setting Codex’s permissions once for the session, instead of approving every small edit by hand
- Handing a long, well-scoped task to Codex cloud, so it keeps working in an isolated environment while you do something else
- Reviewing a diff in the IDE extension, next to the code it touched, before you keep it
Slows the build
- Leaving permissions wide open for a sensitive change instead of narrowing them for that one task
- Skipping the AGENTS.md file, so Codex starts each new task without your conventions loaded
- Handing Codex cloud a vague, open-ended task, where you can’t steer it mid-run the way you can in a live terminal session
- Merging a cloud task’s changes back in without reading the diff first
Git: what it is, and why you need it
Before you build anything, meet the one tool that makes building safe. You need no coding background for it: Git remembers every version of your project, so you can try things, break things, and get back to a working state in seconds.
What Git actually is
Git is a quiet recorder that runs alongside your project. Each time you save your work it keeps a full snapshot, so the entire history of your project lives on your computer, not just whatever the files look like right now.
Why you need it
Codex asks before it edits files or runs commands, unless you widen its permissions for the session. Once you do, Git is what makes that safe: there’s always a working version to return to, so you can hand it a bigger task without the fear of losing what already works.
A commit is a save point
Each commit is a snapshot with a short note, like “added the home page”. Make one after every working step and you can jump back to any of them later.
GitHub’s beginner guide to GitUndo anything, safely
If a change breaks something, you roll back to the last good commit instead of unpicking it by hand. It’s the safety net that keeps a Codex session low-risk even once you’ve widened its permissions.
GitHub is also where Codex can start from
Git lives on your computer. GitHub is a free, private cloud copy of the same project. Keep it private, and never commit secret keys or passwords. Once your project is pushed there, Codex cloud can pick up a task straight from a GitHub issue or repo, without you opening a terminal at all.
Create a free GitHub accountYou rarely type git commands
There’s little to memorize. Ask Codex to “commit this” or “undo the last change” and it runs the git steps for you, inside whatever permission boundary you’ve set. Prefer clicking to typing? The Codex extension for your editor shows each change next to the code it touched before you keep it, and GitHub Desktop gives you plain buttons for saving and rolling back.
Get CodexWhere to host your application
Hosting gives your app a home on the internet so anyone can open it via a web link. Choose a service below to make your site live. (Your database, logins, and business records are stored separately in Supabase, covered below).
| Host | Best for | Notes | Free tier |
|---|---|---|---|
| Vercel | One-click deploys | Connect the repository and each push publishes itself, with nothing for a Vite project to configure. Settle which plan you belong on first: Hobby is licensed for personal, non-commercial use, and a dashboard your company makes decisions from is commercial however small it is, so Pro, at $20/user/mo. | Pro from $20/user/mo (Hobby is non-commercial) |
| Netlify | Drag-and-drop or Git | Connect the repository, or drop the built folder onto the page and be live in a minute. Add the redirect rule it asks for: without it a link straight to the cash-flow page returns a not-found error, and a link to one page is how a dashboard gets read. | Free tier |
| Cloudflare Pages | Readers in several countries | The app is served from wherever the person opening it is. The case for it is a board spread across countries, which is also where you should be most careful everyone is reading the same base currency. | Generous free tier |
| GitHub Pages | Not really this app | Free publishing from a GitHub project after one routing setting. Listed to be ruled out: free means a public repository, and this one sits beside a database holding what your company earns and who owes it money. | Free from a public repo only |
| Firebase Hosting | Teams already on Google | One round of setup, then a single command per release. No argument for it comes from the dashboard itself. The argument is that your logins and documents are Google already. | Free Spark tier |
| AWS Amplify Hosting | Teams already on AWS | Publishes out of the AWS console, and needs the same rewrite rule for a deep link to resolve. Chosen when AWS is on the invoice already and nobody wants another supplier. | Free tier (build + hosting) |
| Surge | Publish from the terminal | A single command sends the built folder online with no repository anywhere in it. Fine for walking a co-founder through the overview. Wrong for anything holding real figures. | Free - unlimited publishing |
| DigitalOcean App Platform | DigitalOcean users | Builds and serves inside the account you already have. One fewer supplier and invoice, which in a small company is a real argument. | Free - 3 static sites, 1 GB/mo transfer |
All eight serve the app well enough that speed is not the deciding question. Three others are: does the plan permit commercial use, since Vercel’s Hobby tier does not. Does it publish from a private repository, given what this code sits beside. And does a deep link resolve for a browser that has never seen your site, because the URL people share points at the page that worried them.
One thing will catch you on launch day, and it is not the host. Nothing computes a figure until a job has run over imported data, so a fresh deploy correctly shows zeros, and the first hour of production usually goes on establishing that the deploy was fine and the import had not been run.
Keep your data in Supabase
Your invoices, payments, expenses and bank lines, the daily figures computed from them, your rates, your settings and your uploaded files. This is also where every job that turns records into figures belongs, because each one has to outrank the person who asked for it.
| Service | Best for | Notes | Free tier |
|---|---|---|---|
| Supabase | Data, auth, files, server jobs | Records and computed figures both live in Postgres, accounts come from its auth service, imported files go into a private bucket, and its edge functions carry the work that has to be permitted more than the person triggering it: parsing an upload, rebuilding a month of figures, filling gaps in a rate table, calling the model behind the forecast. Setting it up is opening a free project and handing the app the project URL and the publishable key. The one to add afterwards is the model provider key, which goes in the function’s secrets and nowhere near the browser. | Free tier, then usage-based |
Where AI genuinely helps a finance dashboard
This template already calls a model in one place (the twelve-month cash-flow forecast) and that is the right place to start, because it is also the one worth being careful about. The four prompts after it add features whose numbers come from queries and whose model only does the writing.
Make the forecast explainable, or make it honest about not being
The forecast that ships is a model asked for realistic monthly figures from the history it is given: a reasonable demo, a poor basis for a hiring decision. The fix is a fork you should take deliberately.
The twelve-month forecast currently sends my history to a model and asks for realistic projections. Change it in two steps. First, compute a baseline in the database from my own figures (a trend over the last twelve months plus a month-of-year seasonal factor) and draw that as the forecast line, naming the method and the months it was fitted from on the chart. Second, keep the model but give it a different job: send it the computed projection and have it return a short commentary on what the shape suggests and which assumptions would break it, with no power to change a number. Label the chart so a reader can tell arithmetic on my data from a model’s opinion, in the chart, not only while it loads.
Categorise the expenses nobody wants to categorise
Every import lands with rows whose category is blank or wrong, and sorting them is the dullest recurring hour of the month. A good fit: contained, useful, and always reviewed before it writes.
Add a screen listing imported expense rows with no category or one I have flagged as doubtful. Send the description, the vendor and the amount to my server-side ai function and get back a suggested category from my own list, plus a confidence and a one-line reason. Show them as a reviewable list I accept, change or reject in bulk, writing nothing until I do. Anything below a confidence I set stays uncategorised rather than guessing. Include recent accepted examples for that vendor so it learns from my corrections, and never invent a category that is not already in my list.
Explain the variance before somebody asks you to
The question after every number that moved is "why". The arithmetic of which lines drove a change is a query. Turning it into two sentences a non-finance colleague can read is the part worth handing over.
Add a "why did this move" action on any figure. Compute the answer with queries first: the top contributing categories, customers or regions behind the change between two periods, with their amounts and their share of the movement. Then send only those computed contributions (no customer names unless I turn that on) to my ai function for two or three sentences explaining the movement in plain language. Print the figures it was given underneath, state the two periods, and where the movement is mostly one row, say so rather than listing three.
Flag what looks wrong in an import before it reaches a chart
The dangerous import is not the one that fails, it is the one that succeeds with a duplicated invoice or a misplaced decimal. Statistics find the outliers. A model is useful for saying which look like mistakes rather than a good month.
After every import, run a check for rows worth a second look: amounts far outside the usual range for that vendor or customer, near-duplicate invoices, dates outside the period I said I was importing, and totals differing from last month by more than a threshold I set. Compute all of it with queries. Then send the flagged rows, without customer names, to my ai function for a one-line reason each on why it might be a mistake, and show the list with an accept or investigate action per row. Nothing is deleted or edited automatically, and the flagged count sits beside the import summary.
Ask your own books a question in plain words
Your dashboard answers the questions you had when you built it. What turns up later is "which customers got slower to pay this year", "what did we spend on contractors by quarter", "was last month bad or just short", and those should not each need a screen.
Add a panel where I ask about my own figures in ordinary words. Have my ai function turn the question into a read-only query against my computed figures tables, run it under my own access rules so it can never reach another company’s data, and use the model only to phrase the answer. Show the query it ran and the rows it used under every answer, state the period and the accounting basis, and refuse rather than guess when the question needs data I do not import. It never writes, and never answers from memory instead of from a query.
Each prompt above should pick whichever model tier fits the job: a fast, lower-cost model for high-volume work, and a stronger reasoning model for anything that weighs tradeoffs against each other. Codex’s model names change faster than this page does, so check OpenAI’s current model line-up (linked in the references below) before you build, rather than copying a name you saw once. Keep all of it behind that same ai function, so one key and one rule set covers every feature you add.
Get a head start with our template
All three routes above start at an empty folder, which is not the only available starting line. This dashboard already exists and runs, so the months an import, the daily figures, the currency layer and a multi-company permission model would have taken become an afternoon of importing your own numbers.
Finance Dashboard
The exact finance dashboard this guide builds, packaged so you can open it, point it at your own backend, and make it yours from there. A real-time finance dashboard that puts revenue, expenses, profitability, cash flow, and receivables on one screen. You import your numbers from a CSV, work in any currency, forecast where cash is heading, and schedule the reports you need.
The key benefits of starting with a template
The import validates and keeps what it rejects, the figures are computed on both accounting bases, and the currency layer admits when a rate was carried forward. That is most of the saving. Behind it the seven pages, the exports, the audit trail and two roles are done too.
Building the core from scratch
~116 hrs
Opening the template, already built
~1 hr
~115 hrs of building you skip
The two figures measure different work. Building the application yourself is the ~116 hrs. The ~1 hr covers adopting the finished one (a database of your own, a first real export imported, your base currency and accounting basis set) and it is the busiest hour of any template here, because this one shows you nothing until real data has been through it. Agreeing what your own figures mean costs the same on either path, so neither number includes it.
An import pipeline that already copes
Upload a CSV into a private bucket and a server-side function parses it, validates every row against the shape it expects, writes what it accepts into the right table and what it refuses into a reject table with the reason, so a total is never quietly short. Sample files for invoices, expenses, accounts, bank lines and rates ship with the project, which is the fastest way to see the shape yours needs.
Figures computed rather than queried per page
Five server-side jobs turn raw invoices, payments, expenses, bills and bank lines into daily revenue, expense, cash-flow, receivable and payable figures, rebuilt for whatever period you name. Revenue is computed on both bases (invoices by issue date for accrual, payments by their date for cash) and your settings carry which one the dashboard means, plus the base currency, the timezone and whether future dates are allowed.
A currency layer that admits what it guessed
A rate table with a calendar over it, and a job that fills the days a market was closed by carrying the last real rate forward, marking those rows as imputed and never overwriting a real rate with a guessed one. That flag is the part most builds skip and the part that answers every awkward question about a converted total being a few units out.
92 live access policies over a multi-company model
Everything hangs off a company, and 92 live row-level security policies decide who reads and writes each of the forty-odd tables. Two roles kept in their own table behind a security-definer check, eight server-side functions doing the work that has to outrank whoever triggered it, and the first account in a company recorded as its admin so the import works on day one. How far the roles reach is worth knowing exactly: the database enforces admin on the roles table and the accounting settings, and every other write is still company-wide, so narrowing those is a described addition. Read the security section above before you go live.
The seven pages, and the paperwork behind them
An overview of KPI cards, then revenue, expenses, profitability, cash flow, and receivables and payables with ageing and days-sales-outstanding, plus reports: downloadable profit-and-loss, balance-sheet, cash-flow and tax-summary packs as PDF or CSV. Saved filter segments, global search, and audit triggers on invoices, payments and expenses recording the old and new value of every change.
A codebase your AI tool can keep extending
Types on everything, hooks grouped by what they query, folders named after features rather than file extensions, and comments wherever the reasoning would not survive a cold read, including on the parts that need them most, the parser and the jobs. The figures layer is where that pays off: a new definition of margin is the change you are most likely to want, and the existing ones show where a definition belongs.
From founders who build on our templates
As an agency we live or die by clean handoffs. The code is structured well enough that we restyle, wire in the client’s data, and ship - no untangling someone else’s mess.
Matt GrahamFounder & CEO, RapidDevCommon questions
It reads a CSV you export, and that is the first thing to know before comparing it with anything. There is no live connector to an accounting system: you export invoices, payments, expenses, bank lines and rates, upload them, and a server-side function validates and loads them. Sample files ship with the project so you can see the shape expected. A live connection to a specific system is a well-defined addition, and the one most people want second, after a month of their own numbers has actually landed.
They go into a reject table with the reason, and you can look at them, which is more important than it sounds. A dashboard quietly missing forty invoices is not a partly-working dashboard, it is a wrong number presented confidently. Check the reject list after every import as a matter of habit. Most entries are a date format or a column that got renamed in your accounting system, and both are five-minute fixes once you can see them.
As it ships, a language model produces it: the history goes to a hosted model asked for realistic monthly figures, and what comes back is twelve months of plausible numbers rather than arithmetic on your data. It is labelled while loading and not on the finished chart. Treat it as a demo rather than a planning tool, and if you will make decisions from a forecast, the first AI prompt above replaces it with a projection computed from your own figures, keeping the model for the commentary where being fluent is the actual job.
Yes, properly, which is rarer than it sounds. You set a base currency, records keep the currency they were written in, and a rate table with a calendar over it does the conversion. The part worth knowing is what happens on days with no rate. Weekends, holidays, the day you happened to invoice: a job carries the last real rate forward and marks those rows as imputed, so a converted total can say which part of itself was estimated. A real rate is never overwritten by a guessed one.
Whichever you set, and it computes both. Your settings carry a basis, and revenue is worked out from invoices by issue date for accrual and from payments by their date for cash. That matters most if you invoice on terms, because the same month can look strong on one basis and thin on the other, and the gap is what the receivables page exists to measure.
No, and this is the second thing to know before you compare it. You can configure a schedule (a report, a frequency, a next run date, recipients, a format) and nothing delivers it, because no mail provider and no timer exist anywhere in the template. Downloading on demand does work: profit and loss, balance sheet, cash flow and a tax summary as PDF or CSV, plus a bulk export. Connecting an email service and something to run the schedule is a small addition, and the first one most businesses want.
No, and the import is the half an AI coding tool helps with most, because it is tedious rather than clever. Describe your export (its columns, its date format, how it writes a credit note) and back come the tables, the parser, the validation, the reject table, the jobs turning records into daily figures, and the rules deciding who may see them. Your share is opening a free Supabase project and getting one real export to point it at.
Yes, and the second half deserves a precise answer rather than a reassuring one. Sign-in comes with two roles, and the first account in a company is its admin. What the database enforces is that only an admin may import, rebuild the figures, change the accounting settings, or decide who else is an admin. What it does not yet enforce is the rest: a viewer can still write a financial record directly, because the interface has no notion of a role, so tightening those rules without a matching pass over the screens would turn ordinary actions into silent failures. Closing it is a described addition. Either way, test a viewer by trying things with it rather than reading the code.
Yes. Every record hangs off a company and the access rules are written around that, which is what makes it suit a group or a practice with clients. Two things before you load anything real. Read the security section above, because the rules deciding what one company can see are the most load-bearing lines here. And test the separation bluntly: two companies, two accounts, and a deliberate attempt to reach the wrong one.
Three lines rather than the usual two: somewhere to hold the data and somewhere to serve the app, both with free tiers, plus the model the forecast calls, usage-based, and the only line here that is not optional out of the box. Once you are reading real figures, the upgrade worth making is Supabase Pro from $25/mo, mostly to stop the pause, since a free project sleeps after a quiet week and a dashboard read monthly is exactly the sort that goes quiet. Nothing on that bill moves when you add a company, a page or a reader.
Nothing here is proprietary, and this template is unusual in having two ways out: your records and computed figures sit in plain PostgreSQL tables any Postgres host accepts from a standard dump, and the reports download as PDF or CSV. Worth remembering where the real lock-in in this category lives, though. Not the data, the definitions. What your business counts as revenue, on which basis, at which rate. Those are in your own code here, in writing.
Yes, and worth doing early. Every host above attaches a domain in a few clicks with HTTPS included. There is a second reason beyond tidiness here: the link you send somebody is a link to your company’s finances, and an address on your own domain is part of how they know it is really yours.
No, though you will type the occasional command: installing Codex, starting the app, applying a database change. The setup section above lists what you need, with a link for each, and once it’s on your machine Codex runs most of those commands for you.
A regular ChatGPT chat can sketch ideas and write snippets, but it isn’t working on your actual project. Codex reads and edits the real files on your computer. The app you get out of it is one you can run and publish, not a preview.
On a ChatGPT plan, Codex’s usage resets on a rolling window rather than billing per token, so a heavy day of building can bump into a limit. You either wait for it to reset, move up a plan, or switch to pay-as-you-go API billing for the rest of the session. Nothing you’ve already built is lost either way, so the work only pauses.
References
Sources checked August 2026- 01CFO trust in financial data (BlackLine survey, Censuswide, 1,300+ respondents, January 2024). prnewswire.com (survey published January 2024)
- 02Pricing (per-company tiers, unlimited users, AUD), Fathom. fathomhq.com
- 03Pricing (per-dashboard tiers, refresh rates, unlimited users), Klipfolio. klipfolio.com
- 04Pricing (per-data-source model, free-tier limits), Databox. databox.com
- 05Pricing (flat monthly tiers, one company active at a time), LivePlan. liveplan.com
- 06Pricing (two “starting at” figures, no stated unit), Jirav. jirav.com
- 07Pricing (Pro plan, free-tier limits, project pausing), Supabase. supabase.com
- 08Web developer hourly rates 2026 (freelance and agency benchmarks). developex.com
- 09Row Level Security, Supabase docs. supabase.com
- 10Storage access control, Supabase docs. supabase.com
- 11Edge Functions secrets and environment variables, Supabase docs. supabase.com
- 12Pricing (plans, usage limits), ChatGPT docs. learn.chatgpt.com
- 13Codex CLI, ChatGPT docs. learn.chatgpt.com
- 14API pricing (models), OpenAI for developers. developers.openai.com
- 15IDE extension, ChatGPT docs. learn.chatgpt.com
- 16ChatGPT desktop app, ChatGPT docs. learn.chatgpt.com
- 17Codex cloud, ChatGPT docs. learn.chatgpt.com
- 18AGENTS.md, ChatGPT docs. learn.chatgpt.com
This guide is general information, not accounting, tax or financial advice. What you may report, on which basis, and how long you must keep a record of it vary by country, and a figure on a dashboard is not a filed return, so check with somebody qualified before you rely on one. Third-party prices, plan terms, and market rates are quoted from the sources above and were last checked on the date shown. Vendors change them without notice, so confirm before you budget. Build hours and the cost estimates derived from them are our own estimates, not quotes. Codex, ChatGPT, and the OpenAI API are products of OpenAI. Verify current capabilities and pricing before relying on them.