Skip to content

Commit 9ab3d46

Browse files
committed
Add fallback for listProjectsByName
1 parent 920fef0 commit 9ab3d46

File tree

4 files changed

+95
-9
lines changed

4 files changed

+95
-9
lines changed

app/projectsmodel.cpp

Lines changed: 40 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -39,6 +39,7 @@ void ProjectsModel::initializeProjectsModel()
3939
if ( mModelType == ProjectModelTypes::LocalProjectsModel )
4040
{
4141
connect( mBackend, &MerginApi::listProjectsByNameFinished, this, &ProjectsModel::onListProjectsByNameFinished );
42+
connect( mBackend, &MerginApi::refetchBrokenProjectsFinished, this, &ProjectsModel::onRefetchBrokenProjectsFinished );
4243
loadLocalProjects();
4344
}
4445
else if ( mModelType != ProjectModelTypes::RecentProjectsModel )
@@ -268,13 +269,32 @@ void ProjectsModel::onListProjectsByNameFinished( const MerginProjectsList &merg
268269
return;
269270
}
270271

272+
// filter out projects which returned errors and refetch them by ID
273+
const QStringList brokenProjects = filterBrokenProjects( merginProjects );
274+
if ( !brokenProjects.isEmpty() )
275+
{
276+
mBackend->refetchBrokenProjects( brokenProjects );
277+
}
278+
271279
beginResetModel();
272280
mergeProjects( merginProjects );
273281
endResetModel();
274282

275283
setModelIsLoading( false );
276284
}
277285

286+
void ProjectsModel::onRefetchBrokenProjectsFinished( const MerginProjectsList &merginProjects )
287+
{
288+
if ( merginProjects.isEmpty() )
289+
{
290+
return;
291+
}
292+
293+
beginResetModel();
294+
mergeProjects( merginProjects, MergeStrategy::KeepPrevious );
295+
endResetModel();
296+
}
297+
278298
void ProjectsModel::mergeProjects( const MerginProjectsList &merginProjects, MergeStrategy mergeStrategy )
279299
{
280300
const LocalProjectsDict localProjects = mLocalProjectsManager->projects();
@@ -651,6 +671,26 @@ void ProjectsModel::loadLocalProjects()
651671
}
652672
}
653673

674+
QStringList ProjectsModel::filterBrokenProjects( const MerginProjectsList &list )
675+
{
676+
QStringList errorProjects;
677+
for ( MerginProject project : list )
678+
{
679+
if ( !project.remoteError.isEmpty() )
680+
{
681+
const auto res = std::find_if( mProjects.begin(), mProjects.end(), [&project]( const Project & localProject )
682+
{
683+
return project.fullName() == localProject.fullName();
684+
} );
685+
if ( res != mProjects.end() )
686+
{
687+
errorProjects.append( res->id() );
688+
}
689+
}
690+
}
691+
return errorProjects;
692+
}
693+
654694
int ProjectsModel::projectIndexFromId( const QString &projectId ) const
655695
{
656696
for ( int i = 0; i < mProjects.count(); i++ )

app/projectsmodel.h

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -165,6 +165,7 @@ class ProjectsModel : public QAbstractListModel
165165
// MerginAPI - project list signals
166166
void onListProjectsFinished( const MerginProjectsList &merginProjects, int projectsCount, int page, const QString &requestId );
167167
void onListProjectsByNameFinished( const MerginProjectsList &merginProjects, const QString &requestId );
168+
void onRefetchBrokenProjectsFinished( const MerginProjectsList &merginProjects );
168169

169170
// Synchronization signals
170171
void onProjectSyncStarted( const QString &projectId );
@@ -203,7 +204,7 @@ class ProjectsModel : public QAbstractListModel
203204
void activeProjectIdChanged( QString projectId );
204205

205206
private:
206-
207+
QStringList filterBrokenProjects( const MerginProjectsList &list );
207208
int projectIndexFromId( const QString &projectId ) const;
208209

209210
void setModelIsLoading( bool state );

core/merginapi.cpp

Lines changed: 43 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -268,6 +268,12 @@ QString MerginApi::listProjectsByName( const QStringList &projectNames )
268268
return requestId;
269269
}
270270

271+
void MerginApi::refetchBrokenProjects( const QStringList &projectIds )
272+
{
273+
const QNetworkReply *reply = getProjectsDetails( projectIds );
274+
connect( reply, &QNetworkReply::finished, this, &MerginApi::refetchBrokenProjectsReplyFinished );
275+
}
276+
271277

272278
void MerginApi::downloadNextItem( const QString &projectId )
273279
{
@@ -1674,7 +1680,7 @@ QNetworkReply *MerginApi::getProjectsDetails( const QStringList &projectIds, con
16741680
{
16751681
if ( withAuth && !validateAuth() )
16761682
{
1677-
for ( const QString& projectId : projectIds )
1683+
for ( const QString &projectId : projectIds )
16781684
{
16791685
emit missingAuthorizationError( projectId );
16801686
}
@@ -1687,7 +1693,7 @@ QNetworkReply *MerginApi::getProjectsDetails( const QStringList &projectIds, con
16871693
}
16881694

16891695
QUrlQuery query;
1690-
query.addQueryItem( QStringLiteral( "uuids" ), projectIds.join(",") );
1696+
query.addQueryItem( QStringLiteral( "uuids" ), projectIds.join( "," ) );
16911697

16921698
QUrl url{};
16931699
url.setUrl( mApiRoot + QStringLiteral( "/v1/project/by_uuids" ) );
@@ -2083,21 +2089,49 @@ void MerginApi::getProjectsDetailsReplyFinished()
20832089
if ( mTransactionalStatus.contains( key ) )
20842090
{
20852091
QJsonObject project = response.value( key ).toObject();
2086-
QString projectFullName = QString("%1/%2").arg( project.value("namespace").toString(), project.value("name").toString());
2092+
QString projectFullName = QString( "%1/%2" ).arg( project.value( "namespace" ).toString(), project.value( "name" ).toString() );
20872093
const bool withAuth = r->request().attribute( static_cast<QNetworkRequest::Attribute>( AttrAuthUsed ) ).toBool();
2088-
if (mTransactionalStatus[key].type == TransactionStatus::Pull )
2094+
if ( mTransactionalStatus[key].type == TransactionStatus::Pull )
20892095
{
2090-
pullProject( projectFullName, key, withAuth);
2091-
} else
2096+
pullProject( projectFullName, key, withAuth );
2097+
}
2098+
else
20922099
{
2093-
pushProject( projectFullName, key, withAuth);
2100+
pushProject( projectFullName, key, withAuth );
20942101
}
20952102
}
20962103
}
20972104
}
20982105
}
20992106
}
21002107

2108+
void MerginApi::refetchBrokenProjectsReplyFinished()
2109+
{
2110+
QNetworkReply *r = qobject_cast<QNetworkReply *>( sender() );
2111+
Q_ASSERT( r );
2112+
2113+
MerginProjectsList projectList;
2114+
2115+
if ( r->error() == QNetworkReply::NoError )
2116+
{
2117+
const QByteArray data = r->readAll();
2118+
const QJsonDocument json = QJsonDocument::fromJson( data );
2119+
projectList = parseProjectsFromJson( json );
2120+
CoreUtils::log( "refetch broken projects", QStringLiteral( "Success - got %1 projects" ).arg( projectList.count() ) );
2121+
}
2122+
else
2123+
{
2124+
QString serverMsg = extractServerErrorMsg( r->readAll() );
2125+
const QString message = QStringLiteral( "Network API error: %1(): %2. %3" ).arg( QStringLiteral( "refetchBrokenProjects" ), r->errorString(), serverMsg );
2126+
emit networkErrorOccurred( serverMsg );
2127+
CoreUtils::log( "refetch broken projects", QStringLiteral( "FAILED - %1" ).arg( message ) );
2128+
}
2129+
2130+
r->deleteLater();
2131+
2132+
emit refetchBrokenProjectsFinished( projectList );
2133+
}
2134+
21012135

21022136
void MerginApi::finalizeProjectPullCopy( const QString &projectFullName, const QString &projectDir, const QString &tempDir, const QString &filePath, const QList<DownloadQueueItem> &items )
21032137
{
@@ -2535,7 +2569,8 @@ void MerginApi::pullInfoReplyFinished()
25352569
transaction.replyPullProjectInfo = nullptr;
25362570

25372571
finishProjectSync( projectFullName, projectId, false );
2538-
} else
2572+
}
2573+
else
25392574
{
25402575
const QString serverMsg = extractServerErrorMsg( r->readAll() );
25412576
const QString message = QStringLiteral( "Network API error: %1(): %2" ).arg( QStringLiteral( "projectInfo" ), r->errorString() );

core/merginapi.h

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -264,6 +264,14 @@ class MerginApi: public QObject
264264
*/
265265
QString listProjectsByName( const QStringList &projectNames = QStringList() );
266266

267+
/**
268+
* Fallback method for listProjectsByName, which tries to request projects by IDs instead of names.
269+
* Uses getProjectsDetails internally.
270+
* \param projectIds QStringList of project IDs
271+
* \see listProjectsByName
272+
*/
273+
void refetchBrokenProjects( const QStringList &projectIds );
274+
267275
/**
268276
* Sends non-blocking POST request to the server to pull (download) a project with a given name.
269277
* On pullProjectReplyFinished, when a response is received, parses data-stream to files and rewrites local files
@@ -633,6 +641,7 @@ class MerginApi: public QObject
633641
void projectDataChanged( const QString &projectFullName, const QString &projectId );
634642
void projectDetached( const QString &projectId );
635643
void projectAttachedToMergin( const QString &projectId );
644+
void refetchBrokenProjectsFinished( const MerginProjectsList &projectList );
636645

637646
void projectAlreadyOnLatestVersion( const QString &projectId );
638647
void missingAuthorizationError( const QString &projectId );
@@ -676,6 +685,7 @@ class MerginApi: public QObject
676685
void listProjectsReplyFinished( const QString &requestId );
677686
void listProjectsByNameReplyFinished( const QString &requestId );
678687
void getProjectsDetailsReplyFinished();
688+
void refetchBrokenProjectsReplyFinished();
679689

680690
// Pull slots
681691
void pullInfoReplyFinished();

0 commit comments

Comments
 (0)