Search in sources :

Example 6 with ForeignInfo

use of org.dbflute.dbmeta.info.ForeignInfo in project dbflute-core by dbflute.

the class TnRelationPropertyTypeImpl method createPropertyAccessor.

protected DfPropertyAccessor createPropertyAccessor(final DfPropertyDesc propertyDesc, TnBeanMetaData myBeanMetaData) {
    final DBMeta dbmeta = myBeanMetaData.getDBMeta();
    assertDBMetaExists(dbmeta, myBeanMetaData);
    final String propertyName = propertyDesc.getPropertyName();
    final ForeignInfo foreignInfo = dbmeta.hasForeign(propertyName) ? dbmeta.findForeignInfo(propertyName) : null;
    return new DfPropertyAccessor() {

        public String getPropertyName() {
            return foreignInfo != null ? foreignInfo.getForeignPropertyName() : propertyName;
        }

        public Class<?> getPropertyType() {
            return foreignInfo != null ? foreignInfo.getPropertyAccessType() : propertyDesc.getPropertyType();
        }

        public Class<?> getGenericType() {
            return propertyDesc.getGenericType();
        }

        public Object getValue(Object target) {
            if (foreignInfo != null && target instanceof Entity) {
                // basically here
                return foreignInfo.read((Entity) target);
            } else {
                return propertyDesc.getValue(target);
            }
        }

        public void setValue(Object target, Object value) {
            if (foreignInfo != null && target instanceof Entity) {
                // basically here
                foreignInfo.write((Entity) target, value);
            } else {
                propertyDesc.setValue(target, value);
            }
        }

        public boolean isReadable() {
            return propertyDesc.isReadable();
        }

        public boolean isWritable() {
            return propertyDesc.isWritable();
        }
    };
}
Also used : DfPropertyAccessor(org.dbflute.helper.beans.DfPropertyAccessor) ForeignInfo(org.dbflute.dbmeta.info.ForeignInfo) Entity(org.dbflute.Entity) DBMeta(org.dbflute.dbmeta.DBMeta)

Example 7 with ForeignInfo

use of org.dbflute.dbmeta.info.ForeignInfo in project dbflute-core by dbflute.

the class AbstractConditionBean method xdoSetupSelectDreamCruiseJourneyLogBook.

protected void xdoSetupSelectDreamCruiseJourneyLogBook() {
    // small waste exists but simple logic is best here
    final ConditionBean departurePort = xgetDreamCruiseDeparturePort();
    for (String relationPath : _dreamCruiseJourneyLogBook) {
        // e.g. _2_5
        final List<String> relNoExpList = Srl.splitList(relationPath, "_");
        final StringBuilder sb = new StringBuilder();
        DBMeta currentMeta = asDBMeta();
        int index = 0;
        for (String relNoExp : relNoExpList) {
            if ("".equals(relNoExp)) {
                continue;
            }
            final Integer relationNo = Integer.valueOf(relNoExp);
            final ForeignInfo foreignInfo = currentMeta.findForeignInfo(relationNo);
            final String foreignPropertyName = foreignInfo.getForeignPropertyName();
            if (index > 0) {
                sb.append(".");
            }
            sb.append(foreignPropertyName);
            currentMeta = foreignInfo.getForeignDBMeta();
            ++index;
        }
        departurePort.invokeSetupSelect(sb.toString());
    }
}
Also used : ForeignInfo(org.dbflute.dbmeta.info.ForeignInfo) DBMeta(org.dbflute.dbmeta.DBMeta)

Example 8 with ForeignInfo

use of org.dbflute.dbmeta.info.ForeignInfo in project dbflute-core by dbflute.

the class AbstractConditionQuery method xassertFCDP.

protected void xassertFCDP(String property, Map<String, Object> parameterMap) {
    // assertFixedConditionDynamicParameter()
    final ForeignInfo foreignInfo = xgetLocalDBMeta().findForeignInfo(property);
    xdoAssertFixedConditionDynamicParameter(property, foreignInfo, parameterMap);
}
Also used : ForeignInfo(org.dbflute.dbmeta.info.ForeignInfo)

Example 9 with ForeignInfo

use of org.dbflute.dbmeta.info.ForeignInfo in project dbflute-core by dbflute.

the class HpFixedConditionQueryResolver method resolveFixedInlineView.

// ===================================================================================
// Resolve Fixed InlineView
// ========================
public String resolveFixedInlineView(String foreignTableSqlName, boolean treatedAsInnerJoin) {
    // so it can uses bridge variables here
    if (_inlineViewResourceMap == null || _inlineViewResourceMap.isEmpty()) {
        // not uses InlineView
        return foreignTableSqlName;
    }
    // alias is required because foreignTableSqlName may be (normal) InlineView
    final String baseAlias = "dffixedbase";
    final String baseIndent;
    if (treatedAsInnerJoin) {
        // ----------"    inner join "
        baseIndent = "               ";
    } else {
        // ----------"    left outer join "
        baseIndent = "                    ";
    }
    final StringBuilder joinSb = new StringBuilder();
    final Map<ForeignInfo, String> relationMap = new HashMap<ForeignInfo, String>();
    final List<String> additionalRealColumnList = new ArrayList<String>();
    // basically not null
    final String resolvedFixedCondition = _resolvedFixedCondition;
    String optimizedCondition = _inlineViewOptimizedCondition;
    int groupIndex = 0;
    for (InlineViewResource resource : _inlineViewResourceMap.values()) {
        final List<ForeignInfo> joinInfoList = resource.getJoinInfoList();
        final String aliasBase = "dffixedjoin";
        String preForeignAlias = null;
        String foreignAlias = null;
        int joinIndex = 0;
        final Map<ForeignInfo, String> foreignAliasMap = new HashMap<ForeignInfo, String>(joinInfoList.size());
        for (ForeignInfo joinInfo : joinInfoList) {
            if (relationMap.containsKey(joinInfo)) {
                // already joined
                // update previous alias
                preForeignAlias = relationMap.get(joinInfo);
                continue;
            }
            final TableSqlName foreignTable;
            final String localAlias;
            {
                final DBMeta foreignDBMeta = joinInfo.getForeignDBMeta();
                foreignTable = foreignDBMeta.getTableSqlName();
                localAlias = (preForeignAlias != null ? preForeignAlias : baseAlias);
                foreignAlias = aliasBase + "_" + groupIndex + "_" + joinIndex;
                preForeignAlias = foreignAlias;
            }
            joinSb.append(ln()).append(baseIndent);
            joinSb.append("     left outer join ").append(foreignTable).append(" ").append(foreignAlias);
            joinSb.append(" on ");
            final Map<ColumnInfo, ColumnInfo> columnInfoMap = joinInfo.getLocalForeignColumnInfoMap();
            int columnIndex = 0;
            for (Entry<ColumnInfo, ColumnInfo> localForeignEntry : columnInfoMap.entrySet()) {
                final ColumnInfo localColumnInfo = localForeignEntry.getKey();
                final ColumnInfo foreignColumninfo = localForeignEntry.getValue();
                if (columnIndex > 0) {
                    joinSb.append(" and ");
                }
                joinSb.append(localAlias).append(".").append(localColumnInfo.getColumnSqlName());
                joinSb.append(" = ").append(foreignAlias).append(".").append(foreignColumninfo.getColumnSqlName());
                ++columnIndex;
            }
            foreignAliasMap.put(joinInfo, foreignAlias);
            relationMap.put(joinInfo, foreignAlias);
            ++joinIndex;
        }
        if (optimizedCondition != null) {
            optimizedCondition = resolvedOptimizedCondition(optimizedCondition, resource, foreignAliasMap);
        }
        collectAdditionalRealColumnList(additionalRealColumnList, resolvedFixedCondition, resource, foreignAlias);
        ++groupIndex;
    }
    if (optimizedCondition != null) {
        // foreign alias for in-line view is resolved here
        optimizedCondition = replaceString(optimizedCondition, getForeignAliasMark(), baseAlias);
        optimizedCondition = filterSubQueryIndentMark(optimizedCondition, false, true);
    }
    final StringBuilder sqlSb = new StringBuilder();
    sqlSb.append("(select ").append(baseAlias).append(".*");
    for (String columnName : additionalRealColumnList) {
        sqlSb.append(", ").append(columnName);
    }
    sqlSb.append(ln()).append(baseIndent);
    sqlSb.append("   from ").append(foreignTableSqlName).append(" ").append(baseAlias);
    sqlSb.append(joinSb);
    if (optimizedCondition != null) {
        buildOptimizedInlineWhereClause(optimizedCondition, baseIndent, sqlSb);
    }
    sqlSb.append(ln()).append(baseIndent);
    sqlSb.append(")");
    return sqlSb.toString();
}
Also used : HashMap(java.util.HashMap) LinkedHashMap(java.util.LinkedHashMap) ArrayList(java.util.ArrayList) ColumnInfo(org.dbflute.dbmeta.info.ColumnInfo) ForeignInfo(org.dbflute.dbmeta.info.ForeignInfo) DBMeta(org.dbflute.dbmeta.DBMeta) TableSqlName(org.dbflute.dbmeta.name.TableSqlName)

Example 10 with ForeignInfo

use of org.dbflute.dbmeta.info.ForeignInfo in project dbflute-core by dbflute.

the class HpFixedConditionQueryResolver method resolveOverRelation.

// ===================================================================================
// Resolve Over Relation
// =====================
protected String resolveOverRelation(String fixedCondition, boolean fixedInline) {
    // analyze:
    // - "$$over($localTable.memberSecurity)$$.REMINDER_QUESTION"
    // - "$$over($foreignTable.memberStatus, DISPLAY_ORDER)$$.ORDER_NO"
    // - "$$over(PURCHASE.product.productStatus)$$.PRODUCT_STATUS_NAME"
    final String relationBeginMark = getRelationBeginMark();
    final String relationEndMark = getRelationEndMark();
    String resolvedClause = fixedCondition;
    String remainder = resolvedClause;
    while (true) {
        // "|$$over(|$localTable.memberSecurity)$$.REMINDER_QUESTION"
        final IndexOfInfo relationBeginIndex = Srl.indexOfFirst(remainder, relationBeginMark);
        if (relationBeginIndex == null) {
            break;
        }
        remainder = relationBeginIndex.substringRear();
        // "$localTable.memberSecurity|)$$|.REMINDER_QUESTION"
        final IndexOfInfo relationEndIndex = Srl.indexOfFirst(remainder, relationEndMark);
        if (relationEndIndex == null) {
            break;
        }
        // remainder is e.g. "$localTable.memberSecurity)$$" now
        // e.g. "$localTable.memberSecurity" or "$foreignTable.memberStatus, DISPLAY_ORDER"
        final String relationExp = relationEndIndex.substringFront();
        // e.g. "$$over($localTable.memberSecurity)$$" or "$$over($foreignTable.memberStatus, DISPLAY_ORDER)$$"
        final String relationVariable = relationBeginMark + relationExp + relationEndMark;
        // e.g. "$localTable" or "$foreignTable" or "PURCHASE"
        final String pointTable;
        // e.g. "memberSecurity" or "product.productStatus" or null (means base only)
        final String targetRelation;
        // e.g. DISPLAY_ORDER or null (means no argument)
        final String secondArg;
        {
            final IndexOfInfo separatorIndex = Srl.indexOfFirst(relationExp, ".");
            if (separatorIndex != null) {
                // normally here
                // e.g. $localTable
                pointTable = separatorIndex.substringFrontTrimmed();
                final String separatorRear = separatorIndex.substringRearTrimmed();
                final IndexOfInfo argIndex = Srl.indexOfFirst(separatorRear, ",");
                targetRelation = argIndex != null ? argIndex.substringFrontTrimmed() : separatorRear;
                secondArg = argIndex != null ? argIndex.substringRearTrimmed() : null;
            } else {
                // e.g. "$$over(PURCHASE)$$"
                final IndexOfInfo argIndex = Srl.indexOfFirst(relationExp, ",");
                pointTable = argIndex != null ? argIndex.substringFrontTrimmed() : Srl.trim(relationExp);
                targetRelation = null;
                secondArg = argIndex != null ? argIndex.substringRearTrimmed() : null;
            }
        }
        final ConditionQuery relationPointCQ;
        final ConditionQuery columnTargetCQ;
        if (Srl.equalsPlain(pointTable, getLocalTableMark())) {
            // local table
            relationPointCQ = _localCQ;
            if (targetRelation != null) {
                columnTargetCQ = invokeColumnTargetCQ(relationPointCQ, targetRelation);
            } else {
                String notice = "The relation on fixed condition is required if the table is not referrer.";
                throwIllegalFixedConditionOverRelationException(notice, pointTable, null, fixedCondition);
                // unreachable
                return null;
            }
        } else if (Srl.equalsPlain(pointTable, getForeignTableMark())) {
            // foreign table
            relationPointCQ = _foreignCQ;
            columnTargetCQ = relationPointCQ;
            if (targetRelation == null) {
                String notice = "The relation on fixed condition is required if the table is not referrer.";
                throwIllegalFixedConditionOverRelationException(notice, pointTable, null, fixedCondition);
                // unreachable
                return null;
            }
            // prepare fixed InlineView
            if (_inlineViewResourceMap == null) {
                _inlineViewResourceMap = new LinkedHashMap<String, InlineViewResource>();
            }
            final InlineViewResource resource;
            if (_inlineViewResourceMap.containsKey(targetRelation)) {
                resource = _inlineViewResourceMap.get(targetRelation);
            } else {
                resource = new InlineViewResource();
                _inlineViewResourceMap.put(targetRelation, resource);
            }
            final String columnName;
            {
                // e.g. "$$over($localTable.memberSecurity)$$|.|REMINDER_QUESTION = ..."
                final IndexOfInfo rearIndex = Srl.indexOfFirst(relationEndIndex.substringRearTrimmed(), ".");
                if (rearIndex == null || rearIndex.getIndex() > 0) {
                    String notice = "The OverRelation variable should continue to column after the variable.";
                    throwIllegalFixedConditionOverRelationException(notice, pointTable, targetRelation, fixedCondition);
                    // unreachable
                    return null;
                }
                // e.g. REMINDER_QUESTION = ...
                final String columnStart = rearIndex.substringRear();
                final IndexOfInfo indexInfo = Srl.indexOfFirst(columnStart, " ", ",", ")", "\n", "\t");
                // REMINDER_QUESTION
                columnName = indexInfo != null ? indexInfo.substringFront() : columnStart;
            }
            // the secondArg should be a column DB name, and then rear column is alias name
            final String resolvedColumn = secondArg != null ? secondArg + " as " + columnName : columnName;
            // selected in in-line view
            resource.addAdditionalColumn(resolvedColumn);
            if (!resource.hasJoinInfo()) {
                // first analyze
                final List<String> traceList = Srl.splitList(targetRelation, ".");
                DBMeta currentDBMeta = _dbmetaProvider.provideDBMeta(_foreignCQ.asTableDbName());
                for (String trace : traceList) {
                    final ForeignInfo foreignInfo = currentDBMeta.findForeignInfo(trace);
                    resource.addJoinInfo(foreignInfo);
                    currentDBMeta = foreignInfo.getForeignDBMeta();
                }
            }
            final List<ForeignInfo> joinInfoList = resource.getJoinInfoList();
            if (!joinInfoList.isEmpty()) {
                // basically true (but just in case)
                final ForeignInfo latestForeignInfo = joinInfoList.get(joinInfoList.size() - 1);
                resource.addOptimizedVariable(relationVariable, latestForeignInfo);
            }
        } else {
            // referrer table
            final DBMeta pointDBMeta;
            try {
                pointDBMeta = _dbmetaProvider.provideDBMeta(pointTable);
            } catch (DBMetaNotFoundException e) {
                String notice = "The table for relation on fixed condition does not exist.";
                throwIllegalFixedConditionOverRelationException(notice, pointTable, targetRelation, fixedCondition, e);
                // unreachable
                return null;
            }
            ConditionQuery referrerQuery = _localCQ.xgetReferrerQuery();
            while (true) {
                if (referrerQuery == null) {
                    // means not found
                    break;
                }
                if (Srl.equalsPlain(pointDBMeta.getTableDbName(), referrerQuery.asTableDbName())) {
                    break;
                }
                referrerQuery = referrerQuery.xgetReferrerQuery();
            }
            relationPointCQ = referrerQuery;
            if (relationPointCQ == null) {
                String notice = "The table for relation on fixed condition was not found in the scope.";
                throwIllegalFixedConditionOverRelationException(notice, pointTable, targetRelation, fixedCondition);
                // unreachable
                return null;
            }
            if (targetRelation != null) {
                columnTargetCQ = invokeColumnTargetCQ(relationPointCQ, targetRelation);
            } else {
                columnTargetCQ = relationPointCQ;
            }
        }
        // resolve over-relation variables in clause
        // e.g. "dfrel_4"
        final String relationAlias = columnTargetCQ.xgetAliasName();
        resolvedClause = replaceString(resolvedClause, relationVariable, relationAlias);
        // after case for loop
        remainder = relationEndIndex.substringRear();
    // no replace even if same relation because of additional column
    // // to prevent from processing same one
    // remainder = replaceString(remainder, relationVariable, relationAlias);
    }
    resolvedClause = adjustOptimizedLine(resolvedClause);
    return resolvedClause;
}
Also used : ForeignInfo(org.dbflute.dbmeta.info.ForeignInfo) DBMeta(org.dbflute.dbmeta.DBMeta) IndexOfInfo(org.dbflute.util.Srl.IndexOfInfo) ConditionQuery(org.dbflute.cbean.ConditionQuery) ArrayList(java.util.ArrayList) List(java.util.List) DBMetaNotFoundException(org.dbflute.exception.DBMetaNotFoundException) LinkedHashMap(java.util.LinkedHashMap)

Aggregations

ForeignInfo (org.dbflute.dbmeta.info.ForeignInfo)20 DBMeta (org.dbflute.dbmeta.DBMeta)8 LinkedHashMap (java.util.LinkedHashMap)4 ColumnInfo (org.dbflute.dbmeta.info.ColumnInfo)4 ArrayList (java.util.ArrayList)3 RelationInfo (org.dbflute.dbmeta.info.RelationInfo)3 List (java.util.List)2 Method (java.lang.reflect.Method)1 HashMap (java.util.HashMap)1 Entity (org.dbflute.Entity)1 ConditionQuery (org.dbflute.cbean.ConditionQuery)1 FixedConditionResolver (org.dbflute.cbean.sqlclause.join.FixedConditionResolver)1 SelectedRelationColumn (org.dbflute.cbean.sqlclause.select.SelectedRelationColumn)1 TableSqlName (org.dbflute.dbmeta.name.TableSqlName)1 PropertyMethodFinder (org.dbflute.dbmeta.property.PropertyMethodFinder)1 DBMetaNotFoundException (org.dbflute.exception.DBMetaNotFoundException)1 DfPropertyAccessor (org.dbflute.helper.beans.DfPropertyAccessor)1 RelationOptionalFactory (org.dbflute.optional.RelationOptionalFactory)1 IndexOfInfo (org.dbflute.util.Srl.IndexOfInfo)1