Example #1
0
    def initialize(self, tag_config_path):
        """Initializes an empty git repository and creates and commits an initial tag configuration.

        If the repository already exists, only the tag configuration file is created and committed.

        Args:
            tag_config_path: The (relative) path to the dotfile tag configuration.
        """
        if not isdir(self.path):
            print('Initializing empty repository in {}'.format(self.path))
            _exec_raw(lambda: Git().init(self.path))

        try:
            self._git().rev_parse()
        except InvalidGitRepositoryError:
            print('Initializing repository in existing directory {}'.format(
                self.path))
            _exec_raw(lambda: Git(self.path).init())

        full_path = join(self.path, tag_config_path)
        if not isfile(full_path):
            print('Creating initial tag configuration')
            makedirs(dirname(full_path), exist_ok=True)
            with open(full_path, 'w') as tag_config:
                tag_config.write('{0}: {0}'.format(gethostname()))
            self.add(tag_config_path)
Example #2
0
 async def pull(self, ctx):
     """Update the bot from github"""
     g = Git()
     try:
         await ctx.send(f"Probably pulled.\n```\n{g.pull()}```")
     except git.exc.GitCommandError as e:
         await ctx.send(f"An error has occured when pulling```\n{e}```")
Example #3
0
    def init(cls, path=None, mkdir=True, odbt=DefaultDBType, **kwargs):
        """Initialize a git repository at the given path if specified

        :param path:
            is the full path to the repo (traditionally ends with /<name>.git)
            or None in which case the repository will be created in the current
            working directory

        :parm mkdir:
            if specified will create the repository directory if it doesn't
            already exists. Creates the directory with a mode=0755.
            Only effective if a path is explicitly given

        :param odbt:
            Object DataBase type - a type which is constructed by providing
            the directory containing the database objects, i.e. .git/objects.
            It will be used to access all object data

        :parm kwargs:
            keyword arguments serving as additional options to the git-init command

        :return: ``git.Repo`` (the newly created repo)"""
        if path:
            path = _expand_path(path)
        if mkdir and path and not os.path.exists(path):
            os.makedirs(path, 0o755)

        # git command automatically chdir into the directory
        git = Git(path)
        git.init(**kwargs)
        return cls(path, odbt=odbt)
Example #4
0
    def __set_path(config: Config, attr: str):
        msg = {
            'root_path': "path of the repository to work on",
        }
        while True:
            if not hasattr(config, attr) or not getattr(config, attr):
                path = prompt_enter_value(msg[attr])
            else:
                path = getattr(config, attr)  # set by script param

            if not __check_path(path):
                setattr(config, attr, "")
                continue

            if (attr == "root_path") & (os.path.realpath(__file__).startswith(
                    os.path.abspath(path))):
                log_error(
                    "Please copy and run the create release script in another place outside of the repository and execute again."
                )
                sys.exit()

            try:
                Git(path)
            except InvalidGitRepositoryError:
                log_error("Path is not a git repository.")

            setattr(config, attr, path)

            info = {
                "root_path": "Executing release in path '",
            }
            log_info(info[attr] + str(getattr(config, attr)) + "'")
            break
Example #5
0
    def init(cls, path=None, mkdir=True, **kwargs):
        """Initialize a git repository at the given path if specified

		:param path:
			is the full path to the repo (traditionally ends with /<name>.git)
			or None in which case the repository will be created in the current 
			working directory

		:parm mkdir:
			if specified will create the repository directory if it doesn't
			already exists. Creates the directory with a mode=0755. 
			Only effective if a path is explicitly given

		:parm kwargs:
			keyword arguments serving as additional options to the git-init command

		:return: ``git.Repo`` (the newly created repo)"""

        if mkdir and path and not os.path.exists(path):
            os.makedirs(path, 0755)

        # git command automatically chdir into the directory
        git = Git(path)
        output = git.init(**kwargs)
        return Repo(path)
Example #6
0
 def urls(self):
     """:return: Iterator yielding all configured URL targets on a remote as strings"""
     try:
         remote_details = self.repo.git.remote("get-url", "--all", self.name)
         for line in remote_details.split('\n'):
             yield line
     except GitCommandError as ex:
         ## We are on git < 2.7 (i.e TravisCI as of Oct-2016),
         #  so `get-utl` command does not exist yet!
         #    see: https://github.com/gitpython-developers/GitPython/pull/528#issuecomment-252976319
         #    and: http://stackoverflow.com/a/32991784/548792
         #
         if 'Unknown subcommand: get-url' in str(ex):
             try:
                 remote_details = self.repo.git.remote("show", self.name)
                 for line in remote_details.split('\n'):
                     if '  Push  URL:' in line:
                         yield line.split(': ')[-1]
             except GitCommandError as ex:
                 if any([msg in str(ex) for msg in ['correct access rights',
                                                    'cannot run ssh']]):
                     # If ssh is not setup to access this repository, see issue 694
                     result = Git().execute(['git', 'config', '--get',
                                             'remote.%s.url' % self.name])
                     yield result
                 else:
                     raise ex
         else:
             raise ex
Example #7
0
 def __init__(self, interval, length, should_notify=True):
     self.cwd = CURRENT_DIRECTORY
     self.start = datetime.datetime.now()
     reg = r'(\d+)'
     length_split = re.split(reg, length)
     time_int = length_split[1]
     time_type = length_split[2]
     if time_type == "h":
         self.until = datetime.datetime.now() + datetime.timedelta(
             hours=int(time_int))
     elif time_type == "m":
         self.until = datetime.datetime.now() + datetime.timedelta(
             minutes=int(time_int))
     elif time_type == "s":
         self.until = datetime.datetime.now() + datetime.timedelta(
             seconds=int(time_int))
     print('Running BIF until {}'.format(self.until))
     interval_split = re.split(reg, interval)
     interval_time = interval_split[1]
     interval_type = interval_split[2]
     if interval_type == "m":
         self.interval = datetime.timedelta(
             minutes=int(interval_time)).total_seconds()
     elif interval_type == "h":
         self.interval = datetime.timedelta(
             minutes=int(interval_time)).total_seconds()
     else:
         self.interval = int(interval_time)
     print('BIF Will Commit Every {} seconds'.format(self.interval))
     self.g = Git(self.cwd)
     self.length = length
     self.should_run = True
     self.should_skip = False
     self.should_notify = should_notify
     self.run()
Example #8
0
    def check(self):
        git = Git()
        output = git.execute(['git', 'ls-remote', '--heads', self.repository])
        if output:
            return True

        return False
Example #9
0
    def clone_from(cls,
                   url,
                   to_path,
                   progress=None,
                   env=None,
                   multi_options=None,
                   **kwargs):
        """Create a clone from the given URL

        :param url: valid git url, see http://www.kernel.org/pub/software/scm/git/docs/git-clone.html#URLS
        :param to_path: Path to which the repository should be cloned to
        :param progress: See 'git.remote.Remote.push'.
        :param env: Optional dictionary containing the desired environment variables.
            Note: Provided variables will be used to update the execution
            environment for `git`. If some variable is not specified in `env`
            and is defined in `os.environ`, value from `os.environ` will be used.
            If you want to unset some variable, consider providing empty string
            as its value.
        :param multi_options: See ``clone`` method
        :param kwargs: see the ``clone`` method
        :return: Repo instance pointing to the cloned directory"""
        git = Git(os.getcwd())
        if env is not None:
            git.update_environment(**env)
        return cls._clone(git, url, to_path, GitCmdObjectDB, progress,
                          multi_options, **kwargs)
Example #10
0
def get_days_since_last_update(path):
    """
    :return: The days since the last update of any of the files in path. If the
             path points to a filename, the last update of that filename is
             returned.
    """
    git = Git(".")
    cmd_str = 'git log -1 --format=%%cd %s' % path
    cmd = shlex.split(cmd_str)

    try:
        date_str = git.execute(command=cmd, with_extended_output=False)
    except GitCommandError:
        raise ValueError('"%s" is not in tracked by this repository.' % path)

    # The date_str is in the following format: Sat Jun 21 10:20:31 2014 -0300
    # We need to parse it, and then do some date math to return the result
    #
    # We ignore the UTC offset because it was "hard to parse" and we don't care
    last_commit_time = datetime.strptime(date_str[:-6], '%a %b %d %H:%M:%S %Y')
    last_commit_date = last_commit_time.date()

    today_date = date.today()

    time_delta = today_date - last_commit_date

    return time_delta.days
Example #11
0
def get():
    parser = reqparse.RequestParser()
    parser.add_argument('repo', location='args', required=True)
    parser.add_argument('port', location='args', required=True)
    data = parser.parse_args()
    repo = data['repo']
    port = data['port']
    try:
        response = requests.get(repo)
        if response.status_code != 200:
            return jsonify({
                'status': 401,
                'error': '{} is not a valid URL'.format(repo)
            })
    except:
        return jsonify({
            'status': 401,
            'error': '{} is not a valid URL'.format(repo)
        })
    gitcmd = Git('.')
    gitcmd.init()
    name = repo.split('/')
    repo_name = name[-1]
    repo_name = repo_name.replace('.git', '')
    gitcmd.clone(repo, 'repos/' + repo_name)
    subprocess.Popen(
        '.flaskapp/bin/uwsgi --http :%s --file repos/{}/wsgi.py --callable app'
        .format(port, repo_name))
    return jsonify({
        'status':
        200,
        'message':
        'Deployed to Raspberry Pi! {} is now running!'.format(repo_name)
    })
Example #12
0
    def __init__(self,
                 options,
                 title=None,
                 default_index=0,
                 options_map_func=None):
        self.KEYS_ENTER = (curses.KEY_ENTER, ord('\n'), ord('\r'))
        self.KEYS_UP = (curses.KEY_UP, ord('k'))
        self.KEYS_DOWN = (curses.KEY_DOWN, ord('j'))
        self.KEYS_SELECT = (curses.KEY_RIGHT, ord(' '))
        self.options = options
        self.title = title
        self.indicator = "=>"
        self.options_map_func = options_map_func
        self.commit_type = [
            "feat", "fix", "docs", "style", "refactor", "test", "chore", "exit"
        ]
        self.git = Git(os.getcwd())
        self.emojis = {
            "feat": "sparkles",
            "fix": "bug",
            "docs": "memo",
            "style": "art",
            "refactor": "recycle",
            "test": "white_check_mark",
            "chore": "building_construction",
        }

        if default_index >= len(options):
            raise ValueError(
                'default_index should be less than the length of options')

        self.index = default_index
    def clone_from(cls, url, to_path, **kwargs):
        """Create a clone from the given URL
		:param url: valid git url, see http://www.kernel.org/pub/software/scm/git/docs/git-clone.html#URLS
		:param to_path: Path to which the repository should be cloned to
		:param **kwargs: see the ``clone`` method
		:return: Repo instance pointing to the cloned directory"""
        return cls._clone(Git(os.getcwd()), url, to_path, GitCmdObjectDB,
                          **kwargs)
Example #14
0
    def graph(self):
        """
        Prints a graph of the git log.

        This is used for testing and debugging only.
        """
        sys.stdout.write(
            Git(self.repodir).execute(["git", "log", "--graph", "--oneline"]))
Example #15
0
    def command(self, command, freezer=None):
        """
        Runs the Git command in self.repo
        """
        args = split(command)
        cmd = Git(self.repodir)

        cmd.execute(args)
Example #16
0
    def clone(self, url):
        """Clones a dotfile repository.

        Args:
            url: The URL of the repository to clone.
        """
        print('Cloning {} into {}'.format(url, self.path))
        _exec_raw(lambda: Git().clone(url, self.path))
Example #17
0
    def graph(self):
        """
        Prints a graph of the git log.

        This is used for testing and debugging only.
        """
        sys.stdout.write(
            Git(self.repodir).execute(['git', 'log', '--graph', '--oneline']))
Example #18
0
def init_logging(gn_env: GNEnvironment) -> None:
    if len(gn_env.config) == 0 or gn_env.config.get(ConfigKeys.TESTING, False):
        # assume we're testing
        return

    logging_type = gn_env.config.get(
        ConfigKeys.TYPE, domain=ConfigKeys.LOGGING, default="logger"
    )
    if (
        logging_type is None
        or len(logging_type.strip()) == 0
        or logging_type in ["logger", "default", "mock"]
    ):
        return

    if logging_type != "sentry":
        raise RuntimeError(f"unknown logging type {logging_type}")

    dsn = gn_env.config.get(ConfigKeys.DSN, domain=ConfigKeys.LOGGING, default="")
    if dsn is None or len(dsn.strip()) == 0:
        logger.warning(
            "sentry logging selected but no DSN supplied, not configuring sentry"
        )
        return

    import socket
    from git.cmd import Git

    home_dir = os.environ.get("DINO_HOME", default=None)
    if home_dir is None:
        home_dir = "."
    tag_name = Git(home_dir).describe()

    import sentry_sdk
    from sentry_sdk import capture_exception as sentry_capture_exception
    from sentry_sdk.integrations.sqlalchemy import SqlalchemyIntegration

    sentry_sdk.init(
        dsn=dsn,
        environment=os.getenv("ENVIRONMENT"),  # TODO: fix DINO_ENVIRONMENT / ENVIRONMENT discrepancy
        server_name=socket.gethostname(),
        release=tag_name,
        integrations=[
            SqlalchemyIntegration(),
            RedisIntegration()
        ],
    )

    def capture_wrapper(e_info) -> None:
        try:
            sentry_capture_exception(e_info)
        except Exception as e2:
            logger.exception(e_info)
            logger.error(f"could not capture exception with sentry: {str(e2)}")

    gn_env.capture_exception = capture_wrapper
Example #19
0
def pull(repo_dir):
    """
    Pull all the new files in the master in specified directory.
    Directory should contain path where .git file is located.
    :param repo_dir: directory where .git file is located
    """
    g = Git(repo_dir)
    g.pull()
    a = Repo(repo_dir)
    for s in a.submodules:
        s.update(recursive=True, init=True)
Example #20
0
 def is_cached(self):
     try:
         cache_path = self.cache_dir + '/' + self.project
         is_dir = os.path.isdir(cache_path)
         if is_dir:
             result = Git(cache_path).execute(
                 ['git', 'rev-parse', '--git-dir'], )
             if result.startswith('.'):
                 return True
             return False
     except Exception:
         return False
Example #21
0
 def __init__(self, options, build_type='job'):
     self.options = options
     repository, project, version = self.parse_repository()
     self.repository = repository
     self.project = project
     self.version = version
     self.cache_dir = Workspace().get_vcs_space('git')
     self.build_type = build_type
     self.workspace = self.cwd
     self.git = Git(working_dir=self.cwd)
     self.refs = None
     self.logger = get_logger('console')
Example #22
0
    def get_contibutors(self) -> list[str]:
        """Return list of Git contributors for given path using `git shortlog`

        :path: Path of which to get contributors
        :flags: Additional flags passed to `git shortlog`
        """
        docfile_path = Path(self.get_source_info()[0]).resolve()
        docfile_name = docfile_path.name
        docdir_path = docfile_path.parent
        min_commits = self.optn_over_conf("min_commits",
                                          "scm_contribs_min_commits")

        limit_authors = self.optn_over_conf("limit_authors",
                                            "scm_contribs_limit_authors")
        if limit_authors is not None and limit_authors < 1:
            logger.warning(
                "List of contributors limited to less than one entry. "
                "Check '(scm_contribs_)limit_authors' option/config value")

        flags: list[str] = []

        contribs_email = directives.choice(
            self.optn_over_conf("email", "scm_contribs_email"),
            ("true", "false"),
        )
        flags += ["-e"] if contribs_email == "true" else []

        contribs_sort = directives.choice(
            self.optn_over_conf("sort", "scm_contribs_sort"),
            ("name", "num"),
        )
        flags += ["-n"] if contribs_sort == "num" else []

        contribs_type = directives.choice(
            self.optn_over_conf("type", "scm_contribs_type"),
            ("author", "committer"),
        )
        flags += ["-c"] if contribs_type == "committer" else []

        git_shortlog_options = ["-s", *flags, "--", docfile_name]

        contributors = []
        git_shortlog = Git(docdir_path).shortlog(*git_shortlog_options)
        git_shortlog_items = git_shortlog.split("\n")
        for item in git_shortlog_items:
            if not item:
                continue
            num, contributor = item.split("\t")
            if int(num) < min_commits:
                continue
            contributors += [contributor]

        return contributors[:limit_authors]
Example #23
0
    def is_type(cls, origin=None):
        if origin is None:
            return False

        g = Git()

        try:
            g.ls_remote(origin)
        except GitCommandError:
            return False

        return True
Example #24
0
    def install_by_url(self, url, ignore_errors=False):
        """ installs from the specified github repo """
        url = url.strip()
        self.github_url_check(url)
        data = self.url_info(url)
        skill_folder = data["folder"]
        path = data["path"]
        self.send_message("msm.installing", data)
        if exists(path):
            LOG.info("skill exists, updating")
            # TODO get hashes before pulling to decide if pip and res.sh should be run
            # TODO ensure skill master branch is checked out, else dont update
            g = Git(path)
            try:
                g.pull()
            except GitCommandError:
                LOG.error("skill modified by user")
                if not ignore_errors:
                    LOG.info("not updating")
                    data["error"] = "skill modified by user"
                    self.send_message("msm.install.failed", data)
                    self.send_message("msm.installed")
                    return False
        else:
            LOG.info("Downloading skill: " + url)
            Repo.clone_from(url, path)

        if skill_folder not in self.skills:
            self.skills[skill_folder] = data

        self.skills[skill_folder]["downloaded"] = True
        try:
            self.run_requirements_sh(skill_folder)
        except SystemRequirementsException:
            if not ignore_errors:
                data["error"] = "could not run requirements.sh"
                self.send_message("msm.install.failed", data)
                self.send_message("msm.installed")
                return False

        try:
            self.run_pip(skill_folder)
        except PipRequirementsException:
            if not ignore_errors:
                data["error"] = "could not run install requirements.txt"
                self.send_message("msm.install.failed", data)
                self.send_message("msm.installed")
                return False

        self.run_skills_requirements(skill_folder)
        self.send_message("msm.install.succeeded", data)
        self.send_message("msm.installed")
        return True
Example #25
0
def pull(repo_dir: str):
    """
    Pull all the new files in the master in specified directory.
    Directory should contain path where .git file is located.

    Arguments:
        :param repo_dir directory where .git file is located
    """
    git = Git(repo_dir)
    git.pull()
    repo = Repo(repo_dir)
    for submodule in repo.submodules:
        submodule.update(recursive=True, init=True)
Example #26
0
    def clone_from(cls, url, to_path, progress=None, env=None, **kwargs):
        """Create a clone from the given URL

        :param url: valid git url, see http://www.kernel.org/pub/software/scm/git/docs/git-clone.html#URLS
        :param to_path: Path to which the repository should be cloned to
        :param progress: See 'git.remote.Remote.push'.
        :param env: Optional dictionary containing the desired environment variables.
        :param kwargs: see the ``clone`` method
        :return: Repo instance pointing to the cloned directory"""
        git = Git(os.getcwd())
        if env is not None:
            git.update_environment(**env)
        return cls._clone(git, url, to_path, GitCmdObjectDB, progress, **kwargs)
Example #27
0
    def __init__(self, path: Path | str) -> None:
        self.path: Path = Path(path)
        self.repo: Repo = Repo(self.path)

        if self.repo.bare:
            logger.critical(
                "Please make sure you entered the correct repository "
                "in [SYNAPSE] -> Playbook.")
            sys.exit(1)

        self.git: Git = Git(self.path)
        self.heads = self.repo.heads
        self.master = self.heads.master
Example #28
0
    def __set_path(config: Config, attr: str):
        while True:
            if not hasattr(config, attr) or not getattr(config, attr):
                tempdir = tempfile.TemporaryDirectory()
                path = tempdir.name
                if not hasattr(config, "two_factor_authentication"):
                    config.two_factor_authentication = prompt_yesno_question(
                        "Are you using two-factor authentication on GitHub?")
                if config.two_factor_authentication:
                    repository_url = "[email protected]:" + config.github_repo + ".git"
                else:
                    repository_url = "https://github.com/" + config.github_repo + ".git"
                log_info("Cloning temporary repository from " + repository_url + " to " + str(path) + " for processing the release...")
                Git(path).clone(repository_url)
            else:
                path = getattr(config, attr)  # set by script param

            if not __check_path(path):
                setattr(config, attr, "")
                continue

            if (attr == "root_path") & (os.path.realpath(__file__).startswith(os.path.abspath(path))):
                log_error(
                    "Please copy and run the create release script in another place outside of the repository and execute again.")
                sys.exit()

            try:
                Git(path)
            except InvalidGitRepositoryError:
                log_error("Path is not a git repository.")

            setattr(config, attr, path)

            info = {
                "root_path": "Executing release in path '",
            }
            log_info(info[attr] + str(getattr(config, attr)) + "'")
            break
Example #29
0
def open_or_clone_repo():
    """Returns opened or cloned repo and 'True' flag if operation successful
    else 'None' object and 'False' flag.
    """
    try:
        return GitRepo(path=procyon_settings.REPO_PATH), True
    except (InvalidGitRepositoryError, NoSuchPathError):
        pass

    try:
        Git(procyon_settings.PROCYON_PATH).clone(procyon_settings.REMOTE_REPO)
    except GitCommandError:
        return None, False

    return GitRepo(path=procyon_settings.REPO_PATH), True
Example #30
0
def checkout(c, name=None):
    _platform = __platform()
    _c_name, _c_platform = f'[hl]{name}[/hl]', f'[hl]{_platform}[/hl]'
    _h_name, _h_platform = f'<b>{name}</b>', f'<b>{_platform}</b>'
    _msg = f'Checkout of :{cfg.icon.component}: %s %s completed @ :{cfg.icon.platform}: %s.'
    try:
        _git = Git(cfg.git.get(name))
        _git.checkout()
        log.success(_msg % (_c_name, '[ok]correctly[/ok]', _c_platform))
        telegrot.success(_msg % (_h_name, '<u>correctly</u>', _h_platform))
        exit(0)
    except Exception:
        log.error(_msg % (_c_name, '[err]not[/err]', _c_platform))
        telegrot.error(_msg % (_h_name, '<u>not</u>', _h_platform))
        exit(1)