From 381db36ddd4aee14a6194b60a84c02060260827c Mon Sep 17 00:00:00 2001 From: Rajeesh K Nambiar Date: Wed, 29 Apr 2009 00:03:22 +0530 Subject: Payyans Doc Converter: Initial version --- payyans-doc-converter/oorunner.py | 171 +++++++++++++++++++++++++ payyans-doc-converter/payyans-doc-converter.py | 113 ++++++++++++++++ 2 files changed, 284 insertions(+) create mode 100644 payyans-doc-converter/oorunner.py create mode 100644 payyans-doc-converter/payyans-doc-converter.py (limited to 'payyans-doc-converter') diff --git a/payyans-doc-converter/oorunner.py b/payyans-doc-converter/oorunner.py new file mode 100644 index 0000000..3241fe7 --- /dev/null +++ b/payyans-doc-converter/oorunner.py @@ -0,0 +1,171 @@ +# OpenOffice utils. +# +# Based on code from: +# PyODConverter (Python OpenDocument Converter) v1.0.0 - 2008-05-05 +# Copyright (C) 2008 Mirko Nasato +# Copyright (C) 2009 Rajeesh K Nambiar +# Licensed under the GNU LGPL v2.1 - or any later version. +# http://www.gnu.org/licenses/lgpl-2.1.html +# + +import sys +import os +import time +import atexit + + +OPENOFFICE_PORT = 2002 + +# Find OpenOffice. +_oopaths=( + ('/usr/lib64/ooo-2.0/program', '/usr/lib64/ooo-2.0/program'), + ('/opt/openoffice.org3/program', '/opt/openoffice.org/basis3.0/program'), + ) + +for p in _oopaths: + if os.path.exists(p[0]): + OPENOFFICE_PATH = p[0] + OPENOFFICE_BIN = os.path.join(OPENOFFICE_PATH, 'soffice') + OPENOFFICE_LIBPATH = p[1] + + # Add to path so we can find uno. + if sys.path.count(OPENOFFICE_LIBPATH) == 0: + sys.path.insert(0, OPENOFFICE_LIBPATH) + # This is required for loadComponentFromURL + os.putenv('URE_BOOTSTRAP','vnd.sun.star.pathname:' + OPENOFFICE_PATH + '/fundamentalrc') + break + + +import uno +from com.sun.star.beans import PropertyValue +from com.sun.star.connection import NoConnectException + + +class OORunner: + """ + Start, stop, and connect to OpenOffice. + """ + def __init__(self, port=OPENOFFICE_PORT): + """ Create OORunner that connects on the specified port. """ + self.port = port + + + def connect(self, no_startup=False): + """ + Connect to OpenOffice. + If a connection cannot be established try to start OpenOffice. + """ + localContext = uno.getComponentContext() + resolver = localContext.ServiceManager.createInstanceWithContext("com.sun.star.bridge.UnoUrlResolver", localContext) + context = None + did_start = False + + n = 0 + while n < 6: + try: + context = resolver.resolve("uno:socket,host=localhost,port=%d;urp;StarOffice.ComponentContext" % self.port) + break + except NoConnectException: + pass + + # If first connect failed then try starting OpenOffice. + if n == 0: + # Exit loop if startup not desired. + if no_startup: + break + self.startup() + did_start = True + + # Pause and try again to connect + time.sleep(1) + n += 1 + + if not context: + raise Exception, "Failed to connect to OpenOffice on port %d" % self.port + + desktop = context.ServiceManager.createInstanceWithContext("com.sun.star.frame.Desktop", context) + + if not desktop: + raise Exception, "Failed to create OpenOffice desktop on port %d" % self.port + + if did_start: + _started_desktops[self.port] = desktop + + return desktop + + + def startup(self): + """ + Start a headless instance of OpenOffice. + """ + args = [OPENOFFICE_BIN, + '-accept=socket,host=localhost,port=%d;urp;StarOffice.ServiceManager' % self.port, + '-norestore', + '-nofirststartwizard', + '-nologo', + '-headless', + ] + env = {'PATH' : '/bin:/usr/bin:%s' % OPENOFFICE_PATH, + 'PYTHONPATH' : OPENOFFICE_LIBPATH, + } + + try: + pid = os.spawnve(os.P_NOWAIT, args[0], args, env) + except Exception, e: + raise Exception, "Failed to start OpenOffice on port %d: %s" % (self.port, e.message) + + if pid <= 0: + raise Exception, "Failed to start OpenOffice on port %d" % self.port + + + def shutdown(self): + """ + Shutdown OpenOffice. + """ + try: + if _started_desktops.get(self.port): + _started_desktops[self.port].terminate() + del _started_desktops[self.port] + except Exception, e: + pass + + + +# Keep track of started desktops and shut them down on exit. +_started_desktops = {} + +def _shutdown_desktops(): + """ Shutdown all OpenOffice desktops that were started by the program. """ + for port, desktop in _started_desktops.items(): + try: + if desktop: + desktop.terminate() + except Exception, e: + pass + + +atexit.register(_shutdown_desktops) + + +def oo_shutdown_if_running(port=OPENOFFICE_PORT): + """ Shutdown OpenOffice if it's running on the specified port. """ + oorunner = OORunner(port) + try: + desktop = oorunner.connect(no_startup=True) + desktop.terminate() + except Exception, e: + pass + + +def oo_properties(**args): + """ + Convert args to OpenOffice property values. + """ + props = [] + for key in args: + prop = PropertyValue() + prop.Name = key + prop.Value = args[key] + props.append(prop) + + return tuple(props) diff --git a/payyans-doc-converter/payyans-doc-converter.py b/payyans-doc-converter/payyans-doc-converter.py new file mode 100644 index 0000000..2734d88 --- /dev/null +++ b/payyans-doc-converter/payyans-doc-converter.py @@ -0,0 +1,113 @@ +#!/usr/bin/env python +# +# Copyright (C) 2009 Rajeesh K Nambiar +# +# This program is free software; you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation; either version 3 of the License, or +# at your option) any later version. +# +# This program 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 General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program; if not, write to the Free Software +# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, +# MA 02110-1301, USA. + +import sys +import os + +# import the oorunner helper module we've written +import oorunner +# Payyans +from payyans import Payyans + +class OOWrapper: + def __init__(self): + # Find OpenOffice. + _oopaths=( + ('/usr/lib64/ooo-2.0/program', '/usr/lib64/ooo-2.0/program'), + ('/opt/openoffice.org3/program', '/opt/openoffice.org/basis3.0/program'), + ) + for p in _oopaths: + if os.path.exists(p[0]): + OPENOFFICE_PATH = p[0] + OPENOFFICE_BIN = os.path.join(OPENOFFICE_PATH, 'soffice') + OPENOFFICE_LIBPATH = p[1] + + # Add to path so we can find uno. + if sys.path.count(OPENOFFICE_LIBPATH) == 0: + sys.path.insert(0, OPENOFFICE_LIBPATH) + os.putenv('URE_BOOTSTRAP','vnd.sun.star.pathname:' + OPENOFFICE_PATH + '/fundamentalrc') + # This is required for loadComponentFromURL to work properly + break + + # start the openoffice instance + oor = oorunner.OORunner() + # get the central desktop object + self.desktop = oor.connect() + self.infile = None + self.outfile = None + + def createTextFilter(self): + # Needed for FilterName - to export to TXT + import uno + from com.sun.star.beans import PropertyValue + TXT = PropertyValue() + TXT.Name = "FilterName" + TXT.Value = "Text" + return TXT + + def convertDocToText(self, docFile): + ''' Convert the Document file to Text format ''' + self.infile = os.path.abspath(docFile) + if not os.path.exists(self.infile): + raise SystemExit ("Input file doesn't exist") + + self.document = self.desktop.loadComponentFromURL("file://"+self.infile, "_blank", 0, ()) + filter = self.createTextFilter() + (fname, ext) = os.path.splitext(self.infile) + self.textfile = fname + ".txt" + self.document.storeAsURL("file://" + self.textfile, (filter,)) + + self.closeOffice() + + def closeOffice(self): + + # Close the document + self.document.dispose() + # Close the OpenOffice desktop + self.desktop.terminate() + + def covertDocWithPayyans(self, inFile, mapFile, outFile, direction): + ''' Call Payyans to do the actual conversion ''' + # @direction : a2u/u2a for ASCII-to-Unicode and vice versa + self.convertDocToText(inFile) + p=Payyans(self.textfile, os.path.abspath(outFile), os.path.abspath(mapFile)) + if not p: + raise SystemExit("Couldn't create Payyan instance") + if direction == "a2u": + p.ascii2unicode() + else: + p.unicode2ascii() + + +if __name__ == "__main__": + if sys.argv.__len__() != 5: + raise SystemExit("usage: "+sys.argv[0]+" ") + infile = sys.argv[1] + outfile = sys.argv[2] + mapfile = sys.argv[3] + direction = sys.argv[4] + if not os.path.exists(os.path.abspath(infile)): + raise SystemExit("Cannot find Input file") + if not os.path.exists(os.path.abspath(mapfile)): + raise SystemExit("Cannot find Mapping file") + if not direction in ['a2u', 'u2a']: + raise SystemExit("Direction should be either 'a2u' or 'u2a'") + + app = OOWrapper() + app.covertDocWithPayyans(infile, mapfile, outfile, direction) -- cgit