예제 #1
0
 def add_user(self, user: str, access_level: AccessLevel) -> None:
     """
     AccessLevel.pull => Guest access
     AccessLevel.triage => Reporter access
     AccessLevel.push => Developer access
     AccessLevel.admin => Maintainer access
     AccessLevel.maintain => Owner access # Only valid for groups
     """
     access_dict = {
         AccessLevel.pull: gitlab.GUEST_ACCESS,
         AccessLevel.triage: gitlab.REPORTER_ACCESS,
         AccessLevel.push: gitlab.DEVELOPER_ACCESS,
         AccessLevel.admin: gitlab.MAINTAINER_ACCESS,
         AccessLevel.maintain: gitlab.OWNER_ACCESS,
     }
     try:
         user_id = self.service.gitlab_instance.users.list(
             username=user)[0].id
     except Exception as e:
         raise GitlabAPIException(f"User {user} not found", e)
     try:
         self.gitlab_repo.members.create({
             "user_id":
             user_id,
             "access_level":
             access_dict[access_level]
         })
     except Exception as e:
         raise GitlabAPIException(f"User {user} already exists", e)
예제 #2
0
    def __get_fork(
            fork_username: str,
            project: "ogr_gitlab.GitlabProject") -> "ogr_gitlab.GitlabProject":
        """
        Returns forked project of a requested user. Internal method, in case the fork
        doesn't exist, raises GitlabAPIException.

        Args:
            fork_username: Username of a user that owns requested fork.
            project: Project to search forks of.

        Returns:
            Requested fork.

        Raises:
            GitlabAPIException, in case the fork doesn't exist.
        """
        forks = list(
            filter(
                lambda fork: fork.gitlab_repo.namespace["full_path"] ==
                fork_username,
                project.get_forks(),
            ))
        if not forks:
            raise GitlabAPIException("Requested fork doesn't exist")
        return forks[0]
예제 #3
0
 def get_issue_labels(self, issue_id: int) -> List[str]:
     try:
         issue = self.gitlab_repo.issues.get(issue_id)
     except gitlab.exceptions.GitlabGetError as ex:
         logger.error(f"Issue {issue_id} was not found.")
         raise GitlabAPIException(f"Issue {issue_id} was not found. ", ex)
     return issue.labels
예제 #4
0
    def set(
        project: "ogr_gitlab.GitlabProject",
        commit: str,
        state: Union[CommitStatus, str],
        target_url: str,
        description: str,
        context: str,
        trim: bool = False,
    ) -> "CommitFlag":
        state = GitlabCommitFlag._validate_state(state)

        if trim:
            description = description[:140]

        try:
            commit_object = project.gitlab_repo.commits.get(commit)
        except gitlab.exceptions.GitlabGetError:
            logger.error(f"Commit {commit} was not found.")
            raise GitlabAPIException(f"Commit {commit} was not found.")

        data_dict = {
            "state": GitlabCommitFlag._state_from_enum(state),
            "target_url": target_url,
            "context": context,
            "description": description,
        }
        raw_status = commit_object.statuses.create(data_dict)
        return GitlabCommitFlag(raw_commit_flag=raw_status, project=project)
예제 #5
0
파일: issue.py 프로젝트: jpopelka/ogr
 def get(project: "ogr_gitlab.GitlabProject", issue_id: int) -> "Issue":
     try:
         return GitlabIssue(project.gitlab_repo.issues.get(issue_id),
                            project)
     except gitlab.exceptions.GitlabGetError as ex:
         raise GitlabAPIException(
             f"Issue {issue_id} was not found. ") from ex
예제 #6
0
 def get_sha_from_tag(self, tag_name: str) -> str:
     try:
         tag = self.gitlab_repo.tags.get(tag_name)
         return tag.attributes["commit"]["id"]
     except gitlab.exceptions.GitlabGetError as ex:
         logger.error(f"Tag {tag_name} was not found.")
         raise GitlabAPIException(f"Tag {tag_name} was not found.", ex)
예제 #7
0
파일: flag.py 프로젝트: lbarcziova/ogr
    def set(
        project: "ogr_gitlab.GitlabProject",
        commit: str,
        state: Union[CommitStatus, str],
        target_url: str,
        description: str,
        context: str,
        trim: bool = False,
    ) -> "CommitFlag":

        if trim:
            description = description[:140]

        if isinstance(state, str):
            warnings.warn(
                "Using the string representation of commit states, that will be removed in 0.14.0"
                " (or 1.0.0 if it comes sooner). Please use CommitStatus enum instead. "
            )
            state = GitlabCommitFlag._states[state]

        try:
            commit_object = project.gitlab_repo.commits.get(commit)
        except gitlab.exceptions.GitlabGetError:
            logger.error(f"Commit {commit} was not found.")
            raise GitlabAPIException(f"Commit {commit} was not found.")

        data_dict = {
            "state": GitlabCommitFlag._state_from_enum(state),
            "target_url": target_url,
            "context": context,
            "description": description,
        }
        raw_status = commit_object.statuses.create(data_dict)
        return GitlabCommitFlag(raw_commit_flag=raw_status, project=project)
예제 #8
0
파일: project.py 프로젝트: mmuzila/ogr
    def create_issue(
        self,
        title: str,
        body: str,
        private: Optional[bool] = None,
        labels: Optional[List[str]] = None,
        assignees: Optional[List[str]] = None,
    ) -> Issue:

        ids = []
        for user in assignees or []:
            users_list = self.service.gitlab_instance.users.list(username=user)

            if not users_list:
                raise GitlabAPIException(f"Unable to find '{user}' username")

            ids.append(str(users_list[0].id))

        return GitlabIssue.create(
            project=self,
            title=title,
            body=body,
            private=private,
            labels=labels,
            assignees=ids,
        )
예제 #9
0
    def commit_comment(self,
                       commit: str,
                       body: str,
                       filename: str = None,
                       row: int = None) -> "CommitComment":
        """
        Create comment on a commit.

        :param commit: str The SHA of the commit needing a comment.
        :param body: str The text of the comment
        :param filename: str The relative path to the file that necessitates a comment
        :param row: int Line index in the diff to comment on.
        :return: CommitComment
        """
        try:
            commit_object = self.gitlab_repo.commits.get(commit)
        except gitlab.exceptions.GitlabGetError:
            logger.error(f"Commit {commit} was not found.")
            raise GitlabAPIException(f"Commit {commit} was not found.")

        if filename and row:
            raw_comment = commit_object.comments.create({
                "note": body,
                "path": filename,
                "line": row,
                "line_type": "new"
            })
        else:
            raw_comment = commit_object.comments.create({"note": body})
        return self._commit_comment_from_gitlab_object(raw_comment, commit)
예제 #10
0
    def set_commit_status(self, commit: str, state: str, target_url: str,
                          description: str, context: str) -> "CommitFlag":
        """
        Create a status on a commit

        :param commit: The SHA of the commit.
        :param state: The state of the status.
        :param target_url: The target URL to associate with this status.
        :param description: A short description of the status
        :param context: A label to differentiate this status from the status of other systems.
        :return: CommitFlag
        """
        try:
            commit_object = self.gitlab_repo.commits.get(commit)
        except gitlab.exceptions.GitlabGetError:
            logger.error(f"Commit {commit} was not found.")
            raise GitlabAPIException(f"Commit {commit} was not found.")

        data_dict = {
            "state": state,
            "target_url": target_url,
            "context": context,
            "description": description,
        }
        raw_status = commit_object.statuses.create(data_dict)
        return self._commit_status_from_gitlab_object(raw_status)
예제 #11
0
 def get_pr_labels(self, pr_id: int) -> List[str]:
     try:
         pr = self.gitlab_repo.mergerequests.get(pr_id)
     except gitlab.exceptions.GitlabGetError as ex:
         logger.error(f"PR {pr_id} was not found.")
         raise GitlabAPIException(f"PR {pr_id} was not found. ", ex)
     return pr.labels
예제 #12
0
파일: issue.py 프로젝트: packit/ogr
    def create(
        project: "ogr_gitlab.GitlabProject",
        title: str,
        body: str,
        private: Optional[bool] = None,
        labels: Optional[List[str]] = None,
        assignees: Optional[List[str]] = None,
    ) -> "Issue":
        if not project.has_issues:
            raise IssueTrackerDisabled()

        assignee_ids = []
        for user in assignees or []:
            users_list = project.service.gitlab_instance.users.list(
                username=user)

            if not users_list:
                raise GitlabAPIException(f"Unable to find '{user}' username")

            assignee_ids.append(str(users_list[0].id))

        data = {"title": title, "description": body}
        if labels:
            data["labels"] = ",".join(labels)
        if assignees:
            data["assignee_ids"] = ",".join(assignee_ids)

        issue = project.gitlab_repo.issues.create(data, confidential=private)
        return GitlabIssue(issue, project)
예제 #13
0
 def add_issue_labels(self, issue_id, labels) -> None:
     try:
         issue = self.gitlab_repo.issues.get(issue_id)
     except gitlab.exceptions.GitlabGetError as ex:
         logger.error(f"Issue {issue_id} was not found.")
         raise GitlabAPIException(f"Issue {issue_id} was not found. ", ex)
     for label in labels:
         issue.labels.append(label)
     issue.save()
예제 #14
0
파일: project.py 프로젝트: jpopelka/ogr
 def get_file_content(self, path, ref=None) -> str:
     ref = ref or self.default_branch
     try:
         file = self.gitlab_repo.files.get(file_path=path, ref=ref)
         return file.decode().decode()
     except gitlab.exceptions.GitlabGetError as ex:
         if ex.response_code == 404:
             raise FileNotFoundError(f"File '{path}' on {ref} not found") from ex
         raise GitlabAPIException() from ex
예제 #15
0
파일: project.py 프로젝트: jpopelka/ogr
 def add_user(self, user: str, access_level: AccessLevel) -> None:
     access_dict = {
         AccessLevel.pull: gitlab.GUEST_ACCESS,
         AccessLevel.triage: gitlab.REPORTER_ACCESS,
         AccessLevel.push: gitlab.DEVELOPER_ACCESS,
         AccessLevel.admin: gitlab.MAINTAINER_ACCESS,
         AccessLevel.maintain: gitlab.OWNER_ACCESS,
     }
     try:
         user_id = self.service.gitlab_instance.users.list(username=user)[0].id
     except Exception as e:
         raise GitlabAPIException(f"User {user} not found") from e
     try:
         self.gitlab_repo.members.create(
             {"user_id": user_id, "access_level": access_dict[access_level]}
         )
     except Exception as e:
         raise GitlabAPIException(f"User {user} already exists") from e
예제 #16
0
 def add_pr_labels(self, pr_id, labels) -> None:
     try:
         pr = self.gitlab_repo.mergerequests.get(pr_id)
     except gitlab.exceptions.GitlabGetError as ex:
         logger.error(f"PR {pr_id} was not found.")
         raise GitlabAPIException(f"PR {pr_id} was not found. ", ex)
     for label in labels:
         pr.labels.append(label)
     pr.save()
예제 #17
0
 def wrapper(*args, **kwargs):
     try:
         return function(*args, **kwargs)
     except github.BadCredentialsException as ex:
         raise GithubAPIException("Invalid Github credentials") from ex
     except gitlab.GitlabAuthenticationError as ex:
         raise GitlabAPIException("Invalid Gitlab credentials") from ex
     except requests.exceptions.ConnectionError as ex:
         raise OgrNetworkError(
             "Could not perform the request due to a network error") from ex
예제 #18
0
파일: project.py 프로젝트: packit/ogr
    def get_commit_comments(self, commit: str) -> List[CommitComment]:
        try:
            commit_object: ProjectCommit = self.gitlab_repo.commits.get(commit)
        except gitlab.exceptions.GitlabGetError as ex:
            logger.error(f"Commit {commit} was not found.")
            raise GitlabAPIException(f"Commit {commit} was not found.") from ex

        return [
            self._commit_comment_from_gitlab_object(comment, commit)
            for comment in commit_object.comments.list()
        ]
예제 #19
0
 def project_create(self, repo: str, namespace: str = None) -> "GitlabProject":
     data = {"name": repo}
     if namespace:
         try:
             group = self.gitlab_instance.groups.get(namespace)
         except gitlab.GitlabGetError:
             raise GitlabAPIException(f"Group {namespace} not found.")
         data["namespace_id"] = group.id
     new_project = self.gitlab_instance.projects.create(data)
     return GitlabProject(
         repo=repo, namespace=namespace, service=self, gitlab_repo=new_project
     )
예제 #20
0
파일: project.py 프로젝트: jpopelka/ogr
 def fork_create(self) -> "GitlabProject":
     try:
         fork = self.gitlab_repo.forks.create({})
     except gitlab.GitlabCreateError as ex:
         logger.error(f"Repo {self.gitlab_repo} cannot be forked")
         raise GitlabAPIException(
             f"Repo {self.gitlab_repo} cannot be forked"
         ) from ex
     logger.debug(f"Forked to {fork.namespace['full_path']}/{fork.path}")
     return GitlabProject(
         namespace=fork.namespace["full_path"], service=self.service, repo=fork.path
     )
예제 #21
0
파일: flag.py 프로젝트: sakalosj/ogr
    def get(project: "ogr_gitlab.GitlabProject", commit: str) -> List["CommitFlag"]:
        try:
            commit_object = project.gitlab_repo.commits.get(commit)
        except gitlab.exceptions.GitlabGetError:
            logger.error(f"Commit {commit} was not found.")
            raise GitlabAPIException(f"Commit {commit} was not found.")

        raw_statuses = commit_object.statuses.list()
        return [
            GitlabCommitFlag(raw_commit_flag=raw_status, project=project)
            for raw_status in raw_statuses
        ]
예제 #22
0
파일: service.py 프로젝트: packit/ogr
    def project_create(
        self,
        repo: str,
        namespace: Optional[str] = None,
        description: Optional[str] = None,
    ) -> "GitlabProject":
        data = {"name": repo}
        if namespace:
            try:
                group = self.gitlab_instance.groups.get(namespace)
            except gitlab.GitlabGetError as ex:
                raise GitlabAPIException(f"Group {namespace} not found.") from ex
            data["namespace_id"] = group.id

        if description:
            data["description"] = description
        try:
            new_project = self.gitlab_instance.projects.create(data)
        except gitlab.GitlabCreateError as ex:
            raise GitlabAPIException("Project already exists") from ex
        return GitlabProject(
            repo=repo, namespace=namespace, service=self, gitlab_repo=new_project
        )
예제 #23
0
파일: issue.py 프로젝트: packit/ogr
    def add_assignee(self, *assignees: str) -> None:
        assignee_ids = self._raw_issue.__dict__.get("assignee_ids") or []
        for assignee in assignees:
            users = self.project.service.gitlab_instance.users.list(  # type: ignore
                username=assignee)
            if not users:
                raise GitlabAPIException(
                    f"Unable to find '{assignee}' username")
            uid = str(users[0].id)
            if uid not in assignee_ids:
                assignee_ids.append(str(users[0].id))

        self._raw_issue.assignee_ids = assignee_ids
        self._raw_issue.save()
예제 #24
0
    def fork_create(self, namespace: Optional[str] = None) -> "GitlabProject":
        data = {}
        if namespace:
            data["namespace_path"] = namespace

        try:
            fork = self.gitlab_repo.forks.create(data=data)
        except gitlab.GitlabCreateError as ex:
            logger.error(f"Repo {self.gitlab_repo} cannot be forked")
            raise GitlabAPIException(
                f"Repo {self.gitlab_repo} cannot be forked") from ex
        logger.debug(f"Forked to {fork.namespace['full_path']}/{fork.path}")
        return GitlabProject(namespace=fork.namespace["full_path"],
                             service=self.service,
                             repo=fork.path)
예제 #25
0
파일: project.py 프로젝트: pawelkopka/ogr
    def fork_create(self) -> "GitlabProject":
        """
        Fork this project using the authenticated user.
        This may raise an exception if the fork already exists.

        :return: fork GitlabProject instance
        """
        try:
            fork = self.gitlab_repo.forks.create({})
        except gitlab.GitlabCreateError:
            logger.error(f"Repo {self.gitlab_repo} cannot be forked")
            raise GitlabAPIException(f"Repo {self.gitlab_repo} cannot be forked")
        return GitlabProject(
            namespace=fork.namespace["full_path"], service=self.service, repo=fork.path
        )
예제 #26
0
파일: project.py 프로젝트: jpopelka/ogr
    def commit_comment(
        self, commit: str, body: str, filename: str = None, row: int = None
    ) -> "CommitComment":
        try:
            commit_object = self.gitlab_repo.commits.get(commit)
        except gitlab.exceptions.GitlabGetError as ex:
            logger.error(f"Commit {commit} was not found.")
            raise GitlabAPIException(f"Commit {commit} was not found.") from ex

        if filename and row:
            raw_comment = commit_object.comments.create(
                {"note": body, "path": filename, "line": row, "line_type": "new"}
            )
        else:
            raw_comment = commit_object.comments.create({"note": body})
        return self._commit_comment_from_gitlab_object(raw_comment, commit)
예제 #27
0
    def get_commit_statuses(self, commit: str) -> List[CommitFlag]:
        """
        Get the statuses of a commit in a project.
        :param commit: The SHA of the commit.
        :return: [CommitFlag]
        """
        try:
            commit_object = self.gitlab_repo.commits.get(commit)
        except gitlab.exceptions.GitlabGetError:
            logger.error(f"Commit {commit} was not found.")
            raise GitlabAPIException(f"Commit {commit} was not found.")

        raw_statuses = commit_object.statuses.list()
        return [
            self._commit_status_from_gitlab_object(raw_status)
            for raw_status in raw_statuses
        ]
예제 #28
0
    def add_reaction(self, reaction: str) -> GitlabReaction:
        try:
            reaction_obj = self._raw_comment.awardemojis.create(
                {"name": reaction})
        except gitlab.exceptions.GitlabCreateError as ex:
            if "404 Award Emoji Name has already been taken" not in str(ex):
                raise GitlabAPIException() from ex

            # this happens only when the reaction was already added
            logger.info(f"The emoji {reaction} has already been taken.")
            (reaction_obj, ) = filter(
                (
                    # we want to return that already given reaction
                    lambda item: item.attributes[
                        "name"] == reaction and item.attributes["user"]["name"]
                    == item.awardemojis.gitlab.user.name),
                self._raw_comment.awardemojis.list(),
            )

        return GitlabReaction(reaction_obj)
예제 #29
0
 def get(project: "ogr_gitlab.GitlabProject", pr_id: int) -> "PullRequest":
     try:
         mr = project.gitlab_repo.mergerequests.get(pr_id)
     except gitlab.GitlabGetError as ex:
         raise GitlabAPIException(f"No PR with id {pr_id} found") from ex
     return GitlabPullRequest(mr, project)
예제 #30
0
 def merge_commit_status(self) -> MergeCommitStatus:
     status = self._raw_pr.merge_status
     if status in self._merge_commit_status:
         return self._merge_commit_status[status]
     else:
         raise GitlabAPIException(f"Invalid merge_status {status}")