Gross margin in software companies: the CTO effect
Learn how gross margin in software companies changes with infrastructure choices, onboarding effort, support load, and custom work.

Why margin slips as revenue grows
More revenue should make a software company healthier. In practice, gross margin often drops when customer growth moves faster than the team's ability to deliver in a repeatable way.
The problem is simple: the product sells like software, but parts of the business still run like a service. Every new account brings hosting costs, setup work, support time, and odd requests that never show up clearly in the price.
A small SaaS team can grow from 40 to 120 customers and still feel poorer. Monthly revenue rises, but one engineer now spends hours on imports, API fixes, billing edge cases, and customer-specific reports. None of those tasks looks serious on its own. Together, they can eat a full salary.
Manual onboarding is a common leak. If every sale needs data cleanup, account setup, training calls, or hand-built workflows, each customer turns into a mini project. Sales celebrates the deal, then delivery picks up a pile of unpaid work.
Support creates the same drag. A 10-minute task sounds harmless until it happens 15 times a day. Resetting a broken sync, explaining a confusing setting, checking a failed job, or fixing a permission issue can quietly add dozens of paid hours each month.
Custom work makes the problem worse. Engineers maintain code only a few customers use. QA has more cases to test. Support has more exceptions to remember. Product planning gets messy because special promises pile up.
This is where technical leadership matters. A strong CTO does not look only at uptime or feature output. They ask which work repeats, which work should become product, and which requests should stay out of the codebase unless a customer pays enough to cover the cost.
When a team misses that discipline, revenue can rise while delivery costs rise even faster. The company looks busy, customers keep coming in, and the margin line gets worse month by month.
What technical leadership changes day to day
A good CTO does not fix margin with one big rewrite. The change shows up in daily decisions: what sales can promise, what engineers build first, what support keeps doing by hand, and which customer requests get a polite no.
That is where margin gets won or lost. If the team ships features that reduce setup time, cut repeat support tickets, and keep the product within clear limits, gross margin usually improves before revenue jumps.
One of the biggest shifts is simple. Product limits get written down early. Sales needs clear rules on what is standard, what costs extra, and what the team will not do. Without that line, every new deal pulls in custom fields, special workflows, or odd integrations that sound harmless on a call and turn into months of hidden labor.
A practical CTO also tracks cost per customer, not just the monthly cloud bill. Two accounts can pay the same price and cost very different amounts to serve. One customer follows the normal setup and sends two support questions a year. Another needs hand-held onboarding, custom reports, and weekly help from engineers. Revenue looks the same. Margin does not.
That changes the work queue. Teams start turning repeated setup steps into defaults, templates, and scripts. They fix the product issue behind recurring tickets instead of answering them forever. They review custom requests against support time and renewal odds. They judge engineering work by whether it lowers service hours per account.
This is why repeatable setup matters so much. If a team spends three hours preparing each new account, that time acts like a service cost even if nobody labels it that way. Teams with strong technical leadership push those hours down with forms, self-serve flows, better defaults, and fewer edge cases.
The same logic applies to support. A bug fix that removes 40 tickets a month often does more for margin than a feature that looks impressive in a demo. Some CTOs learn this the hard way. Others build the habit early and keep one question in view: does this work lower cost, protect retention, or stop custom work from spreading?
That discipline is not glamorous. It is usually what separates a software business with healthy margins from one that grows revenue and still feels tight on cash.
Infrastructure spend you can still control
Many software teams treat cloud spend like rent. They pay it and move on. That hurts gross margin because infrastructure costs often rise quietly, one small choice at a time.
The fix starts with a monthly habit: compare your bill with real usage. Do not stop at the total. Look at CPU, memory, storage, bandwidth, database load, and background jobs. If a server sits at 10% usage for weeks, you are not buying safety. You are buying waste.
Teams also lose money on leftovers. Old staging machines, duplicate logging tools, unused managed services, and oversized database plans stick around because nobody owns the cleanup. A CTO or technical lead should make that cleanup routine, not a once-a-year panic.
A simple monthly review often finds the same problems: app servers sized for last year's traffic, two tools doing the same monitoring job, preview environments nobody uses, workers running too often, or storage plans that cost more than the data needs.
Architecture matters too. Many small SaaS products copy systems built for companies 50 times larger. They add Kubernetes, several queues, multiple databases, and extra services before they have the traffic to justify any of it. That looks impressive in diagrams. It usually looks bad on the margin line.
For a small product, a simpler stack often wins. One solid database, a few well-sized services, clear caching rules, and basic observability can carry a surprising amount of load. Oleg Sotnikov has shown this in practice by running production systems on lean infrastructure, with careful right-sizing and near-perfect uptime, instead of piling on expensive layers.
The same logic applies to operations. If deployments need a senior engineer watching every release, your costs are higher than the cloud bill suggests. Simple deployment checks, clear alerts, and monitoring that points to the real problem cut babysitting time and give the team hours back every week.
Infrastructure spend is controllable when someone checks it on purpose. If nobody does, the bill keeps growing long before revenue does.
Onboarding work that eats service time
A sale does not become healthy revenue on the day the contract gets signed. Margin starts moving when the team spends time getting a customer to their first real result. If that takes two hours for one account and 20 for the next, the price may look the same while the profit does not.
Start with one number: hours from signature to first value. First value means the moment the customer can do the thing they bought the product for. For one SaaS company, that might be the first working dashboard. For another, it might be the first automated report or the first live workflow.
Write down every step in that path and be honest about who touches it. Many teams think onboarding is self-serve until they count the hidden work: a founder joins a kickoff call, an engineer cleans imported data, someone fixes permissions, and a product person explains settings that should have been obvious in the app.
A quick review usually exposes the pattern. The team keeps doing the same account setup, data import, integration checks, training calls, follow-up questions, and pre-launch checks for almost every customer.
Those tasks are not small if they repeat for every account. They pull engineers away from product work and push founders into unpaid service work. That is one reason gross margin in software companies slips even when revenue keeps growing.
The fix is rarely a bigger onboarding team. It is better defaults, tighter templates, and fewer choices at the start. If most customers need the same fields, create a standard import format. If the same three settings confuse people, prefill them. If every account needs the same integration steps, turn them into a guided flow inside the product.
A small SaaS team can save a lot of time this way. A founder who spends six hours per new customer on setup can often cut that to 90 minutes with standard workspaces, sample data, and a fixed launch sequence. That improvement goes straight to margin.
Some onboarding still becomes custom delivery. When a customer wants special data mapping, unusual security rules, or a one-off workflow, treat that as project work and price it separately. If you bundle custom setup into the base subscription, you hide the real cost and train customers to expect consulting for free.
Support load that grows one ticket at a time
Support cost rarely jumps all at once. It creeps up through small requests that look harmless on their own. One extra login issue, one import question, one billing change, then another. After a few months, a team spends half its week answering the same problems, and margin starts to shrink without anyone naming the cause.
A good CTO does not treat support as a separate function. Support is product feedback with a price tag. If five people answer the same question every week, the company does not have a people problem. It has a product, setup, or documentation problem.
A simple ticket sort usually shows where the time goes: bugs, training questions, setup and integration issues, and account or billing changes. That split matters because each type needs a different fix. Bugs need product work. Training questions usually point to confusing screens, weak defaults, or docs nobody can use quickly. Setup issues often point to a weak onboarding flow. Account changes may need self-serve controls so the team stops doing admin work by hand.
Repeat tickets are the expensive ones. If customers keep asking how to import data, do not keep polishing the reply. Change the import flow. Add a sample file. Put the warning in the product at the exact step where people get stuck. One small fix can remove dozens of tickets a month.
It also helps to watch support by customer, not just by topic. Some accounts generate far more work than others. That does not always mean they are bad customers, but it does mean pricing, onboarding, or scope is off. If a low-revenue account needs constant help, the team should notice early.
Turn patterns into product decisions
Support trends should reach the roadmap every month. They should also reach the docs, onboarding scripts, and account rules. Teams that want lean operations should use support data to remove work, not just answer it faster.
When leaders do this well, support gets smaller, calmer, and cheaper. When they do not, every new customer adds a little more service work, and margin slips one ticket at a time.
Custom work and margin drift
A SaaS product gets expensive when the team keeps saying yes to one-off requests. One customer wants a special report. Another asks for a custom approval step. A third needs a private export format. Each request sounds small. Together, they pull engineers away from the main product and add work that never really ends.
The first fix is simple: split product work from client work. If a request helps many customers and fits the product direction, it belongs on the roadmap. If it helps one account close a deal, treat it as custom work with its own price, scope, and owner. When teams mix these two buckets, they lose track of what the product really costs to build and maintain.
A boring test works well here. Before approving a request, ask whether more than a few customers will use it soon, whether the team will need to support it for years, whether it makes setup, testing, or documentation harder, and whether the customer would still buy if it were a paid add-on.
If the answer points to one customer and ongoing effort, call it what it is: a service. That does not make it bad. Some custom work pays well. The problem starts when the company prices it like a free favor.
Free post-sale changes cause quiet damage. Sales promises a few tweaks to get the contract signed. Then product, engineering, and support spend weeks delivering 'small' edits. Set limits early. Include a clear number of changes in onboarding, define what counts as out of scope, and charge for extra work. Most customers accept boundaries when you state them before the work starts.
Services revenue can also hide weak product margins. On paper, revenue goes up. In practice, the company may be funding custom delivery with product engineers and calling it SaaS growth. This is one reason gross margin can look healthy at first and then slide quarter by quarter.
A small team feels this fast. One custom integration for a single client can turn into extra testing, support tickets, release delays, and late-night fixes. Technical leadership matters here because someone needs to say no, or at least say, 'Yes, but this is paid client work, not part of the core product.' That one line protects margin better than most pricing tweaks.
Review your margin step by step
Margin problems usually hide in routine work, not in one dramatic bill. A simple review can show which customers, features, or habits are quietly pulling profit down.
Start by splitting your numbers by customer segment. Do not mix small self-serve accounts with larger customers who need setup calls, extra support, or custom work. If you lump them together, healthy accounts can hide the expensive ones.
A plain spreadsheet is enough for the review:
- Group customers by type, plan, or deal size and write down monthly revenue for each group.
- Subtract direct costs tied to serving them, such as hosting, third-party tools, payment fees, and support time.
- Add labor that often gets ignored, including onboarding hours, migration work, training sessions, and custom delivery.
- Compare the result before and after a product or process change.
- Repeat the same review every month or quarter so small changes do not pile up unnoticed.
Support time needs a real cost, not a guess. If a support engineer spends 15 hours a month on one customer group, assign a dollar amount to those hours. Do the same for founder time, because founder support is still support even if it never shows up on payroll.
Onboarding and custom work often create the biggest surprise. A customer paying $300 a month can look fine until you notice the team spent six hours setting them up and two more hours changing reports for them. A larger account paying $2,000 a month may need less attention and leave you with better margin.
This review also helps you judge changes with less emotion. If a new deployment setup cuts cloud spend by 20%, or a tighter product scope removes 10 hours of custom work each month, the effect should show up quickly. Good technical leadership turns that review into a habit, not a rescue mission after margins already fell.
A realistic example from a small SaaS team
An eight-person B2B SaaS team had a good sales story and a weak cash story. Monthly recurring revenue rose from $48,000 to $66,000 in less than a year, but payroll still felt tight and the founders kept asking why growth was not turning into breathing room.
The problem sat in work they did not track well. Each new customer needed manual setup: create an account, import messy CSV files, fix field mapping, set permissions, and tweak one report because sales had promised a 'small change.' One engineer spent about two days a week on onboarding. The support lead handled 70 to 90 tickets a week, and many tickets came from the same setup issues.
The cloud bill added pressure too. The team had put every customer on bigger instances than they needed because nobody wanted a slow demo or a complaint during a trial. That choice felt safe, but it pushed infrastructure costs up while service time kept growing.
This is often where a fractional CTO starts. In this case, the team made two changes. They replaced manual account setup with automatic tenant creation, a standard import template, and preset user roles. They also removed custom report tweaks from the base plan and offered one default report that covered most customer needs.
Customers did not get less help. They got clearer onboarding. The product checked import files before upload and flagged common mistakes on the spot. Support added short in-app answers for the top five ticket types, which cut repeat questions fast.
Three months later, the numbers looked much better. Onboarding time dropped from about six hours per customer to 90 minutes. Weekly ticket volume fell from around 80 to 35. The monthly cloud bill dropped by about 18% after the team right-sized idle services. Gross margin rose from roughly 63% to 78%.
That is how gross margin in software companies often changes in practice. A team removes work that customers do not really want to pay for, and margin starts to move without a price increase.
Mistakes that hide the real cost
Margins often look fine on a dashboard right up to the moment cash gets tight. The usual reason is simple: the team counts obvious costs and ignores the work that sits between product, support, sales, and founders.
One common mistake is using one average margin number for every customer. That hides the difference between a clean self-serve account and a customer who needs weekly calls, manual setup, special reports, and constant follow-up. Revenue may look the same on paper, but the second customer can eat twice the time.
Founder time gets ignored even more often. If a founder spends six hours a week on demos, onboarding, bug triage, or writing one-off SQL for customers, that is not free. It is labor. It also blocks work on pricing, hiring, and product fixes.
Old tools create another quiet leak. Teams keep legacy services because nobody wants to sort out who owns the cleanup. A forgotten analytics tool, an old staging server, three overlapping support apps, or a paid integration that only one customer still uses can stay on the bill for years. The monthly cost may look small. The total is not.
Short-term sales pressure makes this worse. A team says yes to custom work to close one deal, then says yes again because the first deal worked. Soon the roadmap bends around special cases. Engineers spend time on edge cases, support has more to learn, and onboarding takes longer because every account now starts a little differently.
Hiring more support can hide the same problem instead of fixing it. If users keep asking the same five questions, the product or setup flow usually needs work. More agents may lower the queue today, but they also lock in a cost that repeats every month.
The warning signs show up early. One customer segment asks for much more help than the rest. Founders still handle support or onboarding after the first few hires. Tool renewals happen automatically and nobody reviews usage. Sales keeps promising work the product does not handle cleanly.
A small SaaS team can drift into this without noticing. Ten small exceptions across onboarding, support, tooling, and custom requests can erase more margin than one large cloud bill. Good technical leadership starts by making those hidden costs visible, customer by customer and workflow by workflow.
Quick checks and next steps
When people talk about gross margin in software companies, they often jump straight to hosting bills. That misses the bigger picture. Margin usually leaks through a mix of infrastructure, onboarding time, support effort, and custom work that nobody priced clearly.
A quick review can expose the problem faster than another finance meeting. Start with a short check:
- Name the customer type that costs you the most to serve. If your team cannot answer fast, your reporting is too broad.
- Check whether new customers still need engineer time for setup, data import, permissions, or training.
- Compare support tickets per customer before and after recent releases.
- Read one month of custom requests before you set prices for the next quarter.
- Review infrastructure spend next to support and onboarding, not on its own.
One customer can look profitable on paper and still drain time every week. A team might close a decent annual contract, then spend four engineer hours on setup, answer the same reporting questions every month, and build two one-off features that no other customer wants. Revenue goes up. Margin does not.
Pick one fix and measure it for 30 days. Remove one manual setup step. Cut one recurring support issue. Say no to one custom request unless the price covers the work. Small changes are easier to track, and they show which cost driver matters most.
If you want an outside review, Oleg Sotnikov at oleg.is offers Fractional CTO help for startups and small businesses that need clearer product boundaries, leaner infrastructure, or a more practical path to AI-augmented development. That kind of review helps when the team feels busy, customers seem happy, and the numbers still refuse to improve.
Frequently Asked Questions
Why can gross margin drop even when SaaS revenue goes up?
Revenue can rise while delivery costs rise faster. That happens when new customers bring manual setup, repeat support work, odd requests, and higher hosting costs that your pricing does not fully cover.
What usually hurts margin first in a small SaaS company?
Start with onboarding and support, because teams often ignore those hours. Cloud waste matters too, but a few hours of engineer or founder time per customer can erase margin faster than most people expect.
How do I know if onboarding is too manual?
Check how many human steps happen between signature and first value. If engineers fix imports, set permissions, run training calls, or patch workflows for most new accounts, onboarding still works like a service.
Should we turn custom client requests into product features?
Only build it into the product if several customers will use it soon and it fits your product direction. If one account wants it and your team will support it for years, sell it as paid client work or say no.
How should we charge for special setup, reports, or integrations?
Price one off work separately from the subscription. Put the scope, delivery time, and support limits in writing so sales, engineering, and the customer all see the same boundary.
Which support metrics matter for margin?
Watch tickets per customer, repeat ticket topics, and support hours by account segment. If the same question keeps coming back, fix the screen, flow, or default instead of paying people to answer it forever.
Is reducing cloud spend as useful as fixing product and process issues?
Both matter, but they fix different leaks. Right size servers and remove unused tools for a fast bill reduction, then fix product and onboarding issues to cut labor every month after that.
When does it make sense to hire a fractional CTO?
Bring one in when revenue grows but the team still feels squeezed, or when sales promises keep turning into custom delivery. A good fractional CTO can set product limits, trim waste, and turn repeat work into standard flows without forcing a big rewrite.
What is the simplest way to review gross margin each month?
Run a simple monthly review by customer type. Compare revenue against hosting, third party tools, payment fees, onboarding hours, support time, and custom work so you can see which accounts actually make money.
What quick change usually gives the fastest margin win?
Pick the biggest repeated task and remove it. For many teams, that means standardizing imports, default settings, or account setup, because shaving hours off every new customer moves margin fast.