Page Menu
Home
Software Heritage
Search
Configure Global Search
Log In
Files
F7124082
D7973.id28725.diff
No One
Temporary
Actions
View File
Edit File
Delete File
View Transforms
Subscribe
Mute Notifications
Award Token
Flag For Later
Size
37 KB
Subscribers
None
D7973.id28725.diff
View Options
diff --git a/assets/src/bundles/origin/visits-reporting.js b/assets/src/bundles/origin/visits-reporting.js
--- a/assets/src/bundles/origin/visits-reporting.js
+++ b/assets/src/bundles/origin/visits-reporting.js
@@ -112,8 +112,8 @@
// process input visits
let firstFullVisit;
allVisits.forEach((v, i) => {
- // Turn Unix epoch into Javascript Date object
- v.date = new Date(Math.floor(v.date * 1000));
+ // Turn Python ISO8601 string date into Javascript UTC Date object
+ v.date = new Date(v.date.slice(0, -6));
const visitLink = '<a class="swh-visit-icon swh-visit-' + v.status + '" href="' + v.url + '">' + v.formatted_date + '</a>';
if (v.status === 'full') {
if (!firstFullVisit) {
diff --git a/swh/web/browse/snapshot_context.py b/swh/web/browse/snapshot_context.py
--- a/swh/web/browse/snapshot_context.py
+++ b/swh/web/browse/snapshot_context.py
@@ -8,6 +8,7 @@
from collections import defaultdict
from typing import Any, Dict, List, Optional, Tuple
+from django.http import HttpRequest, HttpResponse
from django.shortcuts import render
from django.utils.html import escape
@@ -48,7 +49,9 @@
_empty_snapshot_id = Snapshot(branches={}).id.hex()
-def _get_branch(branches, branch_name, snapshot_id):
+def _get_branch(
+ branches: List[SnapshotBranchInfo], branch_name: str, snapshot_id: str
+) -> Optional[SnapshotBranchInfo]:
"""
Utility function to get a specific branch from a snapshot.
Returns None if the branch cannot be found.
@@ -71,9 +74,12 @@
if snp_branch and snp_branch[0]["name"] == branch_name:
branches.append(snp_branch[0])
return snp_branch[0]
+ return None
-def _get_release(releases, release_name, snapshot_id):
+def _get_release(
+ releases: List[SnapshotReleaseInfo], release_name: Optional[str], snapshot_id: str
+) -> Optional[SnapshotReleaseInfo]:
"""
Utility function to get a specific release from a snapshot.
Returns None if the release cannot be found.
@@ -81,7 +87,7 @@
filtered_releases = [r for r in releases if r["name"] == release_name]
if filtered_releases:
return filtered_releases[0]
- else:
+ elif release_name:
# case where a large branches list has been truncated
try:
# git origins have specific branches for releases
@@ -102,11 +108,18 @@
if snp_release and snp_release[0]["name"] == release_name:
releases.append(snp_release[0])
return snp_release[0]
+ return None
def _branch_not_found(
- branch_type, branch, snapshot_id, snapshot_sizes, origin_info, timestamp, visit_id
-):
+ branch_type: str,
+ branch: str,
+ snapshot_id: str,
+ snapshot_sizes: Dict[str, int],
+ origin_info: Optional[OriginInfo],
+ timestamp: Optional[str],
+ visit_id: Optional[int],
+) -> None:
"""
Utility function to raise an exception when a specified branch/release
can not be found.
@@ -131,25 +144,25 @@
branch,
snapshot_id,
)
- elif visit_id and snapshot_sizes[target_type] == 0:
+ elif visit_id and snapshot_sizes[target_type] == 0 and origin_info:
msg = (
"Origin with url %s"
" for visit with id %s has an empty list"
" of %s!" % (origin_info["url"], visit_id, branch_type_plural)
)
- elif visit_id:
+ elif visit_id and origin_info:
msg = (
"%s %s associated to visit with"
" id %s for origin with url %s"
" not found!" % (branch_type, branch, visit_id, origin_info["url"])
)
- elif snapshot_sizes[target_type] == 0:
+ elif snapshot_sizes[target_type] == 0 and origin_info and timestamp:
msg = (
"Origin with url %s"
" for visit with timestamp %s has an empty list"
" of %s!" % (origin_info["url"], timestamp, branch_type_plural)
)
- else:
+ elif origin_info and timestamp:
msg = (
"%s %s associated to visit with"
" timestamp %s for origin with "
@@ -569,6 +582,7 @@
# HEAD alias targets a release
release_name = archive.lookup_release(head["target"])["name"]
head_rel = _get_release(releases, release_name, snapshot_id)
+ assert head_rel is not None
if head_rel["target_type"] == "revision":
revision = archive.lookup_revision(head_rel["target"])
root_directory = revision["directory"]
@@ -663,7 +677,9 @@
return snapshot_context
-def _build_breadcrumbs(snapshot_context: SnapshotContext, path: str):
+def _build_breadcrumbs(
+ snapshot_context: SnapshotContext, path: Optional[str]
+) -> List[Dict[str, str]]:
origin_info = snapshot_context["origin_info"]
url_args = snapshot_context["url_args"]
query_params = dict(snapshot_context["query_params"])
@@ -700,14 +716,18 @@
return breadcrumbs
-def _check_origin_url(snapshot_id, origin_url):
+def _check_origin_url(snapshot_id: Optional[str], origin_url: Optional[str]) -> None:
if snapshot_id is None and origin_url is None:
raise BadInputExc("An origin URL must be provided as query parameter.")
def browse_snapshot_directory(
- request, snapshot_id=None, origin_url=None, timestamp=None, path=None
-):
+ request: HttpRequest,
+ snapshot_id: Optional[str] = None,
+ origin_url: Optional[str] = None,
+ timestamp: Optional[str] = None,
+ path: Optional[str] = None,
+) -> HttpResponse:
"""
Django view implementation for browsing a directory in a snapshot context.
"""
@@ -728,7 +748,7 @@
root_directory = snapshot_context["root_directory"]
sha1_git = root_directory
- error_info = {
+ error_info: Dict[str, Any] = {
"status_code": 200,
"description": None,
}
@@ -813,7 +833,7 @@
dir_path = "/" + path
swh_objects = []
- vault_cooking = {
+ vault_cooking: Dict[str, Any] = {
"directory_context": False,
"directory_swhid": None,
"revision_context": False,
@@ -932,7 +952,12 @@
PER_PAGE = 100
-def browse_snapshot_log(request, snapshot_id=None, origin_url=None, timestamp=None):
+def browse_snapshot_log(
+ request: HttpRequest,
+ snapshot_id: Optional[str] = None,
+ origin_url: Optional[str] = None,
+ timestamp: Optional[str] = None,
+) -> HttpResponse:
"""
Django view implementation for browsing a revision history in a
snapshot context.
@@ -991,9 +1016,10 @@
query_params = snapshot_context["query_params"]
snapshot_id = snapshot_context["snapshot_id"]
- query_params["per_page"] = per_page
+ query_params["per_page"] = str(per_page)
revs_ordering = request.GET.get("revs_ordering", "")
- query_params["revs_ordering"] = revs_ordering or None
+ if revs_ordering:
+ query_params["revs_ordering"] = revs_ordering
if origin_info:
browse_view_name = "browse-origin-log"
@@ -1002,14 +1028,14 @@
prev_log_url = None
if len(rev_log) > offset + per_page:
- query_params["offset"] = offset + per_page
+ query_params["offset"] = str(offset + per_page)
prev_log_url = reverse(
browse_view_name, url_args=url_args, query_params=query_params
)
next_log_url = None
if offset != 0:
- query_params["offset"] = offset - per_page
+ query_params["offset"] = str(offset - per_page)
next_log_url = reverse(
browse_view_name, url_args=url_args, query_params=query_params
)
@@ -1029,7 +1055,7 @@
"snapshot": snapshot_id,
}
- if origin_info:
+ if origin_info and visit_info:
revision_metadata["origin url"] = origin_info["url"]
revision_metadata["origin visit date"] = format_utc_iso_date(visit_info["date"])
revision_metadata["origin visit type"] = visit_info["type"]
@@ -1077,8 +1103,12 @@
def browse_snapshot_branches(
- request, snapshot_id=None, origin_url=None, timestamp=None, branch_name_include=None
-):
+ request: HttpRequest,
+ snapshot_id: Optional[str] = None,
+ origin_url: Optional[str] = None,
+ timestamp: Optional[str] = None,
+ branch_name_include: Optional[str] = None,
+) -> HttpResponse:
"""
Django view implementation for browsing a list of branches in a snapshot
context.
@@ -1093,8 +1123,8 @@
visit_id=visit_id or None,
)
- branches_bc = request.GET.get("branches_breadcrumbs", "")
- branches_bc = branches_bc.split(",") if branches_bc else []
+ branches_bc_str = request.GET.get("branches_breadcrumbs", "")
+ branches_bc = branches_bc_str.split(",") if branches_bc_str else []
branches_from = branches_bc[-1] if branches_bc else ""
origin_info = snapshot_context["origin_info"]
@@ -1113,9 +1143,10 @@
target_types=["revision", "alias"],
branch_name_include_substring=branch_name_include,
)
- displayed_branches = []
+ displayed_branches: List[Dict[str, Any]] = []
if snapshot:
- displayed_branches, _, _ = process_snapshot_branches(snapshot)
+ branches, _, _ = process_snapshot_branches(snapshot)
+ displayed_branches = [dict(branch) for branch in branches]
for branch in displayed_branches:
rev_query_params = {}
@@ -1190,11 +1221,11 @@
def browse_snapshot_releases(
- request,
- snapshot_id=None,
- origin_url=None,
- timestamp=None,
- release_name_include=None,
+ request: HttpRequest,
+ snapshot_id: Optional[str] = None,
+ origin_url: Optional[str] = None,
+ timestamp: Optional[str] = None,
+ release_name_include: Optional[str] = None,
):
"""
Django view implementation for browsing a list of releases in a snapshot
@@ -1210,8 +1241,8 @@
visit_id=visit_id or None,
)
- rel_bc = request.GET.get("releases_breadcrumbs", "")
- rel_bc = rel_bc.split(",") if rel_bc else []
+ rel_bc_str = request.GET.get("releases_breadcrumbs", "")
+ rel_bc = rel_bc_str.split(",") if rel_bc_str else []
rel_from = rel_bc[-1] if rel_bc else ""
origin_info = snapshot_context["origin_info"]
@@ -1225,9 +1256,10 @@
target_types=["release", "alias"],
branch_name_include_substring=release_name_include,
)
- displayed_releases = []
+ displayed_releases: List[Dict[str, Any]] = []
if snapshot:
- _, displayed_releases, _ = process_snapshot_branches(snapshot)
+ _, releases, _ = process_snapshot_branches(snapshot)
+ displayed_releases = [dict(release) for release in releases]
for release in displayed_releases:
query_params_tgt = {"snapshot": snapshot_id, "release": release["name"]}
diff --git a/swh/web/browse/views/content.py b/swh/web/browse/views/content.py
--- a/swh/web/browse/views/content.py
+++ b/swh/web/browse/views/content.py
@@ -5,8 +5,9 @@
import difflib
from distutils.util import strtobool
+from typing import Any, Dict, Optional
-from django.http import HttpResponse, JsonResponse
+from django.http import HttpRequest, HttpResponse, JsonResponse
from django.shortcuts import redirect, render
from swh.model.hashutil import hash_to_hex
@@ -32,11 +33,11 @@
@browse_route(
- r"content/(?P<query_string>[0-9a-z_:]*[0-9a-f]+.)/raw/",
+ r"content/(?P<query_string>[0-9a-z_:]*[0-9a-f]+)/raw/",
view_name="browse-content-raw",
checksum_args=["query_string"],
)
-def content_raw(request, query_string):
+def content_raw(request: HttpRequest, query_string: str) -> HttpResponse:
"""Django view that produces a raw display of a content identified
by its hash value.
@@ -70,10 +71,12 @@
@browse_route(
- r"content/(?P<from_query_string>.*)/diff/(?P<to_query_string>.*)/",
+ r"content/(?P<from_query_string>.+)/diff/(?P<to_query_string>.+)/",
view_name="diff-contents",
)
-def _contents_diff(request, from_query_string, to_query_string):
+def _contents_diff(
+ request: HttpRequest, from_query_string: str, to_query_string: str
+) -> HttpResponse:
"""
Browse endpoint used to compute unified diffs between two contents.
@@ -102,11 +105,11 @@
content_to_size = 0
content_from_lines = []
content_to_lines = []
- force = request.GET.get("force", "false")
+ force_str = request.GET.get("force", "false")
path = request.GET.get("path", None)
language = "plaintext"
- force = bool(strtobool(force))
+ force = bool(strtobool(force_str))
if from_query_string == to_query_string:
diff_str = "File renamed without changes"
@@ -173,7 +176,7 @@
return JsonResponse(diff_data)
-def _get_content_from_request(request):
+def _get_content_from_request(request: HttpRequest) -> Dict[str, Any]:
path = request.GET.get("path")
if path is None:
raise BadInputExc("The path query parameter must be provided.")
@@ -196,16 +199,19 @@
browse_context="content",
)
root_directory = snapshot_context["root_directory"]
+ assert root_directory is not None # to keep mypy happy
return archive.lookup_directory_with_path(root_directory, path)
@browse_route(
- r"content/(?P<query_string>[0-9a-z_:]*[0-9a-f]+.)/",
+ r"content/(?P<query_string>[0-9a-z_:]*[0-9a-f]+)/",
r"content/",
view_name="browse-content",
checksum_args=["query_string"],
)
-def content_display(request, query_string=None):
+def content_display(
+ request: HttpRequest, query_string: Optional[str] = None
+) -> HttpResponse:
"""Django view that produces an HTML display of a content identified
by its hash value.
@@ -215,11 +221,11 @@
"""
if query_string is None:
# this case happens when redirected from origin/content or snapshot/content
- content = _get_content_from_request(request)
+ content_data = _get_content_from_request(request)
return redirect(
reverse(
"browse-content",
- url_args={"query_string": f"sha1_git:{content['target']}"},
+ url_args={"query_string": f"sha1_git:{content_data['target']}"},
query_params=request.GET,
),
)
@@ -233,7 +239,7 @@
snapshot_id = request.GET.get("snapshot") or request.GET.get("snapshot_id")
path = request.GET.get("path")
content_data = {}
- error_info = {"status_code": 200, "description": None}
+ error_info: Dict[str, Any] = {"status_code": 200, "description": None}
try:
content_data = request_content(query_string)
except NotFoundExc as e:
@@ -327,9 +333,9 @@
query_params=query_params,
)
breadcrumbs.append({"name": pi["name"], "url": dir_url})
- breadcrumbs.append({"name": filename, "url": None})
+ breadcrumbs.append({"name": filename, "url": ""})
- if path and root_dir != path:
+ if path and root_dir is not None and root_dir != path:
dir_info = archive.lookup_directory_with_path(root_dir, path)
directory_id = dir_info["target"]
elif root_dir != path:
@@ -360,10 +366,10 @@
sha256=content_checksums.get("sha256"),
blake2s256=content_checksums.get("blake2s256"),
content_url=content_url,
- mimetype=content_data.get("mimetype"),
- encoding=content_data.get("encoding"),
+ mimetype=content_data.get("mimetype", ""),
+ encoding=content_data.get("encoding", ""),
size=content_data.get("length", 0),
- language=content_data.get("language"),
+ language=content_data.get("language", ""),
root_directory=root_dir,
path=f"/{path}" if path else None,
filename=filename or "",
@@ -418,7 +424,7 @@
heading = "Content - %s" % content_checksums.get("sha1_git")
if breadcrumbs:
- content_path = "/".join([bc["name"] for bc in breadcrumbs])
+ content_path = "/".join(bc["name"] for bc in breadcrumbs)
heading += " - %s" % content_path
return render(
diff --git a/swh/web/browse/views/directory.py b/swh/web/browse/views/directory.py
--- a/swh/web/browse/views/directory.py
+++ b/swh/web/browse/views/directory.py
@@ -4,8 +4,9 @@
# See top-level LICENSE file for more information
import os
+from typing import Any, Dict, Optional
-from django.http import HttpResponse
+from django.http import HttpRequest, HttpResponse
from django.shortcuts import redirect, render
from swh.model.swhids import ObjectType
@@ -23,21 +24,24 @@
from swh.web.common.utils import gen_path_info, reverse, swh_object_icons
-def _directory_browse(request, sha1_git, path=None):
+def _directory_browse(
+ request: HttpRequest, sha1_git: str, path: Optional[str] = None
+) -> HttpResponse:
root_sha1_git = sha1_git
- error_info = {"status_code": 200, "description": None}
+ dir_sha1_git: Optional[str] = sha1_git
+ error_info: Dict[str, Any] = {"status_code": 200, "description": None}
if path:
try:
dir_info = archive.lookup_directory_with_path(sha1_git, path)
- sha1_git = dir_info["target"]
+ dir_sha1_git = dir_info["target"]
except NotFoundExc as e:
error_info["status_code"] = 404
error_info["description"] = f"NotFoundExc: {str(e)}"
- sha1_git = None
+ dir_sha1_git = None
dirs, files = [], []
- if sha1_git is not None:
- dirs, files = get_directory_entries(sha1_git)
+ if dir_sha1_git is not None:
+ dirs, files = get_directory_entries(dir_sha1_git)
origin_url = request.GET.get("origin_url")
if not origin_url:
origin_url = request.GET.get("origin")
@@ -56,7 +60,7 @@
except NotFoundExc as e:
if str(e).startswith("Origin"):
raw_dir_url = reverse(
- "browse-directory", url_args={"sha1_git": sha1_git}
+ "browse-directory", url_args={"sha1_git": dir_sha1_git}
)
error_message = (
"The Software Heritage archive has a directory "
@@ -144,7 +148,7 @@
dir_metadata = DirectoryMetadata(
object_type=ObjectType.DIRECTORY,
- object_id=sha1_git,
+ object_id=dir_sha1_git,
directory=root_sha1_git,
nb_files=len(files),
nb_dirs=len(dirs),
@@ -159,12 +163,14 @@
vault_cooking = {
"directory_context": True,
- "directory_swhid": f"swh:1:dir:{sha1_git}",
+ "directory_swhid": f"swh:1:dir:{dir_sha1_git}",
"revision_context": False,
"revision_swhid": None,
}
- swh_objects = [SWHObjectInfo(object_type=ObjectType.DIRECTORY, object_id=sha1_git)]
+ swh_objects = [
+ SWHObjectInfo(object_type=ObjectType.DIRECTORY, object_id=dir_sha1_git)
+ ]
if snapshot_context:
if snapshot_context["revision_id"]:
@@ -190,7 +196,7 @@
swhids_info = get_swhids_info(swh_objects, snapshot_context, dir_metadata)
- heading = "Directory - %s" % sha1_git
+ heading = "Directory - %s" % dir_sha1_git
if breadcrumbs:
dir_path = "/".join([bc["name"] for bc in breadcrumbs]) + "/"
heading += " - %s" % dir_path
@@ -244,7 +250,7 @@
view_name="browse-directory",
checksum_args=["sha1_git"],
)
-def directory_browse(request, sha1_git):
+def directory_browse(request: HttpRequest, sha1_git: str) -> HttpResponse:
"""Django view for browsing the content of a directory identified
by its sha1_git value.
@@ -259,7 +265,9 @@
view_name="browse-directory-legacy",
checksum_args=["sha1_git"],
)
-def directory_browse_legacy(request, sha1_git, path):
+def directory_browse_legacy(
+ request: HttpRequest, sha1_git: str, path: str
+) -> HttpResponse:
"""Django view for browsing the content of a directory identified
by its sha1_git value.
@@ -274,13 +282,15 @@
view_name="browse-directory-resolve-content-path",
checksum_args=["sha1_git"],
)
-def _directory_resolve_content_path(request, sha1_git):
+def _directory_resolve_content_path(
+ request: HttpRequest, sha1_git: str
+) -> HttpResponse:
"""
Internal endpoint redirecting to data url for a specific file path
relative to a root directory.
"""
try:
- path = os.path.normpath(request.GET.get("path"))
+ path = os.path.normpath(request.GET.get("path", ""))
if not path.startswith("../"):
dir_info = archive.lookup_directory_with_path(sha1_git, path)
if dir_info["type"] == "file":
diff --git a/swh/web/browse/views/origin.py b/swh/web/browse/views/origin.py
--- a/swh/web/browse/views/origin.py
+++ b/swh/web/browse/views/origin.py
@@ -1,8 +1,11 @@
-# Copyright (C) 2021 The Software Heritage developers
+# Copyright (C) 2021-2022 The Software Heritage developers
# See the AUTHORS file at the top-level directory of this distribution
# License: GNU Affero General Public License version 3, or any later version
# See top-level LICENSE file for more information
+from typing import Optional
+
+from django.http import HttpRequest, HttpResponse
from django.shortcuts import redirect, render
from swh.web.browse.browseurls import browse_route
@@ -25,7 +28,7 @@
r"origin/directory/",
view_name="browse-origin-directory",
)
-def origin_directory_browse(request):
+def origin_directory_browse(request: HttpRequest) -> HttpResponse:
"""Django view for browsing the content of a directory associated
to an origin for a given visit.
@@ -47,7 +50,12 @@
r"origin/(?P<origin_url>.+)/directory/",
view_name="browse-origin-directory-legacy",
)
-def origin_directory_browse_legacy(request, origin_url, timestamp=None, path=None):
+def origin_directory_browse_legacy(
+ request: HttpRequest,
+ origin_url: str,
+ timestamp: Optional[str] = None,
+ path: Optional[str] = None,
+) -> HttpResponse:
"""Django view for browsing the content of a directory associated
to an origin for a given visit.
@@ -68,7 +76,7 @@
r"origin/content/",
view_name="browse-origin-content",
)
-def origin_content_browse(request):
+def origin_content_browse(request: HttpRequest) -> HttpResponse:
"""
This route is deprecated; use http:get:`/browse/content` instead
@@ -87,7 +95,12 @@
r"origin/(?P<origin_url>.+)/content/",
view_name="browse-origin-content-legacy",
)
-def origin_content_browse_legacy(request, origin_url, path=None, timestamp=None):
+def origin_content_browse_legacy(
+ request: HttpRequest,
+ origin_url: str,
+ path: Optional[str] = None,
+ timestamp: Optional[str] = None,
+) -> HttpResponse:
"""
This route is deprecated; use http:get:`/browse/content` instead
@@ -106,7 +119,7 @@
r"origin/log/",
view_name="browse-origin-log",
)
-def origin_log_browse(request):
+def origin_log_browse(request: HttpRequest) -> HttpResponse:
"""
This route is deprecated; use http:get:`/browse/snapshot/log` instead
@@ -123,7 +136,9 @@
r"origin/(?P<origin_url>.+)/log/",
view_name="browse-origin-log-legacy",
)
-def origin_log_browse_legacy(request, origin_url, timestamp=None):
+def origin_log_browse_legacy(
+ request: HttpRequest, origin_url: str, timestamp: Optional[str] = None
+) -> HttpResponse:
"""
This route is deprecated; use http:get:`/browse/snapshot/log` instead
@@ -145,7 +160,7 @@
r"origin/branches/",
view_name="browse-origin-branches",
)
-def origin_branches_browse(request):
+def origin_branches_browse(request: HttpRequest) -> HttpResponse:
"""
This route is deprecated; use http:get:`/browse/snapshot/branches` instead
@@ -163,7 +178,9 @@
r"origin/(?P<origin_url>.+)/branches/",
view_name="browse-origin-branches-legacy",
)
-def origin_branches_browse_legacy(request, origin_url, timestamp=None):
+def origin_branches_browse_legacy(
+ request: HttpRequest, origin_url: str, timestamp: Optional[str] = None
+) -> HttpResponse:
"""
This route is deprecated; use http:get:`/browse/snapshot/branches` instead
@@ -182,7 +199,7 @@
r"origin/releases/",
view_name="browse-origin-releases",
)
-def origin_releases_browse(request):
+def origin_releases_browse(request: HttpRequest) -> HttpResponse:
"""
This route is deprecated; use http:get:`/browse/snapshot/releases` instead
@@ -200,7 +217,9 @@
r"origin/(?P<origin_url>.+)/releases/",
view_name="browse-origin-releases-legacy",
)
-def origin_releases_browse_legacy(request, origin_url, timestamp=None):
+def origin_releases_browse_legacy(
+ request: HttpRequest, origin_url: str, timestamp: Optional[str] = None
+) -> HttpResponse:
"""
This route is deprecated; use http:get:`/browse/snapshot/releases` instead
@@ -215,12 +234,15 @@
return redirect_to_new_route(request, "browse-snapshot-releases")
-def _origin_visits_browse(request, origin_url):
+def _origin_visits_browse(
+ request: HttpRequest, origin_url: Optional[str]
+) -> HttpResponse:
if origin_url is None:
raise BadInputExc("An origin URL must be provided as query parameter.")
origin_info = archive.lookup_origin({"url": origin_url})
origin_visits = get_origin_visits(origin_info)
+
snapshot_context = get_snapshot_context(origin_url=origin_url)
for i, visit in enumerate(origin_visits):
@@ -242,7 +264,7 @@
)
if not snapshot:
visit["snapshot"] = ""
- visit["date"] = parse_iso8601_date_to_utc(visit["date"]).timestamp()
+ visit["date"] = parse_iso8601_date_to_utc(visit["date"]).isoformat()
heading = "Origin visits - %s" % origin_url
@@ -263,7 +285,7 @@
@browse_route(r"origin/visits/", view_name="browse-origin-visits")
-def origin_visits_browse(request):
+def origin_visits_browse(request: HttpRequest) -> HttpResponse:
"""Django view that produces an HTML display of visits reporting
for a given origin.
@@ -276,7 +298,7 @@
@browse_route(
r"origin/(?P<origin_url>.+)/visits/", view_name="browse-origin-visits-legacy"
)
-def origin_visits_browse_legacy(request, origin_url):
+def origin_visits_browse_legacy(request: HttpRequest, origin_url: str) -> HttpResponse:
"""Django view that produces an HTML display of visits reporting
for a given origin.
@@ -287,7 +309,7 @@
@browse_route(r"origin/", view_name="browse-origin")
-def origin_browse(request):
+def origin_browse(request: HttpRequest) -> HttpResponse:
"""Django view that redirects to the display of the latest archived
snapshot for a given software origin.
"""
@@ -299,7 +321,7 @@
@browse_route(r"origin/(?P<origin_url>.+)/", view_name="browse-origin-legacy")
-def origin_browse_legacy(request, origin_url):
+def origin_browse_legacy(request: HttpRequest, origin_url: str) -> HttpResponse:
"""Django view that redirects to the display of the latest archived
snapshot for a given software origin.
"""
diff --git a/swh/web/browse/views/release.py b/swh/web/browse/views/release.py
--- a/swh/web/browse/views/release.py
+++ b/swh/web/browse/views/release.py
@@ -3,6 +3,9 @@
# License: GNU Affero General Public License version 3, or any later version
# See top-level LICENSE file for more information
+from typing import Optional
+
+from django.http import HttpRequest, HttpResponse
from django.shortcuts import render
from swh.model.swhids import ObjectType
@@ -19,7 +22,7 @@
from swh.web.common import archive
from swh.web.common.exc import NotFoundExc, sentry_capture_exception
from swh.web.common.identifiers import get_swhids_info
-from swh.web.common.typing import ReleaseMetadata, SWHObjectInfo
+from swh.web.common.typing import ReleaseMetadata, SnapshotContext, SWHObjectInfo
from swh.web.common.utils import format_utc_iso_date, reverse
@@ -28,7 +31,7 @@
view_name="browse-release",
checksum_args=["sha1_git"],
)
-def release_browse(request, sha1_git):
+def release_browse(request: HttpRequest, sha1_git: str) -> HttpResponse:
"""
Django view that produces an HTML display of a release
identified by its id.
@@ -36,7 +39,7 @@
The url that points to it is :http:get:`/browse/release/(sha1_git)/`.
"""
release = archive.lookup_release(sha1_git)
- snapshot_context = {}
+ snapshot_context: Optional[SnapshotContext] = None
origin_info = None
snapshot_id = request.GET.get("snapshot_id")
if not snapshot_id:
@@ -76,7 +79,8 @@
snapshot_id, release_name=release["name"]
)
- snapshot_id = snapshot_context.get("snapshot_id", None)
+ if snapshot_context is not None:
+ snapshot_id = snapshot_context.get("snapshot_id", None)
release_metadata = ReleaseMetadata(
object_type=ObjectType.RELEASE,
diff --git a/swh/web/browse/views/revision.py b/swh/web/browse/views/revision.py
--- a/swh/web/browse/views/revision.py
+++ b/swh/web/browse/views/revision.py
@@ -6,8 +6,9 @@
import hashlib
import json
import textwrap
+from typing import Any, Dict, List, Optional
-from django.http import JsonResponse
+from django.http import HttpRequest, HttpResponse, JsonResponse
from django.shortcuts import render
from django.utils.safestring import mark_safe
@@ -30,7 +31,7 @@
from swh.web.common import archive
from swh.web.common.exc import NotFoundExc, http_status_code_message
from swh.web.common.identifiers import get_swhids_info
-from swh.web.common.typing import RevisionMetadata, SWHObjectInfo
+from swh.web.common.typing import RevisionMetadata, SnapshotContext, SWHObjectInfo
from swh.web.common.utils import (
format_utc_iso_date,
gen_path_info,
@@ -39,7 +40,12 @@
)
-def _gen_content_url(revision, query_string, path, snapshot_context):
+def _gen_content_url(
+ revision: Dict[str, Any],
+ query_string: str,
+ path: str,
+ snapshot_context: Optional[SnapshotContext],
+) -> str:
if snapshot_context:
query_params = snapshot_context["query_params"]
query_params["path"] = path
@@ -55,7 +61,7 @@
return content_url
-def _gen_diff_link(idx, diff_anchor, link_text):
+def _gen_diff_link(idx: int, diff_anchor: str, link_text: str) -> str:
if idx < _max_displayed_file_diffs:
return gen_link(diff_anchor, link_text)
else:
@@ -66,7 +72,11 @@
_max_displayed_file_diffs = 1000
-def _gen_revision_changes_list(revision, changes, snapshot_context):
+def _gen_revision_changes_list(
+ revision: Dict[str, Any],
+ changes: List[Dict[str, Any]],
+ snapshot_context: Optional[SnapshotContext],
+) -> str:
"""
Returns a HTML string describing the file changes
introduced in a revision.
@@ -151,7 +161,7 @@
view_name="diff-revision",
checksum_args=["sha1_git"],
)
-def _revision_diff(request, sha1_git):
+def _revision_diff(request: HttpRequest, sha1_git: str) -> HttpResponse:
"""
Browse internal endpoint to compute revision diff
"""
@@ -161,7 +171,8 @@
if not origin_url:
origin_url = request.GET.get("origin", None)
timestamp = request.GET.get("timestamp", None)
- visit_id = request.GET.get("visit_id", None)
+ visit_id_str = request.GET.get("visit_id", None)
+ visit_id = int(visit_id_str) if visit_id_str is not None else None
if origin_url:
snapshot_context = get_snapshot_context(
origin_url=origin_url, timestamp=timestamp, visit_id=visit_id
@@ -186,7 +197,7 @@
view_name="browse-revision-log",
checksum_args=["sha1_git"],
)
-def revision_log_browse(request, sha1_git):
+def revision_log_browse(request: HttpRequest, sha1_git: str) -> HttpResponse:
"""
Django view that produces an HTML display of the history
log for a revision identified by its id.
@@ -296,7 +307,7 @@
view_name="browse-revision",
checksum_args=["sha1_git"],
)
-def revision_browse(request, sha1_git):
+def revision_browse(request: HttpRequest, sha1_git: str) -> HttpResponse:
"""
Django view that produces an HTML display of a revision
identified by its id.
@@ -350,7 +361,7 @@
elif snapshot_id:
snapshot_context = get_snapshot_context(snapshot_id)
- error_info = {"status_code": 200, "description": None}
+ error_info: Dict[str, Any] = {"status_code": 200, "description": None}
if path:
try:
diff --git a/swh/web/browse/views/snapshot.py b/swh/web/browse/views/snapshot.py
--- a/swh/web/browse/views/snapshot.py
+++ b/swh/web/browse/views/snapshot.py
@@ -1,9 +1,11 @@
-# Copyright (C) 2018-2019 The Software Heritage developers
+# Copyright (C) 2018-2022 The Software Heritage developers
# See the AUTHORS file at the top-level directory of this distribution
# License: GNU Affero General Public License version 3, or any later version
# See top-level LICENSE file for more information
+from typing import Optional
+from django.http import HttpRequest, HttpResponse
from django.shortcuts import redirect
from swh.web.browse.browseurls import browse_route
@@ -18,7 +20,7 @@
from swh.web.common.utils import redirect_to_new_route, reverse
-def get_snapshot_from_request(request):
+def get_snapshot_from_request(request: HttpRequest) -> str:
snapshot = request.GET.get("snapshot")
if snapshot:
return snapshot
@@ -34,7 +36,7 @@
view_name="browse-snapshot",
checksum_args=["snapshot_id"],
)
-def snapshot_browse(request, snapshot_id):
+def snapshot_browse(request: HttpRequest, snapshot_id: str) -> HttpResponse:
"""Django view for browsing the content of a snapshot.
The url that points to it is :http:get:`/browse/snapshot/(snapshot_id)/`
@@ -52,7 +54,7 @@
view_name="browse-snapshot-directory",
checksum_args=["snapshot_id"],
)
-def snapshot_directory_browse(request, snapshot_id):
+def snapshot_directory_browse(request: HttpRequest, snapshot_id: str) -> HttpResponse:
"""Django view for browsing the content of a directory collected
in a snapshot.
@@ -71,7 +73,9 @@
view_name="browse-snapshot-directory-legacy",
checksum_args=["snapshot_id"],
)
-def snapshot_directory_browse_legacy(request, snapshot_id, path=None):
+def snapshot_directory_browse_legacy(
+ request: HttpRequest, snapshot_id: str, path: Optional[str] = None
+) -> HttpResponse:
"""Django view for browsing the content of a directory collected
in a snapshot.
@@ -91,7 +95,7 @@
view_name="browse-snapshot-content",
checksum_args=["snapshot_id"],
)
-def snapshot_content_browse(request, snapshot_id):
+def snapshot_content_browse(request: HttpRequest, snapshot_id: str) -> HttpResponse:
"""
This route is deprecated; use http:get:`/browse/content` instead
@@ -109,7 +113,9 @@
view_name="browse-snapshot-content-legacy",
checksum_args=["snapshot_id"],
)
-def snapshot_content_browse_legacy(request, snapshot_id, path):
+def snapshot_content_browse_legacy(
+ request: HttpRequest, snapshot_id: str, path: str
+) -> HttpResponse:
"""
This route is deprecated; use http:get:`/browse/content` instead
@@ -128,7 +134,9 @@
view_name="browse-snapshot-log",
checksum_args=["snapshot_id"],
)
-def snapshot_log_browse(request, snapshot_id=None):
+def snapshot_log_browse(
+ request: HttpRequest, snapshot_id: Optional[str] = None
+) -> HttpResponse:
"""Django view that produces an HTML display of revisions history (aka
the commit log) collected in a snapshot.
@@ -161,7 +169,9 @@
view_name="browse-snapshot-branches",
checksum_args=["snapshot_id"],
)
-def snapshot_branches_browse(request, snapshot_id=None):
+def snapshot_branches_browse(
+ request: HttpRequest, snapshot_id: Optional[str] = None
+) -> HttpResponse:
"""Django view that produces an HTML display of the list of branches
collected in a snapshot.
@@ -196,7 +206,9 @@
view_name="browse-snapshot-releases",
checksum_args=["snapshot_id"],
)
-def snapshot_releases_browse(request, snapshot_id=None):
+def snapshot_releases_browse(
+ request: HttpRequest, snapshot_id: Optional[str] = None
+) -> HttpResponse:
"""Django view that produces an HTML display of the list of releases
collected in a snapshot.
diff --git a/swh/web/common/identifiers.py b/swh/web/common/identifiers.py
--- a/swh/web/common/identifiers.py
+++ b/swh/web/common/identifiers.py
@@ -1,9 +1,9 @@
-# Copyright (C) 2020-2021 The Software Heritage developers
+# Copyright (C) 2020-2022 The Software Heritage developers
# See the AUTHORS file at the top-level directory of this distribution
# License: GNU Affero General Public License version 3, or any later version
# See top-level LICENSE file for more information
-from typing import Any, Dict, Iterable, List, Optional
+from typing import Any, Dict, Iterable, List, Mapping, Optional
from urllib.parse import quote, unquote
from typing_extensions import TypedDict
@@ -274,7 +274,7 @@
def get_swhids_info(
swh_objects: Iterable[SWHObjectInfo],
snapshot_context: Optional[SnapshotContext] = None,
- extra_context: Optional[Dict[str, Any]] = None,
+ extra_context: Optional[Mapping[str, Any]] = None,
) -> List[SWHIDInfo]:
"""
Returns a list of dict containing info related to SWHIDs of objects.
diff --git a/swh/web/common/typing.py b/swh/web/common/typing.py
--- a/swh/web/common/typing.py
+++ b/swh/web/common/typing.py
@@ -137,7 +137,7 @@
class SWHObjectInfo(TypedDict):
object_type: ObjectType
- object_id: str
+ object_id: Optional[str]
class SWHIDContext(TypedDict, total=False):
@@ -182,12 +182,12 @@
class DirectoryMetadata(SWHObjectInfo, SWHObjectInfoMetadata):
- directory: str
- nb_files: int
- nb_dirs: int
- sum_file_sizes: int
+ directory: Optional[str]
+ nb_files: Optional[int]
+ nb_dirs: Optional[int]
+ sum_file_sizes: Optional[int]
root_directory: Optional[str]
- path: str
+ path: Optional[str]
revision: Optional[str]
revision_found: Optional[bool]
release: Optional[str]
File Metadata
Details
Attached
Mime Type
text/plain
Expires
Dec 20 2024, 12:37 PM (11 w, 4 d ago)
Storage Engine
blob
Storage Format
Raw Data
Storage Handle
3227798
Attached To
D7973: browse: Add typing to view function signatures
Event Timeline
Log In to Comment