| 
							- #!/usr/bin/env python
 - 
 - # Licensed under the MIT license
 - # http://opensource.org/licenses/mit-license.php
 - # Copyright 2005, Tim Potter <tpot@samba.org>
 - # Copyright 2006 John-Mark Gurney <gurney_j@resnet.uroegon.edu>
 - 
 - __version__ = '$Change$'
 - # $Id$
 - 
 - # make sure debugging is initalized first, other modules can be pulled in
 - # before the "real" debug stuff is setup.  (hmm I could make this a two
 - # stage, where we simulate a namespace to either be thrown away when the
 - # time comes, or merge into the correct one)
 - import debug		# my debugging module
 - debug.doDebugging(True)	# open up debugging port
 - 
 - # Modules to import, maybe config file or something?
 - def tryloadmodule(mod):
 - 	try:
 - 		return __import__(mod)
 - 	except ImportError:
 - 		#import traceback
 - 		#traceback.print_exc()
 - 		pass
 - 
 - # ZipStorage w/ tar support should be last as it will gobble up empty files.
 - # These should be sorted by how much work they do, the least work the earlier.
 - # mpegtsmod can be really expensive.
 - modules = [
 - 	'shoutcast',
 - 	'pyvr',
 - 	'dvd',
 - 	'ZipStorage',
 - 	'mpegtsmod',
 - 	]
 - modmap = {}
 - for i in modules:
 - 	modmap[i] = tryloadmodule(i)
 - 
 - for i in modules:
 - 	debug.insertnamespace(i, modmap[i])
 - 
 - from DIDLLite import TextItem, AudioItem, VideoItem, ImageItem, Resource, StorageFolder
 - from FSStorage import FSDirectory
 - import os
 - import os.path
 - import random
 - import socket
 - import string
 - import sys
 - from twisted.python import log
 - from twisted.internet import reactor
 - 
 - def generateuuid():
 - 	if False:
 - 		return 'uuid:asdflkjewoifjslkdfj'
 - 	return ''.join([ 'uuid:'] + map(lambda x: random.choice(string.letters), xrange(20)))
 - 
 - listenAddr = sys.argv[1]
 - if len(sys.argv) > 2:
 - 	listenPort = int(sys.argv[2])
 - 	if listenPort < 1024 or listenPort > 65535:
 - 		raise ValueError, 'port out of range'
 - else:
 - 	listenPort = random.randint(10000, 65000)
 - 
 - log.startLogging(sys.stdout)
 - 
 - # Create SSDP server
 - 
 - from SSDP import SSDPServer, SSDP_PORT, SSDP_ADDR
 - 
 - s = SSDPServer()
 - debug.insertnamespace('s', s)
 - 
 - port = reactor.listenMulticast(SSDP_PORT, s, listenMultiple=True)
 - port.joinGroup(SSDP_ADDR)
 - port.setLoopbackMode(0)		# don't get our own sends
 - 
 - uuid = generateuuid()
 - urlbase = 'http://%s:%d/' % (listenAddr, listenPort)
 - 
 - # Create SOAP server
 - 
 - from twisted.web import server, resource, static
 - from ContentDirectory import ContentDirectoryServer
 - from ConnectionManager import ConnectionManagerServer
 - 
 - class WebServer(resource.Resource):
 - 	def __init__(self):
 - 		resource.Resource.__init__(self)
 - 
 - class RootDevice(static.Data):
 - 	def __init__(self):
 - 		r = {
 - 			'hostname': socket.gethostname(),
 - 			'uuid': uuid,
 - 			'urlbase': urlbase,
 - 		}
 - 		d = file('root-device.xml').read() % r
 - 		static.Data.__init__(self, d, 'text/xml')
 - 
 - root = WebServer()
 - debug.insertnamespace('root', root)
 - content = resource.Resource()
 - cds = ContentDirectoryServer('My Media Server', klass = FSDirectory, path = 'media', urlbase = os.path.join(urlbase, 'content'), webbase = content)  # This sets up the root to be the media dir so we don't have to enumerate the directory
 - debug.insertnamespace('cds', cds)
 - root.putChild('ContentDirectory', cds)
 - cds = cds.control
 - root.putChild('ConnectionManager', ConnectionManagerServer())
 - root.putChild('root-device.xml', RootDevice())
 - root.putChild('content', content)
 - 
 - 
 - # Purely to ensure some sane mime-types.  On MacOSX I need these.
 - medianode = static.File('pymediaserv')
 - medianode.contentTypes.update( {
 - 	# From: http://support.microsoft.com/kb/288102
 - 	'.asf':	'video/x-ms-asf',
 - 	'.asx':	'video/x-ms-asf',
 - 	'.wma':	'audio/x-ms-wma',
 - 	'.wax':	'audio/x-ms-wax',
 - 	'.wmv':	'video/x-ms-wmv',
 - 	'.wvx':	'video/x-ms-wvx',
 - 	'.wm':	'video/x-ms-wm',
 - 	'.wmx':	'video/x-ms-wmx',
 - 
 - 	#'.ts':	'video/mp2t',
 - 	'.ts':	'video/mpeg',	# we may want this instead of mp2t
 - 	'.m2t':	'video/mpeg',
 - 	'.m2ts':	'video/mpeg',
 - 	'.mp4':	'video/mp4',
 - 	#'.mp4':	'video/mpeg',
 - 	'.dat':	'video/mpeg',	# VCD tracks
 - 	'.ogm':	'application/ogg',
 - 	'.vob':	'video/mpeg',
 - 	#'.m4a': 'audio/mp4',   # D-Link can't seem to play AAC files.
 - })
 - del medianode
 - 
 - site = server.Site(root)
 - reactor.listenTCP(listenPort, site)
 - 
 - # we need to do this after the children are there, since we send notifies
 - s.register('%s::upnp:rootdevice' % uuid,
 - 		'upnp:rootdevice',
 - 		urlbase + 'root-device.xml')
 - 
 - s.register(uuid,
 - 		uuid,
 - 		urlbase + 'root-device.xml')
 - 
 - s.register('%s::urn:schemas-upnp-org:device:MediaServer:1' % uuid,
 - 		'urn:schemas-upnp-org:device:MediaServer:1',
 - 		urlbase + 'root-device.xml')
 - 
 - s.register('%s::urn:schemas-upnp-org:service:ConnectionManager:1' % uuid,
 - 		'urn:schemas-upnp-org:device:ConnectionManager:1',
 - 		urlbase + 'root-device.xml')
 - 
 - s.register('%s::urn:schemas-upnp-org:service:ContentDirectory:1' % uuid,
 - 		'urn:schemas-upnp-org:device:ContentDirectory:1',
 - 		urlbase + 'root-device.xml')
 - 
 - # Main loop
 - 
 - reactor.run()
 
 
  |