# Buggy code
def _run_indexer(options):
    logging.info("Starting indexer %s:%s ..." % (options.host, options.port))
    # initialize crawler
    service = WaveformIndexer((options.host, options.port), MyHandler)
    service.log = logging
    try:
        # prepare paths
        if "," in options.data:
            paths = options.data.split(",")
        else:
            paths = [options.data]
        paths = service._prepare_paths(paths)
        if not paths:
            return
        # prepare map file
        if options.mapping_file:
            with open(options.mapping_file, "r") as f:
                data = f.readlines()
            mappings = parse_mapping_data(data)
            logging.info(
                "Parsed %d lines from mapping file %s"
                % (len(data), options.mapping_file)
            )
        else:
            mappings = {}
        # create file queue and worker processes
        manager = multiprocessing.Manager()
        in_queue = manager.dict()
        work_queue = manager.list()
        out_queue = manager.list()
        log_queue = manager.list()
        # spawn processes
        for i in range(options.number_of_cpus):
            args = (i, in_queue, work_queue, out_queue, log_queue, mappings)
            p = multiprocessing.Process(target=worker, args=args)
            p.daemon = True
            p.start()
        # connect to database
        engine = create_engine(options.db_uri, encoding="utf-8", convert_unicode=True)
        metadata = Base.metadata
        # recreate database
        if options.drop_database:
            metadata.drop_all(engine, checkfirst=True)
        metadata.create_all(engine, checkfirst=True)
        # initialize database + options
        _session = sessionmaker(bind=engine)
        service.session = _session
        service.options = options
        service.mappings = mappings
        # set queues
        service.input_queue = in_queue
        service.work_queue = work_queue
        service.output_queue = out_queue
        service.log_queue = log_queue
        service.paths = paths
        service._reset_walker()
        service._step_walker()
        service.serve_forever(options.poll_interval)
    except KeyboardInterrupt:
        quit()
    logging.info("Indexer stopped.")


# Traceback (TypeError)
2016-04-12 11:47:36,562 [INFO] Starting indexer localhost:0 ...
Traceback (most recent call last):
File "/home/richter/anaconda/bin/obspy-indexer", line 9, in <module>
load_entry_point('obspy==1.0.1', 'console_scripts', 'obspy-indexer')()
File "/home/richter/anaconda/lib/python2.7/site-packages/obspy/db/scripts/indexer.py", line 259, in main
_run_indexer(args)
File "/home/richter/anaconda/lib/python2.7/site-packages/obspy/db/scripts/indexer.py", line 146, in _run_indexer
convert_unicode=True)
File "/home/richter/anaconda/lib/python2.7/site-packages/sqlalchemy/engine/__init__.py", line 386, in create_engine
return strategy.create(*args, **kwargs)
File "/home/richter/anaconda/lib/python2.7/site-packages/sqlalchemy/engine/strategies.py", line 80, in create
dialect = dialect_cls(**dialect_args)
File "/home/richter/anaconda/lib/python2.7/site-packages/sqlalchemy/dialects/postgresql/psycopg2.py", line 546, in __init__
PGDialect.__init__(self, **kwargs)
File "/home/richter/anaconda/lib/python2.7/site-packages/sqlalchemy/dialects/postgresql/base.py", line 2022, in __init__
default.DefaultDialect.__init__(self, **kwargs)
File "/home/richter/anaconda/lib/python2.7/site-packages/sqlalchemy/engine/default.py", line 213, in __init__
encoding
File "/home/richter/anaconda/lib/python2.7/site-packages/sqlalchemy/processors.py", line 138, in to_unicode_processor_factory
return UnicodeResultProcessor(encoding).process
TypeError: __init__() argument 1 must be string, not unicode

# Fixed code
def _run_indexer(options):
    logging.info("Starting indexer %s:%s ..." % (options.host, options.port))
    # initialize crawler
    service = WaveformIndexer((options.host, options.port), MyHandler)
    service.log = logging
    try:
        # prepare paths
        if "," in options.data:
            paths = options.data.split(",")
        else:
            paths = [options.data]
        paths = service._prepare_paths(paths)
        if not paths:
            return
        # prepare map file
        if options.mapping_file:
            with open(options.mapping_file, "r") as f:
                data = f.readlines()
            mappings = parse_mapping_data(data)
            logging.info(
                "Parsed %d lines from mapping file %s"
                % (len(data), options.mapping_file)
            )
        else:
            mappings = {}
        # create file queue and worker processes
        manager = multiprocessing.Manager()
        in_queue = manager.dict()
        work_queue = manager.list()
        out_queue = manager.list()
        log_queue = manager.list()
        # spawn processes
        for i in range(options.number_of_cpus):
            args = (i, in_queue, work_queue, out_queue, log_queue, mappings)
            p = multiprocessing.Process(target=worker, args=args)
            p.daemon = True
            p.start()
        # connect to database
        engine = create_engine(
            options.db_uri, encoding=native_str("utf-8"), convert_unicode=True
        )
        metadata = Base.metadata
        # recreate database
        if options.drop_database:
            metadata.drop_all(engine, checkfirst=True)
        metadata.create_all(engine, checkfirst=True)
        # initialize database + options
        _session = sessionmaker(bind=engine)
        service.session = _session
        service.options = options
        service.mappings = mappings
        # set queues
        service.input_queue = in_queue
        service.work_queue = work_queue
        service.output_queue = out_queue
        service.log_queue = log_queue
        service.paths = paths
        service._reset_walker()
        service._step_walker()
        service.serve_forever(options.poll_interval)
    except KeyboardInterrupt:
        quit()
    logging.info("Indexer stopped.")