The audit you can add to what you already sell.
Three modules, worked in order, with the checks written out so you can run them on a real client rather than read about them. Module one finds the databases and where they live. Module two audits the repositories. Module three is what to charge for the whole thing.
Free, nothing gated, and no email required. Everything you type stays in this browser and is never sent anywhere, which is architectural rather than a promise: there is no server call on this page to send it with.
SPEAKING AT AI UNLEASHED INTENSIVE, FALL 2026, CANCUN
Why discovery comes before security, and not the other way round
The instinct is to start with the repository, because that is where the obvious findings are and a committed API key is a satisfying thing to hand somebody in week one.
Do it in that order and you will produce a report about the systems you happened to look at. You will not know whether the key you found opens the production database or a test one, whether the database it opens holds customer records or sample data, or whether there is a second database nobody mentioned because it belongs to a tool the marketing team bought.
A finding without that context is a fact. A finding with it is a recommendation, and a recommendation is what a client is paying you for. So the order is: work out what data exists and where it lives, then look at what could reach it.
There is a second reason, and it is the commercial one. Discovery is the part a client can answer in a meeting, it costs you almost nothing, and it is what tells you how big the repository job actually is. Quoting a repository audit before you know how many repositories there are is how a fixed fee becomes a loss.
How to work through this
Do it against a real client if you have one and against your own systems if you do not. Your own is a better first run than a hypothetical, because every answer is checkable and you will find something.
Each step has what you do, how to check it, and what a bad answer means when you write it up. Mark each one as you go. Nothing is scored and there is no grade, because the output of an audit is a list of findings rather than a number.
What you get at the end is a text summary of everything you entered. Copy it into your notes or your proposal. That is the point of doing it here rather than reading it.
1. Find the databases, and where they live
You cannot secure what you have not found, and you cannot price the job until you know how big it is.
2. Audit the repositories
Now that you know what data exists, you can say what a given exposure actually reaches.
3. What to charge
Price the work by the hours it takes, then decide where it sits in what you sell.
1. Find the databases, and where they live
You cannot secure what you have not found, and you cannot price the job until you know how big it is.
The goal of this module is one table. Every place client data is stored, what it runs on, who hosts it, which region it sits in, whether anybody has ever restored a backup from it, and whether it holds personal information.
Most small businesses cannot answer this from memory, and that is not a criticism of them. It is usually the first genuinely useful thing you produce, and it is often the moment the engagement becomes real, because somebody in the room learns about a database they did not know existed.
1.1 Ask before you look
Start with the question rather than the investigation. Ask who built it, what it runs on, and where the hosting account is.
- Ask for read only access to the hosting dashboard rather than credentials. Read only is easier for them to say yes to and it is all you need.
- Ask specifically: is there anything else that stores customer information, including spreadsheets, a form tool, a booking system, or a CRM somebody bought on a card.
- Write down who they name as the builder. That person is your best source and often your only one.
What it means: If nobody in the business can name what the system runs on, that is finding number one and it goes at the top of the report. Not as an accusation, as the reason for everything below it.
1.2 Find the connection strings
The connection string tells you the engine, the host and often the region, in one line. It is the fastest identification you will get.
- Look for an environment file: .env, .env.local, .env.production, or the environment variables panel in the hosting provider.
- Look for DATABASE_URL, POSTGRES_URL, MYSQL_URL, MONGODB_URI, REDIS_URL, or a SUPABASE_URL and key pair.
- The scheme names the engine. postgres and postgresql, mysql, mongodb and mongodb+srv, redis, sqlite for a file on disk.
- Do not paste a connection string into a chat tool, a notes app, or anything else on your way to writing it down. It is a credential.
What it means: A connection string that is readable by anybody with the repository or the dashboard is normal and is not itself the finding. Where it is stored, and who can read it, is module 2.
1.3 Work out managed or self hosted
A managed service and a server somebody set up in 2019 are different jobs with different risks, and the answer changes what you recommend.
- Managed looks like a provider console: a Supabase, Neon, PlanetScale, RDS, Atlas or similar dashboard with the database as an object in it.
- Self hosted looks like a virtual machine or a container you can log into, with the database running as a process on it.
- A managed service handles patching and usually backups. A self hosted one does neither unless somebody set it up, and the person who set it up has often left.
What it means: Self hosted with no named owner is a real finding and it is the one most likely to be quietly out of date. Say who is responsible for patching it, and if the answer is nobody, that is the sentence to write.
1.4 Find the region, and write it down
Where the data physically sits matters to some of your client obligations and to some of the contracts their own customers hold them to, whether or not anybody has thought about it.
- The region is on the provider console, usually beside the instance name. It is also often inside the hostname.
- Ask whether any customer contract or privacy notice says where data is held. Then check whether that is where it is actually held.
- Note it per database, not once for the business. A main database in one region and a backup or an analytics copy in another is common and is exactly the kind of thing nobody has looked at.
What it means: A privacy notice that names a region the data is not in is a finding you should raise carefully and in writing. You are not qualified to say what it means legally, and you should say that while you say it.
1.5 Find the backups, then ask when one was last restored
The second half of that sentence is the whole step. A backup nobody has ever restored is a belief, not a backup.
- Confirm backups exist, how often they run, and how long they are kept.
- Ask when a restore was last performed, and by whom. Write down the answer verbatim.
- Check whether the backup is in the same account as the database. If one login controls both, one compromised login loses both.
What it means: Never restored is the normal answer and it belongs in the report every time. The recommendation is small and specific: restore one, to a scratch environment, and time it. That is an afternoon and it converts a belief into a number.
1.6 List who and what can reach it
People, applications, and anything that connects on a schedule. Including the things nobody thinks of as access.
- People with console or client access, by name, including former contractors.
- Applications, and whether each one has its own credential or shares one.
- Analytics, reporting and backup tools, which usually have broad read access and are usually forgotten.
- Check whether the database is reachable from the public internet, or only from inside a network.
What it means: A shared credential used by several applications means you cannot tell which one did anything, and you cannot rotate it without coordinating every one of them. That is worth stating plainly, because it makes every later recommendation harder and more expensive.
1.7 Mark which ones hold personal information
This is the field that decides how much everything else matters, and it is the one that turns your findings into priorities.
- Names with contact details, addresses, dates of birth, account or identification numbers.
- Anything about health, payments, biometrics, or children, which raise the stakes considerably.
- Free text fields, which are where the surprising personal information usually is: support notes, order comments, internal remarks about a customer.
What it means: You are identifying where personal information is, not assessing whether any law applies to it. Say which regime plausibly applies and who they should ask. Do not tell them what it requires.
1.8 Write the inventory down, and hand it over on its own
The table below is the deliverable. It is worth handing over by itself, before the repository work, because it is useful to the client even if they never buy anything else from you.
- One row per store. Include the ones that are not really databases: the spreadsheet, the form tool, the booking system.
- Mark unknowns as unknown rather than leaving them blank. An unknown is a finding and a blank is an oversight.
- Date it. An inventory without a date stops being true and nobody can tell when it stopped.
What it means: If this is the first inventory the business has ever had, say so in the covering note. It reframes what you are about to charge for the second module.
The inventory
One row per place client data is stored, including the ones that are not really databases. Add as many as you need.
STORE 1
Managed or self hosted
Backup restored and timed?
Holds personal information?
Everything in the table stays in this browser. There is no server call on this page, so it cannot be sent anywhere even by accident. Do not put a real password or a full connection string in it anyway: you do not need one to describe a system, and a habit of not pasting credentials into web forms is worth more than this one form being safe.
2. Audit the repositories
Now that you know what data exists, you can say what a given exposure actually reaches.
This is the module with the findings in it, and the reason it is second is that a finding is only worth what you can say about its consequences. "There is an API key in this repository" is a fact. "There is a key in this repository, in the history, that opens the production database you told me holds eleven thousand customer records" is an audit.
Work down the list. Each item is checkable in minutes, and the whole list on a small business stack is a couple of hours once you know where things are.
2.1 Check whether it is public
Start here because it takes ten seconds and it changes the severity of everything else on the list.
- Look at the visibility setting on every repository in the organisation, not just the ones you were shown.
- Check forks. A private repository forked to a personal account and made public is a real and ordinary way this happens.
- Check any repository that was public in the past. Making it private later does not unpublish what was already copied.
What it means: A public repository containing real configuration is the highest severity thing on this list, and it is the one that is genuinely common. Treat anything ever committed to it as disclosed, whatever the file says now.
2.2 Scan the current files for secrets
The obvious pass. Committed API keys, tokens, passwords and connection strings sitting in files that are in the repository today.
- Search for the shapes rather than the words: long random strings, key prefixes used by the providers this client actually uses, and the connection string schemes from module 1.
- Search for the names: SECRET, TOKEN, PASSWORD, API_KEY, PRIVATE_KEY, and any variable name you saw in the environment file.
- Look in the places people forget: configuration files, test fixtures, seed data, documentation, notebooks, and CI workflow files.
- The free repo review scanner on this site does the current file pass on a public repository from your own browser. It is a starting point and it says plainly what it does not check, which is the next two steps.
What it means: Match every credential you find against the module 1 inventory and say what it opens. A key nobody can attribute to a system is a key nobody will prioritise rotating.
2.3 Scan the history, which is the one people miss
A secret that was committed once and removed in the next commit is still in the history and is still burned. This is the single most commonly skipped check on this list.
- Search the full commit history rather than the current tree. The current tree is what a casual look shows you and it is the one place the secret is not.
- Pay attention to the commit that removed a secrets file. That commit is a signpost: it tells you a secret existed and roughly when.
- Check deleted branches and old tags. Removing a file from the default branch does not remove it from a tag that still points at the old commit.
- This is a well documented, ordinary failure class rather than an exotic one. Live tokens committed in plaintext, sometimes surviving in history for weeks after the file itself was cleaned up, is how a large share of published credential incidents actually begin.
What it means: The recommendation for anything found in history is rotation, not deletion. Rewriting history is a separate and disruptive job, and it does not help at all if somebody already has the key. Rotate first, argue about the history afterwards.
2.4 Check gitignore coverage for environment files
The control that stops the next secret being committed. Worth checking even when nothing has been committed yet.
- Confirm .env and its variants are ignored, and that an example file is tracked in their place so nobody has to guess the shape.
- Confirm credential and key file types are ignored: .pem, .key, .p12, service account JSON files.
- Check whether an environment file is currently tracked despite being listed. Adding a path to the ignore file does not untrack a file that is already in.
What it means: A tracked environment file is both a current exposure and a history exposure, and it should be reported as both.
2.5 List who has write access
People, machines, and integrations. Write access is what turns a compromised account into a supply chain problem.
- List every member of the organisation and what they can do. Look specifically for former staff and former contractors.
- Check whether two factor authentication is required for the organisation, rather than merely available.
- List deploy keys, machine users, personal access tokens and installed applications, and what each one can reach. These outlive people and nobody reviews them.
- Check outside collaborators, which is where an agency engagement from two years ago is usually still sitting.
What it means: Access that outlives the person is the most ordinary security failure there is, and it is invisible from the client side until it matters. Name the accounts. A general recommendation to review access will not get done.
2.6 Check branch protection on whatever deploys
Find the branch that reaches production, and find out what stands between a commit on it and a customer.
- Identify the branch that deploys. Do not assume it is the default branch.
- Check whether it requires review, whether checks must pass, and whether administrators can bypass both.
- Check whether force pushes and deletion are allowed on it.
What it means: On a one person project, no branch protection is a reasonable trade and you should say so rather than padding the report. On a team, it is the difference between a mistake and an incident.
2.7 Turn on the free automated protections
Most hosts now offer secret scanning and push protection at no cost. On many accounts they are simply switched off.
- Check whether secret scanning is enabled at the organisation level.
- Check whether push protection is enabled, which is the one that blocks a secret before it is committed rather than reporting it afterwards.
- Check whether anybody receives the alerts, and whether that person still works there.
What it means: This is the cheapest recommendation in your report and it should be flagged as such. Say it takes a few minutes and costs nothing, because a report where every item is expensive gets shelved entirely.
2.8 Run the dependency audit, then read it properly
Run the tool, then do the part the tool cannot: work out which findings actually reach anything.
- Run the audit built into the ecosystem: npm audit, pip-audit, bundle audit, or the equivalent. Record the counts by severity.
- Check whether a lockfile is committed. Without one, the audit describes a build nobody will reproduce.
- Separate what is reachable from what is not. A high severity advisory in a build time tool that never runs in production is not the same as one in the request path, and reporting them identically is how a report loses credibility.
- Check whether automated dependency updates are enabled and whether anybody merges them. A queue of ninety unmerged update pull requests is its own finding.
What it means: Report the counts and then report the two or three that matter, with your reasoning. A raw audit dump is not a deliverable, it is a screenshot of a command somebody could have run themselves.
2.9 Rotate what you found, and verify it changed
The step that turns a report into work done. It is also where the client learns whether rotation is possible at all.
- Rotate anything found in current files or in history. All of it, including the ones somebody is sure were never real.
- Verify the old credential no longer works. A rotation nobody tested is a rotation that may not have happened.
- Record where each credential now lives. If the answer is a new file in the same place, nothing has been fixed.
- Time it. How long a full rotation takes is one of the most useful numbers you can hand a client, and almost none of them know it.
What it means: If a credential cannot be rotated without breaking something, that is a bigger finding than the exposure was. It means the system cannot recover from a leak, and that belongs near the top of the report.
2.10 Write it up so somebody can act on it
Ordered by what it reaches, not by what the tool called it. This is the part that is actually yours.
- One line per finding: what it is, what it reaches from the module 1 inventory, and what closing it takes.
- Sort by consequence, and put the cheap fixes with expensive consequences at the top.
- Say plainly what you did not check. Scope is what stops a clean report being read as a clean bill of health.
- Do not send a report containing a live secret over email or chat. Reference it by location and hand the value over separately.
What it means: A clean run means the ordinary failures are not present on the day you looked. It is worth knowing and it is not the same as being secure. Write that sentence into the report yourself, before somebody quotes your report back at you as if it said otherwise.
The free repo review scanner on this site runs the current file pass on a public repository, in your browser, and it is deliberately explicit that it does not check git history or dependencies. Those are steps three and eight above, and they are the two that need a person.
3. What to charge
Price the work by the hours it takes, then decide where it sits in what you sell.
You now have a scope: a number of data stores and a number of repositories. That is enough to price, and it is why this module is third rather than first.
The estimator below is arithmetic you can argue with rather than a rate card. It turns your own day rate and the size of the client stack into an hours estimate and a fee band. Change the assumptions if you disagree with them, which you might.
What to charge for it
Hours first, then a fee. The hours come from the size of the stack you just inventoried, and the fee comes from your own day rate rather than from a number we made up for you.
Put your day rate in and there is a number.
The estimator will not invent a rate for you. Every fee on this page is your own rate multiplied by hours you can check, which is the only version of this that survives a client asking how you got to it.
Where the audit sits in what you sell
A paid audit does not sell itself from a standing start. Somebody has to have a reason to believe you can find something before they will pay you to look, and the way that reason gets built is by giving away the cheap version of the same judgement first.
This is not theory and it is not a formula from somewhere else. It is the ladder this business actually runs, and each rung below is a real thing on this site rather than an illustration.
1. Free, and it can tell you no
A tool that produces a real answer without a conversation. The repo review scanner does the current file pass on a public repository from your own browser, and it says plainly that it does not check git history or dependencies. Being honest about the gap is what makes the gap sellable.
2. Low priced, and complete on its own
A document somebody can buy on the spot and use without you. Its job is to pay for the advertising that found the buyer, so the real engagement does not have to carry that cost. It has to be genuinely useful alone, because a product sold as a lead magnet is a lead magnet with a price on it.
3. The audit you just priced
Your time, inside their systems, with findings that name their systems. This is the first rung where the client is buying judgement rather than a document, and everything above it exists to make this one an easy yes.
4. The work the audit found
The rotation, the access cleanup, the backup restore that has never been tested. Priced separately and quoted after the audit, never bundled into it. An audit that is really a sales call for a build is an audit whose findings nobody can trust, including you.
The rung people skip is the second one, and skipping it is why the audit is a hard sell. Free proves you are competent. Paid proves somebody will pay you. Those are two different pieces of evidence and the second one is the one that makes the audit easy to quote.
Take it with you
Everything you entered, as text. Copy it into your notes, your proposal, or the covering email. Nothing here has been sent anywhere and closing this tab loses it.
This walkthrough is educational. It teaches an audit that looks for a class of ordinary, well documented failures, and finding none of them means those failures were not present on the day you looked. That is worth knowing and it is not a security opinion, not a penetration test, and not a statement that anybody is compliant with anything. It also makes no claim about what you will earn from it: the pricing module prices hours, and whether anybody buys those hours depends on you, your market and your reputation, none of which are on this page.
Run it on your own systems first.
Every check above is one you can run today, on something you own, without asking anybody for permission. That is the first run, it takes an afternoon, and it is worth doing before you charge somebody for the second one.
You will find something. Everybody does, and finding it on your own stack is considerably cheaper than finding it on theirs.
Find out what is actually broken before you spend another dollar on AI.
Two weeks, fixed fee, fixed start date. A map of what you run, a ranked list of where AI actually holds with a dollar figure on each, and a fixed price plan to build it. You own the document either way.
Read it. If you do not agree we found at least three things worth fixing, tell us and we refund the fee. You keep the document.
$5,000. TWO WEEKS. THE FEE COMES OFF THE BUILD IF YOU START WITHIN SIXTY DAYS.
WHO THIS IS FOR
A company of roughly ten to two hundred people, already running a CRM or operational system, with revenue coming through it and at least one process held together by hand. That includes agencies, whether the system is for your own operation or for a client's. Pre revenue, or want a chatbot on a marketing site? Wrong firm, and we will say so on the first reply.
- $5,000
- FIXED FEE. IT COMES OFF THE BUILD IF YOU START WITHIN SIXTY DAYS.
- 2
- WEEKS, ON A FIXED START DATE.