Интерфейс SyncResolver
- Все суперинтерфейсы:
-
AutoCloseable,ResultSet,RowSet,Wrapper
public interface SyncResolver extends RowSet
Определяет фреймворк, который позволяет приложениям использовать дерево решений для принятия ручного решения о том, что следует сделать при возникновении конфликта синхронизации. Хотя приложениям не обязательно вручную разрешать конфликты синхронизации, этот фреймворк предоставляет средства для делегирования приложениям в случае возникновения конфликтов.
Обратите внимание, что конфликт — это ситуация, когда исходные значения объекта RowSet для строки не совпадают со значениями в источнике данных, что указывает на то, что строка источника данных была изменена с момента последней синхронизации. Также обратите внимание, что исходные значения объекта RowSet — это значения, которые у него были непосредственно перед последней синхронизацией, которые не обязательно являются его начальными значениями.
Описание объекта SyncResolver
Объект SyncResolver — это специализированный объект RowSet, который реализует интерфейс SyncResolver. Он может работать как подключенный объект RowSet (реализация интерфейса JdbcRowSet ) или подключенный объект RowSet (реализация интерфейса CachedRowSet или одного из его подинтерфейсов). Сведения о подинтерфейсах см. в описании пакета javax.sql.rowset. Реализация по умолчанию для объекта SyncResolver реализует интерфейс CachedRowSet, но другие реализации могут выбрать реализацию интерфейса JdbcRowSet для удовлетворения конкретных потребностей. После того, как приложение попыталось синхронизировать объект RowSet с источником данных (вызвав метод CachedRowSet acceptChanges) и были обнаружены один или несколько конфликтов, объект SyncProvider набора строк создаёт экземпляр SyncResolver. Этот новый объект SyncResolver имеет такое же количество строк и столбцов, что и объект RowSet , пытавшийся выполнить синхронизацию. Объект SyncResolver содержит значения из источника данных, которые вызвали конфликт(ы), и null для всех остальных значений. Кроме того, он содержит сведения обо всех конфликтах.
Получение и использование объекта SyncResolver
Когда метод acceptChanges обнаруживает конфликты, объект SyncProvider создаёт объект SyncProviderException и задаёт его с новым объектом SyncResolver. Метод acceptChanges будет выбрасывать это исключение, которое приложение может перехватить и использовать для извлечения объекта SyncResolver , который он содержит. В следующем фрагменте кода используется метод SyncProviderException getSyncResolver для получения объекта SyncResolver resolver. catch (SyncProviderException spe) {
SyncResolver resolver = spe.getSyncResolver();
...
}
} Получив resolver, приложение может использовать его для получения содержащейся в нём информации о конфликте или конфликтах. Объект SyncResolver , такой как resolver, отслеживает конфликты для каждой строки, в которой есть конфликт. Он также накладывает блокировку на таблицу или таблицы, затронутые командой набора строк, чтобы не допустить возникновения новых конфликтов во время разрешения текущих конфликтов.
Следующие типы информации можно получить из объекта SyncResolver:
Какая операция выполнялась при возникновении конфликта
ИнтерфейсSyncProvider определяет четыре константы, описывающие возможные состояния. Три константы описывают тип операции (обновление, удаление или вставка), которую пытался выполнить объект RowSet , когда был обнаружен конфликт, а четвёртая указывает на отсутствие конфликта. Эти константы являются возможными возвращаемыми значениями, когда объект SyncResolver вызывает метод getStatus. int operation = resolver.getStatus();
Значение в источнике данных, вызвавшее конфликт
Конфликт возникает, когда значение, которое изменил объектRowSet и пытается записать в источник данных, также было изменено в источнике данных с момента последней синхронизации. Приложение может вызвать метод SyncResolver getConflictValue для получения значения в источнике данных, являющегося причиной конфликта, так как значения в объекте SyncResolver представляют собой значения конфликтов из источника данных. java.lang.Object conflictValue = resolver.getConflictValue(2);Обратите внимание, что столбец в resolver можно указать по номеру столбца, как это делается в предшествующей строке кода, или по имени столбца.
Используя информацию, извлечённую из методов getStatus и getConflictValue, приложение может определить, какое значение должно быть сохранено в источнике данных. Затем приложение вызывает метод SyncResolver setResolvedValue, который устанавливает значение, подлежащее сохранению, в объект RowSet и также в источнике данных.
resolver.setResolvedValue("DEPT", 8390426); В предшествующей строке кода имя столбца обозначает столбец в объекте RowSet , который должен быть задан указанным значением. Номер столбца также можно использовать для обозначения столбца. Приложение вызывает метод setResolvedValue после разрешения всех конфликтов в текущей строке конфликта и повторяет этот процесс для каждой строки конфликта в объекте SyncResolver .
Перемещение по объекту SyncResolver
Поскольку объект SyncResolver является объектом RowSet, приложение может использовать все методы RowSet для перемещения курсора по объекту SyncResolver . Например, приложение может использовать метод RowSet next для перехода к каждой строке, а затем вызвать метод SyncResolver getStatus , чтобы проверить, содержит ли строка конфликт. В строке с одним или несколькими конфликтами приложение может перебирать столбцы для поиска любых значений, отличных от null, которые будут представлять собой значения из источника данных, находящиеся в конфликте. Для упрощения навигации по объекту SyncResolver , особенно при большом количестве строк без конфликтов, интерфейс SyncResolver определяет методы nextConflict и previousConflict, которые переходят только к строкам, содержащим по крайней мере одно значение конфликта. Затем приложение может вызвать метод SyncResolver getConflictValue, передав ему номер столбца, чтобы получить само значение конфликта. Фрагмент кода в следующем разделе приводит пример.
Пример кода
Следующий фрагмент кода демонстрирует, как отключенный объектRowSet crs может попытаться синхронизироваться с базовым источником данных, а затем разрешить конфликты. В блоке try crs вызывает метод acceptChanges, передавая ему объект Connection con. Если конфликтов нет, изменения в crs просто записываются в источник данных. Однако если конфликт есть, метод acceptChanges выбрасывает объект SyncProviderException, и срабатывает блок catch. В этом примере, который демонстрирует один из многих способов использования объекта SyncResolver, используется метод SyncResolver nextConflict в цикле while. Цикл завершится, когда nextConflict вернёт false, что произойдёт, когда больше не останется строк конфликтов в объекте SyncResolver resolver. В этом конкретном фрагменте кода resolver ищет строки с конфликтами обновления (строки со статусом SyncResolver.UPDATE_ROW_CONFLICT), и остальная часть этого фрагмента кода выполняется только для строк, где произошли конфликты, потому что crs пытался выполнить обновление. После того, как курсор для resolver переместился в следующую строку конфликта, имеющую конфликт обновления, метод getRow указывает номер текущей строки, и курсор для объекта CachedRowSet crs перемещается в аналогичную строку в crs. Перебирая столбцы этой строки в resolver и crs, можно извлечь значения конфликта и сравнить их, чтобы определить, какое из них следует сохранить. В этом фрагменте кода значение в crs устанавливается в качестве разрешённого значения, что означает, что оно будет использовано для перезаписи значения конфликта в источнике данных.
try {
crs.acceptChanges(con);
} catch (SyncProviderException spe) {
SyncResolver resolver = spe.getSyncResolver();
Object crsValue; // value in the RowSet object
Object resolverValue: // value in the SyncResolver object
Object resolvedValue: // value to be persisted
while(resolver.nextConflict()) {
if(resolver.getStatus() == SyncResolver.UPDATE_ROW_CONFLICT) {
int row = resolver.getRow();
crs.absolute(row);
int colCount = crs.getMetaData().getColumnCount();
for(int j = 1; j <= colCount; j++) {
if (resolver.getConflictValue(j) != null) {
crsValue = crs.getObject(j);
resolverValue = resolver.getConflictValue(j);
. . .
// compare crsValue and resolverValue to determine
// which should be the resolved value (the value to persist)
resolvedValue = crsValue;
resolver.setResolvedValue(j, resolvedValue);
}
}
}
}
}
- С тех пор как:
- 1.5
Поля
| Модификатор и тип | Поле | Описание |
|---|---|---|
static int | DELETE_ROW_CONFLICT | Указывает, что конфликт произошёл, когда объект |
static int | INSERT_ROW_CONFLICT | Указывает, что конфликт произошёл, когда объект |
static int | NO_ROW_CONFLICT | Указывает, что никакого конфликта не произошло, когда объект |
static int | UPDATE_ROW_CONFLICT | Указывает, что конфликт произошёл, когда объект |
Поля, объявленные в интерфейсе java.sql.ResultSet
CLOSE_CURSORS_AT_COMMIT, CONCUR_READ_ONLY, CONCUR_UPDATABLE, FETCH_FORWARD, FETCH_REVERSE, FETCH_UNKNOWN, HOLD_CURSORS_OVER_COMMIT, TYPE_FORWARD_ONLY, TYPE_SCROLL_INSENSITIVE, TYPE_SCROLL_SENSITIVE Методы
| Модификатор и тип | Метод | Описание |
|---|---|---|
Object | getConflictValue(int index) | Возвращает значение в указанном столбце в текущей строке этого объекта |
Object | getConflictValue(String columnName) | Возвращает значение в указанном столбце в текущей строке этого объекта |
int | getStatus() | Возвращает состояние конфликта текущей строки этого объекта |
boolean | nextConflict() | Перемещает курсор вниз из текущего положения на следующую строку, содержащую значение конфликта. |
boolean | previousConflict() | Перемещает курсор вверх из текущего положения на предыдущую строку конфликта в этом объекте |
void | setResolvedValue(int index,
Object obj) | Устанавливает obj в качестве значения в столбце index в текущей строке объекта |
void | setResolvedValue(String columnName,
Object obj) | Устанавливает obj в качестве значения в столбце columnName в текущей строке объекта |
Методы, объявленные в интерфейсе java.sql.ResultSet
absolute, afterLast, beforeFirst, cancelRowUpdates, clearWarnings, close, deleteRow, findColumn, first, getArray, getArray, getAsciiStream, getAsciiStream, getBigDecimal, getBigDecimal, getBigDecimal, getBigDecimal, getBinaryStream, getBinaryStream, getBlob, getBlob, getBoolean, getBoolean, getByte, getByte, getBytes, getBytes, getCharacterStream, getCharacterStream, getClob, getClob, getConcurrency, getCursorName, getDate, getDate, getDate, getDate, getDouble, getDouble, getFetchDirection, getFetchSize, getFloat, getFloat, getHoldability, getInt, getInt, getLong, getLong, getMetaData, getNCharacterStream, getNCharacterStream, getNClob, getNClob, getNString, getNString, getObject, getObject, getObject, getObject, getObject, getObject, getRef, getRef, getRow, getRowId, getRowId, getShort, getShort, getSQLXML, getSQLXML, getStatement, getString, getString, getTime, getTime, getTime, getTime, getTimestamp, getTimestamp, getTimestamp, getTimestamp, getType, getUnicodeStream, getUnicodeStream, getURL, getURL, getWarnings, insertRow, isAfterLast, isBeforeFirst, isClosed, isFirst, isLast, last, moveToCurrentRow, moveToInsertRow, next, previous, refreshRow, relative, rowDeleted, rowInserted, rowUpdated, setFetchDirection, setFetchSize, updateArray, updateArray, updateAsciiStream, updateAsciiStream, updateAsciiStream, updateAsciiStream, updateAsciiStream, updateAsciiStream, updateBigDecimal, updateBigDecimal, updateBinaryStream, updateBinaryStream, updateBinaryStream, updateBinaryStream, updateBinaryStream, updateBinaryStream, updateBlob, updateBlob, updateBlob, updateBlob, updateBlob, updateBlob, updateBoolean, updateBoolean, updateByte, updateByte, updateBytes, updateBytes, updateCharacterStream, updateCharacterStream, updateCharacterStream, updateCharacterStream, updateCharacterStream, updateCharacterStream, updateClob, updateClob, updateClob, updateClob, updateClob, updateClob, updateDate, updateDate, updateDouble, updateDouble, updateFloat, updateFloat, updateInt, updateInt, updateLong, updateLong, updateNCharacterStream, updateNCharacterStream, updateNCharacterStream, updateNCharacterStream, updateNClob, updateNClob, updateNClob, updateNClob, updateNClob, updateNClob, updateNString, updateNString, updateNull, updateNull, updateObject, updateObject, updateObject, updateObject, updateObject, updateObject, updateObject, updateObject, updateRef, updateRef, updateRow, updateRowId, updateRowId, updateShort, updateShort, updateSQLXML, updateSQLXML, updateString, updateString, updateTime, updateTime, updateTimestamp, updateTimestamp, wasNull Методы, объявленные в интерфейсе javax.sql.RowSet
addRowSetListener, clearParameters, execute, getCommand, getDataSourceName, getEscapeProcessing, getMaxFieldSize, getMaxRows, getPassword, getQueryTimeout, getTransactionIsolation, getTypeMap, getUrl, getUsername, isReadOnly, removeRowSetListener, setArray, setAsciiStream, setAsciiStream, setAsciiStream, setAsciiStream, setBigDecimal, setBigDecimal, setBinaryStream, setBinaryStream, setBinaryStream, setBinaryStream, setBlob, setBlob, setBlob, setBlob, setBlob, setBlob, setBoolean, setBoolean, setByte, setByte, setBytes, setBytes, setCharacterStream, setCharacterStream, setCharacterStream, setCharacterStream, setClob, setClob, setClob, setClob, setClob, setClob, setCommand, setConcurrency, setDataSourceName, setDate, setDate, setDate, setDate, setDouble, setDouble, setEscapeProcessing, setFloat, setFloat, setInt, setInt, setLong, setLong, setMaxFieldSize, setMaxRows, setNCharacterStream, setNCharacterStream, setNCharacterStream, setNCharacterStream, setNClob, setNClob, setNClob, setNClob, setNClob, setNClob, setNString, setNString, setNull, setNull, setNull, setNull, setObject, setObject, setObject, setObject, setObject, setObject, setPassword, setQueryTimeout, setReadOnly, setRef, setRowId, setRowId, setShort, setShort, setSQLXML, setSQLXML, setString, setString, setTime, setTime, setTime, setTime, setTimestamp, setTimestamp, setTimestamp, setTimestamp, setTransactionIsolation, setType, setTypeMap, setUrl, setURL, setUsername Методы, объявленные в интерфейсе java.sql.Wrapper
isWrapperFor, unwrap Поля
UPDATE_ROW_CONFLICT
static final int UPDATE_ROW_CONFLICT
Указывает, что конфликт произошел во время попытки объекта RowSet обновить строку в источнике данных. Значения в строке источника данных для обновления отличаются от исходных значений объекта RowSet для этой строки, что означает, что строка в источнике данных была обновлена или удалена с момента последней синхронизации.
- См. также:
- Постоянные значения поля
DELETE_ROW_CONFLICT
static final int DELETE_ROW_CONFLICT
Указывает, что конфликт произошел во время попытки объекта RowSet удалить строку в источнике данных. Значения в строке источника данных для обновления отличаются от исходных значений объекта RowSet для этой строки, что означает, что строка в источнике данных была обновлена или удалена с момента последней синхронизации.
- См. также:
- Постоянные значения поля
INSERT_ROW_CONFLICT
static final int INSERT_ROW_CONFLICT
Указывает, что конфликт произошел во время попытки объекта RowSet вставить строку в источник данных. Это означает, что строка с таким же первичным ключом, как и строка для вставки, была вставлена в источник данных с момента последней синхронизации.
- См. также:
- Постоянные значения поля
NO_ROW_CONFLICT
static final int NO_ROW_CONFLICT
Указывает, что не произошло конфликта во время попытки объекта RowSet обновить, удалить или вставить строку в источник данных. Значения в объекте SyncResolver будут содержать значения null только как указание на то, что информация, относящаяся к разрешению конфликта в этой строке, отсутствует.
- См. также:
- Постоянные значения поля
Методы
getStatus
int getStatus()
Возвращает состояние конфликта текущей строки этого объекта SyncResolver, которое указывает на операцию, которую объект RowSet пытался выполнить при возникновении конфликта.
- Возвращает:
- одно из следующих констант:
SyncResolver.UPDATE_ROW_CONFLICT,SyncResolver.DELETE_ROW_CONFLICT,SyncResolver.INSERT_ROW_CONFLICT, илиSyncResolver.NO_ROW_CONFLICT
getConflictValue
Object getConflictValue(int index)
throws SQLException Возвращает значение в указанном столбце в текущей строке этого объекта SyncResolver, которое является значением в источнике данных, вызвавшем конфликт.
- Параметры:
-
index- целое число, определяющее столбец в этой строке объектаSyncResolverдля получения значения, вызвавшего конфликт - Возвращает:
- значение указанного столбца в текущей строке объекта
SyncResolver - Исключения:
-
SQLException- если произошла ошибка доступа к базе данных
getConflictValue
Object getConflictValue(String columnName)
throws SQLException Возвращает значение в указанном столбце в текущей строке этого объекта SyncResolver, которое является значением в источнике данных, вызвавшем конфликт.
- Параметры:
-
columnName- объект String, определяющий столбец в этой строке объектаSyncResolverдля получения значения, вызвавшего конфликт - Возвращает:
- значение указанного столбца в текущей строке объекта
SyncResolver - Исключения:
-
SQLException- если произошла ошибка доступа к базе данных
setResolvedValue
void setResolvedValue(int index,
Object obj)
throws SQLException Устанавливает obj в качестве значения в столбце index в текущей строке объекта RowSet, который синхронизируется. obj устанавливается как значение в источнике данных внутри.
- Параметры:
-
index- целое число, определяющее номер столбца, в который нужно установить значение для сохранения -
obj- объект, представляющий значение, которое нужно установить в объектеRowSetи сохранить в источнике данных - Исключения:
-
SQLException- если произошла ошибка доступа к базе данных
setResolvedValue
void setResolvedValue(String columnName,
Object obj)
throws SQLException Устанавливает obj в качестве значения в столбце columnName в текущей строке объекта RowSet, который синхронизируется. obj устанавливается как значение в источнике данных внутри.
- Параметры:
-
columnName- объект String, определяющий имя столбца, в который нужно установить значение для сохранения -
obj- объект, представляющий значение, которое нужно установить в объектеRowSetи сохранить в источнике данных - Исключения:
-
SQLException- если произошла ошибка доступа к базе данных
nextConflict
boolean nextConflict()
throws SQLException Перемещает курсор вниз из текущего положения на следующую строку, содержащую значение конфликта. Курсор объекта SyncResolver изначально расположен перед первой строкой конфликта; первый вызов метода nextConflict делает первую строку конфликта текущей строкой; второй вызов делает вторую строку конфликта текущей строкой и так далее.
Вызов метода nextConflict неявно закрывает поток ввода, если он открыт, и очищает цепочку предупреждений объекта SyncResolver.
- Возвращает:
-
trueесли новая текущая строка допустима;falseесли больше нет строк - Исключения:
-
SQLException- если произошла ошибка доступа к базе данных или тип набора результатовTYPE_FORWARD_ONLY
previousConflict
boolean previousConflict()
throws SQLException Перемещает курсор вверх из текущего положения на предыдущую строку конфликта в этом объекте SyncResolver.
Вызов метода previousConflict неявно закрывает поток ввода, если он открыт, и очищает цепочку предупреждений объекта SyncResolver.
- Возвращает:
-
trueесли курсор находится на допустимой строке;falseесли он за пределами набора результатов - Исключения:
-
SQLException- если произошла ошибка доступа к базе данных или тип набора результатовTYPE_FORWARD_ONLY
© 1993, 2020, Oracle and/or its affiliates. All rights reserved.
Documentation extracted from Debian's OpenJDK Development Kit package.
Licensed under the GNU General Public License, version 2, with the Classpath Exception.
Various third party code in OpenJDK is licensed under different licenses (see Debian package).
Java and OpenJDK are trademarks or registered trademarks of Oracle and/or its affiliates.
https://docs.oracle.com/en/java/javase/11/docs/api/java.sql.rowset/javax/sql/rowset/spi/SyncResolver.html