/*
 * Licensed to the Apache Software Foundation (ASF) under one
 * or more contributor license agreements.  See the NOTICE file
 * distributed with this work for additional information
 * regarding copyright ownership.  The ASF licenses this file
 * to you under the Apache License, Version 2.0 (the
 * License); you may not use this file except in compliance
 * with the License.  You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing,
 * software distributed under the License is distributed on an
 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
 * KIND, either express or implied.  See the License for the
 * specific language governing permissions and limitations
 * under the License.
 */

#include "cwrapper/TsFile-cwrapper.h"

#include <iomanip>

#include "common/global.h"
#include "reader/expression.h"
#include "reader/filter/and_filter.h"
#include "reader/filter/filter.h"
#include "reader/filter/time_filter.h"
#include "reader/filter/time_operator.h"
#include "reader/result_set.h"
#include "reader/tsfile_reader.h"
#include "utils/errno_define.h"
#include "writer/tsfile_writer.h"

static bool is_init = false;

#define INSERT_DATA_INTO_RECORD(record, column, value)               \
    do {                                                             \
        DataPoint point(column, value);                              \
        if (record->points_.size() + 1 > record->points_.capacity()) \
            return E_BUF_NOT_ENOUGH;                                 \
        record->points_.push_back(point);                            \
        return E_OK;                                                 \
    } while (0)

#define CONSTRUCT_EXP_INTERNAL(exp, column_name) \
    do {                                         \
        exp.column_name = column_name;           \
        exp.operatype = oper;                    \
        exp.children_length = 0;                 \
    } while (0)

#define INSERT_DATA_TABLET_STEP                                             \
    do {                                                                    \
        for (int i = 0; i < tablet->column_num; i++) {                      \
            if (strcmp(tablet->column_schema[i]->name, column_name) == 0) { \
                column_id = i;                                              \
                break;                                                      \
            }                                                               \
        }                                                                   \
        if (column_id == -1) {                                              \
            return tablet;                                                  \
        }                                                                   \
        if (tablet->cur_num + 1 > tablet->max_capacity) {                   \
            return tablet;                                                  \
        }                                                                   \
        tablet->times[line_id] = timestamp;                                 \
    } while (0)
#define TSDataType common::TSDataType
#define TSEncoding common::TSEncoding
#define CompressionType common::CompressionType
#define TsFileReader storage::TsFileReader
#define TsFileWriter storage::TsFileWriter
#define E_OK common::E_OK
#define TsRecord storage::TsRecord
#define DataPoint storage::DataPoint
#define E_BUF_NOT_ENOUGH common::E_BUF_NOT_ENOUGH

TSDataType get_datatype(SchemaInfo schema_info) {
    if (schema_info & TS_TYPE_BOOLEAN) {
        return TSDataType::BOOLEAN;
    } else if (schema_info & TS_TYPE_DOUBLE) {
        return TSDataType::DOUBLE;
    } else if (schema_info & TS_TYPE_FLOAT) {
        return TSDataType::FLOAT;
    } else if (schema_info & TS_TYPE_INT32) {
        return TSDataType::INT32;
    } else if (schema_info & TS_TYPE_INT64) {
        return TSDataType::INT64;
    } else if (schema_info & TS_TYPE_TEXT) {
        return TSDataType::TEXT;
    }
    return TSDataType::INVALID_DATATYPE;
}

TSEncoding get_data_encoding(SchemaInfo schema_info) {
    if (schema_info & TS_ENCODING_PLAIN) {
        return TSEncoding::PLAIN;
    } else if (schema_info & TS_ENCODING_TS_DIFF) {
        return TSEncoding::DIFF;
    } else if (schema_info & TS_ENCODING_BITMAP) {
        return TSEncoding::BITMAP;
    } else if (schema_info & TS_ENCODING_GORILLA) {
        return TSEncoding::GORILLA;
    }
    return TSEncoding::PLAIN;
}

CompressionType get_data_compression(SchemaInfo schema_info) {
    if (schema_info & TS_COMPRESS_UNCOMPRESS) {
        return CompressionType::UNCOMPRESSED;
    } else if (schema_info & TS_COMPRESS_LZ4) {
        return CompressionType::LZ4;
    }
    return CompressionType::UNCOMPRESSED;
}

SchemaInfo get_schema_info(TSDataType type) {
    switch (type) {
        case TSDataType::BOOLEAN:
            return TS_TYPE_BOOLEAN;
        case TSDataType::DOUBLE:
            return TS_TYPE_DOUBLE;
        case TSDataType::FLOAT:
            return TS_TYPE_FLOAT;
        case TSDataType::INT32:
            return TS_TYPE_INT32;
        case TSDataType::INT64:
            return TS_TYPE_INT64;
        case TSDataType::TEXT:
            return TS_TYPE_TEXT;
        default:
            return 0;
    }
}

void init_tsfile_config() {
    if (!is_init) {
        common::init_config_value();
        is_init = true;
    }
}

CTsFileReader ts_reader_open(const char* pathname, ErrorCode* err_code) {
    init_tsfile_config();
    TsFileReader* reader = new TsFileReader();
    int ret = reader->open(pathname);
    if (ret != E_OK) {
        std::cout << "open file failed" << std::endl;
        *err_code = ret;
        delete reader;
        return nullptr;
    }
    return reader;
}

CTsFileWriter ts_writer_open(const char* pathname, ErrorCode* err_code) {
    init_tsfile_config();
    TsFileWriter* writer = new TsFileWriter();
    int flags = O_WRONLY | O_CREAT | O_TRUNC;
#ifdef _WIN32
    flags |= O_BINARY;
#endif
    int ret = writer->open(pathname, flags, 0644);
    if (ret != E_OK) {
        delete writer;
        *err_code = ret;
        return nullptr;
    }
    return writer;
}

CTsFileWriter ts_writer_open_flag(const char* pathname, mode_t flag,
                                  ErrorCode* err_code) {
    init_tsfile_config();
    TsFileWriter* writer = new TsFileWriter();
    int ret = writer->open(pathname, O_CREAT | O_RDWR, flag);
    if (ret != E_OK) {
        delete writer;
        *err_code = ret;
        return nullptr;
    }
    return writer;
}

CTsFileWriter ts_writer_open_conf(const char* pathname, int flag,
                                  ErrorCode* err_code, TsFileConf* conf) {
    *err_code = common::E_INVALID_ARG;
    return nullptr;
}

ErrorCode ts_writer_close(CTsFileWriter writer) {
    TsFileWriter* w = (TsFileWriter*)writer;
    int ret = w->close();
    delete w;
    return ret;
}

ErrorCode ts_reader_close(CTsFileReader reader) {
    TsFileReader* ts_reader = (TsFileReader*)reader;
    delete ts_reader;
    return E_OK;
}

ErrorCode tsfile_register_table_column(CTsFileWriter writer,
                                       const char* table_name,
                                       ColumnSchema* schema) {
    TsFileWriter* w = (TsFileWriter*)writer;

    int ret = w->register_timeseries(
        table_name, storage::MeasurementSchema(
                        schema->name, get_datatype(schema->column_def),
                        get_data_encoding(schema->column_def),
                        get_data_compression(schema->column_def)));
    return ret;
}

ErrorCode tsfile_register_table(CTsFileWriter writer,
                                TableSchema* table_schema) {
    TsFileWriter* w = (TsFileWriter*)writer;
    for (int column_id = 0; column_id < table_schema->column_num; column_id++) {
        ColumnSchema* schema = table_schema->column_schema[column_id];
        ErrorCode ret = w->register_timeseries(
            table_schema->table_name,
            storage::MeasurementSchema(
                schema->name, get_datatype(schema->column_def),
                get_data_encoding(schema->column_def),
                get_data_compression(schema->column_def)));
        if (ret != E_OK) {
            return ret;
        }
    }
    return E_OK;
}

TsFileRowData create_tsfile_row(const char* table_name, int64_t timestamp,
                                int column_length) {
    TsRecord* record = new TsRecord(timestamp, table_name, column_length);
    return record;
}

Tablet* create_tablet(const char* table_name, int max_capacity) {
    Tablet* tablet = new Tablet();
    tablet->table_name = strdup(table_name);
    tablet->max_capacity = max_capacity;
    tablet->times = (timestamp*)malloc(max_capacity * sizeof(int64_t));
    return tablet;
}

int get_size_from_schema_info(SchemaInfo schema_info) {
    if (schema_info & TS_TYPE_BOOLEAN) {
        return sizeof(bool);
    } else if (schema_info & TS_TYPE_DOUBLE) {
        return sizeof(double);
    } else if (schema_info & TS_TYPE_FLOAT) {
        return sizeof(float);
    } else if (schema_info & TS_TYPE_INT32) {
        return sizeof(int32_t);
    } else if (schema_info & TS_TYPE_INT64) {
        return sizeof(int64_t);
    } else if (schema_info & TS_TYPE_TEXT) {
        return sizeof(char*);
    }
    return 0;
}

Tablet* add_column_to_tablet(Tablet* tablet, char* column_name,
                             SchemaInfo column_def) {
    tablet->column_num++;
    tablet->column_schema = (ColumnSchema**)realloc(
        tablet->column_schema, tablet->column_num * sizeof(ColumnSchema*));
    tablet->bitmap =
        (bool**)realloc(tablet->bitmap, tablet->column_num * sizeof(bool*));
    tablet->bitmap[tablet->column_num - 1] =
        (bool*)malloc(tablet->max_capacity * sizeof(bool));
    std::memset(tablet->bitmap[tablet->column_num - 1], 0,
                tablet->max_capacity * sizeof(bool));
    ColumnSchema* schema = new ColumnSchema();
    schema->name = column_name;
    schema->column_def = column_def;
    tablet->column_schema[tablet->column_num - 1] = schema;
    tablet->value =
        (void**)realloc(tablet->value, tablet->column_num * sizeof(void*));
    tablet->value[tablet->column_num - 1] =
        (void*)malloc(tablet->max_capacity * sizeof(int64_t));
    return tablet;
}

Tablet* add_data_to_tablet_i64(Tablet* tablet, int line_id, int64_t timestamp,
                               const char* column_name, int64_t value) {
    int column_id = -1;
    INSERT_DATA_TABLET_STEP;
    memcpy((int64_t*)tablet->value[column_id] + line_id, &value,
           sizeof(int64_t));
    tablet->bitmap[column_id][line_id] = true;
    line_id > tablet->cur_num ? tablet->cur_num = line_id : 0;
    return tablet;
}

Tablet* add_data_to_tablet_i32(Tablet* tablet, int line_id, int64_t timestamp,
                               const char* column_name, int32_t value) {
    int column_id = -1;
    INSERT_DATA_TABLET_STEP;
    memcpy((int32_t*)tablet->value[column_id] + line_id, &value,
           sizeof(int32_t));
    tablet->bitmap[column_id][line_id] = true;
    line_id > tablet->cur_num ? tablet->cur_num = line_id : 0;
    return tablet;
}

Tablet* add_data_to_tablet_float(Tablet* tablet, int line_id, int64_t timestamp,
                                 const char* column_name, float value) {
    int column_id = -1;
    INSERT_DATA_TABLET_STEP;
    memcpy((float*)tablet->value[column_id] + line_id, &value, sizeof(float));
    tablet->bitmap[column_id][line_id] = true;
    line_id > tablet->cur_num ? tablet->cur_num = line_id : 0;
    return tablet;
}

Tablet* add_data_to_tablet_double(Tablet* tablet, int line_id,
                                  int64_t timestamp, const char* column_name,
                                  double value) {
    int column_id = -1;
    INSERT_DATA_TABLET_STEP;
    memcpy((double*)tablet->value[column_id] + line_id, &value, sizeof(double));
    tablet->bitmap[column_id][line_id] = true;
    line_id > tablet->cur_num ? tablet->cur_num = line_id : 0;
    return tablet;
}

Tablet* add_data_to_tablet_bool(Tablet* tablet, int line_id, int64_t timestamp,
                                const char* column_name, bool value) {
    int column_id = -1;
    INSERT_DATA_TABLET_STEP;
    memcpy((bool*)tablet->value[column_id] + line_id, &value, sizeof(bool));
    tablet->bitmap[column_id][line_id] = true;
    line_id > tablet->cur_num ? tablet->cur_num = line_id : 0;
    return tablet;
}

Tablet* add_data_to_tablet_char(Tablet* tablet, int line_id, int64_t timestamp,
                                const char* column_name, char* value) {
    int column_id = -1;
    INSERT_DATA_TABLET_STEP;
    memcpy((char*)tablet->value[column_id] + line_id, &value, sizeof(char*));
    tablet->bitmap[column_id][line_id] = true;
    line_id > tablet->cur_num ? tablet->cur_num = line_id : 0;
    return tablet;
}

// Tablet* add_null_to_tablet(Tablet* tablet, int line_id, int64_t timestamp,
// const char* column_num) {
//     int column_id = -1;
//     for (int i = 0; i < tablet->column_num; i++) {
//         if (strcmp(tablet->column_schema[i]->name, column_num) == 0) {
//             column_id = i;
//             break;
//         }
//     }
//     if (column_id == -1) {
//         return tablet;
//     }

//     if (tablet->cur_num + 1 > tablet->max_capacity) {
//         return tablet;
//     }
//     tablet->times[line_id] = timestamp;
//     memcpy((int64_t*)tablet->value[column_id] + line_id, 0, sizeof(int64_t));
//     line_id > tablet->cur_num ? tablet->cur_num = line_id : 0;
//     return tablet;
// }

ErrorCode destory_tablet(Tablet* tablet) {
    free(tablet->table_name);
    tablet->table_name = nullptr;
    free(tablet->times);
    tablet->times = nullptr;
    for (int i = 0; i < tablet->column_num; i++) {
        free(tablet->column_schema[i]);
        free(tablet->value[i]);
        free(tablet->bitmap[i]);
    }
    free(tablet->bitmap);
    free(tablet->column_schema);
    free(tablet->value);
    delete tablet;
    return E_OK;
}

ErrorCode insert_data_into_tsfile_row_int32(TsFileRowData data, char* columname,
                                            int32_t value) {
    TsRecord* record = (TsRecord*)data;
    INSERT_DATA_INTO_RECORD(record, columname, value);
}

ErrorCode insert_data_into_tsfile_row_boolean(TsFileRowData data,
                                              char* columname, bool value) {
    TsRecord* record = (TsRecord*)data;
    INSERT_DATA_INTO_RECORD(record, columname, value);
}

ErrorCode insert_data_into_tsfile_row_int64(TsFileRowData data, char* columname,
                                            int64_t value) {
    TsRecord* record = (TsRecord*)data;
    INSERT_DATA_INTO_RECORD(record, columname, value);
}

ErrorCode insert_data_into_tsfile_row_float(TsFileRowData data, char* columname,
                                            float value) {
    TsRecord* record = (TsRecord*)data;
    INSERT_DATA_INTO_RECORD(record, columname, value);
}

ErrorCode insert_data_into_tsfile_row_double(TsFileRowData data,
                                             char* columname, double value) {
    TsRecord* record = (TsRecord*)data;
    INSERT_DATA_INTO_RECORD(record, columname, value);
}

ErrorCode tsfile_write_row_data(CTsFileWriter writer, TsFileRowData data) {
    TsFileWriter* w = (TsFileWriter*)writer;
    TsRecord* record = (TsRecord*)data;
    int ret = w->write_record(*record);
    if (ret == E_OK) {
        delete record;
    }
    return ret;
}

ErrorCode destory_tsfile_row(TsFileRowData data) {
    TsRecord* record = (TsRecord*)data;
    if (record != nullptr) {
        delete record;
        record = nullptr;
    }
    return E_OK;
}

ErrorCode tsfile_flush_data(CTsFileWriter writer) {
    TsFileWriter* w = (TsFileWriter*)writer;
    int ret = w->flush();
    return ret;
}

Expression create_column_filter(const char* column_name, OperatorType oper,
                                int32_t int32_value) {
    Expression exp;
    CONSTRUCT_EXP_INTERNAL(exp, column_name);
    exp.const_condition.value_condition = int32_value;
    exp.const_condition.type = TS_TYPE_INT32;
    return exp;
}

Expression create_column_filter(const char* column_name, OperatorType oper,
                                int64_t int64_value) {
    Expression exp;
    CONSTRUCT_EXP_INTERNAL(exp, column_name);
    exp.const_condition.value_condition = int64_value;
    exp.const_condition.type = TS_TYPE_INT64;
    return exp;
}
Expression create_column_filter(const char* column_name, OperatorType oper,
                                bool bool_value) {
    Expression exp;
    CONSTRUCT_EXP_INTERNAL(exp, column_name);
    exp.const_condition.value_condition = bool_value ? 1 : 0;
    exp.const_condition.type = TS_TYPE_BOOLEAN;
    return exp;
}
Expression create_column_filter(const char* column_name, OperatorType oper,
                                float float_value) {
    Expression exp;
    CONSTRUCT_EXP_INTERNAL(exp, column_name);
    memcpy(&exp.const_condition.value_condition, &float_value, sizeof(float));
    exp.const_condition.type = TS_TYPE_FLOAT;
    return exp;
}
Expression create_column_filter(const char* column_name, OperatorType oper,
                                double double_value) {
    Expression exp;
    CONSTRUCT_EXP_INTERNAL(exp, column_name);
    exp.const_condition.value_condition = double_value;
    exp.const_condition.type = TS_TYPE_DOUBLE;
    return exp;
}
Expression create_column_filter(const char* column_name, OperatorType oper,
                                const char* char_value) {
    Expression exp;
    CONSTRUCT_EXP_INTERNAL(exp, column_name);
    exp.const_condition.value_condition = reinterpret_cast<int64_t>(char_value);
    exp.const_condition.type = TS_TYPE_TEXT;
    return exp;
}

TimeFilterExpression* create_andquery_timefilter() {
    storage::Expression* exp = new storage::Expression(storage::AND_EXPR);
    return (TimeFilterExpression*)exp;
}

TimeFilterExpression* create_time_filter(const char* table_name,
                                         const char* column_name,
                                         OperatorType oper, int64_t timestamp) {
    std::string table_name_str(table_name);
    std::string column_name_str(column_name);
    storage::Path path(table_name_str, column_name_str);
    storage::Filter* filter;
    switch (oper) {
        case GT:
            filter = storage::TimeFilter::gt(timestamp);
            break;
        case LT:
            filter = storage::TimeFilter::lt(timestamp);
            break;
        case EQ:
            filter = storage::TimeFilter::eq(timestamp);
            break;
        case NOTEQ:
            filter = storage::TimeFilter::not_eqt(timestamp);
            break;
        case GE:
            filter = storage::TimeFilter::gt_eq(timestamp);
            break;
        case LE:
            filter = storage::TimeFilter::lt_eq(timestamp);
            break;
        default:
            filter = nullptr;
            break;
    }
    storage::Expression* exp =
        new storage::Expression(storage::SERIES_EXPR, path, filter);
    return (TimeFilterExpression*)exp;
}

TimeFilterExpression* add_time_filter_to_and_query(
    TimeFilterExpression* exp_and, TimeFilterExpression* exp) {
    storage::Expression* and_exp = (storage::Expression*)exp_and;
    storage::Expression* time_exp = (storage::Expression*)exp;
    if (and_exp->left_ == nullptr) {
        and_exp->left_ = time_exp;
    } else if (and_exp->right_ == nullptr) {
        and_exp->right_ = time_exp;
    } else {
        storage::Expression* new_exp =
            new storage::Expression(storage::AND_EXPR);
        new_exp->left_ = and_exp->right_;
        and_exp->right_ = new_exp;
        add_time_filter_to_and_query((TimeFilterExpression*)new_exp, exp);
    }
    return exp_and;
}

void destory_time_filter_query(TimeFilterExpression* expression) {
    if (expression == nullptr) {
        return;
    }

    destory_time_filter_query(
        (TimeFilterExpression*)((storage::Expression*)expression)->left_);
    destory_time_filter_query(
        (TimeFilterExpression*)((storage::Expression*)expression)->right_);
    storage::Expression* exp = (storage::Expression*)expression;
    if (exp->type_ == storage::ExpressionType::SERIES_EXPR) {
        delete exp->filter_;
    } else {
        delete exp;
    }
}

Expression create_global_time_expression(OperatorType oper, int64_t timestamp) {
    Expression exp;
    exp.operatype = oper;
    exp.expression_type = GLOBALTIME;
    exp.const_condition.value_condition = timestamp;
    exp.const_condition.type = TS_TYPE_INT64;
    return exp;
}

Expression* and_filter_to_and_query(Expression* exp_and, Expression* exp) {
    if (exp_and->children_length >= MAX_COLUMN_FILTER_NUM - 1) {
        return nullptr;
    }
    exp_and->children[exp_and->children_length++] = exp;
    return exp_and;
}

QueryDataRet ts_reader_query(CTsFileReader reader, const char* table_name,
                             const char** columns_name, int column_num,
                             TimeFilterExpression* expression) {
    TsFileReader* r = (TsFileReader*)reader;
    std::string table_name_str(table_name);
    std::vector<storage::Path> selected_paths;
    for (int i = 0; i < column_num; i++) {
        std::string column_name(columns_name[i]);
        selected_paths.push_back(storage::Path(table_name_str, column_name));
    }

    storage::ResultSet* qds = nullptr;
    storage::QueryExpression* query_expression =
        storage::QueryExpression::create(selected_paths,
                                         (storage::Expression*)expression);
    r->query(query_expression, qds);
    QueryDataRet ret = (QueryDataRet)malloc(sizeof(struct query_data_ret));
    ret->data = qds;
    ret->column_names = (char**)malloc(column_num * sizeof(char*));
    ret->column_num = column_num;
    for (int i = 0; i < column_num; i++) {
        ret->column_names[i] = strdup(columns_name[i]);
    }
    return ret;
}

QueryDataRet ts_reader_begin_end(CTsFileReader reader, const char* table_name,
                                 char** columns_name, int column_num,
                                 timestamp begin, timestamp end) {
    TsFileReader* r = (TsFileReader*)reader;
    std::string table_name_str(table_name);
    std::vector<storage::Path> selected_paths;
    for (int i = 0; i < column_num; i++) {
        std::string column_name(columns_name[i]);
        selected_paths.push_back(storage::Path(table_name_str, column_name));
    }

    storage::ResultSet* qds = nullptr;
    storage::Filter* filter_low = nullptr;
    storage::Filter* filter_high = nullptr;
    storage::Expression* exp = nullptr;
    storage::Filter* and_filter = nullptr;
    if (begin != -1) {
        filter_low = storage::TimeFilter::gt_eq(begin);
    }
    if (end != -1) {
        filter_high = storage::TimeFilter::lt_eq(end);
    }
    if (filter_low != nullptr && filter_high != nullptr) {
        and_filter = new storage::AndFilter(filter_low, filter_high);
        exp = new storage::Expression(storage::GLOBALTIME_EXPR,
                                      and_filter);  // exp never be deleted
    } else if (filter_low != nullptr && filter_high == nullptr) {
        exp = new storage::Expression(storage::GLOBALTIME_EXPR, filter_low);
    } else if (filter_high != nullptr && filter_low == nullptr) {
        exp = new storage::Expression(storage::GLOBALTIME_EXPR, filter_high);
    }
    storage::QueryExpression* query_expr =
        storage::QueryExpression::create(selected_paths, exp);
    r->query(query_expr, qds);
    QueryDataRet ret = (QueryDataRet)malloc(sizeof(struct query_data_ret));
    ret->data = qds;
    ret->column_num = column_num;
    ret->column_names = (char**)malloc(column_num * sizeof(char*));
    for (int i = 0; i < column_num; i++) {
        ret->column_names[i] = strdup(columns_name[i]);
    }
    return ret;
}

QueryDataRet ts_reader_read(CTsFileReader reader, const char* table_name,
                            char** columns_name, int column_num) {
    TsFileReader* r = (TsFileReader*)reader;
    std::string table_name_str(table_name);
    std::vector<storage::Path> selected_paths;
    for (int i = 0; i < column_num; i++) {
        std::string column_name(columns_name[i]);
        selected_paths.push_back(storage::Path(table_name_str, column_name));
    }
    storage::ResultSet* qds = nullptr;
    storage::QueryExpression* query_expr =
        storage::QueryExpression::create(selected_paths, nullptr);
    r->query(query_expr, qds);
    QueryDataRet ret = (QueryDataRet)malloc(sizeof(struct query_data_ret));
    ret->data = qds;
    ret->column_names = (char**)malloc(column_num * sizeof(char*));
    ret->column_num = column_num;
    for (int i = 0; i < column_num; i++) {
        ret->column_names[i] = strdup(columns_name[i]);
    }
    return ret;
}

ErrorCode destory_query_dataret(QueryDataRet data) {
    storage::ResultSet* qds = (storage::ResultSet*)data->data;
    delete qds;
    for (int i = 0; i < data->column_num; i++) {
        free(data->column_names[i]);
    }
    free(data->column_names);
    free(data);
    return E_OK;
}

DataResult* ts_next(QueryDataRet data, int expect_line_count) {
    storage::ResultSet* qds = (storage::ResultSet*)data->data;
    DataResult* result = create_tablet("result", expect_line_count);
    storage::RowRecord* record;
    bool init_tablet = false;
    for (int i = 0; i < expect_line_count; i++) {
        if (!qds->next()) {
            break;
        }
        record = qds->get_row_record();
        int column_num = record->get_fields()->size();
        if (!init_tablet) {
            for (int col = 0; col < column_num; col++) {
                storage::Field* field = record->get_field(col);
                result = add_column_to_tablet(result, data->column_names[col],
                                              get_schema_info(field->type_));
            }
            init_tablet = true;
        }
        for (int col = 0; col < column_num; col++) {
            storage::Field* field = record->get_field(col);
            switch (field->type_) {
                // all data will stored as 8 bytes
                case TSDataType::BOOLEAN:
                    result = add_data_to_tablet_bool(
                        result, i, record->get_timestamp(),
                        data->column_names[col], field->value_.bval_);
                    break;
                case TSDataType::INT32:
                    result = add_data_to_tablet_i32(
                        result, i, record->get_timestamp(),
                        data->column_names[col], field->value_.ival_);
                    break;
                case TSDataType::INT64:
                    result = add_data_to_tablet_i64(
                        result, i, record->get_timestamp(),
                        data->column_names[col], field->value_.lval_);
                    break;
                case TSDataType::FLOAT:
                    result = add_data_to_tablet_float(
                        result, i, record->get_timestamp(),
                        data->column_names[col], field->value_.fval_);
                    break;
                case TSDataType::DOUBLE:
                    result = add_data_to_tablet_double(
                        result, i, record->get_timestamp(),
                        data->column_names[col], field->value_.dval_);
                    break;
                case TSDataType::TEXT:
                    result = add_data_to_tablet_char(
                        result, i, record->get_timestamp(),
                        data->column_names[col], field->value_.sval_);
                    break;
                case TSDataType::NULL_TYPE:
                    // result = add_data_to_tablet(result, i ,
                    // record->get_timestamp(),
                    //                             data->column_names[col], 0);
                    // skip null data
                    break;
                default:
                    std::cout << field->type_ << std::endl;
                    std::cout << "error here" << std::endl;
                    return nullptr;
            }
        }
    }
    return result;
}

void print_data_result(DataResult* result) {
    std::cout << std::left << std::setw(15) << "timestamp";
    for (int i = 0; i < result->column_num; i++) {
        std::cout << std::left << std::setw(15)
                  << result->column_schema[i]->name;
    }
    std::cout << std::endl;
    for (int i = 0; i < result->cur_num; i++) {
        std::cout << std::left << std::setw(15);
        std::cout << result->times[i];
        for (int j = 0; j < result->column_num; j++) {
            ColumnSchema* schema = result->column_schema[j];
            double dval;
            float fval;
            std::cout << std::left << std::setw(15);
            switch (get_datatype(schema->column_def)) {
                case TSDataType::BOOLEAN:
                    std::cout
                        << ((*((int64_t*)result->value[j] + i)) > 0 ? "true"
                                                                    : "false");
                    break;
                case TSDataType::INT32:
                    std::cout << *((int64_t*)result->value[j] + i);
                    break;
                case TSDataType::INT64:
                    std::cout << *((int64_t*)result->value[j] + i);
                    break;
                case TSDataType::FLOAT:
                    memcpy(&fval, (int64_t*)result->value[j] + i,
                           sizeof(float));
                    std::cout << fval;
                    break;
                case TSDataType::DOUBLE:
                    memcpy(&dval, (int64_t*)result->value[j] + i,
                           sizeof(double));
                    std::cout << dval;
                    break;
                default:
                    std::cout << "";
            }
        }
        std::cout << std::endl;
    }
}

// }

// storage::Expression construct_query(Expression* exp) {
//   int column_num = exp->children_length;
//   std::vector<storage::Path> paths;
//   for (int i = 0; i < column_num; i++) {
//     Expression* exp = exp->children[i];
//     if (exp->expression_type != )
//     if (exp->column_name != nullptr ) {
//       std::string column_name = exp->column_name;

//     } else if (column->expression_type == AND) {
//       storage::Expression and_exp = construct_query(table_name,
//       column);
//       // add and_exp to the query
//     }
//     column++;
//   }
//   // construct the query using paths and other information
//   // return the constructed query
// }

// storage::Filter get_filter(int operate_type, Constant condition) {
//   switch(operate_type) {
//     case GT:
//       return storage::TimeFilter::gt();

//   }

// }

// storage::Expression construct_query(const char* table_name,
// Expression exp) {
//   std::string table = table_name;
//   int column_num = exp.children_length;
//   std::vector<storage::Path> paths;
//   paths.reserve(column_num);
//   Expression* column = exp.children;
//   for (int i = 0; i < column_num;i++) {
//     if (column_num == 1) {
//       std::string column_name = column->column_name;
//       // select_list
//       paths.push_back(storage::Path(table, column_name));
//       int operate = column->operatype;
//       Filter filter = get_filter(operate, column->const_condition);
//     }
//   }
// }
