Search in sources :

Example 6 with CreateTableData

use of org.h2.command.ddl.CreateTableData in project ignite by apache.

the class GridSqlQueryParser method parseCreateTable.

/**
 * Parse {@code CREATE TABLE} statement.
 *
 * @param createTbl {@code CREATE TABLE} statement.
 * @see <a href="http://h2database.com/html/grammar.html#create_table">H2 {@code CREATE TABLE} spec.</a>
 */
private GridSqlCreateTable parseCreateTable(CreateTable createTbl) {
    GridSqlCreateTable res = new GridSqlCreateTable();
    res.templateName(QueryUtils.TEMPLATE_PARTITIONED);
    Query qry = CREATE_TABLE_QUERY.get(createTbl);
    if (qry != null) {
        throw new IgniteSQLException("CREATE TABLE ... AS ... syntax is not supported", IgniteQueryErrorCode.UNSUPPORTED_OPERATION);
    }
    List<DefineCommand> constraints = CREATE_TABLE_CONSTRAINTS.get(createTbl);
    if (F.isEmpty(constraints)) {
        throw new IgniteSQLException("No PRIMARY KEY defined for CREATE TABLE", IgniteQueryErrorCode.PARSING);
    }
    if (constraints.size() > 1) {
        throw new IgniteSQLException("Too many constraints - only PRIMARY KEY is supported for CREATE TABLE", IgniteQueryErrorCode.UNSUPPORTED_OPERATION);
    }
    DefineCommand constraint = constraints.get(0);
    if (!(constraint instanceof AlterTableAddConstraint)) {
        throw new IgniteSQLException("Unsupported type of constraint for CREATE TABLE - only PRIMARY KEY " + "is supported", IgniteQueryErrorCode.UNSUPPORTED_OPERATION);
    }
    AlterTableAddConstraint alterTbl = (AlterTableAddConstraint) constraint;
    if (alterTbl.getType() != Command.ALTER_TABLE_ADD_CONSTRAINT_PRIMARY_KEY) {
        throw new IgniteSQLException("Unsupported type of constraint for CREATE TABLE - only PRIMARY KEY " + "is supported", IgniteQueryErrorCode.UNSUPPORTED_OPERATION);
    }
    Schema schema = SCHEMA_COMMAND_SCHEMA.get(createTbl);
    res.schemaName(schema.getName());
    CreateTableData data = CREATE_TABLE_DATA.get(createTbl);
    if (data.globalTemporary) {
        throw new IgniteSQLException("GLOBAL TEMPORARY keyword is not supported", IgniteQueryErrorCode.UNSUPPORTED_OPERATION);
    }
    if (data.temporary) {
        throw new IgniteSQLException("TEMPORARY keyword is not supported", IgniteQueryErrorCode.UNSUPPORTED_OPERATION);
    }
    if (data.isHidden) {
        throw new IgniteSQLException("HIDDEN keyword is not supported", IgniteQueryErrorCode.UNSUPPORTED_OPERATION);
    }
    if (!data.persistIndexes) {
        throw new IgniteSQLException("MEMORY and NOT PERSISTENT keywords are not supported", IgniteQueryErrorCode.UNSUPPORTED_OPERATION);
    }
    LinkedHashMap<String, GridSqlColumn> cols = new LinkedHashMap<>(data.columns.size());
    for (Column col : data.columns) {
        if (cols.put(col.getName(), parseColumn(col)) != null)
            throw new IgniteSQLException("Duplicate column name: " + col.getName(), IgniteQueryErrorCode.PARSING);
    }
    if (cols.containsKey(QueryUtils.KEY_FIELD_NAME.toUpperCase()) || cols.containsKey(QueryUtils.VAL_FIELD_NAME.toUpperCase())) {
        throw new IgniteSQLException("Direct specification of _KEY and _VAL columns is forbidden", IgniteQueryErrorCode.PARSING);
    }
    IndexColumn[] pkIdxCols = CREATE_TABLE_PK.get(createTbl);
    if (F.isEmpty(pkIdxCols))
        throw new AssertionError("No PRIMARY KEY columns specified");
    LinkedHashSet<String> pkCols = new LinkedHashSet<>();
    for (IndexColumn pkIdxCol : pkIdxCols) {
        GridSqlColumn gridCol = cols.get(pkIdxCol.columnName);
        if (gridCol == null) {
            throw new IgniteSQLException("PRIMARY KEY column is not defined: " + pkIdxCol.columnName, IgniteQueryErrorCode.PARSING);
        }
        pkCols.add(gridCol.columnName());
    }
    int keyColsNum = pkCols.size();
    int valColsNum = cols.size() - keyColsNum;
    if (valColsNum == 0) {
        throw new IgniteSQLException("Table must have at least one non PRIMARY KEY column.", IgniteQueryErrorCode.UNSUPPORTED_OPERATION);
    }
    res.columns(cols);
    res.primaryKeyColumns(pkCols);
    res.tableName(data.tableName);
    res.ifNotExists(CREATE_TABLE_IF_NOT_EXISTS.get(createTbl));
    List<String> extraParams = data.tableEngineParams != null ? new ArrayList<String>() : null;
    if (data.tableEngineParams != null)
        for (String s : data.tableEngineParams) extraParams.addAll(F.asList(s.split(",")));
    res.params(extraParams);
    if (!F.isEmpty(extraParams)) {
        Map<String, String> params = new HashMap<>();
        for (String p : extraParams) {
            String[] parts = p.split(PARAM_NAME_VALUE_SEPARATOR);
            if (parts.length > 2) {
                throw new IgniteSQLException("Invalid parameter (key[=value] expected): " + p, IgniteQueryErrorCode.PARSING);
            }
            String name = parts[0].trim().toUpperCase();
            String val = parts.length > 1 ? parts[1].trim() : null;
            if (F.isEmpty(name)) {
                throw new IgniteSQLException("Invalid parameter (key[=value] expected): " + p, IgniteQueryErrorCode.PARSING);
            }
            if (params.put(name, val) != null)
                throw new IgniteSQLException("Duplicate parameter: " + p, IgniteQueryErrorCode.PARSING);
        }
        for (Map.Entry<String, String> e : params.entrySet()) processExtraParam(e.getKey(), e.getValue(), res);
    }
    // Process key wrapping.
    Boolean wrapKey = res.wrapKey();
    if (wrapKey != null && !wrapKey) {
        if (keyColsNum > 1) {
            throw new IgniteSQLException(PARAM_WRAP_KEY + " cannot be false when composite primary key exists.", IgniteQueryErrorCode.PARSING);
        }
        if (!F.isEmpty(res.keyTypeName())) {
            throw new IgniteSQLException(PARAM_WRAP_KEY + " cannot be false when " + PARAM_KEY_TYPE + " is set.", IgniteQueryErrorCode.PARSING);
        }
    }
    boolean wrapKey0 = (res.wrapKey() != null && res.wrapKey()) || !F.isEmpty(res.keyTypeName()) || keyColsNum > 1;
    res.wrapKey(wrapKey0);
    // Process value wrapping.
    Boolean wrapVal = res.wrapValue();
    if (wrapVal != null && !wrapVal) {
        if (valColsNum > 1) {
            throw new IgniteSQLException(PARAM_WRAP_VALUE + " cannot be false when multiple non-primary key " + "columns exist.", IgniteQueryErrorCode.PARSING);
        }
        if (!F.isEmpty(res.valueTypeName())) {
            throw new IgniteSQLException(PARAM_WRAP_VALUE + " cannot be false when " + PARAM_VAL_TYPE + " is set.", IgniteQueryErrorCode.PARSING);
        }
        res.wrapValue(false);
    } else
        // By default value is always wrapped to allow for ALTER TABLE ADD COLUMN commands.
        res.wrapValue(true);
    if (!F.isEmpty(res.valueTypeName()) && F.eq(res.keyTypeName(), res.valueTypeName())) {
        throw new IgniteSQLException("Key and value type names " + "should be different for CREATE TABLE: " + res.valueTypeName(), IgniteQueryErrorCode.PARSING);
    }
    if (res.affinityKey() == null) {
        LinkedHashSet<String> pkCols0 = res.primaryKeyColumns();
        if (!F.isEmpty(pkCols0) && pkCols0.size() == 1 && wrapKey0)
            res.affinityKey(pkCols0.iterator().next());
    }
    return res;
}
Also used : LinkedHashSet(java.util.LinkedHashSet) Query(org.h2.command.dml.Query) LinkedHashMap(java.util.LinkedHashMap) IdentityHashMap(java.util.IdentityHashMap) HashMap(java.util.HashMap) Schema(org.h2.schema.Schema) DefineCommand(org.h2.command.ddl.DefineCommand) LinkedHashMap(java.util.LinkedHashMap) IndexColumn(org.h2.table.IndexColumn) GridSqlType.fromColumn(org.apache.ignite.internal.processors.query.h2.sql.GridSqlType.fromColumn) AlterTableAlterColumn(org.h2.command.ddl.AlterTableAlterColumn) Column(org.h2.table.Column) ExpressionColumn(org.h2.expression.ExpressionColumn) IndexColumn(org.h2.table.IndexColumn) AlterTableAddConstraint(org.h2.command.ddl.AlterTableAddConstraint) CreateTableData(org.h2.command.ddl.CreateTableData) AlterTableAddConstraint(org.h2.command.ddl.AlterTableAddConstraint) IgniteSQLException(org.apache.ignite.internal.processors.query.IgniteSQLException) Map(java.util.Map) LinkedHashMap(java.util.LinkedHashMap) IdentityHashMap(java.util.IdentityHashMap) HashMap(java.util.HashMap)

Example 7 with CreateTableData

use of org.h2.command.ddl.CreateTableData in project ignite by apache.

the class GridReduceQueryExecutor method createMergeTable.

/**
 * @param conn Connection.
 * @param qry Query.
 * @param explain Explain.
 * @return Table.
 * @throws IgniteCheckedException If failed.
 */
@SuppressWarnings("unchecked")
private GridMergeTable createMergeTable(JdbcConnection conn, GridCacheSqlQuery qry, boolean explain) throws IgniteCheckedException {
    try {
        Session ses = (Session) conn.getSession();
        CreateTableData data = new CreateTableData();
        data.tableName = "T___";
        data.schema = ses.getDatabase().getSchema(ses.getCurrentSchemaName());
        data.create = true;
        if (!explain) {
            LinkedHashMap<String, ?> colsMap = qry.columns();
            assert colsMap != null;
            ArrayList<Column> cols = new ArrayList<>(colsMap.size());
            for (Map.Entry<String, ?> e : colsMap.entrySet()) {
                String alias = e.getKey();
                GridSqlType t = (GridSqlType) e.getValue();
                assert !F.isEmpty(alias);
                Column c = new Column(alias, t.type(), t.precision(), t.scale(), t.displaySize());
                cols.add(c);
            }
            data.columns = cols;
        } else
            data.columns = planColumns();
        boolean sortedIndex = !F.isEmpty(qry.sortColumns());
        GridMergeTable tbl = new GridMergeTable(data);
        ArrayList<Index> idxs = new ArrayList<>(2);
        if (explain) {
            idxs.add(new GridMergeIndexUnsorted(ctx, tbl, sortedIndex ? MERGE_INDEX_SORTED : MERGE_INDEX_UNSORTED));
        } else if (sortedIndex) {
            List<GridSqlSortColumn> sortCols = (List<GridSqlSortColumn>) qry.sortColumns();
            GridMergeIndexSorted sortedMergeIdx = new GridMergeIndexSorted(ctx, tbl, MERGE_INDEX_SORTED, GridSqlSortColumn.toIndexColumns(tbl, sortCols));
            idxs.add(GridMergeTable.createScanIndex(sortedMergeIdx));
            idxs.add(sortedMergeIdx);
        } else
            idxs.add(new GridMergeIndexUnsorted(ctx, tbl, MERGE_INDEX_UNSORTED));
        tbl.indexes(idxs);
        return tbl;
    } catch (Exception e) {
        U.closeQuiet(conn);
        throw new IgniteCheckedException(e);
    }
}
Also used : ArrayList(java.util.ArrayList) Index(org.h2.index.Index) CreateTableData(org.h2.command.ddl.CreateTableData) QueryCancelledException(org.apache.ignite.cache.query.QueryCancelledException) IgniteClientDisconnectedException(org.apache.ignite.IgniteClientDisconnectedException) IgniteCheckedException(org.apache.ignite.IgniteCheckedException) IgniteException(org.apache.ignite.IgniteException) SQLException(java.sql.SQLException) IgniteInterruptedCheckedException(org.apache.ignite.internal.IgniteInterruptedCheckedException) CacheException(javax.cache.CacheException) TransactionException(org.apache.ignite.transactions.TransactionException) IgniteCheckedException(org.apache.ignite.IgniteCheckedException) GridSqlSortColumn(org.apache.ignite.internal.processors.query.h2.sql.GridSqlSortColumn) Column(org.h2.table.Column) GridSqlSortColumn(org.apache.ignite.internal.processors.query.h2.sql.GridSqlSortColumn) GridSqlType(org.apache.ignite.internal.processors.query.h2.sql.GridSqlType) Collections.singletonList(java.util.Collections.singletonList) GridIntList(org.apache.ignite.internal.util.GridIntList) List(java.util.List) ArrayList(java.util.ArrayList) Map(java.util.Map) ConcurrentHashMap(java.util.concurrent.ConcurrentHashMap) HashMap(java.util.HashMap) ConcurrentMap(java.util.concurrent.ConcurrentMap) LinkedHashMap(java.util.LinkedHashMap) Session(org.h2.engine.Session)

Example 8 with CreateTableData

use of org.h2.command.ddl.CreateTableData in project h2database by h2database.

the class Database method open.

private synchronized void open(int traceLevelFile, int traceLevelSystemOut) {
    if (persistent) {
        String dataFileName = databaseName + Constants.SUFFIX_OLD_DATABASE_FILE;
        boolean existsData = FileUtils.exists(dataFileName);
        String pageFileName = databaseName + Constants.SUFFIX_PAGE_FILE;
        String mvFileName = databaseName + Constants.SUFFIX_MV_FILE;
        boolean existsPage = FileUtils.exists(pageFileName);
        boolean existsMv = FileUtils.exists(mvFileName);
        if (existsData && (!existsPage && !existsMv)) {
            throw DbException.get(ErrorCode.FILE_VERSION_ERROR_1, "Old database: " + dataFileName + " - please convert the database " + "to a SQL script and re-create it.");
        }
        if (existsPage && !FileUtils.canWrite(pageFileName)) {
            readOnly = true;
        }
        if (existsMv && !FileUtils.canWrite(mvFileName)) {
            readOnly = true;
        }
        if (existsPage && !existsMv) {
            dbSettings.mvStore = false;
        }
        if (readOnly) {
            if (traceLevelFile >= TraceSystem.DEBUG) {
                String traceFile = Utils.getProperty("java.io.tmpdir", ".") + "/" + "h2_" + System.currentTimeMillis();
                traceSystem = new TraceSystem(traceFile + Constants.SUFFIX_TRACE_FILE);
            } else {
                traceSystem = new TraceSystem(null);
            }
        } else {
            traceSystem = new TraceSystem(databaseName + Constants.SUFFIX_TRACE_FILE);
        }
        traceSystem.setLevelFile(traceLevelFile);
        traceSystem.setLevelSystemOut(traceLevelSystemOut);
        trace = traceSystem.getTrace(Trace.DATABASE);
        trace.info("opening {0} (build {1})", databaseName, Constants.BUILD_ID);
        if (autoServerMode) {
            if (readOnly || fileLockMethod == FileLockMethod.NO || fileLockMethod == FileLockMethod.SERIALIZED || fileLockMethod == FileLockMethod.FS || !persistent) {
                throw DbException.getUnsupportedException("autoServerMode && (readOnly || " + "fileLockMethod == NO || " + "fileLockMethod == SERIALIZED || " + "fileLockMethod == FS || " + "inMemory)");
            }
        }
        String lockFileName = databaseName + Constants.SUFFIX_LOCK_FILE;
        if (readOnly) {
            if (FileUtils.exists(lockFileName)) {
                throw DbException.get(ErrorCode.DATABASE_ALREADY_OPEN_1, "Lock file exists: " + lockFileName);
            }
        }
        if (!readOnly && fileLockMethod != FileLockMethod.NO) {
            if (fileLockMethod != FileLockMethod.FS) {
                lock = new FileLock(traceSystem, lockFileName, Constants.LOCK_SLEEP);
                lock.lock(fileLockMethod);
                if (autoServerMode) {
                    startServer(lock.getUniqueId());
                }
            }
        }
        if (SysProperties.MODIFY_ON_WRITE) {
            while (isReconnectNeeded()) {
            // wait until others stopped writing
            }
        } else {
            while (isReconnectNeeded() && !beforeWriting()) {
            // wait until others stopped writing and
            // until we can write (the file is not yet open -
            // no need to re-connect)
            }
        }
        deleteOldTempFiles();
        starting = true;
        if (SysProperties.MODIFY_ON_WRITE) {
            try {
                getPageStore();
            } catch (DbException e) {
                if (e.getErrorCode() != ErrorCode.DATABASE_IS_READ_ONLY) {
                    throw e;
                }
                pageStore = null;
                while (!beforeWriting()) {
                // wait until others stopped writing and
                // until we can write (the file is not yet open -
                // no need to re-connect)
                }
                getPageStore();
            }
        } else {
            getPageStore();
        }
        starting = false;
        if (mvStore == null) {
            writer = WriterThread.create(this, writeDelay);
        } else {
            setWriteDelay(writeDelay);
        }
    } else {
        if (autoServerMode) {
            throw DbException.getUnsupportedException("autoServerMode && inMemory");
        }
        traceSystem = new TraceSystem(null);
        trace = traceSystem.getTrace(Trace.DATABASE);
        if (dbSettings.mvStore) {
            getPageStore();
        }
    }
    systemUser = new User(this, 0, SYSTEM_USER_NAME, true);
    mainSchema = new Schema(this, 0, Constants.SCHEMA_MAIN, systemUser, true);
    infoSchema = new Schema(this, -1, "INFORMATION_SCHEMA", systemUser, true);
    schemas.put(mainSchema.getName(), mainSchema);
    schemas.put(infoSchema.getName(), infoSchema);
    publicRole = new Role(this, 0, Constants.PUBLIC_ROLE_NAME, true);
    roles.put(Constants.PUBLIC_ROLE_NAME, publicRole);
    systemUser.setAdmin(true);
    systemSession = new Session(this, systemUser, ++nextSessionId);
    lobSession = new Session(this, systemUser, ++nextSessionId);
    CreateTableData data = new CreateTableData();
    ArrayList<Column> cols = data.columns;
    Column columnId = new Column("ID", Value.INT);
    columnId.setNullable(false);
    cols.add(columnId);
    cols.add(new Column("HEAD", Value.INT));
    cols.add(new Column("TYPE", Value.INT));
    cols.add(new Column("SQL", Value.STRING));
    boolean create = true;
    if (pageStore != null) {
        create = pageStore.isNew();
    }
    data.tableName = "SYS";
    data.id = 0;
    data.temporary = false;
    data.persistData = persistent;
    data.persistIndexes = persistent;
    data.create = create;
    data.isHidden = true;
    data.session = systemSession;
    meta = mainSchema.createTable(data);
    IndexColumn[] pkCols = IndexColumn.wrap(new Column[] { columnId });
    metaIdIndex = meta.addIndex(systemSession, "SYS_ID", 0, pkCols, IndexType.createPrimaryKey(false, false), true, null);
    objectIds.set(0);
    starting = true;
    Cursor cursor = metaIdIndex.find(systemSession, null, null);
    ArrayList<MetaRecord> records = New.arrayList();
    while (cursor.next()) {
        MetaRecord rec = new MetaRecord(cursor.get());
        objectIds.set(rec.getId());
        records.add(rec);
    }
    Collections.sort(records);
    synchronized (systemSession) {
        for (MetaRecord rec : records) {
            rec.execute(this, systemSession, eventListener);
        }
    }
    if (mvStore != null) {
        mvStore.initTransactions();
        mvStore.removeTemporaryMaps(objectIds);
    }
    recompileInvalidViews(systemSession);
    starting = false;
    if (!readOnly) {
        // set CREATE_BUILD in a new database
        String name = SetTypes.getTypeName(SetTypes.CREATE_BUILD);
        if (settings.get(name) == null) {
            Setting setting = new Setting(this, allocateObjectId(), name);
            setting.setIntValue(Constants.BUILD_ID);
            lockMeta(systemSession);
            addDatabaseObject(systemSession, setting);
        }
        // mark all ids used in the page store
        if (pageStore != null) {
            BitSet f = pageStore.getObjectIds();
            for (int i = 0, len = f.length(); i < len; i++) {
                if (f.get(i) && !objectIds.get(i)) {
                    trace.info("unused object id: " + i);
                    objectIds.set(i);
                }
            }
        }
    }
    getLobStorage().init();
    systemSession.commit(true);
    trace.info("opened {0}", databaseName);
    if (checkpointAllowed > 0) {
        afterWriting();
    }
}
Also used : Schema(org.h2.schema.Schema) BitSet(java.util.BitSet) TraceSystem(org.h2.message.TraceSystem) CreateTableData(org.h2.command.ddl.CreateTableData) Cursor(org.h2.index.Cursor) Constraint(org.h2.constraint.Constraint) DbException(org.h2.message.DbException) IndexColumn(org.h2.table.IndexColumn) IndexColumn(org.h2.table.IndexColumn) Column(org.h2.table.Column) FileLock(org.h2.store.FileLock)

Example 9 with CreateTableData

use of org.h2.command.ddl.CreateTableData in project h2database by h2database.

the class TableView method createShadowTableForRecursiveTableExpression.

/**
 * Create a table for a recursive query.
 *
 * @param isPersistent whether the table is persisted
 * @param targetSession the session
 * @param cteViewName the name
 * @param schema the schema
 * @param columns the columns
 * @param db the database
 * @return the table
 */
public static Table createShadowTableForRecursiveTableExpression(boolean isPersistent, Session targetSession, String cteViewName, Schema schema, List<Column> columns, Database db) {
    // create table data object
    CreateTableData recursiveTableData = new CreateTableData();
    recursiveTableData.id = db.allocateObjectId();
    recursiveTableData.columns = new ArrayList<>(columns);
    recursiveTableData.tableName = cteViewName;
    recursiveTableData.temporary = !isPersistent;
    recursiveTableData.persistData = true;
    recursiveTableData.persistIndexes = isPersistent;
    recursiveTableData.create = true;
    recursiveTableData.session = targetSession;
    // this gets a meta table lock that is not released
    Table recursiveTable = schema.createTable(recursiveTableData);
    if (isPersistent) {
        // this unlock is to prevent lock leak from schema.createTable()
        db.unlockMeta(targetSession);
        synchronized (targetSession) {
            db.addSchemaObject(targetSession, recursiveTable);
        }
    } else {
        targetSession.addLocalTempTable(recursiveTable);
    }
    return recursiveTable;
}
Also used : CreateTableData(org.h2.command.ddl.CreateTableData)

Aggregations

CreateTableData (org.h2.command.ddl.CreateTableData)7 Column (org.h2.table.Column)7 Index (org.h2.index.Index)4 Schema (org.h2.schema.Schema)4 IndexColumn (org.h2.table.IndexColumn)4 HashMap (java.util.HashMap)3 LinkedHashMap (java.util.LinkedHashMap)3 Map (java.util.Map)3 SQLException (java.sql.SQLException)2 ArrayList (java.util.ArrayList)2 Collections.singletonList (java.util.Collections.singletonList)2 List (java.util.List)2 ConcurrentHashMap (java.util.concurrent.ConcurrentHashMap)2 ConcurrentMap (java.util.concurrent.ConcurrentMap)2 CacheException (javax.cache.CacheException)2 IgniteCheckedException (org.apache.ignite.IgniteCheckedException)2 IgniteClientDisconnectedException (org.apache.ignite.IgniteClientDisconnectedException)2 IgniteException (org.apache.ignite.IgniteException)2 QueryCancelledException (org.apache.ignite.cache.query.QueryCancelledException)2 IgniteInterruptedCheckedException (org.apache.ignite.internal.IgniteInterruptedCheckedException)2