#!/usr/bin/python import time import random import mmap import sys, getopt from struct import pack from collections import deque from os.path import dirname, realpath from sys import argv, path path.append(dirname(realpath(__file__)) + '/lib') from Server import Server from Event.EventHandler import EventHandler from Event.EventDispatcher import EventDispatcher from Communication.EndPoint import CommunicationEndPoint from Protocol.Http.Http import Http from Protocol.Websocket.Websocket import Websocket from LdapTree import LdapTree class Application(EventHandler): def __init__(self, hosturi, binddn, basedn, password): super(Application, self).__init__() self._event_methods = { EventDispatcher.eventId('heartbeat') : self._heartbeat, CommunicationEndPoint.eventId('new_msg') : self._handle_data, CommunicationEndPoint.eventId('close') : self._handle_close, CommunicationEndPoint.eventId('upgrade') : self._upgrade } self._websockets = [] self._wstest = open('websocket.html', 'r+b') self._wstestmm = mmap.mmap(self._wstest.fileno(), 0) random.seed() self.ldaptree = LdapTree(hosturi, binddn, basedn, password, False) def __del__(self): self._wstestmm.close() self._wstest.close() def _upgrade(self, event): self._websockets.append(event.subject) # let other also handle the upgrade .. no return True def _heartbeat(self, event): now = pack('!d', time.time()) for event.subject in self._websockets: self.issueEvent(event.subject, 'send_msg', now) return True def _handle_data(self, event): protocol = event.subject.getProtocol() if event.subject.hasProtocol(Http): if event.data.isRequest(): if event.data.getUri() == '/': resp = protocol.createResponse(event.data, 200, 'OK') resp.setBody(self._wstestmm[0:]) elif event.data.getUri() == '/ldap': resp = protocol.createResponse(event.data, 200, 'OK') resp.setHeader('Content-Type', 'image/svg+xml') resp.setBody(self.ldaptree.graph()) else: resp = protocol.createResponse(event.data, 404, 'Not Found') resp.setBody('

404 - Not Found

') self.issueEvent(event.subject, 'send_msg', resp) return True def _handle_close(self, event): if event.subject in self._websockets: print 'websocket closed...' self._websockets = [w for w in self._websockets if w!=event.subject] return True def usage(): print "Usage: " + sys.argv[0] + " ARGUMENT... [OPTIONS]... bindip bindport\n" print "Start a webserver on the given bindip and bindport. On the page a" print "tree representation of all DNs starting with a given base DN is" print "visualized." print "Only simple binds to the directory with DN and password are supported.\n" print "ARGUMENTS:\n" print " {:30s} : {:s}".format('-H, --hosturi=URI', 'The URI to the ldap server to query in the form:') print " {:30s} {:s}".format('', 'ldap[s]://host.uri[:port]') print " {:30s} : {:s}".format('-D, --binddn=DN', 'The DN to use for the LDAP bind.') print " {:30s} : {:s}".format('-p, --password=PASSWORD', 'The password to use for the LDAP bind.') print " {:30s} : {:s}\n".format('-b, --basedn=DN', 'The DN to start the tree with.') print "OPTIONS:\n" print " {:30s} : {:s}".format('-h, --help', 'Show this help page') def main(): try: opts, args = getopt.getopt( sys.argv[1:], 'hH:D:b:p:', ['help', 'hosturi=', 'binddn=', 'basedn=', 'password=']) except getopt.GetoptError as err: print str(err) usage() sys.exit(2) hosturi = binddn = basedn = password = None for o, a in opts: if o in ["-h", "--help"]: usage() sys.exit(0) elif o in ["-H", "--hosturi"]: hosturi = a elif o in ["-D", "--binddn"]: binddn = a elif o in ["-b", "--basedn"]: basedn = a elif o in ["-p", "--password"]: password = a else: print "unknown parameter: " + a usage() sys.exit(2) if not hosturi or not binddn or not basedn or not password: usage() sys.exit(2) server = Server(Application(hosturi, binddn, basedn, password)) server.bindTcp(args[0], int(args[1]), Http()) server.start(1.0) if __name__ == '__main__': main() # vim: set ft=python et ts=8 sw=4 sts=4: