Search in sources :

Example 1 with Column

use of ru.curs.celesta.score.Column in project celesta by CourseOrchestra.

the class DbUpdater method dropOrphanedGrainIndices.

void dropOrphanedGrainIndices(Grain g) {
    /*
         * In general this method repeats the code from updateGrainIndices but only
         * in the part of deletion of indices. It is needed to clear up all indices
         * that were undergone a deletion or a change before an update of table
         * structure is performed. That raises the probability of a successful outcome:
         * hanging at fields indices may interfere with the process.
         */
    final Connection conn = schemaCursor.callContext().getConn();
    Map<String, DbIndexInfo> dbIndices = dbAdaptor.getIndices(conn, g);
    Map<String, Index> myIndices = g.getIndices();
    // Deletion of indices that don't exist in the metadata.
    for (DbIndexInfo dBIndexInfo : dbIndices.values()) {
        if (!myIndices.containsKey(dBIndexInfo.getIndexName())) {
            dbAdaptor.dropIndex(g, dBIndexInfo);
        }
    }
    // Deletion of indices that will be changed later before tables update.
    for (Map.Entry<String, Index> e : myIndices.entrySet()) {
        DbIndexInfo dBIndexInfo = dbIndices.get(e.getKey());
        if (dBIndexInfo != null) {
            boolean reflects = dBIndexInfo.reflects(e.getValue());
            if (!reflects) {
                dbAdaptor.dropIndex(g, dBIndexInfo);
            }
            // Deletion of indices at those fields that will undergo a change
            for (Map.Entry<String, Column<?>> ee : e.getValue().getColumns().entrySet()) {
                DbColumnInfo ci = dbAdaptor.getColumnInfo(conn, ee.getValue());
                if (ci == null || !ci.reflects(ee.getValue())) {
                    dbAdaptor.dropIndex(g, dBIndexInfo);
                    break;
                }
            }
        }
    }
}
Also used : Column(ru.curs.celesta.score.Column) Connection(java.sql.Connection) DbColumnInfo(ru.curs.celesta.dbutils.meta.DbColumnInfo) DbIndexInfo(ru.curs.celesta.dbutils.meta.DbIndexInfo) Index(ru.curs.celesta.score.Index) VersionString(ru.curs.celesta.score.VersionString) HashMap(java.util.HashMap) Map(java.util.Map)

Example 2 with Column

use of ru.curs.celesta.score.Column in project celesta by CourseOrchestra.

the class FirebirdAdaptor method getColumnInfo.

@Override
public DbColumnInfo getColumnInfo(Connection conn, Column<?> c) {
    String sql = String.format("SELECT r.RDB$FIELD_NAME AS column_name,%n" + "        r.RDB$DESCRIPTION AS field_description,%n" + "        r.RDB$NULL_FLAG AS nullable,%n" + "        f.RDB$FIELD_LENGTH AS column_length,%n" + "        f.RDB$FIELD_PRECISION AS column_precision,%n" + "        f.RDB$FIELD_SCALE AS column_scale,%n" + "        CASE f.RDB$FIELD_TYPE%n" + "          WHEN 261 THEN 'BLOB'%n" + "          WHEN 14 THEN 'CHAR'%n" + "          WHEN 40 THEN 'CSTRING'%n" + "          WHEN 11 THEN 'D_FLOAT'%n" + "          WHEN 27 THEN 'DOUBLE PRECISION'%n" + "          WHEN 10 THEN 'FLOAT'%n" + "          WHEN 16 THEN 'BIGINT'%n" + "          WHEN 8 THEN 'INTEGER'%n" + "          WHEN 9 THEN 'QUAD'%n" + "          WHEN 7 THEN 'SMALLINT'%n" + "          WHEN 12 THEN 'DATE'%n" + "          WHEN 13 THEN 'TIME'%n" + "          WHEN 35 THEN 'TIMESTAMP'%n" + "          WHEN 29 THEN 'TIMESTAMP WITH TIME ZONE'%n" + "          WHEN 37 THEN 'VARCHAR'%n" + "          ELSE 'UNKNOWN'%n" + "        END AS column_type,%n" + "        f.RDB$FIELD_SUB_TYPE AS column_subtype%n" + "   FROM RDB$RELATION_FIELDS r%n" + "   LEFT JOIN RDB$FIELDS f ON r.RDB$FIELD_SOURCE = f.RDB$FIELD_NAME%n" + "   LEFT JOIN RDB$COLLATIONS coll ON f.RDB$COLLATION_ID = coll.RDB$COLLATION_ID%n" + "   LEFT JOIN RDB$CHARACTER_SETS cset ON f.RDB$CHARACTER_SET_ID = cset.RDB$CHARACTER_SET_ID%n" + "  WHERE r.RDB$RELATION_NAME='%s_%s' AND r.RDB$FIELD_NAME = '%s'", c.getParentTable().getGrain().getName(), c.getParentTable().getName(), c.getName());
    try (ResultSet rs = SqlUtils.executeQuery(conn, sql)) {
        if (rs.next()) {
            DbColumnInfo result = new DbColumnInfo();
            result.setName(rs.getString("column_name").trim());
            String columnType = rs.getString("column_type").trim();
            Integer columnSubType = rs.getInt("column_subtype");
            if (("BIGINT".equals(columnType) || "INTEGER".equals(columnType)) && Integer.valueOf(2).equals(columnSubType)) {
                result.setType(DecimalColumn.class);
                result.setLength(rs.getInt("column_precision"));
                result.setScale(Math.abs(rs.getInt("column_scale")));
            } else if ("BLOB".equals(columnType) && Integer.valueOf(1).equals(columnSubType)) {
                result.setType(StringColumn.class);
                result.setMax(true);
            } else {
                for (Class<? extends Column<?>> cc : COLUMN_CLASSES) {
                    if (getColumnDefiner(cc).dbFieldType().equalsIgnoreCase(columnType)) {
                        result.setType(cc);
                        break;
                    }
                }
            }
            result.setNullable(rs.getInt("nullable") != 1);
            if (result.getType() == StringColumn.class) {
                result.setLength(rs.getInt("column_length"));
            }
            this.processDefaults(conn, c, result);
            return result;
        } else {
            return null;
        }
    } catch (Exception e) {
        throw new CelestaException(e);
    }
}
Also used : StringColumn(ru.curs.celesta.score.StringColumn) DateTimeColumn(ru.curs.celesta.score.DateTimeColumn) StringColumn(ru.curs.celesta.score.StringColumn) BooleanColumn(ru.curs.celesta.score.BooleanColumn) Column(ru.curs.celesta.score.Column) IntegerColumn(ru.curs.celesta.score.IntegerColumn) DecimalColumn(ru.curs.celesta.score.DecimalColumn) BinaryColumn(ru.curs.celesta.score.BinaryColumn) ResultSet(java.sql.ResultSet) DbColumnInfo(ru.curs.celesta.dbutils.meta.DbColumnInfo) CelestaException(ru.curs.celesta.CelestaException) SQLException(java.sql.SQLException) CelestaException(ru.curs.celesta.CelestaException)

Example 3 with Column

use of ru.curs.celesta.score.Column in project celesta by CourseOrchestra.

the class H2Adaptor method getColumnInfo.

@Override
public DbColumnInfo getColumnInfo(Connection conn, Column<?> c) {
    try {
        DatabaseMetaData metaData = conn.getMetaData();
        String grainName = c.getParentTable().getGrain().getName();
        String tableName = c.getParentTable().getName();
        try (ResultSet rs = metaData.getColumns(null, grainName, tableName, c.getName())) {
            if (rs.next()) {
                DbColumnInfo result = new DbColumnInfo();
                result.setName(rs.getString(COLUMN_NAME));
                String typeName = rs.getString("TYPE_NAME");
                String columnDefault = rs.getString("COLUMN_DEF");
                String columnDefaultForIdentity = "NEXTVAL('" + tableString(grainName, tableName + "_seq") + "')";
                if ("integer".equalsIgnoreCase(typeName) && columnDefaultForIdentity.equals(columnDefault)) {
                    result.setType(IntegerColumn.class);
                    result.setNullable(rs.getInt("NULLABLE") != DatabaseMetaData.columnNoNulls);
                    return result;
                } else if ("clob".equalsIgnoreCase(typeName)) {
                    result.setType(StringColumn.class);
                    result.setMax(true);
                } else {
                    for (Class<? extends Column<?>> cc : COLUMN_CLASSES) {
                        if (getColumnDefiner(cc).dbFieldType().equalsIgnoreCase(typeName)) {
                            result.setType(cc);
                            break;
                        }
                    }
                }
                result.setNullable(rs.getInt("NULLABLE") != DatabaseMetaData.columnNoNulls);
                if (result.getType() == StringColumn.class || result.getType() == DecimalColumn.class) {
                    result.setLength(rs.getInt("COLUMN_SIZE"));
                }
                if (result.getType() == DecimalColumn.class) {
                    result.setScale(rs.getInt("DECIMAL_DIGITS"));
                }
                if (columnDefault != null) {
                    columnDefault = modifyDefault(result, columnDefault, conn);
                    result.setDefaultValue(columnDefault);
                }
                return result;
            } else {
                return null;
            }
        }
    } catch (SQLException e) {
        throw new CelestaException(e.getMessage());
    }
}
Also used : StringColumn(ru.curs.celesta.score.StringColumn) DateTimeColumn(ru.curs.celesta.score.DateTimeColumn) DecimalColumn(ru.curs.celesta.score.DecimalColumn) StringColumn(ru.curs.celesta.score.StringColumn) BinaryColumn(ru.curs.celesta.score.BinaryColumn) BooleanColumn(ru.curs.celesta.score.BooleanColumn) Column(ru.curs.celesta.score.Column) IntegerColumn(ru.curs.celesta.score.IntegerColumn) SQLException(java.sql.SQLException) ResultSet(java.sql.ResultSet) DbColumnInfo(ru.curs.celesta.dbutils.meta.DbColumnInfo) DecimalColumn(ru.curs.celesta.score.DecimalColumn) DatabaseMetaData(java.sql.DatabaseMetaData) CelestaException(ru.curs.celesta.CelestaException)

Example 4 with Column

use of ru.curs.celesta.score.Column in project celesta by CourseOrchestra.

the class OraAdaptor method getColumnInfo.

@Override
public DbColumnInfo getColumnInfo(Connection conn, Column<?> c) {
    try {
        String tableName = String.format("%s_%s", c.getParentTable().getGrain().getName(), c.getParentTable().getName());
        String sql = String.format("SELECT COLUMN_NAME, DATA_TYPE, NULLABLE, CHAR_LENGTH, DATA_PRECISION, DATA_SCALE " + "FROM user_tab_cols    WHERE table_name = '%s' and COLUMN_NAME = '%s'", tableName, c.getName());
        LOGGER.trace(sql);
        Statement stmt = conn.createStatement();
        ResultSet rs = stmt.executeQuery(sql);
        DbColumnInfo result;
        try {
            if (rs.next()) {
                result = new DbColumnInfo();
                result.setName(rs.getString(COLUMN_NAME));
                String typeName = rs.getString("DATA_TYPE");
                if (typeName.startsWith("TIMESTAMP")) {
                    if (typeName.endsWith("WITH TIME ZONE")) {
                        result.setType(ZonedDateTimeColumn.class);
                    } else {
                        result.setType(DateTimeColumn.class);
                    }
                } else if ("float".equalsIgnoreCase(typeName)) {
                    result.setType(FloatingColumn.class);
                } else if ("nclob".equalsIgnoreCase(typeName)) {
                    result.setType(StringColumn.class);
                    result.setMax(true);
                } else if ("number".equalsIgnoreCase(typeName) && rs.getInt("DATA_PRECISION") != 0 && rs.getInt("DATA_SCALE") != 0) {
                    result.setType(DecimalColumn.class);
                    result.setLength(rs.getInt("DATA_PRECISION"));
                    result.setScale(rs.getInt("DATA_SCALE"));
                } else {
                    for (Class<? extends Column<?>> cc : COLUMN_CLASSES) {
                        if (getColumnDefiner(cc).dbFieldType().equalsIgnoreCase(typeName)) {
                            result.setType(cc);
                            break;
                        }
                    }
                }
                if (IntegerColumn.class == result.getType()) {
                    // ограничение CHECK.
                    if (checkForBoolean(conn, c)) {
                        result.setType(BooleanColumn.class);
                    }
                }
                result.setNullable("Y".equalsIgnoreCase(rs.getString("NULLABLE")));
                if (result.getType() == StringColumn.class) {
                    result.setLength(rs.getInt("CHAR_LENGTH"));
                }
            } else {
                return null;
            }
        } finally {
            rs.close();
            stmt.close();
        }
        // Извлекаем значение DEFAULT отдельно.
        processDefaults(conn, c, result);
        return result;
    } catch (SQLException e) {
        throw new CelestaException(e.getMessage());
    }
}
Also used : FloatingColumn(ru.curs.celesta.score.FloatingColumn) FloatingColumn(ru.curs.celesta.score.FloatingColumn) DateTimeColumn(ru.curs.celesta.score.DateTimeColumn) StringColumn(ru.curs.celesta.score.StringColumn) BooleanColumn(ru.curs.celesta.score.BooleanColumn) Column(ru.curs.celesta.score.Column) IntegerColumn(ru.curs.celesta.score.IntegerColumn) ZonedDateTimeColumn(ru.curs.celesta.score.ZonedDateTimeColumn) DecimalColumn(ru.curs.celesta.score.DecimalColumn) BinaryColumn(ru.curs.celesta.score.BinaryColumn) SQLException(java.sql.SQLException) PreparedStatement(java.sql.PreparedStatement) Statement(java.sql.Statement) ResultSet(java.sql.ResultSet) DbColumnInfo(ru.curs.celesta.dbutils.meta.DbColumnInfo) DecimalColumn(ru.curs.celesta.score.DecimalColumn) CelestaException(ru.curs.celesta.CelestaException)

Example 5 with Column

use of ru.curs.celesta.score.Column in project celesta by CourseOrchestra.

the class CursorGenerator method generateCursor.

/**
 * Generate code for schema (grain) element.
 * @param ge Schema (grain) element
 * @param scorePath path to CelestaSQL file
 */
public void generateCursor(GrainElement ge, String scorePath) {
    final String sourcePackage = calcSourcePackage(ge, scorePath);
    if (sourcePackage.isEmpty()) {
        throw new CelestaException("Couldn't generate class file for %s.%s without package", ge.getGrain().getName(), ge.getName());
    }
    final String className = calcClassName(ge);
    final String columnsClassName = "Columns";
    boolean isVersionedGe = ge instanceof VersionedElement && ((VersionedElement) ge).isVersioned();
    ClassName classType = ClassName.bestGuess(className);
    TypeSpec.Builder cursorClass = buildClassDefinition(ge, classType);
    ClassName columnsClassType = classType.nestedClass(columnsClassName);
    cursorClass.addFields(buildMetaFields(ge));
    cursorClass.addMethods(buildConstructors(ge, columnsClassType));
    // FIELDS
    if (ge instanceof DataGrainElement) {
        DataGrainElement dge = (DataGrainElement) ge;
        FieldSpec columnsField = buildColumnsField(columnsClassType);
        cursorClass.addField(columnsField);
        cursorClass.addInitializerBlock(buildColumnsFiledInitializer(columnsField));
        List<FieldSpec> fieldSpecs = buildDataFields(dge);
        cursorClass.addFields(fieldSpecs);
        cursorClass.addMethods(generateGettersAndSetters(fieldSpecs, classType));
        cursorClass.addMethod(buildGetFieldValue(dge.getColumns()));
        cursorClass.addMethod(buildSetFieldValue(dge.getColumns()));
        StringBuilder parseResultOverridingMethodNameBuilder = new StringBuilder("_parseResult");
        Set<Column<?>> pk = Collections.emptySet();
        if (dge instanceof TableElement && !(dge instanceof ReadOnlyTable)) {
            TableElement te = (TableElement) dge;
            pk = new LinkedHashSet<>(te.getPrimaryKey().values());
            cursorClass.addMethod(buildCurrentKeyValues(pk));
            cursorClass.addMethod(buildTryGet(pk));
            cursorClass.addMethod(buildGet(pk));
            if (te instanceof Table) {
                parseResultOverridingMethodNameBuilder.append("Internal");
            }
        }
        final Map<String, ? extends ColumnMeta<?>> columns = dge.getColumns();
        MethodSpec buildParseResultMethod = buildParseResult(columns, parseResultOverridingMethodNameBuilder.toString(), isVersionedGe);
        cursorClass.addMethod(buildParseResultMethod);
        cursorClass.addMethod(buildClearBuffer(columns, pk));
        cursorClass.addMethod(buildCurrentValues(columns));
        cursorClass.addType(buildCursorColumnsAsInnerStaticClass(dge, columnsClassType));
        if (dge instanceof BasicTable) {
            BasicTable t = (BasicTable) dge;
            if (t instanceof Table) {
                cursorClass.addMethods(buildCalcBlobs(columns, className));
                cursorClass.addMethod(buildSetAutoIncrement(columns));
                cursorClass.addMethods(buildTriggerRegistration(classType));
            }
            cursorClass.addTypes(buildOptionFieldsAsInnerStaticClasses(t.getColumns().values()));
        }
        cursorClass.addMethods(buildCompileCopying(ge, classType, columns.keySet(), isVersionedGe));
        cursorClass.addMethod(buildIterator(classType));
    }
    cursorClass.addMethods(buildGrainNameAndObjectName(ge));
    JavaFile javaFile = JavaFile.builder(sourcePackage, cursorClass.build()).skipJavaLangImports(true).indent("    ").build();
    try {
        javaFile.writeTo(srcDir);
    } catch (IOException e) {
        throw new RuntimeException(e);
    }
}
Also used : ReadOnlyTable(ru.curs.celesta.score.ReadOnlyTable) BasicTable(ru.curs.celesta.score.BasicTable) ReadOnlyTable(ru.curs.celesta.score.ReadOnlyTable) Table(ru.curs.celesta.score.Table) MethodSpec(com.squareup.javapoet.MethodSpec) IOException(java.io.IOException) CelestaException(ru.curs.celesta.CelestaException) DataGrainElement(ru.curs.celesta.score.DataGrainElement) FieldSpec(com.squareup.javapoet.FieldSpec) TableElement(ru.curs.celesta.score.TableElement) BasicTable(ru.curs.celesta.score.BasicTable) VersionedElement(ru.curs.celesta.score.VersionedElement) StringColumn(ru.curs.celesta.score.StringColumn) Column(ru.curs.celesta.score.Column) IntegerColumn(ru.curs.celesta.score.IntegerColumn) ZonedDateTimeColumn(ru.curs.celesta.score.ZonedDateTimeColumn) BinaryColumn(ru.curs.celesta.score.BinaryColumn) ClassName(com.squareup.javapoet.ClassName) JavaFile(com.squareup.javapoet.JavaFile) TypeSpec(com.squareup.javapoet.TypeSpec)

Aggregations

Column (ru.curs.celesta.score.Column)15 CelestaException (ru.curs.celesta.CelestaException)11 DbColumnInfo (ru.curs.celesta.dbutils.meta.DbColumnInfo)11 IntegerColumn (ru.curs.celesta.score.IntegerColumn)11 StringColumn (ru.curs.celesta.score.StringColumn)10 SQLException (java.sql.SQLException)9 Map (java.util.Map)9 DateTimeColumn (ru.curs.celesta.score.DateTimeColumn)9 BasicTable (ru.curs.celesta.score.BasicTable)8 IOException (java.io.IOException)7 Connection (java.sql.Connection)7 ResultSet (java.sql.ResultSet)7 HashMap (java.util.HashMap)7 BooleanColumn (ru.curs.celesta.score.BooleanColumn)7 DecimalColumn (ru.curs.celesta.score.DecimalColumn)7 TableElement (ru.curs.celesta.score.TableElement)7 VersionedElement (ru.curs.celesta.score.VersionedElement)7 BinaryColumn (ru.curs.celesta.score.BinaryColumn)6 List (java.util.List)5 Collectors (java.util.stream.Collectors)5