mirror of
https://github.com/OPM/ResInsight.git
synced 2024-12-29 10:21:54 -06:00
Add tool used to extract project file revisions from project file database
* Add tool used to extract project file versions from database * Delete old records from backup to limit number of records to 50
This commit is contained in:
parent
a55b53c725
commit
96481d81a8
@ -66,11 +66,40 @@ bool insertContent( const QString& content )
|
|||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
//--------------------------------------------------------------------------------------------------
|
||||||
|
///
|
||||||
|
//--------------------------------------------------------------------------------------------------
|
||||||
|
bool deleteOldRecords( int maximumRecordCount )
|
||||||
|
{
|
||||||
|
QSqlQuery countQuery( "SELECT COUNT(*) FROM file_versions" );
|
||||||
|
if ( !countQuery.exec() || !countQuery.next() )
|
||||||
|
{
|
||||||
|
RiaLogging::error( "Error counting records: " + countQuery.lastError().text() );
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
int count = countQuery.value( 0 ).toInt();
|
||||||
|
int recordsToDelete = count - maximumRecordCount;
|
||||||
|
if ( recordsToDelete <= 0 ) return true;
|
||||||
|
|
||||||
|
QSqlQuery query;
|
||||||
|
query.prepare( "DELETE FROM file_versions WHERE id IN (SELECT id FROM file_versions ORDER BY timestamp ASC LIMIT :limit)" );
|
||||||
|
query.bindValue( ":limit", recordsToDelete );
|
||||||
|
|
||||||
|
if ( !query.exec() )
|
||||||
|
{
|
||||||
|
QString txt = "Error deleting old records:" + query.lastError().text();
|
||||||
|
RiaLogging::error( txt );
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
//--------------------------------------------------------------------------------------------------
|
//--------------------------------------------------------------------------------------------------
|
||||||
///
|
///
|
||||||
//--------------------------------------------------------------------------------------------------
|
//--------------------------------------------------------------------------------------------------
|
||||||
bool appendTextToDatabase( const QString& databaseFilePath, const QString& content )
|
bool appendTextToDatabase( const QString& databaseFilePath, int maximumRecordCount, const QString& content )
|
||||||
{
|
{
|
||||||
const QString databaseType = "QSQLITE";
|
const QString databaseType = "QSQLITE";
|
||||||
|
|
||||||
@ -101,6 +130,8 @@ bool appendTextToDatabase( const QString& databaseFilePath, const QString& conte
|
|||||||
db.setDatabaseName( databaseFilePath );
|
db.setDatabaseName( databaseFilePath );
|
||||||
|
|
||||||
if ( !createTableIfNeeded() ) return false;
|
if ( !createTableIfNeeded() ) return false;
|
||||||
|
if ( !deleteOldRecords( maximumRecordCount ) ) return false;
|
||||||
|
|
||||||
if ( !insertContent( content ) ) return false;
|
if ( !insertContent( content ) ) return false;
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
|
@ -25,5 +25,5 @@
|
|||||||
//==================================================================================================
|
//==================================================================================================
|
||||||
namespace RiaProjectBackupTools
|
namespace RiaProjectBackupTools
|
||||||
{
|
{
|
||||||
bool appendTextToDatabase( const QString& databaseFilePath, const QString& content );
|
bool appendTextToDatabase( const QString& databaseFilePath, int maximumRecordCount, const QString& content );
|
||||||
}
|
} // namespace RiaProjectBackupTools
|
||||||
|
@ -416,8 +416,9 @@ bool RimProject::writeProjectFile()
|
|||||||
|
|
||||||
if ( RiaPreferences::current()->storeBackupOfProjectFiles() )
|
if ( RiaPreferences::current()->storeBackupOfProjectFiles() )
|
||||||
{
|
{
|
||||||
QString backupFilename = fileName + "db";
|
QString backupFilename = fileName + "db";
|
||||||
RiaProjectBackupTools::appendTextToDatabase( backupFilename, content );
|
const int maximumRecordCount = 50;
|
||||||
|
RiaProjectBackupTools::appendTextToDatabase( backupFilename, maximumRecordCount, content );
|
||||||
}
|
}
|
||||||
|
|
||||||
distributePathsFromGlobalPathList();
|
distributePathsFromGlobalPathList();
|
||||||
|
@ -989,6 +989,11 @@ else(OCTAVE_MKOCTFILE)
|
|||||||
)
|
)
|
||||||
endif(OCTAVE_MKOCTFILE)
|
endif(OCTAVE_MKOCTFILE)
|
||||||
|
|
||||||
|
add_subdirectory(ThirdParty/extract-projectfile-versions)
|
||||||
|
install(TARGETS extract-projectfile-versions
|
||||||
|
DESTINATION ${RESINSIGHT_INSTALL_FOLDER}
|
||||||
|
)
|
||||||
|
|
||||||
# ##############################################################################
|
# ##############################################################################
|
||||||
# Visual Studio : Create the ruleset file to be used by Static Code Analysis
|
# Visual Studio : Create the ruleset file to be used by Static Code Analysis
|
||||||
# https://stackoverflow.com/questions/75031903/how-to-enable-static-analysis-with-custom-ruleset-in-msvc-via-cmakelists-txt
|
# https://stackoverflow.com/questions/75031903/how-to-enable-static-analysis-with-custom-ruleset-in-msvc-via-cmakelists-txt
|
||||||
|
78
ThirdParty/extract-projectfile-versions/.clang-format
vendored
Normal file
78
ThirdParty/extract-projectfile-versions/.clang-format
vendored
Normal file
@ -0,0 +1,78 @@
|
|||||||
|
---
|
||||||
|
Language: Cpp
|
||||||
|
# BasedOnStyle: LLVM
|
||||||
|
AccessModifierOffset: -4
|
||||||
|
AlignAfterOpenBracket: Align
|
||||||
|
AlignConsecutiveAssignments: true
|
||||||
|
AlignConsecutiveDeclarations: true
|
||||||
|
AlignEscapedNewlinesLeft: true
|
||||||
|
AlignOperands: true
|
||||||
|
AlignTrailingComments: false
|
||||||
|
AllowAllParametersOfDeclarationOnNextLine: false
|
||||||
|
AllowShortBlocksOnASingleLine: false
|
||||||
|
AllowShortCaseLabelsOnASingleLine: false
|
||||||
|
AllowShortIfStatementsOnASingleLine: true
|
||||||
|
AllowShortFunctionsOnASingleLine: InlineOnly
|
||||||
|
AllowShortLoopsOnASingleLine: false
|
||||||
|
AlwaysBreakAfterDefinitionReturnType: None
|
||||||
|
AlwaysBreakAfterReturnType: None
|
||||||
|
AlwaysBreakBeforeMultilineStrings: false
|
||||||
|
AlwaysBreakTemplateDeclarations: true
|
||||||
|
BinPackArguments: false
|
||||||
|
BinPackParameters: false
|
||||||
|
BreakBeforeBinaryOperators: None
|
||||||
|
BreakBeforeBraces: Allman
|
||||||
|
BreakBeforeTernaryOperators: true
|
||||||
|
BreakConstructorInitializersBeforeComma: true
|
||||||
|
BreakAfterJavaFieldAnnotations: false
|
||||||
|
BreakStringLiterals: true
|
||||||
|
ColumnLimit: 140
|
||||||
|
CommentPragmas: "^ IWYU pragma:"
|
||||||
|
ConstructorInitializerAllOnOneLineOrOnePerLine: false
|
||||||
|
ConstructorInitializerIndentWidth: 4
|
||||||
|
ContinuationIndentWidth: 4
|
||||||
|
Cpp11BracedListStyle: true
|
||||||
|
DerivePointerAlignment: false
|
||||||
|
DisableFormat: false
|
||||||
|
ForEachMacros: [foreach, Q_FOREACH, BOOST_FOREACH]
|
||||||
|
IncludeCategories:
|
||||||
|
- Regex: '^"(llvm|llvm-c|clang|clang-c)/'
|
||||||
|
Priority: 2
|
||||||
|
- Regex: '^(<|"(gtest|isl|json)/)'
|
||||||
|
Priority: 3
|
||||||
|
- Regex: ".*"
|
||||||
|
Priority: 1
|
||||||
|
IncludeIsMainRegex: "$"
|
||||||
|
IndentCaseLabels: true
|
||||||
|
IndentWidth: 4
|
||||||
|
IndentWrappedFunctionNames: true
|
||||||
|
JavaScriptQuotes: Leave
|
||||||
|
KeepEmptyLinesAtTheStartOfBlocks: false
|
||||||
|
MacroBlockBegin: ""
|
||||||
|
MacroBlockEnd: ""
|
||||||
|
MaxEmptyLinesToKeep: 1
|
||||||
|
NamespaceIndentation: Inner
|
||||||
|
PenaltyBreakAssignment: 13
|
||||||
|
PenaltyBreakBeforeFirstCallParameter: 10000
|
||||||
|
PenaltyBreakComment: 20
|
||||||
|
PenaltyBreakFirstLessLess: 12
|
||||||
|
PenaltyBreakString: 100
|
||||||
|
PenaltyExcessCharacter: 5
|
||||||
|
PenaltyReturnTypeOnItsOwnLine: 30
|
||||||
|
PointerAlignment: Left
|
||||||
|
ReflowComments: true
|
||||||
|
SortIncludes: true
|
||||||
|
SpaceAfterCStyleCast: false
|
||||||
|
SpaceAfterTemplateKeyword: true
|
||||||
|
SpaceBeforeAssignmentOperators: true
|
||||||
|
SpaceBeforeParens: ControlStatements
|
||||||
|
SpaceInEmptyParentheses: false
|
||||||
|
SpacesBeforeTrailingComments: 1
|
||||||
|
SpacesInAngles: false
|
||||||
|
SpacesInContainerLiterals: false
|
||||||
|
SpacesInCStyleCastParentheses: false
|
||||||
|
SpacesInParentheses: true
|
||||||
|
SpacesInSquareBrackets: false
|
||||||
|
Standard: c++20
|
||||||
|
TabWidth: 4
|
||||||
|
UseTab: Never
|
24
ThirdParty/extract-projectfile-versions/CMakeLists.txt
vendored
Normal file
24
ThirdParty/extract-projectfile-versions/CMakeLists.txt
vendored
Normal file
@ -0,0 +1,24 @@
|
|||||||
|
cmake_minimum_required(VERSION 3.5)
|
||||||
|
project(extract-projectfile-versions)
|
||||||
|
|
||||||
|
set(CMAKE_CXX_STANDARD 20)
|
||||||
|
set(CMAKE_INCLUDE_CURRENT_DIR ON)
|
||||||
|
set(CMAKE_AUTOMOC ON)
|
||||||
|
set(CMAKE_AUTORCC ON)
|
||||||
|
set(CMAKE_AUTOUIC ON)
|
||||||
|
|
||||||
|
find_package(Qt5 COMPONENTS Core Sql REQUIRED)
|
||||||
|
|
||||||
|
add_executable(extract-projectfile-versions main.cpp)
|
||||||
|
|
||||||
|
target_link_libraries(extract-projectfile-versions Qt5::Core Qt5::Sql)
|
||||||
|
|
||||||
|
if(MSVC)
|
||||||
|
add_custom_command(
|
||||||
|
TARGET extract-projectfile-versions
|
||||||
|
POST_BUILD
|
||||||
|
COMMAND ${CMAKE_COMMAND} -E copy $<TARGET_RUNTIME_DLLS:extract-projectfile-versions>
|
||||||
|
$<TARGET_FILE_DIR:extract-projectfile-versions>
|
||||||
|
COMMAND_EXPAND_LISTS
|
||||||
|
)
|
||||||
|
endif(MSVC)
|
135
ThirdParty/extract-projectfile-versions/main.cpp
vendored
Normal file
135
ThirdParty/extract-projectfile-versions/main.cpp
vendored
Normal file
@ -0,0 +1,135 @@
|
|||||||
|
#include <QCommandLineParser>
|
||||||
|
#include <QCoreApplication>
|
||||||
|
#include <QDateTime>
|
||||||
|
#include <QDebug>
|
||||||
|
#include <QDir>
|
||||||
|
#include <QFile>
|
||||||
|
#include <QFileInfo>
|
||||||
|
#include <QSqlDatabase>
|
||||||
|
#include <QSqlError>
|
||||||
|
#include <QSqlQuery>
|
||||||
|
|
||||||
|
//--------------------------------------------------------------------------------------------------
|
||||||
|
///
|
||||||
|
//--------------------------------------------------------------------------------------------------
|
||||||
|
std::vector<std::pair<QDateTime, QString>> getAllContent()
|
||||||
|
{
|
||||||
|
std::vector<std::pair<QDateTime, QString>> content;
|
||||||
|
|
||||||
|
QSqlQuery query;
|
||||||
|
|
||||||
|
query.prepare( "SELECT timestamp, content FROM file_versions" );
|
||||||
|
if ( !query.exec() )
|
||||||
|
{
|
||||||
|
qDebug() << "Error retrieving content:" << query.lastError().text();
|
||||||
|
return content;
|
||||||
|
}
|
||||||
|
|
||||||
|
while ( query.next() )
|
||||||
|
{
|
||||||
|
QDateTime timestamp = query.value( 0 ).toDateTime();
|
||||||
|
QString projectContent = query.value( 1 ).toString();
|
||||||
|
content.push_back( std::make_pair( timestamp, projectContent ) );
|
||||||
|
}
|
||||||
|
|
||||||
|
return content;
|
||||||
|
}
|
||||||
|
|
||||||
|
//--------------------------------------------------------------------------------------------------
|
||||||
|
///
|
||||||
|
//--------------------------------------------------------------------------------------------------
|
||||||
|
void extractVersionsToFolder( const QString& destinationFolder )
|
||||||
|
{
|
||||||
|
auto allContent = getAllContent();
|
||||||
|
|
||||||
|
for ( const auto& [timestamp, content] : allContent )
|
||||||
|
{
|
||||||
|
const QString dateFormat = "yyyy-MM-dd_hh-mm-ss";
|
||||||
|
QString filename = destinationFolder + "/" + timestamp.toString( dateFormat ) + ".rsp";
|
||||||
|
QFile file( filename );
|
||||||
|
if ( !file.open( QIODevice::WriteOnly | QIODevice::Text ) )
|
||||||
|
{
|
||||||
|
qCritical() << "Error opening file for writing:" << filename;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
QTextStream out( &file );
|
||||||
|
out << content;
|
||||||
|
file.close();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
int main( int argc, char* argv[] )
|
||||||
|
{
|
||||||
|
QCoreApplication app( argc, argv );
|
||||||
|
QCoreApplication::setApplicationName( "extract-projectfile-versions" );
|
||||||
|
QCoreApplication::setApplicationVersion( "1.0" );
|
||||||
|
|
||||||
|
QCommandLineParser parser;
|
||||||
|
parser.setApplicationDescription(
|
||||||
|
"extract-projectfile-versions is used to restore previous revisions of a ResInsight project from a project file database." );
|
||||||
|
parser.addHelpOption();
|
||||||
|
parser.addVersionOption();
|
||||||
|
|
||||||
|
parser.addPositionalArgument( "file", "ResInsight project file database (*.rspdb)" );
|
||||||
|
parser.addPositionalArgument( "outputfolder", "Output folder all project files" );
|
||||||
|
|
||||||
|
parser.process( app );
|
||||||
|
|
||||||
|
const QStringList args = parser.positionalArguments();
|
||||||
|
if ( args.size() != 2 )
|
||||||
|
{
|
||||||
|
qCritical() << "Failed to detect two input arguments.";
|
||||||
|
parser.showHelp( 1 );
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
QString databaseFilePath = args.front();
|
||||||
|
if ( !QFile::exists( databaseFilePath ) )
|
||||||
|
{
|
||||||
|
qCritical() << "Database file does not exist:" << databaseFilePath;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
QString destinationDir = args[1];
|
||||||
|
QDir dir;
|
||||||
|
if ( !dir.mkpath( destinationDir ) )
|
||||||
|
{
|
||||||
|
qCritical() << "Not able to create destination folder : " << destinationDir;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
const QString databaseType = "QSQLITE";
|
||||||
|
|
||||||
|
if ( !QSqlDatabase::isDriverAvailable( databaseType ) )
|
||||||
|
{
|
||||||
|
qInfo() << "sqlite database is not available.";
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Try to open the SQLITE database
|
||||||
|
QSqlDatabase db = QSqlDatabase::database();
|
||||||
|
if ( !db.isValid() || !db.open() )
|
||||||
|
{
|
||||||
|
qInfo() << "Adding database";
|
||||||
|
|
||||||
|
// Add the SQLITE database, and it it required to do this once per session. The database will be available during the lifetime
|
||||||
|
// of the application, and can be accessed using QSqlDatabase::database()
|
||||||
|
db = QSqlDatabase::addDatabase( databaseType );
|
||||||
|
}
|
||||||
|
|
||||||
|
QFileInfo fileInfo( databaseFilePath );
|
||||||
|
auto dbPath = fileInfo.absoluteFilePath();
|
||||||
|
db.setDatabaseName( dbPath );
|
||||||
|
|
||||||
|
if ( !db.open() )
|
||||||
|
{
|
||||||
|
QString txt = "Error opening database:" + db.lastError().text();
|
||||||
|
qCritical() << txt;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
extractVersionsToFolder( destinationDir );
|
||||||
|
|
||||||
|
return 1;
|
||||||
|
}
|
Loading…
Reference in New Issue
Block a user