Мне нужно проверить изменения в некоторых объектах в нашем приложении, и я думаю об использовании JaVers. Мне нравится поддержка опроса данных аудита, предоставляемая JaVers. Hibernate Envers выглядит хорошо, но хранит данные в той же БД.
Вот мои требования:
- асинхронное ведение журнала — для минимального влияния на производительность
- хранить данные аудита в другом db - также причины производительности
Насколько я вижу, JaVers не предназначен для вышеперечисленного, но, похоже, его можно адаптировать для достижения вышеперечисленного. Вот как:
- JaVers фактически позволяет хранить данные в другой БД. Вы действительно можете обеспечить подключение к любой БД. Это не так, как это задумано, но это работает. Код ниже (обратите внимание на connectionProvider, который может обеспечить подключение к любой БД):
'
final Connection dbConnection =
DriverManager.getConnection("jdbc:mysql://localhost:3306/javers", "root", "root");
ConnectionProvider connectionProvider = new ConnectionProvider() {
@Override
public Connection getConnection() {
//suitable only for testing!
return dbConnection;
}
};
JaversSqlRepository sqlRepository = SqlRepositoryBuilder
.sqlRepository()
.withConnectionProvider(connectionProvider)
.withDialect(DialectName.MYSQL).build();
- The async can be achieved by moving the execution of the JaVers commit into a thread/executor. The challenge with that is that if the execution takes too long, it could be that the object changes before it's logged. There are 2 solutions I can think of here:
- we could create a snapshot of the object (e.g. serialize it to JSON or the like) and pass that to a Thread to log it.
- мы предоставляем собственную реализацию репозитория Javers, которая обрабатывает различия в текущем потоке, а затем передает объекты Snapshot для сохранения в другом потоке. Таким образом, мы будем выполнять только чтение из БД в потоке приложения и запись (что, как правило, более затратно с точки зрения производительности) в потоке аудита.
ВОПРОСЫ:
- я что-то пропустил здесь? Может ли это работать?
- Есть ли у JaVers поддержка создания моментального снимка объекта, который затем можно переместить в другой поток. Он делает это где-то внутри, так что, возможно, это то, что мы могли бы использовать.
ПРОСТО К СВЕДЕНИЮ: Не имеет отношения к вопросу, но вот некоторые другие проблемы, которые я могу придумать, и то, как я планирую их решить:
- из-за отсутствия аудита в той же транзакции, как если бы транзакция завершилась неудачей, это усложнило бы откат аудита. Поэтому нам нужно проверять только те объекты, которые были успешно зафиксированы. Я намерен сделать это, используя Hibernate Interceptor, прослушивая
afterTransactionCompletion
и фиксируя только объекты, обновленные этой транзакцией. - В случае лениво загруженных объектов я мог видеть, как, если мы пытаемся получить к ним доступ после завершения транзакции, может случиться так, что лениво загруженные реквизиты не могут быть доступны (поскольку сеанс также может быть закрыт) - don не знаю, как это исправить, но это может не быть проблемой, так как я думаю, что мы загружаем большинство нетерпеливых реквизитов.