Преглед изворни кода

Add notification about upgrade to admin page

Ben Muthalaly пре 2 година
родитељ
комит
7599dbb79d
2 измењених фајлова са 95 додато и 1 уклоњено
  1. 2 1
      archivebox/core/urls.py
  2. 93 0
      archivebox/templates/admin/base.html

+ 2 - 1
archivebox/core/urls.py

@@ -8,6 +8,7 @@ from django.views.generic.base import RedirectView
 
 
 from core.views import HomepageView, SnapshotView, PublicIndexView, AddView, HealthCheckView
 from core.views import HomepageView, SnapshotView, PublicIndexView, AddView, HealthCheckView
 
 
+from config import VERSION
 
 
 # print('DEBUG', settings.DEBUG)
 # print('DEBUG', settings.DEBUG)
 
 
@@ -30,7 +31,7 @@ urlpatterns = [
 
 
 
 
     path('accounts/', include('django.contrib.auth.urls')),
     path('accounts/', include('django.contrib.auth.urls')),
-    path('admin/', admin.site.urls),
+    path('admin/', admin.site.urls, {'extra_context': {'VERSION': VERSION}}),
 
 
     path('health/', HealthCheckView.as_view(), name='healthcheck'),
     path('health/', HealthCheckView.as_view(), name='healthcheck'),
     path('error/', lambda _: 1/0),
     path('error/', lambda _: 1/0),

+ 93 - 0
archivebox/templates/admin/base.html

@@ -123,6 +123,99 @@
         </div>
         </div>
 
 
         <script>
         <script>
+            const installedVersion = "{{VERSION}}";
+
+            // get versions from GitHub
+            const github_releases_api = "https://api.github.com/repos/pirate/archivebox/releases";
+
+            let release_data = fetch(github_releases_api)
+              .then(response => response.json())
+              .then(release_data => {
+                let upgradeVersion = findUpgradeVersion(installedVersion, release_data);
+                let currentVersion = findCurrentVersion(installedVersion, release_data);
+
+                const showBanner = localStorage.getItem("bannerDismissed") !== "true" && currentVersion.html_url !== upgradeVersion.html_url
+                if (showBanner) {
+                    createBanner(currentVersion, upgradeVersion);
+                }
+              })
+              .catch(error => {
+                console.error('Error fetching release data: ', error);
+              });
+
+            // finds the nearest stable version
+            function findCurrentVersion(currentVersionTagName, releaseData) {
+                for (let i = 0; i < releaseData.length; i++) {
+                    if (compareVersions(releaseData[i].tag_name, currentVersionTagName) <= 0) {
+                        return releaseData[i];
+                    }
+                }
+                return releaseData[releaseData.length - 1];
+            }
+
+            function findUpgradeVersion(currentVersionTagName, releaseData) {
+                for (let i = 0; i < releaseData.length; i++) {
+                    if (majorVersionDiff(releaseData[i].tag_name, currentVersionTagName) === 1) {
+                        return releaseData[i];
+                    }
+                }
+                return releaseData[0];
+            }
+
+            function createBanner(currentVersion, upgradeVersion) {
+                const banner = document.createElement('div');
+                banner.setAttribute('id', 'upgrade-banner');
+                banner.innerHTML = `
+                    There's a new version of ArchiveBox available!
+                    The next major version is <a href=${upgradeVersion.html_url}>${upgradeVersion.tag_name}</a>.
+                    Your current version is <a href=${currentVersion.html_url}>${installedVersion}</a>
+                    <p>
+                    <a href=https://github.com/ArchiveBox/ArchiveBox/wiki/Upgrading-or-Merging-Archives>Upgrading</a> | <a href=https://github.com/ArchiveBox/ArchiveBox/releases>Changelog</a> | <a href=https://github.com/ArchiveBox/ArchiveBox/wiki/Roadmap>Roadmap</a> 
+                    </p>
+                    <button>
+                        <a href="#" onclick="dismissBanner()">Dismiss</a>
+                    </button>
+                `
+                document.body.appendChild(banner);
+            }
+
+
+            // dismisses the version banner and stores a cookie to prevent it from showing again
+            function dismissBanner() {
+                var banner = document.getElementById("version-banner");
+                banner.style.display = "none";
+                localStorage.setItem("bannerDismissed", "true");
+            }
+
+            function parseVersion(v) {
+                return v.replace(/^v/, '').split(".").map(Number);
+            }
+
+            // compares two version strings formatted like "vx.x.x" (where the x's are integers)
+            // and returns 1 if v1 is newer than v2, 0 if they're the same, and -1 
+            // if v1 is older than v2.
+            function compareVersions(v1, v2) {
+                let v1Parts = parseVersion(v1);
+                let v2Parts = parseVersion(v2);
+
+                for (let i = 0; i < 3; i++) {
+                    if (v1Parts[i] < v2Parts[i]) {
+                        return -1;
+                    }
+                    if (v1Parts[i] > v2Parts[i]) {
+                        return 1;
+                    }
+                }
+                return 0;
+            }
+
+            function majorVersionDiff(v1, v2) {
+                let v1Parts = parseVersion(v1);
+                let v2Parts = parseVersion(v2);
+
+                return v1Parts[1] - v2Parts[1];
+            }
+
             $ = django.jQuery;
             $ = django.jQuery;
             $.fn.reverse = [].reverse;
             $.fn.reverse = [].reverse;