cube-js/cube · error

Scheduled refresh is unsupported for ${preAggregation.preAgg

Error message

Scheduled refresh is unsupported for ${preAggregation.preAggregation.type} of ${preAggregation.preAggregationName}

What it means

baseQueryForPreAggregation only knows how to build refresh queries for 'originalSql' (and reference-bearing) pre-aggregations. For any other pre-aggregation type it cannot construct a base refresh query, so scheduled refresh throws this error naming the unsupported type and pre-aggregation.

Source

Thrown at packages/cubejs-server-core/src/core/RefreshScheduler.ts:223

      const dimensionsCount = Object.keys(cubeFromPath.dimensions || {}).length;
      if (measuresCount === 0 && dimensionsCount === 0) {
        throw new Error(
          `Can't refresh pre-aggregation without measures and dimensions: ${preAggregation.preAggregationName}`
        );
      }
      return {
        ...queryingOptions,
        ...(
          measuresCount &&
            { measures: [`${preAggregation.cube}.${Object.keys(cubeFromPath.measures)[0]}`] }
        ),
        ...(
          dimensionsCount &&
            { dimensions: [`${preAggregation.cube}.${Object.keys(cubeFromPath.dimensions)[0]}`] }
        )
      };
    } else {
      throw new Error(
        `Scheduled refresh is unsupported for ${preAggregation.preAggregation.type} of ${preAggregation.preAggregationName}`
      );
    }
  }

  /**
   * Evaluate and returns minimal QueryQueue concurrency value.
   */
  protected async getSchedulerConcurrency(
    core: CubejsServerCore,
    context: RequestContext,
  ): Promise<null | number> {
    const orchestratorApi = await core
      .getOrchestratorApi(context);
    const preaggsQueues = orchestratorApi.getQueryOrchestrator()
      .getPreAggregations()
      .getQueues();

View on GitHub (pinned to 7d981676b3)

Solutions

  1. Set the pre-aggregation type to a scheduler-supported one ('originalSql' or standard 'rollup')
  2. Provide explicit measures/dimensions/timeDimensions references so the pre-aggregation resolves to a supported form
  3. Exclude this pre-aggregation from scheduled refresh (adjust scheduledRefresh config / refreshStrategy) and refresh it on-demand instead
  4. Verify the type string for typos in the data model

Example fix

// before
preAggregations: {
  main: { type: 'rollupLambda' }
}
// after
preAggregations: {
  main: {
    type: 'rollup',
    measureReferences: [Events.count],
    timeDimensionReference: Events.createdAt,
    granularity: 'day'
  }
}
Defensive patterns

Strategy: validation

Validate before calling

const SCHEDULABLE_TYPES = ['originalSql', 'rollup'];
function assertSchedulable(pa) {
  if (!SCHEDULABLE_TYPES.includes(pa.type)) {
    throw new Error(`Exclude ${pa.preAggregationName} (${pa.type}) from scheduled refresh`);
  }
}

Type guard

const isSchedulablePreAgg = (pa: any): pa is { type: 'originalSql' | 'rollup' } =>
  pa?.type === 'originalSql' || pa?.type === 'rollup';

Try / catch

try {
  await scheduler.baseQuery(preAggregation);
} catch (e) {
  if (e.message.startsWith('Scheduled refresh is unsupported for')) {
    logger.warn(`Skipping scheduled refresh: ${e.message}`);
  } else { throw e; }
}

Prevention

When it happens

Trigger: The scheduled refresh scheduler walks pre-aggregations and hits one whose preAggregation.type is not handled by baseQueryForPreAggregation (not originalSql and without usable references), triggering the else-branch throw.

Common situations: Using custom/experimental pre-aggregation types (e.g. rollupLambda, custom member types) with scheduledRefresh enabled; a plugin or compiler extension introduces a new pre-aggregation type the scheduler doesn't recognize; typo in the type field of the pre-aggregation definition.

Related errors


AI-assisted analysis of cube-js/cube@7d981676b3 (2026-09-02). Data as JSON: /api/errors/391c29e60561a41e. Report an issue: GitHub.