command.c 24.7 KB
Newer Older
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16
/*
 * Copyright (c) 2019 TAOS Data, Inc. <jhtao@taosdata.com>
 *
 * This program is free software: you can use, redistribute, and/or modify
 * it under the terms of the GNU Affero General Public License, version 3
 * or later ("AGPL"), as published by the Free Software Foundation.
 *
 * This program is distributed in the hope that it will be useful, but WITHOUT
 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
 * FITNESS FOR A PARTICULAR PURPOSE.
 *
 * You should have received a copy of the GNU Affero General Public License
 * along with this program. If not, see <http://www.gnu.org/licenses/>.
 */

#include "command.h"
D
dapan1121 已提交
17
#include "catalog.h"
D
dapan1121 已提交
18 19
#include "commandInt.h"
#include "scheduler.h"
20
#include "systable.h"
21 22
#include "tdatablock.h"
#include "tglobal.h"
wafwerar's avatar
wafwerar 已提交
23
#include "tgrant.h"
24

25
extern SConfig* tsCfg;
26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41

static int32_t buildRetrieveTableRsp(SSDataBlock* pBlock, int32_t numOfCols, SRetrieveTableRsp** pRsp) {
  size_t rspSize = sizeof(SRetrieveTableRsp) + blockGetEncodeSize(pBlock);
  *pRsp = taosMemoryCalloc(1, rspSize);
  if (NULL == *pRsp) {
    return TSDB_CODE_OUT_OF_MEMORY;
  }

  (*pRsp)->useconds = 0;
  (*pRsp)->completed = 1;
  (*pRsp)->precision = 0;
  (*pRsp)->compressed = 0;
  (*pRsp)->compLen = 0;
  (*pRsp)->numOfRows = htonl(pBlock->info.rows);
  (*pRsp)->numOfCols = htonl(numOfCols);

H
Haojun Liao 已提交
42
  int32_t len = blockEncode(pBlock, (*pRsp)->data, numOfCols);
43 44 45 46 47
  ASSERT(len == rspSize - sizeof(SRetrieveTableRsp));

  return TSDB_CODE_SUCCESS;
}

X
Xiaoyu Wang 已提交
48 49 50 51 52
static int32_t getSchemaBytes(const SSchema* pSchema) {
  switch (pSchema->type) {
    case TSDB_DATA_TYPE_BINARY:
      return (pSchema->bytes - VARSTR_HEADER_SIZE);
    case TSDB_DATA_TYPE_NCHAR:
wmmhello's avatar
wmmhello 已提交
53
    case TSDB_DATA_TYPE_JSON:
X
Xiaoyu Wang 已提交
54 55 56 57 58
      return (pSchema->bytes - VARSTR_HEADER_SIZE) / TSDB_NCHAR_SIZE;
    default:
      return pSchema->bytes;
  }
}
59

X
Xiaoyu Wang 已提交
60
static int32_t buildDescResultDataBlock(SSDataBlock** pOutput) {
61
  SSDataBlock* pBlock = createDataBlock();
X
Xiaoyu Wang 已提交
62 63 64
  if (NULL == pBlock) {
    return TSDB_CODE_OUT_OF_MEMORY;
  }
65

66
  SColumnInfoData infoData = createColumnInfoData(TSDB_DATA_TYPE_VARCHAR, DESCRIBE_RESULT_FIELD_LEN, 1);
X
Xiaoyu Wang 已提交
67 68 69 70 71 72 73 74 75 76 77 78 79
  int32_t         code = blockDataAppendColInfo(pBlock, &infoData);
  if (TSDB_CODE_SUCCESS == code) {
    infoData = createColumnInfoData(TSDB_DATA_TYPE_VARCHAR, DESCRIBE_RESULT_TYPE_LEN, 2);
    code = blockDataAppendColInfo(pBlock, &infoData);
  }
  if (TSDB_CODE_SUCCESS == code) {
    infoData = createColumnInfoData(TSDB_DATA_TYPE_INT, tDataTypes[TSDB_DATA_TYPE_INT].bytes, 3);
    code = blockDataAppendColInfo(pBlock, &infoData);
  }
  if (TSDB_CODE_SUCCESS == code) {
    infoData = createColumnInfoData(TSDB_DATA_TYPE_VARCHAR, DESCRIBE_RESULT_NOTE_LEN, 4);
    code = blockDataAppendColInfo(pBlock, &infoData);
  }
80

X
Xiaoyu Wang 已提交
81 82 83 84 85 86
  if (TSDB_CODE_SUCCESS == code) {
    *pOutput = pBlock;
  } else {
    blockDataDestroy(pBlock);
  }
  return code;
87 88
}

89
static void setDescResultIntoDataBlock(bool sysInfoUser, SSDataBlock* pBlock, int32_t numOfRows, STableMeta* pMeta) {
90
  blockDataEnsureCapacity(pBlock, numOfRows);
91
  pBlock->info.rows = 0;
92 93 94

  // field
  SColumnInfoData* pCol1 = taosArrayGet(pBlock->pDataBlock, 0);
95
  // Type
96
  SColumnInfoData* pCol2 = taosArrayGet(pBlock->pDataBlock, 1);
97
  // Length
98
  SColumnInfoData* pCol3 = taosArrayGet(pBlock->pDataBlock, 2);
99
  // Note
100
  SColumnInfoData* pCol4 = taosArrayGet(pBlock->pDataBlock, 3);
101
  char             buf[DESCRIBE_RESULT_FIELD_LEN] = {0};
102
  for (int32_t i = 0; i < numOfRows; ++i) {
103 104 105 106 107 108 109 110 111
    if (invisibleColumn(sysInfoUser, pMeta->tableType, pMeta->schema[i].flags)) {
      continue;
    }
    STR_TO_VARSTR(buf, pMeta->schema[i].name);
    colDataAppend(pCol1, pBlock->info.rows, buf, false);
    STR_TO_VARSTR(buf, tDataTypes[pMeta->schema[i].type].name);
    colDataAppend(pCol2, pBlock->info.rows, buf, false);
    int32_t bytes = getSchemaBytes(pMeta->schema + i);
    colDataAppend(pCol3, pBlock->info.rows, (const char*)&bytes, false);
112
    STR_TO_VARSTR(buf, i >= pMeta->tableInfo.numOfColumns ? "TAG" : "");
113 114
    colDataAppend(pCol4, pBlock->info.rows, buf, false);
    ++(pBlock->info.rows);
115 116 117
  }
}

118
static int32_t execDescribe(bool sysInfoUser, SNode* pStmt, SRetrieveTableRsp** pRsp) {
119 120
  SDescribeStmt* pDesc = (SDescribeStmt*)pStmt;
  int32_t        numOfRows = TABLE_TOTAL_COL_NUM(pDesc->pMeta);
121

X
Xiaoyu Wang 已提交
122 123 124 125 126 127 128 129 130 131
  SSDataBlock* pBlock = NULL;
  int32_t      code = buildDescResultDataBlock(&pBlock);
  if (TSDB_CODE_SUCCESS == code) {
    setDescResultIntoDataBlock(sysInfoUser, pBlock, numOfRows, pDesc->pMeta);
  }
  if (TSDB_CODE_SUCCESS == code) {
    code = buildRetrieveTableRsp(pBlock, DESCRIBE_RESULT_COLS, pRsp);
  }
  blockDataDestroy(pBlock);
  return code;
132 133
}

134 135
static int32_t execResetQueryCache() { return catalogClearCache(); }

X
Xiaoyu Wang 已提交
136 137 138 139 140 141
static int32_t buildCreateDBResultDataBlock(SSDataBlock** pOutput) {
  SSDataBlock* pBlock = createDataBlock();
  if (NULL == pBlock) {
    return TSDB_CODE_OUT_OF_MEMORY;
  }

H
Haojun Liao 已提交
142
  SColumnInfoData infoData = createColumnInfoData(TSDB_DATA_TYPE_VARCHAR, SHOW_CREATE_DB_RESULT_COLS, 1);
X
Xiaoyu Wang 已提交
143 144 145 146 147
  int32_t         code = blockDataAppendColInfo(pBlock, &infoData);
  if (TSDB_CODE_SUCCESS == code) {
    infoData = createColumnInfoData(TSDB_DATA_TYPE_VARCHAR, SHOW_CREATE_DB_RESULT_FIELD2_LEN, 2);
    code = blockDataAppendColInfo(pBlock, &infoData);
  }
D
dapan1121 已提交
148

X
Xiaoyu Wang 已提交
149 150 151 152 153 154
  if (TSDB_CODE_SUCCESS == code) {
    *pOutput = pBlock;
  } else {
    blockDataDestroy(pBlock);
  }
  return code;
D
dapan1121 已提交
155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181
}

int64_t getValOfDiffPrecision(int8_t unit, int64_t val) {
  int64_t v = 0;
  switch (unit) {
    case 's':
      v = val / 1000;
      break;
    case 'm':
      v = val / tsTickPerMin[TSDB_TIME_PRECISION_MILLI];
      break;
    case 'h':
      v = val / (tsTickPerMin[TSDB_TIME_PRECISION_MILLI] * 60);
      break;
    case 'd':
      v = val / (tsTickPerMin[TSDB_TIME_PRECISION_MILLI] * 24 * 60);
      break;
    case 'w':
      v = val / (tsTickPerMin[TSDB_TIME_PRECISION_MILLI] * 24 * 60 * 7);
      break;
    default:
      break;
  }

  return v;
}

182
char* buildRetension(SArray* pRetension) {
D
dapan1121 已提交
183 184 185 186 187
  size_t size = taosArrayGetSize(pRetension);
  if (size == 0) {
    return NULL;
  }

188 189
  char*       p1 = taosMemoryCalloc(1, 100);
  SRetention* p = taosArrayGet(pRetension, 0);
D
dapan1121 已提交
190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217

  int32_t len = 0;

  int64_t v1 = getValOfDiffPrecision(p->freqUnit, p->freq);
  int64_t v2 = getValOfDiffPrecision(p->keepUnit, p->keep);
  len += sprintf(p1 + len, "%" PRId64 "%c:%" PRId64 "%c", v1, p->freqUnit, v2, p->keepUnit);

  if (size > 1) {
    len += sprintf(p1 + len, ",");
    p = taosArrayGet(pRetension, 1);

    v1 = getValOfDiffPrecision(p->freqUnit, p->freq);
    v2 = getValOfDiffPrecision(p->keepUnit, p->keep);
    len += sprintf(p1 + len, "%" PRId64 "%c:%" PRId64 "%c", v1, p->freqUnit, v2, p->keepUnit);
  }

  if (size > 2) {
    len += sprintf(p1 + len, ",");
    p = taosArrayGet(pRetension, 2);

    v1 = getValOfDiffPrecision(p->freqUnit, p->freq);
    v2 = getValOfDiffPrecision(p->keepUnit, p->keep);
    len += sprintf(p1 + len, "%" PRId64 "%c:%" PRId64 "%c", v1, p->freqUnit, v2, p->keepUnit);
  }

  return p1;
}

X
Xiaoyu Wang 已提交
218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237
static const char* cacheModelStr(int8_t cacheModel) {
  switch (cacheModel) {
    case TSDB_CACHE_MODEL_NONE:
      return TSDB_CACHE_MODEL_NONE_STR;
    case TSDB_CACHE_MODEL_LAST_ROW:
      return TSDB_CACHE_MODEL_LAST_ROW_STR;
    case TSDB_CACHE_MODEL_LAST_VALUE:
      return TSDB_CACHE_MODEL_LAST_VALUE_STR;
    case TSDB_CACHE_MODEL_BOTH:
      return TSDB_CACHE_MODEL_BOTH_STR;
    default:
      break;
  }
  return TSDB_CACHE_MODEL_NONE_STR;
}

static const char* strictStr(int8_t strict) {
  return TSDB_DB_STRICT_ON == strict ? TSDB_DB_STRICT_ON_STR : TSDB_DB_STRICT_OFF_STR;
}

238
static void setCreateDBResultIntoDataBlock(SSDataBlock* pBlock, char* dbFName, SDbCfgInfo* pCfg) {
D
dapan1121 已提交
239 240 241 242 243 244 245 246 247 248 249
  blockDataEnsureCapacity(pBlock, 1);
  pBlock->info.rows = 1;

  SColumnInfoData* pCol1 = taosArrayGet(pBlock->pDataBlock, 0);
  char             buf1[SHOW_CREATE_DB_RESULT_FIELD1_LEN] = {0};
  STR_TO_VARSTR(buf1, dbFName);
  colDataAppend(pCol1, 0, buf1, false);

  SColumnInfoData* pCol2 = taosArrayGet(pBlock->pDataBlock, 1);
  char             buf2[SHOW_CREATE_DB_RESULT_FIELD2_LEN] = {0};
  int32_t          len = 0;
250
  char*            prec = NULL;
D
dapan1121 已提交
251 252 253 254 255 256 257 258 259 260 261 262 263 264 265
  switch (pCfg->precision) {
    case TSDB_TIME_PRECISION_MILLI:
      prec = TSDB_TIME_PRECISION_MILLI_STR;
      break;
    case TSDB_TIME_PRECISION_MICRO:
      prec = TSDB_TIME_PRECISION_MICRO_STR;
      break;
    case TSDB_TIME_PRECISION_NANO:
      prec = TSDB_TIME_PRECISION_NANO_STR;
      break;
    default:
      prec = "none";
      break;
  }

266 267
  char* retentions = buildRetension(pCfg->pRetensions);

X
Xiaoyu Wang 已提交
268 269
  len += sprintf(
      buf2 + VARSTR_HEADER_SIZE,
270
      "CREATE DATABASE `%s` BUFFER %d CACHESIZE %d CACHEMODEL '%s' COMP %d DURATION %dm "
X
Xiaoyu Wang 已提交
271 272
      "WAL_FSYNC_PERIOD %d MAXROWS %d MINROWS %d KEEP %dm,%dm,%dm PAGES %d PAGESIZE %d PRECISION '%s' REPLICA %d "
      "STRICT '%s' WAL_LEVEL %d VGROUPS %d SINGLE_STABLE %d",
273
      dbFName, pCfg->buffer, pCfg->cacheSize, cacheModelStr(pCfg->cacheLast), pCfg->compression, pCfg->daysPerFile, pCfg->walFsyncPeriod,
X
Xiaoyu Wang 已提交
274 275 276
      pCfg->maxRows, pCfg->minRows, pCfg->daysToKeep0, pCfg->daysToKeep1, pCfg->daysToKeep2, pCfg->pages,
      pCfg->pageSize, prec, pCfg->replications, strictStr(pCfg->strict), pCfg->walLevel, pCfg->numOfVgroups,
      1 == pCfg->numOfStables);
D
dapan1121 已提交
277 278 279 280 281 282 283

  if (retentions) {
    len += sprintf(buf2 + VARSTR_HEADER_SIZE + len, " RETENTIONS %s", retentions);
    taosMemoryFree(retentions);
  }

  (varDataLen(buf2)) = len;
284

D
dapan1121 已提交
285 286 287 288
  colDataAppend(pCol2, 0, buf2, false);
}

static int32_t execShowCreateDatabase(SShowCreateDatabaseStmt* pStmt, SRetrieveTableRsp** pRsp) {
X
Xiaoyu Wang 已提交
289 290 291 292 293 294 295 296 297 298
  SSDataBlock* pBlock = NULL;
  int32_t      code = buildCreateDBResultDataBlock(&pBlock);
  if (TSDB_CODE_SUCCESS == code) {
    setCreateDBResultIntoDataBlock(pBlock, pStmt->dbName, pStmt->pCfg);
  }
  if (TSDB_CODE_SUCCESS == code) {
    code = buildRetrieveTableRsp(pBlock, SHOW_CREATE_DB_RESULT_COLS, pRsp);
  }
  blockDataDestroy(pBlock);
  return code;
D
dapan1121 已提交
299
}
300

X
Xiaoyu Wang 已提交
301
static int32_t buildCreateTbResultDataBlock(SSDataBlock** pOutput) {
H
Haojun Liao 已提交
302
  SSDataBlock* pBlock = createDataBlock();
X
Xiaoyu Wang 已提交
303 304 305
  if (NULL == pBlock) {
    return TSDB_CODE_OUT_OF_MEMORY;
  }
D
dapan1121 已提交
306

H
Haojun Liao 已提交
307
  SColumnInfoData infoData = createColumnInfoData(TSDB_DATA_TYPE_VARCHAR, SHOW_CREATE_TB_RESULT_FIELD1_LEN, 1);
X
Xiaoyu Wang 已提交
308 309 310 311 312
  int32_t         code = blockDataAppendColInfo(pBlock, &infoData);
  if (TSDB_CODE_SUCCESS == code) {
    infoData = createColumnInfoData(TSDB_DATA_TYPE_VARCHAR, SHOW_CREATE_TB_RESULT_FIELD2_LEN, 2);
    code = blockDataAppendColInfo(pBlock, &infoData);
  }
D
dapan1121 已提交
313

X
Xiaoyu Wang 已提交
314 315 316 317 318 319
  if (TSDB_CODE_SUCCESS == code) {
    *pOutput = pBlock;
  } else {
    blockDataDestroy(pBlock);
  }
  return code;
D
dapan1121 已提交
320 321 322 323 324
}

void appendColumnFields(char* buf, int32_t* len, STableCfg* pCfg) {
  for (int32_t i = 0; i < pCfg->numOfColumns; ++i) {
    SSchema* pSchema = pCfg->pSchemas + i;
325
    char     type[32];
D
dapan1121 已提交
326 327 328 329
    sprintf(type, "%s", tDataTypes[pSchema->type].name);
    if (TSDB_DATA_TYPE_VARCHAR == pSchema->type) {
      sprintf(type + strlen(type), "(%d)", (int32_t)(pSchema->bytes - VARSTR_HEADER_SIZE));
    } else if (TSDB_DATA_TYPE_NCHAR == pSchema->type) {
330
      sprintf(type + strlen(type), "(%d)", (int32_t)((pSchema->bytes - VARSTR_HEADER_SIZE) / TSDB_NCHAR_SIZE));
D
dapan1121 已提交
331
    }
332

D
dapan1121 已提交
333
    *len += sprintf(buf + VARSTR_HEADER_SIZE + *len, "%s`%s` %s", ((i > 0) ? ", " : ""), pSchema->name, type);
D
dapan1121 已提交
334 335 336 337 338 339
  }
}

void appendTagFields(char* buf, int32_t* len, STableCfg* pCfg) {
  for (int32_t i = 0; i < pCfg->numOfTags; ++i) {
    SSchema* pSchema = pCfg->pSchemas + pCfg->numOfColumns + i;
340
    char     type[32];
D
dapan1121 已提交
341 342 343 344
    sprintf(type, "%s", tDataTypes[pSchema->type].name);
    if (TSDB_DATA_TYPE_VARCHAR == pSchema->type) {
      sprintf(type + strlen(type), "(%d)", (int32_t)(pSchema->bytes - VARSTR_HEADER_SIZE));
    } else if (TSDB_DATA_TYPE_NCHAR == pSchema->type) {
345
      sprintf(type + strlen(type), "(%d)", (int32_t)((pSchema->bytes - VARSTR_HEADER_SIZE) / TSDB_NCHAR_SIZE));
D
dapan1121 已提交
346 347
    }

D
dapan1121 已提交
348
    *len += sprintf(buf + VARSTR_HEADER_SIZE + *len, "%s`%s` %s", ((i > 0) ? ", " : ""), pSchema->name, type);
D
dapan1121 已提交
349 350 351
  }
}

D
dapan1121 已提交
352 353 354
void appendTagNameFields(char* buf, int32_t* len, STableCfg* pCfg) {
  for (int32_t i = 0; i < pCfg->numOfTags; ++i) {
    SSchema* pSchema = pCfg->pSchemas + pCfg->numOfColumns + i;
D
dapan1121 已提交
355
    *len += sprintf(buf + VARSTR_HEADER_SIZE + *len, "%s`%s`", ((i > 0) ? ", " : ""), pSchema->name);
D
dapan1121 已提交
356 357 358
  }
}

D
dapan1121 已提交
359
int32_t appendTagValues(char* buf, int32_t* len, STableCfg* pCfg) {
360 361 362
  SArray* pTagVals = NULL;
  STag*   pTag = (STag*)pCfg->pTags;

D
dapan1121 已提交
363 364 365 366 367 368
  if (NULL == pCfg->pTags || pCfg->numOfTags <= 0) {
    qError("tag missed in table cfg, pointer:%p, numOfTags:%d", pCfg->pTags, pCfg->numOfTags);
    return TSDB_CODE_APP_ERROR;
  }

  if (tTagIsJson(pTag)) {
369
    char* pJson = parseTagDatatoJson(pTag);
D
dapan1121 已提交
370
    if (pJson) {
D
dapan1121 已提交
371
      *len += sprintf(buf + VARSTR_HEADER_SIZE + *len, "%s", pJson);
D
dapan1121 已提交
372
      taosMemoryFree(pJson);
D
dapan1121 已提交
373 374 375 376
    }

    return TSDB_CODE_SUCCESS;
  }
377 378

  int32_t code = tTagToValArray((const STag*)pCfg->pTags, &pTagVals);
D
dapan1121 已提交
379 380 381 382
  if (code) {
    return code;
  }

D
dapan1121 已提交
383
  int16_t valueNum = taosArrayGetSize(pTagVals);
D
dapan1121 已提交
384
  int32_t num = 0;
D
dapan1121 已提交
385 386 387 388
  int32_t j = 0;
  for (int32_t i = 0; i < pCfg->numOfTags; ++i) {
    SSchema* pSchema = pCfg->pSchemas + pCfg->numOfColumns + i;
    if (i > 0) {
D
dapan1121 已提交
389
      *len += sprintf(buf + VARSTR_HEADER_SIZE + *len, ", ");
D
dapan1121 已提交
390
    }
391

D
dapan1121 已提交
392
    if (j >= valueNum) {
D
dapan1121 已提交
393
      *len += sprintf(buf + VARSTR_HEADER_SIZE + *len, "NULL");
D
dapan1121 已提交
394 395
      continue;
    }
396 397

    STagVal* pTagVal = (STagVal*)taosArrayGet(pTagVals, j);
D
dapan1121 已提交
398 399 400 401 402
    if (pSchema->colId > pTagVal->cid) {
      qError("tag value and column mismatch, schemaId:%d, valId:%d", pSchema->colId, pTagVal->cid);
      taosArrayDestroy(pTagVals);
      return TSDB_CODE_APP_ERROR;
    } else if (pSchema->colId == pTagVal->cid) {
403 404
      char    type = pTagVal->type;
      int32_t tlen = 0;
D
dapan1121 已提交
405 406

      if (IS_VAR_DATA_TYPE(type)) {
D
dapan1121 已提交
407
        dataConverToStr(buf + VARSTR_HEADER_SIZE + *len, type, pTagVal->pData, pTagVal->nData, &tlen);
D
dapan1121 已提交
408
      } else {
D
dapan1121 已提交
409
        dataConverToStr(buf + VARSTR_HEADER_SIZE + *len, type, &pTagVal->i64, tDataTypes[type].bytes, &tlen);
D
dapan1121 已提交
410 411 412 413
      }
      *len += tlen;
      j++;
    } else {
D
dapan1121 已提交
414
      *len += sprintf(buf + VARSTR_HEADER_SIZE + *len, "NULL");
D
dapan1121 已提交
415
    }
D
dapan1121 已提交
416 417 418 419 420 421 422

    /*
    if (type == TSDB_DATA_TYPE_BINARY) {
      if (pTagVal->nData > 0) {
        if (num) {
          *len += sprintf(buf + VARSTR_HEADER_SIZE + *len, ", ");
        }
423

D
dapan1121 已提交
424 425 426 427 428 429 430 431 432 433 434 435 436 437 438 439 440 441 442 443 444 445
        memcpy(buf + VARSTR_HEADER_SIZE + *len, pTagVal->pData, pTagVal->nData);
        *len += pTagVal->nData;
      }
    } else if (type == TSDB_DATA_TYPE_NCHAR) {
      if (pTagVal->nData > 0) {
        if (num) {
          *len += sprintf(buf + VARSTR_HEADER_SIZE + *len, ", ");
        }
        int32_t tlen = taosUcs4ToMbs((TdUcs4 *)pTagVal->pData, pTagVal->nData, buf + VARSTR_HEADER_SIZE + *len);
      }
    } else if (type == TSDB_DATA_TYPE_DOUBLE) {
      double val = *(double *)(&pTagVal->i64);
      int    len = 0;
      term = indexTermCreate(suid, ADD_VALUE, type, key, nKey, (const char *)&val, len);
    } else if (type == TSDB_DATA_TYPE_BOOL) {
      int val = *(int *)(&pTagVal->i64);
      int len = 0;
      term = indexTermCreate(suid, ADD_VALUE, TSDB_DATA_TYPE_INT, key, nKey, (const char *)&val, len);
    }
    */
  }

D
dapan1121 已提交
446 447
  taosArrayDestroy(pTagVals);

448
  return TSDB_CODE_SUCCESS;
D
dapan1121 已提交
449 450
}

X
Xiaoyu Wang 已提交
451
void appendTableOptions(char* buf, int32_t* len, SDbCfgInfo* pDbCfg, STableCfg* pCfg) {
D
dapan1121 已提交
452
  if (pCfg->commentLen > 0) {
D
dapan1121 已提交
453
    *len += sprintf(buf + VARSTR_HEADER_SIZE + *len, " COMMENT '%s'", pCfg->pComment);
D
dapan1121 已提交
454
  } else if (0 == pCfg->commentLen) {
D
dapan1121 已提交
455
    *len += sprintf(buf + VARSTR_HEADER_SIZE + *len, " COMMENT ''");
D
dapan1121 已提交
456 457
  }

X
Xiaoyu Wang 已提交
458
  if (NULL != pDbCfg->pRetensions && pCfg->watermark1 > 0) {
D
dapan1121 已提交
459
    *len += sprintf(buf + VARSTR_HEADER_SIZE + *len, " WATERMARK %" PRId64 "a", pCfg->watermark1);
D
dapan1121 已提交
460
    if (pCfg->watermark2 > 0) {
D
dapan1121 已提交
461
      *len += sprintf(buf + VARSTR_HEADER_SIZE + *len, ", %" PRId64 "a", pCfg->watermark2);
D
dapan1121 已提交
462 463 464
    }
  }

X
Xiaoyu Wang 已提交
465
  if (NULL != pDbCfg->pRetensions && pCfg->delay1 > 0) {
D
dapan1121 已提交
466
    *len += sprintf(buf + VARSTR_HEADER_SIZE + *len, " MAX_DELAY %" PRId64 "a", pCfg->delay1);
D
dapan1121 已提交
467
    if (pCfg->delay2 > 0) {
D
dapan1121 已提交
468
      *len += sprintf(buf + VARSTR_HEADER_SIZE + *len, ", %" PRId64 "a", pCfg->delay2);
D
dapan1121 已提交
469 470 471 472
    }
  }

  int32_t funcNum = taosArrayGetSize(pCfg->pFuncs);
X
Xiaoyu Wang 已提交
473
  if (NULL != pDbCfg->pRetensions && funcNum > 0) {
D
dapan1121 已提交
474
    *len += sprintf(buf + VARSTR_HEADER_SIZE + *len, " ROLLUP(");
D
dapan1121 已提交
475 476
    for (int32_t i = 0; i < funcNum; ++i) {
      char* pFunc = taosArrayGet(pCfg->pFuncs, i);
D
dapan1121 已提交
477
      *len += sprintf(buf + VARSTR_HEADER_SIZE + *len, "%s%s", ((i > 0) ? ", " : ""), pFunc);
D
dapan1121 已提交
478
    }
D
dapan1121 已提交
479
    *len += sprintf(buf + VARSTR_HEADER_SIZE + *len, ")");
D
dapan1121 已提交
480
  }
D
dapan1121 已提交
481 482

  if (pCfg->ttl > 0) {
D
dapan1121 已提交
483
    *len += sprintf(buf + VARSTR_HEADER_SIZE + *len, " TTL %d", pCfg->ttl);
D
dapan1121 已提交
484
  }
D
dapan1121 已提交
485 486
}

X
Xiaoyu Wang 已提交
487
static int32_t setCreateTBResultIntoDataBlock(SSDataBlock* pBlock, SDbCfgInfo* pDbCfg, char* tbName, STableCfg* pCfg) {
D
dapan1121 已提交
488 489 490 491 492 493 494 495 496 497
  int32_t code = 0;
  blockDataEnsureCapacity(pBlock, 1);
  pBlock->info.rows = 1;

  SColumnInfoData* pCol1 = taosArrayGet(pBlock->pDataBlock, 0);
  char             buf1[SHOW_CREATE_TB_RESULT_FIELD1_LEN] = {0};
  STR_TO_VARSTR(buf1, tbName);
  colDataAppend(pCol1, 0, buf1, false);

  SColumnInfoData* pCol2 = taosArrayGet(pBlock->pDataBlock, 1);
D
dapan1121 已提交
498 499 500 501 502 503
  char*            buf2 = taosMemoryMalloc(SHOW_CREATE_TB_RESULT_FIELD2_LEN);
  if (NULL == buf2) {
    terrno = TSDB_CODE_TSC_OUT_OF_MEMORY;
    return terrno;
  }
  
D
dapan1121 已提交
504 505 506
  int32_t          len = 0;

  if (TSDB_SUPER_TABLE == pCfg->tableType) {
D
dapan1121 已提交
507
    len += sprintf(buf2 + VARSTR_HEADER_SIZE, "CREATE STABLE `%s` (", tbName);
D
dapan1121 已提交
508
    appendColumnFields(buf2, &len, pCfg);
D
dapan1121 已提交
509
    len += sprintf(buf2 + VARSTR_HEADER_SIZE + len, ") TAGS (");
510
    appendTagFields(buf2, &len, pCfg);
D
dapan1121 已提交
511
    len += sprintf(buf2 + VARSTR_HEADER_SIZE + len, ")");
X
Xiaoyu Wang 已提交
512
    appendTableOptions(buf2, &len, pDbCfg, pCfg);
D
dapan1121 已提交
513
  } else if (TSDB_CHILD_TABLE == pCfg->tableType) {
D
dapan1121 已提交
514
    len += sprintf(buf2 + VARSTR_HEADER_SIZE, "CREATE TABLE `%s` USING `%s` (", tbName, pCfg->stbName);
D
dapan1121 已提交
515
    appendTagNameFields(buf2, &len, pCfg);
D
dapan1121 已提交
516
    len += sprintf(buf2 + VARSTR_HEADER_SIZE + len, ") TAGS (");
D
dapan1121 已提交
517 518
    code = appendTagValues(buf2, &len, pCfg);
    if (code) {
D
dapan1121 已提交
519
      taosMemoryFree(buf2);
D
dapan1121 已提交
520 521
      return code;
    }
D
dapan1121 已提交
522
    len += sprintf(buf2 + VARSTR_HEADER_SIZE + len, ")");
X
Xiaoyu Wang 已提交
523
    appendTableOptions(buf2, &len, pDbCfg, pCfg);
D
dapan1121 已提交
524
  } else {
D
dapan1121 已提交
525
    len += sprintf(buf2 + VARSTR_HEADER_SIZE, "CREATE TABLE `%s` (", tbName);
D
dapan1121 已提交
526
    appendColumnFields(buf2, &len, pCfg);
D
dapan1121 已提交
527
    len += sprintf(buf2 + VARSTR_HEADER_SIZE + len, ")");
528
    appendTableOptions(buf2, &len, pDbCfg, pCfg);
D
dapan1121 已提交
529 530
  }

D
dapan1121 已提交
531
  varDataLen(buf2) = (len > 65535) ? 65535 : len;
532

D
dapan1121 已提交
533
  colDataAppend(pCol2, 0, buf2, false);
D
dapan1121 已提交
534

D
dapan1121 已提交
535 536
  taosMemoryFree(buf2);
  
D
dapan1121 已提交
537 538 539 540
  return TSDB_CODE_SUCCESS;
}

static int32_t execShowCreateTable(SShowCreateTableStmt* pStmt, SRetrieveTableRsp** pRsp) {
X
Xiaoyu Wang 已提交
541 542 543 544
  SSDataBlock* pBlock = NULL;
  int32_t      code = buildCreateTbResultDataBlock(&pBlock);
  if (TSDB_CODE_SUCCESS == code) {
    code = setCreateTBResultIntoDataBlock(pBlock, pStmt->pDbCfg, pStmt->tableName, pStmt->pTableCfg);
D
dapan1121 已提交
545
  }
X
Xiaoyu Wang 已提交
546 547 548 549 550
  if (TSDB_CODE_SUCCESS == code) {
    code = buildRetrieveTableRsp(pBlock, SHOW_CREATE_TB_RESULT_COLS, pRsp);
  }
  blockDataDestroy(pBlock);
  return code;
D
dapan1121 已提交
551 552 553
}

static int32_t execShowCreateSTable(SShowCreateTableStmt* pStmt, SRetrieveTableRsp** pRsp) {
X
Xiaoyu Wang 已提交
554
  STableCfg* pCfg = (STableCfg*)pStmt->pTableCfg;
D
dapan1121 已提交
555 556 557 558
  if (TSDB_SUPER_TABLE != pCfg->tableType) {
    terrno = TSDB_CODE_TSC_NOT_STABLE_ERROR;
    return terrno;
  }
559

D
dapan1121 已提交
560 561
  return execShowCreateTable(pStmt, pRsp);
}
562

D
dapan1121 已提交
563 564
static int32_t execAlterCmd(char* cmd, char* value, bool* processed) {
  int32_t code = 0;
565

D
dapan1121 已提交
566 567 568 569 570 571 572
  if (0 == strcasecmp(cmd, COMMAND_RESET_LOG)) {
    taosResetLog();
    cfgDumpCfg(tsCfg, 0, false);
  } else if (0 == strcasecmp(cmd, COMMAND_SCHEDULE_POLICY)) {
    code = schedulerUpdatePolicy(atoi(value));
  } else if (0 == strcasecmp(cmd, COMMAND_ENABLE_RESCHEDULE)) {
    code = schedulerEnableReSchedule(atoi(value));
D
dapan1121 已提交
573 574
  } else if (0 == strcasecmp(cmd, COMMAND_CATALOG_DEBUG)) {
    code = ctgdHandleDbgCommand(value);
D
dapan1121 已提交
575 576 577 578 579 580 581 582 583 584 585
  } else {
    goto _return;
  }

  *processed = true;

_return:

  if (code) {
    terrno = code;
  }
586 587

  return code;
D
dapan1121 已提交
588 589
}

590
static int32_t execAlterLocal(SAlterLocalStmt* pStmt) {
D
dapan1121 已提交
591
  bool processed = false;
592

D
dapan1121 已提交
593 594 595 596 597 598 599
  if (execAlterCmd(pStmt->config, pStmt->value, &processed)) {
    return terrno;
  }

  if (processed) {
    goto _return;
  }
600

601 602 603 604 605 606 607
  bool forbidden = false;
  taosLocalCfgForbiddenToChange(pStmt->config, &forbidden);
  if (forbidden) {
    terrno = TSDB_CODE_OPS_NOT_SUPPORT;
    return terrno;
  }

D
dapan1121 已提交
608
  if (cfgSetItem(tsCfg, pStmt->config, pStmt->value, CFG_STYPE_ALTER_CMD)) {
609
    return terrno;
D
dapan1121 已提交
610 611
  }

D
dapan1121 已提交
612
  if (taosSetCfg(tsCfg, pStmt->config)) {
613
    return terrno;
D
dapan1121 已提交
614 615
  }

D
dapan1121 已提交
616 617
_return:

D
dapan1121 已提交
618 619
  return TSDB_CODE_SUCCESS;
}
620

X
Xiaoyu Wang 已提交
621
static int32_t buildLocalVariablesResultDataBlock(SSDataBlock** pOutput) {
D
dapan1121 已提交
622
  SSDataBlock* pBlock = taosMemoryCalloc(1, sizeof(SSDataBlock));
X
Xiaoyu Wang 已提交
623 624 625 626
  if (NULL == pBlock) {
    return TSDB_CODE_OUT_OF_MEMORY;
  }

D
dapan1121 已提交
627 628
  pBlock->info.hasVarCol = true;

S
shenglian zhou 已提交
629
  pBlock->pDataBlock = taosArrayInit(SHOW_LOCAL_VARIABLES_RESULT_COLS, sizeof(SColumnInfoData));
D
dapan1121 已提交
630 631 632 633 634 635 636 637 638 639 640

  SColumnInfoData infoData = {0};
  infoData.info.type = TSDB_DATA_TYPE_VARCHAR;
  infoData.info.bytes = SHOW_LOCAL_VARIABLES_RESULT_FIELD1_LEN;

  taosArrayPush(pBlock->pDataBlock, &infoData);

  infoData.info.type = TSDB_DATA_TYPE_VARCHAR;
  infoData.info.bytes = SHOW_LOCAL_VARIABLES_RESULT_FIELD2_LEN;
  taosArrayPush(pBlock->pDataBlock, &infoData);

X
Xiaoyu Wang 已提交
641 642
  *pOutput = pBlock;
  return TSDB_CODE_SUCCESS;
D
dapan1121 已提交
643 644 645 646 647 648 649 650
}

int32_t setLocalVariablesResultIntoDataBlock(SSDataBlock* pBlock) {
  int32_t numOfCfg = taosArrayGetSize(tsCfg->array);
  int32_t numOfRows = 0;
  blockDataEnsureCapacity(pBlock, numOfCfg);

  for (int32_t i = 0, c = 0; i < numOfCfg; ++i, c = 0) {
651
    SConfigItem* pItem = taosArrayGet(tsCfg->array, i);
wafwerar's avatar
wafwerar 已提交
652
    GRANT_CFG_SKIP;
D
dapan1121 已提交
653 654
    char name[TSDB_CONFIG_OPTION_LEN + VARSTR_HEADER_SIZE] = {0};
    STR_WITH_MAXSIZE_TO_VARSTR(name, pItem->name, TSDB_CONFIG_OPTION_LEN + VARSTR_HEADER_SIZE);
655
    SColumnInfoData* pColInfo = taosArrayGet(pBlock->pDataBlock, c++);
D
dapan1121 已提交
656
    colDataAppend(pColInfo, i, name, false);
657 658

    char    value[TSDB_CONFIG_VALUE_LEN + VARSTR_HEADER_SIZE] = {0};
D
dapan1121 已提交
659 660 661 662 663 664 665 666 667 668
    int32_t valueLen = 0;
    cfgDumpItemValue(pItem, &value[VARSTR_HEADER_SIZE], TSDB_CONFIG_VALUE_LEN, &valueLen);
    varDataSetLen(value, valueLen);
    pColInfo = taosArrayGet(pBlock->pDataBlock, c++);
    colDataAppend(pColInfo, i, value, false);

    numOfRows++;
  }

  pBlock->info.rows = numOfRows;
669

D
dapan1121 已提交
670 671 672 673
  return TSDB_CODE_SUCCESS;
}

static int32_t execShowLocalVariables(SRetrieveTableRsp** pRsp) {
X
Xiaoyu Wang 已提交
674 675 676 677
  SSDataBlock* pBlock = NULL;
  int32_t      code = buildLocalVariablesResultDataBlock(&pBlock);
  if (TSDB_CODE_SUCCESS == code) {
    code = setLocalVariablesResultIntoDataBlock(pBlock);
D
dapan1121 已提交
678
  }
X
Xiaoyu Wang 已提交
679 680 681 682 683
  if (TSDB_CODE_SUCCESS == code) {
    code = buildRetrieveTableRsp(pBlock, SHOW_LOCAL_VARIABLES_RESULT_COLS, pRsp);
  }
  blockDataDestroy(pBlock);
  return code;
684
}
D
dapan1121 已提交
685

686
static int32_t createSelectResultDataBlock(SNodeList* pProjects, SSDataBlock** pOutput) {
687
  SSDataBlock* pBlock = createDataBlock();
688
  if (NULL == pBlock) {
D
dapan1121 已提交
689 690 691
    return TSDB_CODE_OUT_OF_MEMORY;
  }

692 693 694 695 696
  SNode* pProj = NULL;
  FOREACH(pProj, pProjects) {
    SColumnInfoData infoData = {0};
    infoData.info.type = ((SExprNode*)pProj)->resType.type;
    infoData.info.bytes = ((SExprNode*)pProj)->resType.bytes;
697
    blockDataAppendColInfo(pBlock, &infoData);
698 699 700 701 702 703 704 705 706 707 708
  }
  *pOutput = pBlock;
  return TSDB_CODE_SUCCESS;
}

int32_t buildSelectResultDataBlock(SNodeList* pProjects, SSDataBlock* pBlock) {
  blockDataEnsureCapacity(pBlock, 1);

  int32_t index = 0;
  SNode*  pProj = NULL;
  FOREACH(pProj, pProjects) {
D
dapan1121 已提交
709 710
    if (QUERY_NODE_VALUE != nodeType(pProj)) {
      return TSDB_CODE_PAR_INVALID_SELECTED_EXPR;
711
    } else {
D
dapan1121 已提交
712 713 714 715 716
      if (((SValueNode*)pProj)->isNull) {
        colDataAppend(taosArrayGet(pBlock->pDataBlock, index++), 0, NULL, true);
      } else {
        colDataAppend(taosArrayGet(pBlock->pDataBlock, index++), 0, nodesGetValueFromNode((SValueNode*)pProj), false);
      }
717 718 719 720
    }
  }

  pBlock->info.rows = 1;
D
dapan1121 已提交
721 722
  return TSDB_CODE_SUCCESS;
}
723

724 725 726 727 728 729 730 731 732
static int32_t execSelectWithoutFrom(SSelectStmt* pSelect, SRetrieveTableRsp** pRsp) {
  SSDataBlock* pBlock = NULL;
  int32_t      code = createSelectResultDataBlock(pSelect->pProjectionList, &pBlock);
  if (TSDB_CODE_SUCCESS == code) {
    code = buildSelectResultDataBlock(pSelect->pProjectionList, pBlock);
  }
  if (TSDB_CODE_SUCCESS == code) {
    code = buildRetrieveTableRsp(pBlock, LIST_LENGTH(pSelect->pProjectionList), pRsp);
  }
X
Xiaoyu Wang 已提交
733
  blockDataDestroy(pBlock);
734 735 736
  return code;
}

737
int32_t qExecCommand(bool sysInfoUser, SNode* pStmt, SRetrieveTableRsp** pRsp) {
738 739
  switch (nodeType(pStmt)) {
    case QUERY_NODE_DESCRIBE_STMT:
740
      return execDescribe(sysInfoUser, pStmt, pRsp);
741 742
    case QUERY_NODE_RESET_QUERY_CACHE_STMT:
      return execResetQueryCache();
743
    case QUERY_NODE_SHOW_CREATE_DATABASE_STMT:
D
dapan1121 已提交
744
      return execShowCreateDatabase((SShowCreateDatabaseStmt*)pStmt, pRsp);
745
    case QUERY_NODE_SHOW_CREATE_TABLE_STMT:
D
dapan1121 已提交
746
      return execShowCreateTable((SShowCreateTableStmt*)pStmt, pRsp);
747
    case QUERY_NODE_SHOW_CREATE_STABLE_STMT:
D
dapan1121 已提交
748
      return execShowCreateSTable((SShowCreateTableStmt*)pStmt, pRsp);
749 750
    case QUERY_NODE_ALTER_LOCAL_STMT:
      return execAlterLocal((SAlterLocalStmt*)pStmt);
751
    case QUERY_NODE_SHOW_LOCAL_VARIABLES_STMT:
D
dapan1121 已提交
752
      return execShowLocalVariables(pRsp);
753 754
    case QUERY_NODE_SELECT_STMT:
      return execSelectWithoutFrom((SSelectStmt*)pStmt, pRsp);
755 756 757 758 759
    default:
      break;
  }
  return TSDB_CODE_FAILED;
}