def test_slugify(self): """Test additional slugify""" self.assertEqual(slugify('This is a test'), 'this-is-a-test') self.assertEqual(slugify('project_with_underscores-v.1.0'), 'project-with-underscores-v10') self.assertEqual(slugify('project_with_underscores-v.1.0', dns_safe=False), 'project_with_underscores-v10') self.assertEqual(slugify('A title_-_with separated parts'), 'a-title-with-separated-parts') self.assertEqual(slugify('A title_-_with separated parts', dns_safe=False), 'a-title_-_with-separated-parts')
def test_slugify(self): """Test additional slugify""" self.assertEqual(slugify('This is a test'), 'this-is-a-test') self.assertEqual(slugify('project_with_underscores-v.1.0'), 'project-with-underscores-v10') self.assertEqual(slugify('project_with_underscores-v.1.0', dns_safe=False), 'project_with_underscores-v10') self.assertEqual(slugify('A title_-_with separated parts'), 'a-title-with-separated-parts') self.assertEqual(slugify('A title_-_with separated parts', dns_safe=False), 'a-title_-_with-separated-parts')
def __init__(self, *args, **kwargs): self.docker_socket = kwargs.pop('docker_socket', DOCKER_SOCKET) super().__init__(*args, **kwargs) self.client = None self.container = None self.container_name = slugify( 'build-{build}-project-{project_id}-{project_name}'.format( build=self.build.get('id'), project_id=self.project.pk, project_name=self.project.slug, )[:DOCKER_HOSTNAME_MAX_LEN], ) # Decide what Docker image to use, based on priorities: # Use the Docker image set by our feature flag: ``testing`` or, if self.project.has_feature(Feature.USE_TESTING_BUILD_IMAGE): self.container_image = 'readthedocs/build:testing' # the image set by user or, if self.config and self.config.build.image: self.container_image = self.config.build.image # the image overridden by the project (manually set by an admin). if self.project.container_image: self.container_image = self.project.container_image if self.project.container_mem_limit: self.container_mem_limit = self.project.container_mem_limit if self.project.container_time_limit: self.container_time_limit = self.project.container_time_limit
def __init__(self, *args, **kwargs): self.docker_socket = kwargs.pop('docker_socket', DOCKER_SOCKET) super().__init__(*args, **kwargs) self.client = None self.container = None self.container_name = slugify( 'build-{build}-project-{project_id}-{project_name}'.format( build=self.build.get('id'), project_id=self.project.pk, project_name=self.project.slug, )[:DOCKER_HOSTNAME_MAX_LEN], ) # Decide what Docker image to use, based on priorities: # Use the Docker image set by our feature flag: ``testing`` or, if self.project.has_feature(Feature.USE_TESTING_BUILD_IMAGE): self.container_image = 'readthedocs/build:testing' # the image set by user or, if self.config and self.config.build.image: self.container_image = self.config.build.image # the image overridden by the project (manually set by an admin). if self.project.container_image: self.container_image = self.project.container_image if self.project.container_mem_limit: self.container_mem_limit = self.project.container_mem_limit if self.project.container_time_limit: self.container_time_limit = self.project.container_time_limit
def validate_name(self, value): potential_slug = slugify(value) if Project.objects.filter(slug=potential_slug).exists(): raise serializers.ValidationError( _('Project with slug "{0}" already exists.').format( potential_slug), ) return value
def save(self, *args, **kwargs): # pylint: disable=arguments-differ from readthedocs.projects import tasks first_save = self.pk is None if not self.slug: # Subdomains can't have underscores in them. self.slug = slugify(self.name) if not self.slug: raise Exception(_('Model must have slug')) super().save(*args, **kwargs) for owner in self.users.all(): assign('view_project', owner, self) try: latest = self.versions.filter(slug=LATEST).first() default_branch = self.get_default_branch() if latest and latest.identifier != default_branch: latest.identifier = default_branch latest.save() except Exception: log.exception('Failed to update latest identifier') try: if not first_save: log.info( 'Re-symlinking project and subprojects: project=%s', self.slug, ) broadcast( type='app', task=tasks.symlink_project, args=[self.pk], ) log.info( 'Re-symlinking superprojects: project=%s', self.slug, ) for relationship in self.superprojects.all(): broadcast( type='app', task=tasks.symlink_project, args=[relationship.parent.pk], ) except Exception: log.exception('failed to symlink project') try: if not first_save: broadcast( type='app', task=tasks.update_static_metadata, args=[self.pk], ) except Exception: log.exception('failed to update static metadata') try: branch = self.default_branch or self.vcs_repo().fallback_branch if not self.versions.filter(slug=LATEST).exists(): self.versions.create_latest(identifier=branch) except Exception: log.exception('Error creating default branches')
def clean_name(self): name = self.cleaned_data.get('name', '') if not self.instance.pk: potential_slug = slugify(name) if Project.objects.filter(slug=potential_slug).exists(): raise forms.ValidationError( _('Invalid project name, a project already exists with that name')) return name
def clean_name(self): name = self.cleaned_data.get('name', '') if not self.instance.pk: potential_slug = slugify(name) if Project.objects.filter(slug=potential_slug).exists(): raise forms.ValidationError( _('Invalid project name, a project already exists with that name')) # yapf: disable # noqa return name
def clean_name(self): """Raise exception on duplicate organization.""" name = self.cleaned_data['name'] if self.instance and self.instance.name and name == self.instance.name: return name if Organization.objects.filter(slug=slugify(name)).exists(): raise forms.ValidationError( _('Organization %(name)s already exists'), params={'name': name}, ) return name
def get_container_name(self): if self.build: name = 'build-{build}-project-{project_id}-{project_name}'.format( build=self.build.get('id'), project_id=self.project.pk, project_name=self.project.slug, ) else: # An uuid is added, so the container name is unique per sync. uuid_ = uuid.uuid4().hex[:8] name = f'sync-{uuid_}-project-{self.project.pk}-{self.project.slug}' return slugify(name[:DOCKER_HOSTNAME_MAX_LEN])
def clean_name(self): name = self.cleaned_data.get('name', '') if not self.instance.pk: potential_slug = slugify(name) if Project.objects.filter(slug=potential_slug).exists(): raise forms.ValidationError( _('Invalid project name, a project already exists with that name'), ) # yapf: disable # noqa if not potential_slug: # Check the generated slug won't be empty raise forms.ValidationError(_('Invalid project name'),) return name
def save(self, *args, **kwargs): # pylint: disable=arguments-differ from readthedocs.projects import tasks first_save = self.pk is None if not self.slug: # Subdomains can't have underscores in them. self.slug = slugify(self.name) if self.slug == '': raise Exception(_('Model must have slug')) super(Project, self).save(*args, **kwargs) for owner in self.users.all(): assign('view_project', owner, self) try: if self.default_branch: latest = self.versions.get(slug=LATEST) if latest.identifier != self.default_branch: latest.identifier = self.default_branch latest.save() except Exception: log.exception('Failed to update latest identifier') # Add exceptions here for safety try: self.sync_supported_versions() except Exception: log.exception('failed to sync supported versions') try: if not first_save: broadcast( type='app', task=tasks.symlink_project, args=[self.pk], ) except Exception: log.exception('failed to symlink project') try: if not first_save: broadcast( type='app', task=tasks.update_static_metadata, args=[self.pk], ) except Exception: log.exception('failed to update static metadata') try: branch = self.default_branch or self.vcs_repo().fallback_branch if not self.versions.filter(slug=LATEST).exists(): self.versions.create_latest(identifier=branch) except Exception: log.exception('Error creating default branches')
def __init__(self, *args, **kwargs): self.docker_socket = kwargs.pop('docker_socket', DOCKER_SOCKET) super(DockerEnvironment, self).__init__(*args, **kwargs) self.client = None self.container = None self.container_name = slugify( 'build-{build}-project-{project_id}-{project_name}'.format( build=self.build.get('id'), project_id=self.project.pk, project_name=self.project.slug, )[:DOCKER_HOSTNAME_MAX_LEN]) if self.project.container_mem_limit: self.container_mem_limit = self.project.container_mem_limit if self.project.container_time_limit: self.container_time_limit = self.project.container_time_limit
def clean_name(self): """Raise exception on duplicate organization slug.""" name = self.cleaned_data['name'] # Skip slug validation on already created organizations. if self.instance.pk: return name potential_slug = slugify(name) if not potential_slug: raise forms.ValidationError(_('Invalid organization name: no slug generated')) if Organization.objects.filter(slug=potential_slug).exists(): raise forms.ValidationError( _('Organization %(name)s already exists'), params={'name': name}, ) return name
def __init__(self, *args, **kwargs): self.docker_socket = kwargs.pop('docker_socket', DOCKER_SOCKET) super(DockerBuildEnvironment, self).__init__(*args, **kwargs) self.client = None self.container = None self.container_name = slugify( 'build-{build}-project-{project_id}-{project_name}'.format( build=self.build.get('id'), project_id=self.project.pk, project_name=self.project.slug, )[:DOCKER_HOSTNAME_MAX_LEN] ) if self.config and self.config.build_image: self.container_image = self.config.build_image if self.project.container_image: self.container_image = self.project.container_image if self.project.container_mem_limit: self.container_mem_limit = self.project.container_mem_limit if self.project.container_time_limit: self.container_time_limit = self.project.container_time_limit
def test_change_name(self): """ Changing the name of the organization won't change the slug. So changing it to something that will generate an existing slug shouldn't matter. """ new_name = 'Test Org' org_slug = self.organization.slug self.assertNotEqual(new_name, self.organization.name) self.assertEqual(slugify(new_name), org_slug) resp = self.client.post( reverse('organization_edit', args=[self.organization.slug]), data={'name': new_name}, ) self.assertEqual(resp.status_code, 302) self.organization.refresh_from_db() self.assertEqual(self.organization.name, new_name) self.assertEqual(self.organization.slug, org_slug)
def save(self, *args, **kwargs): # pylint: disable=arguments-differ from readthedocs.projects import tasks first_save = self.pk is None if not self.slug: # Subdomains can't have underscores in them. self.slug = slugify(self.name) if self.slug == '': raise Exception(_("Model must have slug")) super(Project, self).save(*args, **kwargs) for owner in self.users.all(): assign('view_project', owner, self) try: if self.default_branch: latest = self.versions.get(slug=LATEST) if latest.identifier != self.default_branch: latest.identifier = self.default_branch latest.save() except Exception: log.exception('Failed to update latest identifier') # Add exceptions here for safety try: self.sync_supported_versions() except Exception: log.exception('failed to sync supported versions') try: if not first_save: broadcast(type='app', task=tasks.symlink_project, args=[self.pk]) except Exception: log.exception('failed to symlink project') try: if not first_save: broadcast(type='app', task=tasks.update_static_metadata, args=[self.pk]) except Exception: log.exception('failed to update static metadata') try: branch = self.default_branch or self.vcs_repo().fallback_branch if not self.versions.filter(slug=LATEST).exists(): self.versions.create_latest(identifier=branch) except Exception: log.exception('Error creating default branches')
def save(self, *args, **kwargs): # pylint: disable=signature-differs if not self.slug: self.slug = slugify(self.name) super().save(*args, **kwargs)
def save(self, *args, **kwargs): # pylint: disable=arguments-differ if not self.slug: self.slug = slugify(self.name) super().save(*args, **kwargs)
def save(self, *args, **kwargs): # pylint: disable=arguments-differ from readthedocs.projects import tasks first_save = self.pk is None if not self.slug: # Subdomains can't have underscores in them. self.slug = slugify(self.name) if not self.slug: raise Exception(_('Model must have slug')) if self.documentation_type == 'auto': # This used to determine the type and automatically set the # documentation type to Sphinx for rST and Mkdocs for markdown. # It now just forces Sphinx, due to markdown support. self.documentation_type = 'sphinx' super(Project, self).save(*args, **kwargs) for owner in self.users.all(): assign('view_project', owner, self) try: latest = self.versions.filter(slug=LATEST).first() default_branch = self.get_default_branch() if latest and latest.identifier != default_branch: latest.identifier = default_branch latest.save() except Exception: log.exception('Failed to update latest identifier') # Add exceptions here for safety try: self.sync_supported_versions() except Exception: log.exception('failed to sync supported versions') try: if not first_save: log.info( 'Re-symlinking project and subprojects: project=%s', self.slug, ) broadcast( type='app', task=tasks.symlink_project, args=[self.pk], ) log.info( 'Re-symlinking superprojects: project=%s', self.slug, ) for relationship in self.superprojects.all(): broadcast( type='app', task=tasks.symlink_project, args=[relationship.parent.pk], ) except Exception: log.exception('failed to symlink project') try: if not first_save: broadcast( type='app', task=tasks.update_static_metadata, args=[self.pk], ) except Exception: log.exception('failed to update static metadata') try: branch = self.default_branch or self.vcs_repo().fallback_branch if not self.versions.filter(slug=LATEST).exists(): self.versions.create_latest(identifier=branch) except Exception: log.exception('Error creating default branches')