Try it free

Best practices for data partitioning

  • Latest Dynatrace
  • Best practices
  • Published Aug 24, 2026

Buckets are logical storage units that hold records behind Dynatrace tables. Users query data through tables such as logs, spans, or events, while buckets store and manage the underlying data in the background. Each bucket is associated with a specific data type; logs and spans must reside in separate buckets. A well-designed bucket strategy improves query performance, reduces DPS consumption, and supports compliance-driven retention requirements. These best practices walk you through sizing and designing that strategy.

Calculate total and per-application signal volume first

Before designing a bucket strategy, calculate your actual ingest volume. The default bucket limit per environment is 80 buckets, which is typically sufficient for up to 5 TB/day per table. If total daily volume is below 5 TB/day per table and no application has compliance-driven retention requirements, default buckets may be sufficient.

To calculate volume

  1. Use the Data Partitioning Helper notebook in your Dynatrace environment.
  2. Run the total logs and spans volume queries to get average daily ingest for each signal type.
  3. Run the per-application volume breakdown to identify which applications drive the most traffic.

The per-application breakdown reveals imbalances, for example, one critical application ingesting 700 GB/day while all others contribute minimal volume. Identifying these imbalances lets you isolate high-volume applications in dedicated buckets, improving query performance for all other teams.

Create dedicated buckets for apps exceeding 250 GB/day

Create a dedicated bucket for any application ingesting more than 250 GB/day. This threshold exists because Dynatrace applies default query limits of 500 GB scanned per query. At 250 GB/day ingest, a user can query approximately 48 hours of data before hitting the scan limit, a comfortable range that leaves room for growth.

The following table shows how ingest volume affects the queryable time range before hitting the 500 GB scan limit:

Ingest per dayDQL queryable window without hitting the limit

20 TB/day

~35 minutes

10 TB/day

~1.2 hours

1 TB/day

~12 hours

250 GB/day

~48 hours

Applications below 250 GB/day can share a bucket without degrading query experience. Applications above this threshold benefit from isolation in their own bucket.

Scan limits can be adjusted on a per-query basis, but increasing them raises both query runtime and DPS cost. Use dedicated buckets for high-volume applications instead of raising limits.

Separate buckets for compliance retention requirements

Create dedicated buckets for any application or data type with specific retention requirements that differ from your default policy. For example, if PCI DSS requires 12-month retention for all payment service spans, create a dedicated bucket with a 12-month retention period for that application, even if its ingest volume is below the 250 GB/day threshold.

To incorporate retention requirements into your bucket design

  1. Identify all applications or data types with specific retention mandates.
  2. Document the required retention period for each.
  3. Create a separate bucket for each distinct retention requirement.
  4. Route signals with that requirement to the appropriate bucket using an OpenPipeline storage processor.

Use a clear naming convention that encodes the application and retention period, for example, credit-card-order-service_spans_360 for 12-month span retention.

Use dt.security_context for routing

Configure OpenPipeline storage processors to route signals to the correct bucket based on dt.security_context or another enrichment attribute. Routing by dt.security_context aligns bucket routing with IAM access control, ensuring that the same field used for permissions also governs where data is stored.

To configure routing

  1. Create the target bucket in Settings > Storage Management with the appropriate retention period.
  2. Open the OpenPipeline configuration for the relevant signal type (logs or spans).
  3. Add a storage processor that matches on dt.security_context (or the equivalent routing attribute) and routes matching signals to the new bucket.
  4. Enable the routing processor and confirm that the routing order is correct; processors are evaluated in sequence, so place more specific rules before broader catch-all rules.

Enrichment gaps block routing. If dt.security_context or the routing attribute is missing from signals, the storage processor cannot match them and the signals fall through to the default bucket. Resolve enrichment gaps before configuring bucket routing.

Validate traffic routing after configuration

After enabling OpenPipeline routing processors, confirm that signals are landing in the correct buckets.

To validate routing

  1. Run the per-bucket volume query in the Data Partitioning Helper notebook to see signal distribution across buckets.
  2. Confirm that the percentage of traffic routed to non-default buckets matches the expected routing plan.
  3. Run representative DQL queries scoped to each bucket and compare response times against the pre-partitioning baseline.
  4. Confirm that retention policies are applied correctly to compliance-sensitive buckets.

If signals are not routing as expected, check the OpenPipeline processor order and confirm that the enrichment attributes used in routing rules are present on the signals being ingested.

Ready for more?

Explore the other best practice for this stage, or return to Partition your Grail data to continue your upgrade.

  • Best practices for a logs bucket strategy
Related tags
Dynatrace Platform