Sometimes when I write a little python script – with only a few lines of code – it starts growing and I keep adding functionality. When a certain threshold is reached I start thinking that there should be a logger used (instead of print) and maybe a configuration file (instead of all these commandline switches). Since python coding is not something I do on a daily basis python code is not something I come up with just like that. So I either copy & paste code from other scripts or even have to look up how exactly the logger is set up putty download , how a configuration file is loaded or how signal handler is registered. It’s always the same story and as a keen Emacs user I finally made it an end 🙂
Using emacs auto-insert-mode. In my configuration auto-insert-mode inserts the file „“ from my „~/.emacs.d/templates/“ directory and inserts into the buffer whenever I open a yet non-existing file with the .py extension:

(setq auto-insert-directory "~/.emacs.d/templates/"
      auto-insert-query nil)
(add-to-list 'auto-insert-alist '(".*\\.py[3]?$" . [ "" ]))

This works pretty well and of course hosts my nitty gritty python boiler plate that I want to see in my scripts (no matter how small they are 🙂 ):


import logging
import logging.handlers
import signal
import sys
import os
import time
import argparse

# Author     : Matthias
# Description: Python script template

class Application:

    name               = ''
    version            = ''
    log                = None
    properties         = None
    parser             = None
    args               = None

    def __init__(self):
        signal.signal(signal.SIGINT, Application.signal_int_handler)        
        parser = argparse.ArgumentParser(description="", epilog="")
        parser.add_argument("-v", "--verbose", help="Be more verbose when logging", action="store_true")
        parser.add_argument("-P", "--properties", help="A properties file for use by the application", type=str)
        parser.add_argument("-l", "--loghost", help="Name of host to receive log messages", default="")
        parser.add_argument("-p" puttygen download , "--logport", help="Port of service to receive log messages", type=int, default=logging.handlers.DEFAULT_TCP_LOGGING_PORT)
        parser.add_argument("-d", "--logdomain", help="Domain for logging", default="this-script")
        parser.add_argument("-r", "--remotelog", help="Enable remote logging with default host and port", action="store_true")
        self.args = parser.parse_args()
        self.parser = parser
    def setup_logging(self):
        self.log = logging.getLogger(self.args.logdomain)
        rootlogger = logging.getLogger()
        formatstring='%(asctime)s %(levelname)-15s %(name)s # %(message)s'
        formatter = logging.Formatter(fmt=formatstring, datefmt='%d.%m.%y %I:%M:%S')
        handler = None
        if self.args.remotelog:
            handler = logging.handlers.SocketHandler(self.loghost_name, self.loghost_port)
            handler = logging.StreamHandler(sys.stderr)
        level = logging.INFO
        if self.args.verbose:
            level = logging.DEBUG
    def read_properties(self, filename):
        """ Read the file passed as parameter as a properties file. """
        if filename:
            properties = {}
            comment_char = "#"
            seperator = ":"
            with open(filename, "rt") as f:
                for line in f:
                    l = line.strip()
                    if l and not l.startswith(comment_char):
                        key_value = l.split(seperator)
                        key = key_value[0].strip()
                        value = seperator.join(key_value[1:]).strip().strip('"') 
                        properties[key] = value 
   = properties

    def signal_int_handler(signal, frame):
        interrupt_msg = '\r\n\r\n{} {} terminated by keyboard interrupt'.format(, Application.version)

    def run(self):

def main():
    app = Application()'{} {} is starting'.format(, app.version))'{} {} is done'.format(, app.version))

if __name__ == '__main__':

# Done
# # # end of script