Example #1
0
 def handle_status(self, args):
     if self.is_initialized():
         try:
             level = self.get_level()
             level.status()
         except KeyError:
             level_name = operations.get_operator().read_level_file()
             print(
                 'Currently on unregistered level: "{}"'.format(level_name))
     else:
         print("Git Gud not initialized.")
         print('Initialize using "git gud init"')
Example #2
0
 def load_level(self, level):
     # Clear remotes
     self.assert_initialized(skip_level_check=True)
     file_operator = operations.get_operator()
     level_repo = file_operator.setup_repo()
     if level_repo:
         for remote in level_repo.remotes:
             level_repo.delete_remote(remote)
     else:
         file_operator.setup_repo()
     file_operator.clear_tracked_commits()
     level.setup()
     file_operator.write_level(level)
Example #3
0
    def assert_initialized(self, skip_level_check=False):
        if not self.is_initialized():
            raise InitializationError(
                'Git gud has not been initialized. Use "git gud init" to initialize'
            )  # noqa: E501

        if not skip_level_check:
            try:
                self.get_level()
            except KeyError:
                level_name = operations.get_operator().read_level_file()
                raise InitializationError(
                    'Currently loaded level does not exist: "{}"'.format(
                        level_name))
Example #4
0
    def _setup(self):
        file_operator = operations.get_operator(initialize_repo=True)
        commits, head = parse_spec(self.file('setup.spec'))
        file_operator.create_tree(commits, head)

        latest_commit = '0'
        for commit_name, _, _, _ in commits:
            try:
                if int(commit_name) > int(latest_commit):
                    latest_commit = commit_name
            except ValueError:
                pass  # Commit is merge and doesn't have number

        file_operator.write_last_commit(latest_commit)
Example #5
0
def test_load(gg):
    load_tests = [
        ('git gud load 1', all_skills["1"]["1"]),
        ('git gud load rampup', all_skills["rampup"]["1"]),
        ('git gud load 2 detaching', all_skills["2"]["detaching"]),
        ('git gud load rampup 4', all_skills["rampup"]["4"]),
        ('git gud load 5-octopus', all_skills["5"]["octopus"]),
        ('git gud load rampup-4', all_skills["rampup"]["4"]),
        ('git gud load -2', all_skills["rampup"]["2"])
    ]

    for command, level in load_tests:
        subprocess.call(command, shell=True)
        op = operations.get_operator()
        assert level == op.get_level()
Example #6
0
 def parse(self):
     args, _ = self.parser.parse_known_args()
     if args.command is None:
         if operations.get_operator() is None:
             print('Currently in an uninitialized directory.')
             print(
                 'Get started by running "git gud init" in an empty directory!'
             )  # noqa: E501
         else:
             self.parser.print_help()
     else:
         try:
             self.command_dict[args.command](args)
         except InitializationError as error:
             print(error)
Example #7
0
 def parse(self):
     if len(sys.argv) >= 2 and sys.argv[1] in self.aliases:
         sys.argv[1] = self.aliases[sys.argv[1]]
     args, _ = self.parser.parse_known_args(sys.argv[1:])
     if args.command is None:
         if get_operator() is None:
             print('Currently in an uninitialized directory.')
             print(
                 'Get started by running "git gud init" in an empty directory!'
             )  # noqa: E501
         else:
             self.parser.print_help()
     else:
         try:
             self.command_dict[args.command](args)
         except InitializationError as error:
             print(error)
Example #8
0
    def handle_load(self, args):
        self.assert_initialized()
        args.skill_name = args.skill_name.lower()
        if args.level_name:
            args.level_name = args.level_name.lower()

        if args.skill_name in {"next", "prev", "previous"}:
            self.load_level_by_direction(args.skill_name, args.force)
            return

        # No matter what, the dash separates the skill and level
        if '-' in args.skill_name:
            identifier = args.skill_name + (args.level_name or '')
        else:
            identifier = args.skill_name + '-' + (args.level_name or '')
        if identifier.count('-') != 1:
            print("Load formula must not contain more than one dash.")
            return

        args.skill_name, args.level_name = identifier.split('-')

        if not args.skill_name:
            args.skill_name, loaded_level_name = get_operator() \
                    .get_level_identifier()
            print("Inferring skill from currently loaded level: {} {}".format(
                args.skill_name, loaded_level_name))
        if not args.level_name:
            args.level_name = '1'

        # Skill doesn't exist
        if args.skill_name not in all_skills.keys():
            print('Skill "{}" does not exist'.format(args.skill_name))
            print('\nTo view levels/skills, use "git gud levels --all"')
            return

        # Level doesn't exist
        skill = all_skills[args.skill_name]
        if args.level_name not in skill.keys():
            print('Level "{}" does not exist.'.format(args.level_name))
            print('\nTo view levels/skills, use "git gud levels --all"')
            return

        level = skill[args.level_name]
        self.load_level(level)
Example #9
0
def setup_rebase_conflict():
    file_operator = get_operator()

    with open("foo", "w") as f:
        f.write("branch 1")
    file_operator.repo.index.add("foo")
    file_operator.repo.index.commit("Add a file")

    file_operator.repo.git.checkout('-b', 'branch', 'HEAD~')
    with open("foo", "w") as f:
        f.write("branch 2")
    file_operator.repo.index.add("foo")
    file_operator.repo.index.commit("Add a file")

    try:
        file_operator.repo.git.rebase('master')
    except GitCommandError:
        # This will happen every time
        pass
Example #10
0
    def handle_commit(self, args):
        self.assert_initialized()
        file_operator = get_operator()
        last_commit = file_operator.get_last_commit()
        commit_name = str(int(last_commit) + 1)

        if args.file is not None:
            try:
                int(args.file)
                commit_name = args.file
            except ValueError:
                pass

        commit = file_operator.add_and_commit(commit_name, silent=False)
        file_operator.track_commit(commit_name, commit.hexsha)

        # Next "git gud commit" name
        if int(commit_name) > int(last_commit):
            file_operator.write_last_commit(commit_name)
Example #11
0
    def handle_init(self, args):
        # Make sure it's safe to initialize

        file_operator = get_operator()
        if file_operator:
            if not args.force:
                repo_already_initialized()
                return
            else:
                force_initializing()
        elif len(list(Path.cwd().iterdir())) != 0:
            if not (args.force and args.prettyplease):
                cant_init_repo_not_empty()
                return
            else:
                deleting_and_initializing()

        file_operator = Operator(Path.cwd())
        file_operator.init_gg()

        self.load_level(all_skills["0"]["1"])
Example #12
0
    def _setup(self):
        file_operator = operations.get_operator()
        file_operator.use_repo()
        commits, head = parse_spec(self.file('setup.spec'))

        details_path = self.file('details.yaml')
        if details_path.is_file():
            details = yaml.safe_load(details_path.open())
        else:
            details = None

        file_operator.create_tree(commits, head, details, self.level_dir)

        latest_commit = '0'
        for commit_name, _, _, _ in commits:
            try:
                if int(commit_name) > int(latest_commit):
                    latest_commit = commit_name
            except ValueError:
                pass  # Commit is merge and doesn't have number

        file_operator.write_last_commit(latest_commit)
Example #13
0
    def handle_commit(self, args):
        self.assert_initialized()
        file_operator = operations.get_operator()
        last_commit = file_operator.get_last_commit()
        commit_name = str(int(last_commit) + 1)

        if args.file is not None:
            try:
                int(args.file)
                commit_name = args.file
            except ValueError:
                pass

        print_info('Created file "{}"'.format(commit_name))
        mock_simulate('git add {}'.format(commit_name))
        mock_simulate('git commit -m "{}"'.format(commit_name))

        commit = file_operator.add_and_commit(commit_name)
        print_info("New Commit: {}".format(commit.hexsha[:7]))
        file_operator.track_commit(commit_name, commit.hexsha)

        # Next "git gud commit" name
        if int(commit_name) > int(last_commit):
            file_operator.write_last_commit(commit_name)
Example #14
0
 def mark_visited(self):
     file_operator = operations.get_operator()
     file_operator.mark_level(self, "visited")
Example #15
0
    def handle_load(self, args):
        self.assert_initialized(skip_level_check=True)

        args.skill_name = args.skill_name.lower()

        if args.skill_name:
            if args.skill_name in {"next", "prev", "previous"}:
                if args.skill_name == "prev":
                    args.skill_name = "previous"

                self.assert_initialized("Cannot load {} level.".format(
                    args.skill_name))
                level = get_operator().get_level()

                if args.skill_name == "next":
                    if not args.force and not level.has_ever_been_completed():
                        handle_load_confirm()
                        return
                    level_to_load = level.next_level
                else:
                    level_to_load = level.prev_level

                if level_to_load is not None:
                    self.load_level(level_to_load)
                else:
                    if args.skill_name == "next":
                        all_levels_complete()
                    else:
                        print(
                            'Already on the first level. To reload the level, use "git gud reload".'
                        )  # noqa: E501
                    print('\nTo view levels/skills, use "git gud levels --all"'
                          )  # noqa: E501
                return

        # No matter what, the dash separates the skill and level
        if '-' in args.skill_name:
            identifier = args.skill_name + (args.level_name or '')
        else:
            identifier = args.skill_name + '-' + (args.level_name or '')
        if identifier.count('-') != 1:
            print("Load formula must not contain more than one dash.")
            return

        args.skill_name, args.level_name = identifier.split('-')

        if not args.skill_name:
            args.skill_name, loaded_level_name = get_operator() \
                    .get_level_identifier()
            print("Inferring skill from currently loaded level: {} {}".format(
                args.skill_name, loaded_level_name))
        if not args.level_name:
            args.level_name = '1'

        if args.skill_name in all_skills.keys():
            skill = all_skills[args.skill_name]
            if args.level_name in skill.keys():
                level = skill[args.level_name]
                self.load_level(level)
            else:
                print('Level "{}" does not exist.'.format(args.level_name))
                print('\nTo view levels/skills, use "git gud levels --all"')
        else:
            print('Skill "{}" does not exist'.format(args.skill_name))
            print('\nTo view levels/skills, use "git gud levels --all"')
Example #16
0
 def handle_level(self, args):
     self.assert_initialized()
     level = get_operator().get_level()
     skill = level.skill
     show_skill_tree([skill, level], expand_skills=False)
Example #17
0
 def handle_test(self, args):
     self.assert_initialized()
     level = get_operator().get_level()
     level.test()
Example #18
0
 def handle_reset(self, args):
     self.assert_initialized()
     level = get_operator().get_level()
     self.load_level(level)
Example #19
0
 def handle_goal(self, args):
     self.assert_initialized()
     get_operator().get_level().goal()
Example #20
0
 def handle_explain(self, args):
     self.assert_initialized()
     get_operator().get_level().explain()
Example #21
0
def display_staging_area_content(**kwargs):
    file_operator = operations.get_operator()
    staging_area = file_operator.get_staging_content()
    display_tree_content("Staging Area:", staging_area, **kwargs)
Example #22
0
def target_branch_str():
    file_operator = operations.get_operator()
    referred_by = file_operator.get_branches_by_commit()
    for target in referred_by:
        referred_by[target] = ", ".join(referred_by[target])
    return referred_by
Example #23
0
 def _setup(self):
     # Make sure we are not in a git repo
     file_operator = operations.get_operator()
     file_operator.destroy_repo()
Example #24
0
 def mark_partial(self):
     file_operator = operations.get_operator()
     file_operator.mark_level(self, "partial")
Example #25
0
 def _test(self):
     # Check if we are in a git repo
     file_operator = operations.get_operator()
     return file_operator.repo is not None
Example #26
0
 def get_progress(self):
     file_operator = operations.get_operator()
     return file_operator.get_level_progress(self)
Example #27
0
def display_working_directory_content(**kwargs):
    file_operator = operations.get_operator()
    working_dir = file_operator.get_working_directory_content()
    display_tree_content("Working Directory:", working_dir, **kwargs)
Example #28
0
 def is_initialized(self):
     return get_operator() is not None
Example #29
0
    def __init__(self):
        self.file_operator = get_operator(
        )  # Only gets operator if in a valid gitgud repo

        self.parser = argparse.ArgumentParser(prog='git gud')

        subparsers = self.parser.add_subparsers(title='Subcommands',
                                                metavar='<command>',
                                                dest='command')

        # TODO Add git gud help <command>, which would return the same output as git gud <command> -- help

        # TODO Display help message for subcommand when it fails.
        # ie `git gud load level1 challenge1 random-input` should have output similar to `git gud load --help`

        start_parser = subparsers.add_parser('start', help='Git started!')
        status_parser = subparsers.add_parser(
            'status', help='Print out the current level')
        instructions_parser = subparsers.add_parser(
            'instructions', help='Show the instructions for the current level')
        reset_parser = subparsers.add_parser('reset',
                                             help='Reset the current level')
        test_parser = subparsers.add_parser(
            'test',
            help=
            'Test to see if you\'ve successfully completed the current level')
        progress_parser = subparsers.add_parser(
            'progress', help='Continue to the next level')
        levels_parser = subparsers.add_parser('levels', help='List levels')
        challenges_parser = subparsers.add_parser(
            'challenges',
            help=
            'List challenges in current level or in other level if specified')
        load_parser = subparsers.add_parser(
            'load', help='Load a specific level or challenge')
        commit_parser = subparsers.add_parser(
            'commit', help='Quickly create and commit a file')
        goal_parser = subparsers.add_parser(
            'goal', help='Show a description of the current goal')
        show_tree_parser = subparsers.add_parser(
            'show-tree', help='Show the current state of the branching tree')

        start_parser.add_argument('--force', action='store_true')

        challenges_parser.add_argument('level_name',
                                       metavar='level',
                                       nargs='?')

        load_parser.add_argument('level_name',
                                 metavar='level',
                                 help='Level to load')
        load_parser.add_argument('challenge_name',
                                 metavar='challenge',
                                 nargs='?',
                                 help='Challenge to load')

        commit_parser.add_argument('file', nargs='?')

        self.command_dict = {
            'start': self.handle_start,
            'status': self.handle_status,
            'instructions': self.handle_instructions,
            'reset': self.handle_reset,
            'test': self.handle_test,
            'progress': self.handle_progress,
            'levels': self.handle_levels,
            'challenges': self.handle_challenges,
            'load': self.handle_load,
            'commit': self.handle_commit,
            'goal': self.handle_goal,
            'show_tree': self.handle_show_tree,
        }
Example #30
0
 def load_level(self, level):
     self.assert_initialized(skip_level_check=True)
     file_operator = get_operator()
     file_operator.clear_tracked_commits()
     level.setup()
     file_operator.write_level(level)