Author: kschenk
Date: Sun Nov 27 23:07:13 2011
New Revision: 1206906
URL: http://svn.apache.org/viewvc?rev=1206906&view=rev
Log:
kls -- added usk/python
Added:
incubator/ooo/ooo-site/trunk/content/udk/python/
incubator/ooo/ooo-site/trunk/content/udk/python/download/
incubator/ooo/ooo-site/trunk/content/udk/python/download/pyuno-linux-x86-0.9.2.tar.gz
(with props)
incubator/ooo/ooo-site/trunk/content/udk/python/download/pyuno-linux-x86-0.9.3.tar.gz
(with props)
incubator/ooo/ooo-site/trunk/content/udk/python/download/pyuno-win32-0.9.2.zip
(with props)
incubator/ooo/ooo-site/trunk/content/udk/python/download/pyuno-win32-0.9.3.zip
(with props)
incubator/ooo/ooo-site/trunk/content/udk/python/images/
incubator/ooo/ooo-site/trunk/content/udk/python/images/customized_setup.png
(with props)
incubator/ooo/ooo-site/trunk/content/udk/python/images/mode_component.png
(with props)
incubator/ooo/ooo-site/trunk/content/udk/python/images/mode_ipc.png (with
props)
incubator/ooo/ooo-site/trunk/content/udk/python/images/modes.sxd (with
props)
incubator/ooo/ooo-site/trunk/content/udk/python/images/optional_components.png
(with props)
incubator/ooo/ooo-site/trunk/content/udk/python/libpyuno.so.gz (with
props)
incubator/ooo/ooo-site/trunk/content/udk/python/makefile.mk
incubator/ooo/ooo-site/trunk/content/udk/python/oood/
incubator/ooo/ooo-site/trunk/content/udk/python/oood/index.html (with
props)
incubator/ooo/ooo-site/trunk/content/udk/python/oood/makefile.mk
incubator/ooo/ooo-site/trunk/content/udk/python/oood/oood-0.1.0.zip (with
props)
incubator/ooo/ooo-site/trunk/content/udk/python/oood/oood-config.xml
(with props)
incubator/ooo/ooo-site/trunk/content/udk/python/oood/oood.py (with props)
incubator/ooo/ooo-site/trunk/content/udk/python/python-bridge.html (with
props)
incubator/ooo/ooo-site/trunk/content/udk/python/pyuno-doc.zip (with props)
incubator/ooo/ooo-site/trunk/content/udk/python/samples/
incubator/ooo/ooo-site/trunk/content/udk/python/samples/Addons.xcu
incubator/ooo/ooo-site/trunk/content/udk/python/samples/biblioaccess.py
(with props)
incubator/ooo/ooo-site/trunk/content/udk/python/samples/hello_world_comp.py
(with props)
incubator/ooo/ooo-site/trunk/content/udk/python/samples/ooextract.py
(with props)
incubator/ooo/ooo-site/trunk/content/udk/python/samples/oomerge.py (with
props)
incubator/ooo/ooo-site/trunk/content/udk/python/samples/python-tokencounter-calc-addin.oxt
(with props)
incubator/ooo/ooo-site/trunk/content/udk/python/samples/swriter.py (with
props)
incubator/ooo/ooo-site/trunk/content/udk/python/samples/swritercomp.py
(with props)
incubator/ooo/ooo-site/trunk/content/udk/python/samples/swritercompclient.py
(with props)
incubator/ooo/ooo-site/trunk/content/udk/python/scriptingframework/
incubator/ooo/ooo-site/trunk/content/udk/python/scriptingframework/bilder.odp
(with props)
incubator/ooo/ooo-site/trunk/content/udk/python/scriptingframework/dynamicDialog.py
(with props)
incubator/ooo/ooo-site/trunk/content/udk/python/scriptingframework/index.html
(with props)
incubator/ooo/ooo-site/trunk/content/udk/python/scriptingframework/macro_run_dlg.PNG
(with props)
incubator/ooo/ooo-site/trunk/content/udk/python/scriptingframework/makefile.mk
incubator/ooo/ooo-site/trunk/content/udk/python/scriptingframework/push_me_python4.odt
(with props)
incubator/ooo/ooo-site/trunk/content/udk/python/scriptingframework/pyhello2.uno.pkg
(with props)
Added:
incubator/ooo/ooo-site/trunk/content/udk/python/download/pyuno-linux-x86-0.9.2.tar.gz
URL:
http://svn.apache.org/viewvc/incubator/ooo/ooo-site/trunk/content/udk/python/download/pyuno-linux-x86-0.9.2.tar.gz?rev=1206906&view=auto
==============================================================================
Binary file - no diff available.
Propchange:
incubator/ooo/ooo-site/trunk/content/udk/python/download/pyuno-linux-x86-0.9.2.tar.gz
------------------------------------------------------------------------------
svn:mime-type = application/x-gzip
Added:
incubator/ooo/ooo-site/trunk/content/udk/python/download/pyuno-linux-x86-0.9.3.tar.gz
URL:
http://svn.apache.org/viewvc/incubator/ooo/ooo-site/trunk/content/udk/python/download/pyuno-linux-x86-0.9.3.tar.gz?rev=1206906&view=auto
==============================================================================
Binary file - no diff available.
Propchange:
incubator/ooo/ooo-site/trunk/content/udk/python/download/pyuno-linux-x86-0.9.3.tar.gz
------------------------------------------------------------------------------
svn:mime-type = application/x-gzip
Added:
incubator/ooo/ooo-site/trunk/content/udk/python/download/pyuno-win32-0.9.2.zip
URL:
http://svn.apache.org/viewvc/incubator/ooo/ooo-site/trunk/content/udk/python/download/pyuno-win32-0.9.2.zip?rev=1206906&view=auto
==============================================================================
Binary file - no diff available.
Propchange:
incubator/ooo/ooo-site/trunk/content/udk/python/download/pyuno-win32-0.9.2.zip
------------------------------------------------------------------------------
svn:executable = *
Propchange:
incubator/ooo/ooo-site/trunk/content/udk/python/download/pyuno-win32-0.9.2.zip
------------------------------------------------------------------------------
svn:mime-type = application/octet-stream
Added:
incubator/ooo/ooo-site/trunk/content/udk/python/download/pyuno-win32-0.9.3.zip
URL:
http://svn.apache.org/viewvc/incubator/ooo/ooo-site/trunk/content/udk/python/download/pyuno-win32-0.9.3.zip?rev=1206906&view=auto
==============================================================================
Binary file - no diff available.
Propchange:
incubator/ooo/ooo-site/trunk/content/udk/python/download/pyuno-win32-0.9.3.zip
------------------------------------------------------------------------------
svn:executable = *
Propchange:
incubator/ooo/ooo-site/trunk/content/udk/python/download/pyuno-win32-0.9.3.zip
------------------------------------------------------------------------------
svn:mime-type = application/octet-stream
Added:
incubator/ooo/ooo-site/trunk/content/udk/python/images/customized_setup.png
URL:
http://svn.apache.org/viewvc/incubator/ooo/ooo-site/trunk/content/udk/python/images/customized_setup.png?rev=1206906&view=auto
==============================================================================
Binary file - no diff available.
Propchange:
incubator/ooo/ooo-site/trunk/content/udk/python/images/customized_setup.png
------------------------------------------------------------------------------
svn:mime-type = image/png
Added: incubator/ooo/ooo-site/trunk/content/udk/python/images/mode_component.png
URL:
http://svn.apache.org/viewvc/incubator/ooo/ooo-site/trunk/content/udk/python/images/mode_component.png?rev=1206906&view=auto
==============================================================================
Binary file - no diff available.
Propchange:
incubator/ooo/ooo-site/trunk/content/udk/python/images/mode_component.png
------------------------------------------------------------------------------
svn:mime-type = image/png
Added: incubator/ooo/ooo-site/trunk/content/udk/python/images/mode_ipc.png
URL:
http://svn.apache.org/viewvc/incubator/ooo/ooo-site/trunk/content/udk/python/images/mode_ipc.png?rev=1206906&view=auto
==============================================================================
Binary file - no diff available.
Propchange: incubator/ooo/ooo-site/trunk/content/udk/python/images/mode_ipc.png
------------------------------------------------------------------------------
svn:mime-type = image/png
Added: incubator/ooo/ooo-site/trunk/content/udk/python/images/modes.sxd
URL:
http://svn.apache.org/viewvc/incubator/ooo/ooo-site/trunk/content/udk/python/images/modes.sxd?rev=1206906&view=auto
==============================================================================
Binary file - no diff available.
Propchange: incubator/ooo/ooo-site/trunk/content/udk/python/images/modes.sxd
------------------------------------------------------------------------------
svn:mime-type = application/octet-stream
Added:
incubator/ooo/ooo-site/trunk/content/udk/python/images/optional_components.png
URL:
http://svn.apache.org/viewvc/incubator/ooo/ooo-site/trunk/content/udk/python/images/optional_components.png?rev=1206906&view=auto
==============================================================================
Binary file - no diff available.
Propchange:
incubator/ooo/ooo-site/trunk/content/udk/python/images/optional_components.png
------------------------------------------------------------------------------
svn:mime-type = image/png
Added: incubator/ooo/ooo-site/trunk/content/udk/python/libpyuno.so.gz
URL:
http://svn.apache.org/viewvc/incubator/ooo/ooo-site/trunk/content/udk/python/libpyuno.so.gz?rev=1206906&view=auto
==============================================================================
Binary file - no diff available.
Propchange: incubator/ooo/ooo-site/trunk/content/udk/python/libpyuno.so.gz
------------------------------------------------------------------------------
svn:executable = *
Propchange: incubator/ooo/ooo-site/trunk/content/udk/python/libpyuno.so.gz
------------------------------------------------------------------------------
svn:mime-type = application/x-gzip
Added: incubator/ooo/ooo-site/trunk/content/udk/python/makefile.mk
URL:
http://svn.apache.org/viewvc/incubator/ooo/ooo-site/trunk/content/udk/python/makefile.mk?rev=1206906&view=auto
==============================================================================
--- incubator/ooo/ooo-site/trunk/content/udk/python/makefile.mk (added)
+++ incubator/ooo/ooo-site/trunk/content/udk/python/makefile.mk Sun Nov 27
23:07:13 2011
@@ -0,0 +1,51 @@
+PRJNAME=udkwww
+PRJ=..
+
+.INCLUDE : settings.mk
+.INCLUDE : pyversion.mk
+
+ROOT=$(MISC)$/pyuno-doc
+SCRIPTRT_VERSION=0.1.0
+
+FILES=\
+ $(ROOT)$/python-bridge.html \
+ $(ROOT)$/images$/customized_setup.png \
+ $(ROOT)$/images$/mode_component.png \
+ $(ROOT)$/images$/mode_ipc.png \
+ $(ROOT)$/images$/optional_components.png \
+ $(ROOT)$/samples$/swriter.py \
+ $(ROOT)$/samples$/swritercomp.py \
+ $(ROOT)$/samples$/ooextract.py \
+ $(ROOT)$/samples$/oomerge.py \
+ $(ROOT)$/samples$/biblioaccess.py \
+ $(ROOT)$/samples$/swritercompclient.py \
+ $(ROOT)$/samples$/hello_world_pyuno.zip \
+ $(ROOT)$/samples$/hello-framework-python.sxp \
+ $(ROOT)$/scriptrt4python-$(SCRIPTRT_VERSION).zip
+
+$(MISC)$/pyuno-doc.zip : $(FILES)
+ -rm -f $@
+ cd $(MISC) && zip -r pyuno-doc.zip pyuno-doc
+
+$(ROOT)$/samples$/hello_world_pyuno.zip : samples$/hello_world_comp.py
samples$/Addons.xcu
+ -+$(MKDIRHIER) $(@:d)
+ -rm -f $@
+ zip $@ $<
+
+$(ROOT)$/scriptrt4python-$(SCRIPTRT_VERSION).zip : \
+ scriptingframework/runtime.py scriptingframework/Scripting.xcu
+ -+$(MKDIRHIER) $(@:d)
+ -rm -f $@
+ zip $@ $<
+
+$(ROOT)$/samples$/hello-framework-python.sxp :
scriptingframework/HelloFramework.py scriptingframework/parcel-descriptor.xml
+ -+$(MKDIRHIER) $(@:d)
+ -rm -f $@
+ +cd scriptingframework && zip ..$/$@ HelloFramework.py
parcel-descriptor.xml
+
+$(ROOT)$/% : %
+ -+$(MKDIRHIER) $(@:d)
+ -rm -f $@
+ cat $? > $@
+
+
Added: incubator/ooo/ooo-site/trunk/content/udk/python/oood/index.html
URL:
http://svn.apache.org/viewvc/incubator/ooo/ooo-site/trunk/content/udk/python/oood/index.html?rev=1206906&view=auto
==============================================================================
--- incubator/ooo/ooo-site/trunk/content/udk/python/oood/index.html (added)
+++ incubator/ooo/ooo-site/trunk/content/udk/python/oood/index.html Sun Nov 27
23:07:13 2011
@@ -0,0 +1,333 @@
+<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
+<html>
+<head>
+<title>oood.py - a simple daemon for OpenOffice.org</title>
+</head>
+<body>
+<h1>oood.py - A simple daemon for OpenOffice.org</h1>
+
+<p>oood.py is a daemon, which controls a pool of 'anonymous' office instances
+(workers).
+<p>
+The workers can be used as backend for Java/python/C++ batch
+processes for document conversion, mail merges, etc. You don't need to rewrite
your current scripts,
+a client connects to a daemon-controlled office just as if would connect to a
normal office. Up to
+now, I only checked the functionality for batch clients, for server clients
(e.g. a tomcat or zope),
+there may be some problems, you should simply try it.
+
+<p>The daemon ensures, that only one client at a time is connected to one
OpenOffice instance
+(because one OOo instance in general can't cope with more than one scripter).
Workers
+get restarted after a certain amount of uses or after office crashes.
+
+<p>A client can connect to a daemon as if it would connect to a normal
'non-daemoned' office,
+so you don't need to adapt your scripts.
+
+<p> oood.py has been implemented in pure python, but it
+uses some office components. This should make it easy to modify the daemon
+to your needs if desired.
+
+<p>
+Download: <a href="oood-0.1.0.zip">oood-0.1.0.zip</a> (less than 10k):
+<h1> State </h1>
+The daemon comes in version 0.1.0. It is in a alpha state, it has
+currently only be tested on Linux x86. It may run on other Unix
+platforms, but it is definitely known <strong>not to run on windows</strong>.
Simply try
+out to check if it is useful for you (after carefully reading this manual).
+
+<p>
+The daemon and this document is targeted at experienced OOo script developers.
+
+<h1> Security</h1>
+The daemon and its usage is in general <strong>INSECURE</strong>. Everyone,
who can connect
+to the daemon can use the underlying office instances and thus
+has full access to the machine (with the daemon's user rights) and
+via socket communication to other machines accessible via sockets
+from the worker machine.
+
+All worker instances run under the same (= the daemon's userid) meaning
+that a menace user may spy other worker office instances.
+
+<p>
+
+However, some simple limitations can be done.
+<ul>
+<li> Limiting the access to the daemon.<br/>
+ You can use the connection string to limit the access to a certain network
interface.
+ E.g. using
+
+ socket,host=localhost,port=2002;urp
+
+ means, that the daemon (and the underlying office instances) can only be
accessed
+ from the same machine, where the daemon is running on.
+
+ One may easily extend the daemon source to limit access e.g. to certain
hosts.
+
+ There is no user administration.
+
+<li> User rights <br/>
+ Create a special user for running the office instances. Limit the
+ user's rights to the absolute minimum.
+</ul>
+
+You should use this solution only in a trustworthy environments.
+
+<h1>Installation</h1>
+
+<h2> Office installation</h2>
+It is assumed, that you use an office from the 1.1.x series.
+The office daemon works on an arbitrary number of office user installations,
which
+must have been created from the same network installation with a single system
user.
+
+Ideally you create a new system user (e.g. oood) therefor, but if you just
+want to try it out, you can use your normal system user.
+
+(The following description is more or less copied from a mail by J. Barfurth
+in [email protected]).
+
+First do a new multi-user installation ( start
+
+$ setup -net
+
+) from the downloaded installation set.
+
+Afterwards, create multiple single user installations by starting
+<p>
+(use 01 instead of XX)
+<p>
+
+$ setup -d /home/oood/ooo1.1_srvXX
+
+<p>
+from within the office/program directory.
+After the setup run, edit ~/.sversionrc file and replace
+"OpenOffice.org 1.1.0" with "OpenOffice.org 1.1.0_srvXX". .
+
+Repeat these steps with XX = 02, 03, ... . You need as many installations
+as you expect concurrent users. You may also start with a low number
+and add instances later on.
+
+Afterwards, your .sversionrc file should look like
+
+<pre>
+[Versions]
+OpenOffice.org 1.1 srv01=file:///home/oood/ooo1.1_srv01
+OpenOffice.org 1.1 srv02=file:///home/oood/ooo1.1_srv02
+OpenOffice.org 1.1 srv03=file:///home/oood/ooo1.1_srv03
+</pre>
+
+<h2> Daemon installation</h2>
+Switch to the OpenOffice.org's program directory and
+extract the oood-0.1.0.zip file. Open the oood-0.1.0/oood-config.xml file
+in a text editor and add the paths of every worker instances with a
+
+<user-installation url="file:///home/oood/ooo1.1_srv01" />
+
+tag. For a start, just add one or two instances to see how the daemon is
working.
+All other settings in oood-config.xml can be left untouched. The meaning
+of the other settings are documented in the comments.
+
+<h1>Daemon administration</h1>
+<h2>Starting</h2>
+The daemon must be started with OpenOffice.org's python from within the OOo's
program
+directory.
+<p>
+
+
+$ ./python oood-0.1.0/oood.py -c oood-0.1.0/oood-config.xml run
+
+</p>
+You get the log on the stdout blocking the shell. Depending on the number of
+workers you have configured, it may
+take quite a while to start. When you get a
+
+<p>
+Accepting on <your-connection-string>
+</p>
+
+the daemon is ready to serve requests.
+
+<h2>Stopping</h2>
+
+From a different shell, start
+<p>
+$ ./python oood-0.1.0/bin/oood.py -c oood-0.1.0/config/oood-config.xml stop
+
+<p>
+
+Signals the daemon to terminate all running workers and itself.
+
+The daemon can only be stopped this way after a successful startup.
+
+<h2>Requesting status information</h2>
+<p>
+$ ./python oood-0.1.0/oood.py -c oood-0.1.0/oood-config.xml status
+<p>
+Gives you a list of workers and their state.
+
+<h1> Usage patterns </h1>
+You can now connect to the daemon with an arbitrary (Java, C++, python)
+client program in exactly the same way as you connect to a normal
+OpenOffice.org.
+
+<p>The daemon delegates your request to one of its worker offices. For the
+time of usage, this worker office is exclusively used by your client program.
+The end of usage is detected by the daemon through a breakdown
+of the interprocess bridge (which occurs, when the last
+reference is gone, the client explicitly disposes the remote bridge or
+the client process terminates).
+
+<h1> Performance</h1>
+All requests to the office are tunneled through the daemon process. This
+means an additional load on the server machine and a performance overhead
+for every request. This is typically neglectable when your call frequency
+is low (say less than 10 Calls/s), but becomes a significant overhead
+for higher call frequencies.
+
+<h1>Logging</h1>
+<h2> Log level</h2>
+<p>There is 3 log levels.</p>
+
+<table border="3" summary="Log levels">
+<tr><td>SERIOUS</td><td>Only startup information and errors get written into
the log</td></tr>
+<tr><td>INFO</td><td>information about every connect and disconnect get logged
(default)</td></tr>
+<tr><td>DETAIL</td><td>Log level mostly sensible for debugging</td></tr>
+</table>
+
+<p>Level INFO includes SERIOUS, DETAIL includes INFO and HIGH.</p>
+
+<h2> Log format </h2>
+Every line, that gets logged, has the following format
+
+<pre>
+current-time [loglevel] : Logtext
+</pre>
+
+The numbers in curly brackets (e.g. {2/5}) in the logtext signals
+the free/total number of worker processes in the pool .
+
+<h2> Startup log </h2>
+A typical startup log looks as follows ( on INFO loglevel)
+<pre>
+
+Wed Nov 26 19:11:19 2003 [SERIOUS]: Started on pid 674
+Wed Nov 26 19:11:19 2003 [INFO ]: Starting office workers ...
+Wed Nov 26 19:11:19 2003 [INFO ]: Worker-0:<oood.OfficeProcess
+ file:///home/joergl/OpenOffice.org1.1.0_instance-0;
+ pid=692;connectStr=pipe,name=oood-instance-0,usage=0> started
+Wed Nov 26 19:11:59 2003 [INFO ]: {2/2} WorkerAll instances started
+Wed Nov 26 19:11:59 2003 [SERIOUS]: Accepting on
socket,host=localhost,port=2002;urp
+
+</pre>
+First line gives the pid of the daemon process (in case
+you want to terminate the process during startup). Then follows for
+every worker process, that gets started a line showing the used
+home directory and connection string.
+
+<h2> Working log </h2>
+Below you can see a typical log of a single connect attempt:
+<pre>
+Wed Nov 26 19:24:02 2003 [INFO ]: {1/2} -> Worker-0(1 uses) serves
localhost:32770
+Wed Nov 26 19:24:13 2003 [INFO ]: localhost:32770 disconnects from Worker-0(1
uses) (used for 10.7s)
+Wed Nov 26 19:24:13 2003 [INFO ]: {2/2} <- Worker-0(1 uses) reenters pool
+
+</pre>
+
+First line states that out of the pool Worker-0 1is used to serve the incoming
+request from localhost:32770. The {1/2} indicates, that there one free worker
+left is in the pool.
+
+Second line states, that the interprocess bridge between the daemon
+and the requesting process has broken down. Additionally,
+the number of uses and the duration of the last use in seconds is shown.
+
+In case, the number of uses is less than the max-usage-count-per-instance,
+the process is simply added to the pool of available offices again (as it
+documented by the third line. The {2/2} states, that there are now exactly
+two workers in the pool again.
+
+In case the max-usage-count-per-instance is exceeded, this worker instance is
automatically
+terminated and a fresh instance is restarted. This shall tide up memory leaks.
+
+When there is no free worker left anymore and a client request comes in,
+the request is rejected and a line like the following gets logged:
+<pre>
+Sat May 22 22:28:46 2004 [SERIOUS]: {0/2} localhost:32776 rejected
+</pre>
+
+The client script simply gets a empty reference instead of the requested
object.
+<p>
+<font size="-2">
+Note: Preferably it would receive a RuntimeException with an appropriate
+message, but a bug somewhere around pyuno, the scripting components
+and the remote bridge currently prevents this (the daemons crashes
+quite fast).
+</font>
+
+<h2> Termination log </h2>
+Once daemon termination has been initiated, the log should look like the
following:
+<pre>
+Sat May 22 22:33:00 2004 [SERIOUS]: Accepting on
socket,host=localhost,port=2002;urp stopped, waiting for shutdownthread
+Sat May 22 22:33:00 2004 [INFO ]: Admin thread terminating
+Sat May 22 22:33:00 2004 [INFO ]: terminating Worker-0(1 uses)
+Sat May 22 22:33:00 2004 [INFO ]: Worker-0(1 uses) terminated
+Sat May 22 22:33:00 2004 [INFO ]: terminating Worker-1(1 uses)
+Sat May 22 22:33:00 2004 [INFO ]: Worker-1(1 uses) terminated
+Sat May 22 22:33:00 2004 [SERIOUS]: Terminating normally
+</pre>
+<h1> Robustness </h1>
+Robustness and stability is certainly a key feature of a daemon. The following
+situations are currently handled:
+
+<ul>
+<li> Running out of workers <br/>
+In case all worker instances are busy and the pool is empty, every new
+connection attempt is rejected, the client receives an empty reference
+instead of the servicemanager or componentcontext object.
+
+<p>
+<font size="-2">
+Note: Preferably it would receive a RuntimeException with an appropriate
+message, but a bug somewhere around pyuno, the scripting components
+and the remote bridge currently prevents this (the daemons crashes
+quite fast).
+</font>
+
+<p>
+The connection attempt gets logged appropriately.
+<li> A worker office crashes or deadlocks <br/>
+Before a worker reenters the pool, it is checked, whether
+it is still responsive and it checks whether a deadlock
+with the solarmutex blocks the whole office. In case
+such a situation occurred, the worker is killed and a fresh
+instance is started and added again to the pool.
+
+<p>
+The check is currently quite rudimentary, it may
+be improved in future.
+</li>
+
+<li> Worker processes are restarted after a certain amount of client uses.
This ensures,
+that an ill office instance will die sooner or later.
+</li>
+
+<li> Note: In case the daemon itself crashes (I am currently not aware of such
a situation),
+ the worker instances don't
+ terminate, an admin needs to kill the instances by hand and restart
the daemon.
+</li>
+
+</ul>
+
+<h1> License </h1>
+As you are used to when using OOo, this program is LGPL.
+
+<h1> Feedback</h1>
+Please give feedback through [email protected] mailing list.
+
+
+<h1> Author </h1>
+The daemon has been developed by <a href="mailto:[email protected]">Joerg
Budischewski</a>.
+I'd very much welcome patches for an improved daemon and would even very much
welcome someone
+taking over maintenance for the daemon.
+
+</body>
+</html>
Propchange: incubator/ooo/ooo-site/trunk/content/udk/python/oood/index.html
------------------------------------------------------------------------------
svn:eol-style = native
Added: incubator/ooo/ooo-site/trunk/content/udk/python/oood/makefile.mk
URL:
http://svn.apache.org/viewvc/incubator/ooo/ooo-site/trunk/content/udk/python/oood/makefile.mk?rev=1206906&view=auto
==============================================================================
--- incubator/ooo/ooo-site/trunk/content/udk/python/oood/makefile.mk (added)
+++ incubator/ooo/ooo-site/trunk/content/udk/python/oood/makefile.mk Sun Nov 27
23:07:13 2011
@@ -0,0 +1,26 @@
+PRJNAME=udkwww
+PRJ=../..
+
+.INCLUDE : settings.mk
+.INCLUDE : pyversion.mk
+
+VERSION=0.1.0
+
+ROOT=$(MISC)$/oood-$(VERSION)
+
+FILES=\
+ $(ROOT)/oood.py \
+ $(ROOT)/index.html \
+ $(ROOT)/oood-config.xml
+
+
+$(ROOT).zip : $(FILES)
+ -rm -f $@
+ cd $(MISC) && zip -r oood-$(VERSION).zip oood-$(VERSION)
+ md5sum $@
+
+
+$(ROOT)/% : %
+ -+$(MKDIRHIER) $(@:d)
+ rm -f $@
+ cat $< > $@
Added: incubator/ooo/ooo-site/trunk/content/udk/python/oood/oood-0.1.0.zip
URL:
http://svn.apache.org/viewvc/incubator/ooo/ooo-site/trunk/content/udk/python/oood/oood-0.1.0.zip?rev=1206906&view=auto
==============================================================================
Binary file - no diff available.
Propchange: incubator/ooo/ooo-site/trunk/content/udk/python/oood/oood-0.1.0.zip
------------------------------------------------------------------------------
svn:mime-type = application/octet-stream
Added: incubator/ooo/ooo-site/trunk/content/udk/python/oood/oood-config.xml
URL:
http://svn.apache.org/viewvc/incubator/ooo/ooo-site/trunk/content/udk/python/oood/oood-config.xml?rev=1206906&view=auto
==============================================================================
--- incubator/ooo/ooo-site/trunk/content/udk/python/oood/oood-config.xml (added)
+++ incubator/ooo/ooo-site/trunk/content/udk/python/oood/oood-config.xml Sun
Nov 27 23:07:13 2011
@@ -0,0 +1,38 @@
+<?xml version="1.0"?>
+<oood-config>
+ <!-- uncomment this to allow connects from all hosts -->
+ <!--acceptor value="socket,host=0,port=2002;urp"-->
+
+ <!-- allow connects from this machine only -->
+ <acceptor value="socket,host=localhost,port=2002;urp"/>
+
+ <!-- is used to shutdown and retrieve information from the daemon -->
+ <admin-acceptor value="socket,host=localhost,port=2001;urp"/>
+
+ <!-- path to user installations -->
+ <user-installation url="file:///home/joergl/OpenOffice.org1.1.0_instance-0"
/>
+ <user-installation url="file:///home/joergl/OpenOffice.org1.1.0_instance-1"
/>
+<!--
+ <user-installation url="file:///home/joergl/OpenOffice.org1.1.0_instance-2"
/>
+-->
+ <!-- number of seconds, that are given an OpenOffice.org worker instance to
start.
+ In case the time is exceeded, daemon will terminate (and thus signaling,
+ that there is something wrong with the overall setup)
+ -->
+ <tolerated-startuptime-per-instance value="180"/>
+
+ <!-- a concrete OOo instances gets sick with time (e.g. memory leaks,
inconsistencies,
+ aborted scripts which left documents opened, etc. ). Attribute max gives
the
+ number upper number of 'uses' by
+ a client, after which the office instance gets restarted. As a fixed
+ limit tends to lead to load peaks on certain points of time, this limit
can
+ be randomized with the random attribute.
+ -->
+ <usage-count-per-instance max="10" random="3"/>
+
+ <!-- The verbosity of the daemon.
+ Can be high (errors only),
+ info (proposed, gives some useful administration information),
+ detail (for debugging) -->
+ <logging level="info"/>
+</oood-config>
Propchange: incubator/ooo/ooo-site/trunk/content/udk/python/oood/oood-config.xml
------------------------------------------------------------------------------
svn:eol-style = native
Added: incubator/ooo/ooo-site/trunk/content/udk/python/oood/oood.py
URL:
http://svn.apache.org/viewvc/incubator/ooo/ooo-site/trunk/content/udk/python/oood/oood.py?rev=1206906&view=auto
==============================================================================
--- incubator/ooo/ooo-site/trunk/content/udk/python/oood/oood.py (added)
+++ incubator/ooo/ooo-site/trunk/content/udk/python/oood/oood.py Sun Nov 27
23:07:13 2011
@@ -0,0 +1,678 @@
+#*************************************************************************
+#
+# $RCSfile: oood.py,v $
+#
+# $Revision: 1.1 $
+#
+# last change: $Author: jbu $ $Date: 2004/10/03 17:41:40 $
+#
+# The Contents of this file are made available subject to the terms of
+# either of the following licenses
+#
+# - GNU Lesser General Public License Version 2.1
+# - Sun Industry Standards Source License Version 1.1
+#
+# Sun Microsystems Inc., October, 2000
+#
+# GNU Lesser General Public License Version 2.1
+# =============================================
+# Copyright 2000 by Sun Microsystems, Inc.
+# 901 San Antonio Road, Palo Alto, CA 94303, USA
+#
+# This library is free software; you can redistribute it and/or
+# modify it under the terms of the GNU Lesser General Public
+# License version 2.1, as published by the Free Software Foundation.
+#
+# This library is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+# Lesser General Public License for more details.
+#
+# You should have received a copy of the GNU Lesser General Public
+# License along with this library; if not, write to the Free Software
+# Foundation, Inc., 59 Temple Place, Suite 330, Boston,
+# MA 02111-1307 USA
+#
+#
+# Sun Industry Standards Source License Version 1.1
+# =================================================
+# The contents of this file are subject to the Sun Industry Standards
+# Source License Version 1.1 (the "License"); You may not use this file
+# except in compliance with the License. You may obtain a copy of the
+# License at http://www.openoffice.org/license.html.
+#
+# Software provided under this License is provided on an "AS IS" basis,
+# WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING,
+# WITHOUT LIMITATION, WARRANTIES THAT THE SOFTWARE IS FREE OF DEFECTS,
+# MERCHANTABLE, FIT FOR A PARTICULAR PURPOSE, OR NON-INFRINGING.
+# See the License for the specific provisions governing your rights and
+# obligations concerning the Software.
+#
+# The Initial Developer of the Original Code is: Joerg Budischewski
+#
+# Copyright: 2000 by Sun Microsystems, Inc.
+#
+# All Rights Reserved.
+#
+# Contributor(s): Joerg Budischewski
+#
+#*************************************************************************
+import uno
+import unohelper
+import os
+import time
+import sys
+import signal
+import threading
+import random
+
+from com.sun.star.bridge import XInstanceProvider
+from com.sun.star.connection import NoConnectException,
ConnectionSetupException
+from com.sun.star.io import XStreamListener
+from com.sun.star.lang import IllegalArgumentException
+from com.sun.star.uno import RuntimeException
+from com.sun.star.xml.sax import XDocumentHandler, InputSource
+from com.sun.star.io import XInputStream
+from com.sun.star.container import XNameAccess
+from com.sun.star.beans import NamedValue
+
+SERIOUS = 0
+INFO = 1
+DETAIL = 2
+LEVEL2STRING = { SERIOUS : "SERIOUS", INFO : "INFO " , DETAIL : "DETAIL " }
+COMMANDS = ( "run", "stop" , "status" )
+cmd = None
+configfile = None
+
+def usage():
+ print "usage: oood.py -c config-file run|stop|status"
+ print " daemon for openoffice"
+
+
+i = 1
+while i < len(sys.argv):
+ if sys.argv[i] == "-c":
+ i = i + 1
+ configfile = sys.argv[i]
+ elif sys.argv[i] in COMMANDS:
+ cmd = sys.argv[i]
+ else:
+ usage()
+ os._exit(1)
+ i = i + 1
+
+if cmd == None or configfile == None:
+ usage()
+ os._exit(1)
+
+
+class FileInputStream( XInputStream, unohelper.Base ):
+ def __init__( self, path ):
+ self.f = file( path )
+
+ def closeInput( self):
+ self.f.close()
+
+ def skipBytes( self, nByteCount ):
+ self.f.read( nByteCount )
+
+ def readBytes( self, retSeq, nByteCount ):
+ s = self.f.read( nByteCount )
+ return len( s ) , uno.ByteSequence( s )
+
+ def readSomeBytes( self, retSeq , nByteCount ):
+ #as we never block !
+ return self.readBytes( retSeq, nByteCount )
+
+ def available( self ):
+ return 0
+
+class Config:
+ def __init__( self ):
+ self.acceptor = ""
+ self.userInstallation = ()
+ self.toleratedStartupTimePerInstance = 180
+ self.maxUsageCountPerInstance = 10
+ self.randomUsageCountPerInstance = 3
+ self.loglevel = INFO
+
+ def __str__(self):
+ return "acceptor="+self.acceptor+",
userInstallation="+str(self.userInstallation) + \
+ ", toleratedStartupTimePerInstance=" + str( \
+ self.toleratedStartupTimePerInstance ) + ",
maxUsageCountPerInstance="+ \
+ str( self.maxUsageCountPerInstance ) + ",
randomUsageCountPerInstance=" + \
+ str( self.randomUsageCountPerInstance ) + ",loglevel= "+
str(self.loglevel)
+
+class ConfigHandler( XDocumentHandler, unohelper.Base ):
+ def __init__( self ):
+ pass
+
+ def startDocument( self ):
+ self.config = Config()
+
+ def endDocument( self ):
+ pass
+
+ def startElement( self , name, attlist):
+ if name == "acceptor":
+ self.config.acceptor = attlist.getValueByIndex(0 )
+ elif name == "admin-acceptor":
+ self.config.adminAcceptor = attlist.getValueByIndex(0 )
+ elif name == "user-installation":
+ self.config.userInstallation = self.config.userInstallation + (
+ attlist.getValueByName( "url" ), )
+ elif name == "tolerated-startuptime-per-instance":
+ self.config.toleratedStartupTimePerInstance = int(
+ attlist.getValueByName( "value" ) )
+ elif name == "usage-count-per-instance":
+ self.config.maxUsageCountPerInstance = int(
+ attlist.getValueByName( "max" ) )
+ self.config.randomUsageCountPerInstance = int(
+ attlist.getValueByName( "random" ) )
+ elif name == "logging":
+ l = attlist.getValueByName( "level" )
+ if l == "info":
+ self.config.loglevel = INFO
+ elif l == "serious":
+ self.config.loglevel = SERIOUS
+ elif l == "detail":
+ self.config.loglevel = DETAIL
+ else:
+ raise RuntimeException( "Unknown loglevel " + l , None )
+
+ def endElement( self, name ):
+ pass
+
+ def characters ( self, chars ):
+ pass
+
+ def ignoreableWhitespace( self, chars ):
+ pass
+
+ def setDocumentLocator( self, locator ):
+ pass
+
+def readConfiguration( path, parser ):
+ h = ConfigHandler()
+ parser.setDocumentHandler( h )
+ parser.parseStream(
+ InputSource( FileInputStream( path ) , "", path, path ) )
+ return h.config
+
+def namedValueTupleToMap( t ):
+ m = {}
+ for i in t:
+ m[ i.Name ] = i.Value
+ return m
+
+ctx = uno.getComponentContext()
+config = readConfiguration(
+
configfile,ctx.ServiceManager.createInstance("com.sun.star.xml.sax.Parser"))
+
+if cmd == "stop":
+ uno.getComponentContext().ServiceManager.createInstance(
+ "com.sun.star.bridge.UnoUrlResolver").resolve(
+ "uno:"+config.adminAcceptor+";oood.Shutdown" )
+ os._exit(0)
+elif cmd == "status":
+ status = uno.getComponentContext().ServiceManager.createInstance(
+ "com.sun.star.bridge.UnoUrlResolver").resolve(
+ "uno:"+config.adminAcceptor+";oood.Status" )
+
+ if status == None:
+ print "Couldn't resolve status object"
+ print "Instances in daemon (free/total): " +str(status.getByName(
"available" )) + \
+ "/" + str( status.getByName( "poolsize" ) )
+
+ workers = status.getByName( "workers" )
+ print "Worker\tpid\tin use\tusages\tduration\tuser-directory"
+ for i in workers:
+ out = ""
+ m = namedValueTupleToMap( i )
+ inuse = " "
+ duration = " \t"
+ if m["usage-time"] > 0:
+ inuse = "x"
+ duration = str( round(m["usage-time" ],2) ) + "s \t"
+
+ print str( m["index"]) + "\t" + \
+ str( m["pid"] ) + " \t" + \
+ inuse +"\t" + \
+ str( m["usage"] ) + "\t" + \
+ duration +\
+ str( m["user-dir" ] )
+ os._exit(0)
+
+NULL_DEVICE = "/dev/null"
+processPool = None
+
+
+class PoolAdderThread( threading.Thread ):
+ def __init__( self, process ):
+ threading.Thread.__init__( self )
+ self.process = process
+
+ def run( self ):
+ try:
+ if not self.process.restartWhenNecessary():
+ logger.log( SERIOUS, "FATAL: could not restart worker " +
+ str(self.process) + ", terminating now !" )
+ os._exit(1)
+ processPool.append( self.process )
+ logger.log( INFO, processPool.getStateString()+" <-
"+str(self.process)+
+ " reenters pool" )
+ except Exception,e:
+ logger.log( SERIOUS, str(e) )
+
+
+class Status( unohelper.Base, XNameAccess ):
+ def __init__( self, processList ):
+ self.map = {}
+ self.map[ "poolsize" ] = len( processList )
+ available = 0
+ workers = []
+ for i in processList:
+ v = None
+ if i.timestamp == None:
+ v = NamedValue( "usage-time" , 0 )
+ available = available + 1
+ else:
+ v = NamedValue( "usage-time", time.time() - i.timestamp )
+
+ t = NamedValue( "pid", i.pid ), \
+ NamedValue( "usage", i.usage ), \
+ v, \
+ NamedValue( "user-dir" , i.userid ), \
+ NamedValue( "index", i.index )
+ workers.append( t )
+ self.map[ "workers" ] = tuple( workers )
+ self.map[ "available" ] = available
+
+ def getByName( self, name ):
+ if self.map.has_key( name ):
+ return self.map[ name ]
+ raise NoSuchElementException( "unknown element " + name, self )
+
+ def getElementNames( self ):
+ return tuple( self.map.keys() )
+
+ def hasByName( self , name ):
+ return self.map.has_key( name )
+
+ def getElementType( self ):
+ return Type()
+
+ def hasElements( self ):
+ return True
+
+class ProcessPool:
+ def __init__( self ):
+ self.lst = []
+ self.mutex = threading.Lock()
+
+ def append( self , item ):
+ self.mutex.acquire()
+ self.lst.append( item )
+ self.mutex.release()
+
+ def initializationFinished( self ):
+ self.all = tuple( self.lst )
+
+ def size( self ):
+ return len( self.lst )
+
+ def terminate( self ):
+ for i in self.all:
+ i.terminate()
+
+ def pop( self ):
+ ret = None
+ while ret == None:
+ self.mutex.acquire()
+ if len(self.lst) == 0:
+ self.mutex.release()
+ break
+ ret = self.lst.pop(0)
+ self.mutex.release()
+ if not ret.isResponsive():
+ # process has died inbetween
+ PoolAdderThread( ret ).start()
+ ret = None
+ return ret
+
+ def waitTillReady( self ):
+ for i in self.lst:
+ if not i.waitTillReady(
+ self.size() * config.toleratedStartupTimePerInstance ):
+ os._exit(1)
+ def getStateString( self):
+ global config
+ return "{" + str(self.size()) + "/" +
str(len(config.userInstallation)) + "}"
+
+class Logger:
+ def __init__( self , out, level ):
+ self.out = out
+ self.level = level
+
+ def log( self, level , text ):
+ if level <= self.level:
+ self.out.write(
+ time.asctime() + " ["+
+ LEVEL2STRING[level] +"]: " + text + "\n")
+
+processPool = ProcessPool()
+random.seed()
+logger = Logger( sys.stdout, config.loglevel )
+shutdownThread = None
+
+acceptor = ctx.ServiceManager.createInstance(
+ "com.sun.star.connection.Acceptor" )
+bridgefactory = ctx.ServiceManager.createInstance(
+ "com.sun.star.bridge.BridgeFactory" )
+connector = ctx.ServiceManager.createInstance(
+ "com.sun.star.connection.Connector" )
+
+def getConnectString( index ):
+ return "pipe,name=oood-instance-" + str(index)
+
+class AdminInstanceProvider( unohelper.Base, XInstanceProvider ):
+ def getInstance( self, name ):
+ object = None
+ if name == "oood.Shutdown":
+ global shutdownThread
+ shutdownThread = threading.Timer( 1.0, shutdown , (0,processPool) )
+ shutdownThread.start()
+ elif name == "oood.Status":
+ object = Status( processPool.all )
+ else:
+ logger.log( DETAIL, "AdminInstanceProvider: Unknown object " +name
)
+ return object
+
+class AdminAcceptorThread( threading.Thread ):
+ def __init__( self , ctx, acceptString ):
+ threading.Thread.__init__(self)
+ self.ctx = ctx
+ self.acceptString = acceptString
+ self.acceptor = self.ctx.ServiceManager.createInstance(
+ "com.sun.star.connection.Acceptor")
+
+ def run( self ):
+ logger.log( INFO, "Admin thread started" )
+ while True:
+ c = self.acceptor.accept( self.acceptString )
+ if c == None:
+ break
+ logger.log( DETAIL, "Accepted admin connection from "+
+ extractContactInfo(c.getDescription()))
+ bridgefactory.createBridge( "", "urp", c, AdminInstanceProvider() )
+
+ logger.log( INFO, "Admin thread terminating" )
+
+ def cancel( self ):
+ self.acceptor.stopAccepting( )
+
+class TerminateThread( threading.Thread ):
+ def __init__( self, ctx ):
+ threading.Thread.__init__( self )
+ self.ctx = ctx
+
+ def run( self ):
+ try:
+ self.ctx.ServiceManager.createInstance(
"com.sun.star.frame.Desktop").terminate()
+ except Exception:
+ pass
+
+class ResponsivenessChecker( threading.Thread ):
+ def __init__( self, process ):
+ threading.Thread.__init__(self)
+ self.process = process
+ self.responsive = False
+
+ def isResponsive( self ):
+ self.join( 4 )
+ return self.responsive
+
+ def run( self ):
+ try:
+ # still alive ?
+ smgr = self.process.ctx.ServiceManager
+ desktop = smgr.createInstance( "com.sun.star.frame.Desktop" )
+
+ # check for typical solar-mutex deadlock
+ desktop.getCurrentComponent()
+
+ # more checks may be added
+ self.responsive = True
+
+ except Exception,e:
+ logger.log( SERIOUS, "responsiveness-check for " + str(
self.process) +
+ " failed: " + str(e) )
+
+def calculateMaxUsageCount():
+ return config.maxUsageCountPerInstance + \
+ ( 1. - 2*random.random()) * config.randomUsageCountPerInstance
+
+def shutdown( returncode , pool ):
+ acceptor.stopAccepting()
+ pool.terminate()
+
+class OfficeProcess:
+ def __init__( self , userid, index):
+ self.userid = userid
+ self.index = index
+ self.pid = None
+ self.usage = 0
+ self.timestamp = None
+ self.bridge = None
+ self.ctx = None
+
+ def start(self):
+ self.pid = os.spawnlp(
+ os.P_NOWAIT,
+ "soffice",
+ "" , # what is this for a string ?
+ "-env:UserInstallation="+self.userid ,
+ "-headless",
+ "-norestore",
+ "-invisible",
+ "-accept="+getConnectString(self.index)+ ";urp;" )
+
+ def kill( self ):
+ if self.pid:
+ os.kill( self.pid, signal.SIGKILL )
+ logger.log( INFO, str( self ) + " killed" )
+
+ def isAlive( self ):
+ return os.system( "ps -p " + str( self.pid ) + " >" + NULL_DEVICE ) == 0
+
+ def terminate( self ):
+ if self.ctx:
+ t = TerminateThread( self.ctx )
+ logger.log( INFO, "terminating " +str( self ) )
+ t.start()
+ t.join( 4 )
+ if t.isAlive():
+ logger.log(
+ SERIOUS, repr( self ) + " did not react on terminate,
killing instance" )
+ self.kill()
+ else:
+ logger.log( INFO, str( self ) + " terminated" )
+ self.ctx = None
+
+ def terminateAndRestart( self ):
+ self.terminate()
+ time.sleep( 4 )
+ self.start()
+ if not self.waitTillReady( config.toleratedStartupTimePerInstance ):
+ logger.log( SERIOUS, "could not restart instance "+str(self)+",
terminating" )
+ return False
+ self.usage = 0
+ return True
+
+ def tryConnect( self ):
+ try:
+ con = connector.connect( getConnectString( self.index ) )
+ self.bridge = bridgefactory.createBridge( "", "urp" , con, None )
+ self.ctx = self.bridge.getInstance( "StarOffice.ComponentContext" )
+ return self.ctx != None
+ except NoConnectException,e:
+ logger.log( DETAIL, str(self)+ " not yet responsive" )
+ except Exception,e:
+ logger.log( SERIOUS , "couldn't connect to instance ("+str(e)+")" )
+ return False
+
+ def waitTillReady( self , timeout ):
+ start = time.time()
+ while not self.tryConnect( ) and time.time()-start < timeout:
+ time.sleep( 4 )
+
+ if time.time() - start > timeout:
+ return False
+ return True
+
+ def __str__(self):
+ return "Worker-" + str(self.index) + "("+str(self.usage)+" uses)"
+
+ def __repr__(self):
+ return "<oood.OfficeProcess %s;pid=%d;connectStr=%s,usage=%d>" % \
+ (self.userid,self.pid,getConnectString(self.index),self.usage)
+
+ def startUsage( self ):
+ self.usage = self.usage + 1
+ self.timestamp = time.time()
+
+ def getUsageDuration( self ):
+ return time.time() - self.timestamp
+
+ def endUsage( self ):
+ self.timestamp = None
+
+ def isResponsive( self ):
+ t = ResponsivenessChecker( self )
+ t.start()
+ return t.isResponsive()
+
+ def restartWhenNecessary( self ):
+ if not self.isResponsive():
+ logger.log( INFO, "process " + str(self) +\
+ " not responsive anymore, restarting" )
+ self.usage = 0
+ return self.terminateAndRestart()
+
+ if self.usage >= calculateMaxUsageCount():
+ logger.log( INFO, "max usage count for instance " + str(self) +\
+ " reached, restarting" )
+ return self.terminateAndRestart()
+ return True
+
+
+
+class ConnectionListener( unohelper.Base, XStreamListener ):
+ def __init__( self , officeProcess, conDesc ):
+ self.officeProcess = officeProcess
+ self.conDesc = conDesc
+
+ def clear( self ):
+ if self.officeProcess != None:
+ logger.log( INFO, self.conDesc + " disconnects from " +
+ str( self.officeProcess ) + " (used for "+
+ str(round(self.officeProcess.getUsageDuration(),1))
+"s) " )
+ self.officeProcess.endUsage( )
+ PoolAdderThread( self.officeProcess ).start()
+ self.officeProcess = None
+
+ def started( self ):
+ pass
+
+ def closed( self ):
+ self.clear()
+ def terminated( self ):
+ self.clear()
+ def error( self , exception ):
+ self.clear()
+
+
+class OfficeInstanceProvider( unohelper.Base, XInstanceProvider ):
+ def __init__( self, office ):
+ self.office = office
+
+ def getInstance( self, name ):
+ logger.log( DETAIL, "resolving name " +name )
+ object = self.office.bridge.getInstance( name )
+ return object
+
+class EmptyPoolInstanceProvider( unohelper.Base, XInstanceProvider ):
+ def getInstance( self, name ):
+ return None
+# raise RuntimeException( "No office instance available, try later" ,
None )
+
+def extractContactInfo( namevalue ):
+ lst = namevalue.split( "," )
+ host = ""
+ port = ""
+ for i in lst:
+ if i.startswith( "peerHost" ):
+ host = i.split("=")[1]
+ elif i.startswith( "peerPort" ):
+ port = i.split("=")[1]
+ return host + ":" + port
+
+
+logger.log( SERIOUS, "Started on pid " + str( os.getpid() ) )
+
+
+index = 0
+logger.log( INFO, "Starting office workers ..." )
+
+for i in config.userInstallation:
+ office = OfficeProcess( i , index )
+ office.start()
+ logger.log( INFO, "Worker-" +str(index) + ":" + repr(office) +" started")
+ processPool.append( office )
+ index = index + 1
+
+processPool.waitTillReady()
+processPool.initializationFinished()
+
+adminThread = AdminAcceptorThread( ctx, config.adminAcceptor )
+adminThread.start()
+
+logger.log( INFO , processPool.getStateString()+ " WorkerAll instances
started" )
+logger.log( SERIOUS, "Accepting on " + config.acceptor )
+
+while True:
+ con = acceptor.accept( config.acceptor )
+ if con == None:
+ break
+
+ conDesc = extractContactInfo(con.getDescription())
+ logger.log( INFO , "Incoming request for a worker from " + conDesc )
+ process = processPool.pop()
+ if process == None:
+ logger.log( SERIOUS, processPool.getStateString()+" " + conDesc +
+ " rejected, all workers are busy" )
+ bridgefactory.createBridge(
+ "", "urp", con , EmptyPoolInstanceProvider( ) )
+ else:
+ process.startUsage()
+ logger.log( INFO, processPool.getStateString()+" -> " +
+ str(process) +" serves "+conDesc)
+
+ con.addStreamListener( ConnectionListener(process,conDesc) )
+ bridgefactory.createBridge(
+ "", "urp", con , OfficeInstanceProvider( process ) )
+
+logger.log( SERIOUS, "Accepting on " + config.acceptor +
+ " stopped, waiting for shutdownthread")
+
+adminThread.cancel()
+
+if shutdownThread != None:
+ shutdownThread.join()
+
+if adminThread != None:
+ adminThread.join()
+
+logger.log( SERIOUS, "Terminating normally")
+
+
Propchange: incubator/ooo/ooo-site/trunk/content/udk/python/oood/oood.py
------------------------------------------------------------------------------
svn:eol-style = native