diff --git a/admin/nodes/forms.py b/admin/nodes/forms.py new file mode 100644 index 00000000000..553c465da4a --- /dev/null +++ b/admin/nodes/forms.py @@ -0,0 +1,7 @@ +from django import forms + + +class RegistrationDateForm(forms.Form): + registered_date = forms.DateTimeField( + widget=forms.DateTimeInput(attrs={'class': 'form-control'}), + ) diff --git a/admin/nodes/urls.py b/admin/nodes/urls.py index 1d5f6e0bac9..a697eccc968 100644 --- a/admin/nodes/urls.py +++ b/admin/nodes/urls.py @@ -18,6 +18,7 @@ re_path(r'^(?P[a-z0-9]+)/logs/$', views.AdminNodeLogView.as_view(), name='node-logs'), re_path(r'^(?P[a-z0-9]+)/schema_responses/$', views.AdminNodeSchemaResponseView.as_view(), name='schema-responses'), + re_path(r'^(?P[a-z0-9]+)/update_registration_date/$', views.RegistrationUpdateDateView.as_view(), name='update-registration-date'), re_path(r'^(?P[a-z0-9]+)/update_embargo/$', views.RegistrationUpdateEmbargoView.as_view(), name='update-embargo'), re_path(r'^(?P[a-z0-9]+)/change_provider/$', views.RegistrationChangeProviderView.as_view(), name='change-provider'), re_path(r'^(?P[a-z0-9]+)/remove/$', views.NodeDeleteView.as_view(), name='remove'), diff --git a/admin/nodes/views.py b/admin/nodes/views.py index db0f0119f18..a363c62ee37 100644 --- a/admin/nodes/views.py +++ b/admin/nodes/views.py @@ -22,6 +22,7 @@ from admin.base.views import GuidView from admin.base.forms import GuidForm from admin.notifications.views import delete_selected_notifications +from admin.nodes.forms import RegistrationDateForm from api.share.utils import update_share from api.caching.tasks import update_storage_usage_cache @@ -89,6 +90,36 @@ def get_success_url(self): return reverse('nodes:node', kwargs={'guid': self.kwargs['guid']}) +class RegistrationUpdateDateView(NodeMixin, View): + permission_required = 'osf.change_node' + raise_exception = True + + def post(self, request, *args, **kwargs): + node = self.get_object() + form = RegistrationDateForm(request.POST) + if form.is_valid(): + last_date = node.registered_date + new_date = form.cleaned_data['registered_date'] + node.registered_date = new_date + node.created = new_date + node.save() + + node.add_log( + action=NodeLog.REGISTRATION_DATE_UPDATED, + auth=request, + params={ + 'last_date': str(last_date), + 'new_date': str(new_date) + }, + log_date=timezone.now(), + should_hide=True, + ) + messages.success(request, 'Registration date updated successfully.') + else: + messages.error(request, 'Please enter a valid date.') + return redirect(self.get_success_url()) + + class NodeView(NodeMixin, GuidView): """ Allows authorized users to view node info. """ @@ -100,6 +131,9 @@ def get_context_data(self, **kwargs): context = super().get_context_data(**kwargs) node = self.get_object() + if isinstance(node, Registration): + context['registration_date_form'] = RegistrationDateForm(initial={'registered_date': node.registered_date}) + children = node.get_nodes(is_node_link=False) # Annotate guid because django templates prohibit accessing attributes that start with underscores children = AbstractNode.objects.filter( diff --git a/admin/templates/nodes/node.html b/admin/templates/nodes/node.html index caf8bd5ebc6..177b29ddaf6 100644 --- a/admin/templates/nodes/node.html +++ b/admin/templates/nodes/node.html @@ -42,6 +42,28 @@

{{ node.type|cut:'osf.'|title }}: {{ node.title }} + {% csrf_token %} + {{ registration_date_form.as_p }} + + + + + {% endif %} + {% endif %} Title {{ node.title }} diff --git a/osf/models/nodelog.py b/osf/models/nodelog.py index 0297c42bdec..a098a7a0ef8 100644 --- a/osf/models/nodelog.py +++ b/osf/models/nodelog.py @@ -86,6 +86,7 @@ class NodeLog(ObjectIDMixin, BaseModel): CATEGORY_UPDATED = 'category_updated' ARTICLE_DOI_UPDATED = 'article_doi_updated' + REGISTRATION_DATE_UPDATED = 'registration_date_updated' ADDON_ADDED = 'addon_added' ADDON_REMOVED = 'addon_removed'