Skip to content

Commit

Permalink
Check QGIS desktop plugin version for edited QGS file
Browse files Browse the repository at this point in the history
  • Loading branch information
Gustry committed Mar 6, 2024
1 parent 8ab21b1 commit ca7841e
Show file tree
Hide file tree
Showing 11 changed files with 153 additions and 5 deletions.
2 changes: 1 addition & 1 deletion lizmap/app/system/mainconfig.ini.php
Original file line number Diff line number Diff line change
Expand Up @@ -36,10 +36,10 @@
; Lizmap QGIS desktop plugin required/recommended minimum version for newly or updated project only
; This version MUST match at least on https://plugins.qgis.org/plugins/lizmap/#plugin-versions
; with the minimum QGIS server version supported above.
; This is experimental for now.
; This value is only forwarded to the plugin thanks to the server metadata. According to the age of the project, it
; will be either recommended or required.
lizmapDesktopPlugin="4.1.8"
lizmapDesktopPluginDate="2024-01-30"

; Versions written in QGIS/CFG files, for the GIS administrator
; Lizmap CFG files with a lower target version are not displayed in the landing page, but displayed in the administration panel to warn the GIS administrator
Expand Down
2 changes: 2 additions & 0 deletions lizmap/modules/admin/locales/en_US/admin.UTF-8.properties
Original file line number Diff line number Diff line change
Expand Up @@ -341,6 +341,8 @@ Open the project in QGIS desktop with an updated version of the plugin
project.list.column.target.lizmap.version.label=Target version
project.list.column.target.lizmap.version.label.longer=Target version of Lizmap Web Client
project.list.column.lizmap.plugin.version.label=Lizmap plugin
project.list.column.qgis.desktop.recent.label=This QGIS project has been recently updated in QGIS Desktop, \
but with a too old Lizmap plugin version. You should upgrade your plugin in the QGIS plugin manager.
project.list.column.lizmap.warnings.count.label=Warnings
project.list.column.lizmap.warnings.explanations.label=Check your Lizmap plugin in QGIS Desktop to fix these warnings
project.list.column.authorized.groups.label=Groups
Expand Down
6 changes: 6 additions & 0 deletions lizmap/modules/admin/templates/project_list_zone.tpl
Original file line number Diff line number Diff line change
Expand Up @@ -181,8 +181,14 @@ to view the hidden columns data and when there is no data for these columns -->
{assign $title = $title . ' - '}
{/if}
{assign $title = $title . @admin.project.list.column.lizmap.plugin.version.label@ . ' ' . $p['lizmap_plugin_version']}
{if $p['lizmap_plugin_update'] }
{assign $title = $title . ' ' . @admin.project.list.column.qgis.desktop.recent.label@}
{/if}
<td title="{$title}" class="{$class}">
{$p['qgis_version']}
{if $p['lizmap_plugin_update'] }
<span class='badge badge-warning'>⚠</span>
{/if}
</td>

<!-- Target version of Lizmap Web Client -->
Expand Down
1 change: 1 addition & 0 deletions lizmap/modules/admin/zones/project_list.zone.php
Original file line number Diff line number Diff line change
Expand Up @@ -175,6 +175,7 @@ private function getProjectListItem($inspectionDirectoryPath, $projectMetadata)
'lizmap_web_client_target_version' => $projectMetadata->getLizmapWebClientTargetVersion(),
// convert int to string orderable
'lizmap_plugin_version' => $this->pluginIntVersionToSortableString($projectMetadata->getLizmapPluginVersion()),
'lizmap_plugin_update' => $projectMetadata->updateQgisLizmapPlugin(),
'file_time' => $projectMetadata->getFileTime(),
'layer_count' => $projectMetadata->getLayerCount(),
'acl_groups' => $projectMetadata->getAclGroups(),
Expand Down
21 changes: 21 additions & 0 deletions lizmap/modules/lizmap/lib/Project/Project.php
Original file line number Diff line number Diff line change
Expand Up @@ -327,6 +327,16 @@ public function getQgisProjectVersion()
return $this->qgis->getQgisProjectVersion();
}

/**
* Get the last date saved in the QGIS file.
*
* @return string last saved date time of the file
*/
public function getLastSaveDateTime()
{
return $this->qgis->getLastSaveDateTime();
}

/**
* Get the version of the Lizmap plugin
* used by the project editor on QGIS Desktop.
Expand Down Expand Up @@ -2359,6 +2369,17 @@ public function needsUpdateWarning()
return false;
}

/**
* Project needs an update on plugin side.
* The check is done only is the QGIS file has been edited recently.
*
* @return bool true if the plugin needs to be updated
*/
public function updateQgisLizmapPlugin()
{
return $this->getMetadata()->updateQgisLizmapPlugin();
}

/**
* Project warnings in the CFG file.
*
Expand Down
61 changes: 61 additions & 0 deletions lizmap/modules/lizmap/lib/Project/ProjectMetadata.php
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,7 @@ public function __construct(Project $project)
'map' => $project->getRelativeQgisPath(),
'acl' => $project->checkAcl(),
'qgisProjectVersion' => $project->getQgisProjectVersion(),
'lastSaveDateTime' => $project->getLastSaveDateTime(),
'lizmapPluginVersion' => $project->getLizmapPluginVersion(),
'lizmapWebClientTargetVersion' => $project->getLizmapWebCLientTargetVersion(),
'needsUpdateError' => $project->needsUpdateError(),
Expand Down Expand Up @@ -181,6 +182,16 @@ public function getWMTSGetCapabilitiesUrl()
return $this->data['wmtsGetCapabilitiesUrl'];
}

/**
* The last save date time of the QGIS file.
*
* @return string the last save date time
*/
public function getLastSaveDateTime()
{
return $this->data['lastSaveDateTime'];
}

/**
* The QGIS desktop project version.
*
Expand Down Expand Up @@ -211,6 +222,56 @@ public function getLizmapWebCLientTargetVersion()
return $this->data['lizmapWebClientTargetVersion'];
}

/**
* If the QGIS desktop needs an update of the plugin.
* The check is not done only if the project has been edited recently compare to the date of the Lizmap Web Client.
*
* @return bool If the plugin should be updated in QGIS Desktop
*/
public function updateQgisLizmapPlugin()
{
// Not the best choice, maybe because of git for dev, dates are not correct
// $projectDate = date($this->getFileTime());
// Better to use lastSaveDateTime in the QGS file
$projectDate = strtotime($this->getLastSaveDateTime());

// Which date to use for reference ?
// LWC date is too old. For 3.8 for instance, for dev, it's currently 2023-11-24
// But for LWC 3.7, it's ok because we have frequent releases now.
// $projectInfos = \Jelix\Core\Infos\AppInfos::load();
// $releaseDate = $projectInfos->versionDate;
// So let's use a date matching the plugin version
$releaseDate = \jApp::config()->minimumRequiredVersion['lizmapDesktopPluginDate'];

if ($projectDate < strtotime($releaseDate)) {
// Project file date is older than internal release date, we do nothing
// Project can stay on the server without any update
return false;
}

// Project file is newer than the release date
// We check against the hard coded version
$recommendedVersion = \jApp::config()->minimumRequiredVersion['lizmapDesktopPlugin'];

$projectVersion = $this->getLizmapPluginVersion();
if (!is_numeric($projectVersion)) {
// It shouldn't happen to much, but before the version was like "master".
return false;
}

// TODO It would be nice to avoid code duplication,
// we have code to manage versions for sorting, display, integer comparaison...
$intVersion6Digit = (strlen($projectVersion) == 6 ? $projectVersion : '0'.$projectVersion);
list($majorVersion, $minorVersion, $patchVersion) = str_split($intVersion6Digit, 2);

if (version_compare($majorVersion.'.'.$minorVersion.'.'.$patchVersion, $recommendedVersion) >= 0) {
// Lizmap plugin version in the CFG file is newer than the hard coded version
return false;
}

return true;
}

/**
* Check if the project needs an update which is critical.
*
Expand Down
34 changes: 34 additions & 0 deletions lizmap/modules/lizmap/lib/Project/QgisProject.php
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,13 @@ class QgisProject
*/
protected $qgisProjectVersion;

/**
* Last saved date time in the QGIS file.
*
* @var string
*/
protected $lastSaveDateTime;

/**
* @var array contains WMS info
*/
Expand Down Expand Up @@ -105,6 +112,7 @@ class QgisProject
'layers',
'data',
'qgisProjectVersion',
'lastSaveDateTime',
'customProjectVariables',
);

Expand Down Expand Up @@ -225,6 +233,16 @@ public function getQgisProjectVersion()
return $this->qgisProjectVersion;
}

/**
* Last saved date time in the QGIS file.
*
* @return string
*/
public function getLastSaveDateTime()
{
return $this->lastSaveDateTime;
}

public function getWMSInformation()
{
return $this->WMSInformation;
Expand Down Expand Up @@ -1192,6 +1210,7 @@ protected function readXmlProject($qgs_path)

// get QGIS project version
$this->qgisProjectVersion = $this->readQgisProjectVersion($qgsXml);
$this->lastSaveDateTime = $this->readLastSaveDateTime($qgsXml);

$this->WMSInformation = $this->readWMSInformation($qgsXml);
$this->canvasColor = $this->readCanvasColor($qgsXml);
Expand Down Expand Up @@ -1259,6 +1278,21 @@ protected function readWMSInformation($qgsLoad)
);
}

/**
* Read the last modified date of the QGS file.
*
* @param \SimpleXMLElement $xml
*
* @return string
*/
protected function readLastSaveDateTime($xml)
{
$qgisRoot = $xml->xpath('//qgis');
$qgisRootZero = $qgisRoot[0];

return (string) $qgisRootZero->attributes()->saveDateTime;
}

/**
* @param \SimpleXMLElement $xml
*/
Expand Down
2 changes: 1 addition & 1 deletion lizmap/modules/view/controllers/lizMap.classic.php
Original file line number Diff line number Diff line change
Expand Up @@ -567,7 +567,7 @@ function f($x)
}

$serverInfoAccess = (\jAcl2::check('lizmap.admin.access') || \jAcl2::check('lizmap.admin.server.information.view'));
if ($serverInfoAccess && $lproj->projectCountCfgWarnings() >= 1) {
if ($serverInfoAccess && ($lproj->projectCountCfgWarnings() >= 1 || $lproj->updateQgisLizmapPlugin())) {
$jsWarning = "
lizMap.events.on(
{
Expand Down
6 changes: 3 additions & 3 deletions tests/units/README.md
Original file line number Diff line number Diff line change
@@ -1,11 +1,11 @@
Unit tests for Lizmap
=====================

A unit tests shoud be added each time you fix a bug or provide a new feature / API.
A unit tests should be added each time you fix a bug or provide a new feature / API.

- testslib directory: where classes inheriting from Lizmap classes or new classes
- `testslib` directory: where classes inheriting from Lizmap classes or new classes
for tests are stored.
No need to do a `require`. These classes are autoloaded, if their name ends
with `ForTests`.
- tmp: use this directory to store temporary content for your tests
- `tmp`: use this directory to store temporary content for your tests
- Other directories : they contain tests.
13 changes: 13 additions & 0 deletions tests/units/classes/Project/QgisProjectTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -234,6 +234,19 @@ public function testReadLayers()
}
}

public function testReadQgisMetadata()
{
$testQgis = new qgisProjectForTests();
$xml = simplexml_load_file(__DIR__.'/Ressources/readLayers_316.qgs');
$this->assertEquals('31607', $testQgis->readQgisVersionForTests($xml));
$this->assertEquals('2021-06-14T11:50:51', $testQgis->readLastSaveDateTimeForTests($xml));

$testQgis = new qgisProjectForTests();
$xml = simplexml_load_file(__DIR__.'/Ressources/readLayers_310.qgs');
$this->assertEquals('31004', $testQgis->readQgisVersionForTests($xml));
$this->assertEquals('', $testQgis->readLastSaveDateTimeForTests($xml));
}

public function testReadRelations()
{
$expectedRelations = array(
Expand Down
10 changes: 10 additions & 0 deletions tests/units/testslib/QgisProjectForTests.php
Original file line number Diff line number Diff line change
Expand Up @@ -66,6 +66,16 @@ public function readLayersForTests($xml)
return $this->readLayers($xml);
}

public function readQgisVersionForTests($xml)
{
return $this->readQgisProjectVersion($xml);
}

public function readLastSaveDateTimeForTests($xml)
{
return $this->readLastSaveDateTime($xml);
}

public function readRelationsForTests($xml)
{
$this->xml = $xml;
Expand Down

0 comments on commit ca7841e

Please sign in to comment.