1. Docs
  2. Pulumi IaC
  3. Clouds
  4. Kubernetes
  5. Guides
  6. Infra services

Kubernetes infrastructure services

    AWS has a catalog of managed infrastructure services that support and complement Kubernetes clusters and their workloads.

    At a minimum, networking must be configured for deployment of an EKS cluster.

    AWS exposes a Virtual Private Cloud API which can be used to create resources into a virtual network. With the VPC you can define the region’s Availability Zones to use, alongwith Route Tables, Subnets, Internet Gateways, NAT Gateways and Security Groups.

    The full code for this stack is on GitHub.

    Azure has a catalog of managed infrastructure services that support and complement Kubernetes clusters and their workloads.

    At a minimum, networking must be configured for deployment of an AKS cluster.

    AWS exposes a Virtual Network API which can be used to create resources into a virtual network. With the VPC you can define use, alongwith Route Tables, Subnets, Security Groups and VPN Gateways.

    The full code for this stack is on GitHub.

    Google Cloud has a catalog of managed infrastructure services that support and complement Kubernetes clusters and their workloads.

    At a minimum, networking must be configured for deployment of an EKS cluster.

    Google Cloud exposes a Virtual Private Cloud API which can be used to create resources into a virtual network. With the VPC you can define the region to use, alongwith Routes, Subnets, Forwarding Rules, and Firewall Rules.

    The full code for this stack is on GitHub.

    Overview

    We’ll configure and deploy:

    • Networking: To provide a virtual network for the cluster.
    • Storage: To provide data stores for the cluster.

    Networking

    In Crosswalk for AWS we showcase how to define networking:

    Create a New VPC for Kubernetes

    Create a new VPC to use with the cluster with custom settings and best-practice defaults.

    import * as awsx from "@pulumi/awsx";
    
    // Create a new VPC with custom settings.
    const vpcName = "eksVpc";
    const vpc = new awsx.ec2.Vpc(vpcName, {
        cidrBlock: "172.16.0.0/16",
        numberOfAvailabilityZones: "all",
        tags: { "Name": vpcName },
    });
    
    // Export the VPC resource IDs.
    export const vpcId = vpc.id;
    export const publicSubnetIds = vpc.publicSubnetIds;
    export const privateSubnetIds = vpc.privateSubnetIds;
    

    Create a New Virtual Network for Kubernetes

    Create a new Virtual Network to use with the cluster with custom settings and best-practice defaults.

    // Create a Virtual Network for the cluster.
    const vnet = new azure.network.VirtualNetwork(name, {
        resourceGroupName: config.resourceGroupName,
        addressSpaces: ["10.2.0.0/16"],
    });
    
    // Create a Subnet for the cluster.
    const subnet = new azure.network.Subnet(name, {
        resourceGroupName: config.resourceGroupName,
        virtualNetworkName: vnet.name,
        addressPrefix: "10.2.1.0/24",
    });
    

    Create a New VPC for Kubernetes

    Create a new network to use with the cluster with custom settings and best-practice defaults.

    import * as gcp from "@pulumi/gcp";
    
    const network = new gcp.compute.Network(name, {
        project: config.project,
        autoCreateSubnetworks: false,
    });
    export const networkName = network.name;
    
    const subnet = new gcp.compute.Subnetwork(name, {
        project: config.project,
        region: pulumi.output(config.zone).apply(zone =>
            (<string>zone)
                .split("-")
                .slice(0, 2)
                .join("-"),
        ),
        ipCidrRange: "10.0.0.0/24",
        network: network.name,
        secondaryIpRanges: [{ rangeName: "pods", ipCidrRange: "10.1.0.0/16" }],
    });
    export const subnetworkName = subnet.name;
    

    Use the Default VPC with Kubernetes

    Use the account’s default VPC.

    import * as awsx from "@pulumi/awsx";
    
    // Use the default VPC.
    const defaultVpc = awsx.ec2.Vpc.getDefault();
    
    // Export the VPC resource IDs.
    export const defaultVpcId = defaultVpc.id;
    export const defaultPublicSubnetIds = defaultVpc.publicSubnetIds;
    export const defaultPrivateSubnetIds = defaultVpc.privateSubnetIds;
    

    Use an Existing VPC with Kubernetes

    To use an existing VPC, provide the IDs of the VPC and its resources.

    import * as awsx from "@pulumi/awsx";
    
    // Use an existing VPC, subnets, and gateways.
    const existingVpc = awsx.ec2.Vpc.fromExistingIds("existingVpc", {
        vpcId: "vpc-00000000000000000",
        publicSubnetIds: ["subnet-00000000000000000", "subnet-11111111111111111"],
        privateSubnetIds: ["subnet-22222222222222222", "subnet-33333333333333333"],
        internetGatewayId: "igw-00000000000000000",
        natGatewayIds: ["nat-00000000000000000", "nat-11111111111111111"],
    })
    
    // Export the VPC resource IDs.
    export const existingVpcId = existingVpc.id;
    export const existingPublicSubnetIds = existingVpc.publicSubnetIds;
    export const existingPrivateSubnetIds = existingVpc.privateSubnetIds;
    

    Requirements & Recommendations

    See the official docs EKS Network Requirements and AWS VPC Recommendations for more details.

    See the official Networking docs for more details.

    See the official Networking docs for more details.

    Storage

    Cloud storage persists data in many forms, from data warehouses to analytics, and is presented as object, file, block storage, and migration capabilities.

    Generally, the storage services in this stack tend to be foundational for teams, and is typically shared across clusters and orgs.

    In the managed clusters, the worker node groups by default will use block devices, and Kubernetes itself could manage PersistentVolumes.

    Often times, this layer may be conflated with storage services managed in stacks closer to the apps, such as the Kubernetes Cluster Services or App Services. Those higher layers tend to primarily focus on the direct needs of a given Kubernetes cluster and its apps, rather than the needs of your complete architecture.

    Amazon Simple Storage Service (S3)

    See Crosswalk AWS S3 and the AWS S3 docs for more details.

    Elastic Container Registry (ECR)

    See Crosswalk AWS ECR and the AWS ECR docs for more details.

    Amazon Elastic File System (EFS)

    See Persisting Kubernetes Workloads with Amazon EFS and the AWS EFS docs for more details.

    Azure Blob Storage

    Create a new blob storage with a data source of a local directory and files.

    import * as azure from "@pulumi/azure";
    
    // Create an Azure Resource Group.
    const resourceGroup = new azure.core.ResourceGroup("website-rg", {
        location: azure.Locations.WestUS,
    });
    
    // Create a Storage Account.
    const storageAccount = new azure.storage.Account("websitesa", {
        resourceGroupName: resourceGroup.name,
        accountReplicationType: "LRS",
        accountTier: "Standard",
        accountKind: "StorageV2",
    });
    
    // Upload the following files from a local directory.
    ["index.html", "404.html"].map(name =>
        new azure.storage.Blob(name, {
            name,
            resourceGroupName: resourceGroup.name,
            storageAccountName: storageAccount.name,
            storageContainerName: "wwwroot",
            type: "block",
            source: `./wwwroot/${name}`,
            contentType: "text/html",
        }),
    );
    

    Azure Container Registry (ACR)

    Create a new registry, build a local Docker image, and push it to the registry.

    import * as azure from "@pulumi/azure";
    
    // Create an Azure Resource Group.
    const resourceGroup = new azure.core.ResourceGroup("rg", {
        location: "West US",
        name: "resourceGroup1",
    });
    
    // Create an ACR.
    const registry = new azure.containerservice.Registry("acr", {
        adminEnabled: false,
        georeplicationLocations: [
            "East US",
            "West Europe",
        ],
        location: resourceGroup.location,
        name: "containerRegistry1",
        resourceGroupName: resourceGroup.name,
        sku: "Premium",
    });
    
    // Build a local Docker image with a given Dockerfile context, and push it
    // to the registry.
    const customImage = "node-app";
    const appImage = new docker.Image(customImage, {
        imageName: pulumi.interpolate`${registry.loginServer}/${customImage}:v1.0.0`,
        build: {
            context: `./${customImage}`,
        },
        registry: {
            server: registry.loginServer,
            username: registry.adminUsername,
            password: registry.adminPassword,
        },
    });
    

    Google Container Registry (GCR)

    Fetch the URL to use for the Debian container image.

    import * as gcp from "@pulumi/gcp";
    
    const debian = gcp.container.getRegistryImage({
        name: "debian",
    });
    
    export const gcrLocation = debian.imageUrl;
    

    Fetch the project’s registry and display its GCR location.

    import * as gcp from "@pulumi/gcp";
    
    const registry = gcp.container.getRegistryRepository();
    export const gcrLocation = registry.repositoryUrl;
    

    Build a local Docker image with a given Dockerfile context, and push it to the registry.

    import * as docker from "@pulumi/docker";
    
    const customImage = "node-app";
    const appImage = new docker.Image(customImage, {
        imageName: pulumi.interpolate`${registry.repositoryUrl}/${customImage}:v1.0.0`,
        build: {
            context: `./${customImage}`,
        },
    });
    

    Google Cloud Object Storage

    Create a new bucket with a data source of a local file.

    import * as gcp from "@pulumi/gcp";
    
    const picture = new gcp.storage.BucketObject("picture", {
        bucket: "image-store",
        source: new pulumi.asset.FileAsset("/images/nature/garden-tiger-moth.jpg"),
    });
    
      PulumiUP 2024. Watch On Demand.