Exemplo n.º 1
0
def test_validate_argument_column_mapping():
    table_stub = pretend.stub(columns=(
        pretend.stub(key="foo"),
        pretend.stub(key="bar"),
    ),
                              name="foobartable")
    with pytest.raises(TypeError):
        db.validate_argument_column_mapping("baz", table_stub)
Exemplo n.º 2
0
def test_validate_argument_column_mapping():
    table_stub = pretend.stub(
        columns=(
            pretend.stub(key="foo"),
            pretend.stub(key="bar"),
        ),
        name="foobartable"
    )
    with pytest.raises(TypeError):
        db.validate_argument_column_mapping("baz", table_stub)
Exemplo n.º 3
0
    def upsert_project(self, name, username, user_ip, **additional_columns):
        # NOTE: pypi behaviour is to assign the first submitter of a
        # project the "owner" role. this code does not
        # perform that behaviour (implement in the view instead)
        db.validate_argument_column_mapping(additional_columns, packages)

        existing_project = self.get_project(name)

        if existing_project:
            message = "updating project {0}".format(existing_project['name'])
            query = (packages.update().where(
                packages.c.name == existing_project['name']))
        else:
            message = "create"
            query = packages.insert()

        self.engine.execute(
            query.values(name=name,
                         normalized_name=utils.normalize_project_name(name),
                         **additional_columns))

        self._insert_journal_entry(name, None, message, username, user_ip)
Exemplo n.º 4
0
    def upsert_project(self, name, username, user_ip, **additional_columns):
        # NOTE: pypi behaviour is to assign the first submitter of a
        # project the "owner" role. this code does not
        # perform that behaviour (implement in the view instead)
        db.validate_argument_column_mapping(additional_columns, packages)

        existing_project = self.get_project(name)

        if existing_project:
            message = "updating project {0}".format(existing_project['name'])
            query = (packages.update()
                     .where(packages.c.name == existing_project['name']))
        else:
            message = "create"
            query = packages.insert()

        self.engine.execute(query.values(
            name=name,
            normalized_name=utils.normalize_project_name(name),
            **additional_columns
        ))

        self._insert_journal_entry(name, None, message, username, user_ip)
Exemplo n.º 5
0
    def upsert_release(self, project_name, version, username, user_ip,
                       classifiers=None, release_dependencies=None,
                       description=None, **additional_db_values):
        """
        Takes in the following:

        * project_name: the name of the package to insert
        * version: the version of the package to insert
        * username: username of the user upserting the package
        * user_ip: ip address of the user upserting the package
        * classifiers: a list of the classifiers to classify the release with
        * release_dependencies: a dictionary of
            'ReleaseDependencyKind.value: [specifier]' pairs.
        * description: a restructured text description of the release/project
        * additional_db_values: any other column in the release table,
            as specified by get_settable_release_columns

        and inserts the release (if one doesn't exist), or updates otherwise
        """
        is_update = self.get_release(project_name, version) is not None
        modified_elements = list(additional_db_values.keys())

        db.validate_argument_column_mapping(
            additional_db_values,
            releases,
            blacklist=['name', 'version', 'description', 'description_html',
                       '_pypi_ordering', '_pypi_hidden']
        )

        if not is_update:
            additional_db_values['name'] = project_name
            additional_db_values['version'] = version

        if description:
            modified_elements += ['description', 'description_html']
            additional_db_values['description'] = description
            additional_db_values['description_html'] = \
                readme.rst.render(description)[0]

        if len(additional_db_values) > 0:
            if is_update:
                self.engine.execute(
                    releases
                    .update()
                    .where(releases.columns.name == project_name)
                    .where(releases.columns.version == version)
                    .values(**additional_db_values)
                )
            else:
                self.engine.execute(
                    releases.insert().values(**additional_db_values)
                )

        # external tables

        # this is legacy behavior. According to PEP-438, we should
        # no longer support parsing urls from descriptions
        hosting_mode = self.get_hosting_mode(project_name)
        if hosting_mode in ('pypi-scrape-crawl', 'pypi-scrape') \
           and 'description_html' in additional_db_values:

            self.update_release_external_urls(
                project_name, version,
                utils.find_links_from_html(
                    additional_db_values['description_html']
                )
            )

        if classifiers:
            modified_elements.append('classifiers')
            self.update_release_classifiers(project_name, version,
                                            classifiers)

        if release_dependencies:
            self.update_release_dependencies(project_name, version,
                                             release_dependencies)

        if is_update:
            journal_message = 'update {0}'.format(','.join(modified_elements))
        else:
            journal_message = "new release"

        self._insert_journal_entry(project_name, version, journal_message,
                                   username, user_ip)

        # insert specific actions

        if not is_update:
            self._update_release_ordering(project_name)
Exemplo n.º 6
0
    def upsert_release(self,
                       project_name,
                       version,
                       username,
                       user_ip,
                       classifiers=None,
                       release_dependencies=None,
                       description=None,
                       **additional_db_values):
        """
        Takes in the following:

        * project_name: the name of the package to insert
        * version: the version of the package to insert
        * username: username of the user upserting the package
        * user_ip: ip address of the user upserting the package
        * classifiers: a list of the classifiers to classify the release with
        * release_dependencies: a dictionary of
            'ReleaseDependencyKind.value: [specifier]' pairs.
        * description: a restructured text description of the release/project
        * additional_db_values: any other column in the release table,
            as specified by get_settable_release_columns

        and inserts the release (if one doesn't exist), or updates otherwise
        """
        is_update = self.get_release(project_name, version) is not None
        modified_elements = list(additional_db_values.keys())

        db.validate_argument_column_mapping(additional_db_values,
                                            releases,
                                            blacklist=[
                                                'name', 'version',
                                                'description',
                                                'description_html',
                                                '_pypi_ordering',
                                                '_pypi_hidden'
                                            ])

        if not is_update:
            additional_db_values['name'] = project_name
            additional_db_values['version'] = version

        if description:
            modified_elements += ['description', 'description_html']
            additional_db_values['description'] = description
            additional_db_values['description_html'] = \
                readme.rst.render(description)[0]

        if len(additional_db_values) > 0:
            if is_update:
                self.engine.execute(releases.update().where(
                    releases.columns.name == project_name).where(
                        releases.columns.version == version).values(
                            **additional_db_values))
            else:
                self.engine.execute(
                    releases.insert().values(**additional_db_values))

        # external tables

        # this is legacy behavior. According to PEP-438, we should
        # no longer support parsing urls from descriptions
        hosting_mode = self.get_hosting_mode(project_name)
        if hosting_mode in ('pypi-scrape-crawl', 'pypi-scrape') \
           and 'description_html' in additional_db_values:

            self.update_release_external_urls(
                project_name, version,
                utils.find_links_from_html(
                    additional_db_values['description_html']))

        if classifiers:
            modified_elements.append('classifiers')
            self.update_release_classifiers(project_name, version, classifiers)

        if release_dependencies:
            self.update_release_dependencies(project_name, version,
                                             release_dependencies)

        if is_update:
            journal_message = 'update {0}'.format(','.join(modified_elements))
        else:
            journal_message = "new release"

        self._insert_journal_entry(project_name, version, journal_message,
                                   username, user_ip)

        # insert specific actions

        if not is_update:
            self._update_release_ordering(project_name)