Second Try

We would be trying to create a mini git clone from this tutorial. I aspect this to go long. In general git is awesome source code manager which is wieldy use.

So first we would be creating a lib file and executing file.

Let’s create a file called wag which would have following code.

1
2
3
4
#!/usr/bin/env python3

import libwag
libwag.main()

Then we would create another file which would be libwag.py with just a main function in it.

1
2
def main():
    print ("Hello from libwag")

We would then make our wag file executable by shell chmod +x wag. Now you can run wag by

1
./wag

In output screen you would get “Hello from libwag”.

We would be using several inbuilt module which are available in python to achieve working things.

First we would be importing a module called argparse. As per docs of argparse, it is a parser for command-line options, arguments and sub-command.

We would be importing sys module for getting arguments passed to program.

Our write a git, would be command line application which would work similar to git. For example for initiating we do git init here we would do wag init.

Note: To understand things better it would be better(not required), if you read documentation of argparse and checkout tutorial given in documentation.

We’ll need to handle subcommands (as in git: init, commit, etc.) In argparse language, these are called “subparsers”. In our current program it would always take one subparsers. Our argument would get stored in a string name command. And based on this string we would call different functions which we would require for our program to work.

Note: We would need to add each parser/command to our subparser so that our parser can dected whether the command we are passing is valid or not.

After all of above our code would look like below:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
import sys
import argparse

argparser = argparse.ArgumentParser(description="Another Content Tracker")
argsubparsers = argparser.add_subparsers(title="Commands", dest="command")
argsubparsers.required = True
argsp = argsubparsers.add_parser("init", help="Initialize a new, empty repository.")

def main(argv=sys.argv[1:]):
    args = argparser.parse_args(argv)
    print(args.command)
    print("Hello from libwag")

If you would try to run above code as ./wag init it would print init and “Hello from libwag”. We would have multiple commands so, we would write a control flow to call different functions we make.

To keep things consistent we would use same nomenclature to define our functions. In our main function we would use a control flow statement then call function as per requirement. We would need to define the function we are calling.

1
2
3
4
5
6
7
8
def main(argv=sys.argv[1:]):
    args = argparser.parse_args(argv)
    if args.command == "init":
        cmd_init(args)


def cmd_init(args):
    print("Hello from init")

Now when we would call init it would call our cmd_init(args) method and do things for now just print “Hello from init”.

As we know(“I just came to know this today.”) git init also takes path as an optional argument and if path is not passed it would initialize current directory, if path is passed it would create that repository if it doesn’t exists. And initialize repo with .git directory.

We would add argument to our init command. Where we had defined our init command we would be adding code for to add an argument.

1
2
argsp = argsubparsers.add_parser("init", help="Initialize a new, empty repository.")
argsp.add_argument("path", metavar="directory", nargs="?", default=".", help="Where to create the repository.")