At some point, hosting a website became embarrassingly complicated.
You can’t just put files on a server anymore. Apparently, you need a cloud strategy. You need containers. You need orchestration. You need serverless functions talking to managed services through an API gateway while six dashboards monitor the cost of the dashboards monitoring the application.
And obviously, all of this should live inside AWS, Microsoft Azure, Google Cloud, or another enormous cloud platform.
Otherwise, are you even doing infrastructure?
I’ve been building and hosting websites for more than 20 years. I use traditional shared hosting for smaller websites and VPSs or dedicated servers for larger projects, depending on what the project actually needs.
I have never used AWS for my projects.
I have never used Azure, Google Cloud, or a similar hyperscale cloud platform for them either.
My projects have never depended on one of those platforms, and somehow, everything still works. Websites go online. Blogs load. Company presentation sites do their job. Clients can visit pages. The internet does not reject my deployments because they lack a sufficiently complicated architecture diagram.
This approach has saved me time and money.
That does not mean the giant cloud platforms are bad. They are extraordinary pieces of infrastructure, and plenty of companies have excellent reasons to use them.
But the automatic assumption that every modern project belongs inside the same tiny group of giant cloud providers is bizarre.
More importantly, it is helping create an internet that depends far too heavily on far too few companies.
The cloud became the default before anyone asked why
There is a huge difference between asking:
What infrastructure does this project need?
And asking:
Which cloud services should we use?
The second question has already made the biggest decision for you.
It assumes that the project belongs on a hyperscale platform. Now all that remains is choosing the products, wiring them together, configuring permissions, estimating costs, and pretending the resulting pile of dependencies is simpler because nobody has to physically touch a server.
This is how a straightforward website ends up with object storage, edge functions, a managed database, a managed cache, a managed queue, centralized logging, proprietary identity, an API gateway, a container registry, and an infrastructure-as-code repository large enough to require its own maintenance schedule.
Every individual decision can sound reasonable.
Storage as a service? Convenient.
Managed database? Convenient.
Authentication platform? Convenient.
Serverless functions? Convenient.
Global CDN? Convenient.
Managed Kubernetes? Convenient, assuming the alternative was unmanaged Kubernetes and not simply avoiding Kubernetes.
Add enough convenient services together and you eventually build a system nobody fully understands, hosted by a company you cannot realistically leave.
That might be justified for a large, complicated application. It is harder to justify for a blog.
The strange part is that we barely distinguish between those cases anymore. “Put it in the cloud” has become the default answer whether the project is a multinational software platform or a company website with an about page and a contact form.
Those are not the same infrastructure problem.
My stack changes because projects are different
I don’t have one universal hosting architecture.
That is the point.
For a small website, traditional shared hosting can be perfectly fine. It provides a place to host the site without requiring a dedicated server or turning a simple project into an infrastructure hobby.
If the project needs more resources or control, a VPS may make sense.
If the requirements justify dedicated hardware, a dedicated server is still a perfectly legitimate option.
The decision looks something like this:
What does this project actually need?
Small, straightforward website
-> Shared hosting may be enough
More control, resources, or flexibility
-> Consider a VPS
Requirements that justify dedicated resources
-> Consider a dedicated server
Unusual scale, global distribution, specialized managed services
-> A large cloud platform may make sense
Notice that the cloud platform is still there.
It just has to earn its place.
I don’t begin with the assumption that every project needs hyperscale infrastructure. I start with the project and work outward.
Most of what I host consists of websites, blogs, company presentation sites, and similar web projects. These are real projects, but they are not pretending to be Netflix. They need suitable infrastructure, not infinite theoretical scalability.
Apache is perfectly capable of serving these kinds of websites. Traditional hosting is perfectly capable of running them. A VPS can provide plenty of control when more control is actually needed.
CentOS was my favorite Linux distribution for many years. It did not make the infrastructure exciting. It made the infrastructure understandable, which is far more useful.
I also generally recommend control panels, especially for quick administrative actions and less experienced users. They are not mandatory, and they are not appropriate for every server, but dismissing them because “real developers use the command line” is mostly macho nonsense.
If a tool makes a legitimate administrative task quicker and clearer, it is useful.
Infrastructure should be selected with that same practical attitude.
Boring infrastructure has one enormous advantage
You can understand it.
That sounds almost too basic to mention, but understandability has become an underrated technical feature.
A traditional server setup has a relatively direct mental model:
- There is a physical or virtual machine.
- It runs an operating system.
- A web server such as Apache handles requests.
- The website or application runs there.
- The machine has finite resources.
- If the project outgrows those resources, something needs to change.
There are still plenty of ways to get this wrong. Servers require maintenance. Software needs updates. Security matters. Hardware and networks fail. Backups do not magically happen just because the architecture is simple.
But the core model is visible.
A modern cloud application can exist across dozens of products, each with its own configuration, permissions, logs, limits, pricing model, and failure behavior.
The application is no longer just the code. It is the code plus IAM policies plus cloud resources plus deployment configuration plus provider-specific networking plus managed-service settings plus whatever undocumented assumptions are hiding in the account.
At that point, nobody really “runs” the application.
People negotiate with it.
Complexity is sometimes unavoidable. But when a simple architecture can satisfy the requirements, choosing the complicated one is not automatically better engineering.
Sometimes it is just more engineering.
Complexity looks impressive, so we keep buying it
The technology industry rewards visible complexity.
A developer who says, “I put the website on a server,” does not sound particularly impressive.
A developer who says, “We designed a cloud-native, event-driven platform using container orchestration and managed infrastructure primitives” sounds more serious, even if the end result is still a website displaying six pages and a contact form.
Complex systems produce diagrams.
Diagrams produce meetings.
Meetings produce job titles.
Simple infrastructure mostly produces a working website, which is apparently less exciting.
This creates a perverse incentive. We start solving problems we do not have because those solutions are culturally associated with mature engineering.
Nobody wants to be accused of building something outdated. Nobody wants to tell the team that a basic VPS might be enough when every conference talk is discussing platform engineering, service meshes, serverless architectures, and globally distributed systems.
So we plan for imaginary scale.
We design for millions of users before finding the first hundred.
We distribute applications that have no meaningful reason to be distributed.
We introduce orchestration before there is anything worth orchestrating.
Then we spend months operating the infrastructure required to operate the infrastructure.
That is not always sophistication. Sometimes it is fear wearing a technical vocabulary.
You do not need Kubernetes just because it exists
Kubernetes is useful.
It solves difficult problems involving container orchestration, scheduling, service discovery, deployment, scaling, resource management, and resilience. Large organizations with many services and teams can have completely valid reasons to use it.
But Kubernetes solves Kubernetes-shaped problems.
A personal website is not a Kubernetes-shaped problem.
A company presentation site is not a Kubernetes-shaped problem.
A blog is not a Kubernetes-shaped problem.
A straightforward web application does not become more professional because its HTTP requests pass through an ingress controller before reaching a container that replaced a process that could have run directly on a server.
Kubernetes also comes with an operating cost that does not disappear just because the cluster is managed.
Someone still needs to understand deployments, pods, services, ingress, storage, secrets, networking, resource limits, access control, upgrades, monitoring, and the collection of extensions that inevitably starts growing around the cluster.
Managed Kubernetes can remove part of the operational burden. It cannot remove the conceptual burden.
If you need what Kubernetes provides, that burden may be worthwhile.
If you don’t, congratulations. You have successfully created an entire category of work for yourself.
Containers have useful properties. Kubernetes is a powerful platform. Neither fact means every project needs either one.
Sometimes a normal process running on a normal server is not technical debt.
Sometimes it is the correct answer.
Serverless still has servers and now also has a pricing equation
Serverless infrastructure makes sense for certain workloads.
Short-lived tasks, event processing, unpredictable bursts, and workloads that benefit from scaling to zero can be good fits. The provider handles much of the underlying infrastructure, and that can save serious operational effort.
But “serverless” is one of those terms that quietly encourages people to stop thinking.
The servers did not disappear. Ownership and billing changed.
Instead of renting straightforward capacity, you may now pay according to requests, execution duration, memory allocation, storage operations, data transfer, logging, and the other services required to connect everything.
That can be efficient.
It can also turn a simple application into a distributed billing event.
A serverless function may be easy to deploy in isolation. A real serverless application is rarely one isolated function. It usually depends on triggers, permissions, gateways, managed storage, monitoring, deployment tooling, and provider-specific behavior.
The more of those pieces you use, the less portable the system becomes.
Again, none of this makes serverless bad.
It means “serverless” should be an architectural decision, not a fashion choice.
If a conventional application on a conventional server can perform the task reliably, I do not see a problem that needs fixing.
A long-running process is allowed to exist.
A cron job is allowed to exist.
A server is allowed to remain turned on.
Managed services manage you too
Managed services are attractive because they remove work.
A managed database can handle maintenance tasks that would otherwise require time and expertise. A managed identity service can save developers from implementing sensitive authentication systems. Managed queues, caches, storage, and monitoring can accelerate development substantially.
That is all real value.
But the word “managed” tends to emphasize what you stop managing while hiding what you give up.
You give up some control.
You accept a provider’s limits and operational behavior.
You build around its APIs.
You depend on its pricing.
You depend on its product roadmap.
You depend on its policies.
You depend on its account and permission systems.
You depend on the service continuing to exist in a recognizable form.
If several important parts of the application depend on proprietary services from the same provider, leaving becomes progressively more difficult.
Moving a conventional application between servers is not always easy, but at least the pieces are usually recognizable. A web server is a web server. Files are files. Common database engines are available from many providers.
Moving an application deeply integrated with one cloud company’s identity, database, messaging, storage, function runtime, monitoring, and deployment products is not moving a server.
It is a rewrite with luggage.
Vendor lock-in can be an acceptable trade. A proprietary service may provide enough value to justify it completely.
But developers should stop pretending the lock-in is not there simply because the service has a friendly SDK.
Convenience is not independence.
Cloud pricing is simple until you use the cloud
The basic cloud sales pitch is appealing: use what you need and pay for what you use.
That model can be excellent for workloads that change rapidly or need flexible capacity.
It can also create bills assembled from a strange collection of requests, execution time, storage classes, operations, transfer directions, reserved capacity, logs, metrics, gateways, addresses, and regional variations.
The application architecture becomes a pricing architecture.
Every technical decision can introduce another meter.
Run code? Metered.
Store data? Metered.
Read the data? Possibly metered.
Transfer the data? Definitely pay attention.
Keep detailed logs so you can understand the distributed architecture? That is another product.
Analyze why the logging product costs so much? This may require additional monitoring.
With traditional hosting or a VPS, the cost model is often more direct. You rent a defined amount of capacity. The project runs inside that capacity. If it outgrows the available resources, you optimize it or change the infrastructure.
That model is less elastic, but it is easy to understand.
Simple hosting can also be inexpensive. In some cases, a small personal website can even be hosted for free. The right cost depends entirely on the project and its requirements, so pretending there is one universal cheapest option would be dishonest.
Still, plenty of projects do not need a pricing calculator with 40 inputs.
Saving money is not just about finding the lowest monthly price. It is also about avoiding unnecessary engineering, avoiding unnecessary administration, and avoiding an architecture that requires specialized expertise to keep a simple website online.
For more than 20 years, choosing traditional hosting, VPSs, or dedicated servers according to actual project requirements has saved me both time and money.
That is not a theoretical possibility.
It is what I have done.
The deeper problem is not cloud technology
The deeper problem is concentration.
AWS is the most recognizable name in this conversation, which is why it works in the title. But this is not really about AWS.
It is about an internet where an enormous amount of compute, storage, networking, authentication, DNS, content delivery, and application infrastructure is increasingly concentrated around a small number of giant companies.
AWS, Microsoft Azure, and Google Cloud are the obvious examples. Other large platforms and infrastructure intermediaries add more layers to the same pattern.
Each company may run technically impressive infrastructure.
Each individual customer may have a perfectly good reason to use it.
But if everyone makes the same individually reasonable choice, we can still end up with a collectively fragile internet.
That is the part developer culture tends to ignore.
Centralization is convenient right up until the centralized thing fails.
Then thousands of supposedly independent services can start failing together.
One cloud problem can become everybody’s problem
Cloud providers experience outages. So do smaller hosting companies, private data centers, internet service providers, DNS operators, and individual servers.
The existence of an outage does not prove that a provider is incompetent.
It proves that infrastructure fails.
The concentration question is about the blast radius.
On December 7, 2021, AWS experienced a major service event in its Northern Virginia region. An automated capacity-scaling activity triggered unexpected behavior that overwhelmed networking devices connecting AWS’s internal network to its main network.
That internal network supported foundational capabilities such as monitoring, internal DNS, authorization, and parts of the EC2 control plane. The resulting congestion affected multiple AWS services and even impaired AWS’s ability to monitor the incident and handle support cases normally.
The important lesson is not that AWS had a bad day.
The lesson is that many separate-looking cloud services can share critical internal dependencies. When one foundational layer fails, the neat boxes in the architecture diagram stop looking quite so independent.
Microsoft Azure provided another example on January 25, 2023.
A networking change associated with adding capacity to Microsoft’s global wide area network caused widespread connectivity problems. From 07:08 UTC until 12:43 UTC, customers experienced latency and timeouts connecting to resources hosted in Azure regions.
The incident also affected other Microsoft services, including Microsoft 365 and Power Platform. Azure Government services that depended on the public Azure cloud were affected too.
One networking event did not remain one networking event.
It crossed services and customer boundaries because those systems shared major infrastructure underneath.
Google Cloud had a major global incident on June 12, 2025. A policy change triggered a failure in Google’s Service Control system, part of the infrastructure used to apply quota and policy checks to API requests.
The problematic policy data was replicated globally. A software path without appropriate error handling encountered the bad data and crashed, causing increased errors across many Google Cloud and Google Workspace products.
The status infrastructure was affected too, delaying Google’s first public incident report. Some customers also lost visibility because their own monitoring systems were running on the same cloud experiencing the outage.
That last detail should make every infrastructure engineer slightly uncomfortable.
Your application is down.
Your monitoring is down.
The system meant to tell you the cloud is down is also down.
Efficient.
Cloud dependencies do not stop at the cloud provider
The June 2025 Google Cloud incident demonstrated something even more important.
Cloudflare suffered a significant outage at the same time because part of the storage infrastructure behind its Workers KV service depended on a third-party cloud provider affected by the incident.
Cloudflare reported that the outage lasted 2 hours and 28 minutes and globally affected customers using several impacted services. Workers KV was a critical dependency for products involving configuration, authentication, and asset delivery, so failures spread into Cloudflare Access, WARP, Gateway, Turnstile, Workers AI, Pages, Stream, and other products.
This is what modern infrastructure dependency chains look like.
A developer depends on a platform.
That platform depends on another service.
That service depends on a cloud provider.
The developer may not even know which underlying company is ultimately hosting a critical part of the stack.
The service has a different logo, a different account, and a separate invoice. Architecturally, however, the dependency may still lead back to one of the same few giant infrastructure providers.
This is why buying services from several vendors does not automatically create independence.
Sometimes you have simply purchased the same cloud dependency through multiple layers of abstraction.
I use Cloudflare, and I’m still uncomfortable with Cloudflare
I occasionally use Cloudflare, and I think it is a good service.
It solves real problems well. Its scale, network, security features, DNS, and performance tools make it attractive for obvious reasons.
I also dislike how much Cloudflare has contributed to the centralization of the internet.
That may sound contradictory. It is not.
A service can be excellent and still occupy an unhealthy position in the broader ecosystem.
In fact, excellent services are exactly the ones most likely to become central points of dependency. People use them because they are good. Tooling starts assuming they are available. Tutorials make them the default. Competing at the same scale becomes harder.
Eventually, a service that was once optional becomes part of the internet’s unofficial plumbing.
On November 18, 2025, Cloudflare experienced significant failures delivering core network traffic after a database permissions change caused a Bot Management configuration file to unexpectedly double in size.
The oversized file propagated across Cloudflare’s network. Core proxy software had a size limit below the new file size, causing failures across the network.
Cloudflare said core traffic was largely flowing normally again by 14:30 UTC, with all systems functioning normally by 17:06 UTC.
Cloudflare itself acknowledged the significance of its position in the internet ecosystem.
That position is exactly what concerns me.
I can appreciate the product while questioning whether so much internet traffic should depend on one company.
We need more alternatives at that scale, not because Cloudflare is uniquely bad, but because no company should become too difficult for the internet to route around.
Smaller providers fail, but they fail smaller
Traditional hosting providers and independent VPS companies are not magically reliable.
Some are excellent. Some are terrible. Some will suffer hardware failures, network outages, security incidents, overloaded servers, bad support, or business problems.
A cheap VPS is not automatically resilient.
A dedicated server is still one physical machine unless the architecture accounts for that.
Shared hosting can have resource limitations and noisy neighbors. It can offer less control. It may not support unusual software requirements. Scaling may require migration rather than moving a slider in a dashboard.
Simple infrastructure has real limitations.
The point is not that small providers never fail.
The point is that they usually fail independently.
If one small hosting provider has a major incident, its customers are affected. That is serious for those customers, but it does not automatically take a huge collection of unrelated global services down with it.
Concentration changes the nature of failure.
When a dominant cloud, CDN, DNS operator, identity platform, or payment processor has a major incident, enormous numbers of businesses can be affected simultaneously.
That is systemic risk.
Moving every project to one of three giant clouds may improve the infrastructure available to each individual project. It can also make the wider internet more dependent on the same underlying systems.
Both things can be true.
Reliability is not only about how rarely one provider fails. It is also about how much fails with it.
Multi-cloud is not a magic spell
The industry’s answer to cloud concentration is often “multi-cloud.”
In theory, that means designing a system that can run across multiple major cloud providers.
In practice, it can mean paying several giant companies while multiplying your architecture, operational requirements, deployment tooling, networking complexity, security configuration, and staff expertise.
A genuinely portable multi-cloud application can be valuable for organizations that require that level of resilience or negotiating power.
It can also be spectacular overkill.
If avoiding dependence on one complicated platform requires building an abstraction layer across three complicated platforms, the cure may be worse than the disease.
For many smaller projects, provider diversity does not require an enterprise multi-cloud strategy.
It can mean keeping an application portable.
It can mean preferring common technologies.
It can mean choosing a hosting provider without deeply coupling every application component to proprietary services.
It can mean maintaining the realistic ability to move the project elsewhere.
Portability does not need a branded framework.
Sometimes it is simply the result of not making the application unnecessarily difficult to host.
The cloud is excellent when you actually need a cloud
There are plenty of projects for which a hyperscale cloud platform is the right answer.
Applications with unpredictable global traffic may benefit from elastic capacity.
Large companies may need geographic regions, compliance programs, sophisticated access controls, managed data platforms, global networking, machine learning infrastructure, or integration with an existing cloud ecosystem.
Teams running many services may benefit from orchestration.
Specialized workloads may be far easier to build with managed cloud products than with traditional infrastructure.
Fast-growing companies may reasonably decide that vendor lock-in is an acceptable price for speed.
I have no argument with any of that.
The problem begins when tools designed for extraordinary scale become the default recommendation for ordinary projects.
Most websites do not need the infrastructure capabilities of a multinational cloud provider.
They need to load.
They need reasonable security.
They need backups and maintenance appropriate to their requirements.
They need enough capacity for their real traffic.
They need an operator who understands where they are hosted and how to recover them.
A massive catalog of managed services does not automatically improve any of those things.
Sometimes it provides useful solutions.
Sometimes it provides tempting solutions to problems the project never had.
Choosing less is still an engineering decision
Using shared hosting is not refusing to make an infrastructure decision.
It is making one.
Using a VPS is not failing to adopt cloud-native architecture.
It is deciding that the project needs a virtual server.
Using a dedicated server is not being trapped in the past.
It is choosing dedicated resources when the requirements justify them.
Apache does not stop working because it lacks a venture-backed origin story.
Control panels do not become useless because somebody prefers managing everything through configuration repositories.
Traditional hosting is not obsolete because the cloud industry has better marketing.
These tools and infrastructure models still exist because they continue to solve real problems.
The useful question is not whether a stack looks modern.
The useful questions are much less exciting:
- Does it meet the project’s requirements?
- Is it reliable enough for the actual use case?
- Can the people responsible for it understand and maintain it?
- Is the cost reasonable?
- Can the project be moved if necessary?
- What external services does it depend on?
- What happens when the provider changes its prices or policies?
- What happens when the provider goes down?
- Does each additional layer solve a real problem?
- Are we building for actual users or hypothetical millions?
If the answers lead to AWS, Azure, Google Cloud, Kubernetes, or serverless infrastructure, fine.
Use them.
But make them win the argument first.
Do not hand them the project because developer culture has decided that renting a normal server is embarrassing.
The internet needs more than three landlords
The internet is not completely centralized. No single company controls all of it, and there are still many hosting providers, network operators, data centers, independent services, and infrastructure companies.
But too much critical infrastructure is moving into too few hands.
That deserves more concern than it currently gets.
When the same small group of companies increasingly provides compute, storage, networking, DNS, identity, content delivery, databases, AI services, and application platforms, developers become dependent on more than technology.
They become dependent on pricing decisions.
Policy decisions.
Account decisions.
Product roadmaps.
Geopolitical decisions.
Corporate priorities.
Terms of service.
The continued willingness of a giant company to provide a product under conditions the customer can accept.
A diverse hosting ecosystem provides alternatives.
Small hosting companies matter.
Independent VPS providers matter.
Dedicated server providers matter.
Traditional shared hosting businesses matter.
Different providers using different networks and infrastructure matter.
Not every hosting company needs to become a miniature hyperscaler. In fact, I would prefer that they didn’t.
The internet is healthier when developers have real choices, including simple ones.
I don’t hate the cloud. I hate inevitability.
I am not trying to recreate the internet of 2003.
I do not think old technology is automatically better. I do not think new technology is automatically pointless. I do not believe every developer should manage physical servers or reject every managed service.
I am not even completely independent of large technology companies, and I have no interest in pretending otherwise.
I occasionally use Cloudflare because it is useful, while remaining uncomfortable with the degree of centralization it represents.
What I reject is the idea that the giant cloud ecosystem is inevitable.
I reject the assumption that serious infrastructure must belong to AWS, Azure, Google Cloud, or another hyperscale platform.
I reject the idea that complexity is proof of engineering maturity.
I reject the idea that a project should surrender portability and control before it has a reason to do so.
For more than 20 years, I have used traditional shared hosting for smaller websites and VPSs or dedicated servers for larger projects, based on actual requirements.
I have hosted websites, blogs, company presentation sites, and similar projects.
I have never used AWS or a similar hyperscale cloud platform for my projects.
That approach has saved me time and money.
It will not be right for every project. It does not need to be.
It only needs to prove one thing:
The giant cloud is an option, not a law of nature.
Sometimes the boring solution is the one you can understand, afford, maintain, and move.
Sometimes a website is just a website.
And sometimes the healthiest thing we can do for the internet is stop giving the same handful of companies every single piece of it.
Before opening another cloud account, ask one uncomfortable question:
What problem am I actually paying this giant company to solve?
You may have a very good answer.
You may also realize that what you really need is a server.
Sources
- Summary of the AWS Service Event in the Northern Virginia (US-EAST-1) Region, December 7, 2021
- Post Incident Review: Azure Networking Global WAN Issues, January 25, 2023
- Google Cloud Incident Report: Multiple Google Cloud Products, June 12, 2025
- Cloudflare Service Outage, June 12, 2025 ([blog.cloudflare.com]
- Cloudflare Outage, November 18, 2025
- Author's Website
Top comments (0)