package com.easyagents.federation.sql.runtime;

import com.easyagents.federation.sql.federation.FederationTableStatistics;
import com.easyagents.federation.sql.source.SourceId;
import java.util.List;
import org.apache.calcite.plan.RelOptCluster;
import org.apache.calcite.plan.RelOptTable;
import org.apache.calcite.plan.RelTraitSet;
import org.apache.calcite.rel.RelNode;
import org.apache.calcite.rel.core.TableScan;
import org.apache.calcite.rel.hint.RelHint;
import org.apache.calcite.rel.metadata.RelMetadataQuery;

/**
 * 将调用方冻结统计中的表行数暴露给 Calcite 元数据查询。
 */
public final class FederationStatisticsTableScan extends TableScan {

    private final FederationTableStatistics statistics;
    private final SourceId sourceId;

    /**
     * 创建带稳定行数估算的逻辑表扫描。
     *
     * @param cluster 关系表达式集群
     * @param traitSet 关系特征
     * @param hints 扫描提示
     * @param table Calcite 表定义
     * @param statistics 冻结的表统计
     * @param sourceId 物理数据源标识
     */
    FederationStatisticsTableScan(
        RelOptCluster cluster,
        RelTraitSet traitSet,
        List<RelHint> hints,
        RelOptTable table,
        FederationTableStatistics statistics,
        SourceId sourceId
    ) {
        super(cluster, traitSet, hints, table);
        this.statistics = statistics;
        this.sourceId = sourceId;
    }

    /** {@inheritDoc} */
    @Override
    public double estimateRowCount(RelMetadataQuery metadataQuery) {
        return statistics.estimatedRows();
    }

    /**
     * 返回本次编译冻结的表统计。
     *
     * @return 表统计快照
     */
    FederationTableStatistics statistics() {
        return statistics;
    }

    /**
     * 返回物理数据源标识，用于限制跨源 Join 搜索范围。
     *
     * @return 物理数据源标识
     */
    SourceId sourceId() {
        return sourceId;
    }

    /** {@inheritDoc} */
    @Override
    public RelNode copy(RelTraitSet traitSet, List<RelNode> inputs) {
        if (!inputs.isEmpty()) {
            throw new IllegalArgumentException("table scan must not have inputs");
        }
        return new FederationStatisticsTableScan(
            getCluster(),
            traitSet,
            getHints(),
            table,
            statistics,
            sourceId
        );
    }
}
