content/influxdb3/clustered/admin/scale-cluster.md
InfluxDB Clustered lets you scale individual components of your cluster both
vertically and horizontally to match your specific workload.
Use the AppInstance resource defined in your influxdb.yml to manage
resources available to each component.
The following scaling strategies can be applied to components in your InfluxDB cluster.
Vertical scaling (also known as "scaling up") involves increasing the resources (such as RAM or CPU) available to a process or system. Vertical scaling is typically used to handle resource-intensive tasks that require more processing power.
{{< html-diagram/scaling-strategy "vertical" >}}
Horizontal scaling (also known as "scaling out") involves increasing the number of nodes or processes available to perform a given task. Horizontal scaling is typically used to increase the amount of workload or throughput a system can manage, but also provides additional redundancy and failover.
{{< html-diagram/scaling-strategy "horizontal" >}}
Scaling your entire InfluxDB Cluster is done by scaling your Kubernetes cluster and is managed outside of InfluxDB. The process of scaling your entire Kubernetes cluster depends on your underlying Kubernetes provider. You can also use Kubernetes autoscaling to automatically scale your cluster as needed.
The following components of your InfluxDB cluster are scaled by modifying
properties in your AppInstance resource:
[!Note]
Scale your Catalog and Object store
Your InfluxDB Catalog and Object store are managed outside of your
AppInstanceresource. Scaling mechanisms for these components depend on the technology and underlying provider used for each.
{{< tabs-wrapper >}} {{% tabs "small" %}} AppInstance Helm {{% /tabs %}}
{{% tab-content %}}
<!----------------------------- BEGIN APPINSTANCE ----------------------------->Use the spec.package.spec.resources property in your AppInstance resource
defined in your influxdb.yml to define system resource minimums and limits
for each pod and the number of replicas per component.
requests are the minimum that the Kubernetes scheduler should reserve for a pod.
limits are the maximum that a pod should be allowed to use.
Your AppInstance resource can include the following properties to define
resource minimums and limits per pod and replicas per component:
spec.package.spec.resources
ingester
requests
cpu: Minimum CPU resource units to assign to ingestersmemory: Minimum memory resource units to assign to ingestersreplicas: Number of ingester replicas to provisionlimits
cpu: Maximum CPU resource units to assign to ingestersmemory: Maximum memory resource units to assign to ingesterscompactor
requests
cpu: Minimum CPU resource units to assign to compactorsmemory: Minimum memory resource units to assign to compactorsreplicas: Number of compactor replicas to provisionlimits
cpu: Maximum CPU resource units to assign to compactorsmemory: Maximum memory resource units to assign to compactorsquerier
requests
cpu: Minimum CPU resource units to assign to queriersmemory: Minimum memory resource units to assign to queriersreplicas: Number of querier replicas to provisionlimits
cpu: Maximum CPU resource units to assign to queriersmemory: Maximum memory resource units to assign to queriersrouter
requests
cpu: Minimum CPU resource units to assign to routersmemory: Minimum memory resource units to assign to routersreplicas: Number of router replicas to provisionlimits
cpu: Maximum CPU Resource units to assign to routersmemory: Maximum memory resource units to assign to routersgarbage-collector
requests
cpu: Minimum CPU resource units to assign to the garbage collectormemory: Minimum memory resource units to assign to the garbage collectorlimits
cpu: Maximum CPU Resource units to assign to the garbage collectormemory: Maximum memory resource units to assign to the garbage collector{{< expand-wrapper >}}
{{% expand "View example AppInstance with resource requests and limits" %}}
{{% code-placeholders "(INGESTER|COMPACTOR|QUERIER|ROUTER|GC)(CPU(MAX|MIN)|MEMORY_(MAX|MIN)|REPLICAS)" %}}
apiVersion: kubecfg.dev/v1alpha1
kind: AppInstance
# ...
spec:
package:
spec:
# The following settings tune the various pods for their cpu/memory/replicas
# based on workload needs. Only uncomment the specific resources you want
# to change. Anything left commented will use the package default.
resources:
ingester:
requests:
cpu: INGESTER_CPU_MIN
memory: INGESTER_MEMORY_MIN
replicas: INGESTER_REPLICAS # Default is 3
limits:
cpu: INGESTER_CPU_MAX
memory: INGESTER_MEMORY_MAX
compactor:
requests:
cpu: COMPACTOR_CPU_MIN
memory: COMPACTOR_MEMORY_MIN
replicas: COMPACTOR_REPLICAS # Default is 1
limits:
cpu: COMPACTOR_CPU_MAX
memory: COMPACTOR_MEMORY_MAX
querier:
requests:
cpu: QUERIER_CPU_MIN
memory: QUERIER_MEMORY_MIN
replicas: QUERIER_REPLICAS # Default is 1
limits:
cpu: QUERIER_CPU_MAX
memory: QUERIER_MEMORY_MAX
router:
requests:
cpu: ROUTER_CPU_MIN
memory: ROUTER_MEMORY_MIN
replicas: ROUTER_REPLICAS # Default is 1
limits:
cpu: ROUTER_CPU_MAX
memory: ROUTER_MEMORY_MAX
garbage-collector:
requests:
cpu: GC_CPU_MIN
memory: GC_MEMORY_MIN
limits:
cpu: GC_CPU_MAX
memory: GC_MEMORY_MAX
{{% /code-placeholders %}}
{{% /expand %}} {{< /expand-wrapper >}}
<!------------------------------ END APPINSTANCE ------------------------------>{{% /tab-content %}} {{% tab-content %}}
<!--------------------------------- BEGIN HELM -------------------------------->Use the resources property in your values.yaml to define system resource
minimums and limits for each pod and the number of replicas per component.
requests are the minimum that the Kubernetes scheduler should reserve for a pod.
limits are the maximum that a pod should be allowed to use.
Use the following properties to define resource minimums and limits per pod and replicas per component:
resources
ingester
requests
cpu: Minimum CPU resource units to assign to ingestersmemory: Minimum memory resource units to assign to ingestersreplicas: Number of ingester replicas to provisionlimits
cpu: Maximum CPU resource units to assign to ingestersmemory: Maximum memory resource units to assign to ingesterscompactor
requests
cpu: Minimum CPU resource units to assign to compactorsmemory: Minimum memory resource units to assign to compactorsreplicas: Number of compactor replicas to provisionlimits
cpu: Maximum CPU resource units to assign to compactorsmemory: Maximum memory resource units to assign to compactorsquerier
requests
cpu: Minimum CPU resource units to assign to queriersmemory: Minimum memory resource units to assign to queriersreplicas: Number of querier replicas to provisionlimits
cpu: Maximum CPU resource units to assign to queriersmemory: Maximum memory resource units to assign to queriersrouter
requests
cpu: Minimum CPU resource units to assign to routersmemory: Minimum memory resource units to assign to routersreplicas: Number of router replicas to provisionlimits
cpu: Maximum CPU Resource units to assign to routersmemory: Maximum memory resource units to assign to routersgarbage-collector
requests
cpu: Minimum CPU resource units to assign to the garbage collectormemory: Minimum memory resource units to assign to the garbage collectorlimits
cpu: Maximum CPU Resource units to assign to the garbage collectormemory: Maximum memory resource units to assign to the garbage collector{{< expand-wrapper >}}
{{% expand "View example values.yaml with resource requests and limits" %}}
{{% code-placeholders "(INGESTER|COMPACTOR|QUERIER|ROUTER|GC)(CPU(MAX|MIN)|MEMORY_(MAX|MIN)|REPLICAS)" %}}
# ...
resources:
ingester:
requests:
cpu: INGESTER_CPU_MIN
memory: INGESTER_MEMORY_MIN
replicas: INGESTER_REPLICAS # Default is 3
limits:
cpu: INGESTER_CPU_MAX
memory: INGESTER_MEMORY_MAX
compactor:
requests:
cpu: COMPACTOR_CPU_MIN
memory: COMPACTOR_MEMORY_MIN
replicas: COMPACTOR_REPLICAS # Default is 1
limits:
cpu: COMPACTOR_CPU_MAX
memory: COMPACTOR_MEMORY_MAX
querier:
requests:
cpu: QUERIER_CPU_MIN
memory: QUERIER_MEMORY_MIN
replicas: QUERIER_REPLICAS # Default is 1
limits:
cpu: QUERIER_CPU_MAX
memory: QUERIER_MEMORY_MAX
router:
requests:
cpu: ROUTER_CPU_MIN
memory: ROUTER_MEMORY_MIN
replicas: ROUTER_REPLICAS # Default is 1
limits:
cpu: ROUTER_CPU_MAX
memory: ROUTER_MEMORY_MAX
garbage-collector:
requests:
cpu: GC_CPU_MIN
memory: GC_MEMORY_MIN
limits:
cpu: GC_CPU_MAX
memory: GC_MEMORY_MAX
{{% /code-placeholders %}}
{{% /expand %}} {{< /expand-wrapper >}}
<!---------------------------------- END HELM --------------------------------->{{% /tab-content %}} {{< /tabs-wrapper >}}
[!Note] Applying resource limits to pods is optional, but provides better resource isolation and protects against pods using more resources than intended. For information, see Kubernetes resource requests and limits.
To horizontally scale a component in your InfluxDB cluster, increase or decrease the number of replicas for the component and apply the change.
[!Warning]
Only use the AppInstance to scale component replicas
Only use the
AppInstanceresource to scale component replicas. Manually scaling replicas may cause errors.
For example--to horizontally scale your Ingester:
{{< code-tabs-wrapper >}} {{% code-tabs %}} AppInstance Helm {{% /code-tabs %}} {{% code-tab-content %}}
apiVersion: kubecfg.dev/v1alpha1
kind: AppInstance
# ...
spec:
package:
spec:
resources:
ingester:
requests:
# ...
replicas: 6
{{% /code-tab-content %}} {{% code-tab-content %}}
# ...
resources:
ingester:
requests:
# ...
replicas: 6
{{% /code-tab-content %}} {{< /code-tabs-wrapper >}}
To vertically scale a component in your InfluxDB cluster, increase or decrease the CPU and memory resource units to assign to component pods and apply the change.
{{< code-tabs-wrapper >}} {{% code-tabs %}} AppInstance Helm {{% /code-tabs %}} {{% code-tab-content %}}
apiVersion: kubecfg.dev/v1alpha1
kind: AppInstance
# ...
spec:
package:
spec:
resources:
ingester:
requests:
cpu: "500m"
memory: "512MiB"
# ...
limits:
cpu: "1000m"
memory: "1024MiB"
{{% /code-tab-content %}} {{% code-tab-content %}}
# ...
resources:
ingester:
requests:
cpu: "500m"
memory: "512MiB"
# ...
limits:
cpu: "1000m"
memory: "1024MiB"
{{% /code-tab-content %}} {{< /code-tabs-wrapper >}}
After modifying the AppInstance resource, use kubectl apply to apply the
configuration changes to your cluster and scale the updated components.
{{< code-tabs-wrapper >}} {{% code-tabs %}} AppInstance Helm {{% /code-tabs %}} {{% code-tab-content %}}
<!-- pytest.mark.skip -->kubectl apply \
--filename myinfluxdb.yml \
--namespace influxdb
{{% /code-tab-content %}} {{% code-tab-content %}}
<!-- pytest.mark.skip -->helm upgrade \
influxdata/influxdb3-clustered \
-f ./values.yml \
--namespace influxdb
{{% /code-tab-content %}} {{< /code-tabs-wrapper >}}
The Router can be scaled both vertically and horizontally.
Latency of the Router’s write endpoint is directly impacted by:
The Ingester can be scaled both vertically and horizontally.
Ingesters use an attached storage volume to store the Write-Ahead Log (WAL). With more storage available, Ingesters can keep bigger WAL buffers, which improves query performance and reduces pressure on the Compactor. Storage speed also helps with query performance.
Configure the storage volume attached to Ingester pods in the
spec.package.spec.ingesterStorage property of your AppInstance resource or,
if using Helm, the ingesterStorage property of your values.yaml.
{{< expand-wrapper >}} {{% expand "View example Ingester storage configuration" %}}
{{% code-placeholders "STORAGE_(CLASS|SIZE)" %}}
{{< code-tabs-wrapper >}} {{% code-tabs %}} AppInstance Helm {{% /code-tabs %}} {{% code-tab-content %}}
apiVersion: kubecfg.dev/v1alpha1
kind: AppInstance
# ...
spec:
package:
spec:
# ...
ingesterStorage:
# (Optional) Set the storage class. This will differ based on the K8s
#environment and desired storage characteristics.
# If not set, the default storage class is used.
storageClassName: STORAGE_CLASS
# Set the storage size (minimum 2Gi recommended)
storage: STORAGE_SIZE
{{% /code-tab-content %}} {{% code-tab-content %}}
# ...
ingesterStorage:
# (Optional) Set the storage class. This will differ based on the K8s
#environment and desired storage characteristics.
# If not set, the default storage class is used.
storageClassName: STORAGE_CLASS
# Set the storage size (minimum 2Gi recommended)
storage: STORAGE_SIZE
{{% /code-tab-content %}} {{< /code-tabs-wrapper >}}
{{% /code-placeholders %}}
{{% /expand %}} {{< /expand-wrapper >}}
The Querier can be scaled both vertically and horizontally.
[!Important] When scaling the Compactor, scale CPU and memory resources together.
The Garbage collector is a lightweight process that typically doesn't require significant system resources.
The Catalog store is a PostgreSQL-compatible database that stores critical metadata for your InfluxDB cluster. An underprovisioned Catalog store can cause write outages and system-wide performance issues.
The Catalog service (iox-shared-catalog statefulset) caches and manages access to the Catalog store.
[!Note]
Managing Catalog components
The Catalog service is managed through the
AppInstanceresource, while the Catalog store is managed separately according to your PostgreSQL implementation.
The Object store contains time series data in Parquet format.
Scaling strategies depend on the underlying object storage services used. Most services support horizontal scaling for redundancy, failover, and increased capacity.