Chapters

4 Deployment Models and Virtualization

cloud-computing
cloud
computing
deployment

4.1 Start With What a Deployment Model Actually Decides

The previous chapter’s responsibility bracket answered “who runs which layer of the stack” — infrastructure, platform, or application. This chapter answers a different question sitting underneath it: whose hardware is it, and who else is allowed on it? That is what a deployment model decides. It is not a service model — a single IaaS server can run on public, private, hybrid, or community infrastructure, and the deployment model is a separate axis you choose independently, exactly as the origins chapter’s NIST three-pillar model kept essential characteristics, service models, and deployment models apart. This chapter builds that third pillar in full, then drops one level lower again, to the virtualization mechanism that makes any of these models physically possible.

A useful plain-language anchor before the taxonomy starts: Oxford Dictionaries defines the cloud itself as “a network of remote servers hosted on the Internet and used to store, manage, and process data in place of local servers or personal computers.” For an IoT system specifically, that network is not optional infrastructure sitting off to one side — it is where device management and configuration happen, where data aggregation, processing, storage, and analysis/visualization happen, and where service customization and infrastructure sharing happen. Every deployment-model choice below is a choice about who owns, and who else shares, the servers doing that work.

Not the same question as the sibling chapter: Cloud Deployment Models for IoT asks "which deployment model should this IoT workload use, backed by what governance record?" This chapter asks the question underneath that one: "what is a public cloud, a private cloud, on-premise versus off-premise, and a hypervisor versus a container, mechanically, before any IoT placement decision gets made?"

4.2 The Four NIST Deployment Models

NIST defines four deployment models: public, private, community, and hybrid. Together they describe who may use the cloud infrastructure and how distinct cloud environments are composed. Distributed cloud, multi-cloud, and inter-cloud are useful architecture or operating patterns, but they are not additional members of this NIST pillar.

Public Cloud

A cloud set-up for the use of any person or industry, typically owned by the organization that offers the service.

Private Cloud

A cloud set-up functioning only for a single organization, typically managed either by that organization itself (on-premises) or by a third party (off-premises).

Community Cloud

A shared set-up for several organizations with common concerns -- such as security, compliance, or jurisdiction -- managed by one or more members, a third party, or both.

Hybrid Cloud

Two or more distinct private, community, or public cloud infrastructures joined by technology that supports data and application portability.

Public cloud is what most people picture first: Amazon Web Services, Google Compute Engine, and Microsoft Azure are the source material's own named examples. Its advantages follow directly from being shared, provider-owned infrastructure -- it is easy to set up at low cost because the provider covers the hardware, application, and bandwidth costs; it scales to meet demand; and pay-per-use ensures that, from the user's perspective, no paid-for resources sit idle.

Private cloud trades that shared-cost advantage for exclusivity: the set-up serves a single organization only, whether that organization manages it itself or a third party manages it on the organization's behalf. The advantages are total control over the system and data, and correspondingly fewer security concerns to negotiate with a shared tenant base. The named disadvantage is the mirror image of public cloud's low up-front cost: regular maintenance is the organization's own burden, not something absorbed into a shared bill.

Trait
Public Cloud
Private Cloud
Virtualized resources
Publicly shared
Privately shared
Customer types
Multiple
Limited
Connectivity
Over the internet
Over the internet or a private network
Security
Low
High

Community cloud is the fourth model, not an "other." It serves a defined group of organizations that share governance requirements, while remaining distinct from a private cloud serving only one organization. Hybrid cloud is also a NIST deployment model in its own right: it composes two or more distinct private, community, or public cloud infrastructures through technology that supports data and application portability, such as controlled load movement between them.

4.2.1 Architecture and operating patterns beyond the NIST taxonomy

Three related patterns answer a different question: how an organization distributes workloads across locations or coordinates more than one cloud service. Keep them alongside the deployment models for design work, but do not count them as extra NIST deployment models.

Distributed Cloud

Cloud services or resources are placed across multiple physical locations while governance and operation remain coordinated. Public-resource computing and volunteer cloud are two possible distributed arrangements.

Multi-Cloud

An organization deliberately uses services from more than one cloud provider or cloud environment, often to improve flexibility, resilience, or negotiating control.

Inter-Cloud

Separate clouds interoperate or federate so that services, data, or capacity can cross provider boundaries under agreed technical and governance rules.

4.3 Comparing and Choosing: On-Premise, Off-Premise, Dedicated, and Shared

  1. Cloud Clara places a pump shutoff beside the pump while a broken wide-area link cannot block it.

    Keep the fast shutoff close to the pump.

  2. Clara routes long records to private storage and large batch review to public cloud services.

    Place long records and large reviews where they fit.

  3. Clara tests ordered signed events outward and bounded versioned policy inward, with no direct remote override.

    Test the signed handoff without giving remote control free rein.

CP-0060 decision strip: Deployment model choice becomes concrete when a fast control deadline and a long historical workload share one system.

Deployment model choice becomes concrete when a fast control deadline and a long historical workload share one system. Figure 4.1 places a city-pump interlock, fleet records, elastic analytics, and the hybrid evidence hand-off.

Four-stage cloud placement diagram: a 20-millisecond edge or private interlock, private-cloud identity and regulated records, public-cloud elastic storage and analytics, and asynchronous signed events with versioned policy returned through a hybrid boundary.
Figure 4.1: A pump fleet separates local private control, private-cloud records, public-cloud analytics, and a signed hybrid evidence path.

In Figure 4.1, Edge / private control owns the 20 ms shut-off and survives WAN loss. Public cloud buys elastic storage, batch analytics, and managed queues, while Hybrid evidence path uploads sequenced signed events and returns versioned policy rather than granting an unbounded cloud override.

The public-versus-private comparison above already hints at the real trade-off underneath every deployment decision: security and control on one side, cost and scale on the other. A second, complementary view makes the same four core models easier to place side by side, by crossing two independent questions -- is the infrastructure on the organization's own premises or hosted elsewhere, and is access dedicated to one tenant or shared across several?

On-Premise
Off-Premise
Dedicated Access
Private cloud
Hosted private cloud
Shared Access
Community cloud
Public cloud

Reading that matrix column by column resolves a distinction the plain private-versus-public framing tends to blur: "private" is not a synonym for "on-premises." A private cloud can be hosted off-premises by a third party and still be dedicated to a single organization -- the defining trait of a private cloud is dedicated access, not physical location. Community cloud occupies the position most people would otherwise expect private cloud to sit in: on-premises, but shared across a defined group rather than dedicated to one tenant. Public cloud is the only combination that is both off-premises and shared, which is exactly why it earns the lowest security rating and the lowest per-unit cost in the comparison table above -- more tenants sharing more distant infrastructure is the same trade-off expressed two different ways.

Put together, the practical decision route is: name whether the workload needs dedicated infrastructure (regulatory, latency, or control reasons) or can tolerate shared infrastructure; then name whether an organization is willing to operate that infrastructure itself or would rather have it hosted. Those two answers, independently, land on one of the four cells above -- hybrid and multi-cloud arrangements are simply combinations of more than one cell at once, which is why they were introduced as compositions rather than as a fifth and sixth cell of their own.

4.4 Under the Hood: Virtual Machines, Containers, and a Worked Docker Example

Every deployment model above describes an ownership and sharing arrangement -- it says nothing yet about the mechanism that lets one physical server safely host more than one tenant's workload at once. That mechanism is virtualization: it is what enables clouds to run separate workloads under strict resource partitioning, letting CPU and memory be used optimally while still giving each workload security guarantees against the others sharing the same hardware.

Two approaches deliver that partitioning, and they trade off in opposite directions:

Virtual Machines

Multiple instances of potentially different operating systems running on the same physical machine -- the mechanism underneath Infrastructure-as-a-Service. Each instance carries its own full guest OS.

Containers

Different applications running on a virtualized OS within partitions -- the mechanism underneath Platform-as-a-Service. Execution stays safe to the kernel even if an application inside a container has security issues.

The diagram behind that pair of cards makes the structural difference concrete. On the virtual-machine side, each application sits on its own binaries/libraries, on its own full guest operating system, and all of those guest OS instances sit on a hypervisor, which itself sits on the host OS and the physical server. On the container side, each application sits on its own (or shared, where appropriate) binaries/libraries, but the containers sit directly on the host OS -- there is no per-container guest OS and no hypervisor layer at all. Containers are isolated from each other, but they share the host OS, and share binaries/libraries wherever that sharing is safe to do.

Removing the guest-OS-per-instance and hypervisor layers is what produces the container approach's named advantages: containers are fast to instantiate, can be destroyed as needed, need no hypervisor, can share OS libraries across instances, and are easy to scale. Every one of those five advantages is a direct consequence of the same structural fact -- there is simply less machinery to start, stop, and duplicate per instance than a virtual machine requires.

A worked example, read rather than run. Walk through the following the way you would read someone else's terminal session, not as an install-and-follow-along lab -- the point here is to see the container model operate end to end, not to stand up a working Docker environment. It is adapted from the classic "Get Started" walkthrough at docs.docker.com (the source material's own tutorial pinned Python 2.7, a version long past its end of life; a version-neutral base image is used below instead, and every other instruction is transcribed as taught).

A Dockerfile is a plain-text recipe for an image -- it names a starting point and a sequence of build steps:

# Use a Python runtime as the parent image
FROM python:slim
# Set the working directory to /app
WORKDIR /app
# Copy the current directory contents into the container at /app
ADD . /app
# Install any needed packages specified in requirements.txt
RUN pip install --trusted-host pypi.python.org -r requirements.txt
# Make port 80 available to the world outside this container
EXPOSE 80
# Define an environment variable
ENV NAME World
# Run app.py when the container launches
CMD ["python", "app.py"]

Reading it top to bottom: start from a Python base image; make `/app` the working directory; copy the current directory's contents into that `/app` folder inside the image; install whatever packages `requirements.txt` lists; declare that the container will listen on port 80; set one environment variable; and finally, name the command that runs when a container starts from this image. `app.py` itself, in the source's own walkthrough, does one thing -- it listens for connections on port 80 and returns an HTML page.

Building an image from that Dockerfile and giving it a name, then running a container from it, is two commands:

docker build -t docker-file .
docker run -p 4000:80 docker-file

The first command builds the image and tags it `docker-file` (the name the source's own walkthrough uses for the `docker run` step). The second command starts a container from that image: `-p 4000:80` maps port 80 inside the container -- the port `EXPOSE 80` declared -- to port 4000 on the host machine, which is why a browser on the host would reach the running application at port 4000, not port 80. That single `-p` flag is the entire bridge between "a process listening inside an isolated container" and "a service reachable from outside it."

4.5 Lab: Constrained IoT Ingestion Container

This lab turns the VM/container comparison into evidence. Build a minimal HTTP ingestion process, bind it only to localhost, cap CPU and memory, record the image digest and build provenance, and force both a bad-input failure and a process restart. The container boundary reduces packaging variation; it does not provide a separate kernel or remove the need to secure the host.

Create server.py:

import json
from http.server import BaseHTTPRequestHandler, HTTPServer

class Handler(BaseHTTPRequestHandler):
    def do_POST(self):
        try:
            length = int(self.headers.get("content-length", "0"))
            event = json.loads(self.rfile.read(length))
            assert isinstance(event.get("device"), str)
            assert isinstance(event.get("value"), (int, float))
            print(json.dumps({"accepted": event}, sort_keys=True), flush=True)
            self.send_response(202)
        except (ValueError, AssertionError, json.JSONDecodeError) as error:
            print(json.dumps({"rejected": type(error).__name__}), flush=True)
            self.send_response(400)
        self.end_headers()

HTTPServer(("0.0.0.0", 8080), Handler).serve_forever()

Create Dockerfile:

FROM python:3.13-alpine
WORKDIR /app
COPY server.py .
USER 65532:65532
EXPOSE 8080
CMD ["python", "server.py"]

Build and run it from a disposable lab directory:

docker buildx build --load --provenance=mode=max --sbom=true -t iot-ingest:defa .
docker image inspect iot-ingest:defa --format '{{.Id}}'
docker run --name iot-ingest-defa --detach \
  --publish 127.0.0.1:8080:8080 \
  --memory 128m --cpus 0.5 --pids-limit 64 \
  --read-only --tmpfs /tmp:rw,noexec,nosuid,size=16m \
  --restart on-failure:3 iot-ingest:defa
curl -i -X POST http://127.0.0.1:8080 -d '{"device":"lab-7","value":21.4}'
curl -i -X POST http://127.0.0.1:8080 -d '{"device":7,"value":"bad"}'
docker stats --no-stream iot-ingest-defa
docker logs --timestamps iot-ingest-defa

Record the Docker/Buildx versions, Dockerfile checksum, image digest, provenance/SBOM location, published interface and port, resource limits, accepted and rejected request status, log timestamps, restart count, and cleanup. Stop and remove only the named lab container when finished: docker rm --force iot-ingest-defa.

Failure Evidence Is Required

Repeat with malformed JSON, with port 8080 already occupied, and with the process killed inside the container. A useful record distinguishes application rejection, host-port allocation failure, resource exhaustion, process restart, and host failure. Do not treat docker ps as proof that ingestion, isolation, or recovery works.

4.6 Summary

A deployment model answers a question a service model does not: whose infrastructure is it, and who is allowed to use it? NIST’s four models are public, private, community, and hybrid. Distributed cloud, multi-cloud, and inter-cloud instead describe placement, coordination, or federation patterns that may be used with those models. The on-premise/off-premise by dedicated/shared-access matrix resolves the common confusion that “private” means “on-premises” — it does not; dedicated access is the defining trait of private cloud, regardless of who hosts it. Underneath any deployment model, virtualization is the mechanism that lets one physical server safely partition workloads: virtual machines give each workload a full guest OS on a shared hypervisor, while containers skip both layers and run directly on the shared host OS, which is why containers are faster to instantiate, destroy, and scale. A worked Dockerfile — build steps, a base image, an exposed port, and a run command with a port mapping — shows that mechanism operating end to end.

4.7 Key Takeaway

“Private” describes who has access, not where the server sits — and “container” is not a smaller virtual machine, it is a different mechanism that removes the guest-OS-per-instance and hypervisor layers entirely. Before naming a deployment model or a virtualization approach, name the actual trade-off it makes: ownership versus sharing, and how much machinery runs per isolated instance.

4.8 See Also

Service Models: IaaS, PaaS, and SaaS

The previous chapter in this module: the responsibility bracket this chapter's deployment-model taxonomy sits alongside as a separate, independent axis.

Service Management, SLAs, and Economics

The next chapter in this module: once a deployment model and a virtualization approach are chosen, this is how the resulting service gets managed, billed, and paid for.

Cloud Deployment Models for IoT

The applied companion chapter: turns this chapter's deployment-model taxonomy into an IoT placement decision with a governance record.