diff options
author | Stefan Winkler | 2009-07-15 10:31:17 +0000 |
---|---|---|
committer | Stefan Winkler | 2009-07-15 10:31:17 +0000 |
commit | 7f249e39e14a013aa81a3f3cb0cd4ac4e5af9732 (patch) | |
tree | 47e35bef1225f15aa368853a354d7a088ceb805c | |
parent | 060296c6ad18ca0a2953e0976f15ee9ed2d98522 (diff) | |
download | cdo-7f249e39e14a013aa81a3f3cb0cd4ac4e5af9732.tar.gz cdo-7f249e39e14a013aa81a3f3cb0cd4ac4e5af9732.tar.xz cdo-7f249e39e14a013aa81a3f3cb0cd4ac4e5af9732.zip |
[249610] [DB] Support external references (Implementation)
https://bugs.eclipse.org/bugs/show_bug.cgi?id=249610
10 files changed, 434 insertions, 67 deletions
diff --git a/plugins/org.eclipse.emf.cdo.server.db/src/org/eclipse/emf/cdo/server/db/CDODBUtil.java b/plugins/org.eclipse.emf.cdo.server.db/src/org/eclipse/emf/cdo/server/db/CDODBUtil.java index f3c03ade60..afde3adbbb 100644 --- a/plugins/org.eclipse.emf.cdo.server.db/src/org/eclipse/emf/cdo/server/db/CDODBUtil.java +++ b/plugins/org.eclipse.emf.cdo.server.db/src/org/eclipse/emf/cdo/server/db/CDODBUtil.java @@ -8,12 +8,12 @@ * Contributors: * Eike Stepper - initial API and implementation * Stefan Winkler - 271444: [DB] Multiple refactorings - * https://bugs.eclipse.org/bugs/show_bug.cgi?id=271444 - * + * Stefan Winkler - 249610: [DB] Support external references (Implementation) */ package org.eclipse.emf.cdo.server.db; import org.eclipse.emf.cdo.common.id.CDOID; +import org.eclipse.emf.cdo.common.id.CDOIDExternal; import org.eclipse.emf.cdo.common.id.CDOIDUtil; import org.eclipse.emf.cdo.server.db.mapping.IMappingStrategy; import org.eclipse.emf.cdo.server.internal.db.DBStore; @@ -120,27 +120,32 @@ public final class CDODBUtil } /** - * Get the long value of a CDOID (by delegating to {@link CDOIDUtil#getLong(org.eclipse.emf.cdo.common.id.CDOID)}) In - * addition, provide a check for external IDs which are not supported by the DBStore - * - * @param id - * the ID to convert to long - * @return the long value of the ID - * @throws IllegalArgumentException - * if the ID is not convertibla - * @since 2.0 + * @since 3.0 */ - public static long getLong(CDOID id) + public static long convertCDOIDToLong(IExternalReferenceManager manager, IDBStoreAccessor accessor, CDOID id) { - if (id != null && id.getType() == CDOID.Type.EXTERNAL_OBJECT) + if (id.getType() == CDOID.Type.EXTERNAL_OBJECT) { - throw new IllegalArgumentException("DBStore does not support external references: " + id); //$NON-NLS-1$ + return manager.mapExternalReference(accessor, (CDOIDExternal)id); } return CDOIDUtil.getLong(id); } /** + * @since 3.0 + */ + public static CDOID convertLongToCDOID(IExternalReferenceManager manager, IDBStoreAccessor accessor, long id) + { + if (id < 0) + { + return manager.unmapExternalReference(accessor, id); + } + + return CDOIDUtil.createLong(id); + } + + /** * Execute update on the given prepared statement and handle common cases of return values. * * @param stmt diff --git a/plugins/org.eclipse.emf.cdo.server.db/src/org/eclipse/emf/cdo/server/db/IDBStore.java b/plugins/org.eclipse.emf.cdo.server.db/src/org/eclipse/emf/cdo/server/db/IDBStore.java index 0613a904f4..16650ea480 100644 --- a/plugins/org.eclipse.emf.cdo.server.db/src/org/eclipse/emf/cdo/server/db/IDBStore.java +++ b/plugins/org.eclipse.emf.cdo.server.db/src/org/eclipse/emf/cdo/server/db/IDBStore.java @@ -8,7 +8,7 @@ * Contributors: * Eike Stepper - initial API and implementation * Stefan Winkler - 271444: [DB] Multiple refactorings - * https://bugs.eclipse.org/bugs/show_bug.cgi?id=271444 + * Stefan Winkler - 249610: [DB] Support external references (Implementation) */ package org.eclipse.emf.cdo.server.db; @@ -41,19 +41,26 @@ public interface IDBStore extends IStore public IDBConnectionProvider getDBConnectionProvider(); /** + * Get the meta data manager associated with this DBStore. + * * @since 2.0 */ - public IDBStoreAccessor getReader(ISession session); + public IMetaDataManager getMetaDataManager(); + + /** + * Get the manager for external references. + * + * @since 3.0 + */ + public IExternalReferenceManager getExternalReferenceManager(); /** * @since 2.0 */ - public IDBStoreAccessor getWriter(ITransaction transaction); + public IDBStoreAccessor getReader(ISession session); /** - * Get the meta data manager associated with this DBStore. - * * @since 2.0 */ - public IMetaDataManager getMetaDataManager(); + public IDBStoreAccessor getWriter(ITransaction transaction); } diff --git a/plugins/org.eclipse.emf.cdo.server.db/src/org/eclipse/emf/cdo/server/db/IExternalReferenceManager.java b/plugins/org.eclipse.emf.cdo.server.db/src/org/eclipse/emf/cdo/server/db/IExternalReferenceManager.java new file mode 100644 index 0000000000..729a38d5de --- /dev/null +++ b/plugins/org.eclipse.emf.cdo.server.db/src/org/eclipse/emf/cdo/server/db/IExternalReferenceManager.java @@ -0,0 +1,36 @@ +/** + * Copyright (c) 2004 - 2009 Eike Stepper (Berlin, Germany) and others. + * All rights reserved. This program and the accompanying materials + * are made available under the terms of the Eclipse Public License v1.0 + * which accompanies this distribution, and is available at + * http://www.eclipse.org/legal/epl-v10.html + * + * Contributors: + * Stefan Winkler - initial API and implementation + * Stefan Winkler - bug 249610: [DB] Support external references (Implementation) + * Eike Stepper - maintenance + */ +package org.eclipse.emf.cdo.server.db; + +import org.eclipse.emf.cdo.common.id.CDOIDExternal; + +/** + * @author Stefan Winkler + * @since 3.0 + */ +public interface IExternalReferenceManager +{ + public long mapExternalReference(IDBStoreAccessor accessor, CDOIDExternal id); + + public CDOIDExternal unmapExternalReference(IDBStoreAccessor accessor, long mappedId); + + /** + * @author Eike Stepper + */ + public interface Internal extends IExternalReferenceManager + { + public IDBStore getStore(); + + public void setStore(IDBStore store); + } +} diff --git a/plugins/org.eclipse.emf.cdo.server.db/src/org/eclipse/emf/cdo/server/internal/db/CDODBSchema.java b/plugins/org.eclipse.emf.cdo.server.db/src/org/eclipse/emf/cdo/server/internal/db/CDODBSchema.java index 3fa7e2888f..07b8b3e9aa 100644 --- a/plugins/org.eclipse.emf.cdo.server.db/src/org/eclipse/emf/cdo/server/internal/db/CDODBSchema.java +++ b/plugins/org.eclipse.emf.cdo.server.db/src/org/eclipse/emf/cdo/server/internal/db/CDODBSchema.java @@ -1,13 +1,14 @@ /** - * Copyright (c) 2004 - 2009 Eike Stepper (Berlin, Germany) and others. + * Copyright (c) 2004 - 2009 Eike Stepper (Berlin, Germany) and others. * All rights reserved. This program and the accompanying materials * are made available under the terms of the Eclipse Public License v1.0 * which accompanies this distribution, and is available at * http://www.eclipse.org/legal/epl-v10.html - * + * * Contributors: * Eike Stepper - initial API and implementation * Stefan Winkler - 271444: [DB] Multiple refactorings https://bugs.eclipse.org/bugs/show_bug.cgi?id=271444 + * Stefan Winkler - 249610: [DB] Support external references (Implementation) * */ package org.eclipse.emf.cdo.server.internal.db; @@ -98,6 +99,23 @@ public class CDODBSchema extends DBSchema PACKAGE_INFOS.addIndex(IDBIndex.Type.NON_UNIQUE, PACKAGE_INFOS_UNIT); /** + * DBTable cdo_external_refs + */ + public static final IDBTable EXTERNAL_REFS = INSTANCE.addTable("cdo_external_refs"); //$NON-NLS-1$ + + public static final IDBField EXTERNAL_ID = // + EXTERNAL_REFS.addField("id", DBType.BIGINT); //$NON-NLS-1$ + + public static final IDBField EXTERNAL_URI = // + EXTERNAL_REFS.addField("uri", DBType.VARCHAR); //$NON-NLS-1$ + + public static final IDBIndex INDEX_EXTERNAL_REFS_ID = // + EXTERNAL_REFS.addIndex(IDBIndex.Type.PRIMARY_KEY, EXTERNAL_ID); + + public static final IDBIndex INDEX_EXTERNAL_REFS_HASH = // + EXTERNAL_REFS.addIndex(IDBIndex.Type.NON_UNIQUE, EXTERNAL_URI); + + /** * Name of object table */ public static final String CDO_OBJECTS = "cdo_objects"; //$NON-NLS-1$ diff --git a/plugins/org.eclipse.emf.cdo.server.db/src/org/eclipse/emf/cdo/server/internal/db/DBStore.java b/plugins/org.eclipse.emf.cdo.server.db/src/org/eclipse/emf/cdo/server/internal/db/DBStore.java index 9de67bcd32..1f86c6765b 100644 --- a/plugins/org.eclipse.emf.cdo.server.db/src/org/eclipse/emf/cdo/server/internal/db/DBStore.java +++ b/plugins/org.eclipse.emf.cdo.server.db/src/org/eclipse/emf/cdo/server/internal/db/DBStore.java @@ -9,6 +9,7 @@ * Eike Stepper - initial API and implementation * Stefan Winkler - https://bugs.eclipse.org/bugs/show_bug.cgi?id=259402 * Stefan Winkler - 271444: [DB] Multiple refactorings https://bugs.eclipse.org/bugs/show_bug.cgi?id=271444 + * Stefan Winkler - 249610: [DB] Support external references (Implementation) */ package org.eclipse.emf.cdo.server.internal.db; @@ -16,6 +17,7 @@ import org.eclipse.emf.cdo.server.ISession; import org.eclipse.emf.cdo.server.ITransaction; import org.eclipse.emf.cdo.server.IView; import org.eclipse.emf.cdo.server.db.IDBStore; +import org.eclipse.emf.cdo.server.db.IExternalReferenceManager; import org.eclipse.emf.cdo.server.db.IMetaDataManager; import org.eclipse.emf.cdo.server.db.mapping.IMappingStrategy; import org.eclipse.emf.cdo.server.internal.db.bundle.OM; @@ -60,6 +62,10 @@ public class DBStore extends LongIDStore implements IDBStore private IDBConnectionProvider dbConnectionProvider; + private IMetaDataManager metaDataManager; + + private IExternalReferenceManager.Internal externalReferenceManager; + @ExcludeFromDump private transient ProgressDistributor accessorWriteDistributor = new ProgressDistributor.Geometric() { @@ -82,8 +88,6 @@ public class DBStore extends LongIDStore implements IDBStore @ExcludeFromDump private transient StoreAccessorPool writerPool = new StoreAccessorPool(this, null); - private transient IMetaDataManager metaDataManager; - public DBStore() { super(TYPE, set(ChangeFormat.REVISION, ChangeFormat.DELTA), // @@ -129,6 +133,27 @@ public class DBStore extends LongIDStore implements IDBStore dbConnectionProvider = DBUtil.createConnectionProvider(dataSource); } + public IMetaDataManager getMetaDataManager() + { + return metaDataManager; + } + + public IExternalReferenceManager getExternalReferenceManager() + { + return externalReferenceManager; + } + + @Override + public Set<ChangeFormat> getSupportedChangeFormats() + { + if (mappingStrategy.hasDeltaSupport()) + { + return set(ChangeFormat.DELTA); + } + + return set(ChangeFormat.REVISION); + } + public ProgressDistributor getAccessorWriteDistributor() { return accessorWriteDistributor; @@ -242,6 +267,10 @@ public class DBStore extends LongIDStore implements IDBStore reStart(connection); } + externalReferenceManager = createExternalReferenceManager(); + externalReferenceManager.setStore(this); + LifecycleUtil.activate(externalReferenceManager); + connection.commit(); } finally @@ -314,6 +343,9 @@ public class DBStore extends LongIDStore implements IDBStore LifecycleUtil.deactivate(metaDataManager); metaDataManager = null; + LifecycleUtil.deactivate(externalReferenceManager); + externalReferenceManager = null; + try { connection = getConnection(); @@ -355,6 +387,11 @@ public class DBStore extends LongIDStore implements IDBStore super.doDeactivate(); } + protected IExternalReferenceManager.Internal createExternalReferenceManager() + { + return new ExternalReferenceManager(); + } + protected IDBSchema createSchema() { String name = getRepository().getName(); @@ -370,22 +407,4 @@ public class DBStore extends LongIDStore implements IDBStore { return System.currentTimeMillis(); } - - public IMetaDataManager getMetaDataManager() - { - return metaDataManager; - } - - @Override - public Set<ChangeFormat> getSupportedChangeFormats() - { - if (mappingStrategy.hasDeltaSupport()) - { - return set(ChangeFormat.DELTA); - } - else - { - return set(ChangeFormat.REVISION); - } - } } diff --git a/plugins/org.eclipse.emf.cdo.server.db/src/org/eclipse/emf/cdo/server/internal/db/ExternalReferenceManager.java b/plugins/org.eclipse.emf.cdo.server.db/src/org/eclipse/emf/cdo/server/internal/db/ExternalReferenceManager.java new file mode 100644 index 0000000000..2bbfcac381 --- /dev/null +++ b/plugins/org.eclipse.emf.cdo.server.db/src/org/eclipse/emf/cdo/server/internal/db/ExternalReferenceManager.java @@ -0,0 +1,245 @@ +/** + * Copyright (c) 2004 - 2009 Eike Stepper (Berlin, Germany) and others. + * All rights reserved. This program and the accompanying materials + * are made available under the terms of the Eclipse Public License v1.0 + * which accompanies this distribution, and is available at + * http://www.eclipse.org/legal/epl-v10.html + * + * Contributors: + * Stefan Winkler - initial API and implementation + * Stefan Winkler - bug 249610: [DB] Support external references (Implementation) + * Eike Stepper - maintenance + */ +package org.eclipse.emf.cdo.server.internal.db; + +import org.eclipse.emf.cdo.common.id.CDOIDExternal; +import org.eclipse.emf.cdo.common.id.CDOIDUtil; +import org.eclipse.emf.cdo.server.db.CDODBUtil; +import org.eclipse.emf.cdo.server.db.IDBStore; +import org.eclipse.emf.cdo.server.db.IDBStoreAccessor; +import org.eclipse.emf.cdo.server.db.IExternalReferenceManager; +import org.eclipse.emf.cdo.server.db.IPreparedStatementCache.ReuseProbability; +import org.eclipse.emf.cdo.server.internal.db.bundle.OM; + +import org.eclipse.net4j.db.DBException; +import org.eclipse.net4j.db.DBUtil; +import org.eclipse.net4j.util.ReflectUtil.ExcludeFromDump; +import org.eclipse.net4j.util.lifecycle.Lifecycle; +import org.eclipse.net4j.util.lifecycle.LifecycleUtil; + +import java.sql.Connection; +import java.sql.PreparedStatement; +import java.sql.ResultSet; +import java.sql.SQLException; +import java.sql.Statement; +import java.util.concurrent.atomic.AtomicLong; + +/** + * @author Stefan Winkler + */ +public class ExternalReferenceManager extends Lifecycle implements IExternalReferenceManager.Internal +{ + private IDBStore store; + + private AtomicLong lastMappedId = new AtomicLong(0); + + @ExcludeFromDump + private transient String sqlSelectByLongId; + + @ExcludeFromDump + private transient String sqlSelectByURI; + + @ExcludeFromDump + private transient String sqlInsert; + + public ExternalReferenceManager() + { + } + + public IDBStore getStore() + { + return store; + } + + public void setStore(IDBStore store) + { + this.store = store; + } + + public long mapExternalReference(IDBStoreAccessor accessor, CDOIDExternal id) + { + String uri = id.getURI(); + long result = lookupByID(accessor, uri); + if (result < 0) + { + // mapping found + return result; + } + + return insertNew(accessor, uri); + } + + public CDOIDExternal unmapExternalReference(IDBStoreAccessor accessor, long mappedId) + { + PreparedStatement stmt = null; + ResultSet rs = null; + + try + { + stmt = accessor.getStatementCache().getPreparedStatement(sqlSelectByLongId, ReuseProbability.HIGH); + stmt.setLong(1, mappedId); + rs = stmt.executeQuery(); + + if (!rs.next()) + { + OM.LOG.error("External ID " + mappedId + " not found. Database inconsistent!"); + throw new IllegalStateException("External ID " + mappedId + " not found. Database inconsistent!"); + } + + String uri = rs.getString(1); + return CDOIDUtil.createExternal(uri); + } + catch (SQLException e) + { + throw new DBException(e); + } + finally + { + DBUtil.close(rs); + accessor.getStatementCache().releasePreparedStatement(stmt); + } + } + + @Override + protected void doBeforeActivate() throws Exception + { + super.doBeforeActivate(); + checkState(store, "Store is not set"); + } + + @Override + protected void doActivate() throws Exception + { + super.doActivate(); + IDBStoreAccessor reader = getStore().getReader(null); + Connection connection = reader.getConnection(); + Statement statement = null; + + try + { + String sql = "SELECT MIN(" + CDODBSchema.EXTERNAL_ID + ") FROM " + CDODBSchema.EXTERNAL_REFS; + + statement = connection.createStatement(); + ResultSet result = statement.executeQuery(sql); + + if (result.next()) + { + lastMappedId.set(result.getLong(1)); + } + + // else: resultSet is empty => table is empty + // and lastMappedId stays 0 - as initialized. + } + catch (SQLException ex) + { + throw new DBException(ex); + } + finally + { + DBUtil.close(statement); + LifecycleUtil.deactivate(reader); // Don't let the null-context accessor go to the pool! + } + + sqlInsert = "INSERT INTO " + CDODBSchema.EXTERNAL_REFS + " VALUES (?,?,?)"; //$NON-NLS-1$ //$NON-NLS-2$ + StringBuilder builder = new StringBuilder(); + builder.append("INSERT INTO "); + builder.append(CDODBSchema.EXTERNAL_REFS); + builder.append("("); + builder.append(CDODBSchema.EXTERNAL_ID); + builder.append(","); + builder.append(CDODBSchema.EXTERNAL_URI); + builder.append(") VALUES (?,?)"); + + sqlInsert = builder.toString(); + + builder = new StringBuilder(); + builder.append("SELECT "); //$NON-NLS-1$ + builder.append(CDODBSchema.EXTERNAL_ID); + builder.append(" FROM "); //$NON-NLS-1$ + builder.append(CDODBSchema.EXTERNAL_REFS); + builder.append(" WHERE "); //$NON-NLS-1$ + builder.append(CDODBSchema.EXTERNAL_URI); + builder.append(" =? "); //$NON-NLS-1$ + + sqlSelectByURI = builder.toString(); + + builder = new StringBuilder(); + builder.append("SELECT "); //$NON-NLS-1$ + builder.append(CDODBSchema.EXTERNAL_URI); + builder.append(" FROM "); //$NON-NLS-1$ + builder.append(CDODBSchema.EXTERNAL_REFS); + builder.append(" WHERE "); //$NON-NLS-1$ + builder.append(CDODBSchema.EXTERNAL_ID); + builder.append(" =? "); //$NON-NLS-1$ + + sqlSelectByLongId = builder.toString(); + } + + private long insertNew(IDBStoreAccessor accessor, String uri) + { + long newMappedId = lastMappedId.decrementAndGet(); + + PreparedStatement stmt = null; + + try + { + stmt = accessor.getStatementCache().getPreparedStatement(sqlInsert, ReuseProbability.MEDIUM); + stmt.setLong(1, newMappedId); + stmt.setString(2, uri); + + CDODBUtil.sqlUpdate(stmt, true); + return newMappedId; + } + catch (SQLException e) + { + throw new DBException(e); + } + finally + { + accessor.getStatementCache().releasePreparedStatement(stmt); + } + } + + private long lookupByID(IDBStoreAccessor accessor, String uri) + { + PreparedStatement stmt = null; + ResultSet rs = null; + + try + { + stmt = accessor.getStatementCache().getPreparedStatement(sqlSelectByURI, ReuseProbability.HIGH); + stmt.setString(1, uri); + + rs = stmt.executeQuery(); + + if (rs.next()) + { + return rs.getLong(1); + } + else + { + // not found ... + return 0; + } + } + catch (SQLException e) + { + throw new DBException(e); + } + finally + { + DBUtil.close(rs); + accessor.getStatementCache().releasePreparedStatement(stmt); + } + } +} diff --git a/plugins/org.eclipse.emf.cdo.server.db/src/org/eclipse/emf/cdo/server/internal/db/mapping/TypeMapping.java b/plugins/org.eclipse.emf.cdo.server.db/src/org/eclipse/emf/cdo/server/internal/db/mapping/TypeMapping.java index 9d7289896c..afd8e4bea0 100644 --- a/plugins/org.eclipse.emf.cdo.server.db/src/org/eclipse/emf/cdo/server/internal/db/mapping/TypeMapping.java +++ b/plugins/org.eclipse.emf.cdo.server.db/src/org/eclipse/emf/cdo/server/internal/db/mapping/TypeMapping.java @@ -15,8 +15,11 @@ package org.eclipse.emf.cdo.server.internal.db.mapping; import org.eclipse.emf.cdo.common.id.CDOID; -import org.eclipse.emf.cdo.common.id.CDOIDUtil; +import org.eclipse.emf.cdo.server.IStoreAccessor; +import org.eclipse.emf.cdo.server.StoreThreadLocal; import org.eclipse.emf.cdo.server.db.CDODBUtil; +import org.eclipse.emf.cdo.server.db.IDBStoreAccessor; +import org.eclipse.emf.cdo.server.db.IExternalReferenceManager; import org.eclipse.emf.cdo.server.db.mapping.IMappingStrategy; import org.eclipse.emf.cdo.server.db.mapping.ITypeMapping; import org.eclipse.emf.cdo.server.internal.db.DBAnnotation; @@ -69,6 +72,16 @@ public abstract class TypeMapping implements ITypeMapping dbType = type; } + public final IMappingStrategy getMappingStrategy() + { + return mappingStrategy; + } + + public final EStructuralFeature getFeature() + { + return feature; + } + public final void setValueFromRevision(PreparedStatement stmt, int index, InternalCDORevision revision) throws SQLException { @@ -122,11 +135,6 @@ public abstract class TypeMapping implements ITypeMapping return value; } - public final EStructuralFeature getFeature() - { - return feature; - } - protected final Object getRevisionValue(InternalCDORevision revision) { return revision.getValue(getFeature()); @@ -257,13 +265,26 @@ public abstract class TypeMapping implements ITypeMapping return null; } - return CDOIDUtil.createLong(id); + IExternalReferenceManager externalRefs = getMappingStrategy().getStore().getExternalReferenceManager(); + return CDODBUtil.convertLongToCDOID(externalRefs, getAccessor(), id); } @Override protected void doSetValue(PreparedStatement stmt, int index, Object value) throws SQLException { - super.doSetValue(stmt, index, CDODBUtil.getLong((CDOID)value)); + super.doSetValue(stmt, index, CDODBUtil.convertCDOIDToLong(getMappingStrategy().getStore() + .getExternalReferenceManager(), getAccessor(), (CDOID)value)); + } + + private IDBStoreAccessor getAccessor() + { + IStoreAccessor accessor = StoreThreadLocal.getAccessor(); + if (accessor == null) + { + throw new IllegalStateException("Can only be called from within a valid IDBStoreAccessor context"); + } + + return (IDBStoreAccessor)accessor; } } diff --git a/plugins/org.eclipse.emf.cdo.server.db/src/org/eclipse/emf/cdo/server/internal/db/mapping/horizontal/AbstractHorizontalClassMapping.java b/plugins/org.eclipse.emf.cdo.server.db/src/org/eclipse/emf/cdo/server/internal/db/mapping/horizontal/AbstractHorizontalClassMapping.java index ae68e0dd13..39b3f55e5a 100644 --- a/plugins/org.eclipse.emf.cdo.server.db/src/org/eclipse/emf/cdo/server/internal/db/mapping/horizontal/AbstractHorizontalClassMapping.java +++ b/plugins/org.eclipse.emf.cdo.server.db/src/org/eclipse/emf/cdo/server/internal/db/mapping/horizontal/AbstractHorizontalClassMapping.java @@ -8,15 +8,17 @@ * Contributors: * Eike Stepper - initial API and implementation * Stefan Winkler - 271444: [DB] Multiple refactorings https://bugs.eclipse.org/bugs/show_bug.cgi?id=271444 + * Stefan Winkler - 249610: [DB] Support external references (Implementation) */ package org.eclipse.emf.cdo.server.internal.db.mapping.horizontal; import org.eclipse.emf.cdo.common.id.CDOID; -import org.eclipse.emf.cdo.common.id.CDOIDUtil; import org.eclipse.emf.cdo.common.model.CDOModelUtil; import org.eclipse.emf.cdo.common.revision.CDORevision; import org.eclipse.emf.cdo.eresource.EresourcePackage; +import org.eclipse.emf.cdo.server.db.CDODBUtil; import org.eclipse.emf.cdo.server.db.IDBStoreAccessor; +import org.eclipse.emf.cdo.server.db.IExternalReferenceManager; import org.eclipse.emf.cdo.server.db.IMetaDataManager; import org.eclipse.emf.cdo.server.db.mapping.IClassMapping; import org.eclipse.emf.cdo.server.db.mapping.IListMapping; @@ -143,9 +145,11 @@ public abstract class AbstractHorizontalClassMapping implements IClassMapping * @return <code>true</code> if the revision has been read successfully.<br> * <code>false</code> if the revision does not exist in the DB. */ - protected final boolean readValuesFromStatement(PreparedStatement pstmt, InternalCDORevision revision) + protected final boolean readValuesFromStatement(PreparedStatement pstmt, InternalCDORevision revision, + IDBStoreAccessor accessor) { ResultSet resultSet = null; + try { if (TRACER.isEnabled()) @@ -160,7 +164,7 @@ public abstract class AbstractHorizontalClassMapping implements IClassMapping { if (TRACER.isEnabled()) { - TRACER.format("Resultset was empty."); //$NON-NLS-1$ + TRACER.format("Resultset was empty"); //$NON-NLS-1$ } return false; @@ -170,10 +174,10 @@ public abstract class AbstractHorizontalClassMapping implements IClassMapping revision.setVersion(resultSet.getInt(i++)); revision.setCreated(resultSet.getLong(i++)); revision.setRevised(resultSet.getLong(i++)); - revision.setResourceID(CDOIDUtil.createLong(resultSet.getLong(i++))); - - // TODO add mapping for external container CDOIDs here -> - revision.setContainerID(CDOIDUtil.createLong(resultSet.getLong(i++))); + revision.setResourceID(CDODBUtil.convertLongToCDOID(getExternalReferenceManager(), accessor, resultSet + .getLong(i++))); + revision.setContainerID(CDODBUtil.convertLongToCDOID(getExternalReferenceManager(), accessor, resultSet + .getLong(i++))); revision.setContainingFeatureID(resultSet.getInt(i++)); for (ITypeMapping mapping : valueMappings) @@ -228,6 +232,11 @@ public abstract class AbstractHorizontalClassMapping implements IClassMapping return getMappingStrategy().getStore().getMetaDataManager(); } + protected final IExternalReferenceManager getExternalReferenceManager() + { + return mappingStrategy.getStore().getExternalReferenceManager(); + } + protected final IMappingStrategy getMappingStrategy() { return mappingStrategy; diff --git a/plugins/org.eclipse.emf.cdo.server.db/src/org/eclipse/emf/cdo/server/internal/db/mapping/horizontal/HorizontalAuditClassMapping.java b/plugins/org.eclipse.emf.cdo.server.db/src/org/eclipse/emf/cdo/server/internal/db/mapping/horizontal/HorizontalAuditClassMapping.java index 91c2dbdb32..b60f8bbb0d 100644 --- a/plugins/org.eclipse.emf.cdo.server.db/src/org/eclipse/emf/cdo/server/internal/db/mapping/horizontal/HorizontalAuditClassMapping.java +++ b/plugins/org.eclipse.emf.cdo.server.db/src/org/eclipse/emf/cdo/server/internal/db/mapping/horizontal/HorizontalAuditClassMapping.java @@ -8,6 +8,7 @@ * Contributors: * Eike Stepper - initial API and implementation * Stefan Winkler - major refactoring + * Stefan Winkler - 249610: [DB] Support external references (Implementation) */ package org.eclipse.emf.cdo.server.internal.db.mapping.horizontal; @@ -161,6 +162,7 @@ public class HorizontalAuditClassMapping extends AbstractHorizontalClassMapping int listChunk) { PreparedStatement pstmt = null; + try { pstmt = accessor.getStatementCache().getPreparedStatement(sqlSelectAttributesByTime, ReuseProbability.MEDIUM); @@ -169,7 +171,7 @@ public class HorizontalAuditClassMapping extends AbstractHorizontalClassMapping pstmt.setLong(3, timeStamp); // Read singleval-attribute table always (even without modeled attributes!) - boolean success = readValuesFromStatement(pstmt, revision); + boolean success = readValuesFromStatement(pstmt, revision, accessor); // Read multival tables only if revision exists if (success) @@ -200,7 +202,7 @@ public class HorizontalAuditClassMapping extends AbstractHorizontalClassMapping pstmt.setInt(2, version); // Read singleval-attribute table always (even without modeled attributes!) - boolean success = readValuesFromStatement(pstmt, revision); + boolean success = readValuesFromStatement(pstmt, revision, accessor); // Read multival tables only if revision exists if (success) @@ -319,7 +321,7 @@ public class HorizontalAuditClassMapping extends AbstractHorizontalClassMapping pstmt.setLong(1, CDOIDUtil.getLong(revision.getID())); // Read singleval-attribute table always (even without modeled attributes!) - boolean success = readValuesFromStatement(pstmt, revision); + boolean success = readValuesFromStatement(pstmt, revision, accessor); // Read multival tables only if revision exists if (success) @@ -355,8 +357,10 @@ public class HorizontalAuditClassMapping extends AbstractHorizontalClassMapping stmt.setLong(col++, accessor.getStore().getMetaDataManager().getMetaID(revision.getEClass())); stmt.setLong(col++, revision.getCreated()); stmt.setLong(col++, revision.getRevised()); - stmt.setLong(col++, CDOIDUtil.getLong(revision.getResourceID())); - stmt.setLong(col++, CDODBUtil.getLong((CDOID)revision.getContainerID())); + stmt.setLong(col++, CDODBUtil.convertCDOIDToLong(getExternalReferenceManager(), accessor, revision + .getResourceID())); + stmt.setLong(col++, CDODBUtil.convertCDOIDToLong(getExternalReferenceManager(), accessor, (CDOID)revision + .getContainerID())); stmt.setInt(col++, revision.getContainingFeatureID()); for (ITypeMapping mapping : getValueMappings()) diff --git a/plugins/org.eclipse.emf.cdo.server.db/src/org/eclipse/emf/cdo/server/internal/db/mapping/horizontal/HorizontalNonAuditClassMapping.java b/plugins/org.eclipse.emf.cdo.server.db/src/org/eclipse/emf/cdo/server/internal/db/mapping/horizontal/HorizontalNonAuditClassMapping.java index 786cff0a73..77b44ce6f9 100644 --- a/plugins/org.eclipse.emf.cdo.server.db/src/org/eclipse/emf/cdo/server/internal/db/mapping/horizontal/HorizontalNonAuditClassMapping.java +++ b/plugins/org.eclipse.emf.cdo.server.db/src/org/eclipse/emf/cdo/server/internal/db/mapping/horizontal/HorizontalNonAuditClassMapping.java @@ -8,6 +8,7 @@ * Contributors: * Eike Stepper - initial API and implementation * Stefan Winkler - major refactoring + * Stefan Winkler - 249610: [DB] Support external references (Implementation) */ package org.eclipse.emf.cdo.server.internal.db.mapping.horizontal; @@ -192,8 +193,10 @@ public class HorizontalNonAuditClassMapping extends AbstractHorizontalClassMappi stmt.setLong(col++, accessor.getStore().getMetaDataManager().getMetaID(revision.getEClass())); stmt.setLong(col++, revision.getCreated()); stmt.setLong(col++, revision.getRevised()); - stmt.setLong(col++, CDOIDUtil.getLong(revision.getResourceID())); - stmt.setLong(col++, CDODBUtil.getLong((CDOID)revision.getContainerID())); + stmt.setLong(col++, CDODBUtil.convertCDOIDToLong(getExternalReferenceManager(), accessor, revision + .getResourceID())); + stmt.setLong(col++, CDODBUtil.convertCDOIDToLong(getExternalReferenceManager(), accessor, (CDOID)revision + .getContainerID())); stmt.setInt(col++, revision.getContainingFeatureID()); for (ITypeMapping mapping : getValueMappings()) @@ -295,7 +298,7 @@ public class HorizontalNonAuditClassMapping extends AbstractHorizontalClassMappi pstmt.setLong(1, CDOIDUtil.getLong(revision.getID())); // Read singleval-attribute table always (even without modeled attributes!) - boolean success = readValuesFromStatement(pstmt, revision); + boolean success = readValuesFromStatement(pstmt, revision, accessor); // Read multival tables only if revision exists if (success) @@ -486,8 +489,8 @@ public class HorizontalNonAuditClassMapping extends AbstractHorizontalClassMappi stmt.setInt(col++, newVersion); stmt.setLong(col++, created); - stmt.setLong(col++, CDODBUtil.getLong(newResourceId)); - stmt.setLong(col++, CDODBUtil.getLong(newContainerId)); + stmt.setLong(col++, CDODBUtil.convertCDOIDToLong(getExternalReferenceManager(), accessor, newResourceId)); + stmt.setLong(col++, CDODBUtil.convertCDOIDToLong(getExternalReferenceManager(), accessor, newContainerId)); stmt.setInt(col++, newContainingFeatureId); for (Pair<ITypeMapping, Object> change : attributeChanges) |