Coverage for jaypore_ci/remotes/git.py: 100%
27 statements
« prev ^ index » next coverage.py v7.2.2, created at 2023-03-30 09:04 +0000
« prev ^ index » next coverage.py v7.2.2, created at 2023-03-30 09:04 +0000
1"""
2This is used to save the pipeline status to git itself.
3"""
4import time
5import subprocess
7from jaypore_ci.interfaces import Remote
8from jaypore_ci.repos import Git
9from jaypore_ci.logging import logger
12class GitRemote(Remote): # pylint: disable=too-many-instance-attributes
13 """
14 You can save pipeline status to git using this remote.
16 To push/fetch your local refs to a git remote you can run
18 .. code-block:: console
20 git fetch origin refs/jayporeci/*:refs/jayporeci/*
21 git push origin refs/jayporeci/*:refs/jayporeci/*
22 """
24 @classmethod
25 def from_env(cls, *, repo: Git) -> "GitRemote":
26 """
27 Creates a remote instance from the environment.
28 """
29 assert isinstance(repo, Git), "Git remote can only work in a git repo"
30 return cls(
31 repo=repo,
32 branch=repo.branch,
33 sha=repo.sha,
34 )
36 def __init__(self, *, repo, **kwargs):
37 super().__init__(**kwargs)
38 self.repo = repo
40 def logging(self):
41 """
42 Return's a logging instance with information about git bound to it.
43 """
44 return logger.bind(repo=self.repo)
46 def publish(self, report: str, status: str) -> None:
47 """
48 Will publish the report via email.
50 :param report: Report to write to remote.
51 :param status: One of ["pending", "success", "error", "failure",
52 "warning"] This is the dot next to each commit in gitea.
53 """
54 assert status in ("pending", "success", "error", "failure", "warning")
55 now = time.time()
56 lines = ""
57 git_blob_sha = subprocess.check_output(
58 "git hash-object -w --stdin",
59 input=report,
60 text=True,
61 stderr=subprocess.STDOUT,
62 shell=True,
63 ).strip()
64 lines += f"\n100644 blob {git_blob_sha}\t{now}.txt"
65 lines = lines.strip()
66 git_tree_sha = subprocess.run(
67 "git mktree",
68 input=lines,
69 text=True,
70 shell=True,
71 check=False,
72 stderr=subprocess.STDOUT,
73 stdout=subprocess.PIPE,
74 ).stdout.strip()
75 git_commit_sha = subprocess.run(
76 f"git commit-tree {git_tree_sha}",
77 text=True,
78 input=f"JayporeCI status: {now}",
79 shell=True,
80 check=False,
81 stderr=subprocess.STDOUT,
82 stdout=subprocess.PIPE,
83 )
84 assert git_commit_sha.returncode == 0
85 git_commit_sha = (
86 subprocess.check_output(
87 f"git update-ref refs/jayporeci/{self.repo.sha} {git_commit_sha.stdout.strip()}",
88 shell=True,
89 stderr=subprocess.STDOUT,
90 )
91 .decode()
92 .strip()
93 )
94 self.logging().info(
95 "Published status to local git: refs/jayporeci/{self.repo.sha} {git_commit_sha}"
96 )