mirror of
https://github.com/ansible/awx.git
synced 2026-01-12 10:30:03 -03:30
add API versioning for /api/v2/
This commit is contained in:
parent
7dda6106d1
commit
95ea370e5e
@ -31,6 +31,7 @@ from awx.api.filters import FieldLookupBackend
|
||||
from awx.main.models import * # noqa
|
||||
from awx.main.utils import * # noqa
|
||||
from awx.api.serializers import ResourceAccessListElementSerializer
|
||||
from awx.api.versioning import URLPathVersioning
|
||||
|
||||
__all__ = ['APIView', 'GenericAPIView', 'ListAPIView', 'SimpleListAPIView',
|
||||
'ListCreateAPIView', 'SubListAPIView', 'SubListCreateAPIView',
|
||||
@ -86,6 +87,8 @@ def get_view_description(cls, html=False):
|
||||
|
||||
class APIView(views.APIView):
|
||||
|
||||
versioning_class = URLPathVersioning
|
||||
|
||||
def initialize_request(self, request, *args, **kwargs):
|
||||
'''
|
||||
Store the Django REST Framework Request object as an attribute on the
|
||||
@ -161,6 +164,7 @@ class APIView(views.APIView):
|
||||
'new_in_240': getattr(self, 'new_in_240', False),
|
||||
'new_in_300': getattr(self, 'new_in_300', False),
|
||||
'new_in_310': getattr(self, 'new_in_310', False),
|
||||
'new_in_320': getattr(self, 'new_in_320', False),
|
||||
'deprecated': getattr(self, 'deprecated', False),
|
||||
}
|
||||
|
||||
@ -188,6 +192,23 @@ class APIView(views.APIView):
|
||||
|
||||
return data
|
||||
|
||||
def determine_version(self, request, *args, **kwargs):
|
||||
return (
|
||||
getattr(request, 'version', None),
|
||||
getattr(request, 'versioning_scheme', None),
|
||||
)
|
||||
|
||||
def dispatch(self, request, *args, **kwargs):
|
||||
if self.versioning_class is not None:
|
||||
scheme = self.versioning_class()
|
||||
request.version, request.versioning_scheme = (
|
||||
scheme.determine_version(request, *args, **kwargs),
|
||||
scheme
|
||||
)
|
||||
if 'version' in kwargs:
|
||||
kwargs.pop('version')
|
||||
return super(APIView, self).dispatch(request, *args, **kwargs)
|
||||
|
||||
|
||||
class GenericAPIView(generics.GenericAPIView, APIView):
|
||||
# Base class for all model-based views.
|
||||
@ -424,7 +445,7 @@ class SubListCreateAPIView(SubListAPIView, ListCreateAPIView):
|
||||
obj = serializer.save()
|
||||
serializer = self.get_serializer(instance=obj)
|
||||
|
||||
headers = {'Location': obj.get_absolute_url()}
|
||||
headers = {'Location': obj.get_absolute_url(request)}
|
||||
return Response(serializer.data, status=status.HTTP_201_CREATED, headers=headers)
|
||||
|
||||
|
||||
|
||||
@ -4,9 +4,10 @@
|
||||
# Python
|
||||
import copy
|
||||
import json
|
||||
import logging
|
||||
import re
|
||||
import six
|
||||
import logging
|
||||
import urllib
|
||||
from collections import OrderedDict
|
||||
from dateutil import rrule
|
||||
|
||||
@ -18,7 +19,6 @@ from django.conf import settings
|
||||
from django.contrib.auth import authenticate
|
||||
from django.contrib.auth.models import User
|
||||
from django.contrib.contenttypes.models import ContentType
|
||||
from django.core.urlresolvers import reverse
|
||||
from django.core.exceptions import ObjectDoesNotExist, ValidationError as DjangoValidationError
|
||||
from django.db import models
|
||||
from django.utils.translation import ugettext_lazy as _
|
||||
@ -43,11 +43,12 @@ from awx.main.models import * # noqa
|
||||
from awx.main.access import get_user_capabilities
|
||||
from awx.main.fields import ImplicitRoleField
|
||||
from awx.main.utils import (
|
||||
get_type_for_model, get_model_for_type, build_url, timestamp_apiformat,
|
||||
get_type_for_model, get_model_for_type, timestamp_apiformat,
|
||||
camelcase_to_underscore, getattrd, parse_yaml_or_json)
|
||||
from awx.main.validators import vars_validate_or_raise
|
||||
|
||||
from awx.conf.license import feature_enabled
|
||||
from awx.api.versioning import reverse
|
||||
from awx.api.fields import BooleanNullField, CharNullField, ChoiceNullField, EncryptedPasswordField, VerbatimField
|
||||
|
||||
logger = logging.getLogger('awx.api.serializers')
|
||||
@ -103,7 +104,7 @@ SUMMARIZABLE_FK_FIELDS = {
|
||||
}
|
||||
|
||||
|
||||
def reverse_gfk(content_object):
|
||||
def reverse_gfk(content_object, request):
|
||||
'''
|
||||
Computes a reverse for a GenericForeignKey field.
|
||||
|
||||
@ -116,7 +117,7 @@ def reverse_gfk(content_object):
|
||||
return {}
|
||||
|
||||
return {
|
||||
camelcase_to_underscore(content_object.__class__.__name__): content_object.get_absolute_url()
|
||||
camelcase_to_underscore(content_object.__class__.__name__): content_object.get_absolute_url(request=request)
|
||||
}
|
||||
|
||||
|
||||
@ -268,9 +269,9 @@ class BaseSerializer(serializers.ModelSerializer):
|
||||
if obj is None or not hasattr(obj, 'get_absolute_url'):
|
||||
return ''
|
||||
elif isinstance(obj, User):
|
||||
return reverse('api:user_detail', args=(obj.pk,))
|
||||
return self.reverse('api:user_detail', kwargs={'pk': obj.pk})
|
||||
else:
|
||||
return obj.get_absolute_url()
|
||||
return obj.get_absolute_url(request=self.context.get('request'))
|
||||
|
||||
def _get_related(self, obj):
|
||||
return {} if obj is None else self.get_related(obj)
|
||||
@ -278,9 +279,9 @@ class BaseSerializer(serializers.ModelSerializer):
|
||||
def get_related(self, obj):
|
||||
res = OrderedDict()
|
||||
if getattr(obj, 'created_by', None):
|
||||
res['created_by'] = reverse('api:user_detail', args=(obj.created_by.pk,))
|
||||
res['created_by'] = self.reverse('api:user_detail', kwargs={'pk': obj.created_by.pk})
|
||||
if getattr(obj, 'modified_by', None):
|
||||
res['modified_by'] = reverse('api:user_detail', args=(obj.modified_by.pk,))
|
||||
res['modified_by'] = self.reverse('api:user_detail', kwargs={'pk': obj.modified_by.pk})
|
||||
return res
|
||||
|
||||
def _get_summary_fields(self, obj):
|
||||
@ -496,6 +497,10 @@ class BaseSerializer(serializers.ModelSerializer):
|
||||
raise ValidationError(d)
|
||||
return attrs
|
||||
|
||||
def reverse(self, *args, **kwargs):
|
||||
kwargs['request'] = self.context.get('request')
|
||||
return reverse(*args, **kwargs)
|
||||
|
||||
|
||||
class EmptySerializer(serializers.Serializer):
|
||||
pass
|
||||
@ -525,11 +530,11 @@ class UnifiedJobTemplateSerializer(BaseSerializer):
|
||||
def get_related(self, obj):
|
||||
res = super(UnifiedJobTemplateSerializer, self).get_related(obj)
|
||||
if obj.current_job:
|
||||
res['current_job'] = obj.current_job.get_absolute_url()
|
||||
res['current_job'] = obj.current_job.get_absolute_url(request=self.context.get('request'))
|
||||
if obj.last_job:
|
||||
res['last_job'] = obj.last_job.get_absolute_url()
|
||||
res['last_job'] = obj.last_job.get_absolute_url(request=self.context.get('request'))
|
||||
if obj.next_schedule:
|
||||
res['next_schedule'] = obj.next_schedule.get_absolute_url()
|
||||
res['next_schedule'] = obj.next_schedule.get_absolute_url(request=self.context.get('request'))
|
||||
return res
|
||||
|
||||
def get_types(self):
|
||||
@ -589,19 +594,19 @@ class UnifiedJobSerializer(BaseSerializer):
|
||||
def get_related(self, obj):
|
||||
res = super(UnifiedJobSerializer, self).get_related(obj)
|
||||
if obj.unified_job_template:
|
||||
res['unified_job_template'] = obj.unified_job_template.get_absolute_url()
|
||||
res['unified_job_template'] = obj.unified_job_template.get_absolute_url(request=self.context.get('request'))
|
||||
if obj.schedule:
|
||||
res['schedule'] = obj.schedule.get_absolute_url()
|
||||
res['schedule'] = obj.schedule.get_absolute_url(request=self.context.get('request'))
|
||||
if isinstance(obj, ProjectUpdate):
|
||||
res['stdout'] = reverse('api:project_update_stdout', args=(obj.pk,))
|
||||
res['stdout'] = self.reverse('api:project_update_stdout', kwargs={'pk': obj.pk})
|
||||
elif isinstance(obj, InventoryUpdate):
|
||||
res['stdout'] = reverse('api:inventory_update_stdout', args=(obj.pk,))
|
||||
res['stdout'] = self.reverse('api:inventory_update_stdout', kwargs={'pk': obj.pk})
|
||||
elif isinstance(obj, Job):
|
||||
res['stdout'] = reverse('api:job_stdout', args=(obj.pk,))
|
||||
res['stdout'] = self.reverse('api:job_stdout', kwargs={'pk': obj.pk})
|
||||
elif isinstance(obj, AdHocCommand):
|
||||
res['stdout'] = reverse('api:ad_hoc_command_stdout', args=(obj.pk,))
|
||||
res['stdout'] = self.reverse('api:ad_hoc_command_stdout', kwargs={'pk': obj.pk})
|
||||
if obj.workflow_job_id:
|
||||
res['source_workflow_job'] = reverse('api:workflow_job_detail', args=(obj.workflow_job_id,))
|
||||
res['source_workflow_job'] = self.reverse('api:workflow_job_detail', kwargs={'pk': obj.workflow_job_id})
|
||||
return res
|
||||
|
||||
def get_summary_fields(self, obj):
|
||||
@ -811,14 +816,14 @@ class UserSerializer(BaseSerializer):
|
||||
def get_related(self, obj):
|
||||
res = super(UserSerializer, self).get_related(obj)
|
||||
res.update(dict(
|
||||
teams = reverse('api:user_teams_list', args=(obj.pk,)),
|
||||
organizations = reverse('api:user_organizations_list', args=(obj.pk,)),
|
||||
admin_of_organizations = reverse('api:user_admin_of_organizations_list', args=(obj.pk,)),
|
||||
projects = reverse('api:user_projects_list', args=(obj.pk,)),
|
||||
credentials = reverse('api:user_credentials_list', args=(obj.pk,)),
|
||||
roles = reverse('api:user_roles_list', args=(obj.pk,)),
|
||||
activity_stream = reverse('api:user_activity_stream_list', args=(obj.pk,)),
|
||||
access_list = reverse('api:user_access_list', args=(obj.pk,)),
|
||||
teams = self.reverse('api:user_teams_list', kwargs={'pk': obj.pk}),
|
||||
organizations = self.reverse('api:user_organizations_list', kwargs={'pk': obj.pk}),
|
||||
admin_of_organizations = self.reverse('api:user_admin_of_organizations_list', kwargs={'pk': obj.pk}),
|
||||
projects = self.reverse('api:user_projects_list', kwargs={'pk': obj.pk}),
|
||||
credentials = self.reverse('api:user_credentials_list', kwargs={'pk': obj.pk}),
|
||||
roles = self.reverse('api:user_roles_list', kwargs={'pk': obj.pk}),
|
||||
activity_stream = self.reverse('api:user_activity_stream_list', kwargs={'pk': obj.pk}),
|
||||
access_list = self.reverse('api:user_access_list', kwargs={'pk': obj.pk}),
|
||||
))
|
||||
return res
|
||||
|
||||
@ -864,20 +869,20 @@ class OrganizationSerializer(BaseSerializer):
|
||||
def get_related(self, obj):
|
||||
res = super(OrganizationSerializer, self).get_related(obj)
|
||||
res.update(dict(
|
||||
projects = reverse('api:organization_projects_list', args=(obj.pk,)),
|
||||
inventories = reverse('api:organization_inventories_list', args=(obj.pk,)),
|
||||
workflow_job_templates = reverse('api:organization_workflow_job_templates_list', args=(obj.pk,)),
|
||||
users = reverse('api:organization_users_list', args=(obj.pk,)),
|
||||
admins = reverse('api:organization_admins_list', args=(obj.pk,)),
|
||||
teams = reverse('api:organization_teams_list', args=(obj.pk,)),
|
||||
credentials = reverse('api:organization_credential_list', args=(obj.pk,)),
|
||||
activity_stream = reverse('api:organization_activity_stream_list', args=(obj.pk,)),
|
||||
notification_templates = reverse('api:organization_notification_templates_list', args=(obj.pk,)),
|
||||
notification_templates_any = reverse('api:organization_notification_templates_any_list', args=(obj.pk,)),
|
||||
notification_templates_success = reverse('api:organization_notification_templates_success_list', args=(obj.pk,)),
|
||||
notification_templates_error = reverse('api:organization_notification_templates_error_list', args=(obj.pk,)),
|
||||
object_roles = reverse('api:organization_object_roles_list', args=(obj.pk,)),
|
||||
access_list = reverse('api:organization_access_list', args=(obj.pk,)),
|
||||
projects = self.reverse('api:organization_projects_list', kwargs={'pk': obj.pk}),
|
||||
inventories = self.reverse('api:organization_inventories_list', kwargs={'pk': obj.pk}),
|
||||
workflow_job_templates = self.reverse('api:organization_workflow_job_templates_list', kwargs={'pk': obj.pk}),
|
||||
users = self.reverse('api:organization_users_list', kwargs={'pk': obj.pk}),
|
||||
admins = self.reverse('api:organization_admins_list', kwargs={'pk': obj.pk}),
|
||||
teams = self.reverse('api:organization_teams_list', kwargs={'pk': obj.pk}),
|
||||
credentials = self.reverse('api:organization_credential_list', kwargs={'pk': obj.pk}),
|
||||
activity_stream = self.reverse('api:organization_activity_stream_list', kwargs={'pk': obj.pk}),
|
||||
notification_templates = self.reverse('api:organization_notification_templates_list', kwargs={'pk': obj.pk}),
|
||||
notification_templates_any = self.reverse('api:organization_notification_templates_any_list', kwargs={'pk': obj.pk}),
|
||||
notification_templates_success = self.reverse('api:organization_notification_templates_success_list', kwargs={'pk': obj.pk}),
|
||||
notification_templates_error = self.reverse('api:organization_notification_templates_error_list', kwargs={'pk': obj.pk}),
|
||||
object_roles = self.reverse('api:organization_object_roles_list', kwargs={'pk': obj.pk}),
|
||||
access_list = self.reverse('api:organization_access_list', kwargs={'pk': obj.pk}),
|
||||
))
|
||||
return res
|
||||
|
||||
@ -903,8 +908,8 @@ class ProjectOptionsSerializer(BaseSerializer):
|
||||
def get_related(self, obj):
|
||||
res = super(ProjectOptionsSerializer, self).get_related(obj)
|
||||
if obj.credential:
|
||||
res['credential'] = reverse('api:credential_detail',
|
||||
args=(obj.credential.pk,))
|
||||
res['credential'] = self.reverse('api:credential_detail',
|
||||
kwargs={'pk': obj.credential.pk})
|
||||
return res
|
||||
|
||||
def validate(self, attrs):
|
||||
@ -953,28 +958,28 @@ class ProjectSerializer(UnifiedJobTemplateSerializer, ProjectOptionsSerializer):
|
||||
def get_related(self, obj):
|
||||
res = super(ProjectSerializer, self).get_related(obj)
|
||||
res.update(dict(
|
||||
teams = reverse('api:project_teams_list', args=(obj.pk,)),
|
||||
playbooks = reverse('api:project_playbooks', args=(obj.pk,)),
|
||||
update = reverse('api:project_update_view', args=(obj.pk,)),
|
||||
project_updates = reverse('api:project_updates_list', args=(obj.pk,)),
|
||||
schedules = reverse('api:project_schedules_list', args=(obj.pk,)),
|
||||
activity_stream = reverse('api:project_activity_stream_list', args=(obj.pk,)),
|
||||
notification_templates_any = reverse('api:project_notification_templates_any_list', args=(obj.pk,)),
|
||||
notification_templates_success = reverse('api:project_notification_templates_success_list', args=(obj.pk,)),
|
||||
notification_templates_error = reverse('api:project_notification_templates_error_list', args=(obj.pk,)),
|
||||
access_list = reverse('api:project_access_list', args=(obj.pk,)),
|
||||
object_roles = reverse('api:project_object_roles_list', args=(obj.pk,)),
|
||||
teams = self.reverse('api:project_teams_list', kwargs={'pk': obj.pk}),
|
||||
playbooks = self.reverse('api:project_playbooks', kwargs={'pk': obj.pk}),
|
||||
update = self.reverse('api:project_update_view', kwargs={'pk': obj.pk}),
|
||||
project_updates = self.reverse('api:project_updates_list', kwargs={'pk': obj.pk}),
|
||||
schedules = self.reverse('api:project_schedules_list', kwargs={'pk': obj.pk}),
|
||||
activity_stream = self.reverse('api:project_activity_stream_list', kwargs={'pk': obj.pk}),
|
||||
notification_templates_any = self.reverse('api:project_notification_templates_any_list', kwargs={'pk': obj.pk}),
|
||||
notification_templates_success = self.reverse('api:project_notification_templates_success_list', kwargs={'pk': obj.pk}),
|
||||
notification_templates_error = self.reverse('api:project_notification_templates_error_list', kwargs={'pk': obj.pk}),
|
||||
access_list = self.reverse('api:project_access_list', kwargs={'pk': obj.pk}),
|
||||
object_roles = self.reverse('api:project_object_roles_list', kwargs={'pk': obj.pk}),
|
||||
))
|
||||
if obj.organization:
|
||||
res['organization'] = reverse('api:organization_detail',
|
||||
args=(obj.organization.pk,))
|
||||
res['organization'] = self.reverse('api:organization_detail',
|
||||
kwargs={'pk': obj.organization.pk})
|
||||
# Backwards compatibility.
|
||||
if obj.current_update:
|
||||
res['current_update'] = reverse('api:project_update_detail',
|
||||
args=(obj.current_update.pk,))
|
||||
res['current_update'] = self.reverse('api:project_update_detail',
|
||||
kwargs={'pk': obj.current_update.pk})
|
||||
if obj.last_update:
|
||||
res['last_update'] = reverse('api:project_update_detail',
|
||||
args=(obj.last_update.pk,))
|
||||
res['last_update'] = self.reverse('api:project_update_detail',
|
||||
kwargs={'pk': obj.last_update.pk})
|
||||
return res
|
||||
|
||||
def to_representation(self, obj):
|
||||
@ -1039,9 +1044,9 @@ class ProjectUpdateSerializer(UnifiedJobSerializer, ProjectOptionsSerializer):
|
||||
def get_related(self, obj):
|
||||
res = super(ProjectUpdateSerializer, self).get_related(obj)
|
||||
res.update(dict(
|
||||
project = reverse('api:project_detail', args=(obj.project.pk,)),
|
||||
cancel = reverse('api:project_update_cancel', args=(obj.pk,)),
|
||||
notifications = reverse('api:project_update_notifications_list', args=(obj.pk,)),
|
||||
project = self.reverse('api:project_detail', kwargs={'pk': obj.project.pk}),
|
||||
cancel = self.reverse('api:project_update_cancel', kwargs={'pk': obj.pk}),
|
||||
notifications = self.reverse('api:project_update_notifications_list', kwargs={'pk': obj.pk}),
|
||||
))
|
||||
return res
|
||||
|
||||
@ -1078,23 +1083,22 @@ class InventorySerializer(BaseSerializerWithVariables):
|
||||
def get_related(self, obj):
|
||||
res = super(InventorySerializer, self).get_related(obj)
|
||||
res.update(dict(
|
||||
hosts = reverse('api:inventory_hosts_list', args=(obj.pk,)),
|
||||
groups = reverse('api:inventory_groups_list', args=(obj.pk,)),
|
||||
root_groups = reverse('api:inventory_root_groups_list', args=(obj.pk,)),
|
||||
variable_data = reverse('api:inventory_variable_data', args=(obj.pk,)),
|
||||
script = reverse('api:inventory_script_view', args=(obj.pk,)),
|
||||
tree = reverse('api:inventory_tree_view', args=(obj.pk,)),
|
||||
inventory_sources = reverse('api:inventory_inventory_sources_list', args=(obj.pk,)),
|
||||
activity_stream = reverse('api:inventory_activity_stream_list', args=(obj.pk,)),
|
||||
job_templates = reverse('api:inventory_job_template_list', args=(obj.pk,)),
|
||||
scan_job_templates = reverse('api:inventory_scan_job_template_list', args=(obj.pk,)),
|
||||
ad_hoc_commands = reverse('api:inventory_ad_hoc_commands_list', args=(obj.pk,)),
|
||||
access_list = reverse('api:inventory_access_list', args=(obj.pk,)),
|
||||
object_roles = reverse('api:inventory_object_roles_list', args=(obj.pk,)),
|
||||
#single_fact = reverse('api:inventory_single_fact_view', args=(obj.pk,)),
|
||||
hosts = self.reverse('api:inventory_hosts_list', kwargs={'pk': obj.pk}),
|
||||
groups = self.reverse('api:inventory_groups_list', kwargs={'pk': obj.pk}),
|
||||
root_groups = self.reverse('api:inventory_root_groups_list', kwargs={'pk': obj.pk}),
|
||||
variable_data = self.reverse('api:inventory_variable_data', kwargs={'pk': obj.pk}),
|
||||
script = self.reverse('api:inventory_script_view', kwargs={'pk': obj.pk}),
|
||||
tree = self.reverse('api:inventory_tree_view', kwargs={'pk': obj.pk}),
|
||||
inventory_sources = self.reverse('api:inventory_inventory_sources_list', kwargs={'pk': obj.pk}),
|
||||
activity_stream = self.reverse('api:inventory_activity_stream_list', kwargs={'pk': obj.pk}),
|
||||
job_templates = self.reverse('api:inventory_job_template_list', kwargs={'pk': obj.pk}),
|
||||
scan_job_templates = self.reverse('api:inventory_scan_job_template_list', kwargs={'pk': obj.pk}),
|
||||
ad_hoc_commands = self.reverse('api:inventory_ad_hoc_commands_list', kwargs={'pk': obj.pk}),
|
||||
access_list = self.reverse('api:inventory_access_list', kwargs={'pk': obj.pk}),
|
||||
object_roles = self.reverse('api:inventory_object_roles_list', kwargs={'pk': obj.pk}),
|
||||
))
|
||||
if obj.organization:
|
||||
res['organization'] = reverse('api:organization_detail', args=(obj.organization.pk,))
|
||||
res['organization'] = self.reverse('api:organization_detail', kwargs={'pk': obj.organization.pk})
|
||||
return res
|
||||
|
||||
def to_representation(self, obj):
|
||||
@ -1143,24 +1147,23 @@ class HostSerializer(BaseSerializerWithVariables):
|
||||
def get_related(self, obj):
|
||||
res = super(HostSerializer, self).get_related(obj)
|
||||
res.update(dict(
|
||||
variable_data = reverse('api:host_variable_data', args=(obj.pk,)),
|
||||
groups = reverse('api:host_groups_list', args=(obj.pk,)),
|
||||
all_groups = reverse('api:host_all_groups_list', args=(obj.pk,)),
|
||||
job_events = reverse('api:host_job_events_list', args=(obj.pk,)),
|
||||
job_host_summaries = reverse('api:host_job_host_summaries_list', args=(obj.pk,)),
|
||||
activity_stream = reverse('api:host_activity_stream_list', args=(obj.pk,)),
|
||||
inventory_sources = reverse('api:host_inventory_sources_list', args=(obj.pk,)),
|
||||
ad_hoc_commands = reverse('api:host_ad_hoc_commands_list', args=(obj.pk,)),
|
||||
ad_hoc_command_events = reverse('api:host_ad_hoc_command_events_list', args=(obj.pk,)),
|
||||
fact_versions = reverse('api:host_fact_versions_list', args=(obj.pk,)),
|
||||
#single_fact = reverse('api:host_single_fact_view', args=(obj.pk,)),
|
||||
variable_data = self.reverse('api:host_variable_data', kwargs={'pk': obj.pk}),
|
||||
groups = self.reverse('api:host_groups_list', kwargs={'pk': obj.pk}),
|
||||
all_groups = self.reverse('api:host_all_groups_list', kwargs={'pk': obj.pk}),
|
||||
job_events = self.reverse('api:host_job_events_list', kwargs={'pk': obj.pk}),
|
||||
job_host_summaries = self.reverse('api:host_job_host_summaries_list', kwargs={'pk': obj.pk}),
|
||||
activity_stream = self.reverse('api:host_activity_stream_list', kwargs={'pk': obj.pk}),
|
||||
inventory_sources = self.reverse('api:host_inventory_sources_list', kwargs={'pk': obj.pk}),
|
||||
ad_hoc_commands = self.reverse('api:host_ad_hoc_commands_list', kwargs={'pk': obj.pk}),
|
||||
ad_hoc_command_events = self.reverse('api:host_ad_hoc_command_events_list', kwargs={'pk': obj.pk}),
|
||||
fact_versions = self.reverse('api:host_fact_versions_list', kwargs={'pk': obj.pk}),
|
||||
))
|
||||
if obj.inventory:
|
||||
res['inventory'] = reverse('api:inventory_detail', args=(obj.inventory.pk,))
|
||||
res['inventory'] = self.reverse('api:inventory_detail', kwargs={'pk': obj.inventory.pk})
|
||||
if obj.last_job:
|
||||
res['last_job'] = reverse('api:job_detail', args=(obj.last_job.pk,))
|
||||
res['last_job'] = self.reverse('api:job_detail', kwargs={'pk': obj.last_job.pk})
|
||||
if obj.last_job_host_summary:
|
||||
res['last_job_host_summary'] = reverse('api:job_host_summary_detail', args=(obj.last_job_host_summary.pk,))
|
||||
res['last_job_host_summary'] = self.reverse('api:job_host_summary_detail', kwargs={'pk': obj.last_job_host_summary.pk})
|
||||
return res
|
||||
|
||||
def get_summary_fields(self, obj):
|
||||
@ -1253,22 +1256,21 @@ class GroupSerializer(BaseSerializerWithVariables):
|
||||
def get_related(self, obj):
|
||||
res = super(GroupSerializer, self).get_related(obj)
|
||||
res.update(dict(
|
||||
variable_data = reverse('api:group_variable_data', args=(obj.pk,)),
|
||||
hosts = reverse('api:group_hosts_list', args=(obj.pk,)),
|
||||
potential_children = reverse('api:group_potential_children_list', args=(obj.pk,)),
|
||||
children = reverse('api:group_children_list', args=(obj.pk,)),
|
||||
all_hosts = reverse('api:group_all_hosts_list', args=(obj.pk,)),
|
||||
job_events = reverse('api:group_job_events_list', args=(obj.pk,)),
|
||||
job_host_summaries = reverse('api:group_job_host_summaries_list', args=(obj.pk,)),
|
||||
activity_stream = reverse('api:group_activity_stream_list', args=(obj.pk,)),
|
||||
inventory_sources = reverse('api:group_inventory_sources_list', args=(obj.pk,)),
|
||||
ad_hoc_commands = reverse('api:group_ad_hoc_commands_list', args=(obj.pk,)),
|
||||
#single_fact = reverse('api:group_single_fact_view', args=(obj.pk,)),
|
||||
variable_data = self.reverse('api:group_variable_data', kwargs={'pk': obj.pk}),
|
||||
hosts = self.reverse('api:group_hosts_list', kwargs={'pk': obj.pk}),
|
||||
potential_children = self.reverse('api:group_potential_children_list', kwargs={'pk': obj.pk}),
|
||||
children = self.reverse('api:group_children_list', kwargs={'pk': obj.pk}),
|
||||
all_hosts = self.reverse('api:group_all_hosts_list', kwargs={'pk': obj.pk}),
|
||||
job_events = self.reverse('api:group_job_events_list', kwargs={'pk': obj.pk}),
|
||||
job_host_summaries = self.reverse('api:group_job_host_summaries_list', kwargs={'pk': obj.pk}),
|
||||
activity_stream = self.reverse('api:group_activity_stream_list', kwargs={'pk': obj.pk}),
|
||||
inventory_sources = self.reverse('api:group_inventory_sources_list', kwargs={'pk': obj.pk}),
|
||||
ad_hoc_commands = self.reverse('api:group_ad_hoc_commands_list', kwargs={'pk': obj.pk}),
|
||||
))
|
||||
if obj.inventory:
|
||||
res['inventory'] = reverse('api:inventory_detail', args=(obj.inventory.pk,))
|
||||
res['inventory'] = self.reverse('api:inventory_detail', kwargs={'pk': obj.inventory.pk})
|
||||
if obj.inventory_source:
|
||||
res['inventory_source'] = reverse('api:inventory_source_detail', args=(obj.inventory_source.pk,))
|
||||
res['inventory_source'] = self.reverse('api:inventory_source_detail', kwargs={'pk': obj.inventory_source.pk})
|
||||
return res
|
||||
|
||||
def validate_name(self, value):
|
||||
@ -1363,11 +1365,11 @@ class CustomInventoryScriptSerializer(BaseSerializer):
|
||||
def get_related(self, obj):
|
||||
res = super(CustomInventoryScriptSerializer, self).get_related(obj)
|
||||
res.update(dict(
|
||||
object_roles = reverse('api:inventory_script_object_roles_list', args=(obj.pk,)),
|
||||
object_roles = self.reverse('api:inventory_script_object_roles_list', kwargs={'pk': obj.pk}),
|
||||
))
|
||||
|
||||
if obj.organization:
|
||||
res['organization'] = reverse('api:organization_detail', args=(obj.organization.pk,))
|
||||
res['organization'] = self.reverse('api:organization_detail', kwargs={'pk': obj.organization.pk})
|
||||
return res
|
||||
|
||||
|
||||
@ -1381,10 +1383,10 @@ class InventorySourceOptionsSerializer(BaseSerializer):
|
||||
def get_related(self, obj):
|
||||
res = super(InventorySourceOptionsSerializer, self).get_related(obj)
|
||||
if obj.credential:
|
||||
res['credential'] = reverse('api:credential_detail',
|
||||
args=(obj.credential.pk,))
|
||||
res['credential'] = self.reverse('api:credential_detail',
|
||||
kwargs={'pk': obj.credential.pk})
|
||||
if obj.source_script:
|
||||
res['source_script'] = reverse('api:inventory_script_detail', args=(obj.source_script.pk,))
|
||||
res['source_script'] = self.reverse('api:inventory_script_detail', kwargs={'pk': obj.source_script.pk})
|
||||
return res
|
||||
|
||||
def validate_source_vars(self, value):
|
||||
@ -1437,27 +1439,27 @@ class InventorySourceSerializer(UnifiedJobTemplateSerializer, InventorySourceOpt
|
||||
def get_related(self, obj):
|
||||
res = super(InventorySourceSerializer, self).get_related(obj)
|
||||
res.update(dict(
|
||||
update = reverse('api:inventory_source_update_view', args=(obj.pk,)),
|
||||
inventory_updates = reverse('api:inventory_source_updates_list', args=(obj.pk,)),
|
||||
schedules = reverse('api:inventory_source_schedules_list', args=(obj.pk,)),
|
||||
activity_stream = reverse('api:inventory_activity_stream_list', args=(obj.pk,)),
|
||||
hosts = reverse('api:inventory_source_hosts_list', args=(obj.pk,)),
|
||||
groups = reverse('api:inventory_source_groups_list', args=(obj.pk,)),
|
||||
notification_templates_any = reverse('api:inventory_source_notification_templates_any_list', args=(obj.pk,)),
|
||||
notification_templates_success = reverse('api:inventory_source_notification_templates_success_list', args=(obj.pk,)),
|
||||
notification_templates_error = reverse('api:inventory_source_notification_templates_error_list', args=(obj.pk,)),
|
||||
update = self.reverse('api:inventory_source_update_view', kwargs={'pk': obj.pk}),
|
||||
inventory_updates = self.reverse('api:inventory_source_updates_list', kwargs={'pk': obj.pk}),
|
||||
schedules = self.reverse('api:inventory_source_schedules_list', kwargs={'pk': obj.pk}),
|
||||
activity_stream = self.reverse('api:inventory_activity_stream_list', kwargs={'pk': obj.pk}),
|
||||
hosts = self.reverse('api:inventory_source_hosts_list', kwargs={'pk': obj.pk}),
|
||||
groups = self.reverse('api:inventory_source_groups_list', kwargs={'pk': obj.pk}),
|
||||
notification_templates_any = self.reverse('api:inventory_source_notification_templates_any_list', kwargs={'pk': obj.pk}),
|
||||
notification_templates_success = self.reverse('api:inventory_source_notification_templates_success_list', kwargs={'pk': obj.pk}),
|
||||
notification_templates_error = self.reverse('api:inventory_source_notification_templates_error_list', kwargs={'pk': obj.pk}),
|
||||
))
|
||||
if obj.inventory:
|
||||
res['inventory'] = reverse('api:inventory_detail', args=(obj.inventory.pk,))
|
||||
res['inventory'] = self.reverse('api:inventory_detail', kwargs={'pk': obj.inventory.pk})
|
||||
if obj.group:
|
||||
res['group'] = reverse('api:group_detail', args=(obj.group.pk,))
|
||||
res['group'] = self.reverse('api:group_detail', kwargs={'pk': obj.group.pk})
|
||||
# Backwards compatibility.
|
||||
if obj.current_update:
|
||||
res['current_update'] = reverse('api:inventory_update_detail',
|
||||
args=(obj.current_update.pk,))
|
||||
res['current_update'] = self.reverse('api:inventory_update_detail',
|
||||
kwargs={'pk': obj.current_update.pk})
|
||||
if obj.last_update:
|
||||
res['last_update'] = reverse('api:inventory_update_detail',
|
||||
args=(obj.last_update.pk,))
|
||||
res['last_update'] = self.reverse('api:inventory_update_detail',
|
||||
kwargs={'pk': obj.last_update.pk})
|
||||
return res
|
||||
|
||||
def to_representation(self, obj):
|
||||
@ -1488,9 +1490,9 @@ class InventoryUpdateSerializer(UnifiedJobSerializer, InventorySourceOptionsSeri
|
||||
def get_related(self, obj):
|
||||
res = super(InventoryUpdateSerializer, self).get_related(obj)
|
||||
res.update(dict(
|
||||
inventory_source = reverse('api:inventory_source_detail', args=(obj.inventory_source.pk,)),
|
||||
cancel = reverse('api:inventory_update_cancel', args=(obj.pk,)),
|
||||
notifications = reverse('api:inventory_update_notifications_list', args=(obj.pk,)),
|
||||
inventory_source = self.reverse('api:inventory_source_detail', kwargs={'pk': obj.inventory_source.pk}),
|
||||
cancel = self.reverse('api:inventory_update_cancel', kwargs={'pk': obj.pk}),
|
||||
notifications = self.reverse('api:inventory_update_notifications_list', kwargs={'pk': obj.pk}),
|
||||
))
|
||||
return res
|
||||
|
||||
@ -1518,16 +1520,16 @@ class TeamSerializer(BaseSerializer):
|
||||
def get_related(self, obj):
|
||||
res = super(TeamSerializer, self).get_related(obj)
|
||||
res.update(dict(
|
||||
projects = reverse('api:team_projects_list', args=(obj.pk,)),
|
||||
users = reverse('api:team_users_list', args=(obj.pk,)),
|
||||
credentials = reverse('api:team_credentials_list', args=(obj.pk,)),
|
||||
roles = reverse('api:team_roles_list', args=(obj.pk,)),
|
||||
object_roles = reverse('api:team_object_roles_list', args=(obj.pk,)),
|
||||
activity_stream = reverse('api:team_activity_stream_list', args=(obj.pk,)),
|
||||
access_list = reverse('api:team_access_list', args=(obj.pk,)),
|
||||
projects = self.reverse('api:team_projects_list', kwargs={'pk': obj.pk}),
|
||||
users = self.reverse('api:team_users_list', kwargs={'pk': obj.pk}),
|
||||
credentials = self.reverse('api:team_credentials_list', kwargs={'pk': obj.pk}),
|
||||
roles = self.reverse('api:team_roles_list', kwargs={'pk': obj.pk}),
|
||||
object_roles = self.reverse('api:team_object_roles_list', kwargs={'pk': obj.pk}),
|
||||
activity_stream = self.reverse('api:team_activity_stream_list', kwargs={'pk': obj.pk}),
|
||||
access_list = self.reverse('api:team_access_list', kwargs={'pk': obj.pk}),
|
||||
))
|
||||
if obj.organization:
|
||||
res['organization'] = reverse('api:organization_detail', args=(obj.organization.pk,))
|
||||
res['organization'] = self.reverse('api:organization_detail', kwargs={'pk': obj.organization.pk})
|
||||
return res
|
||||
|
||||
def to_representation(self, obj):
|
||||
@ -1564,11 +1566,11 @@ class RoleSerializer(BaseSerializer):
|
||||
|
||||
def get_related(self, obj):
|
||||
ret = super(RoleSerializer, self).get_related(obj)
|
||||
ret['users'] = reverse('api:role_users_list', args=(obj.pk,))
|
||||
ret['teams'] = reverse('api:role_teams_list', args=(obj.pk,))
|
||||
ret['users'] = self.reverse('api:role_users_list', kwargs={'pk': obj.pk})
|
||||
ret['teams'] = self.reverse('api:role_teams_list', kwargs={'pk': obj.pk})
|
||||
try:
|
||||
if obj.content_object:
|
||||
ret.update(reverse_gfk(obj.content_object))
|
||||
ret.update(reverse_gfk(obj.content_object, self.context.get('request')))
|
||||
except AttributeError:
|
||||
# AttributeError's happen if our content_object is pointing at
|
||||
# a model that no longer exists. This is dirty data and ideally
|
||||
@ -1610,7 +1612,7 @@ class ResourceAccessListElementSerializer(UserSerializer):
|
||||
try:
|
||||
role_dict['resource_name'] = role.content_object.name
|
||||
role_dict['resource_type'] = role.content_type.name
|
||||
role_dict['related'] = reverse_gfk(role.content_object)
|
||||
role_dict['related'] = reverse_gfk(role.content_object, self.context.get('request'))
|
||||
except AttributeError:
|
||||
pass
|
||||
if role.content_type is not None:
|
||||
@ -1638,7 +1640,7 @@ class ResourceAccessListElementSerializer(UserSerializer):
|
||||
if role.content_type is not None:
|
||||
role_dict['resource_name'] = role.content_object.name
|
||||
role_dict['resource_type'] = role.content_type.name
|
||||
role_dict['related'] = reverse_gfk(role.content_object)
|
||||
role_dict['related'] = reverse_gfk(role.content_object, self.context.get('request'))
|
||||
role_dict['user_capabilities'] = {'unattach': requesting_user.can_access(
|
||||
Role, 'unattach', role, team_role, 'parents', data={}, skip_sub_obj_read_check=False)}
|
||||
else:
|
||||
@ -1717,22 +1719,22 @@ class CredentialSerializer(BaseSerializer):
|
||||
res = super(CredentialSerializer, self).get_related(obj)
|
||||
|
||||
if obj.organization:
|
||||
res['organization'] = reverse('api:organization_detail', args=(obj.organization.pk,))
|
||||
res['organization'] = self.reverse('api:organization_detail', kwargs={'pk': obj.organization.pk})
|
||||
|
||||
res.update(dict(
|
||||
activity_stream = reverse('api:credential_activity_stream_list', args=(obj.pk,)),
|
||||
access_list = reverse('api:credential_access_list', args=(obj.pk,)),
|
||||
object_roles = reverse('api:credential_object_roles_list', args=(obj.pk,)),
|
||||
owner_users = reverse('api:credential_owner_users_list', args=(obj.pk,)),
|
||||
owner_teams = reverse('api:credential_owner_teams_list', args=(obj.pk,)),
|
||||
activity_stream = self.reverse('api:credential_activity_stream_list', kwargs={'pk': obj.pk}),
|
||||
access_list = self.reverse('api:credential_access_list', kwargs={'pk': obj.pk}),
|
||||
object_roles = self.reverse('api:credential_object_roles_list', kwargs={'pk': obj.pk}),
|
||||
owner_users = self.reverse('api:credential_owner_users_list', kwargs={'pk': obj.pk}),
|
||||
owner_teams = self.reverse('api:credential_owner_teams_list', kwargs={'pk': obj.pk}),
|
||||
))
|
||||
|
||||
parents = [role for role in obj.admin_role.parents.all() if role.object_id is not None]
|
||||
if parents:
|
||||
res.update({parents[0].content_type.name:parents[0].content_object.get_absolute_url()})
|
||||
res.update({parents[0].content_type.name:parents[0].content_object.get_absolute_url(self.context.get('request'))})
|
||||
elif len(obj.admin_role.members.all()) > 0:
|
||||
user = obj.admin_role.members.all()[0]
|
||||
res.update({'user': reverse('api:user_detail', args=(user.pk,))})
|
||||
res.update({'user': self.reverse('api:user_detail', kwargs={'pk': user.pk})})
|
||||
|
||||
return res
|
||||
|
||||
@ -1746,7 +1748,7 @@ class CredentialSerializer(BaseSerializer):
|
||||
'type': 'user',
|
||||
'name': user.username,
|
||||
'description': ' '.join([user.first_name, user.last_name]),
|
||||
'url': reverse('api:user_detail', args=(user.pk,)),
|
||||
'url': self.reverse('api:user_detail', kwargs={'pk': user.pk}),
|
||||
})
|
||||
|
||||
for parent in [role for role in obj.admin_role.parents.all() if role.object_id is not None]:
|
||||
@ -1755,7 +1757,7 @@ class CredentialSerializer(BaseSerializer):
|
||||
'type': camelcase_to_underscore(parent.content_object.__class__.__name__),
|
||||
'name': parent.content_object.name,
|
||||
'description': parent.content_object.description,
|
||||
'url': parent.content_object.get_absolute_url(),
|
||||
'url': parent.content_object.get_absolute_url(self.context.get('request')),
|
||||
})
|
||||
|
||||
return summary_dict
|
||||
@ -1862,19 +1864,19 @@ class JobOptionsSerializer(LabelsListMixin, BaseSerializer):
|
||||
|
||||
def get_related(self, obj):
|
||||
res = super(JobOptionsSerializer, self).get_related(obj)
|
||||
res['labels'] = reverse('api:job_template_label_list', args=(obj.pk,))
|
||||
res['labels'] = self.reverse('api:job_template_label_list', kwargs={'pk': obj.pk})
|
||||
if obj.inventory:
|
||||
res['inventory'] = reverse('api:inventory_detail', args=(obj.inventory.pk,))
|
||||
res['inventory'] = self.reverse('api:inventory_detail', kwargs={'pk': obj.inventory.pk})
|
||||
if obj.project:
|
||||
res['project'] = reverse('api:project_detail', args=(obj.project.pk,))
|
||||
res['project'] = self.reverse('api:project_detail', kwargs={'pk': obj.project.pk})
|
||||
if obj.credential:
|
||||
res['credential'] = reverse('api:credential_detail', args=(obj.credential.pk,))
|
||||
res['credential'] = self.reverse('api:credential_detail', kwargs={'pk': obj.credential.pk})
|
||||
if obj.cloud_credential:
|
||||
res['cloud_credential'] = reverse('api:credential_detail',
|
||||
args=(obj.cloud_credential.pk,))
|
||||
res['cloud_credential'] = self.reverse('api:credential_detail',
|
||||
kwargs={'pk': obj.cloud_credential.pk})
|
||||
if obj.network_credential:
|
||||
res['network_credential'] = reverse('api:credential_detail',
|
||||
args=(obj.network_credential.pk,))
|
||||
res['network_credential'] = self.reverse('api:credential_detail',
|
||||
kwargs={'pk': obj.network_credential.pk})
|
||||
return res
|
||||
|
||||
def to_representation(self, obj):
|
||||
@ -1947,20 +1949,20 @@ class JobTemplateSerializer(JobTemplateMixin, UnifiedJobTemplateSerializer, JobO
|
||||
def get_related(self, obj):
|
||||
res = super(JobTemplateSerializer, self).get_related(obj)
|
||||
res.update(dict(
|
||||
jobs = reverse('api:job_template_jobs_list', args=(obj.pk,)),
|
||||
schedules = reverse('api:job_template_schedules_list', args=(obj.pk,)),
|
||||
activity_stream = reverse('api:job_template_activity_stream_list', args=(obj.pk,)),
|
||||
launch = reverse('api:job_template_launch', args=(obj.pk,)),
|
||||
notification_templates_any = reverse('api:job_template_notification_templates_any_list', args=(obj.pk,)),
|
||||
notification_templates_success = reverse('api:job_template_notification_templates_success_list', args=(obj.pk,)),
|
||||
notification_templates_error = reverse('api:job_template_notification_templates_error_list', args=(obj.pk,)),
|
||||
access_list = reverse('api:job_template_access_list', args=(obj.pk,)),
|
||||
survey_spec = reverse('api:job_template_survey_spec', args=(obj.pk,)),
|
||||
labels = reverse('api:job_template_label_list', args=(obj.pk,)),
|
||||
object_roles = reverse('api:job_template_object_roles_list', args=(obj.pk,)),
|
||||
jobs = self.reverse('api:job_template_jobs_list', kwargs={'pk': obj.pk}),
|
||||
schedules = self.reverse('api:job_template_schedules_list', kwargs={'pk': obj.pk}),
|
||||
activity_stream = self.reverse('api:job_template_activity_stream_list', kwargs={'pk': obj.pk}),
|
||||
launch = self.reverse('api:job_template_launch', kwargs={'pk': obj.pk}),
|
||||
notification_templates_any = self.reverse('api:job_template_notification_templates_any_list', kwargs={'pk': obj.pk}),
|
||||
notification_templates_success = self.reverse('api:job_template_notification_templates_success_list', kwargs={'pk': obj.pk}),
|
||||
notification_templates_error = self.reverse('api:job_template_notification_templates_error_list', kwargs={'pk': obj.pk}),
|
||||
access_list = self.reverse('api:job_template_access_list', kwargs={'pk': obj.pk}),
|
||||
survey_spec = self.reverse('api:job_template_survey_spec', kwargs={'pk': obj.pk}),
|
||||
labels = self.reverse('api:job_template_label_list', kwargs={'pk': obj.pk}),
|
||||
object_roles = self.reverse('api:job_template_object_roles_list', kwargs={'pk': obj.pk}),
|
||||
))
|
||||
if obj.host_config_key:
|
||||
res['callback'] = reverse('api:job_template_callback', args=(obj.pk,))
|
||||
res['callback'] = self.reverse('api:job_template_callback', kwargs={'pk': obj.pk})
|
||||
return res
|
||||
|
||||
def validate(self, attrs):
|
||||
@ -2015,22 +2017,22 @@ class JobSerializer(UnifiedJobSerializer, JobOptionsSerializer):
|
||||
def get_related(self, obj):
|
||||
res = super(JobSerializer, self).get_related(obj)
|
||||
res.update(dict(
|
||||
job_events = reverse('api:job_job_events_list', args=(obj.pk,)),
|
||||
job_host_summaries = reverse('api:job_job_host_summaries_list', args=(obj.pk,)),
|
||||
activity_stream = reverse('api:job_activity_stream_list', args=(obj.pk,)),
|
||||
notifications = reverse('api:job_notifications_list', args=(obj.pk,)),
|
||||
labels = reverse('api:job_label_list', args=(obj.pk,)),
|
||||
job_events = self.reverse('api:job_job_events_list', kwargs={'pk': obj.pk}),
|
||||
job_host_summaries = self.reverse('api:job_job_host_summaries_list', kwargs={'pk': obj.pk}),
|
||||
activity_stream = self.reverse('api:job_activity_stream_list', kwargs={'pk': obj.pk}),
|
||||
notifications = self.reverse('api:job_notifications_list', kwargs={'pk': obj.pk}),
|
||||
labels = self.reverse('api:job_label_list', kwargs={'pk': obj.pk}),
|
||||
))
|
||||
if obj.job_template:
|
||||
res['job_template'] = reverse('api:job_template_detail',
|
||||
args=(obj.job_template.pk,))
|
||||
res['job_template'] = self.reverse('api:job_template_detail',
|
||||
kwargs={'pk': obj.job_template.pk})
|
||||
if obj.can_start or True:
|
||||
res['start'] = reverse('api:job_start', args=(obj.pk,))
|
||||
res['start'] = self.reverse('api:job_start', kwargs={'pk': obj.pk})
|
||||
if obj.can_cancel or True:
|
||||
res['cancel'] = reverse('api:job_cancel', args=(obj.pk,))
|
||||
res['cancel'] = self.reverse('api:job_cancel', kwargs={'pk': obj.pk})
|
||||
if obj.project_update:
|
||||
res['project_update'] = reverse('api:project_update_detail', args=(obj.project_update.pk,))
|
||||
res['relaunch'] = reverse('api:job_relaunch', args=(obj.pk,))
|
||||
res['project_update'] = self.reverse('api:project_update_detail', kwargs={'pk': obj.project_update.pk})
|
||||
res['relaunch'] = self.reverse('api:job_relaunch', kwargs={'pk': obj.pk})
|
||||
return res
|
||||
|
||||
def get_artifacts(self, obj):
|
||||
@ -2175,16 +2177,16 @@ class AdHocCommandSerializer(UnifiedJobSerializer):
|
||||
def get_related(self, obj):
|
||||
res = super(AdHocCommandSerializer, self).get_related(obj)
|
||||
if obj.inventory:
|
||||
res['inventory'] = reverse('api:inventory_detail', args=(obj.inventory.pk,))
|
||||
res['inventory'] = self.reverse('api:inventory_detail', kwargs={'pk': obj.inventory.pk})
|
||||
if obj.credential:
|
||||
res['credential'] = reverse('api:credential_detail', args=(obj.credential.pk,))
|
||||
res['credential'] = self.reverse('api:credential_detail', kwargs={'pk': obj.credential.pk})
|
||||
res.update(dict(
|
||||
events = reverse('api:ad_hoc_command_ad_hoc_command_events_list', args=(obj.pk,)),
|
||||
activity_stream = reverse('api:ad_hoc_command_activity_stream_list', args=(obj.pk,)),
|
||||
notifications = reverse('api:ad_hoc_command_notifications_list', args=(obj.pk,)),
|
||||
events = self.reverse('api:ad_hoc_command_ad_hoc_command_events_list', kwargs={'pk': obj.pk}),
|
||||
activity_stream = self.reverse('api:ad_hoc_command_activity_stream_list', kwargs={'pk': obj.pk}),
|
||||
notifications = self.reverse('api:ad_hoc_command_notifications_list', kwargs={'pk': obj.pk}),
|
||||
))
|
||||
res['cancel'] = reverse('api:ad_hoc_command_cancel', args=(obj.pk,))
|
||||
res['relaunch'] = reverse('api:ad_hoc_command_relaunch', args=(obj.pk,))
|
||||
res['cancel'] = self.reverse('api:ad_hoc_command_cancel', kwargs={'pk': obj.pk})
|
||||
res['relaunch'] = self.reverse('api:ad_hoc_command_relaunch', kwargs={'pk': obj.pk})
|
||||
return res
|
||||
|
||||
def to_representation(self, obj):
|
||||
@ -2229,12 +2231,12 @@ class SystemJobTemplateSerializer(UnifiedJobTemplateSerializer):
|
||||
def get_related(self, obj):
|
||||
res = super(SystemJobTemplateSerializer, self).get_related(obj)
|
||||
res.update(dict(
|
||||
jobs = reverse('api:system_job_template_jobs_list', args=(obj.pk,)),
|
||||
schedules = reverse('api:system_job_template_schedules_list', args=(obj.pk,)),
|
||||
launch = reverse('api:system_job_template_launch', args=(obj.pk,)),
|
||||
notification_templates_any = reverse('api:system_job_template_notification_templates_any_list', args=(obj.pk,)),
|
||||
notification_templates_success = reverse('api:system_job_template_notification_templates_success_list', args=(obj.pk,)),
|
||||
notification_templates_error = reverse('api:system_job_template_notification_templates_error_list', args=(obj.pk,)),
|
||||
jobs = self.reverse('api:system_job_template_jobs_list', kwargs={'pk': obj.pk}),
|
||||
schedules = self.reverse('api:system_job_template_schedules_list', kwargs={'pk': obj.pk}),
|
||||
launch = self.reverse('api:system_job_template_launch', kwargs={'pk': obj.pk}),
|
||||
notification_templates_any = self.reverse('api:system_job_template_notification_templates_any_list', kwargs={'pk': obj.pk}),
|
||||
notification_templates_success = self.reverse('api:system_job_template_notification_templates_success_list', kwargs={'pk': obj.pk}),
|
||||
notification_templates_error = self.reverse('api:system_job_template_notification_templates_error_list', kwargs={'pk': obj.pk}),
|
||||
|
||||
))
|
||||
return res
|
||||
@ -2249,11 +2251,11 @@ class SystemJobSerializer(UnifiedJobSerializer):
|
||||
def get_related(self, obj):
|
||||
res = super(SystemJobSerializer, self).get_related(obj)
|
||||
if obj.system_job_template:
|
||||
res['system_job_template'] = reverse('api:system_job_template_detail',
|
||||
args=(obj.system_job_template.pk,))
|
||||
res['notifications'] = reverse('api:system_job_notifications_list', args=(obj.pk,))
|
||||
res['system_job_template'] = self.reverse('api:system_job_template_detail',
|
||||
kwargs={'pk': obj.system_job_template.pk})
|
||||
res['notifications'] = self.reverse('api:system_job_notifications_list', kwargs={'pk': obj.pk})
|
||||
if obj.can_cancel or True:
|
||||
res['cancel'] = reverse('api:system_job_cancel', args=(obj.pk,))
|
||||
res['cancel'] = self.reverse('api:system_job_cancel', kwargs={'pk': obj.pk})
|
||||
return res
|
||||
|
||||
|
||||
@ -2275,22 +2277,22 @@ class WorkflowJobTemplateSerializer(JobTemplateMixin, LabelsListMixin, UnifiedJo
|
||||
def get_related(self, obj):
|
||||
res = super(WorkflowJobTemplateSerializer, self).get_related(obj)
|
||||
res.update(dict(
|
||||
workflow_jobs = reverse('api:workflow_job_template_jobs_list', args=(obj.pk,)),
|
||||
schedules = reverse('api:workflow_job_template_schedules_list', args=(obj.pk,)),
|
||||
launch = reverse('api:workflow_job_template_launch', args=(obj.pk,)),
|
||||
copy = reverse('api:workflow_job_template_copy', args=(obj.pk,)),
|
||||
workflow_nodes = reverse('api:workflow_job_template_workflow_nodes_list', args=(obj.pk,)),
|
||||
labels = reverse('api:workflow_job_template_label_list', args=(obj.pk,)),
|
||||
activity_stream = reverse('api:workflow_job_template_activity_stream_list', args=(obj.pk,)),
|
||||
notification_templates_any = reverse('api:workflow_job_template_notification_templates_any_list', args=(obj.pk,)),
|
||||
notification_templates_success = reverse('api:workflow_job_template_notification_templates_success_list', args=(obj.pk,)),
|
||||
notification_templates_error = reverse('api:workflow_job_template_notification_templates_error_list', args=(obj.pk,)),
|
||||
access_list = reverse('api:workflow_job_template_access_list', args=(obj.pk,)),
|
||||
object_roles = reverse('api:workflow_job_template_object_roles_list', args=(obj.pk,)),
|
||||
survey_spec = reverse('api:workflow_job_template_survey_spec', args=(obj.pk,)),
|
||||
workflow_jobs = self.reverse('api:workflow_job_template_jobs_list', kwargs={'pk': obj.pk}),
|
||||
schedules = self.reverse('api:workflow_job_template_schedules_list', kwargs={'pk': obj.pk}),
|
||||
launch = self.reverse('api:workflow_job_template_launch', kwargs={'pk': obj.pk}),
|
||||
copy = self.reverse('api:workflow_job_template_copy', kwargs={'pk': obj.pk}),
|
||||
workflow_nodes = self.reverse('api:workflow_job_template_workflow_nodes_list', kwargs={'pk': obj.pk}),
|
||||
labels = self.reverse('api:workflow_job_template_label_list', kwargs={'pk': obj.pk}),
|
||||
activity_stream = self.reverse('api:workflow_job_template_activity_stream_list', kwargs={'pk': obj.pk}),
|
||||
notification_templates_any = self.reverse('api:workflow_job_template_notification_templates_any_list', kwargs={'pk': obj.pk}),
|
||||
notification_templates_success = self.reverse('api:workflow_job_template_notification_templates_success_list', kwargs={'pk': obj.pk}),
|
||||
notification_templates_error = self.reverse('api:workflow_job_template_notification_templates_error_list', kwargs={'pk': obj.pk}),
|
||||
access_list = self.reverse('api:workflow_job_template_access_list', kwargs={'pk': obj.pk}),
|
||||
object_roles = self.reverse('api:workflow_job_template_object_roles_list', kwargs={'pk': obj.pk}),
|
||||
survey_spec = self.reverse('api:workflow_job_template_survey_spec', kwargs={'pk': obj.pk}),
|
||||
))
|
||||
if obj.organization:
|
||||
res['organization'] = reverse('api:organization_detail', args=(obj.organization.pk,))
|
||||
res['organization'] = self.reverse('api:organization_detail', kwargs={'pk': obj.organization.pk})
|
||||
return res
|
||||
|
||||
def validate_extra_vars(self, value):
|
||||
@ -2312,15 +2314,15 @@ class WorkflowJobSerializer(LabelsListMixin, UnifiedJobSerializer):
|
||||
def get_related(self, obj):
|
||||
res = super(WorkflowJobSerializer, self).get_related(obj)
|
||||
if obj.workflow_job_template:
|
||||
res['workflow_job_template'] = reverse('api:workflow_job_template_detail',
|
||||
args=(obj.workflow_job_template.pk,))
|
||||
res['notifications'] = reverse('api:workflow_job_notifications_list', args=(obj.pk,))
|
||||
res['workflow_nodes'] = reverse('api:workflow_job_workflow_nodes_list', args=(obj.pk,))
|
||||
res['labels'] = reverse('api:workflow_job_label_list', args=(obj.pk,))
|
||||
res['activity_stream'] = reverse('api:workflow_job_activity_stream_list', args=(obj.pk,))
|
||||
res['relaunch'] = reverse('api:workflow_job_relaunch', args=(obj.pk,))
|
||||
res['workflow_job_template'] = self.reverse('api:workflow_job_template_detail',
|
||||
kwargs={'pk': obj.workflow_job_template.pk})
|
||||
res['notifications'] = self.reverse('api:workflow_job_notifications_list', kwargs={'pk': obj.pk})
|
||||
res['workflow_nodes'] = self.reverse('api:workflow_job_workflow_nodes_list', kwargs={'pk': obj.pk})
|
||||
res['labels'] = self.reverse('api:workflow_job_label_list', kwargs={'pk': obj.pk})
|
||||
res['activity_stream'] = self.reverse('api:workflow_job_activity_stream_list', kwargs={'pk': obj.pk})
|
||||
res['relaunch'] = self.reverse('api:workflow_job_relaunch', kwargs={'pk': obj.pk})
|
||||
if obj.can_cancel or True:
|
||||
res['cancel'] = reverse('api:workflow_job_cancel', args=(obj.pk,))
|
||||
res['cancel'] = self.reverse('api:workflow_job_cancel', kwargs={'pk': obj.pk})
|
||||
return res
|
||||
|
||||
def to_representation(self, obj):
|
||||
@ -2362,7 +2364,7 @@ class WorkflowNodeBaseSerializer(BaseSerializer):
|
||||
def get_related(self, obj):
|
||||
res = super(WorkflowNodeBaseSerializer, self).get_related(obj)
|
||||
if obj.unified_job_template:
|
||||
res['unified_job_template'] = obj.unified_job_template.get_absolute_url()
|
||||
res['unified_job_template'] = obj.unified_job_template.get_absolute_url(self.context.get('request'))
|
||||
return res
|
||||
|
||||
def validate(self, attrs):
|
||||
@ -2380,11 +2382,11 @@ class WorkflowJobTemplateNodeSerializer(WorkflowNodeBaseSerializer):
|
||||
|
||||
def get_related(self, obj):
|
||||
res = super(WorkflowJobTemplateNodeSerializer, self).get_related(obj)
|
||||
res['success_nodes'] = reverse('api:workflow_job_template_node_success_nodes_list', args=(obj.pk,))
|
||||
res['failure_nodes'] = reverse('api:workflow_job_template_node_failure_nodes_list', args=(obj.pk,))
|
||||
res['always_nodes'] = reverse('api:workflow_job_template_node_always_nodes_list', args=(obj.pk,))
|
||||
res['success_nodes'] = self.reverse('api:workflow_job_template_node_success_nodes_list', kwargs={'pk': obj.pk})
|
||||
res['failure_nodes'] = self.reverse('api:workflow_job_template_node_failure_nodes_list', kwargs={'pk': obj.pk})
|
||||
res['always_nodes'] = self.reverse('api:workflow_job_template_node_always_nodes_list', kwargs={'pk': obj.pk})
|
||||
if obj.workflow_job_template:
|
||||
res['workflow_job_template'] = reverse('api:workflow_job_template_detail', args=(obj.workflow_job_template.pk,))
|
||||
res['workflow_job_template'] = self.reverse('api:workflow_job_template_detail', kwargs={'pk': obj.workflow_job_template.pk})
|
||||
return res
|
||||
|
||||
def to_internal_value(self, data):
|
||||
@ -2440,13 +2442,13 @@ class WorkflowJobNodeSerializer(WorkflowNodeBaseSerializer):
|
||||
|
||||
def get_related(self, obj):
|
||||
res = super(WorkflowJobNodeSerializer, self).get_related(obj)
|
||||
res['success_nodes'] = reverse('api:workflow_job_node_success_nodes_list', args=(obj.pk,))
|
||||
res['failure_nodes'] = reverse('api:workflow_job_node_failure_nodes_list', args=(obj.pk,))
|
||||
res['always_nodes'] = reverse('api:workflow_job_node_always_nodes_list', args=(obj.pk,))
|
||||
res['success_nodes'] = self.reverse('api:workflow_job_node_success_nodes_list', kwargs={'pk': obj.pk})
|
||||
res['failure_nodes'] = self.reverse('api:workflow_job_node_failure_nodes_list', kwargs={'pk': obj.pk})
|
||||
res['always_nodes'] = self.reverse('api:workflow_job_node_always_nodes_list', kwargs={'pk': obj.pk})
|
||||
if obj.job:
|
||||
res['job'] = obj.job.get_absolute_url()
|
||||
res['job'] = obj.job.get_absolute_url(self.context.get('request'))
|
||||
if obj.workflow_job:
|
||||
res['workflow_job'] = reverse('api:workflow_job_detail', args=(obj.workflow_job.pk,))
|
||||
res['workflow_job'] = self.reverse('api:workflow_job_detail', kwargs={'pk': obj.workflow_job.pk})
|
||||
return res
|
||||
|
||||
|
||||
@ -2500,10 +2502,10 @@ class JobHostSummarySerializer(BaseSerializer):
|
||||
def get_related(self, obj):
|
||||
res = super(JobHostSummarySerializer, self).get_related(obj)
|
||||
res.update(dict(
|
||||
job=reverse('api:job_detail', args=(obj.job.pk,))))
|
||||
job=self.reverse('api:job_detail', kwargs={'pk': obj.job.pk})))
|
||||
if obj.host is not None:
|
||||
res.update(dict(
|
||||
host=reverse('api:host_detail', args=(obj.host.pk,))
|
||||
host=self.reverse('api:host_detail', kwargs={'pk': obj.host.pk})
|
||||
))
|
||||
return res
|
||||
|
||||
@ -2533,16 +2535,16 @@ class JobEventSerializer(BaseSerializer):
|
||||
def get_related(self, obj):
|
||||
res = super(JobEventSerializer, self).get_related(obj)
|
||||
res.update(dict(
|
||||
job = reverse('api:job_detail', args=(obj.job_id,)),
|
||||
job = self.reverse('api:job_detail', kwargs={'pk': obj.job_id}),
|
||||
))
|
||||
if obj.parent_id:
|
||||
res['parent'] = reverse('api:job_event_detail', args=(obj.parent_id,))
|
||||
res['parent'] = self.reverse('api:job_event_detail', kwargs={'pk': obj.parent_id})
|
||||
if obj.children.exists():
|
||||
res['children'] = reverse('api:job_event_children_list', args=(obj.pk,))
|
||||
res['children'] = self.reverse('api:job_event_children_list', kwargs={'pk': obj.pk})
|
||||
if obj.host_id:
|
||||
res['host'] = reverse('api:host_detail', args=(obj.host_id,))
|
||||
res['host'] = self.reverse('api:host_detail', kwargs={'pk': obj.host_id})
|
||||
if obj.hosts.exists():
|
||||
res['hosts'] = reverse('api:job_event_hosts_list', args=(obj.pk,))
|
||||
res['hosts'] = self.reverse('api:job_event_hosts_list', kwargs={'pk': obj.pk})
|
||||
return res
|
||||
|
||||
def get_summary_fields(self, obj):
|
||||
@ -2582,10 +2584,10 @@ class AdHocCommandEventSerializer(BaseSerializer):
|
||||
def get_related(self, obj):
|
||||
res = super(AdHocCommandEventSerializer, self).get_related(obj)
|
||||
res.update(dict(
|
||||
ad_hoc_command = reverse('api:ad_hoc_command_detail', args=(obj.ad_hoc_command_id,)),
|
||||
ad_hoc_command = self.reverse('api:ad_hoc_command_detail', kwargs={'pk': obj.ad_hoc_command_id}),
|
||||
))
|
||||
if obj.host:
|
||||
res['host'] = reverse('api:host_detail', args=(obj.host.pk,))
|
||||
res['host'] = self.reverse('api:host_detail', kwargs={'pk': obj.host.pk})
|
||||
return res
|
||||
|
||||
def to_representation(self, obj):
|
||||
@ -2809,11 +2811,11 @@ class NotificationTemplateSerializer(BaseSerializer):
|
||||
def get_related(self, obj):
|
||||
res = super(NotificationTemplateSerializer, self).get_related(obj)
|
||||
res.update(dict(
|
||||
test = reverse('api:notification_template_test', args=(obj.pk,)),
|
||||
notifications = reverse('api:notification_template_notification_list', args=(obj.pk,)),
|
||||
test = self.reverse('api:notification_template_test', kwargs={'pk': obj.pk}),
|
||||
notifications = self.reverse('api:notification_template_notification_list', kwargs={'pk': obj.pk}),
|
||||
))
|
||||
if obj.organization:
|
||||
res['organization'] = reverse('api:organization_detail', args=(obj.organization.pk,))
|
||||
res['organization'] = self.reverse('api:organization_detail', kwargs={'pk': obj.organization.pk})
|
||||
return res
|
||||
|
||||
def _recent_notifications(self, obj):
|
||||
@ -2883,7 +2885,7 @@ class NotificationSerializer(BaseSerializer):
|
||||
def get_related(self, obj):
|
||||
res = super(NotificationSerializer, self).get_related(obj)
|
||||
res.update(dict(
|
||||
notification_template = reverse('api:notification_template_detail', args=(obj.notification_template.pk,)),
|
||||
notification_template = self.reverse('api:notification_template_detail', kwargs={'pk': obj.notification_template.pk}),
|
||||
))
|
||||
return res
|
||||
|
||||
@ -2897,7 +2899,7 @@ class LabelSerializer(BaseSerializer):
|
||||
def get_related(self, obj):
|
||||
res = super(LabelSerializer, self).get_related(obj)
|
||||
if obj.organization:
|
||||
res['organization'] = reverse('api:organization_detail', args=(obj.organization.pk,))
|
||||
res['organization'] = self.reverse('api:organization_detail', kwargs={'pk': obj.organization.pk})
|
||||
return res
|
||||
|
||||
|
||||
@ -2911,10 +2913,10 @@ class ScheduleSerializer(BaseSerializer):
|
||||
def get_related(self, obj):
|
||||
res = super(ScheduleSerializer, self).get_related(obj)
|
||||
res.update(dict(
|
||||
unified_jobs = reverse('api:schedule_unified_jobs_list', args=(obj.pk,)),
|
||||
unified_jobs = self.reverse('api:schedule_unified_jobs_list', kwargs={'pk': obj.pk}),
|
||||
))
|
||||
if obj.unified_job_template:
|
||||
res['unified_job_template'] = obj.unified_job_template.get_absolute_url()
|
||||
res['unified_job_template'] = obj.unified_job_template.get_absolute_url(self.context.get('request'))
|
||||
return res
|
||||
|
||||
def validate_unified_job_template(self, value):
|
||||
@ -3038,7 +3040,7 @@ class ActivityStreamSerializer(BaseSerializer):
|
||||
def get_related(self, obj):
|
||||
rel = {}
|
||||
if obj.actor is not None:
|
||||
rel['actor'] = reverse('api:user_detail', args=(obj.actor.pk,))
|
||||
rel['actor'] = self.reverse('api:user_detail', kwargs={'pk': obj.actor.pk})
|
||||
for fk, __ in self._local_summarizable_fk_fields:
|
||||
if not hasattr(obj, fk):
|
||||
continue
|
||||
@ -3051,12 +3053,12 @@ class ActivityStreamSerializer(BaseSerializer):
|
||||
continue
|
||||
id_list.append(getattr(thisItem, 'id', None))
|
||||
if fk == 'custom_inventory_script':
|
||||
rel[fk].append(reverse('api:inventory_script_detail', args=(thisItem.id,)))
|
||||
rel[fk].append(self.reverse('api:inventory_script_detail', kwargs={'pk': thisItem.id}))
|
||||
else:
|
||||
rel[fk].append(reverse('api:' + fk + '_detail', args=(thisItem.id,)))
|
||||
rel[fk].append(self.reverse('api:' + fk + '_detail', kwargs={'pk': thisItem.id}))
|
||||
|
||||
if fk == 'schedule':
|
||||
rel['unified_job_template'] = thisItem.unified_job_template.get_absolute_url()
|
||||
rel['unified_job_template'] = thisItem.unified_job_template.get_absolute_url(self.context.get('request'))
|
||||
return rel
|
||||
|
||||
def get_summary_fields(self, obj):
|
||||
@ -3137,7 +3139,10 @@ class FactVersionSerializer(BaseFactSerializer):
|
||||
'datetime': timestamp_apiformat(obj.timestamp),
|
||||
'module': obj.module,
|
||||
}
|
||||
res['fact_view'] = build_url('api:host_fact_compare_view', args=(obj.host.pk,), get=params)
|
||||
res['fact_view'] = '%s?%s' % (
|
||||
reverse('api:host_fact_compare_view', kwargs={'pk': obj.host.pk}, request=self.context.get('request')),
|
||||
urllib.urlencode(params)
|
||||
)
|
||||
return res
|
||||
|
||||
|
||||
@ -3151,7 +3156,7 @@ class FactSerializer(BaseFactSerializer):
|
||||
|
||||
def get_related(self, obj):
|
||||
res = super(FactSerializer, self).get_related(obj)
|
||||
res['host'] = obj.host.get_absolute_url()
|
||||
res['host'] = obj.host.get_absolute_url(self.context.get('request'))
|
||||
return res
|
||||
|
||||
def to_representation(self, obj):
|
||||
|
||||
@ -9,5 +9,6 @@
|
||||
{% if new_in_240 %}> _Added in Ansible Tower 2.4.0_{% endif %}
|
||||
{% if new_in_300 %}> _Added in Ansible Tower 3.0.0_{% endif %}
|
||||
{% if new_in_310 %}> _New in Ansible Tower 3.1.0_{% endif %}
|
||||
{% if new_in_320 %}> _New in Ansible Tower 3.2.0_{% endif %}
|
||||
{% if deprecated %}> _This resource has been deprecated and will be removed in a future release_{% endif %}
|
||||
{% endif %}
|
||||
|
||||
@ -331,7 +331,7 @@ activity_stream_urls = patterns('awx.api.views',
|
||||
)
|
||||
|
||||
v1_urls = patterns('awx.api.views',
|
||||
url(r'^$', 'api_v1_root_view'),
|
||||
url(r'^$', 'api_version_root_view'),
|
||||
url(r'^ping/$', 'api_v1_ping_view'),
|
||||
url(r'^config/$', 'api_v1_config_view'),
|
||||
url(r'^auth/$', 'auth_view'),
|
||||
@ -376,5 +376,5 @@ v1_urls = patterns('awx.api.views',
|
||||
|
||||
urlpatterns = patterns('awx.api.views',
|
||||
url(r'^$', 'api_root_view'),
|
||||
url(r'^v1/', include(v1_urls)),
|
||||
url(r'^(?P<version>(v1|v2))/', include(v1_urls))
|
||||
)
|
||||
|
||||
30
awx/api/versioning.py
Normal file
30
awx/api/versioning.py
Normal file
@ -0,0 +1,30 @@
|
||||
# Copyright (c) 2017 Ansible by Red Hat
|
||||
# All Rights Reserved.
|
||||
|
||||
from rest_framework.reverse import reverse as drf_reverse
|
||||
from rest_framework.versioning import URLPathVersioning as BaseVersioning
|
||||
|
||||
|
||||
def reverse(viewname, args=None, kwargs=None, request=None, format=None, **extra):
|
||||
if request is None or getattr(request, 'version', None) is None:
|
||||
# We need the "current request" to determine the correct version to
|
||||
# prepend to reverse URLs. If there is no "current request", assume
|
||||
# the latest API version.
|
||||
if kwargs is None:
|
||||
kwargs = {}
|
||||
if 'version' not in kwargs:
|
||||
kwargs['version'] = 'v2'
|
||||
return drf_reverse(viewname, args, kwargs, request, format, **extra)
|
||||
|
||||
|
||||
class URLPathVersioning(BaseVersioning):
|
||||
|
||||
def reverse(self, viewname, args=None, kwargs=None, request=None, format=None, **extra):
|
||||
if request.version is not None:
|
||||
kwargs = {} if (kwargs is None) else kwargs
|
||||
kwargs[self.version_param] = request.version
|
||||
request = None
|
||||
|
||||
return super(BaseVersioning, self).reverse(
|
||||
viewname, args, kwargs, request, format, **extra
|
||||
)
|
||||
154
awx/api/views.py
154
awx/api/views.py
@ -20,7 +20,6 @@ from collections import OrderedDict
|
||||
from django.conf import settings
|
||||
from django.contrib.auth.models import User, AnonymousUser
|
||||
from django.core.cache import cache
|
||||
from django.core.urlresolvers import reverse
|
||||
from django.core.exceptions import FieldError
|
||||
from django.db.models import Q, Count, F
|
||||
from django.db import IntegrityError, transaction, connection
|
||||
@ -65,6 +64,7 @@ from awx.main.ha import is_ha_environment
|
||||
from awx.api.authentication import TaskAuthentication, TokenGetAuthentication
|
||||
from awx.api.generics import get_view_name
|
||||
from awx.api.generics import * # noqa
|
||||
from awx.api.versioning import reverse
|
||||
from awx.conf.license import get_license, feature_enabled, feature_exists, LicenseForbids
|
||||
from awx.main.models import * # noqa
|
||||
from awx.main.utils import * # noqa
|
||||
@ -128,17 +128,17 @@ class ApiRootView(APIView):
|
||||
authentication_classes = []
|
||||
permission_classes = (AllowAny,)
|
||||
view_name = _('REST API')
|
||||
versioning_class = None
|
||||
|
||||
def get(self, request, format=None):
|
||||
''' list supported API versions '''
|
||||
|
||||
current = reverse('api:api_v1_root_view', args=[])
|
||||
v1 = reverse('api:api_version_root_view', kwargs={'version': 'v1'})
|
||||
v2 = reverse('api:api_version_root_view', kwargs={'version': 'v2'})
|
||||
data = dict(
|
||||
description = _('Ansible Tower REST API'),
|
||||
current_version = current,
|
||||
available_versions = dict(
|
||||
v1 = current
|
||||
),
|
||||
current_version = v2,
|
||||
available_versions = dict(v1 = v1, v2 = v2),
|
||||
)
|
||||
if feature_enabled('rebranding'):
|
||||
data['custom_logo'] = settings.CUSTOM_LOGO
|
||||
@ -146,52 +146,52 @@ class ApiRootView(APIView):
|
||||
return Response(data)
|
||||
|
||||
|
||||
class ApiV1RootView(APIView):
|
||||
class ApiVersionRootView(APIView):
|
||||
|
||||
authentication_classes = []
|
||||
view_name = _('Version')
|
||||
permission_classes = (AllowAny,)
|
||||
view_name = _('Version 1')
|
||||
|
||||
def get(self, request, format=None):
|
||||
''' list top level resources '''
|
||||
|
||||
data = OrderedDict()
|
||||
data['authtoken'] = reverse('api:auth_token_view')
|
||||
data['ping'] = reverse('api:api_v1_ping_view')
|
||||
data['config'] = reverse('api:api_v1_config_view')
|
||||
data['settings'] = reverse('api:setting_category_list')
|
||||
data['me'] = reverse('api:user_me_list')
|
||||
data['dashboard'] = reverse('api:dashboard_view')
|
||||
data['organizations'] = reverse('api:organization_list')
|
||||
data['users'] = reverse('api:user_list')
|
||||
data['projects'] = reverse('api:project_list')
|
||||
data['project_updates'] = reverse('api:project_update_list')
|
||||
data['teams'] = reverse('api:team_list')
|
||||
data['credentials'] = reverse('api:credential_list')
|
||||
data['inventory'] = reverse('api:inventory_list')
|
||||
data['inventory_scripts'] = reverse('api:inventory_script_list')
|
||||
data['inventory_sources'] = reverse('api:inventory_source_list')
|
||||
data['inventory_updates'] = reverse('api:inventory_update_list')
|
||||
data['groups'] = reverse('api:group_list')
|
||||
data['hosts'] = reverse('api:host_list')
|
||||
data['job_templates'] = reverse('api:job_template_list')
|
||||
data['jobs'] = reverse('api:job_list')
|
||||
data['job_events'] = reverse('api:job_event_list')
|
||||
data['ad_hoc_commands'] = reverse('api:ad_hoc_command_list')
|
||||
data['system_job_templates'] = reverse('api:system_job_template_list')
|
||||
data['system_jobs'] = reverse('api:system_job_list')
|
||||
data['schedules'] = reverse('api:schedule_list')
|
||||
data['roles'] = reverse('api:role_list')
|
||||
data['notification_templates'] = reverse('api:notification_template_list')
|
||||
data['notifications'] = reverse('api:notification_list')
|
||||
data['labels'] = reverse('api:label_list')
|
||||
data['unified_job_templates'] = reverse('api:unified_job_template_list')
|
||||
data['unified_jobs'] = reverse('api:unified_job_list')
|
||||
data['activity_stream'] = reverse('api:activity_stream_list')
|
||||
data['workflow_job_templates'] = reverse('api:workflow_job_template_list')
|
||||
data['workflow_jobs'] = reverse('api:workflow_job_list')
|
||||
data['workflow_job_template_nodes'] = reverse('api:workflow_job_template_node_list')
|
||||
data['workflow_job_nodes'] = reverse('api:workflow_job_node_list')
|
||||
data['authtoken'] = reverse('api:auth_token_view', request=request)
|
||||
data['ping'] = reverse('api:api_v1_ping_view', request=request)
|
||||
data['config'] = reverse('api:api_v1_config_view', request=request)
|
||||
data['settings'] = reverse('api:setting_category_list', request=request)
|
||||
data['me'] = reverse('api:user_me_list', request=request)
|
||||
data['dashboard'] = reverse('api:dashboard_view', request=request)
|
||||
data['organizations'] = reverse('api:organization_list', request=request)
|
||||
data['users'] = reverse('api:user_list', request=request)
|
||||
data['projects'] = reverse('api:project_list', request=request)
|
||||
data['project_updates'] = reverse('api:project_update_list', request=request)
|
||||
data['teams'] = reverse('api:team_list', request=request)
|
||||
data['credentials'] = reverse('api:credential_list', request=request)
|
||||
data['inventory'] = reverse('api:inventory_list', request=request)
|
||||
data['inventory_scripts'] = reverse('api:inventory_script_list', request=request)
|
||||
data['inventory_sources'] = reverse('api:inventory_source_list', request=request)
|
||||
data['inventory_updates'] = reverse('api:inventory_update_list', request=request)
|
||||
data['groups'] = reverse('api:group_list', request=request)
|
||||
data['hosts'] = reverse('api:host_list', request=request)
|
||||
data['job_templates'] = reverse('api:job_template_list', request=request)
|
||||
data['jobs'] = reverse('api:job_list', request=request)
|
||||
data['job_events'] = reverse('api:job_event_list', request=request)
|
||||
data['ad_hoc_commands'] = reverse('api:ad_hoc_command_list', request=request)
|
||||
data['system_job_templates'] = reverse('api:system_job_template_list', request=request)
|
||||
data['system_jobs'] = reverse('api:system_job_list', request=request)
|
||||
data['schedules'] = reverse('api:schedule_list', request=request)
|
||||
data['roles'] = reverse('api:role_list', request=request)
|
||||
data['notification_templates'] = reverse('api:notification_template_list', request=request)
|
||||
data['notifications'] = reverse('api:notification_list', request=request)
|
||||
data['labels'] = reverse('api:label_list', request=request)
|
||||
data['unified_job_templates'] = reverse('api:unified_job_template_list', request=request)
|
||||
data['unified_jobs'] = reverse('api:unified_job_list', request=request)
|
||||
data['activity_stream'] = reverse('api:activity_stream_list', request=request)
|
||||
data['workflow_job_templates'] = reverse('api:workflow_job_template_list', request=request)
|
||||
data['workflow_jobs'] = reverse('api:workflow_job_list', request=request)
|
||||
data['workflow_job_template_nodes'] = reverse('api:workflow_job_template_node_list', request=request)
|
||||
data['workflow_job_nodes'] = reverse('api:workflow_job_node_list', request=request)
|
||||
return Response(data)
|
||||
|
||||
|
||||
@ -336,12 +336,12 @@ class DashboardView(APIView):
|
||||
def get(self, request, format=None):
|
||||
''' Show Dashboard Details '''
|
||||
data = OrderedDict()
|
||||
data['related'] = {'jobs_graph': reverse('api:dashboard_jobs_graph_view')}
|
||||
data['related'] = {'jobs_graph': reverse('api:dashboard_jobs_graph_view', request=request)}
|
||||
user_inventory = get_user_queryset(request.user, Inventory)
|
||||
inventory_with_failed_hosts = user_inventory.filter(hosts_with_active_failures__gt=0)
|
||||
user_inventory_external = user_inventory.filter(has_inventory_sources=True)
|
||||
failed_inventory = sum(i.inventory_sources_with_failures for i in user_inventory)
|
||||
data['inventories'] = {'url': reverse('api:inventory_list'),
|
||||
data['inventories'] = {'url': reverse('api:inventory_list', request=request),
|
||||
'total': user_inventory.count(),
|
||||
'total_with_inventory_source': user_inventory_external.count(),
|
||||
'job_failed': inventory_with_failed_hosts.count(),
|
||||
@ -352,13 +352,13 @@ class DashboardView(APIView):
|
||||
ec2_inventory_sources = user_inventory_sources.filter(source='ec2')
|
||||
ec2_inventory_failed = ec2_inventory_sources.filter(status='failed')
|
||||
data['inventory_sources'] = {}
|
||||
data['inventory_sources']['rax'] = {'url': reverse('api:inventory_source_list') + "?source=rax",
|
||||
data['inventory_sources']['rax'] = {'url': reverse('api:inventory_source_list', request=request) + "?source=rax",
|
||||
'label': 'Rackspace',
|
||||
'failures_url': reverse('api:inventory_source_list') + "?source=rax&status=failed",
|
||||
'failures_url': reverse('api:inventory_source_list', request=request) + "?source=rax&status=failed",
|
||||
'total': rax_inventory_sources.count(),
|
||||
'failed': rax_inventory_failed.count()}
|
||||
data['inventory_sources']['ec2'] = {'url': reverse('api:inventory_source_list') + "?source=ec2",
|
||||
'failures_url': reverse('api:inventory_source_list') + "?source=ec2&status=failed",
|
||||
data['inventory_sources']['ec2'] = {'url': reverse('api:inventory_source_list', request=request) + "?source=ec2",
|
||||
'failures_url': reverse('api:inventory_source_list', request=request) + "?source=ec2&status=failed",
|
||||
'label': 'Amazon EC2',
|
||||
'total': ec2_inventory_sources.count(),
|
||||
'failed': ec2_inventory_failed.count()}
|
||||
@ -366,23 +366,23 @@ class DashboardView(APIView):
|
||||
user_groups = get_user_queryset(request.user, Group)
|
||||
groups_job_failed = (Group.objects.filter(hosts_with_active_failures__gt=0) | Group.objects.filter(groups_with_active_failures__gt=0)).count()
|
||||
groups_inventory_failed = Group.objects.filter(inventory_sources__last_job_failed=True).count()
|
||||
data['groups'] = {'url': reverse('api:group_list'),
|
||||
'failures_url': reverse('api:group_list') + "?has_active_failures=True",
|
||||
data['groups'] = {'url': reverse('api:group_list', request=request),
|
||||
'failures_url': reverse('api:group_list', request=request) + "?has_active_failures=True",
|
||||
'total': user_groups.count(),
|
||||
'job_failed': groups_job_failed,
|
||||
'inventory_failed': groups_inventory_failed}
|
||||
|
||||
user_hosts = get_user_queryset(request.user, Host)
|
||||
user_hosts_failed = user_hosts.filter(has_active_failures=True)
|
||||
data['hosts'] = {'url': reverse('api:host_list'),
|
||||
'failures_url': reverse('api:host_list') + "?has_active_failures=True",
|
||||
data['hosts'] = {'url': reverse('api:host_list', request=request),
|
||||
'failures_url': reverse('api:host_list', request=request) + "?has_active_failures=True",
|
||||
'total': user_hosts.count(),
|
||||
'failed': user_hosts_failed.count()}
|
||||
|
||||
user_projects = get_user_queryset(request.user, Project)
|
||||
user_projects_failed = user_projects.filter(last_job_failed=True)
|
||||
data['projects'] = {'url': reverse('api:project_list'),
|
||||
'failures_url': reverse('api:project_list') + "?last_job_failed=True",
|
||||
data['projects'] = {'url': reverse('api:project_list', request=request),
|
||||
'failures_url': reverse('api:project_list', request=request) + "?last_job_failed=True",
|
||||
'total': user_projects.count(),
|
||||
'failed': user_projects_failed.count()}
|
||||
|
||||
@ -393,26 +393,26 @@ class DashboardView(APIView):
|
||||
hg_projects = user_projects.filter(scm_type='hg')
|
||||
hg_failed_projects = hg_projects.filter(last_job_failed=True)
|
||||
data['scm_types'] = {}
|
||||
data['scm_types']['git'] = {'url': reverse('api:project_list') + "?scm_type=git",
|
||||
data['scm_types']['git'] = {'url': reverse('api:project_list', request=request) + "?scm_type=git",
|
||||
'label': 'Git',
|
||||
'failures_url': reverse('api:project_list') + "?scm_type=git&last_job_failed=True",
|
||||
'failures_url': reverse('api:project_list', request=request) + "?scm_type=git&last_job_failed=True",
|
||||
'total': git_projects.count(),
|
||||
'failed': git_failed_projects.count()}
|
||||
data['scm_types']['svn'] = {'url': reverse('api:project_list') + "?scm_type=svn",
|
||||
data['scm_types']['svn'] = {'url': reverse('api:project_list', request=request) + "?scm_type=svn",
|
||||
'label': 'Subversion',
|
||||
'failures_url': reverse('api:project_list') + "?scm_type=svn&last_job_failed=True",
|
||||
'failures_url': reverse('api:project_list', request=request) + "?scm_type=svn&last_job_failed=True",
|
||||
'total': svn_projects.count(),
|
||||
'failed': svn_failed_projects.count()}
|
||||
data['scm_types']['hg'] = {'url': reverse('api:project_list') + "?scm_type=hg",
|
||||
data['scm_types']['hg'] = {'url': reverse('api:project_list', request=request) + "?scm_type=hg",
|
||||
'label': 'Mercurial',
|
||||
'failures_url': reverse('api:project_list') + "?scm_type=hg&last_job_failed=True",
|
||||
'failures_url': reverse('api:project_list', request=request) + "?scm_type=hg&last_job_failed=True",
|
||||
'total': hg_projects.count(),
|
||||
'failed': hg_failed_projects.count()}
|
||||
|
||||
user_jobs = get_user_queryset(request.user, Job)
|
||||
user_failed_jobs = user_jobs.filter(failed=True)
|
||||
data['jobs'] = {'url': reverse('api:job_list'),
|
||||
'failure_url': reverse('api:job_list') + "?failed=True",
|
||||
data['jobs'] = {'url': reverse('api:job_list', request=request),
|
||||
'failure_url': reverse('api:job_list', request=request) + "?failed=True",
|
||||
'total': user_jobs.count(),
|
||||
'failed': user_failed_jobs.count()}
|
||||
|
||||
@ -421,15 +421,15 @@ class DashboardView(APIView):
|
||||
credential_list = get_user_queryset(request.user, Credential)
|
||||
job_template_list = get_user_queryset(request.user, JobTemplate)
|
||||
organization_list = get_user_queryset(request.user, Organization)
|
||||
data['users'] = {'url': reverse('api:user_list'),
|
||||
data['users'] = {'url': reverse('api:user_list', request=request),
|
||||
'total': user_list.count()}
|
||||
data['organizations'] = {'url': reverse('api:organization_list'),
|
||||
data['organizations'] = {'url': reverse('api:organization_list', request=request),
|
||||
'total': organization_list.count()}
|
||||
data['teams'] = {'url': reverse('api:team_list'),
|
||||
data['teams'] = {'url': reverse('api:team_list', request=request),
|
||||
'total': team_list.count()}
|
||||
data['credentials'] = {'url': reverse('api:credential_list'),
|
||||
data['credentials'] = {'url': reverse('api:credential_list', request=request),
|
||||
'total': credential_list.count()}
|
||||
data['job_templates'] = {'url': reverse('api:job_template_list'),
|
||||
data['job_templates'] = {'url': reverse('api:job_template_list', request=request),
|
||||
'total': job_template_list.count()}
|
||||
return Response(data)
|
||||
|
||||
@ -516,6 +516,7 @@ class AuthView(APIView):
|
||||
new_in_240 = True
|
||||
|
||||
def get(self, request):
|
||||
from rest_framework.reverse import reverse
|
||||
data = OrderedDict()
|
||||
err_backend, err_message = request.session.get('social_auth_error', (None, None))
|
||||
auth_backends = load_backends(settings.AUTHENTICATION_BACKENDS, force_load=True).items()
|
||||
@ -527,6 +528,7 @@ class AuthView(APIView):
|
||||
(not feature_enabled('enterprise_auth') and
|
||||
name in ['saml', 'radius']):
|
||||
continue
|
||||
|
||||
login_url = reverse('social:begin', args=(name,))
|
||||
complete_url = request.build_absolute_uri(reverse('social:complete', args=(name,)))
|
||||
backend_data = {
|
||||
@ -1167,7 +1169,7 @@ class ProjectUpdateView(RetrieveAPIView):
|
||||
if not project_update:
|
||||
return Response({}, status=status.HTTP_400_BAD_REQUEST)
|
||||
else:
|
||||
headers = {'Location': project_update.get_absolute_url()}
|
||||
headers = {'Location': project_update.get_absolute_url(request=request)}
|
||||
return Response({'project_update': project_update.id},
|
||||
headers=headers,
|
||||
status=status.HTTP_202_ACCEPTED)
|
||||
@ -2273,7 +2275,7 @@ class InventorySourceUpdateView(RetrieveAPIView):
|
||||
if not inventory_update:
|
||||
return Response({}, status=status.HTTP_400_BAD_REQUEST)
|
||||
else:
|
||||
headers = {'Location': inventory_update.get_absolute_url()}
|
||||
headers = {'Location': inventory_update.get_absolute_url(request=request)}
|
||||
return Response(dict(inventory_update=inventory_update.id), status=status.HTTP_202_ACCEPTED, headers=headers)
|
||||
else:
|
||||
return self.http_method_not_allowed(request, *args, **kwargs)
|
||||
@ -2741,7 +2743,7 @@ class JobTemplateCallback(GenericAPIView):
|
||||
return Response(data, status=status.HTTP_400_BAD_REQUEST)
|
||||
|
||||
# Return the location of the new job.
|
||||
headers = {'Location': job.get_absolute_url()}
|
||||
headers = {'Location': job.get_absolute_url(request=request)}
|
||||
return Response(status=status.HTTP_201_CREATED, headers=headers)
|
||||
|
||||
|
||||
@ -3035,7 +3037,7 @@ class WorkflowJobRelaunch(WorkflowsEnforcementMixin, GenericAPIView):
|
||||
new_workflow_job.signal_start()
|
||||
|
||||
data = WorkflowJobSerializer(new_workflow_job, context=self.get_serializer_context()).data
|
||||
headers = {'Location': new_workflow_job.get_absolute_url()}
|
||||
headers = {'Location': new_workflow_job.get_absolute_url(request=request)}
|
||||
return Response(data, status=status.HTTP_201_CREATED, headers=headers)
|
||||
|
||||
|
||||
@ -3419,7 +3421,7 @@ class JobRelaunch(RetrieveAPIView, GenericAPIView):
|
||||
data = JobSerializer(new_job, context=self.get_serializer_context()).data
|
||||
# Add job key to match what old relaunch returned.
|
||||
data['job'] = new_job.id
|
||||
headers = {'Location': new_job.get_absolute_url()}
|
||||
headers = {'Location': new_job.get_absolute_url(request=request)}
|
||||
return Response(data, status=status.HTTP_201_CREATED, headers=headers)
|
||||
|
||||
|
||||
@ -3693,7 +3695,7 @@ class AdHocCommandRelaunch(GenericAPIView):
|
||||
data = AdHocCommandSerializer(new_ad_hoc_command, context=self.get_serializer_context()).data
|
||||
# Add ad_hoc_command key to match what was previously returned.
|
||||
data['ad_hoc_command'] = new_ad_hoc_command.id
|
||||
headers = {'Location': new_ad_hoc_command.get_absolute_url()}
|
||||
headers = {'Location': new_ad_hoc_command.get_absolute_url(request=request)}
|
||||
return Response(data, status=status.HTTP_201_CREATED, headers=headers)
|
||||
|
||||
|
||||
@ -3994,7 +3996,7 @@ class NotificationTemplateTest(GenericAPIView):
|
||||
return Response({}, status=status.HTTP_400_BAD_REQUEST)
|
||||
else:
|
||||
send_notifications.delay([notification.id])
|
||||
headers = {'Location': notification.get_absolute_url()}
|
||||
headers = {'Location': notification.get_absolute_url(request=request)}
|
||||
return Response({"notification": notification.id},
|
||||
headers=headers,
|
||||
status=status.HTTP_202_ACCEPTED)
|
||||
|
||||
@ -7,7 +7,6 @@ import sys
|
||||
|
||||
# Django
|
||||
from django.conf import settings
|
||||
from django.core.urlresolvers import reverse
|
||||
from django.http import Http404
|
||||
from django.utils.translation import ugettext_lazy as _
|
||||
|
||||
@ -20,6 +19,7 @@ from rest_framework import status
|
||||
# Tower
|
||||
from awx.api.generics import * # noqa
|
||||
from awx.api.permissions import IsSuperUser
|
||||
from awx.api.versioning import reverse
|
||||
from awx.main.utils import * # noqa
|
||||
from awx.main.utils.handlers import BaseHTTPSHandler, LoggingConnectivityException
|
||||
from awx.conf.license import get_licensed_features
|
||||
@ -49,7 +49,7 @@ class SettingCategoryList(ListAPIView):
|
||||
else:
|
||||
categories = {}
|
||||
for category_slug in sorted(categories.keys()):
|
||||
url = reverse('api:setting_singleton_detail', args=(category_slug,))
|
||||
url = reverse('api:setting_singleton_detail', kwargs={'category_slug': category_slug}, request=self.request)
|
||||
setting_categories.append(SettingCategory(url, category_slug, categories[category_slug]))
|
||||
return setting_categories
|
||||
|
||||
|
||||
@ -1,9 +1,11 @@
|
||||
# Copyright (c) 2015 Ansible, Inc.
|
||||
# All Rights Reserved.
|
||||
|
||||
# Tower
|
||||
from awx.api.versioning import reverse
|
||||
|
||||
# Django
|
||||
from django.db import models
|
||||
from django.core.urlresolvers import reverse
|
||||
from django.utils.translation import ugettext_lazy as _
|
||||
|
||||
__all__ = ['ActivityStream']
|
||||
@ -63,8 +65,8 @@ class ActivityStream(models.Model):
|
||||
label = models.ManyToManyField("Label", blank=True)
|
||||
role = models.ManyToManyField("Role", blank=True)
|
||||
|
||||
def get_absolute_url(self):
|
||||
return reverse('api:activity_stream_detail', args=(self.pk,))
|
||||
def get_absolute_url(self, request=None):
|
||||
return reverse('api:activity_stream_detail', kwargs={'pk': self.pk}, request=request)
|
||||
|
||||
def save(self, *args, **kwargs):
|
||||
# For compatibility with Django 1.4.x, attempt to handle any calls to
|
||||
|
||||
@ -16,9 +16,9 @@ from django.utils.text import Truncator
|
||||
from django.utils.timezone import utc
|
||||
from django.utils.translation import ugettext_lazy as _
|
||||
from django.core.exceptions import ValidationError
|
||||
from django.core.urlresolvers import reverse
|
||||
|
||||
# AWX
|
||||
from awx.api.versioning import reverse
|
||||
from awx.main.models.base import * # noqa
|
||||
from awx.main.models.unified_jobs import * # noqa
|
||||
from awx.main.models.notifications import JobNotificationMixin, NotificationTemplate
|
||||
@ -143,8 +143,8 @@ class AdHocCommand(UnifiedJob, JobNotificationMixin):
|
||||
from awx.main.tasks import RunAdHocCommand
|
||||
return RunAdHocCommand
|
||||
|
||||
def get_absolute_url(self):
|
||||
return reverse('api:ad_hoc_command_detail', args=(self.pk,))
|
||||
def get_absolute_url(self, request=None):
|
||||
return reverse('api:ad_hoc_command_detail', kwargs={'pk': self.pk}, request=request)
|
||||
|
||||
def get_ui_url(self):
|
||||
return urljoin(settings.TOWER_URL_BASE, "/#/ad_hoc_commands/{}".format(self.pk))
|
||||
@ -318,8 +318,8 @@ class AdHocCommandEvent(CreatedModifiedModel):
|
||||
editable=False,
|
||||
)
|
||||
|
||||
def get_absolute_url(self):
|
||||
return reverse('api:ad_hoc_command_event_detail', args=(self.pk,))
|
||||
def get_absolute_url(self, request=None):
|
||||
return reverse('api:ad_hoc_command_event_detail', kwargs={'pk': self.pk}, request=request)
|
||||
|
||||
def __unicode__(self):
|
||||
return u'%s @ %s' % (self.get_event_display(), self.created.isoformat())
|
||||
|
||||
@ -5,9 +5,9 @@
|
||||
from django.db import models
|
||||
from django.utils.translation import ugettext_lazy as _
|
||||
from django.core.exceptions import ValidationError
|
||||
from django.core.urlresolvers import reverse
|
||||
|
||||
# AWX
|
||||
from awx.api.versioning import reverse
|
||||
from awx.main.fields import ImplicitRoleField
|
||||
from awx.main.constants import CLOUD_PROVIDERS
|
||||
from awx.main.utils import decrypt_field
|
||||
@ -271,8 +271,8 @@ class Credential(PasswordFieldsModel, CommonModelNameNotUnique, ResourceMixin):
|
||||
needed.append(field)
|
||||
return needed
|
||||
|
||||
def get_absolute_url(self):
|
||||
return reverse('api:credential_detail', args=(self.pk,))
|
||||
def get_absolute_url(self, request=None):
|
||||
return reverse('api:credential_detail', kwargs={'pk': self.pk}, request=request)
|
||||
|
||||
def clean_host(self):
|
||||
"""Ensure that if this is a type of credential that requires a
|
||||
|
||||
@ -14,10 +14,10 @@ from django.db import models
|
||||
from django.utils.translation import ugettext_lazy as _
|
||||
from django.db import transaction
|
||||
from django.core.exceptions import ValidationError
|
||||
from django.core.urlresolvers import reverse
|
||||
from django.utils.timezone import now
|
||||
|
||||
# AWX
|
||||
from awx.api.versioning import reverse
|
||||
from awx.main.constants import CLOUD_PROVIDERS
|
||||
from awx.main.fields import AutoOneToOneField, ImplicitRoleField
|
||||
from awx.main.managers import HostManager
|
||||
@ -117,9 +117,8 @@ class Inventory(CommonModelNameNotUnique, ResourceMixin):
|
||||
'admin_role',
|
||||
])
|
||||
|
||||
def get_absolute_url(self):
|
||||
return reverse('api:inventory_detail', args=(self.pk,))
|
||||
|
||||
def get_absolute_url(self, request=None):
|
||||
return reverse('api:inventory_detail', kwargs={'pk': self.pk}, request=request)
|
||||
|
||||
variables_dict = VarsDictProperty('variables')
|
||||
|
||||
@ -389,8 +388,8 @@ class Host(CommonModelNameNotUnique):
|
||||
def __unicode__(self):
|
||||
return self.name
|
||||
|
||||
def get_absolute_url(self):
|
||||
return reverse('api:host_detail', args=(self.pk,))
|
||||
def get_absolute_url(self, request=None):
|
||||
return reverse('api:host_detail', kwargs={'pk': self.pk}, request=request)
|
||||
|
||||
def update_computed_fields(self, update_inventory=True, update_groups=True):
|
||||
'''
|
||||
@ -520,8 +519,8 @@ class Group(CommonModelNameNotUnique):
|
||||
def __unicode__(self):
|
||||
return self.name
|
||||
|
||||
def get_absolute_url(self):
|
||||
return reverse('api:group_detail', args=(self.pk,))
|
||||
def get_absolute_url(self, request=None):
|
||||
return reverse('api:group_detail', kwargs={'pk': self.pk}, request=request)
|
||||
|
||||
@transaction.atomic
|
||||
def delete_recursive(self):
|
||||
@ -1137,8 +1136,8 @@ class InventorySource(UnifiedJobTemplate, InventorySourceOptions):
|
||||
else:
|
||||
return 'none'
|
||||
|
||||
def get_absolute_url(self):
|
||||
return reverse('api:inventory_source_detail', args=(self.pk,))
|
||||
def get_absolute_url(self, request=None):
|
||||
return reverse('api:inventory_source_detail', kwargs={'pk': self.pk}, request=request)
|
||||
|
||||
def _can_update(self):
|
||||
if self.source == 'custom':
|
||||
@ -1246,8 +1245,8 @@ class InventoryUpdate(UnifiedJob, InventorySourceOptions, JobNotificationMixin):
|
||||
update_fields.append('name')
|
||||
super(InventoryUpdate, self).save(*args, **kwargs)
|
||||
|
||||
def get_absolute_url(self):
|
||||
return reverse('api:inventory_update_detail', args=(self.pk,))
|
||||
def get_absolute_url(self, request=None):
|
||||
return reverse('api:inventory_update_detail', kwargs={'pk': self.pk}, request=request)
|
||||
|
||||
def get_ui_url(self):
|
||||
return urljoin(settings.TOWER_URL_BASE, "/#/inventory_sync/{}".format(self.pk))
|
||||
@ -1322,5 +1321,5 @@ class CustomInventoryScript(CommonModelNameNotUnique, ResourceMixin):
|
||||
parent_role=['organization.auditor_role', 'organization.member_role', 'admin_role'],
|
||||
)
|
||||
|
||||
def get_absolute_url(self):
|
||||
return reverse('api:inventory_script_detail', args=(self.pk,))
|
||||
def get_absolute_url(self, request=None):
|
||||
return reverse('api:inventory_script_detail', kwargs={'pk': self.pk}, request=request)
|
||||
|
||||
@ -18,9 +18,9 @@ from django.utils.encoding import force_text
|
||||
from django.utils.timezone import utc
|
||||
from django.utils.translation import ugettext_lazy as _
|
||||
from django.core.exceptions import ValidationError
|
||||
from django.core.urlresolvers import reverse
|
||||
|
||||
# AWX
|
||||
from awx.api.versioning import reverse
|
||||
from awx.main.constants import CLOUD_PROVIDERS
|
||||
from awx.main.models.base import * # noqa
|
||||
from awx.main.models.unified_jobs import * # noqa
|
||||
@ -293,8 +293,8 @@ class JobTemplate(UnifiedJobTemplate, JobOptions, SurveyJobTemplateMixin, Resour
|
||||
'''
|
||||
return self.create_unified_job(**kwargs)
|
||||
|
||||
def get_absolute_url(self):
|
||||
return reverse('api:job_template_detail', args=(self.pk,))
|
||||
def get_absolute_url(self, request=None):
|
||||
return reverse('api:job_template_detail', kwargs={'pk': self.pk}, request=request)
|
||||
|
||||
def can_start_without_user_input(self, callback_extra_vars=None):
|
||||
'''
|
||||
@ -471,8 +471,8 @@ class Job(UnifiedJob, JobOptions, SurveyJobMixin, JobNotificationMixin):
|
||||
def _get_unified_job_template_class(cls):
|
||||
return JobTemplate
|
||||
|
||||
def get_absolute_url(self):
|
||||
return reverse('api:job_detail', args=(self.pk,))
|
||||
def get_absolute_url(self, request=None):
|
||||
return reverse('api:job_detail', kwargs={'pk': self.pk}, request=request)
|
||||
|
||||
def get_ui_url(self):
|
||||
return urljoin(settings.TOWER_URL_BASE, "/#/jobs/{}".format(self.pk))
|
||||
@ -688,8 +688,8 @@ class JobHostSummary(CreatedModifiedModel):
|
||||
(self.host.name, self.changed, self.dark, self.failures, self.ok,
|
||||
self.processed, self.skipped)
|
||||
|
||||
def get_absolute_url(self):
|
||||
return reverse('api:job_host_summary_detail', args=(self.pk,))
|
||||
def get_absolute_url(self, request=None):
|
||||
return reverse('api:job_host_summary_detail', kwargs={'pk': self.pk}, request=request)
|
||||
|
||||
def save(self, *args, **kwargs):
|
||||
# If update_fields has been specified, add our field names to it,
|
||||
@ -906,8 +906,8 @@ class JobEvent(CreatedModifiedModel):
|
||||
editable=False,
|
||||
)
|
||||
|
||||
def get_absolute_url(self):
|
||||
return reverse('api:job_event_detail', args=(self.pk,))
|
||||
def get_absolute_url(self, request=None):
|
||||
return reverse('api:job_event_detail', kwargs={'pk': self.pk}, request=request)
|
||||
|
||||
def __unicode__(self):
|
||||
return u'%s @ %s' % (self.get_event_display2(), self.created.isoformat())
|
||||
@ -1220,8 +1220,8 @@ class SystemJobTemplate(UnifiedJobTemplate, SystemJobOptions):
|
||||
def _get_unified_job_field_names(cls):
|
||||
return ['name', 'description', 'job_type', 'extra_vars']
|
||||
|
||||
def get_absolute_url(self):
|
||||
return reverse('api:system_job_template_detail', args=(self.pk,))
|
||||
def get_absolute_url(self, request=None):
|
||||
return reverse('api:system_job_template_detail', kwargs={'pk': self.pk}, request=request)
|
||||
|
||||
@property
|
||||
def cache_timeout_blocked(self):
|
||||
@ -1276,8 +1276,8 @@ class SystemJob(UnifiedJob, SystemJobOptions, JobNotificationMixin):
|
||||
def websocket_emit_data(self):
|
||||
return {}
|
||||
|
||||
def get_absolute_url(self):
|
||||
return reverse('api:system_job_detail', args=(self.pk,))
|
||||
def get_absolute_url(self, request=None):
|
||||
return reverse('api:system_job_detail', kwargs={'pk': self.pk}, request=request)
|
||||
|
||||
def get_ui_url(self):
|
||||
return urljoin(settings.TOWER_URL_BASE, "/#/management_jobs/{}".format(self.pk))
|
||||
|
||||
@ -3,10 +3,10 @@
|
||||
|
||||
# Django
|
||||
from django.db import models
|
||||
from django.core.urlresolvers import reverse
|
||||
from django.utils.translation import ugettext_lazy as _
|
||||
|
||||
# AWX
|
||||
from awx.api.versioning import reverse
|
||||
from awx.main.models.base import CommonModelNameNotUnique
|
||||
from awx.main.models.unified_jobs import UnifiedJobTemplate, UnifiedJob
|
||||
|
||||
@ -30,8 +30,8 @@ class Label(CommonModelNameNotUnique):
|
||||
on_delete=models.CASCADE,
|
||||
)
|
||||
|
||||
def get_absolute_url(self):
|
||||
return reverse('api:label_detail', args=(self.pk,))
|
||||
def get_absolute_url(self, request=None):
|
||||
return reverse('api:label_detail', kwargs={'pk': self.pk}, request=request)
|
||||
|
||||
@staticmethod
|
||||
def get_orphaned_labels():
|
||||
|
||||
@ -4,11 +4,12 @@
|
||||
import logging
|
||||
|
||||
from django.db import models
|
||||
from django.core.urlresolvers import reverse
|
||||
from django.core.mail.message import EmailMessage
|
||||
from django.utils.translation import ugettext_lazy as _
|
||||
from django.utils.encoding import smart_str
|
||||
|
||||
# AWX
|
||||
from awx.api.versioning import reverse
|
||||
from awx.main.models.base import * # noqa
|
||||
from awx.main.utils import encrypt_field, decrypt_field
|
||||
from awx.main.notifications.email_backend import CustomEmailBackend
|
||||
@ -56,8 +57,8 @@ class NotificationTemplate(CommonModel):
|
||||
|
||||
notification_configuration = JSONField(blank=False)
|
||||
|
||||
def get_absolute_url(self):
|
||||
return reverse('api:notification_template_detail', args=(self.pk,))
|
||||
def get_absolute_url(self, request=None):
|
||||
return reverse('api:notification_template_detail', kwargs={'pk': self.pk}, request=request)
|
||||
|
||||
@property
|
||||
def notification_class(self):
|
||||
@ -169,9 +170,9 @@ class Notification(CreatedModifiedModel):
|
||||
editable=False,
|
||||
)
|
||||
body = JSONField(blank=True)
|
||||
|
||||
def get_absolute_url(self):
|
||||
return reverse('api:notification_detail', args=(self.pk,))
|
||||
|
||||
def get_absolute_url(self, request=None):
|
||||
return reverse('api:notification_detail', kwargs={'pk': self.pk}, request=request)
|
||||
|
||||
|
||||
class JobNotificationMixin(object):
|
||||
|
||||
@ -10,12 +10,12 @@ import uuid
|
||||
# Django
|
||||
from django.conf import settings
|
||||
from django.db import models
|
||||
from django.core.urlresolvers import reverse
|
||||
from django.contrib.auth.models import User
|
||||
from django.utils.timezone import now as tz_now
|
||||
from django.utils.translation import ugettext_lazy as _
|
||||
|
||||
# AWX
|
||||
from awx.api.versioning import reverse
|
||||
from awx.main.fields import AutoOneToOneField, ImplicitRoleField
|
||||
from awx.main.models.base import * # noqa
|
||||
from awx.main.models.rbac import (
|
||||
@ -65,8 +65,8 @@ class Organization(CommonModel, NotificationFieldsModel, ResourceMixin):
|
||||
)
|
||||
|
||||
|
||||
def get_absolute_url(self):
|
||||
return reverse('api:organization_detail', args=(self.pk,))
|
||||
def get_absolute_url(self, request=None):
|
||||
return reverse('api:organization_detail', kwargs={'pk': self.pk}, request=request)
|
||||
|
||||
def __unicode__(self):
|
||||
return self.name
|
||||
@ -109,8 +109,8 @@ class Team(CommonModelNameNotUnique, ResourceMixin):
|
||||
parent_role=['organization.auditor_role', 'member_role'],
|
||||
)
|
||||
|
||||
def get_absolute_url(self):
|
||||
return reverse('api:team_detail', args=(self.pk,))
|
||||
def get_absolute_url(self, request=None):
|
||||
return reverse('api:team_detail', kwargs={'pk': self.pk}, request=request)
|
||||
|
||||
|
||||
class Permission(CommonModelNameNotUnique):
|
||||
@ -167,8 +167,8 @@ class Permission(CommonModelNameNotUnique):
|
||||
'+adhoc' if self.run_ad_hoc_commands else '',
|
||||
))
|
||||
|
||||
def get_absolute_url(self):
|
||||
return reverse('api:permission_detail', args=(self.pk,))
|
||||
def get_absolute_url(self, request=None):
|
||||
return reverse('api:permission_detail', kwargs={'pk': self.pk}, request=request)
|
||||
|
||||
|
||||
class Profile(CreatedModifiedModel):
|
||||
@ -326,6 +326,6 @@ class AuthToken(BaseModel):
|
||||
|
||||
# Add get_absolute_url method to User model if not present.
|
||||
if not hasattr(User, 'get_absolute_url'):
|
||||
def user_get_absolute_url(user):
|
||||
return reverse('api:user_detail', args=(user.pk,))
|
||||
def user_get_absolute_url(user, request=None):
|
||||
return reverse('api:user_detail', kwargs={'pk': user.pk}, request=request)
|
||||
User.add_to_class('get_absolute_url', user_get_absolute_url)
|
||||
|
||||
@ -14,10 +14,10 @@ from django.utils.translation import ugettext_lazy as _
|
||||
from django.utils.encoding import smart_str, smart_text
|
||||
from django.utils.text import slugify
|
||||
from django.core.exceptions import ValidationError
|
||||
from django.core.urlresolvers import reverse
|
||||
from django.utils.timezone import now, make_aware, get_default_timezone
|
||||
|
||||
# AWX
|
||||
from awx.api.versioning import reverse
|
||||
from awx.main.models.base import * # noqa
|
||||
from awx.main.models.notifications import (
|
||||
NotificationTemplate,
|
||||
@ -401,8 +401,8 @@ class Project(UnifiedJobTemplate, ProjectOptions, ResourceMixin):
|
||||
success=list(success_notification_templates),
|
||||
any=list(any_notification_templates))
|
||||
|
||||
def get_absolute_url(self):
|
||||
return reverse('api:project_detail', args=(self.pk,))
|
||||
def get_absolute_url(self, request=None):
|
||||
return reverse('api:project_detail', kwargs={'pk': self.pk}, request=request)
|
||||
|
||||
|
||||
class ProjectUpdate(UnifiedJob, ProjectOptions, JobNotificationMixin):
|
||||
@ -470,8 +470,8 @@ class ProjectUpdate(UnifiedJob, ProjectOptions, JobNotificationMixin):
|
||||
def result_stdout_limited(self, start_line=0, end_line=None, redact_sensitive=True):
|
||||
return self._result_stdout_raw_limited(start_line, end_line, redact_sensitive=redact_sensitive, escape_ascii=True)
|
||||
|
||||
def get_absolute_url(self):
|
||||
return reverse('api:project_update_detail', args=(self.pk,))
|
||||
def get_absolute_url(self, request=None):
|
||||
return reverse('api:project_update_detail', kwargs={'pk': self.pk}, request=request)
|
||||
|
||||
def get_ui_url(self):
|
||||
return urlparse.urljoin(settings.TOWER_URL_BASE, "/#/scm_update/{}".format(self.pk))
|
||||
|
||||
@ -9,13 +9,12 @@ import re
|
||||
|
||||
# Django
|
||||
from django.db import models, transaction, connection
|
||||
from django.core.urlresolvers import reverse
|
||||
from django.contrib.contenttypes.models import ContentType
|
||||
from django.contrib.contenttypes.fields import GenericForeignKey
|
||||
from django.utils.translation import ugettext_lazy as _
|
||||
|
||||
|
||||
# AWX
|
||||
from awx.api.versioning import reverse
|
||||
from django.contrib.auth.models import User # noqa
|
||||
from awx.main.models.base import * # noqa
|
||||
|
||||
@ -145,8 +144,8 @@ class Role(models.Model):
|
||||
super(Role, self).save(*args, **kwargs)
|
||||
self.rebuild_role_ancestor_list([self.id], [])
|
||||
|
||||
def get_absolute_url(self):
|
||||
return reverse('api:role_detail', args=(self.pk,))
|
||||
def get_absolute_url(self, request=None):
|
||||
return reverse('api:role_detail', kwargs={'pk': self.pk}, request=request)
|
||||
|
||||
def __contains__(self, accessor):
|
||||
if type(accessor) == User:
|
||||
|
||||
@ -13,10 +13,10 @@ from django.utils.timezone import now, make_aware, get_default_timezone
|
||||
from django.utils.translation import ugettext_lazy as _
|
||||
|
||||
# AWX
|
||||
from awx.api.versioning import reverse
|
||||
from awx.main.models.base import * # noqa
|
||||
from awx.main.utils import ignore_inventory_computed_fields
|
||||
from awx.main.consumers import emit_channel_notification
|
||||
from django.core.urlresolvers import reverse
|
||||
from awx.main.fields import JSONField
|
||||
|
||||
logger = logging.getLogger('awx.main.models.schedule')
|
||||
@ -98,8 +98,8 @@ class Schedule(CommonModel):
|
||||
def __unicode__(self):
|
||||
return u'%s_t%s_%s_%s' % (self.name, self.unified_job_template.id, self.id, self.next_run)
|
||||
|
||||
def get_absolute_url(self):
|
||||
return reverse('api:schedule_detail', args=(self.pk,))
|
||||
def get_absolute_url(self, request=None):
|
||||
return reverse('api:schedule_detail', kwargs={'pk': self.pk}, request=request)
|
||||
|
||||
def update_computed_fields(self):
|
||||
future_rs = dateutil.rrule.rrulestr(self.rrule, forceset=True)
|
||||
|
||||
@ -153,10 +153,10 @@ class UnifiedJobTemplate(PolymorphicModel, CommonModelNameNotUnique, Notificatio
|
||||
related_name='%(class)s_labels'
|
||||
)
|
||||
|
||||
def get_absolute_url(self):
|
||||
def get_absolute_url(self, request=None):
|
||||
real_instance = self.get_real_instance()
|
||||
if real_instance != self:
|
||||
return real_instance.get_absolute_url()
|
||||
return real_instance.get_absolute_url(request=request)
|
||||
else:
|
||||
return ''
|
||||
|
||||
|
||||
@ -7,10 +7,10 @@
|
||||
# Django
|
||||
from django.db import models
|
||||
from django.conf import settings
|
||||
from django.core.urlresolvers import reverse
|
||||
#from django import settings as tower_settings
|
||||
|
||||
# AWX
|
||||
from awx.api.versioning import reverse
|
||||
from awx.main.models import prevent_search, UnifiedJobTemplate, UnifiedJob
|
||||
from awx.main.models.notifications import (
|
||||
NotificationTemplate,
|
||||
@ -177,8 +177,8 @@ class WorkflowJobTemplateNode(WorkflowNodeBase):
|
||||
on_delete=models.CASCADE,
|
||||
)
|
||||
|
||||
def get_absolute_url(self):
|
||||
return reverse('api:workflow_job_template_node_detail', args=(self.pk,))
|
||||
def get_absolute_url(self, request=None):
|
||||
return reverse('api:workflow_job_template_node_detail', kwargs={'pk': self.pk}, request=request)
|
||||
|
||||
def create_wfjt_node_copy(self, user, workflow_job_template=None):
|
||||
'''
|
||||
@ -223,8 +223,8 @@ class WorkflowJobNode(WorkflowNodeBase):
|
||||
editable=False,
|
||||
)
|
||||
|
||||
def get_absolute_url(self):
|
||||
return reverse('api:workflow_job_node_detail', args=(self.pk,))
|
||||
def get_absolute_url(self, request=None):
|
||||
return reverse('api:workflow_job_node_detail', kwargs={'pk': self.pk}, request=request)
|
||||
|
||||
def get_job_kwargs(self):
|
||||
'''
|
||||
@ -365,8 +365,8 @@ class WorkflowJobTemplate(UnifiedJobTemplate, WorkflowJobOptions, SurveyJobTempl
|
||||
return (base_list +
|
||||
['survey_spec', 'survey_enabled', 'organization'])
|
||||
|
||||
def get_absolute_url(self):
|
||||
return reverse('api:workflow_job_template_detail', args=(self.pk,))
|
||||
def get_absolute_url(self, request=None):
|
||||
return reverse('api:workflow_job_template_detail', kwargs={'pk': self.pk}, request=request)
|
||||
|
||||
@property
|
||||
def cache_timeout_blocked(self):
|
||||
@ -467,8 +467,8 @@ class WorkflowJob(UnifiedJob, WorkflowJobOptions, SurveyJobMixin, JobNotificatio
|
||||
def socketio_emit_data(self):
|
||||
return {}
|
||||
|
||||
def get_absolute_url(self):
|
||||
return reverse('api:workflow_job_detail', args=(self.pk,))
|
||||
def get_absolute_url(self, request=None):
|
||||
return reverse('api:workflow_job_detail', kwargs={'pk': self.pk}, request=request)
|
||||
|
||||
def get_ui_url(self):
|
||||
return urljoin(settings.TOWER_URL_BASE, '/#/workflows/{}'.format(self.pk))
|
||||
|
||||
@ -1,12 +1,11 @@
|
||||
import mock
|
||||
import pytest
|
||||
|
||||
from awx.api.versioning import reverse
|
||||
from awx.main.middleware import ActivityStreamMiddleware
|
||||
from awx.main.models.activity_stream import ActivityStream
|
||||
from awx.main.access import ActivityStreamAccess
|
||||
|
||||
from django.core.urlresolvers import reverse
|
||||
|
||||
|
||||
def mock_feature_enabled(feature):
|
||||
return True
|
||||
@ -37,7 +36,7 @@ def test_basic_fields(monkeypatch, organization, get, user, settings):
|
||||
activity_stream.save()
|
||||
|
||||
aspk = activity_stream.pk
|
||||
url = reverse('api:activity_stream_detail', args=(aspk,))
|
||||
url = reverse('api:activity_stream_detail', kwargs={'pk': aspk})
|
||||
response = get(url, user('admin', True))
|
||||
|
||||
assert response.status_code == 200
|
||||
@ -64,7 +63,7 @@ def test_middleware_actor_added(monkeypatch, post, get, user, settings):
|
||||
org_id = response.data['id']
|
||||
activity_stream = ActivityStream.objects.filter(organization__pk=org_id).first()
|
||||
|
||||
url = reverse('api:activity_stream_detail', args=(activity_stream.pk,))
|
||||
url = reverse('api:activity_stream_detail', kwargs={'pk': activity_stream.pk})
|
||||
response = get(url, u)
|
||||
|
||||
assert response.status_code == 200
|
||||
@ -147,14 +146,14 @@ def test_stream_user_direct_role_updates(get, post, organization_factory):
|
||||
users=['test'],
|
||||
inventories=['inv1'])
|
||||
|
||||
url = reverse('api:user_roles_list', args=(objects.users.test.pk,))
|
||||
url = reverse('api:user_roles_list', kwargs={'pk': objects.users.test.pk})
|
||||
post(url, dict(id=objects.inventories.inv1.read_role.pk), objects.superusers.admin)
|
||||
|
||||
activity_stream = ActivityStream.objects.filter(
|
||||
inventory__pk=objects.inventories.inv1.pk,
|
||||
user__pk=objects.users.test.pk,
|
||||
role__pk=objects.inventories.inv1.read_role.pk).first()
|
||||
url = reverse('api:activity_stream_detail', args=(activity_stream.pk,))
|
||||
url = reverse('api:activity_stream_detail', kwargs={'pk': activity_stream.pk})
|
||||
response = get(url, objects.users.test)
|
||||
|
||||
assert response.data['object1'] == 'user'
|
||||
|
||||
@ -1,7 +1,7 @@
|
||||
import mock # noqa
|
||||
import pytest
|
||||
|
||||
from django.core.urlresolvers import reverse
|
||||
from awx.api.versioning import reverse
|
||||
|
||||
|
||||
"""
|
||||
@ -108,8 +108,8 @@ def test_user_post_ad_hoc_command_list_without_inventory(alice, post_adhoc, inve
|
||||
|
||||
@pytest.mark.django_db
|
||||
def test_admin_post_inventory_ad_hoc_command_list(admin, post_adhoc, inventory):
|
||||
post_adhoc(reverse('api:inventory_ad_hoc_commands_list', args=(inventory.id,)), {'inventory': None}, admin, expect=201)
|
||||
post_adhoc(reverse('api:inventory_ad_hoc_commands_list', args=(inventory.id,)), {}, admin, expect=201)
|
||||
post_adhoc(reverse('api:inventory_ad_hoc_commands_list', kwargs={'pk': inventory.id}), {'inventory': None}, admin, expect=201)
|
||||
post_adhoc(reverse('api:inventory_ad_hoc_commands_list', kwargs={'pk': inventory.id}), {}, admin, expect=201)
|
||||
|
||||
|
||||
@pytest.mark.django_db
|
||||
@ -121,19 +121,19 @@ def test_get_inventory_ad_hoc_command_list(admin, alice, post_adhoc, get, invent
|
||||
post_adhoc(reverse('api:ad_hoc_command_list'), {'inventory': inv2.id}, admin, expect=201)
|
||||
res = get(reverse('api:ad_hoc_command_list'), admin, expect=200)
|
||||
assert res.data['count'] == 2
|
||||
res = get(reverse('api:inventory_ad_hoc_commands_list', args=(inv1.id,)), admin, expect=200)
|
||||
res = get(reverse('api:inventory_ad_hoc_commands_list', kwargs={'pk': inv1.id}), admin, expect=200)
|
||||
assert res.data['count'] == 1
|
||||
res = get(reverse('api:inventory_ad_hoc_commands_list', args=(inv2.id,)), admin, expect=200)
|
||||
res = get(reverse('api:inventory_ad_hoc_commands_list', kwargs={'pk': inv2.id}), admin, expect=200)
|
||||
assert res.data['count'] == 1
|
||||
|
||||
inv1.adhoc_role.members.add(alice)
|
||||
res = get(reverse('api:inventory_ad_hoc_commands_list', args=(inv1.id,)), alice, expect=200)
|
||||
res = get(reverse('api:inventory_ad_hoc_commands_list', kwargs={'pk': inv1.id}), alice, expect=200)
|
||||
assert res.data['count'] == 1
|
||||
|
||||
machine_credential.use_role.members.add(alice)
|
||||
res = get(reverse('api:inventory_ad_hoc_commands_list', args=(inv1.id,)), alice, expect=200)
|
||||
res = get(reverse('api:inventory_ad_hoc_commands_list', kwargs={'pk': inv1.id}), alice, expect=200)
|
||||
assert res.data['count'] == 1
|
||||
res = get(reverse('api:inventory_ad_hoc_commands_list', args=(inv2.id,)), alice, expect=403)
|
||||
res = get(reverse('api:inventory_ad_hoc_commands_list', kwargs={'pk': inv2.id}), alice, expect=403)
|
||||
|
||||
|
||||
@pytest.mark.django_db
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
import pytest
|
||||
|
||||
from django.core.urlresolvers import reverse
|
||||
from awx.api.versioning import reverse
|
||||
|
||||
|
||||
@pytest.mark.django_db
|
||||
@ -10,7 +10,7 @@ def test_user_role_view_access(rando, inventory, mocker, post):
|
||||
data = {"id": role_pk}
|
||||
mock_access = mocker.MagicMock(can_attach=mocker.MagicMock(return_value=False))
|
||||
with mocker.patch('awx.main.access.RoleAccess', return_value=mock_access):
|
||||
post(url=reverse('api:user_roles_list', args=(rando.pk,)),
|
||||
post(url=reverse('api:user_roles_list', kwargs={'pk': rando.pk}),
|
||||
data=data, user=rando, expect=403)
|
||||
mock_access.can_attach.assert_called_once_with(
|
||||
inventory.admin_role, rando, 'members', data,
|
||||
@ -25,7 +25,7 @@ def test_team_role_view_access(rando, team, inventory, mocker, post):
|
||||
data = {"id": role_pk}
|
||||
mock_access = mocker.MagicMock(can_attach=mocker.MagicMock(return_value=False))
|
||||
with mocker.patch('awx.main.access.RoleAccess', return_value=mock_access):
|
||||
post(url=reverse('api:team_roles_list', args=(team.pk,)),
|
||||
post(url=reverse('api:team_roles_list', kwargs={'pk': team.pk}),
|
||||
data=data, user=rando, expect=403)
|
||||
mock_access.can_attach.assert_called_once_with(
|
||||
inventory.admin_role, team, 'member_role.parents', data,
|
||||
@ -40,7 +40,7 @@ def test_role_team_view_access(rando, team, inventory, mocker, post):
|
||||
data = {"id": team.pk}
|
||||
mock_access = mocker.MagicMock(return_value=False, __name__='mocked')
|
||||
with mocker.patch('awx.main.access.RoleAccess.can_attach', mock_access):
|
||||
post(url=reverse('api:role_teams_list', args=(role_pk,)),
|
||||
post(url=reverse('api:role_teams_list', kwargs={'pk': role_pk}),
|
||||
data=data, user=rando, expect=403)
|
||||
mock_access.assert_called_once_with(
|
||||
inventory.admin_role, team, 'member_role.parents', data,
|
||||
@ -54,7 +54,7 @@ def test_org_associate_with_junk_data(rando, admin_user, organization, post):
|
||||
will turn off if the action is an association
|
||||
"""
|
||||
user_data = {'is_system_auditor': True, 'id': rando.pk}
|
||||
post(url=reverse('api:organization_users_list', args=(organization.pk,)),
|
||||
post(url=reverse('api:organization_users_list', kwargs={'pk': organization.pk}),
|
||||
data=user_data, expect=204, user=admin_user)
|
||||
# assure user is now an org member
|
||||
assert rando in organization.member_role
|
||||
|
||||
@ -1,7 +1,7 @@
|
||||
import mock # noqa
|
||||
import pytest
|
||||
|
||||
from django.core.urlresolvers import reverse
|
||||
from awx.api.versioning import reverse
|
||||
|
||||
|
||||
#
|
||||
@ -36,14 +36,14 @@ def test_credential_validation_error_with_bad_user(post, admin):
|
||||
|
||||
@pytest.mark.django_db
|
||||
def test_create_user_credential_via_user_credentials_list(post, get, alice):
|
||||
response = post(reverse('api:user_credentials_list', args=(alice.pk,)), {
|
||||
response = post(reverse('api:user_credentials_list', kwargs={'pk': alice.pk}), {
|
||||
'user': alice.pk,
|
||||
'name': 'Some name',
|
||||
'username': 'someusername',
|
||||
}, alice)
|
||||
assert response.status_code == 201
|
||||
|
||||
response = get(reverse('api:user_credentials_list', args=(alice.pk,)), alice)
|
||||
response = get(reverse('api:user_credentials_list', kwargs={'pk': alice.pk}), alice)
|
||||
assert response.status_code == 200
|
||||
assert response.data['count'] == 1
|
||||
|
||||
@ -60,7 +60,7 @@ def test_create_user_credential_via_credentials_list_xfail(post, alice, bob):
|
||||
|
||||
@pytest.mark.django_db
|
||||
def test_create_user_credential_via_user_credentials_list_xfail(post, alice, bob):
|
||||
response = post(reverse('api:user_credentials_list', args=(bob.pk,)), {
|
||||
response = post(reverse('api:user_credentials_list', kwargs={'pk': bob.pk}), {
|
||||
'user': bob.pk,
|
||||
'name': 'Some name',
|
||||
'username': 'someusername'
|
||||
@ -82,7 +82,7 @@ def test_create_team_credential(post, get, team, organization, org_admin, team_m
|
||||
}, org_admin)
|
||||
assert response.status_code == 201
|
||||
|
||||
response = get(reverse('api:team_credentials_list', args=(team.pk,)), team_member)
|
||||
response = get(reverse('api:team_credentials_list', kwargs={'pk': team.pk}), team_member)
|
||||
assert response.status_code == 200
|
||||
assert response.data['count'] == 1
|
||||
|
||||
@ -92,14 +92,14 @@ def test_create_team_credential(post, get, team, organization, org_admin, team_m
|
||||
|
||||
@pytest.mark.django_db
|
||||
def test_create_team_credential_via_team_credentials_list(post, get, team, org_admin, team_member):
|
||||
response = post(reverse('api:team_credentials_list', args=(team.pk,)), {
|
||||
response = post(reverse('api:team_credentials_list', kwargs={'pk': team.pk}), {
|
||||
'team': team.pk,
|
||||
'name': 'Some name',
|
||||
'username': 'someusername',
|
||||
}, org_admin)
|
||||
assert response.status_code == 201
|
||||
|
||||
response = get(reverse('api:team_credentials_list', args=(team.pk,)), team_member)
|
||||
response = get(reverse('api:team_credentials_list', kwargs={'pk': team.pk}), team_member)
|
||||
assert response.status_code == 200
|
||||
assert response.data['count'] == 1
|
||||
|
||||
@ -136,7 +136,7 @@ def test_create_team_credential_by_team_member_xfail(post, team, organization, a
|
||||
def test_grant_org_credential_to_org_user_through_role_users(post, credential, organization, org_admin, org_member):
|
||||
credential.organization = organization
|
||||
credential.save()
|
||||
response = post(reverse('api:role_users_list', args=(credential.use_role.id,)), {
|
||||
response = post(reverse('api:role_users_list', kwargs={'pk': credential.use_role.id}), {
|
||||
'id': org_member.id
|
||||
}, org_admin)
|
||||
assert response.status_code == 204
|
||||
@ -146,7 +146,7 @@ def test_grant_org_credential_to_org_user_through_role_users(post, credential, o
|
||||
def test_grant_org_credential_to_org_user_through_user_roles(post, credential, organization, org_admin, org_member):
|
||||
credential.organization = organization
|
||||
credential.save()
|
||||
response = post(reverse('api:user_roles_list', args=(org_member.id,)), {
|
||||
response = post(reverse('api:user_roles_list', kwargs={'pk': org_member.id}), {
|
||||
'id': credential.use_role.id
|
||||
}, org_admin)
|
||||
assert response.status_code == 204
|
||||
@ -156,7 +156,7 @@ def test_grant_org_credential_to_org_user_through_user_roles(post, credential, o
|
||||
def test_grant_org_credential_to_non_org_user_through_role_users(post, credential, organization, org_admin, alice):
|
||||
credential.organization = organization
|
||||
credential.save()
|
||||
response = post(reverse('api:role_users_list', args=(credential.use_role.id,)), {
|
||||
response = post(reverse('api:role_users_list', kwargs={'pk': credential.use_role.id}), {
|
||||
'id': alice.id
|
||||
}, org_admin)
|
||||
assert response.status_code == 400
|
||||
@ -166,7 +166,7 @@ def test_grant_org_credential_to_non_org_user_through_role_users(post, credentia
|
||||
def test_grant_org_credential_to_non_org_user_through_user_roles(post, credential, organization, org_admin, alice):
|
||||
credential.organization = organization
|
||||
credential.save()
|
||||
response = post(reverse('api:user_roles_list', args=(alice.id,)), {
|
||||
response = post(reverse('api:user_roles_list', kwargs={'pk': alice.id}), {
|
||||
'id': credential.use_role.id
|
||||
}, org_admin)
|
||||
assert response.status_code == 400
|
||||
@ -176,7 +176,7 @@ def test_grant_org_credential_to_non_org_user_through_user_roles(post, credentia
|
||||
def test_grant_private_credential_to_user_through_role_users(post, credential, alice, bob):
|
||||
# normal users can't do this
|
||||
credential.admin_role.members.add(alice)
|
||||
response = post(reverse('api:role_users_list', args=(credential.use_role.id,)), {
|
||||
response = post(reverse('api:role_users_list', kwargs={'pk': credential.use_role.id}), {
|
||||
'id': bob.id
|
||||
}, alice)
|
||||
assert response.status_code == 400
|
||||
@ -186,7 +186,7 @@ def test_grant_private_credential_to_user_through_role_users(post, credential, a
|
||||
def test_grant_private_credential_to_org_user_through_role_users(post, credential, org_admin, org_member):
|
||||
# org admins can't either
|
||||
credential.admin_role.members.add(org_admin)
|
||||
response = post(reverse('api:role_users_list', args=(credential.use_role.id,)), {
|
||||
response = post(reverse('api:role_users_list', kwargs={'pk': credential.use_role.id}), {
|
||||
'id': org_member.id
|
||||
}, org_admin)
|
||||
assert response.status_code == 400
|
||||
@ -195,7 +195,7 @@ def test_grant_private_credential_to_org_user_through_role_users(post, credentia
|
||||
@pytest.mark.django_db
|
||||
def test_sa_grant_private_credential_to_user_through_role_users(post, credential, admin, bob):
|
||||
# but system admins can
|
||||
response = post(reverse('api:role_users_list', args=(credential.use_role.id,)), {
|
||||
response = post(reverse('api:role_users_list', kwargs={'pk': credential.use_role.id}), {
|
||||
'id': bob.id
|
||||
}, admin)
|
||||
assert response.status_code == 204
|
||||
@ -205,7 +205,7 @@ def test_sa_grant_private_credential_to_user_through_role_users(post, credential
|
||||
def test_grant_private_credential_to_user_through_user_roles(post, credential, alice, bob):
|
||||
# normal users can't do this
|
||||
credential.admin_role.members.add(alice)
|
||||
response = post(reverse('api:user_roles_list', args=(bob.id,)), {
|
||||
response = post(reverse('api:user_roles_list', kwargs={'pk': bob.id}), {
|
||||
'id': credential.use_role.id
|
||||
}, alice)
|
||||
assert response.status_code == 400
|
||||
@ -215,7 +215,7 @@ def test_grant_private_credential_to_user_through_user_roles(post, credential, a
|
||||
def test_grant_private_credential_to_org_user_through_user_roles(post, credential, org_admin, org_member):
|
||||
# org admins can't either
|
||||
credential.admin_role.members.add(org_admin)
|
||||
response = post(reverse('api:user_roles_list', args=(org_member.id,)), {
|
||||
response = post(reverse('api:user_roles_list', kwargs={'pk': org_member.id}), {
|
||||
'id': credential.use_role.id
|
||||
}, org_admin)
|
||||
assert response.status_code == 400
|
||||
@ -224,7 +224,7 @@ def test_grant_private_credential_to_org_user_through_user_roles(post, credentia
|
||||
@pytest.mark.django_db
|
||||
def test_sa_grant_private_credential_to_user_through_user_roles(post, credential, admin, bob):
|
||||
# but system admins can
|
||||
response = post(reverse('api:user_roles_list', args=(bob.id,)), {
|
||||
response = post(reverse('api:user_roles_list', kwargs={'pk': bob.id}), {
|
||||
'id': credential.use_role.id
|
||||
}, admin)
|
||||
assert response.status_code == 204
|
||||
@ -235,7 +235,7 @@ def test_grant_org_credential_to_team_through_role_teams(post, credential, organ
|
||||
assert org_auditor not in credential.read_role
|
||||
credential.organization = organization
|
||||
credential.save()
|
||||
response = post(reverse('api:role_teams_list', args=(credential.use_role.id,)), {
|
||||
response = post(reverse('api:role_teams_list', kwargs={'pk': credential.use_role.id}), {
|
||||
'id': team.id
|
||||
}, org_admin)
|
||||
assert response.status_code == 204
|
||||
@ -247,7 +247,7 @@ def test_grant_org_credential_to_team_through_team_roles(post, credential, organ
|
||||
assert org_auditor not in credential.read_role
|
||||
credential.organization = organization
|
||||
credential.save()
|
||||
response = post(reverse('api:team_roles_list', args=(team.id,)), {
|
||||
response = post(reverse('api:team_roles_list', kwargs={'pk': team.id}), {
|
||||
'id': credential.use_role.id
|
||||
}, org_admin)
|
||||
assert response.status_code == 204
|
||||
@ -257,7 +257,7 @@ def test_grant_org_credential_to_team_through_team_roles(post, credential, organ
|
||||
@pytest.mark.django_db
|
||||
def test_sa_grant_private_credential_to_team_through_role_teams(post, credential, admin, team):
|
||||
# not even a system admin can grant a private cred to a team though
|
||||
response = post(reverse('api:role_teams_list', args=(credential.use_role.id,)), {
|
||||
response = post(reverse('api:role_teams_list', kwargs={'pk': credential.use_role.id}), {
|
||||
'id': team.id
|
||||
}, admin)
|
||||
assert response.status_code == 400
|
||||
@ -266,7 +266,7 @@ def test_sa_grant_private_credential_to_team_through_role_teams(post, credential
|
||||
@pytest.mark.django_db
|
||||
def test_sa_grant_private_credential_to_team_through_team_roles(post, credential, admin, team):
|
||||
# not even a system admin can grant a private cred to a team though
|
||||
response = post(reverse('api:role_teams_list', args=(team.id,)), {
|
||||
response = post(reverse('api:role_teams_list', kwargs={'pk': team.id}), {
|
||||
'id': credential.use_role.id
|
||||
}, admin)
|
||||
assert response.status_code == 400
|
||||
@ -305,7 +305,7 @@ def test_credential_detail(post, get, organization, org_admin):
|
||||
'organization': organization.id,
|
||||
}, org_admin)
|
||||
assert response.status_code == 201
|
||||
response = get(reverse('api:credential_detail', args=(response.data['id'],)), org_admin)
|
||||
response = get(reverse('api:credential_detail', kwargs={'pk': response.data['id']}), org_admin)
|
||||
assert response.status_code == 200
|
||||
summary_fields = response.data['summary_fields']
|
||||
assert 'organization' in summary_fields
|
||||
@ -330,11 +330,11 @@ def test_list_created_org_credentials(post, get, organization, org_admin, org_me
|
||||
assert response.status_code == 200
|
||||
assert response.data['count'] == 0
|
||||
|
||||
response = get(reverse('api:organization_credential_list', args=(organization.pk,)), org_admin)
|
||||
response = get(reverse('api:organization_credential_list', kwargs={'pk': organization.pk}), org_admin)
|
||||
assert response.status_code == 200
|
||||
assert response.data['count'] == 1
|
||||
|
||||
response = get(reverse('api:organization_credential_list', args=(organization.pk,)), org_member)
|
||||
response = get(reverse('api:organization_credential_list', kwargs={'pk': organization.pk}), org_member)
|
||||
assert response.status_code == 200
|
||||
assert response.data['count'] == 0
|
||||
|
||||
|
||||
@ -6,11 +6,11 @@ import urlparse
|
||||
import urllib
|
||||
|
||||
# AWX
|
||||
from awx.api.versioning import reverse
|
||||
from awx.main.models.fact import Fact
|
||||
from awx.main.utils import timestamp_apiformat
|
||||
|
||||
# Django
|
||||
from django.core.urlresolvers import reverse
|
||||
from django.utils import timezone
|
||||
|
||||
|
||||
@ -26,7 +26,7 @@ def setup_common(hosts, fact_scans, get, user, epoch=timezone.now(), get_params=
|
||||
hosts = hosts(host_count=host_count)
|
||||
fact_scans(fact_scans=3, timestamp_epoch=epoch)
|
||||
|
||||
url = reverse('api:host_fact_versions_list', args=(hosts[0].pk,))
|
||||
url = reverse('api:host_fact_versions_list', kwargs={'pk': hosts[0].pk})
|
||||
response = get(url, user('admin', True), data=get_params)
|
||||
|
||||
return (hosts[0], response)
|
||||
@ -37,7 +37,7 @@ def check_url(url1_full, fact_known, module):
|
||||
url1 = url1_split.path
|
||||
url1_params = urlparse.parse_qsl(url1_split.query)
|
||||
|
||||
url2 = reverse('api:host_fact_compare_view', args=(fact_known.host.pk,))
|
||||
url2 = reverse('api:host_fact_compare_view', kwargs={'pk': fact_known.host.pk})
|
||||
url2_params = [('module', module), ('datetime', timestamp_apiformat(fact_known.timestamp))]
|
||||
|
||||
assert url1 == url2
|
||||
@ -64,7 +64,7 @@ def check_system_tracking_feature_forbidden(response):
|
||||
@pytest.mark.license_feature
|
||||
def test_system_tracking_license_get(hosts, get, user):
|
||||
hosts = hosts(host_count=1)
|
||||
url = reverse('api:host_fact_versions_list', args=(hosts[0].pk,))
|
||||
url = reverse('api:host_fact_versions_list', kwargs={'pk': hosts[0].pk})
|
||||
response = get(url, user('admin', True))
|
||||
|
||||
check_system_tracking_feature_forbidden(response)
|
||||
@ -75,7 +75,7 @@ def test_system_tracking_license_get(hosts, get, user):
|
||||
@pytest.mark.license_feature
|
||||
def test_system_tracking_license_options(hosts, options, user):
|
||||
hosts = hosts(host_count=1)
|
||||
url = reverse('api:host_fact_versions_list', args=(hosts[0].pk,))
|
||||
url = reverse('api:host_fact_versions_list', kwargs={'pk': hosts[0].pk})
|
||||
response = options(url, None, user('admin', True))
|
||||
|
||||
check_system_tracking_feature_forbidden(response)
|
||||
@ -86,7 +86,7 @@ def test_system_tracking_license_options(hosts, options, user):
|
||||
@pytest.mark.license_feature
|
||||
def test_no_facts_db(hosts, get, user):
|
||||
hosts = hosts(host_count=1)
|
||||
url = reverse('api:host_fact_versions_list', args=(hosts[0].pk,))
|
||||
url = reverse('api:host_fact_versions_list', kwargs={'pk': hosts[0].pk})
|
||||
response = get(url, user('admin', True))
|
||||
|
||||
response_expected = {
|
||||
@ -119,7 +119,7 @@ def test_basic_options_fields(hosts, fact_scans, options, user, monkeypatch_json
|
||||
hosts = hosts(host_count=1)
|
||||
fact_scans(fact_scans=1)
|
||||
|
||||
url = reverse('api:host_fact_versions_list', args=(hosts[0].pk,))
|
||||
url = reverse('api:host_fact_versions_list', kwargs={'pk': hosts[0].pk})
|
||||
response = options(url, None, user('admin', True), pk=hosts[0].id)
|
||||
|
||||
assert 'related' in response.data['actions']['GET']
|
||||
@ -228,7 +228,7 @@ def _test_user_access_control(hosts, fact_scans, get, user_obj, team_obj):
|
||||
|
||||
team_obj.member_role.members.add(user_obj)
|
||||
|
||||
url = reverse('api:host_fact_versions_list', args=(hosts[0].pk,))
|
||||
url = reverse('api:host_fact_versions_list', kwargs={'pk': hosts[0].pk})
|
||||
response = get(url, user_obj)
|
||||
return response
|
||||
|
||||
|
||||
@ -2,8 +2,8 @@ import mock
|
||||
import pytest
|
||||
import json
|
||||
|
||||
from awx.api.versioning import reverse
|
||||
from awx.main.utils import timestamp_apiformat
|
||||
from django.core.urlresolvers import reverse
|
||||
from django.utils import timezone
|
||||
|
||||
|
||||
@ -27,7 +27,7 @@ def setup_common(hosts, fact_scans, get, user, epoch=timezone.now(), module_name
|
||||
hosts = hosts(host_count=1)
|
||||
facts = fact_scans(fact_scans=1, timestamp_epoch=epoch)
|
||||
|
||||
url = reverse('api:host_fact_compare_view', args=(hosts[0].pk,))
|
||||
url = reverse('api:host_fact_compare_view', kwargs={'pk': hosts[0].pk})
|
||||
response = get(url, user('admin', True), data=get_params)
|
||||
|
||||
fact_known = find_fact(facts, hosts[0].id, module_name, epoch)
|
||||
@ -44,7 +44,7 @@ def check_system_tracking_feature_forbidden(response):
|
||||
@pytest.mark.license_feature
|
||||
def test_system_tracking_license_get(hosts, get, user):
|
||||
hosts = hosts(host_count=1)
|
||||
url = reverse('api:host_fact_compare_view', args=(hosts[0].pk,))
|
||||
url = reverse('api:host_fact_compare_view', kwargs={'pk': hosts[0].pk})
|
||||
response = get(url, user('admin', True))
|
||||
|
||||
check_system_tracking_feature_forbidden(response)
|
||||
@ -55,7 +55,7 @@ def test_system_tracking_license_get(hosts, get, user):
|
||||
@pytest.mark.license_feature
|
||||
def test_system_tracking_license_options(hosts, options, user):
|
||||
hosts = hosts(host_count=1)
|
||||
url = reverse('api:host_fact_compare_view', args=(hosts[0].pk,))
|
||||
url = reverse('api:host_fact_compare_view', kwargs={'pk': hosts[0].pk})
|
||||
response = options(url, None, user('admin', True))
|
||||
|
||||
check_system_tracking_feature_forbidden(response)
|
||||
@ -65,7 +65,7 @@ def test_system_tracking_license_options(hosts, options, user):
|
||||
@pytest.mark.django_db
|
||||
def test_no_fact_found(hosts, get, user):
|
||||
hosts = hosts(host_count=1)
|
||||
url = reverse('api:host_fact_compare_view', args=(hosts[0].pk,))
|
||||
url = reverse('api:host_fact_compare_view', kwargs={'pk': hosts[0].pk})
|
||||
response = get(url, user('admin', True))
|
||||
|
||||
expected_response = {
|
||||
@ -81,7 +81,7 @@ def test_basic_fields(hosts, fact_scans, get, user, monkeypatch_jsonbfield_get_d
|
||||
hosts = hosts(host_count=1)
|
||||
fact_scans(fact_scans=1)
|
||||
|
||||
url = reverse('api:host_fact_compare_view', args=(hosts[0].pk,))
|
||||
url = reverse('api:host_fact_compare_view', kwargs={'pk': hosts[0].pk})
|
||||
response = get(url, user('admin', True))
|
||||
|
||||
assert 'related' in response.data
|
||||
@ -95,7 +95,7 @@ def test_basic_fields(hosts, fact_scans, get, user, monkeypatch_jsonbfield_get_d
|
||||
assert 'name' in response.data['summary_fields']['host']
|
||||
assert 'description' in response.data['summary_fields']['host']
|
||||
assert 'host' in response.data['related']
|
||||
assert reverse('api:host_detail', args=(hosts[0].pk,)) == response.data['related']['host']
|
||||
assert reverse('api:host_detail', kwargs={'pk': hosts[0].pk}) == response.data['related']['host']
|
||||
|
||||
|
||||
@mock.patch('awx.api.views.feature_enabled', new=mock_feature_enabled)
|
||||
@ -149,7 +149,7 @@ def _test_user_access_control(hosts, fact_scans, get, user_obj, team_obj):
|
||||
|
||||
team_obj.member_role.members.add(user_obj)
|
||||
|
||||
url = reverse('api:host_fact_compare_view', args=(hosts[0].pk,))
|
||||
url = reverse('api:host_fact_compare_view', kwargs={'pk': hosts[0].pk})
|
||||
response = get(url, user_obj)
|
||||
return response
|
||||
|
||||
|
||||
@ -2,17 +2,17 @@
|
||||
# Other host tests should live here to make this test suite more complete.
|
||||
import pytest
|
||||
|
||||
from django.core.urlresolvers import reverse
|
||||
from awx.api.versioning import reverse
|
||||
|
||||
|
||||
@pytest.mark.django_db
|
||||
def test_basic_fields(hosts, fact_scans, get, user):
|
||||
hosts = hosts(host_count=1)
|
||||
|
||||
url = reverse('api:host_detail', args=(hosts[0].pk,))
|
||||
url = reverse('api:host_detail', kwargs={'pk': hosts[0].pk})
|
||||
response = get(url, user('admin', True))
|
||||
|
||||
assert 'related' in response.data
|
||||
assert 'fact_versions' in response.data['related']
|
||||
assert reverse('api:host_fact_versions_list', args=(hosts[0].pk,)) == response.data['related']['fact_versions']
|
||||
assert reverse('api:host_fact_versions_list', kwargs={'pk': hosts[0].pk}) == response.data['related']['fact_versions']
|
||||
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
import pytest
|
||||
|
||||
from django.core.urlresolvers import reverse
|
||||
from awx.api.versioning import reverse
|
||||
|
||||
|
||||
@pytest.mark.django_db
|
||||
@ -12,10 +12,10 @@ def test_inventory_source_notification_on_cloud_only(get, post, group_factory, u
|
||||
not_is = g_not.inventory_source
|
||||
cloud_is.source = 'ec2'
|
||||
cloud_is.save()
|
||||
url = reverse('api:inventory_source_notification_templates_any_list', args=(cloud_is.id,))
|
||||
url = reverse('api:inventory_source_notification_templates_any_list', kwargs={'pk': cloud_is.id})
|
||||
response = post(url, dict(id=notification_template.id), u)
|
||||
assert response.status_code == 204
|
||||
url = reverse('api:inventory_source_notification_templates_success_list', args=(not_is.id,))
|
||||
url = reverse('api:inventory_source_notification_templates_success_list', kwargs={'pk': not_is.id})
|
||||
response = post(url, dict(id=notification_template.id), u)
|
||||
assert response.status_code == 400
|
||||
|
||||
@ -32,7 +32,7 @@ def test_edit_inventory(put, inventory, alice, role_field, expected_status_code)
|
||||
data = { 'organization': inventory.organization.id, 'name': 'New name', 'description': 'Hello world', }
|
||||
if role_field:
|
||||
getattr(inventory, role_field).members.add(alice)
|
||||
put(reverse('api:inventory_detail', args=(inventory.id,)), data, alice, expect=expected_status_code)
|
||||
put(reverse('api:inventory_detail', kwargs={'pk': inventory.id}), data, alice, expect=expected_status_code)
|
||||
|
||||
|
||||
@pytest.mark.parametrize('order_by', ('script', '-script', 'script,pk', '-script,pk'))
|
||||
@ -62,7 +62,7 @@ def test_create_inventory_group(post, inventory, alice, role_field, expected_sta
|
||||
data = { 'name': 'New name', 'description': 'Hello world', }
|
||||
if role_field:
|
||||
getattr(inventory, role_field).members.add(alice)
|
||||
post(reverse('api:inventory_groups_list', args=(inventory.id,)), data, alice, expect=expected_status_code)
|
||||
post(reverse('api:inventory_groups_list', kwargs={'pk': inventory.id}), data, alice, expect=expected_status_code)
|
||||
|
||||
|
||||
@pytest.mark.parametrize("role_field,expected_status_code", [
|
||||
@ -77,7 +77,7 @@ def test_create_inventory_group_child(post, group, alice, role_field, expected_s
|
||||
data = { 'name': 'New name', 'description': 'Hello world', }
|
||||
if role_field:
|
||||
getattr(group.inventory, role_field).members.add(alice)
|
||||
post(reverse('api:group_children_list', args=(group.id,)), data, alice, expect=expected_status_code)
|
||||
post(reverse('api:group_children_list', kwargs={'pk': group.id}), data, alice, expect=expected_status_code)
|
||||
|
||||
|
||||
@pytest.mark.parametrize("role_field,expected_status_code", [
|
||||
@ -92,7 +92,7 @@ def test_edit_inventory_group(put, group, alice, role_field, expected_status_cod
|
||||
data = { 'name': 'New name', 'description': 'Hello world', }
|
||||
if role_field:
|
||||
getattr(group.inventory, role_field).members.add(alice)
|
||||
put(reverse('api:group_detail', args=(group.id,)), data, alice, expect=expected_status_code)
|
||||
put(reverse('api:group_detail', kwargs={'pk': group.id}), data, alice, expect=expected_status_code)
|
||||
|
||||
|
||||
@pytest.mark.parametrize("role_field,expected_status_code", [
|
||||
@ -106,7 +106,7 @@ def test_edit_inventory_group(put, group, alice, role_field, expected_status_cod
|
||||
def test_delete_inventory_group(delete, group, alice, role_field, expected_status_code):
|
||||
if role_field:
|
||||
getattr(group.inventory, role_field).members.add(alice)
|
||||
delete(reverse('api:group_detail', args=(group.id,)), alice, expect=expected_status_code)
|
||||
delete(reverse('api:group_detail', kwargs={'pk': group.id}), alice, expect=expected_status_code)
|
||||
|
||||
|
||||
@pytest.mark.parametrize("role_field,expected_status_code", [
|
||||
@ -121,7 +121,7 @@ def test_create_inventory_host(post, inventory, alice, role_field, expected_stat
|
||||
data = { 'name': 'New name', 'description': 'Hello world', }
|
||||
if role_field:
|
||||
getattr(inventory, role_field).members.add(alice)
|
||||
post(reverse('api:inventory_hosts_list', args=(inventory.id,)), data, alice, expect=expected_status_code)
|
||||
post(reverse('api:inventory_hosts_list', kwargs={'pk': inventory.id}), data, alice, expect=expected_status_code)
|
||||
|
||||
|
||||
@pytest.mark.parametrize("role_field,expected_status_code", [
|
||||
@ -136,7 +136,7 @@ def test_create_inventory_group_host(post, group, alice, role_field, expected_st
|
||||
data = { 'name': 'New name', 'description': 'Hello world', }
|
||||
if role_field:
|
||||
getattr(group.inventory, role_field).members.add(alice)
|
||||
post(reverse('api:group_hosts_list', args=(group.id,)), data, alice, expect=expected_status_code)
|
||||
post(reverse('api:group_hosts_list', kwargs={'pk': group.id}), data, alice, expect=expected_status_code)
|
||||
|
||||
|
||||
@pytest.mark.parametrize("role_field,expected_status_code", [
|
||||
@ -151,7 +151,7 @@ def test_edit_inventory_host(put, host, alice, role_field, expected_status_code)
|
||||
data = { 'name': 'New name', 'description': 'Hello world', }
|
||||
if role_field:
|
||||
getattr(host.inventory, role_field).members.add(alice)
|
||||
put(reverse('api:host_detail', args=(host.id,)), data, alice, expect=expected_status_code)
|
||||
put(reverse('api:host_detail', kwargs={'pk': host.id}), data, alice, expect=expected_status_code)
|
||||
|
||||
|
||||
@pytest.mark.parametrize("role_field,expected_status_code", [
|
||||
@ -165,7 +165,7 @@ def test_edit_inventory_host(put, host, alice, role_field, expected_status_code)
|
||||
def test_delete_inventory_host(delete, host, alice, role_field, expected_status_code):
|
||||
if role_field:
|
||||
getattr(host.inventory, role_field).members.add(alice)
|
||||
delete(reverse('api:host_detail', args=(host.id,)), alice, expect=expected_status_code)
|
||||
delete(reverse('api:host_detail', kwargs={'pk': host.id}), alice, expect=expected_status_code)
|
||||
|
||||
|
||||
@pytest.mark.parametrize("role_field,expected_status_code", [
|
||||
@ -179,4 +179,4 @@ def test_delete_inventory_host(delete, host, alice, role_field, expected_status_
|
||||
def test_inventory_source_update(post, inventory_source, alice, role_field, expected_status_code):
|
||||
if role_field:
|
||||
getattr(inventory_source.group.inventory, role_field).members.add(alice)
|
||||
post(reverse('api:inventory_source_update_view', args=(inventory_source.id,)), {}, alice, expect=expected_status_code)
|
||||
post(reverse('api:inventory_source_update_view', kwargs={'pk': inventory_source.id}), {}, alice, expect=expected_status_code)
|
||||
|
||||
@ -6,7 +6,7 @@ from awx.main.models.credential import Credential
|
||||
from awx.main.models.inventory import Inventory
|
||||
from awx.main.models.jobs import Job, JobTemplate
|
||||
|
||||
from django.core.urlresolvers import reverse
|
||||
from awx.api.versioning import reverse
|
||||
|
||||
|
||||
@pytest.fixture
|
||||
@ -85,7 +85,7 @@ def test_job_ignore_unprompted_vars(runtime_data, job_template_prompts, post, ad
|
||||
|
||||
with mocker.patch.object(JobTemplate, 'create_unified_job', return_value=mock_job):
|
||||
with mocker.patch('awx.api.serializers.JobSerializer.to_representation'):
|
||||
response = post(reverse('api:job_template_launch', args=[job_template.pk]),
|
||||
response = post(reverse('api:job_template_launch', kwargs={'pk':job_template.pk}),
|
||||
runtime_data, admin_user, expect=201)
|
||||
assert JobTemplate.create_unified_job.called
|
||||
assert JobTemplate.create_unified_job.call_args == ({'extra_vars':{}},)
|
||||
@ -116,7 +116,7 @@ def test_job_accept_prompted_vars(runtime_data, job_template_prompts, post, admi
|
||||
|
||||
with mocker.patch.object(JobTemplate, 'create_unified_job', return_value=mock_job):
|
||||
with mocker.patch('awx.api.serializers.JobSerializer.to_representation'):
|
||||
response = post(reverse('api:job_template_launch', args=[job_template.pk]),
|
||||
response = post(reverse('api:job_template_launch', kwargs={'pk':job_template.pk}),
|
||||
runtime_data, admin_user, expect=201)
|
||||
assert JobTemplate.create_unified_job.called
|
||||
assert JobTemplate.create_unified_job.call_args == (runtime_data,)
|
||||
@ -136,7 +136,7 @@ def test_job_accept_null_tags(job_template_prompts, post, admin_user, mocker):
|
||||
|
||||
with mocker.patch.object(JobTemplate, 'create_unified_job', return_value=mock_job):
|
||||
with mocker.patch('awx.api.serializers.JobSerializer.to_representation'):
|
||||
post(reverse('api:job_template_launch', args=[job_template.pk]),
|
||||
post(reverse('api:job_template_launch', kwargs={'pk': job_template.pk}),
|
||||
{'job_tags': '', 'skip_tags': ''}, admin_user, expect=201)
|
||||
assert JobTemplate.create_unified_job.called
|
||||
assert JobTemplate.create_unified_job.call_args == ({'job_tags':'', 'skip_tags':''},)
|
||||
@ -162,7 +162,7 @@ def test_job_accept_prompted_vars_null(runtime_data, job_template_prompts_null,
|
||||
|
||||
with mocker.patch.object(JobTemplate, 'create_unified_job', return_value=mock_job):
|
||||
with mocker.patch('awx.api.serializers.JobSerializer.to_representation'):
|
||||
response = post(reverse('api:job_template_launch', args=[job_template.pk]),
|
||||
response = post(reverse('api:job_template_launch', kwargs={'pk': job_template.pk}),
|
||||
runtime_data, rando, expect=201)
|
||||
assert JobTemplate.create_unified_job.called
|
||||
assert JobTemplate.create_unified_job.call_args == (runtime_data,)
|
||||
@ -178,7 +178,7 @@ def test_job_reject_invalid_prompted_vars(runtime_data, job_template_prompts, po
|
||||
job_template = job_template_prompts(True)
|
||||
|
||||
response = post(
|
||||
reverse('api:job_template_launch', args=[job_template.pk]),
|
||||
reverse('api:job_template_launch', kwargs={'pk':job_template.pk}),
|
||||
dict(job_type='foobicate', # foobicate is not a valid job type
|
||||
inventory=87865, credential=48474), admin_user, expect=400)
|
||||
|
||||
@ -193,7 +193,7 @@ def test_job_reject_invalid_prompted_extra_vars(runtime_data, job_template_promp
|
||||
job_template = job_template_prompts(True)
|
||||
|
||||
response = post(
|
||||
reverse('api:job_template_launch', args=[job_template.pk]),
|
||||
reverse('api:job_template_launch', kwargs={'pk':job_template.pk}),
|
||||
dict(extra_vars='{"unbalanced brackets":'), admin_user, expect=400)
|
||||
|
||||
assert 'extra_vars' in response.data
|
||||
@ -207,7 +207,7 @@ def test_job_launch_fails_without_inventory(deploy_jobtemplate, post, admin_user
|
||||
deploy_jobtemplate.save()
|
||||
|
||||
response = post(reverse('api:job_template_launch',
|
||||
args=[deploy_jobtemplate.pk]), {}, admin_user, expect=400)
|
||||
kwargs={'pk': deploy_jobtemplate.pk}), {}, admin_user, expect=400)
|
||||
|
||||
assert response.data['inventory'] == ["Job Template 'inventory' is missing or undefined."]
|
||||
|
||||
@ -219,7 +219,7 @@ def test_job_launch_fails_without_inventory_access(job_template_prompts, runtime
|
||||
job_template.execute_role.members.add(rando)
|
||||
|
||||
# Assure that giving an inventory without access to the inventory blocks the launch
|
||||
response = post(reverse('api:job_template_launch', args=[job_template.pk]),
|
||||
response = post(reverse('api:job_template_launch', kwargs={'pk':job_template.pk}),
|
||||
dict(inventory=runtime_data['inventory']), rando, expect=403)
|
||||
|
||||
assert response.data['detail'] == u'You do not have permission to perform this action.'
|
||||
@ -232,7 +232,7 @@ def test_job_launch_fails_without_credential_access(job_template_prompts, runtim
|
||||
job_template.execute_role.members.add(rando)
|
||||
|
||||
# Assure that giving a credential without access blocks the launch
|
||||
response = post(reverse('api:job_template_launch', args=[job_template.pk]),
|
||||
response = post(reverse('api:job_template_launch', kwargs={'pk':job_template.pk}),
|
||||
dict(credential=runtime_data['credential']), rando, expect=403)
|
||||
|
||||
assert response.data['detail'] == u'You do not have permission to perform this action.'
|
||||
@ -244,7 +244,7 @@ def test_job_block_scan_job_type_change(job_template_prompts, post, admin_user):
|
||||
job_template = job_template_prompts(True)
|
||||
|
||||
# Assure that changing the type of a scan job blocks the launch
|
||||
response = post(reverse('api:job_template_launch', args=[job_template.pk]),
|
||||
response = post(reverse('api:job_template_launch', kwargs={'pk':job_template.pk}),
|
||||
dict(job_type='scan'), admin_user, expect=400)
|
||||
|
||||
assert 'job_type' in response.data
|
||||
@ -255,7 +255,7 @@ def test_job_block_scan_job_type_change(job_template_prompts, post, admin_user):
|
||||
def test_job_block_scan_job_inv_change(mocker, bad_scan_JT, runtime_data, post, admin_user):
|
||||
# Assure that giving a new inventory for a scan job blocks the launch
|
||||
with mocker.patch('awx.main.access.BaseAccess.check_license'):
|
||||
response = post(reverse('api:job_template_launch', args=[bad_scan_JT.pk]),
|
||||
response = post(reverse('api:job_template_launch', kwargs={'pk': bad_scan_JT.pk}),
|
||||
dict(inventory=runtime_data['inventory']), admin_user,
|
||||
expect=400)
|
||||
|
||||
@ -333,7 +333,7 @@ def test_job_launch_unprompted_vars_with_survey(mocker, survey_spec_factory, job
|
||||
with mocker.patch.object(JobTemplate, 'create_unified_job', return_value=mock_job):
|
||||
with mocker.patch('awx.api.serializers.JobSerializer.to_representation', return_value={}):
|
||||
response = post(
|
||||
reverse('api:job_template_launch', args=[job_template.pk]),
|
||||
reverse('api:job_template_launch', kwargs={'pk':job_template.pk}),
|
||||
dict(extra_vars={"job_launch_var": 3, "survey_var": 4}),
|
||||
admin_user, expect=201)
|
||||
assert JobTemplate.create_unified_job.called
|
||||
@ -362,7 +362,7 @@ def test_callback_accept_prompted_extra_var(mocker, survey_spec_factory, job_tem
|
||||
with mocker.patch('awx.api.serializers.JobSerializer.to_representation', return_value={}):
|
||||
with mocker.patch('awx.api.views.JobTemplateCallback.find_matching_hosts', return_value=[host]):
|
||||
post(
|
||||
reverse('api:job_template_callback', args=[job_template.pk]),
|
||||
reverse('api:job_template_callback', kwargs={'pk': job_template.pk}),
|
||||
dict(extra_vars={"job_launch_var": 3, "survey_var": 4}, host_config_key="foo"),
|
||||
admin_user, expect=201, format='json')
|
||||
assert JobTemplate.create_unified_job.called
|
||||
@ -387,7 +387,7 @@ def test_callback_ignore_unprompted_extra_var(mocker, survey_spec_factory, job_t
|
||||
with mocker.patch('awx.api.serializers.JobSerializer.to_representation', return_value={}):
|
||||
with mocker.patch('awx.api.views.JobTemplateCallback.find_matching_hosts', return_value=[host]):
|
||||
post(
|
||||
reverse('api:job_template_callback', args=[job_template.pk]),
|
||||
reverse('api:job_template_callback', kwargs={'pk':job_template.pk}),
|
||||
dict(extra_vars={"job_launch_var": 3, "survey_var": 4}, host_config_key="foo"),
|
||||
admin_user, expect=201, format='json')
|
||||
assert JobTemplate.create_unified_job.called
|
||||
|
||||
@ -2,11 +2,11 @@ import pytest
|
||||
|
||||
# AWX
|
||||
from awx.api.serializers import JobTemplateSerializer, JobLaunchSerializer
|
||||
from awx.api.versioning import reverse
|
||||
from awx.main.models.jobs import Job
|
||||
from awx.main.migrations import _save_password_keys as save_password_keys
|
||||
|
||||
# Django
|
||||
from django.core.urlresolvers import reverse
|
||||
from django.apps import apps
|
||||
|
||||
|
||||
@ -56,7 +56,7 @@ def test_edit_sensitive_fields(patch, job_template_factory, alice, grant_project
|
||||
if grant_inventory:
|
||||
objs.inventory.use_role.members.add(alice)
|
||||
|
||||
patch(reverse('api:job_template_detail', args=(objs.job_template.id,)), {
|
||||
patch(reverse('api:job_template_detail', kwargs={'pk': objs.job_template.id}), {
|
||||
'name': 'Some name',
|
||||
'project': objs.project.id,
|
||||
'credential': objs.credential.id,
|
||||
@ -72,7 +72,7 @@ def test_reject_dict_extra_vars_patch(patch, job_template_factory, admin_user):
|
||||
jt = job_template_factory(
|
||||
'jt', organization='org1', project='prj', inventory='inv', credential='cred'
|
||||
).job_template
|
||||
patch(reverse('api:job_template_detail', args=(jt.id,)),
|
||||
patch(reverse('api:job_template_detail', kwargs={'pk': jt.id}),
|
||||
{'extra_vars': {'foo': 5}}, admin_user, expect=400)
|
||||
|
||||
|
||||
@ -84,12 +84,12 @@ def test_edit_playbook(patch, job_template_factory, alice):
|
||||
objs.credential.use_role.members.add(alice)
|
||||
objs.inventory.use_role.members.add(alice)
|
||||
|
||||
patch(reverse('api:job_template_detail', args=(objs.job_template.id,)), {
|
||||
patch(reverse('api:job_template_detail', kwargs={'pk': objs.job_template.id}), {
|
||||
'playbook': 'alt-helloworld.yml',
|
||||
}, alice, expect=200)
|
||||
|
||||
objs.inventory.use_role.members.remove(alice)
|
||||
patch(reverse('api:job_template_detail', args=(objs.job_template.id,)), {
|
||||
patch(reverse('api:job_template_detail', kwargs={'pk': objs.job_template.id}), {
|
||||
'playbook': 'helloworld.yml',
|
||||
}, alice, expect=403)
|
||||
|
||||
@ -101,7 +101,7 @@ def test_invalid_json_body(patch, job_template_factory, alice, json_body):
|
||||
objs = job_template_factory('jt', organization='org1')
|
||||
objs.job_template.admin_role.members.add(alice)
|
||||
resp = patch(
|
||||
reverse('api:job_template_detail', args=(objs.job_template.id,)),
|
||||
reverse('api:job_template_detail', kwargs={'pk': objs.job_template.id}),
|
||||
json_body,
|
||||
alice,
|
||||
expect=400
|
||||
@ -117,7 +117,7 @@ def test_edit_nonsenstive(patch, job_template_factory, alice):
|
||||
jt = objs.job_template
|
||||
jt.admin_role.members.add(alice)
|
||||
|
||||
res = patch(reverse('api:job_template_detail', args=(jt.id,)), {
|
||||
res = patch(reverse('api:job_template_detail', kwargs={'pk': jt.id}), {
|
||||
'name': 'updated',
|
||||
'description': 'bar',
|
||||
'forks': 14,
|
||||
@ -157,7 +157,7 @@ def test_job_template_role_user(post, organization_factory, job_template_factory
|
||||
inventory='test_inv',
|
||||
project='test_proj')
|
||||
|
||||
url = reverse('api:user_roles_list', args=(objects.users.test.pk,))
|
||||
url = reverse('api:user_roles_list', kwargs={'pk': objects.users.test.pk})
|
||||
response = post(url, dict(id=jt_objects.job_template.execute_role.pk), objects.superusers.admin)
|
||||
assert response.status_code == 204
|
||||
|
||||
@ -168,12 +168,12 @@ def test_jt_admin_copy_edit_functional(jt_copy_edit, rando, get, post):
|
||||
jt_copy_edit.admin_role.members.add(rando)
|
||||
jt_copy_edit.save()
|
||||
|
||||
get_response = get(reverse('api:job_template_detail', args=[jt_copy_edit.pk]), user=rando)
|
||||
get_response = get(reverse('api:job_template_detail', kwargs={'pk':jt_copy_edit.pk}), user=rando)
|
||||
assert get_response.status_code == 200
|
||||
|
||||
post_data = get_response.data
|
||||
post_data['name'] = '%s @ 12:19:47 pm' % post_data['name']
|
||||
post_response = post(reverse('api:job_template_list', args=[]), user=rando, data=post_data)
|
||||
post_response = post(reverse('api:job_template_list'), user=rando, data=post_data)
|
||||
assert post_response.status_code == 403
|
||||
|
||||
|
||||
@ -244,7 +244,7 @@ def test_disallow_template_delete_on_running_job(job_template_factory, delete, a
|
||||
inventory='i',
|
||||
organization='o')
|
||||
objects.job_template.create_unified_job()
|
||||
delete_response = delete(reverse('api:job_template_detail', args=[objects.job_template.pk]), user=admin_user)
|
||||
delete_response = delete(reverse('api:job_template_detail', kwargs={'pk': objects.job_template.pk}), user=admin_user)
|
||||
assert delete_response.status_code == 409
|
||||
|
||||
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
import pytest
|
||||
|
||||
from django.core.urlresolvers import reverse
|
||||
from awx.api.versioning import reverse
|
||||
|
||||
|
||||
@pytest.fixture
|
||||
@ -70,7 +70,7 @@ def test_org_counts_detail_admin(resourced_organization, user, get):
|
||||
# Check that all types of resources are counted by a superuser
|
||||
external_admin = user('admin', True)
|
||||
response = get(reverse('api:organization_detail',
|
||||
args=[resourced_organization.pk]), external_admin)
|
||||
kwargs={'pk': resourced_organization.pk}), external_admin)
|
||||
assert response.status_code == 200
|
||||
|
||||
counts = response.data['summary_fields']['related_field_counts']
|
||||
@ -82,7 +82,7 @@ def test_org_counts_detail_member(resourced_organization, user, get):
|
||||
# Check that a non-admin org member can only see users / admin in detail view
|
||||
member_user = resourced_organization.member_role.members.get(username='org-member 1')
|
||||
response = get(reverse('api:organization_detail',
|
||||
args=[resourced_organization.pk]), member_user)
|
||||
kwargs={'pk': resourced_organization.pk}), member_user)
|
||||
assert response.status_code == 200
|
||||
|
||||
counts = response.data['summary_fields']['related_field_counts']
|
||||
@ -100,7 +100,7 @@ def test_org_counts_detail_member(resourced_organization, user, get):
|
||||
def test_org_counts_list_admin(resourced_organization, user, get):
|
||||
# Check that all types of resources are counted by a superuser
|
||||
external_admin = user('admin', True)
|
||||
response = get(reverse('api:organization_list', args=[]), external_admin)
|
||||
response = get(reverse('api:organization_list'), external_admin)
|
||||
assert response.status_code == 200
|
||||
|
||||
counts = response.data['results'][0]['summary_fields']['related_field_counts']
|
||||
@ -112,7 +112,7 @@ def test_org_counts_list_member(resourced_organization, user, get):
|
||||
# Check that a non-admin user can only see the full project and
|
||||
# user count, consistent with the RBAC rules
|
||||
member_user = resourced_organization.member_role.members.get(username='org-member 1')
|
||||
response = get(reverse('api:organization_list', args=[]), member_user)
|
||||
response = get(reverse('api:organization_list'), member_user)
|
||||
assert response.status_code == 200
|
||||
|
||||
counts = response.data['results'][0]['summary_fields']['related_field_counts']
|
||||
@ -131,7 +131,7 @@ def test_org_counts_list_member(resourced_organization, user, get):
|
||||
def test_new_org_zero_counts(user, post):
|
||||
# Check that a POST to the organization list endpoint returns
|
||||
# correct counts, including the new record
|
||||
org_list_url = reverse('api:organization_list', args=[])
|
||||
org_list_url = reverse('api:organization_list')
|
||||
post_response = post(url=org_list_url, data={'name': 'test organization',
|
||||
'description': ''}, user=user('admin', True))
|
||||
assert post_response.status_code == 201
|
||||
@ -146,7 +146,7 @@ def test_two_organizations(resourced_organization, organizations, user, get):
|
||||
# Check correct results for two organizations are returned
|
||||
external_admin = user('admin', True)
|
||||
organization_zero = organizations(1)[0]
|
||||
response = get(reverse('api:organization_list', args=[]), external_admin)
|
||||
response = get(reverse('api:organization_list'), external_admin)
|
||||
assert response.status_code == 200
|
||||
|
||||
org_id_full = resourced_organization.id
|
||||
@ -171,12 +171,12 @@ def test_scan_JT_counted(resourced_organization, user, get):
|
||||
counts_dict['job_templates'] += 1
|
||||
|
||||
# Test list view
|
||||
list_response = get(reverse('api:organization_list', args=[]), admin_user)
|
||||
list_response = get(reverse('api:organization_list'), admin_user)
|
||||
assert list_response.status_code == 200
|
||||
assert list_response.data['results'][0]['summary_fields']['related_field_counts'] == counts_dict
|
||||
|
||||
# Test detail view
|
||||
detail_response = get(reverse('api:organization_detail', args=[resourced_organization.pk]), admin_user)
|
||||
detail_response = get(reverse('api:organization_detail', kwargs={'pk': resourced_organization.pk}), admin_user)
|
||||
assert detail_response.status_code == 200
|
||||
assert detail_response.data['summary_fields']['related_field_counts'] == counts_dict
|
||||
|
||||
@ -194,12 +194,12 @@ def test_JT_not_double_counted(resourced_organization, user, get):
|
||||
counts_dict['job_templates'] += 1
|
||||
|
||||
# Test list view
|
||||
list_response = get(reverse('api:organization_list', args=[]), admin_user)
|
||||
list_response = get(reverse('api:organization_list'), admin_user)
|
||||
assert list_response.status_code == 200
|
||||
assert list_response.data['results'][0]['summary_fields']['related_field_counts'] == counts_dict
|
||||
|
||||
# Test detail view
|
||||
detail_response = get(reverse('api:organization_detail', args=[resourced_organization.pk]), admin_user)
|
||||
detail_response = get(reverse('api:organization_detail', kwargs={'pk': resourced_organization.pk}), admin_user)
|
||||
assert detail_response.status_code == 200
|
||||
assert detail_response.data['summary_fields']['related_field_counts'] == counts_dict
|
||||
|
||||
@ -220,7 +220,7 @@ def test_JT_associated_with_project(organizations, project, user, get):
|
||||
inventory=unrelated_inv,
|
||||
playbook="test_playbook.yml")
|
||||
|
||||
response = get(reverse('api:organization_list', args=[]), external_admin)
|
||||
response = get(reverse('api:organization_list'), external_admin)
|
||||
assert response.status_code == 200
|
||||
|
||||
org_id = organization.id
|
||||
|
||||
@ -7,7 +7,7 @@ import mock
|
||||
|
||||
|
||||
# Django
|
||||
from django.core.urlresolvers import reverse
|
||||
from awx.api.versioning import reverse
|
||||
|
||||
# AWX
|
||||
from awx.main.models import * # noqa
|
||||
@ -29,10 +29,10 @@ def test_organization_list_access_tests(options, head, get, admin, alice):
|
||||
@pytest.mark.django_db
|
||||
def test_organization_access_tests(organization, get, admin, alice, bob):
|
||||
organization.member_role.members.add(alice)
|
||||
get(reverse('api:organization_detail', args=(organization.id,)), user=admin, expect=200)
|
||||
get(reverse('api:organization_detail', args=(organization.id,)), user=alice, expect=200)
|
||||
get(reverse('api:organization_detail', args=(organization.id,)), user=bob, expect=403)
|
||||
get(reverse('api:organization_detail', args=(organization.id,)), user=None, expect=401)
|
||||
get(reverse('api:organization_detail', kwargs={'pk': organization.id}), user=admin, expect=200)
|
||||
get(reverse('api:organization_detail', kwargs={'pk': organization.id}), user=alice, expect=200)
|
||||
get(reverse('api:organization_detail', kwargs={'pk': organization.id}), user=bob, expect=403)
|
||||
get(reverse('api:organization_detail', kwargs={'pk': organization.id}), user=None, expect=401)
|
||||
|
||||
|
||||
@pytest.mark.django_db
|
||||
@ -68,9 +68,9 @@ def test_organization_project_list(organization, project_factory, get, alice, bo
|
||||
organization.admin_role.members.add(alice)
|
||||
organization.member_role.members.add(bob)
|
||||
prj1.use_role.members.add(bob)
|
||||
assert get(reverse('api:organization_projects_list', args=(organization.id,)), user=alice).data['count'] == 2
|
||||
assert get(reverse('api:organization_projects_list', args=(organization.id,)), user=bob).data['count'] == 1
|
||||
assert get(reverse('api:organization_projects_list', args=(organization.id,)), user=rando).status_code == 403
|
||||
assert get(reverse('api:organization_projects_list', kwargs={'pk': organization.id}), user=alice).data['count'] == 2
|
||||
assert get(reverse('api:organization_projects_list', kwargs={'pk': organization.id}), user=bob).data['count'] == 1
|
||||
assert get(reverse('api:organization_projects_list', kwargs={'pk': organization.id}), user=rando).status_code == 403
|
||||
|
||||
|
||||
@pytest.mark.django_db
|
||||
@ -78,12 +78,12 @@ def test_organization_user_list(organization, get, admin, alice, bob):
|
||||
organization.admin_role.members.add(alice)
|
||||
organization.member_role.members.add(alice)
|
||||
organization.member_role.members.add(bob)
|
||||
assert get(reverse('api:organization_users_list', args=(organization.id,)), user=admin).data['count'] == 2
|
||||
assert get(reverse('api:organization_users_list', args=(organization.id,)), user=alice).data['count'] == 2
|
||||
assert get(reverse('api:organization_users_list', args=(organization.id,)), user=bob).data['count'] == 2
|
||||
assert get(reverse('api:organization_admins_list', args=(organization.id,)), user=admin).data['count'] == 1
|
||||
assert get(reverse('api:organization_admins_list', args=(organization.id,)), user=alice).data['count'] == 1
|
||||
assert get(reverse('api:organization_admins_list', args=(organization.id,)), user=bob).data['count'] == 1
|
||||
assert get(reverse('api:organization_users_list', kwargs={'pk': organization.id}), user=admin).data['count'] == 2
|
||||
assert get(reverse('api:organization_users_list', kwargs={'pk': organization.id}), user=alice).data['count'] == 2
|
||||
assert get(reverse('api:organization_users_list', kwargs={'pk': organization.id}), user=bob).data['count'] == 2
|
||||
assert get(reverse('api:organization_admins_list', kwargs={'pk': organization.id}), user=admin).data['count'] == 1
|
||||
assert get(reverse('api:organization_admins_list', kwargs={'pk': organization.id}), user=alice).data['count'] == 1
|
||||
assert get(reverse('api:organization_admins_list', kwargs={'pk': organization.id}), user=bob).data['count'] == 1
|
||||
|
||||
|
||||
@pytest.mark.django_db
|
||||
@ -93,9 +93,9 @@ def test_organization_inventory_list(organization, inventory_factory, get, alice
|
||||
organization.admin_role.members.add(alice)
|
||||
organization.member_role.members.add(bob)
|
||||
inv1.use_role.members.add(bob)
|
||||
assert get(reverse('api:organization_inventories_list', args=(organization.id,)), user=alice).data['count'] == 2
|
||||
assert get(reverse('api:organization_inventories_list', args=(organization.id,)), user=bob).data['count'] == 1
|
||||
get(reverse('api:organization_inventories_list', args=(organization.id,)), user=rando, expect=403)
|
||||
assert get(reverse('api:organization_inventories_list', kwargs={'pk': organization.id}), user=alice).data['count'] == 2
|
||||
assert get(reverse('api:organization_inventories_list', kwargs={'pk': organization.id}), user=bob).data['count'] == 1
|
||||
get(reverse('api:organization_inventories_list', kwargs={'pk': organization.id}), user=rando, expect=403)
|
||||
|
||||
|
||||
@pytest.mark.django_db
|
||||
@ -123,25 +123,25 @@ def test_create_organization_xfail(post, alice):
|
||||
@pytest.mark.django_db
|
||||
def test_add_user_to_organization(post, organization, alice, bob):
|
||||
organization.admin_role.members.add(alice)
|
||||
post(reverse('api:organization_users_list', args=(organization.id,)), {'id': bob.id}, user=alice, expect=204)
|
||||
post(reverse('api:organization_users_list', kwargs={'pk': organization.id}), {'id': bob.id}, user=alice, expect=204)
|
||||
assert bob in organization.member_role
|
||||
post(reverse('api:organization_users_list', args=(organization.id,)), {'id': bob.id, 'disassociate': True} , user=alice, expect=204)
|
||||
post(reverse('api:organization_users_list', kwargs={'pk': organization.id}), {'id': bob.id, 'disassociate': True} , user=alice, expect=204)
|
||||
assert bob not in organization.member_role
|
||||
|
||||
|
||||
@pytest.mark.django_db
|
||||
def test_add_user_to_organization_xfail(post, organization, alice, bob):
|
||||
organization.member_role.members.add(alice)
|
||||
post(reverse('api:organization_users_list', args=(organization.id,)), {'id': bob.id}, user=alice, expect=403)
|
||||
post(reverse('api:organization_users_list', kwargs={'pk': organization.id}), {'id': bob.id}, user=alice, expect=403)
|
||||
|
||||
|
||||
@pytest.mark.django_db
|
||||
def test_add_admin_to_organization(post, organization, alice, bob):
|
||||
organization.admin_role.members.add(alice)
|
||||
post(reverse('api:organization_admins_list', args=(organization.id,)), {'id': bob.id}, user=alice, expect=204)
|
||||
post(reverse('api:organization_admins_list', kwargs={'pk': organization.id}), {'id': bob.id}, user=alice, expect=204)
|
||||
assert bob in organization.admin_role
|
||||
assert bob in organization.member_role
|
||||
post(reverse('api:organization_admins_list', args=(organization.id,)), {'id': bob.id, 'disassociate': True} , user=alice, expect=204)
|
||||
post(reverse('api:organization_admins_list', kwargs={'pk': organization.id}), {'id': bob.id, 'disassociate': True} , user=alice, expect=204)
|
||||
assert bob not in organization.admin_role
|
||||
assert bob not in organization.member_role
|
||||
|
||||
@ -149,42 +149,42 @@ def test_add_admin_to_organization(post, organization, alice, bob):
|
||||
@pytest.mark.django_db
|
||||
def test_add_admin_to_organization_xfail(post, organization, alice, bob):
|
||||
organization.member_role.members.add(alice)
|
||||
post(reverse('api:organization_admins_list', args=(organization.id,)), {'id': bob.id}, user=alice, expect=403)
|
||||
post(reverse('api:organization_admins_list', kwargs={'pk': organization.id}), {'id': bob.id}, user=alice, expect=403)
|
||||
|
||||
|
||||
@pytest.mark.django_db
|
||||
def test_update_organization(get, put, organization, alice, bob):
|
||||
organization.admin_role.members.add(alice)
|
||||
data = get(reverse('api:organization_detail', args=(organization.id,)), user=alice, expect=200).data
|
||||
data = get(reverse('api:organization_detail', kwargs={'pk': organization.id}), user=alice, expect=200).data
|
||||
data['description'] = 'hi'
|
||||
put(reverse('api:organization_detail', args=(organization.id,)), data, user=alice, expect=200)
|
||||
put(reverse('api:organization_detail', kwargs={'pk': organization.id}), data, user=alice, expect=200)
|
||||
organization.refresh_from_db()
|
||||
assert organization.description == 'hi'
|
||||
data['description'] = 'bye'
|
||||
put(reverse('api:organization_detail', args=(organization.id,)), data, user=bob, expect=403)
|
||||
put(reverse('api:organization_detail', kwargs={'pk': organization.id}), data, user=bob, expect=403)
|
||||
|
||||
|
||||
@pytest.mark.django_db
|
||||
@mock.patch('awx.main.access.BaseAccess.check_license', lambda *a, **kw: True)
|
||||
def test_delete_organization(delete, organization, admin):
|
||||
delete(reverse('api:organization_detail', args=(organization.id,)), user=admin, expect=204)
|
||||
delete(reverse('api:organization_detail', kwargs={'pk': organization.id}), user=admin, expect=204)
|
||||
|
||||
|
||||
@pytest.mark.django_db
|
||||
@mock.patch('awx.main.access.BaseAccess.check_license', lambda *a, **kw: True)
|
||||
def test_delete_organization2(delete, organization, alice):
|
||||
organization.admin_role.members.add(alice)
|
||||
delete(reverse('api:organization_detail', args=(organization.id,)), user=alice, expect=204)
|
||||
delete(reverse('api:organization_detail', kwargs={'pk': organization.id}), user=alice, expect=204)
|
||||
|
||||
|
||||
@pytest.mark.django_db
|
||||
@mock.patch('awx.main.access.BaseAccess.check_license', lambda *a, **kw: True)
|
||||
def test_delete_organization_xfail1(delete, organization, alice):
|
||||
organization.member_role.members.add(alice)
|
||||
delete(reverse('api:organization_detail', args=(organization.id,)), user=alice, expect=403)
|
||||
delete(reverse('api:organization_detail', kwargs={'pk': organization.id}), user=alice, expect=403)
|
||||
|
||||
|
||||
@pytest.mark.django_db
|
||||
@mock.patch('awx.main.access.BaseAccess.check_license', lambda *a, **kw: True)
|
||||
def test_delete_organization_xfail2(delete, organization):
|
||||
delete(reverse('api:organization_detail', args=(organization.id,)), user=None, expect=401)
|
||||
delete(reverse('api:organization_detail', kwargs={'pk': organization.id}), user=None, expect=401)
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
import pytest
|
||||
|
||||
from django.core.urlresolvers import reverse
|
||||
from awx.api.versioning import reverse
|
||||
from django.test.client import RequestFactory
|
||||
|
||||
from awx.main.models import Role, Group, UnifiedJobTemplate, JobTemplate
|
||||
@ -30,17 +30,17 @@ class TestOptionsRBAC:
|
||||
def test_inventory_group_host_can_add(self, inventory, alice, options):
|
||||
inventory.admin_role.members.add(alice)
|
||||
|
||||
response = options(reverse('api:inventory_hosts_list', args=[inventory.pk]), alice)
|
||||
response = options(reverse('api:inventory_hosts_list', kwargs={'pk': inventory.pk}), alice)
|
||||
assert 'POST' in response.data['actions']
|
||||
response = options(reverse('api:inventory_groups_list', args=[inventory.pk]), alice)
|
||||
response = options(reverse('api:inventory_groups_list', kwargs={'pk': inventory.pk}), alice)
|
||||
assert 'POST' in response.data['actions']
|
||||
|
||||
def test_inventory_group_host_can_not_add(self, inventory, bob, options):
|
||||
inventory.read_role.members.add(bob)
|
||||
|
||||
response = options(reverse('api:inventory_hosts_list', args=[inventory.pk]), bob)
|
||||
response = options(reverse('api:inventory_hosts_list', kwargs={'pk': inventory.pk}), bob)
|
||||
assert 'POST' not in response.data['actions']
|
||||
response = options(reverse('api:inventory_groups_list', args=[inventory.pk]), bob)
|
||||
response = options(reverse('api:inventory_groups_list', kwargs={'pk': inventory.pk}), bob)
|
||||
assert 'POST' not in response.data['actions']
|
||||
|
||||
def test_user_list_can_add(self, org_member, org_admin, options):
|
||||
@ -192,7 +192,7 @@ class TestAccessListCapabilities:
|
||||
inventory.admin_role.members.add(rando)
|
||||
|
||||
with mocker.patch.object(access_registry[Role][0], 'can_unattach', mock_access_method):
|
||||
response = get(reverse('api:inventory_access_list', args=(inventory.id,)), rando)
|
||||
response = get(reverse('api:inventory_access_list', kwargs={'pk': inventory.id}), rando)
|
||||
|
||||
mock_access_method.assert_called_once_with(inventory.admin_role, rando, 'members', **self.extra_kwargs)
|
||||
self._assert_one_in_list(response.data)
|
||||
@ -202,7 +202,7 @@ class TestAccessListCapabilities:
|
||||
def test_access_list_indirect_access_capability(
|
||||
self, inventory, organization, org_admin, get, mocker, mock_access_method):
|
||||
with mocker.patch.object(access_registry[Role][0], 'can_unattach', mock_access_method):
|
||||
response = get(reverse('api:inventory_access_list', args=(inventory.id,)), org_admin)
|
||||
response = get(reverse('api:inventory_access_list', kwargs={'pk': inventory.id}), org_admin)
|
||||
|
||||
mock_access_method.assert_called_once_with(organization.admin_role, org_admin, 'members', **self.extra_kwargs)
|
||||
self._assert_one_in_list(response.data, sublist='indirect_access')
|
||||
@ -214,7 +214,7 @@ class TestAccessListCapabilities:
|
||||
team.member_role.children.add(inventory.admin_role)
|
||||
|
||||
with mocker.patch.object(access_registry[Role][0], 'can_unattach', mock_access_method):
|
||||
response = get(reverse('api:inventory_access_list', args=(inventory.id,)), team_member)
|
||||
response = get(reverse('api:inventory_access_list', kwargs={'pk': inventory.id}), team_member)
|
||||
|
||||
mock_access_method.assert_called_once_with(inventory.admin_role, team.member_role, 'parents', **self.extra_kwargs)
|
||||
self._assert_one_in_list(response.data)
|
||||
@ -223,7 +223,7 @@ class TestAccessListCapabilities:
|
||||
|
||||
def test_user_access_list_direct_access_capability(self, rando, get):
|
||||
"When a user views their own access list, they cannot unattach their admin role"
|
||||
response = get(reverse('api:user_access_list', args=(rando.id,)), rando)
|
||||
response = get(reverse('api:user_access_list', kwargs={'pk': rando.id}), rando)
|
||||
direct_access_list = response.data['results'][0]['summary_fields']['direct_access']
|
||||
assert not direct_access_list[0]['role']['user_capabilities']['unattach']
|
||||
|
||||
@ -233,7 +233,7 @@ def test_team_roles_unattach(mocker, team, team_member, inventory, mock_access_m
|
||||
team.member_role.children.add(inventory.admin_role)
|
||||
|
||||
with mocker.patch.object(access_registry[Role][0], 'can_unattach', mock_access_method):
|
||||
response = get(reverse('api:team_roles_list', args=(team.id,)), team_member)
|
||||
response = get(reverse('api:team_roles_list', kwargs={'pk': team.id}), team_member)
|
||||
|
||||
# Did we assess whether team_member can remove team's permission to the inventory?
|
||||
mock_access_method.assert_called_once_with(
|
||||
@ -248,7 +248,7 @@ def test_user_roles_unattach(mocker, organization, alice, bob, mock_access_metho
|
||||
organization.member_role.members.add(bob)
|
||||
|
||||
with mocker.patch.object(access_registry[Role][0], 'can_unattach', mock_access_method):
|
||||
response = get(reverse('api:user_roles_list', args=(alice.id,)), bob)
|
||||
response = get(reverse('api:user_roles_list', kwargs={'pk': alice.id}), bob)
|
||||
|
||||
# Did we assess whether bob can remove alice's permission to the inventory?
|
||||
mock_access_method.assert_called_once_with(
|
||||
@ -259,7 +259,7 @@ def test_user_roles_unattach(mocker, organization, alice, bob, mock_access_metho
|
||||
@pytest.mark.django_db
|
||||
def test_team_roles_unattach_functional(team, team_member, inventory, get):
|
||||
team.member_role.children.add(inventory.admin_role)
|
||||
response = get(reverse('api:team_roles_list', args=(team.id,)), team_member)
|
||||
response = get(reverse('api:team_roles_list', kwargs={'pk': team.id}), team_member)
|
||||
# Team member should be able to remove access to inventory, becauase
|
||||
# the inventory admin_role grants that ability
|
||||
assert response.data['results'][0]['summary_fields']['user_capabilities']['unattach']
|
||||
@ -269,7 +269,7 @@ def test_team_roles_unattach_functional(team, team_member, inventory, get):
|
||||
def test_user_roles_unattach_functional(organization, alice, bob, get):
|
||||
organization.member_role.members.add(alice)
|
||||
organization.member_role.members.add(bob)
|
||||
response = get(reverse('api:user_roles_list', args=(alice.id,)), bob)
|
||||
response = get(reverse('api:user_roles_list', kwargs={'pk': alice.id}), bob)
|
||||
# Org members cannot revoke the membership of other members
|
||||
assert not response.data['results'][0]['summary_fields']['user_capabilities']['unattach']
|
||||
|
||||
@ -336,7 +336,7 @@ def test_prefetch_jt_copy_capability(job_template, project, inventory, machine_c
|
||||
|
||||
@pytest.mark.django_db
|
||||
def test_manual_projects_no_update(project, get, admin_user):
|
||||
response = get(reverse('api:project_detail', args=[project.pk]), admin_user, expect=200)
|
||||
response = get(reverse('api:project_detail', kwargs={'pk': project.pk}), admin_user, expect=200)
|
||||
assert not response.data['summary_fields']['user_capabilities']['start']
|
||||
assert not response.data['summary_fields']['user_capabilities']['schedule']
|
||||
|
||||
@ -369,5 +369,5 @@ def test_license_check_not_called(mocker, job_template, project, org_admin, get)
|
||||
job_template.save() # need this to make the JT visible
|
||||
mock_license_check = mocker.MagicMock()
|
||||
with mocker.patch('awx.main.access.BaseAccess.check_license', mock_license_check):
|
||||
get(reverse('api:job_template_detail', args=[job_template.pk]), org_admin, expect=200)
|
||||
get(reverse('api:job_template_detail', kwargs={'pk': job_template.pk}), org_admin, expect=200)
|
||||
assert not mock_license_check.called
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
import pytest
|
||||
|
||||
from django.core.urlresolvers import reverse
|
||||
from awx.api.versioning import reverse
|
||||
from awx.main.models import Role
|
||||
|
||||
|
||||
@ -19,7 +19,7 @@ def test_indirect_access_list(get, organization, project, team_factory, user, ad
|
||||
|
||||
project_admin_team.admin_role.members.add(team_admin)
|
||||
|
||||
result = get(reverse('api:project_access_list', args=(project.id,)), admin)
|
||||
result = get(reverse('api:project_access_list', kwargs={'pk': project.id}), admin)
|
||||
assert result.status_code == 200
|
||||
|
||||
# Result should be:
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
import pytest
|
||||
|
||||
from django.core.urlresolvers import reverse
|
||||
from awx.api.versioning import reverse
|
||||
|
||||
|
||||
@pytest.mark.django_db
|
||||
|
||||
@ -9,10 +9,8 @@ import os
|
||||
# Mock
|
||||
import mock
|
||||
|
||||
# Django
|
||||
from django.core.urlresolvers import reverse
|
||||
|
||||
# AWX
|
||||
from awx.api.versioning import reverse
|
||||
from awx.conf.models import Setting
|
||||
from awx.main.utils.handlers import BaseHTTPSHandler, LoggingConnectivityException
|
||||
|
||||
@ -32,7 +30,7 @@ def mock_no_license_file(mocker):
|
||||
|
||||
@pytest.mark.django_db
|
||||
def test_license_cannot_be_removed_via_system_settings(mock_no_license_file, get, put, patch, delete, admin, enterprise_license):
|
||||
url = reverse('api:setting_singleton_detail', args=('system',))
|
||||
url = reverse('api:setting_singleton_detail', kwargs={'category_slug': 'system'})
|
||||
response = get(url, user=admin, expect=200)
|
||||
assert not response.data['LICENSE']
|
||||
Setting.objects.create(key='TOWER_URL_BASE', value='https://towerhost')
|
||||
@ -53,13 +51,13 @@ def test_license_cannot_be_removed_via_system_settings(mock_no_license_file, get
|
||||
@pytest.mark.django_db
|
||||
def test_url_base_defaults_to_request(options, admin):
|
||||
# If TOWER_URL_BASE is not set, default to the Tower request hostname
|
||||
resp = options(reverse('api:setting_singleton_detail', args=('system',)), user=admin, expect=200)
|
||||
resp = options(reverse('api:setting_singleton_detail', kwargs={'category_slug': 'system'}), user=admin, expect=200)
|
||||
assert resp.data['actions']['PUT']['TOWER_URL_BASE']['default'] == 'http://testserver'
|
||||
|
||||
|
||||
@pytest.mark.django_db
|
||||
def test_jobs_settings(get, put, patch, delete, admin):
|
||||
url = reverse('api:setting_singleton_detail', args=('jobs',))
|
||||
url = reverse('api:setting_singleton_detail', kwargs={'category_slug': 'jobs'})
|
||||
get(url, user=admin, expect=200)
|
||||
delete(url, user=admin, expect=204)
|
||||
response = get(url, user=admin, expect=200)
|
||||
@ -80,7 +78,7 @@ def test_jobs_settings(get, put, patch, delete, admin):
|
||||
|
||||
@pytest.mark.django_db
|
||||
def test_ldap_settings(get, put, patch, delete, admin, enterprise_license):
|
||||
url = reverse('api:setting_singleton_detail', args=('ldap',))
|
||||
url = reverse('api:setting_singleton_detail', kwargs={'category_slug': 'ldap'})
|
||||
get(url, user=admin, expect=404)
|
||||
Setting.objects.create(key='LICENSE', value=enterprise_license)
|
||||
get(url, user=admin, expect=200)
|
||||
@ -107,7 +105,7 @@ def test_ldap_settings(get, put, patch, delete, admin, enterprise_license):
|
||||
@pytest.mark.django_db
|
||||
def test_empty_ldap_dn(get, put, patch, delete, admin, enterprise_license,
|
||||
setting):
|
||||
url = reverse('api:setting_singleton_detail', args=('ldap',))
|
||||
url = reverse('api:setting_singleton_detail', kwargs={'category_slug': 'ldap'})
|
||||
Setting.objects.create(key='LICENSE', value=enterprise_license)
|
||||
|
||||
patch(url, user=admin, data={setting: ''}, expect=200)
|
||||
@ -121,7 +119,7 @@ def test_empty_ldap_dn(get, put, patch, delete, admin, enterprise_license,
|
||||
|
||||
@pytest.mark.django_db
|
||||
def test_radius_settings(get, put, patch, delete, admin, enterprise_license, settings):
|
||||
url = reverse('api:setting_singleton_detail', args=('radius',))
|
||||
url = reverse('api:setting_singleton_detail', kwargs={'category_slug': 'radius'})
|
||||
get(url, user=admin, expect=404)
|
||||
Setting.objects.create(key='LICENSE', value=enterprise_license)
|
||||
response = get(url, user=admin, expect=200)
|
||||
@ -155,7 +153,7 @@ def test_radius_settings(get, put, patch, delete, admin, enterprise_license, set
|
||||
|
||||
@pytest.mark.django_db
|
||||
def test_ui_settings(get, put, patch, delete, admin, enterprise_license):
|
||||
url = reverse('api:setting_singleton_detail', args=('ui',))
|
||||
url = reverse('api:setting_singleton_detail', kwargs={'category_slug': 'ui'})
|
||||
response = get(url, user=admin, expect=200)
|
||||
assert 'CUSTOM_LOGO' not in response.data
|
||||
assert 'CUSTOM_LOGIN_INFO' not in response.data
|
||||
|
||||
@ -2,8 +2,8 @@ import mock
|
||||
import pytest
|
||||
import json
|
||||
|
||||
from django.core.urlresolvers import reverse
|
||||
|
||||
from awx.api.versioning import reverse
|
||||
from awx.main.models.jobs import JobTemplate, Job
|
||||
from awx.main.models.activity_stream import ActivityStream
|
||||
from awx.conf.license import LicenseForbids
|
||||
@ -30,7 +30,7 @@ def job_template_with_survey(job_template_factory):
|
||||
def test_survey_spec_view_denied(job_template_with_survey, get, admin_user):
|
||||
# TODO: Test non-enterprise license
|
||||
response = get(reverse('api:job_template_survey_spec',
|
||||
args=(job_template_with_survey.id,)), admin_user, expect=402)
|
||||
kwargs={'pk': job_template_with_survey.id}), admin_user, expect=402)
|
||||
assert response.data['detail'] == 'Your license does not allow adding surveys.'
|
||||
|
||||
|
||||
@ -76,7 +76,7 @@ def test_deny_creating_with_survey(project, post, admin_user):
|
||||
@pytest.mark.django_db
|
||||
@pytest.mark.survey
|
||||
def test_survey_spec_view_allowed(deploy_jobtemplate, get, admin_user):
|
||||
get(reverse('api:job_template_survey_spec', args=(deploy_jobtemplate.id,)),
|
||||
get(reverse('api:job_template_survey_spec', kwargs={'pk': deploy_jobtemplate.id}),
|
||||
admin_user, expect=200)
|
||||
|
||||
|
||||
@ -85,7 +85,7 @@ def test_survey_spec_view_allowed(deploy_jobtemplate, get, admin_user):
|
||||
@pytest.mark.survey
|
||||
def test_survey_spec_sucessful_creation(survey_spec_factory, job_template, post, admin_user):
|
||||
survey_input_data = survey_spec_factory('new_question')
|
||||
post(url=reverse('api:job_template_survey_spec', args=(job_template.id,)),
|
||||
post(url=reverse('api:job_template_survey_spec', kwargs={'pk': job_template.id}),
|
||||
data=survey_input_data, user=admin_user, expect=200)
|
||||
updated_jt = JobTemplate.objects.get(pk=job_template.pk)
|
||||
assert updated_jt.survey_spec == survey_input_data
|
||||
@ -98,10 +98,14 @@ def test_survey_spec_sucessful_creation(survey_spec_factory, job_template, post,
|
||||
def test_survey_spec_non_dict_error(deploy_jobtemplate, post, admin_user):
|
||||
"""When a question doesn't follow the standard format, verify error thrown."""
|
||||
response = post(
|
||||
url=reverse('api:job_template_survey_spec', args=(deploy_jobtemplate.id,)),
|
||||
data={"description": "Email of the submitter",
|
||||
"spec": ["What is your email?"], "name": "Email survey"},
|
||||
user=admin_user, expect=400)
|
||||
url=reverse('api:job_template_survey_spec', kwargs={'pk': deploy_jobtemplate.id}),
|
||||
data={
|
||||
"description": "Email of the submitter",
|
||||
"spec": ["What is your email?"], "name": "Email survey"
|
||||
},
|
||||
user=admin_user,
|
||||
expect=400
|
||||
)
|
||||
assert response.data['error'] == "Survey question 0 is not a json object."
|
||||
|
||||
|
||||
@ -110,9 +114,11 @@ def test_survey_spec_non_dict_error(deploy_jobtemplate, post, admin_user):
|
||||
@pytest.mark.survey
|
||||
def test_survey_spec_dual_names_error(survey_spec_factory, deploy_jobtemplate, post, user):
|
||||
response = post(
|
||||
url=reverse('api:job_template_survey_spec', args=(deploy_jobtemplate.id,)),
|
||||
url=reverse('api:job_template_survey_spec', kwargs={'pk': deploy_jobtemplate.id}),
|
||||
data=survey_spec_factory(['submitter_email', 'submitter_email']),
|
||||
user=user('admin', True), expect=400)
|
||||
user=user('admin', True),
|
||||
expect=400
|
||||
)
|
||||
assert response.data['error'] == "'variable' 'submitter_email' duplicated in survey question 1."
|
||||
|
||||
|
||||
@ -166,7 +172,7 @@ def test_job_template_delete_access_with_survey(job_template_with_survey, admin_
|
||||
@pytest.mark.survey
|
||||
def test_delete_survey_spec_without_license(job_template_with_survey, delete, admin_user):
|
||||
"""Functional delete test through the survey_spec view."""
|
||||
delete(reverse('api:job_template_survey_spec', args=[job_template_with_survey.pk]),
|
||||
delete(reverse('api:job_template_survey_spec', kwargs={'pk': job_template_with_survey.pk}),
|
||||
admin_user, expect=200)
|
||||
new_jt = JobTemplate.objects.get(pk=job_template_with_survey.pk)
|
||||
assert new_jt.survey_spec == {}
|
||||
@ -185,7 +191,7 @@ def test_launch_survey_enabled_but_no_survey_spec(job_template_factory, post, ad
|
||||
obj = objects.job_template
|
||||
obj.survey_enabled = True
|
||||
obj.save()
|
||||
response = post(reverse('api:job_template_launch', args=[obj.pk]),
|
||||
response = post(reverse('api:job_template_launch', kwargs={'pk':obj.pk}),
|
||||
dict(extra_vars=dict(survey_var=7)), admin_user, expect=201)
|
||||
assert 'survey_var' in response.data['ignored_fields']['extra_vars']
|
||||
|
||||
@ -205,7 +211,7 @@ def test_launch_with_non_empty_survey_spec_no_license(job_template_factory, post
|
||||
obj = objects.job_template
|
||||
obj.survey_enabled = False
|
||||
obj.save()
|
||||
post(reverse('api:job_template_launch', args=[obj.pk]), {}, admin_user, expect=201)
|
||||
post(reverse('api:job_template_launch', kwargs={'pk': obj.pk}), {}, admin_user, expect=201)
|
||||
|
||||
|
||||
@pytest.mark.django_db
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
import pytest
|
||||
|
||||
from django.core.urlresolvers import reverse
|
||||
from awx.api.versioning import reverse
|
||||
|
||||
|
||||
@pytest.mark.django_db
|
||||
|
||||
@ -1,7 +1,6 @@
|
||||
import pytest
|
||||
|
||||
from django.core.urlresolvers import reverse
|
||||
|
||||
from awx.api.versioning import reverse
|
||||
from awx.main.models import UnifiedJob, ProjectUpdate
|
||||
from awx.main.tests.base import URI
|
||||
|
||||
@ -60,7 +59,7 @@ formats = [
|
||||
def test_project_update_redaction_enabled(get, format, content_type, test_cases, admin):
|
||||
for test_data in test_cases:
|
||||
job = test_data['project']
|
||||
response = get(reverse("api:project_update_stdout", args=(job.pk,)) + "?format=" + format, user=admin, expect=200, accept=content_type)
|
||||
response = get(reverse("api:project_update_stdout", kwargs={'pk': job.pk}) + "?format=" + format, user=admin, expect=200, accept=content_type)
|
||||
assert content_type in response['CONTENT-TYPE']
|
||||
assert response.data is not None
|
||||
content = response.data['content'] if format == 'json' else response.data
|
||||
@ -74,7 +73,7 @@ def test_project_update_redaction_enabled(get, format, content_type, test_cases,
|
||||
def test_job_redaction_disabled(get, format, content_type, negative_test_cases, admin):
|
||||
for test_data in negative_test_cases:
|
||||
job = test_data['job']
|
||||
response = get(reverse("api:job_stdout", args=(job.pk,)) + "?format=" + format, user=admin, expect=200, format=format)
|
||||
response = get(reverse("api:job_stdout", kwargs={'pk': job.pk}) + "?format=" + format, user=admin, expect=200, format=format)
|
||||
content = response.data['content'] if format == 'json' else response.data
|
||||
assert response.data is not None
|
||||
assert test_data['uri'].username in content
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
import pytest
|
||||
|
||||
from django.core.urlresolvers import reverse
|
||||
from awx.api.versioning import reverse
|
||||
|
||||
|
||||
#
|
||||
@ -39,7 +39,7 @@ def test_create_delete_create_user(post, delete, admin):
|
||||
response = post(reverse('api:user_list'), EXAMPLE_USER_DATA, admin)
|
||||
assert response.status_code == 201
|
||||
|
||||
response = delete(reverse('api:user_detail', args=(response.data['id'],)), admin)
|
||||
response = delete(reverse('api:user_detail', kwargs={'pk': response.data['id']}), admin)
|
||||
assert response.status_code == 204
|
||||
|
||||
response = post(reverse('api:user_list'), EXAMPLE_USER_DATA, admin)
|
||||
|
||||
@ -1,12 +1,11 @@
|
||||
import mock
|
||||
import pytest
|
||||
|
||||
from awx.api.versioning import reverse
|
||||
from awx.main.models.notifications import NotificationTemplate, Notification
|
||||
from awx.main.models.inventory import Inventory, Group
|
||||
from awx.main.models.jobs import JobTemplate
|
||||
|
||||
from django.core.urlresolvers import reverse
|
||||
|
||||
|
||||
@pytest.mark.django_db
|
||||
def test_get_notification_template_list(get, user, notification_template):
|
||||
@ -29,7 +28,7 @@ def test_basic_parameterization(get, post, user, organization):
|
||||
headers={"Test": "Header"})),
|
||||
u)
|
||||
assert response.status_code == 201
|
||||
url = reverse('api:notification_template_detail', args=(response.data['id'],))
|
||||
url = reverse('api:notification_template_detail', kwargs={'pk': response.data['id']})
|
||||
response = get(url, u)
|
||||
assert 'related' in response.data
|
||||
assert 'organization' in response.data['related']
|
||||
@ -60,7 +59,7 @@ def test_encrypted_subfields(get, post, user, organization):
|
||||
u)
|
||||
assert response.status_code == 201
|
||||
notification_template_actual = NotificationTemplate.objects.get(id=response.data['id'])
|
||||
url = reverse('api:notification_template_detail', args=(response.data['id'],))
|
||||
url = reverse('api:notification_template_detail', kwargs={'pk': response.data['id']})
|
||||
response = get(url, u)
|
||||
assert response.data['notification_configuration']['account_token'] == "$encrypted$"
|
||||
with mock.patch.object(notification_template_actual.notification_class, "send_messages", assert_send):
|
||||
@ -89,13 +88,13 @@ def test_inherited_notification_templates(get, post, user, organization, project
|
||||
g.save()
|
||||
jt = JobTemplate.objects.create(name='test', inventory=i, project=project, playbook='debug.yml')
|
||||
jt.save()
|
||||
url = reverse('api:organization_notification_templates_any_list', args=(organization.id,))
|
||||
url = reverse('api:organization_notification_templates_any_list', kwargs={'pk': organization.id})
|
||||
response = post(url, dict(id=notification_templates[0]), u)
|
||||
assert response.status_code == 204
|
||||
url = reverse('api:project_notification_templates_any_list', args=(project.id,))
|
||||
url = reverse('api:project_notification_templates_any_list', kwargs={'pk': project.id})
|
||||
response = post(url, dict(id=notification_templates[1]), u)
|
||||
assert response.status_code == 204
|
||||
url = reverse('api:job_template_notification_templates_any_list', args=(jt.id,))
|
||||
url = reverse('api:job_template_notification_templates_any_list', kwargs={'pk': jt.id})
|
||||
response = post(url, dict(id=notification_templates[2]), u)
|
||||
assert response.status_code == 204
|
||||
assert len(jt.notification_templates['any']) == 3
|
||||
@ -113,18 +112,18 @@ def test_notification_template_merging(get, post, user, organization, project, n
|
||||
|
||||
@pytest.mark.django_db
|
||||
def test_notification_template_simple_patch(patch, notification_template, admin):
|
||||
patch(reverse('api:notification_template_detail', args=(notification_template.id,)), { 'name': 'foo'}, admin, expect=200)
|
||||
patch(reverse('api:notification_template_detail', kwargs={'pk': notification_template.id}), { 'name': 'foo'}, admin, expect=200)
|
||||
|
||||
|
||||
@pytest.mark.django_db
|
||||
def test_notification_template_invalid_notification_type(patch, notification_template, admin):
|
||||
patch(reverse('api:notification_template_detail', args=(notification_template.id,)), { 'notification_type': 'invalid'}, admin, expect=400)
|
||||
patch(reverse('api:notification_template_detail', kwargs={'pk': notification_template.id}), { 'notification_type': 'invalid'}, admin, expect=400)
|
||||
|
||||
|
||||
@pytest.mark.django_db
|
||||
def test_disallow_delete_when_notifications_pending(delete, user, notification_template):
|
||||
u = user('superuser', True)
|
||||
url = reverse('api:notification_template_detail', args=(notification_template.id,))
|
||||
url = reverse('api:notification_template_detail', kwargs={'pk': notification_template.id})
|
||||
Notification.objects.create(notification_template=notification_template,
|
||||
status='pending')
|
||||
response = delete(url, user=u)
|
||||
|
||||
@ -3,7 +3,7 @@
|
||||
import mock # noqa
|
||||
import pytest
|
||||
|
||||
from django.core.urlresolvers import reverse
|
||||
from awx.api.versioning import reverse
|
||||
from awx.main.models import Project
|
||||
|
||||
|
||||
@ -38,13 +38,13 @@ def test_user_project_paged_list(get, organization_factory):
|
||||
|
||||
# first page has first project and no previous page
|
||||
pk = objects.users.alice.pk
|
||||
url = reverse('api:user_projects_list', args=(pk,))
|
||||
url = reverse('api:user_projects_list', kwargs={'pk':pk,})
|
||||
results = get(url, objects.users.alice, QUERY_STRING='page_size=1').data
|
||||
assert results['count'] == 3
|
||||
assert len(results['results']) == 1
|
||||
assert results['previous'] is None
|
||||
assert results['next'] == (
|
||||
'/api/v1/users/%s/projects/?page=2&page_size=1' % pk
|
||||
'/api/v2/users/%s/projects/?page=2&page_size=1' % pk
|
||||
)
|
||||
|
||||
# second page has one more, a previous and next page
|
||||
@ -52,10 +52,10 @@ def test_user_project_paged_list(get, organization_factory):
|
||||
QUERY_STRING='page=2&page_size=1').data
|
||||
assert len(results['results']) == 1
|
||||
assert results['previous'] == (
|
||||
'/api/v1/users/%s/projects/?page=1&page_size=1' % pk
|
||||
'/api/v2/users/%s/projects/?page=1&page_size=1' % pk
|
||||
)
|
||||
assert results['next'] == (
|
||||
'/api/v1/users/%s/projects/?page=3&page_size=1' % pk
|
||||
'/api/v2/users/%s/projects/?page=3&page_size=1' % pk
|
||||
)
|
||||
|
||||
# third page has last project and a previous page
|
||||
@ -63,7 +63,7 @@ def test_user_project_paged_list(get, organization_factory):
|
||||
QUERY_STRING='page=3&page_size=1').data
|
||||
assert len(results['results']) == 1
|
||||
assert results['previous'] == (
|
||||
'/api/v1/users/%s/projects/?page=2&page_size=1' % pk
|
||||
'/api/v2/users/%s/projects/?page=2&page_size=1' % pk
|
||||
)
|
||||
assert results['next'] is None
|
||||
|
||||
@ -81,7 +81,7 @@ def test_user_project_paged_list_with_unicode(get, organization_factory):
|
||||
roles=['project-☁-1.admin_role:alice','project-☁-2.admin_role:alice'],
|
||||
)
|
||||
pk = objects.users.alice.pk
|
||||
url = reverse('api:user_projects_list', args=(pk,))
|
||||
url = reverse('api:user_projects_list', kwargs={'pk':pk,})
|
||||
|
||||
# first on first page, next page link contains unicode char
|
||||
results = get(url, objects.users.alice,
|
||||
@ -89,7 +89,7 @@ def test_user_project_paged_list_with_unicode(get, organization_factory):
|
||||
assert results['count'] == 2
|
||||
assert len(results['results']) == 1
|
||||
assert results['next'] == (
|
||||
'/api/v1/users/%s/projects/?page=2&page_size=1&search=%%E2%%98%%81' % pk # noqa
|
||||
'/api/v2/users/%s/projects/?page=2&page_size=1&search=%%E2%%98%%81' % pk # noqa
|
||||
)
|
||||
|
||||
# second project on second page, previous page link contains unicode char
|
||||
@ -98,7 +98,7 @@ def test_user_project_paged_list_with_unicode(get, organization_factory):
|
||||
assert results['count'] == 2
|
||||
assert len(results['results']) == 1
|
||||
assert results['previous'] == (
|
||||
'/api/v1/users/%s/projects/?page=1&page_size=1&search=%%E2%%98%%81' % pk # noqa
|
||||
'/api/v2/users/%s/projects/?page=1&page_size=1&search=%%E2%%98%%81' % pk # noqa
|
||||
)
|
||||
|
||||
|
||||
@ -114,21 +114,23 @@ def test_user_project_list(get, organization_factory):
|
||||
'bob project.admin_role:bob',
|
||||
'shared project.admin_role:bob',
|
||||
'shared project.admin_role:alice'])
|
||||
|
||||
assert get(reverse('api:user_projects_list', args=(objects.superusers.admin.pk,)), objects.superusers.admin).data['count'] == 3
|
||||
assert get(reverse(
|
||||
'api:user_projects_list',
|
||||
kwargs={'pk':objects.superusers.admin.pk,}
|
||||
), objects.superusers.admin).data['count'] == 3
|
||||
|
||||
# admins can see everyones projects
|
||||
assert get(reverse('api:user_projects_list', args=(objects.users.alice.pk,)), objects.superusers.admin).data['count'] == 2
|
||||
assert get(reverse('api:user_projects_list', args=(objects.users.bob.pk,)), objects.superusers.admin).data['count'] == 2
|
||||
assert get(reverse('api:user_projects_list', kwargs={'pk':objects.users.alice.pk,}), objects.superusers.admin).data['count'] == 2
|
||||
assert get(reverse('api:user_projects_list', kwargs={'pk':objects.users.bob.pk,}), objects.superusers.admin).data['count'] == 2
|
||||
|
||||
# users can see their own projects
|
||||
assert get(reverse('api:user_projects_list', args=(objects.users.alice.pk,)), objects.users.alice).data['count'] == 2
|
||||
assert get(reverse('api:user_projects_list', kwargs={'pk':objects.users.alice.pk,}), objects.users.alice).data['count'] == 2
|
||||
|
||||
# alice should only be able to see the shared project when looking at bobs projects
|
||||
assert get(reverse('api:user_projects_list', args=(objects.users.bob.pk,)), objects.users.alice).data['count'] == 1
|
||||
assert get(reverse('api:user_projects_list', kwargs={'pk':objects.users.bob.pk,}), objects.users.alice).data['count'] == 1
|
||||
|
||||
# alice should see all projects they can see when viewing an admin
|
||||
assert get(reverse('api:user_projects_list', args=(objects.superusers.admin.pk,)), objects.users.alice).data['count'] == 2
|
||||
assert get(reverse('api:user_projects_list', kwargs={'pk':objects.superusers.admin.pk,}), objects.users.alice).data['count'] == 2
|
||||
|
||||
|
||||
@pytest.mark.django_db
|
||||
@ -139,35 +141,35 @@ def test_team_project_list(get, team_project_list):
|
||||
alice, bob, admin = objects.users.alice, objects.users.bob, objects.superusers.admin
|
||||
|
||||
# admins can see all projects on a team
|
||||
assert get(reverse('api:team_projects_list', args=(team1.pk,)), admin).data['count'] == 2
|
||||
assert get(reverse('api:team_projects_list', args=(team2.pk,)), admin).data['count'] == 2
|
||||
assert get(reverse('api:team_projects_list', kwargs={'pk':team1.pk,}), admin).data['count'] == 2
|
||||
assert get(reverse('api:team_projects_list', kwargs={'pk':team2.pk,}), admin).data['count'] == 2
|
||||
|
||||
# users can see all projects on teams they are a member of
|
||||
assert get(reverse('api:team_projects_list', args=(team1.pk,)), alice).data['count'] == 2
|
||||
assert get(reverse('api:team_projects_list', kwargs={'pk':team1.pk,}), alice).data['count'] == 2
|
||||
|
||||
# but if she does, then she should only see the shared project
|
||||
team2.read_role.members.add(alice)
|
||||
assert get(reverse('api:team_projects_list', args=(team2.pk,)), alice).data['count'] == 1
|
||||
assert get(reverse('api:team_projects_list', kwargs={'pk':team2.pk,}), alice).data['count'] == 1
|
||||
team2.read_role.members.remove(alice)
|
||||
|
||||
# admins can see all projects
|
||||
assert get(reverse('api:user_projects_list', args=(admin.pk,)), admin).data['count'] == 3
|
||||
assert get(reverse('api:user_projects_list', kwargs={'pk':admin.pk,}), admin).data['count'] == 3
|
||||
|
||||
# admins can see everyones projects
|
||||
assert get(reverse('api:user_projects_list', args=(alice.pk,)), admin).data['count'] == 2
|
||||
assert get(reverse('api:user_projects_list', args=(bob.pk,)), admin).data['count'] == 2
|
||||
assert get(reverse('api:user_projects_list', kwargs={'pk':alice.pk,}), admin).data['count'] == 2
|
||||
assert get(reverse('api:user_projects_list', kwargs={'pk':bob.pk,}), admin).data['count'] == 2
|
||||
|
||||
# users can see their own projects
|
||||
assert get(reverse('api:user_projects_list', args=(alice.pk,)), alice).data['count'] == 2
|
||||
assert get(reverse('api:user_projects_list', kwargs={'pk':alice.pk,}), alice).data['count'] == 2
|
||||
|
||||
# alice should see all projects they can see when viewing an admin
|
||||
assert get(reverse('api:user_projects_list', args=(admin.pk,)), alice).data['count'] == 2
|
||||
assert get(reverse('api:user_projects_list', kwargs={'pk':admin.pk,}), alice).data['count'] == 2
|
||||
|
||||
|
||||
@pytest.mark.django_db
|
||||
def test_team_project_list_fail1(get, team_project_list):
|
||||
objects = team_project_list
|
||||
res = get(reverse('api:team_projects_list', args=(objects.teams.team2.pk,)), objects.users.alice)
|
||||
res = get(reverse('api:team_projects_list', kwargs={'pk':objects.teams.team2.pk,}), objects.users.alice)
|
||||
assert res.status_code == 403
|
||||
|
||||
|
||||
@ -210,19 +212,22 @@ def test_create_project_null_organization_xfail(post, organization, org_admin):
|
||||
|
||||
@pytest.mark.django_db()
|
||||
def test_patch_project_null_organization(patch, organization, project, admin):
|
||||
patch(reverse('api:project_detail', args=(project.id,)), { 'name': 't', 'organization': organization.id}, admin, expect=200)
|
||||
patch(reverse('api:project_detail', kwargs={'pk':project.id,}), { 'name': 't', 'organization': organization.id}, admin, expect=200)
|
||||
|
||||
|
||||
@pytest.mark.django_db()
|
||||
def test_patch_project_null_organization_xfail(patch, project, org_admin):
|
||||
patch(reverse('api:project_detail', args=(project.id,)), { 'name': 't', 'organization': None}, org_admin, expect=400)
|
||||
patch(reverse('api:project_detail', kwargs={'pk':project.id,}), { 'name': 't', 'organization': None}, org_admin, expect=400)
|
||||
|
||||
|
||||
@pytest.mark.django_db
|
||||
def test_cannot_schedule_manual_project(project, admin_user, post):
|
||||
response = post(
|
||||
reverse('api:project_schedules_list', args=(project.pk,)),
|
||||
{"name": "foo", "description": "", "enabled": True,
|
||||
reverse('api:project_schedules_list', kwargs={'pk':project.pk,}),
|
||||
{
|
||||
"name": "foo", "description": "", "enabled": True,
|
||||
"rrule": "DTSTART:20160926T040000Z RRULE:FREQ=HOURLY;INTERVAL=1",
|
||||
"extra_data": {}}, admin_user, expect=400)
|
||||
"extra_data": {}
|
||||
}, admin_user, expect=400
|
||||
)
|
||||
assert 'Manual' in response.data['unified_job_template'][0]
|
||||
|
||||
@ -2,7 +2,7 @@ import mock # noqa
|
||||
import pytest
|
||||
|
||||
from django.db import transaction
|
||||
from django.core.urlresolvers import reverse
|
||||
from awx.api.versioning import reverse
|
||||
from awx.main.models.rbac import Role, ROLE_SINGLETON_SYSTEM_ADMINISTRATOR
|
||||
|
||||
|
||||
@ -78,14 +78,14 @@ def test_roles_filter_visibility(get, organization, project, admin, alice, bob):
|
||||
Role.singleton('system_auditor').members.add(alice)
|
||||
project.update_role.members.add(admin)
|
||||
|
||||
assert get(reverse('api:user_roles_list', args=(admin.id,)) + '?id=%d' % project.update_role.id, user=admin).data['count'] == 1
|
||||
assert get(reverse('api:user_roles_list', args=(admin.id,)) + '?id=%d' % project.update_role.id, user=alice).data['count'] == 1
|
||||
assert get(reverse('api:user_roles_list', args=(admin.id,)) + '?id=%d' % project.update_role.id, user=bob).data['count'] == 0
|
||||
assert get(reverse('api:user_roles_list', kwargs={'pk': admin.id}) + '?id=%d' % project.update_role.id, user=admin).data['count'] == 1
|
||||
assert get(reverse('api:user_roles_list', kwargs={'pk': admin.id}) + '?id=%d' % project.update_role.id, user=alice).data['count'] == 1
|
||||
assert get(reverse('api:user_roles_list', kwargs={'pk': admin.id}) + '?id=%d' % project.update_role.id, user=bob).data['count'] == 0
|
||||
organization.auditor_role.members.add(bob)
|
||||
assert get(reverse('api:user_roles_list', args=(admin.id,)) + '?id=%d' % project.update_role.id, user=bob).data['count'] == 1
|
||||
assert get(reverse('api:user_roles_list', kwargs={'pk': admin.id}) + '?id=%d' % project.update_role.id, user=bob).data['count'] == 1
|
||||
organization.auditor_role.members.remove(bob)
|
||||
project.use_role.members.add(bob) # sibling role should still grant visibility
|
||||
assert get(reverse('api:user_roles_list', args=(admin.id,)) + '?id=%d' % project.update_role.id, user=bob).data['count'] == 1
|
||||
assert get(reverse('api:user_roles_list', kwargs={'pk': admin.id}) + '?id=%d' % project.update_role.id, user=bob).data['count'] == 1
|
||||
|
||||
|
||||
@pytest.mark.django_db
|
||||
@ -104,7 +104,7 @@ def test_cant_delete_role(delete, admin):
|
||||
# Some day we might want to do this, but until that is speced out, lets
|
||||
# ensure we don't slip up and allow this implicitly through some helper or
|
||||
# another
|
||||
response = delete(reverse('api:role_detail', args=(admin.admin_role.id,)), admin)
|
||||
response = delete(reverse('api:role_detail', kwargs={'pk': admin.admin_role.id}), admin)
|
||||
assert response.status_code == 405
|
||||
|
||||
|
||||
@ -115,7 +115,7 @@ def test_cant_delete_role(delete, admin):
|
||||
|
||||
@pytest.mark.django_db
|
||||
def test_get_user_roles_list(get, admin):
|
||||
url = reverse('api:user_roles_list', args=(admin.id,))
|
||||
url = reverse('api:user_roles_list', kwargs={'pk': admin.id})
|
||||
response = get(url, admin)
|
||||
assert response.status_code == 200
|
||||
roles = response.data
|
||||
@ -136,7 +136,7 @@ def test_user_view_other_user_roles(organization, inventory, team, get, alice, b
|
||||
# Bob is an org admin, alice can see this.
|
||||
# Bob is in a team that alice is not, alice cannot see that bob is a member of that team.
|
||||
|
||||
url = reverse('api:user_roles_list', args=(bob.id,))
|
||||
url = reverse('api:user_roles_list', kwargs={'pk': bob.id})
|
||||
response = get(url, alice)
|
||||
assert response.status_code == 200
|
||||
roles = response.data
|
||||
@ -171,7 +171,7 @@ def test_user_view_other_user_roles(organization, inventory, team, get, alice, b
|
||||
@pytest.mark.django_db
|
||||
def test_add_role_to_user(role, post, admin):
|
||||
assert admin.roles.filter(id=role.id).count() == 0
|
||||
url = reverse('api:user_roles_list', args=(admin.id,))
|
||||
url = reverse('api:user_roles_list', kwargs={'pk': admin.id})
|
||||
|
||||
response = post(url, {'id': role.id}, admin)
|
||||
assert response.status_code == 204
|
||||
@ -189,7 +189,7 @@ def test_add_role_to_user(role, post, admin):
|
||||
@pytest.mark.django_db
|
||||
def test_remove_role_from_user(role, post, admin):
|
||||
assert admin.roles.filter(id=role.id).count() == 0
|
||||
url = reverse('api:user_roles_list', args=(admin.id,))
|
||||
url = reverse('api:user_roles_list', kwargs={'pk': admin.id})
|
||||
response = post(url, {'id': role.id}, admin)
|
||||
assert response.status_code == 204
|
||||
assert admin.roles.filter(id=role.id).count() == 1
|
||||
@ -207,7 +207,7 @@ def test_remove_role_from_user(role, post, admin):
|
||||
@pytest.mark.django_db
|
||||
def test_get_teams_roles_list(get, team, organization, admin):
|
||||
team.member_role.children.add(organization.admin_role)
|
||||
url = reverse('api:team_roles_list', args=(team.id,))
|
||||
url = reverse('api:team_roles_list', kwargs={'pk': team.id})
|
||||
response = get(url, admin)
|
||||
assert response.status_code == 200
|
||||
roles = response.data
|
||||
@ -219,7 +219,7 @@ def test_get_teams_roles_list(get, team, organization, admin):
|
||||
@pytest.mark.django_db
|
||||
def test_add_role_to_teams(team, post, admin):
|
||||
assert team.member_role.children.filter(id=team.member_role.id).count() == 0
|
||||
url = reverse('api:team_roles_list', args=(team.id,))
|
||||
url = reverse('api:team_roles_list', kwargs={'pk': team.id})
|
||||
|
||||
response = post(url, {'id': team.member_role.id}, admin)
|
||||
assert response.status_code == 204
|
||||
@ -237,7 +237,7 @@ def test_add_role_to_teams(team, post, admin):
|
||||
@pytest.mark.django_db
|
||||
def test_remove_role_from_teams(team, post, admin):
|
||||
assert team.member_role.children.filter(id=team.member_role.id).count() == 0
|
||||
url = reverse('api:team_roles_list', args=(team.id,))
|
||||
url = reverse('api:team_roles_list', kwargs={'pk': team.id})
|
||||
response = post(url, {'id': team.member_role.id}, admin)
|
||||
assert response.status_code == 204
|
||||
assert team.member_role.children.filter(id=team.member_role.id).count() == 1
|
||||
@ -254,7 +254,7 @@ def test_remove_role_from_teams(team, post, admin):
|
||||
|
||||
@pytest.mark.django_db
|
||||
def test_get_role(get, admin, role):
|
||||
url = reverse('api:role_detail', args=(role.id,))
|
||||
url = reverse('api:role_detail', kwargs={'pk': role.id})
|
||||
response = get(url, admin)
|
||||
assert response.status_code == 200
|
||||
assert response.data['id'] == role.id
|
||||
@ -262,7 +262,7 @@ def test_get_role(get, admin, role):
|
||||
|
||||
@pytest.mark.django_db
|
||||
def test_put_role_405(put, admin, role):
|
||||
url = reverse('api:role_detail', args=(role.id,))
|
||||
url = reverse('api:role_detail', kwargs={'pk': role.id})
|
||||
response = put(url, {'name': 'Some new name'}, admin)
|
||||
assert response.status_code == 405
|
||||
#r = Role.objects.get(id=role.id)
|
||||
@ -271,7 +271,7 @@ def test_put_role_405(put, admin, role):
|
||||
|
||||
@pytest.mark.django_db
|
||||
def test_put_role_access_denied(put, alice, role):
|
||||
url = reverse('api:role_detail', args=(role.id,))
|
||||
url = reverse('api:role_detail', kwargs={'pk': role.id})
|
||||
response = put(url, {'name': 'Some new name'}, alice)
|
||||
assert response.status_code == 403 or response.status_code == 405
|
||||
|
||||
@ -284,7 +284,7 @@ def test_put_role_access_denied(put, alice, role):
|
||||
@pytest.mark.django_db
|
||||
def test_get_role_users(get, admin, role):
|
||||
role.members.add(admin)
|
||||
url = reverse('api:role_users_list', args=(role.id,))
|
||||
url = reverse('api:role_users_list', kwargs={'pk': role.id})
|
||||
response = get(url, admin)
|
||||
assert response.status_code == 200
|
||||
assert response.data['count'] == 1
|
||||
@ -293,7 +293,7 @@ def test_get_role_users(get, admin, role):
|
||||
|
||||
@pytest.mark.django_db
|
||||
def test_add_user_to_role(post, admin, role):
|
||||
url = reverse('api:role_users_list', args=(role.id,))
|
||||
url = reverse('api:role_users_list', kwargs={'pk': role.id})
|
||||
assert role.members.filter(id=admin.id).count() == 0
|
||||
post(url, {'id': admin.id}, admin)
|
||||
assert role.members.filter(id=admin.id).count() == 1
|
||||
@ -302,7 +302,7 @@ def test_add_user_to_role(post, admin, role):
|
||||
@pytest.mark.django_db
|
||||
def test_remove_user_to_role(post, admin, role):
|
||||
role.members.add(admin)
|
||||
url = reverse('api:role_users_list', args=(role.id,))
|
||||
url = reverse('api:role_users_list', kwargs={'pk': role.id})
|
||||
assert role.members.filter(id=admin.id).count() == 1
|
||||
post(url, {'disassociate': True, 'id': admin.id}, admin)
|
||||
assert role.members.filter(id=admin.id).count() == 0
|
||||
@ -318,7 +318,7 @@ def test_org_admin_add_user_to_job_template(post, organization, check_jobtemplat
|
||||
assert org_admin in check_jobtemplate.admin_role
|
||||
assert joe not in check_jobtemplate.execute_role
|
||||
|
||||
post(reverse('api:role_users_list', args=(check_jobtemplate.execute_role.id,)), {'id': joe.id}, org_admin)
|
||||
post(reverse('api:role_users_list', kwargs={'pk': check_jobtemplate.execute_role.id}), {'id': joe.id}, org_admin)
|
||||
assert joe in check_jobtemplate.execute_role
|
||||
|
||||
|
||||
@ -333,7 +333,7 @@ def test_org_admin_remove_user_from_job_template(post, organization, check_jobte
|
||||
assert org_admin in check_jobtemplate.admin_role
|
||||
assert joe in check_jobtemplate.execute_role
|
||||
|
||||
post(reverse('api:role_users_list', args=(check_jobtemplate.execute_role.id,)), {'disassociate': True, 'id': joe.id}, org_admin)
|
||||
post(reverse('api:role_users_list', kwargs={'pk': check_jobtemplate.execute_role.id}), {'disassociate': True, 'id': joe.id}, org_admin)
|
||||
assert joe not in check_jobtemplate.execute_role
|
||||
|
||||
|
||||
@ -347,7 +347,7 @@ def test_user_fail_to_add_user_to_job_template(post, organization, check_jobtemp
|
||||
assert joe not in check_jobtemplate.execute_role
|
||||
|
||||
with transaction.atomic():
|
||||
res = post(reverse('api:role_users_list', args=(check_jobtemplate.execute_role.id,)), {'id': joe.id}, rando)
|
||||
res = post(reverse('api:role_users_list', kwargs={'pk': check_jobtemplate.execute_role.id}), {'id': joe.id}, rando)
|
||||
assert res.status_code == 403
|
||||
|
||||
assert joe not in check_jobtemplate.execute_role
|
||||
@ -364,7 +364,7 @@ def test_user_fail_to_remove_user_to_job_template(post, organization, check_jobt
|
||||
assert joe in check_jobtemplate.execute_role
|
||||
|
||||
with transaction.atomic():
|
||||
res = post(reverse('api:role_users_list', args=(check_jobtemplate.execute_role.id,)), {'disassociate': True, 'id': joe.id}, rando)
|
||||
res = post(reverse('api:role_users_list', kwargs={'pk': check_jobtemplate.execute_role.id}), {'disassociate': True, 'id': joe.id}, rando)
|
||||
assert res.status_code == 403
|
||||
|
||||
assert joe in check_jobtemplate.execute_role
|
||||
@ -378,7 +378,7 @@ def test_user_fail_to_remove_user_to_job_template(post, organization, check_jobt
|
||||
@pytest.mark.django_db
|
||||
def test_get_role_teams(get, team, admin, role):
|
||||
role.parents.add(team.member_role)
|
||||
url = reverse('api:role_teams_list', args=(role.id,))
|
||||
url = reverse('api:role_teams_list', kwargs={'pk': role.id})
|
||||
response = get(url, admin)
|
||||
assert response.status_code == 200
|
||||
assert response.data['count'] == 1
|
||||
@ -387,7 +387,7 @@ def test_get_role_teams(get, team, admin, role):
|
||||
|
||||
@pytest.mark.django_db
|
||||
def test_add_team_to_role(post, team, admin, role):
|
||||
url = reverse('api:role_teams_list', args=(role.id,))
|
||||
url = reverse('api:role_teams_list', kwargs={'pk': role.id})
|
||||
assert role.members.filter(id=admin.id).count() == 0
|
||||
res = post(url, {'id': team.id}, admin)
|
||||
assert res.status_code == 204
|
||||
@ -397,7 +397,7 @@ def test_add_team_to_role(post, team, admin, role):
|
||||
@pytest.mark.django_db
|
||||
def test_remove_team_from_role(post, team, admin, role):
|
||||
role.members.add(admin)
|
||||
url = reverse('api:role_teams_list', args=(role.id,))
|
||||
url = reverse('api:role_teams_list', kwargs={'pk': role.id})
|
||||
assert role.members.filter(id=admin.id).count() == 1
|
||||
res = post(url, {'disassociate': True, 'id': team.id}, admin)
|
||||
assert res.status_code == 204
|
||||
@ -412,7 +412,7 @@ def test_remove_team_from_role(post, team, admin, role):
|
||||
@pytest.mark.django_db
|
||||
def test_role_parents(get, team, admin, role):
|
||||
role.parents.add(team.member_role)
|
||||
url = reverse('api:role_parents_list', args=(role.id,))
|
||||
url = reverse('api:role_parents_list', kwargs={'pk': role.id})
|
||||
response = get(url, admin)
|
||||
assert response.status_code == 200
|
||||
assert response.data['count'] == 1
|
||||
@ -427,7 +427,7 @@ def test_role_parents(get, team, admin, role):
|
||||
@pytest.mark.django_db
|
||||
def test_role_children(get, team, admin, role):
|
||||
role.parents.add(team.member_role)
|
||||
url = reverse('api:role_children_list', args=(team.member_role.id,))
|
||||
url = reverse('api:role_children_list', kwargs={'pk': team.member_role.id})
|
||||
response = get(url, admin)
|
||||
assert response.status_code == 200
|
||||
assert response.data['count'] == 2
|
||||
@ -441,7 +441,7 @@ def test_role_children(get, team, admin, role):
|
||||
|
||||
@pytest.mark.django_db
|
||||
def test_ensure_rbac_fields_are_present(organization, get, admin):
|
||||
url = reverse('api:organization_detail', args=(organization.id,))
|
||||
url = reverse('api:organization_detail', kwargs={'pk': organization.id})
|
||||
response = get(url, admin)
|
||||
assert response.status_code == 200
|
||||
org = response.data
|
||||
@ -450,7 +450,7 @@ def test_ensure_rbac_fields_are_present(organization, get, admin):
|
||||
assert 'object_roles' in org['summary_fields']
|
||||
|
||||
role_pk = org['summary_fields']['object_roles']['admin_role']['id']
|
||||
role_url = reverse('api:role_detail', args=(role_pk,))
|
||||
role_url = reverse('api:role_detail', kwargs={'pk': role_pk})
|
||||
org_role_response = get(role_url, admin)
|
||||
|
||||
assert org_role_response.status_code == 200
|
||||
@ -460,7 +460,7 @@ def test_ensure_rbac_fields_are_present(organization, get, admin):
|
||||
|
||||
@pytest.mark.django_db
|
||||
def test_ensure_role_summary_is_present(organization, get, user):
|
||||
url = reverse('api:organization_detail', args=(organization.id,))
|
||||
url = reverse('api:organization_detail', kwargs={'pk': organization.id})
|
||||
response = get(url, user('admin', True))
|
||||
assert response.status_code == 200
|
||||
org = response.data
|
||||
|
||||
@ -1,6 +1,7 @@
|
||||
import mock
|
||||
import pytest
|
||||
|
||||
from awx.api.versioning import reverse
|
||||
from awx.main.access import (
|
||||
BaseAccess,
|
||||
JobTemplateAccess,
|
||||
@ -12,7 +13,6 @@ from awx.main.models.jobs import JobTemplate
|
||||
from awx.main.models.schedules import Schedule
|
||||
from django.apps import apps
|
||||
|
||||
from django.core.urlresolvers import reverse
|
||||
|
||||
|
||||
@pytest.fixture
|
||||
@ -250,7 +250,7 @@ def test_job_template_creator_access(project, rando, post):
|
||||
with mock.patch(
|
||||
'awx.main.models.projects.ProjectOptions.playbooks',
|
||||
new_callable=mock.PropertyMock(return_value=['helloworld.yml'])):
|
||||
response = post(reverse('api:job_template_list', args=[]), dict(
|
||||
response = post(reverse('api:job_template_list'), dict(
|
||||
name='newly-created-jt',
|
||||
job_type='run',
|
||||
ask_inventory_on_launch=True,
|
||||
|
||||
@ -6,7 +6,7 @@ import pytest
|
||||
def get_related_assert():
|
||||
def fn(model_obj, related, resource_name, related_resource_name):
|
||||
assert related_resource_name in related
|
||||
assert related[related_resource_name] == '/api/v1/%s/%d/%s/' % (resource_name, model_obj.pk, related_resource_name)
|
||||
assert related[related_resource_name] == '/api/v2/%s/%d/%s/' % (resource_name, model_obj.pk, related_resource_name)
|
||||
return fn
|
||||
|
||||
|
||||
|
||||
@ -68,7 +68,7 @@ class TestJobSerializerGetRelated():
|
||||
def test_job_template_present(self, get_related_mock_and_run, job):
|
||||
related = get_related_mock_and_run(JobSerializer, job)
|
||||
assert 'job_template' in related
|
||||
assert related['job_template'] == '/api/v1/%s/%d/' % ('job_templates', job.job_template.pk)
|
||||
assert related['job_template'] == '/api/v2/%s/%d/' % ('job_templates', job.job_template.pk)
|
||||
|
||||
|
||||
@mock.patch('awx.api.serializers.BaseSerializer.to_representation', lambda self,obj: {
|
||||
|
||||
@ -104,7 +104,7 @@ class TestJobTemplateSerializerGetSummaryFields():
|
||||
serializer.show_capabilities = ['copy', 'edit']
|
||||
serializer._summary_field_labels = lambda self: []
|
||||
serializer._recent_jobs = lambda self: []
|
||||
request = APIRequestFactory().get('/api/v1/job_templates/42/')
|
||||
request = APIRequestFactory().get('/api/v2/job_templates/42/')
|
||||
request.user = user
|
||||
view = JobTemplateDetail()
|
||||
view.request = request
|
||||
|
||||
@ -56,7 +56,7 @@ class TestWorkflowNodeBaseSerializerGetRelated():
|
||||
def test_workflow_unified_job_template_present(self, get_related_mock_and_run, workflow_job_template_node_related):
|
||||
related = get_related_mock_and_run(WorkflowNodeBaseSerializer, workflow_job_template_node_related)
|
||||
assert 'unified_job_template' in related
|
||||
assert related['unified_job_template'] == '/api/v1/%s/%d/' % ('job_templates', workflow_job_template_node_related.unified_job_template.pk)
|
||||
assert related['unified_job_template'] == '/api/v2/%s/%d/' % ('job_templates', workflow_job_template_node_related.unified_job_template.pk)
|
||||
|
||||
def test_workflow_unified_job_template_absent(self, workflow_job_template_node):
|
||||
related = WorkflowJobTemplateNodeSerializer().get_related(workflow_job_template_node)
|
||||
@ -100,7 +100,7 @@ class TestWorkflowJobTemplateNodeSerializerGetRelated():
|
||||
def test_workflow_job_template_present(self, get_related_mock_and_run, workflow_job_template_node_related):
|
||||
related = get_related_mock_and_run(WorkflowJobTemplateNodeSerializer, workflow_job_template_node_related)
|
||||
assert 'workflow_job_template' in related
|
||||
assert related['workflow_job_template'] == '/api/v1/%s/%d/' % ('workflow_job_templates', workflow_job_template_node_related.workflow_job_template.pk)
|
||||
assert related['workflow_job_template'] == '/api/v2/%s/%d/' % ('workflow_job_templates', workflow_job_template_node_related.workflow_job_template.pk)
|
||||
|
||||
def test_workflow_job_template_absent(self, workflow_job_template_node):
|
||||
related = WorkflowJobTemplateNodeSerializer().get_related(workflow_job_template_node)
|
||||
@ -179,7 +179,7 @@ class TestWorkflowJobNodeSerializerGetRelated():
|
||||
def test_workflow_job_present(self, get_related_mock_and_run, workflow_job_node_related):
|
||||
related = get_related_mock_and_run(WorkflowJobNodeSerializer, workflow_job_node_related)
|
||||
assert 'workflow_job' in related
|
||||
assert related['workflow_job'] == '/api/v1/%s/%d/' % ('workflow_jobs', workflow_job_node_related.workflow_job.pk)
|
||||
assert related['workflow_job'] == '/api/v2/%s/%d/' % ('workflow_jobs', workflow_job_node_related.workflow_job.pk)
|
||||
|
||||
def test_workflow_job_absent(self, workflow_job_node):
|
||||
related = WorkflowJobNodeSerializer().get_related(workflow_job_node)
|
||||
@ -188,7 +188,7 @@ class TestWorkflowJobNodeSerializerGetRelated():
|
||||
def test_job_present(self, get_related_mock_and_run, workflow_job_node_related):
|
||||
related = get_related_mock_and_run(WorkflowJobNodeSerializer, workflow_job_node_related)
|
||||
assert 'job' in related
|
||||
assert related['job'] == '/api/v1/%s/%d/' % ('jobs', workflow_job_node_related.job.pk)
|
||||
assert related['job'] == '/api/v2/%s/%d/' % ('jobs', workflow_job_node_related.job.pk)
|
||||
|
||||
def test_job_absent(self, workflow_job_node):
|
||||
related = WorkflowJobNodeSerializer().get_related(workflow_job_node)
|
||||
|
||||
@ -4,7 +4,7 @@ import pytest
|
||||
from collections import namedtuple
|
||||
|
||||
from awx.api.views import (
|
||||
ApiV1RootView,
|
||||
ApiVersionRootView,
|
||||
JobTemplateLabelList,
|
||||
JobTemplateSurveySpec,
|
||||
)
|
||||
@ -17,7 +17,7 @@ def mock_response_new(mocker):
|
||||
return m
|
||||
|
||||
|
||||
class TestApiV1RootView:
|
||||
class TestApiRootView:
|
||||
def test_get_endpoints(self, mocker, mock_response_new):
|
||||
endpoints = [
|
||||
'authtoken',
|
||||
@ -51,7 +51,7 @@ class TestApiV1RootView:
|
||||
'workflow_job_templates',
|
||||
'workflow_jobs',
|
||||
]
|
||||
view = ApiV1RootView()
|
||||
view = ApiVersionRootView()
|
||||
ret = view.get(mocker.MagicMock())
|
||||
|
||||
assert ret == mock_response_new
|
||||
|
||||
@ -12,7 +12,6 @@ from awx.main.utils.common import ( # noqa
|
||||
encrypt_field,
|
||||
parse_yaml_or_json,
|
||||
decrypt_field,
|
||||
build_url,
|
||||
timestamp_apiformat,
|
||||
model_instance_diff,
|
||||
model_to_dict,
|
||||
|
||||
@ -31,7 +31,6 @@ from django.db.models import ManyToManyField
|
||||
from rest_framework.exceptions import ParseError, PermissionDenied
|
||||
from django.utils.encoding import smart_str
|
||||
from django.utils.text import slugify
|
||||
from django.core.urlresolvers import reverse
|
||||
from django.apps import apps
|
||||
|
||||
# PyCrypto
|
||||
@ -736,14 +735,6 @@ def get_pk_from_dict(_dict, key):
|
||||
return None
|
||||
|
||||
|
||||
def build_url(*args, **kwargs):
|
||||
get = kwargs.pop('get', {})
|
||||
url = reverse(*args, **kwargs)
|
||||
if get:
|
||||
url += '?' + urllib.urlencode(get)
|
||||
return url
|
||||
|
||||
|
||||
def timestamp_apiformat(timestamp):
|
||||
timestamp = timestamp.isoformat()
|
||||
if timestamp.endswith('+00:00'):
|
||||
|
||||
@ -34,7 +34,7 @@
|
||||
<div class="collapse navbar-collapse" id="navbar-collapse">
|
||||
<ul class="nav navbar-nav navbar-right">
|
||||
{% if user.is_authenticated %}
|
||||
<li><a href="{% url 'api:user_me_list' %}" data-toggle="tooltip" data-placement="bottom" data-delay="1000" title="Logged in as {{ user }}{% if user.get_full_name %} ({{ user.get_full_name }}){% endif %}"><span class="glyphicon glyphicon-user"></span> <span class="visible-xs-inline">Logged in as </span>{{ user }}{% if user.get_full_name %}<span class="visible-xs-inline"> ({{ user.get_full_name }})</span>{% endif %}</a></li>
|
||||
<li><a href="{% url 'api:user_me_list' version=request.version %}" data-toggle="tooltip" data-placement="bottom" data-delay="1000" title="Logged in as {{ user }}{% if user.get_full_name %} ({{ user.get_full_name }}){% endif %}"><span class="glyphicon glyphicon-user"></span> <span class="visible-xs-inline">Logged in as </span>{{ user }}{% if user.get_full_name %}<span class="visible-xs-inline"> ({{ user.get_full_name }})</span>{% endif %}</a></li>
|
||||
{% endif %}
|
||||
<li><a href="//docs.ansible.com/ansible-tower/{{short_tower_version}}/html/towerapi/index.html" target="_blank" data-toggle="tooltip" data-placement="bottom" data-delay="1000" title="{% trans 'Ansible Tower API Guide' %}"><span class="glyphicon glyphicon-question-sign"></span><span class="visible-xs-inline">{% trans 'Ansible Tower API Guide' %}</span></a></li>
|
||||
<li><a href="/" data-toggle="tooltip" data-placement="bottom" data-delay="1000" title="{% trans 'Back to Ansible Tower' %}"><span class="glyphicon glyphicon-circle-arrow-left"></span><span class="visible-xs-inline">{% trans 'Back to Ansible Tower' %}</span></a></li>
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user