#!/usr/bin/env python

"""
A command line tool for creating BagIt bags on Unix systems with md5deep 
installed.

Basic usage is to give bag a directory to bag up:

    % bag my_directory

You can bag multiple directories if you wish:

    % bag directory1 directory2

Optionally you can pass metadata intended for the bag-info.txt:

    % bag --source-organization "Library of Congress" directory

For more help see:

    % bag --help 
"""

from optparse import OptionParser

import logging

import bagit

# command line options will be created for these bag-info.txt headers 
bag_info_headers = [
    'Source-Organization', 
    'Organization-Address', 
    'Contact-Name', 
    'Contact-Phone', 
    'Contact-Email',
    'External-Description', 
    'External-Identifier',
    'Bag-Size', 
    'Bag-Group-Identifier', 
    'Bag-Count',
    'Internal-Sender-Identifier', 
    'Internal-Sender-Description',
    # Bagging Date is autogenerated
    # Payload-Oxum is autogenerated
]

class BagOptionParser(OptionParser):
    def __init__(self, *args, **opts):
        self.bag_info = {}
        OptionParser.__init__(self, *args, **opts)

def bag_info_store(option, opt, value, parser):
    opt = opt.lstrip('--')
    opt_caps = '-'.join([o.capitalize() for o in opt.split('-')])
    parser.bag_info[opt_caps] = value

def make_opt_parser():
    parser = BagOptionParser(usage='usage: %prog [options] dir1 dir2 ...')
    parser.add_option('--processes', action='store', type="int", 
                      dest='processes', default=1, 
                      help='parallelize checksums generation')
    parser.add_option('--log', action='store', dest='log')
    parser.add_option('--quiet', action='store_true', dest='quiet')

    for header in bag_info_headers:
        parser.add_option('--%s' % header.lower(), type="string", 
                          action='callback', callback=bag_info_store)
    return parser

def configure_logging(opts):
    log_format="%(asctime)s - %(levelname)s - %(message)s"
    if opts.quiet:
        level = logging.ERROR
    else:
        level = logging.INFO
    if opts.log:
        logging.basicConfig(filename=opts.log, level=level, format=log_format)
    else:
        logging.basicConfig(level=level, format=log_format)

if __name__ == '__main__':
    opt_parser = make_opt_parser()
    opts, args = opt_parser.parse_args()
    configure_logging(opts)
    for bag_dir in args:
        bagit.make_bag(bag_dir, bag_info=opt_parser.bag_info, 
                       processes=opts.processes)
