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
7 changes: 7 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,13 @@ Types of changes:
- `Fixed`: for any bug fixes.
- `Security`: in case of vulnerabilities.

## [2.1.0]

### Changed

- Improved the usage metrics logging system to handle class-based views, including the individual Blast data object endpoints and the transient dataset download endpoints.
- Replaced Alias API view functions with ModelViewSet subclass for consistency with other data object API endpoints and to benefit from the Django REST Framework. (While this API change is technically *not* backwards-compatible, the nature of the `/api/alias/` functionality and its lack of known use to date justifies this "minor" violation of semantic versioning.)

## [2.0.1]

### Fixed
Expand Down
8 changes: 3 additions & 5 deletions app/api/serializers.py
Original file line number Diff line number Diff line change
Expand Up @@ -138,15 +138,13 @@ class Meta:


class AliasSerializer(serializers.ModelSerializer):
transient = TransientSerializer(read_only=True)
host = HostSerializer(read_only=True)
transient = serializers.SerializerMethodField()
host = serializers.SerializerMethodField()

class Meta:
model = models.Alias
fields = ["alias", "transient", "host"]

transient = serializers.SerializerMethodField()
host = serializers.SerializerMethodField()
depth = 1

@extend_schema_field(serializers.CharField(allow_null=True))
def get_transient(self, obj):
Expand Down
24 changes: 13 additions & 11 deletions app/api/tests/test_api.py
Original file line number Diff line number Diff line change
Expand Up @@ -92,9 +92,10 @@ def test_alias(self):
name = '2022testone'
alias = '2022testone-alias-test!'
# Attempt to create an alias without permission
response = self.client.post(f'/api/alias/{alias}/{object_type}/{name}/')
# print(f'[{response.status_code}] {response.content}')
data = json.loads(response.content)
response = self.client.post('/api/alias/', json={
'alias': alias,
object_type: name,
})
self.assertTrue(response.status_code == status.HTTP_403_FORBIDDEN)
# Grant the user permission
add_permission = Permission.objects.get(
Expand All @@ -103,22 +104,25 @@ def test_alias(self):
)
user.user_permissions.add(add_permission)
assert user.has_perm('host.add_alias')
response = self.client.post(f'/api/alias/{alias}/{object_type}/{name}/')
response = self.client.post('/api/alias/', data={
'alias': alias,
object_type: name,
})
self.assertTrue(response.status_code == status.HTTP_201_CREATED)
data = json.loads(response.content)
self.assertTrue(data["message"].startswith("Alias successfully created:"))
# Fetch information about the alias anonymously
self.client.logout()
response = self.client.get(f'/api/alias/{alias}/')
self.assertTrue(response.status_code == status.HTTP_200_OK)
# Fail when attempting to create another alias with the same name
self.client.force_login(user)
object_type = 'host'
response = self.client.post(f'/api/alias/{alias}/{object_type}/{name}/')
self.assertTrue(response.status_code == status.HTTP_409_CONFLICT)
response = self.client.post('/api/alias/', data={
'alias': alias,
object_type: name,
})
self.assertTrue(response.status_code == status.HTTP_400_BAD_REQUEST)
# Attempt to delete an alias without permission
response = self.client.delete(f'/api/alias/{alias}/')
# print(f'[{response.status_code}] {response.content}')
self.assertTrue(response.status_code == status.HTTP_403_FORBIDDEN)
# Grant the user delete permission
delete_permission = Permission.objects.get(
Expand All @@ -128,10 +132,8 @@ def test_alias(self):
user.user_permissions.add(delete_permission)
# Delete the alias
response = self.client.delete(f'/api/alias/{alias}/')
# print(f'[{response.status_code}] {response.content}')
self.assertTrue(response.status_code == status.HTTP_204_NO_CONTENT)
# Attempt to delete a non-existent alias
alias = 'foo'
response = self.client.delete(f'/api/alias/{alias}/')
self.assertTrue(response.status_code == status.HTTP_404_NOT_FOUND)
# print(f'[{response.status_code}] {response.content}')
37 changes: 24 additions & 13 deletions app/api/urls.py
Original file line number Diff line number Diff line change
@@ -1,8 +1,9 @@
import os

from django.urls import path, re_path
from django.urls import re_path, include
from rest_framework.routers import DefaultRouter

from . import views
import api.views

base_path = os.environ.get("BASE_PATH", "").strip("/")
if base_path != "":
Expand All @@ -11,20 +12,30 @@
urlpatterns = [
re_path(
base_path + r"^dataset/(?P<transient_name>[a-zA-Z0-9_-]+)/export/$",
views.DatasetExportView.as_view(),
api.views.DatasetExportView.as_view(),
),
re_path(
base_path + r"^dataset/(?P<transient_name>[a-zA-Z0-9_-]+)/$",
views.DatasetView.as_view(),
api.views.DatasetView.as_view(),
),
path(base_path + 'alias/<str:alias>/', views.alias_handler_get_delete, ),
path(base_path + 'alias/<str:alias>/<str:object_type>/<str:name>/', views.alias_handler_post),
]

# if os.environ.get("ALLOW_API_POST") == "YES":
# urlpatterns.append(
# path(
# f"""{base_path}transient/post/name=<str:transient_name>&ra=<str:transient_ra>&dec=<str:transient_dec>""",
# views.post_transient,
# )
# )
router = DefaultRouter()

router.register(r"transient", api.views.TransientViewSet)
router.register(r"aperture", api.views.ApertureViewSet)
router.register(r"cutout", api.views.CutoutViewSet, basename="cutout")
router.register(r"filter", api.views.FilterViewSet)
router.register(r"aperturephotometry", api.views.AperturePhotometryViewSet)
router.register(r"sedfittingresult", api.views.SEDFittingResultViewSet, basename="sedfittingresult")
router.register(r"taskregister", api.views.TaskRegisterViewSet)
router.register(r"task", api.views.TaskViewSet)
router.register(r"host", api.views.HostViewSet)
router.register(r"alias", api.views.AliasViewSet)

# Login/Logout
api_url_patterns = [
re_path("", include(router.urls)),
]

urlpatterns += api_url_patterns
Loading