import * as plugins from './smartclickhouse.plugins.js'; import type { SmartClickHouseDb } from './smartclickhouse.classes.smartclickhouse.js'; import { ClickhouseTable } from './smartclickhouse.classes.clickhousetable.js'; /** * Creates a pre-configured ClickhouseTable for time-series data. * This is the backward-compatible equivalent of the old TimeDataTable class. * * The table uses MergeTree engine, orders by timestamp, and has auto-schema evolution enabled. */ export async function createTimeDataTable( db: SmartClickHouseDb, tableName: string, retainDataForDays: number = 30, ): Promise { const table = new TimeDataTable(db, tableName, retainDataForDays); await table.setup(); return table; } /** * TimeDataTable — a ClickhouseTable pre-configured for time-series data. * Provides backward-compatible convenience methods (addData, getLastEntries, etc.). */ export class TimeDataTable extends ClickhouseTable { /** * Static factory for backward compatibility */ public static async getTable( smartClickHouseDbRefArg: SmartClickHouseDb, tableNameArg: string, retainDataForDays: number = 30, ): Promise { return createTimeDataTable(smartClickHouseDbRefArg, tableNameArg, retainDataForDays); } constructor(db: SmartClickHouseDb, tableName: string, retainDataForDays: number = 30) { super(db, { tableName, engine: { engine: 'MergeTree' }, orderBy: 'timestamp' as any, retainDataForDays, autoSchemaEvolution: true, }); } /** * Insert data with auto-schema evolution and object flattening. * Backward-compatible: accepts arbitrary JSON objects with a timestamp field. */ public async addData(dataArg: any): Promise { if (!dataArg.timestamp || typeof dataArg.timestamp !== 'number') { throw new Error('timestamp must be of type number'); } return this.insert(dataArg); } /** * Get the last N entries ordered by timestamp DESC */ public async getLastEntries(count: number): Promise { return this.query() .orderBy('timestamp' as any, 'DESC') .limit(count) .toArray(); } /** * Get entries newer than a unix timestamp (in milliseconds) */ public async getEntriesNewerThan(unixTimestamp: number): Promise { return this.db.clickhouseHttpClient.queryPromise(` SELECT * FROM ${this.options.database}.${this.options.tableName} WHERE timestamp > toDateTime(${unixTimestamp / 1000}) FORMAT JSONEachRow `); } /** * Get entries between two unix timestamps (in milliseconds) */ public async getEntriesBetween(unixTimestampStart: number, unixTimestampEnd: number): Promise { return this.db.clickhouseHttpClient.queryPromise(` SELECT * FROM ${this.options.database}.${this.options.tableName} WHERE timestamp > toDateTime(${unixTimestampStart / 1000}) AND timestamp < toDateTime(${unixTimestampEnd / 1000}) FORMAT JSONEachRow `); } /** * Delete entries older than N days */ public async deleteOldEntries(days: number): Promise { await this.db.clickhouseHttpClient.mutatePromise(` ALTER TABLE ${this.options.database}.${this.options.tableName} DELETE WHERE timestamp < now() - INTERVAL ${days} DAY `); await this.waitForMutations(); } /** * Drop the table (backward-compatible alias for drop()) */ public async delete(): Promise { return this.drop(); } /** * Watch for new entries via polling (backward-compatible wrapper) */ public watchNewEntries(): plugins.smartrx.rxjs.Observable { return this.watch(); } }