Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
13 changes: 13 additions & 0 deletions app/activeproject.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -211,6 +211,11 @@ bool ActiveProject::forceLoad( const QString &filePath, bool force )
emit projectReloaded( mQgsProject );
emit positionTrackingSupportedChanged();
emit mapSketchesEnabledChanged();

if ( mLocalProject.isValid() )
{
emit projectSyncCheckRequested( mLocalProject.fullName(), true );
}
}

bool foundErrorsInLoadedProject = validateProject();
Expand Down Expand Up @@ -668,3 +673,11 @@ bool ActiveProject::photoSketchingEnabled() const

return mQgsProject->readBoolEntry( QStringLiteral( "Mergin" ), QStringLiteral( "PhotoSketching/Enabled" ), false );
}

void ActiveProject::checkForProjectUpdate()
{
if ( isProjectLoaded() )
{
emit projectSyncCheckRequested( projectFullName(), true );
}
}
5 changes: 5 additions & 0 deletions app/activeproject.h
Comment thread
gabriel-bolbotina marked this conversation as resolved.
Original file line number Diff line number Diff line change
Expand Up @@ -169,6 +169,8 @@ class ActiveProject: public QObject

void syncActiveProject( const LocalProject &project, SyncOptions::RequestOrigin requestOrigin );

void projectSyncCheckRequested( const QString &projectFullName, bool withAuth );

void mapThemeChanged( const QString &mapTheme );

void positionTrackingSupportedChanged();
Expand All @@ -192,6 +194,9 @@ class ActiveProject: public QObject

void requestSync( SyncOptions::RequestOrigin requestOrigin = SyncOptions::RequestOrigin::ManualRequest );

//! Checks whether the currently loaded project has a newer version available on the server
Q_INVOKABLE void checkForProjectUpdate();

private:

/**
Expand Down
2 changes: 2 additions & 0 deletions app/main.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -646,6 +646,8 @@ int main( int argc, char *argv[] )
merginApi->reloadProjectRole( activeProject.projectFullName() );
} );

QObject::connect( &activeProject, &ActiveProject::projectSyncCheckRequested, ma.get(), &MerginApi::isProjectSyncNeeded );

QObject::connect( ma.get(), &MerginApi::authChanged, &lambdaContext, [merginApi = ma.get(), &activeProject]()
{
if ( activeProject.isProjectLoaded() )
Expand Down
10 changes: 9 additions & 1 deletion app/notificationmodel.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,8 @@ QHash<int, QByteArray> NotificationModel::roleNames() const
{ IdRole, "id" },
{ MessageRole, "message" },
{ TypeRole, "type" },
{ IconRole, "icon" }
{ IconRole, "icon" },
{ ActionRole, "action" }
};
}

Expand All @@ -60,6 +61,7 @@ QVariant NotificationModel::data( const QModelIndex &index, int role ) const
if ( role == MessageRole ) return notification.message();
if ( role == TypeRole ) return notification.type();
if ( role == IconRole ) return notification.icon();
if ( role == ActionRole ) return notification.action();

return {};
}
Expand Down Expand Up @@ -156,6 +158,12 @@ void NotificationModel::onNotificationClicked( uint id )
emit showSyncFailedDialogClicked();
break;
}
case NotificationType::ActionType::SyncProjectAction:
{
remove( id );
emit showProjectNewVersionClicked();
break;
}
default: break;
}
}
Expand Down
6 changes: 4 additions & 2 deletions app/notificationmodel.h
Original file line number Diff line number Diff line change
Expand Up @@ -43,7 +43,8 @@ class NotificationType
NoAction,
ShowProjectIssuesAction,
ShowSwitchWorkspaceAction,
ShowSyncFailedDialog
ShowSyncFailedDialog,
SyncProjectAction
};
Q_ENUM( ActionType )

Expand Down Expand Up @@ -89,7 +90,7 @@ class NotificationModel : public QAbstractListModel
public:
enum NotificationModelRoles
{
IdRole = Qt::UserRole + 1, MessageRole, TypeRole, IconRole
IdRole = Qt::UserRole + 1, MessageRole, TypeRole, IconRole, ActionRole
};
Q_ENUM( NotificationModelRoles )

Expand All @@ -111,6 +112,7 @@ class NotificationModel : public QAbstractListModel
void rowCountChanged();
void showProjectIssuesActionClicked();
void showSwitchWorkspaceActionClicked();
void showProjectNewVersionClicked();
void showSyncFailedDialogClicked();

private:
Expand Down
10 changes: 8 additions & 2 deletions app/qml/components/MMNotification.qml
Original file line number Diff line number Diff line change
Expand Up @@ -109,12 +109,18 @@ Rectangle {
verticalCenter: parent.verticalCenter
rightMargin: 20 * __dp
}
iconSource: __style.closeIcon
iconSource: model.action === MM.NotificationType.SyncProjectAction ? __style.syncIcon : __style.closeIcon
iconColor: text.color
bgndColor: __style.transparentColor
bgndHoverColor: __style.transparentColor

onClicked: __notificationModel.remove(model.id)
onClicked: {
if ( model.action === MM.NotificationType.SyncProjectAction ) {
__notificationModel.onNotificationClicked( model.id )
} else {
__notificationModel.remove( model.id )
}
}
}

Behavior on scale { NumberAnimation { easing.type: Easing.OutCubic; from: 0; to: 1.0; duration: 200 } }
Expand Down
16 changes: 16 additions & 0 deletions app/qml/main.qml
Comment thread
gabriel-bolbotina marked this conversation as resolved.
Original file line number Diff line number Diff line change
Expand Up @@ -84,6 +84,8 @@ ApplicationWindow {

// Stop/Start sync animation when user goes to map
syncButton.iconRotateAnimationRunning = ( __syncManager.hasPendingSync( __activeProject.projectFullName() ) )

__activeProject.checkForProjectUpdate()
}
else if ( stateManager.state === "projects" ) {
projectController.openPanel()
Expand Down Expand Up @@ -1090,6 +1092,17 @@ ApplicationWindow {
{
ssoExpiredTokenDialog.open()
}

function onProjectSyncRequired( projectFullName )
{
if ( __activeProject.projectFullName() === projectFullName )
{
__notificationModel.addInfo(
qsTr( "There is a new version of the project available" ),
MM.NotificationType.SyncProjectAction
)
}
}
}

Connections {
Expand All @@ -1112,6 +1125,9 @@ ApplicationWindow {
function onShowSyncFailedDialogClicked() {
syncFailedDialog.open()
}
function onShowProjectNewVersionClicked() {
__activeProject.requestSync()
}
}

Connections {
Expand Down
1 change: 1 addition & 0 deletions app/test/testmerginapi.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -2378,6 +2378,7 @@ void TestMerginApi::testAutosync()
AppSettings as;
ActiveLayer al;
ActiveProject activeProject( as, al, mApi->localProjectsManager() );
QObject::connect( &activeProject, &ActiveProject::projectSyncCheckRequested, mApi, &MerginApi::isProjectSyncNeeded );

mApi->localProjectsManager().addLocalProject( projectDir, projectName );

Expand Down
34 changes: 34 additions & 0 deletions core/merginapi.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -4597,3 +4597,37 @@ bool MerginApi::serverVersionIsAtLeast( const int requiredMajor, const int requi
// check patch
return serverPatch >= requiredPatch;
}

void MerginApi::isProjectSyncNeededFinished()
{
QNetworkReply *r = qobject_cast<QNetworkReply *>( sender() );
Q_ASSERT( r );

const QString projectFullName = r->request().attribute( static_cast<QNetworkRequest::Attribute>( AttrProjectFullName ) ).toString();

if ( r->error() == QNetworkReply::NoError )
{
const QByteArray data = r->readAll();
const MerginProjectMetadata serverProject = MerginProjectMetadata::fromJson( data );

// skip if a sync is already in progress for this project
if ( !mTransactionalStatus.contains( projectFullName ) )
{
const LocalProject projectInfo = mLocalProjects.projectFromMerginName( projectFullName );
if ( projectInfo.isValid() && projectInfo.localVersion != -1 && projectInfo.localVersion < serverProject.version )
{
emit projectSyncRequired( projectFullName );
}
}
}
r->deleteLater();
}
Comment thread
gabriel-bolbotina marked this conversation as resolved.

void MerginApi::isProjectSyncNeeded( const QString &projectFullName, bool withAuth )
{
const QNetworkReply *reply = getProjectInfo( projectFullName, withAuth );
if ( !reply )
return;

connect( reply, &QNetworkReply::finished, this, &MerginApi::isProjectSyncNeededFinished );
}
5 changes: 5 additions & 0 deletions core/merginapi.h
Original file line number Diff line number Diff line change
Expand Up @@ -645,6 +645,8 @@ class MerginApi: public QObject
*/
Q_INVOKABLE void reloadProjectRole( const QString &projectFullName );

Q_INVOKABLE void isProjectSyncNeeded( const QString &projectFullName, bool withAuth );

/**
* Returns the network manager used for Mergin API requests
*/
Expand Down Expand Up @@ -689,6 +691,7 @@ class MerginApi: public QObject

void listProjectsFinished( const MerginProjectsList &merginProjects, int projectCount, int page, QString requestId );
void listProjectsFailed();
void projectSyncRequired( const QString &projectFullName );
void listProjectsByNameFinished( const MerginProjectsList &merginProjects, QString requestId );
void syncProjectFinished( const QString &projectFullName, bool successfully, int version );
void projectReloadNeededAfterSync( const QString &projectFullName );
Expand Down Expand Up @@ -783,6 +786,8 @@ class MerginApi: public QObject

// Pull slots
void pullInfoReplyFinished();
void isProjectSyncNeededFinished();

void downloadItemReplyFinished( DownloadQueueItem item );
void cacheServerConfig();

Expand Down
Loading