Hi! After studying http://wiki.pylonshq.com/display/pylonscookbook/How+to+run+Pylons+as+a+Windows+service
and inspired in the activate_workingenv function found in http://wiki.pylonshq.com/display/pylonscookbook/mod_wsgi+and+workingenv.py we finally have a working implementation of a Pylons WindowsService that works using a virtualenv. The winservice.ini has an aditional line indicating the virtauil environment's packages folder [winservice] ... virtualenv_package_root = c:\Python25\env-pylons096\Lib\site-packages The only problem that remains is to "install" many Windows services, one by ini, following the paste philosophy about sharing code and starting many instances, each defined by its own ini file. Our solution (poor man's way) is to have hardcoded in the service code the used ini. Any help is appreciated Here is the code of the WindowsService. All the magic about using virtualenv is in the "activate_virtualenv" function ------------------------------------- import os, sys import ConfigParser class DefaultSettings(object): def __init__(self, iniFileName): try: os.stat(iniFileName) except WindowsError, e: raise Exception("Create the '%s' file or add the name of the correct .ini as an extra argument to the commandline." % iniFileName ) print "Reading the configuration from '%s'." % iniFileName self.ini = iniFileName # create a config parser opject and populate it with the ini file c = ConfigParser.SafeConfigParser() c.read(self.ini) self.c = c def getDefaults(self): ''' Check for and get the default settings ''' if ( (not self.c.has_section('winservice')) or (not self.c.has_option('winservice', 'service_name')) or (not self.c.has_option('winservice', 'service_display_name')) or (not self.c.has_option('winservice', 'service_description')) ): print 'setting defaults' self.setDefaults() service_name = self.c.get('winservice', 'service_name') service_display_name = self.c.get('winservice', 'service_display_name') service_description = self.c.get('winservice', 'service_description') virtualenv_package_root = self.c.get('winservice', 'virtualenv_package_root') iniFile = self.ini return service_name, service_display_name, service_description, iniFile, virtualenv_package_root def setDefaults(self): ''' set and add the default setting to the ini file ''' if not self.c.has_section('winservice'): self.c.add_section('winservice') self.c.set('winservice', 'service_name', 'WSCGIService') self.c.set('winservice', 'service_display_name', 'WSCGI windows service') self.c.set('winservice', 'service_description', 'WSCGI windows service') cfg = file(self.ini, 'wr') self.c.write(cfg) cfg.close() print ''' you must set the winservice section service_name, service_display_name, and service_description options to define the service in the %s file ''' % self.ini sys.exit() inifilename = "winservice.ini" import pkg_resources import win32serviceutil import win32service import win32event def activate_virtualenv(package_root): import sys sys.path.insert(0, package_root) real_setuptools = open(os.path.join(package_root,'setuptools.pth ')).read().strip() sys.path.insert(0, os.path.join(package_root, real_setuptools)) # Load all distributions into the working set. from pkg_resources import working_set, Environment env = Environment(package_root) env.scan() distributions, errors = working_set.find_plugins(env) for dist in distributions: working_set.add(dist) class MyService(win32serviceutil.ServiceFramework): """NT Service.""" fullpath = os.path.realpath(__file__) here = os.path.dirname(fullpath) os.chdir(here) d = DefaultSettings(inifilename) service_name, service_display_name, service_description, iniFile, virtualenv_pkg_root = d.getDefaults() _svc_name_ = service_name _svc_display_name_ = service_display_name _svc_description_ = service_description def __init__(self, args): win32serviceutil.ServiceFramework.__init__(self, args) # create an event that SvcDoRun can wait on and SvcStop # can set. self.stop_event = win32event.CreateEvent(None, 0, 0, None) def SvcDoRun(self): activate_virtualenv(self.virtualenv_pkg_root) from paste.script.serve import ServeCommand as Server s = Server(None) #print "Starting:", s s.run([self.iniFile]) win32event.WaitForSingleObject(self.stop_event, win32event.INFINITE) def SvcStop(self): self.ReportServiceStatus(win32service.SERVICE_STOP_PENDING) #win32event.SetEvent(self.stop_event) self.ReportServiceStatus(win32service.SERVICE_STOPPED) sys.exit() if __name__ == '__main__': win32serviceutil.HandleCommandLine(MyService) --~--~---------~--~----~------------~-------~--~----~ You received this message because you are subscribed to the Google Groups "pylons-discuss" group. To post to this group, send email to [email protected] To unsubscribe from this group, send email to [EMAIL PROTECTED] For more options, visit this group at http://groups.google.com/group/pylons-discuss?hl=en -~----------~----~----~----~------~----~------~--~---
