You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@openoffice.apache.org by ja...@apache.org on 2013/01/24 13:21:39 UTC
svn commit: r1437973 [7/11] - in
/openoffice/branches/l10n/main/l10ntools/source: ./ filter/ filter/merge/
filter/utils/ help/
Added: openoffice/branches/l10n/main/l10ntools/source/help/HelpFileDocument.java
URL: http://svn.apache.org/viewvc/openoffice/branches/l10n/main/l10ntools/source/help/HelpFileDocument.java?rev=1437973&view=auto
==============================================================================
--- openoffice/branches/l10n/main/l10ntools/source/help/HelpFileDocument.java (added)
+++ openoffice/branches/l10n/main/l10ntools/source/help/HelpFileDocument.java Thu Jan 24 12:21:38 2013
@@ -0,0 +1,82 @@
+/**************************************************************
+ *
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (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.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ *
+ *************************************************************/
+
+
+
+package com.sun.star.help;
+
+import java.io.File;
+import java.io.Reader;
+import java.io.FileInputStream;
+import java.io.InputStreamReader;
+//import java.io.FileReader;
+import java.io.StringReader;
+
+import org.apache.lucene.document.Document;
+import org.apache.lucene.document.Field;
+
+/** Lucene Document for help files */
+public class HelpFileDocument
+{
+ /** Creates reader for UTF-8 files
+ */
+ private static Reader getReaderForFile( File aFile )
+ throws java.io.FileNotFoundException, java.io.UnsupportedEncodingException {
+ Reader aReader;
+ if( aFile != null ) {
+ FileInputStream fis = new FileInputStream( aFile );
+ aReader = new InputStreamReader( fis, "UTF-8" );
+ }
+ else {
+ aReader = new StringReader( "" );
+ }
+ return aReader;
+ }
+
+ /** Makes a document for a File.
+ */
+ public static Document Document( String aModule, File aCaptionFile, File aContentFile )
+ throws java.io.FileNotFoundException, java.io.UnsupportedEncodingException {
+ Document doc = new Document();
+
+ // Add the path of the file as a field named "path". Use a field that is
+ // indexed (i.e. searchable), but don't tokenize the field into words.
+ File aFile = aCaptionFile != null ? aCaptionFile : aContentFile;
+ if( aFile != null )
+ {
+ String aPath = "#HLP#" + aModule + "/" + aFile.getName();
+ doc.add(new Field("path", aPath, Field.Store.YES, Field.Index.NOT_ANALYZED));
+ }
+
+ // Add the caption of the file to a field named "caption". Specify a Reader,
+ // so that the text of the file is tokenized and indexed, but not stored.
+ doc.add( new Field( "caption", getReaderForFile( aCaptionFile ) ) );
+
+ // Add the contents of the file to a field named "content". Specify a Reader,
+ // so that the text of the file is tokenized and indexed, but not stored.
+ doc.add( new Field( "content", getReaderForFile( aContentFile ) ) );
+
+ // return the document
+ return doc;
+ }
+
+ private HelpFileDocument() {}
+}
Propchange: openoffice/branches/l10n/main/l10ntools/source/help/HelpFileDocument.java
------------------------------------------------------------------------------
svn:executable = *
Added: openoffice/branches/l10n/main/l10ntools/source/help/HelpIndexerTool.java
URL: http://svn.apache.org/viewvc/openoffice/branches/l10n/main/l10ntools/source/help/HelpIndexerTool.java?rev=1437973&view=auto
==============================================================================
--- openoffice/branches/l10n/main/l10ntools/source/help/HelpIndexerTool.java (added)
+++ openoffice/branches/l10n/main/l10ntools/source/help/HelpIndexerTool.java Thu Jan 24 12:21:38 2013
@@ -0,0 +1,408 @@
+/**************************************************************
+ *
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (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.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ *
+ *************************************************************/
+
+
+
+package com.sun.star.help;
+
+import java.io.FileInputStream;
+import java.io.FileOutputStream;
+import java.util.Arrays;
+import java.util.HashSet;
+import java.util.List;
+import java.util.zip.ZipEntry;
+import java.util.zip.ZipOutputStream;
+import java.util.zip.CRC32;
+import org.apache.lucene.analysis.standard.StandardAnalyzer;
+import org.apache.lucene.analysis.cjk.CJKAnalyzer;
+import org.apache.lucene.analysis.Analyzer;
+import org.apache.lucene.index.IndexWriter;
+import org.apache.lucene.util.Version;
+import org.apache.lucene.store.NIOFSDirectory;
+
+import java.io.File;
+import java.io.FileNotFoundException;
+import java.io.IOException;
+import java.util.Date;
+
+/**
+ When this tool is used with long path names on Windows, that is paths which start
+ with \\?\, then the caller must make sure that the path is unique. This is achieved
+ by removing '.' and '..' from the path. Paths which are created by
+ osl_getSystemPathFromFileURL fulfill this requirement. This is necessary because
+ lucene is patched to not use File.getCanonicalPath. See long_path.patch in the lucene
+ module.
+ */
+
+public class HelpIndexerTool
+{
+ public HelpIndexerTool()
+ {
+ }
+
+
+ /**
+ * @param args the command line arguments
+ */
+ public static void main( String[] args )
+ {
+ boolean bExtensionMode = false;
+ mainImpl( args, bExtensionMode );
+ }
+
+ public static void mainImpl( String[] args, boolean bExtensionMode )
+ {
+ String aDirToZipStr = "";
+ String aSrcDirStr = "";
+ String aLanguageStr = "";
+ String aModule = "";
+ String aTargetZipFileStr = "";
+ String aCfsName = "";
+ String aSegmentName = "";
+
+ // Scan arguments
+ //If this tool is invoked in the build process for extensions help,
+ //then -extension must be set.
+ boolean bExtension = false;
+ boolean bLang = false;
+ boolean bMod = false;
+ boolean bZipDir = false;
+ boolean bSrcDir = false;
+ boolean bOutput = false;
+ boolean bCfsName = false;
+ boolean bSegmentName = false;
+
+ int nArgCount = args.length;
+ for( int i = 0 ; i < nArgCount ; i++ )
+ {
+ if( "-extension".equals(args[i]) )
+ {
+ bExtension = true;
+ }
+ else if( "-lang".equals(args[i]) )
+ {
+ if( i + 1 < nArgCount )
+ {
+ aLanguageStr = args[i + 1];
+ bLang = true;
+ }
+ i++;
+ }
+ else if( "-mod".equals(args[i]) )
+ {
+ if( i + 1 < nArgCount )
+ {
+ aModule = args[i + 1];
+ bMod = true;
+ }
+ i++;
+ }
+ else if( "-zipdir".equals(args[i]) )
+ {
+ if( i + 1 < nArgCount )
+ {
+ aDirToZipStr = args[i + 1];
+ bZipDir = true;
+ }
+ i++;
+ }
+ else if( "-srcdir".equals(args[i]) )
+ {
+ if( i + 1 < nArgCount )
+ {
+ aSrcDirStr = args[i + 1];
+ bSrcDir = true;
+ }
+ i++;
+ }
+ else if( "-o".equals(args[i]) )
+ {
+ if( i + 1 < nArgCount )
+ {
+ aTargetZipFileStr = args[i + 1];
+ bOutput = true;
+ }
+ i++;
+ }
+ else if( "-checkcfsandsegname".equals(args[i]) )
+ {
+ if( i + 1 < nArgCount )
+ {
+ aCfsName = args[i + 1] + ".cfs";
+ bCfsName = true;
+ }
+ i++;
+ if( i + 1 < nArgCount )
+ {
+ aSegmentName = "segments" + args[i + 1];
+ bSegmentName = true;
+ }
+ i++;
+ if (!(bCfsName && bSegmentName))
+ {
+ System.out.println("Usage: HelpIndexer -checkcfsandsegname _0 _3 (2 arguments needed)");
+ System.exit( -1 );
+ }
+ }
+ }
+
+ if( !bLang || !bMod || !bZipDir || (!bOutput && !bExtensionMode && !bExtension) )
+ {
+ if( bExtensionMode )
+ return;
+
+ System.out.println("Usage: HelpIndexer -lang ISOLangCode -mod HelpModule -zipdir TempZipDir -o OutputZipFile");
+ System.out.println("Usage: HelpIndexer -extension -lang ISOLangCode -mod HelpModule -zipdir PathToLangDir");
+ System.exit( -1 );
+ }
+
+ String aIndexDirName = aModule + ".idxl";
+ File aIndexDir = new File( aDirToZipStr + File.separator + aIndexDirName );
+ if( !bSrcDir )
+ aSrcDirStr = aDirToZipStr;
+ File aCaptionFilesDir = new File( aSrcDirStr + File.separator + "caption" );
+ File aContentFilesDir = new File( aSrcDirStr + File.separator + "content" );
+
+ try
+ {
+ Date start = new Date();
+ Analyzer analyzer = aLanguageStr.equals("ja") ? (Analyzer)new CJKAnalyzer(Version.LUCENE_29) : (Analyzer)new StandardAnalyzer(Version.LUCENE_29);
+ IndexWriter writer = new IndexWriter( NIOFSDirectory.open(aIndexDir), analyzer, true, IndexWriter.MaxFieldLength.UNLIMITED );
+ if( !bExtensionMode )
+ System.out.println( "Lucene: Indexing to directory '" + aIndexDir + "'..." );
+ int nRet = indexDocs( writer, aModule, bExtensionMode, aCaptionFilesDir, aContentFilesDir );
+ if( nRet != -1 )
+ {
+ if( !bExtensionMode )
+ {
+ System.out.println();
+ System.out.println( "Optimizing ..." );
+ }
+ writer.optimize();
+ }
+ writer.close();
+
+ boolean bCfsFileOk = true;
+ boolean bSegmentFileOk = true;
+ if( bCfsName && bSegmentName && !bExtensionMode && nRet != -1 )
+ {
+ String aCompleteCfsFileName = aDirToZipStr + File.separator + aIndexDirName + File.separator + aCfsName;
+ String aCompleteSegmentFileName = aDirToZipStr + File.separator + aIndexDirName + File.separator + aSegmentName;
+ File aCfsFile = new File( aCompleteCfsFileName );
+ File aSegmentFile = new File( aCompleteSegmentFileName );
+ bCfsFileOk = aCfsFile.exists();
+ bSegmentFileOk = aSegmentFile.exists();
+ System.out.println( "Checking cfs file " + aCfsName+ ": " + (bCfsFileOk ? "Found" : "Not found") );
+ System.out.println( "Checking segment file " + aSegmentName+ ": " + (bSegmentFileOk ? "Found" : "Not found") );
+ }
+
+ if( bExtensionMode || bExtension)
+ {
+ if( !bSrcDir )
+ {
+ deleteRecursively( aCaptionFilesDir );
+ deleteRecursively( aContentFilesDir );
+ }
+ }
+ else
+ {
+ if( nRet == -1 )
+ deleteRecursively( aIndexDir );
+
+ if( bCfsFileOk && bSegmentFileOk )
+ System.out.println( "Zipping ..." );
+ File aDirToZipFile = new File( aDirToZipStr );
+ createZipFile( aDirToZipFile, aTargetZipFileStr );
+ deleteRecursively( aDirToZipFile );
+ }
+
+ if( !bCfsFileOk )
+ {
+ System.out.println( "cfs file check failed, terminating..." );
+ System.exit( -1 );
+ }
+
+ if( !bSegmentFileOk )
+ {
+ System.out.println( "segment file check failed, terminating..." );
+ System.exit( -1 );
+ }
+
+ Date end = new Date();
+ if( !bExtensionMode )
+ System.out.println(end.getTime() - start.getTime() + " total milliseconds");
+ }
+ catch (IOException e)
+ {
+ if( bExtensionMode )
+ return;
+
+ System.out.println(" caught a " + e.getClass() +
+ "\n with message: " + e.getMessage());
+ System.exit( -1 );
+ }
+ }
+
+ private static int indexDocs(IndexWriter writer, String aModule, boolean bExtensionMode,
+ File aCaptionFilesDir, File aContentFilesDir) throws IOException
+ {
+ if( !aCaptionFilesDir.canRead() || !aCaptionFilesDir.isDirectory() )
+ {
+ if( !bExtensionMode )
+ System.out.println( "Not found: " + aCaptionFilesDir );
+ return -1;
+ }
+ if( !aContentFilesDir.canRead() || !aContentFilesDir.isDirectory() )
+ {
+ if( !bExtensionMode )
+ System.out.println( "Not found: " + aContentFilesDir );
+ return -1;
+ }
+
+ String[] aCaptionFiles = aCaptionFilesDir.list();
+ List aCaptionFilesList = Arrays.asList( aCaptionFiles );
+ HashSet aCaptionFilesHashSet = new HashSet( aCaptionFilesList );
+
+ String[] aContentFiles = aContentFilesDir.list();
+ List aContentFilesList = Arrays.asList( aContentFiles );
+ HashSet aContentFilesHashSet = new HashSet( aContentFilesList );
+
+ // Loop over caption files and find corresponding content file
+ if( !bExtensionMode )
+ System.out.println( "Indexing, adding files" );
+ int nCaptionFilesLen = aCaptionFiles.length;
+ for( int i = 0 ; i < nCaptionFilesLen ; i++ )
+ {
+ String aCaptionFileStr = aCaptionFiles[i];
+ File aCaptionFile = new File( aCaptionFilesDir, aCaptionFileStr );
+ File aContentFile = null;
+ if( aContentFilesHashSet.contains( aCaptionFileStr ) )
+ aContentFile = new File( aContentFilesDir, aCaptionFileStr );
+
+ if( !bExtensionMode )
+ System.out.print( "." );
+ writer.addDocument( HelpFileDocument.Document( aModule, aCaptionFile, aContentFile ) );
+ }
+
+ // Loop over content files to find remaining files not mapped to caption files
+ int nContentFilesLen = aContentFiles.length;
+ for( int i = 0 ; i < nContentFilesLen ; i++ )
+ {
+ String aContentFileStr = aContentFiles[i];
+ if( !aCaptionFilesHashSet.contains( aContentFileStr ) )
+ {
+ // Not already handled in caption files loop
+ File aCaptionFile = null;
+ File aContentFile = new File( aContentFilesDir, aContentFileStr );
+ if( !bExtensionMode )
+ System.out.print( "." );
+ writer.addDocument( HelpFileDocument.Document( aModule, aCaptionFile, aContentFile ) );
+ }
+ }
+ return 0;
+ }
+
+ public static void createZipFile( File aDirToZip, String aTargetZipFileStr )
+ throws FileNotFoundException, IOException
+ {
+ FileOutputStream fos = new FileOutputStream( aTargetZipFileStr );
+ ZipOutputStream zos = new ZipOutputStream( fos );
+
+ File[] aChildrenFiles = aDirToZip.listFiles();
+ int nFileCount = aChildrenFiles.length;
+ for( int i = 0 ; i < nFileCount ; i++ )
+ addToZipRecursively( zos, aChildrenFiles[i], null );
+
+ zos.close();
+ }
+
+ public static void addToZipRecursively( ZipOutputStream zos, File aFile, String aBasePath )
+ throws FileNotFoundException, IOException
+ {
+ if( aFile.isDirectory() )
+ {
+ String aDirName = aFile.getName();
+ if( aDirName.equalsIgnoreCase( "caption" ) || aDirName.equalsIgnoreCase( "content" ) )
+ return;
+
+ File[] aChildrenFiles = aFile.listFiles();
+ String aNewBasePath = "";
+ if( aBasePath != null )
+ aNewBasePath += aBasePath + File.separator;
+ aNewBasePath += aDirName;
+
+ int nFileCount = aChildrenFiles.length;
+ for( int i = 0 ; i < nFileCount ; i++ )
+ addToZipRecursively( zos, aChildrenFiles[i], aNewBasePath );
+
+ return;
+ }
+
+ // No directory
+ // read contents of file we are going to put in the zip
+ int fileLength = (int) aFile.length();
+ FileInputStream fis = new FileInputStream( aFile );
+ byte[] wholeFile = new byte[fileLength];
+ int bytesRead = fis.read( wholeFile, 0, fileLength );
+ fis.close();
+
+ String aFileName = aFile.getName();
+ String aEntryName = "";
+ if( aBasePath != null )
+ aEntryName += aBasePath + "/";
+ aEntryName += aFileName;
+ ZipEntry aZipEntry = new ZipEntry( aEntryName );
+ aZipEntry.setTime( aFile.lastModified() );
+ aZipEntry.setSize( fileLength );
+
+ int nMethod = ( aFileName.toLowerCase().endsWith( ".jar" ) )
+ ? ZipEntry.STORED : ZipEntry.DEFLATED;
+ aZipEntry.setMethod( nMethod );
+
+ CRC32 tempCRC = new CRC32();
+ tempCRC.update( wholeFile, 0, wholeFile.length );
+ aZipEntry.setCrc( tempCRC.getValue() );
+
+ // write the contents into the zip element
+ zos.putNextEntry( aZipEntry );
+ zos.write( wholeFile, 0, fileLength );
+ zos.closeEntry();
+ }
+
+ static public boolean deleteRecursively( File aFile )
+ {
+ if( aFile.isDirectory() )
+ {
+ File[] aChildrenFiles = aFile.listFiles();
+ int nFileCount = aChildrenFiles.length;
+ for( int i = 0 ; i < nFileCount ; i++ )
+ {
+ File aChildrenFile = aChildrenFiles[i];
+ boolean bSuccess = deleteRecursively( aChildrenFile );
+ if( !bSuccess )
+ return false;
+ }
+ }
+
+ return aFile.delete();
+ }
+}
+
Propchange: openoffice/branches/l10n/main/l10ntools/source/help/HelpIndexerTool.java
------------------------------------------------------------------------------
svn:executable = *
Added: openoffice/branches/l10n/main/l10ntools/source/help/HelpLinker.cxx
URL: http://svn.apache.org/viewvc/openoffice/branches/l10n/main/l10ntools/source/help/HelpLinker.cxx?rev=1437973&view=auto
==============================================================================
--- openoffice/branches/l10n/main/l10ntools/source/help/HelpLinker.cxx (added)
+++ openoffice/branches/l10n/main/l10ntools/source/help/HelpLinker.cxx Thu Jan 24 12:21:38 2013
@@ -0,0 +1,1095 @@
+/**************************************************************
+ *
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (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.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ *
+ *************************************************************/
+
+
+
+#include "HelpCompiler.hxx"
+
+#include <map>
+
+#include <string.h>
+#include <limits.h>
+
+#include <libxslt/xslt.h>
+#include <libxslt/transform.h>
+#include <libxslt/xsltutils.h>
+#include <libxslt/functions.h>
+#include <libxslt/extensions.h>
+
+#include <sal/types.h>
+#include <osl/time.h>
+#include <rtl/bootstrap.hxx>
+
+#include <expat.h>
+
+class IndexerPreProcessor
+{
+private:
+ std::string m_aModuleName;
+ fs::path m_fsIndexBaseDir;
+ fs::path m_fsCaptionFilesDirName;
+ fs::path m_fsContentFilesDirName;
+
+ xsltStylesheetPtr m_xsltStylesheetPtrCaption;
+ xsltStylesheetPtr m_xsltStylesheetPtrContent;
+
+public:
+ IndexerPreProcessor( const std::string& aModuleName, const fs::path& fsIndexBaseDir,
+ const fs::path& idxCaptionStylesheet, const fs::path& idxContentStylesheet );
+ ~IndexerPreProcessor();
+
+ void processDocument( xmlDocPtr doc, const std::string& EncodedDocPath );
+};
+
+IndexerPreProcessor::IndexerPreProcessor
+ ( const std::string& aModuleName, const fs::path& fsIndexBaseDir,
+ const fs::path& idxCaptionStylesheet, const fs::path& idxContentStylesheet )
+ : m_aModuleName( aModuleName )
+ , m_fsIndexBaseDir( fsIndexBaseDir )
+{
+ m_fsCaptionFilesDirName = fsIndexBaseDir / "caption";
+ fs::create_directory( m_fsCaptionFilesDirName );
+
+ m_fsContentFilesDirName = fsIndexBaseDir / "content";
+ fs::create_directory( m_fsContentFilesDirName );
+
+ m_xsltStylesheetPtrCaption = xsltParseStylesheetFile
+ ((const xmlChar *)idxCaptionStylesheet.native_file_string().c_str());
+ m_xsltStylesheetPtrContent = xsltParseStylesheetFile
+ ((const xmlChar *)idxContentStylesheet.native_file_string().c_str());
+}
+
+IndexerPreProcessor::~IndexerPreProcessor()
+{
+ if( m_xsltStylesheetPtrCaption )
+ xsltFreeStylesheet( m_xsltStylesheetPtrCaption );
+ if( m_xsltStylesheetPtrContent )
+ xsltFreeStylesheet( m_xsltStylesheetPtrContent );
+}
+
+
+std::string getEncodedPath( const std::string& Path )
+{
+ rtl::OString aOStr_Path( Path.c_str() );
+ rtl::OUString aOUStr_Path( rtl::OStringToOUString
+ ( aOStr_Path, fs::getThreadTextEncoding() ) );
+ rtl::OUString aPathURL;
+ osl::File::getFileURLFromSystemPath( aOUStr_Path, aPathURL );
+ rtl::OString aOStr_PathURL( rtl::OUStringToOString
+ ( aPathURL, fs::getThreadTextEncoding() ) );
+ std::string aStdStr_PathURL( aOStr_PathURL.getStr() );
+ return aStdStr_PathURL;
+}
+
+void IndexerPreProcessor::processDocument
+ ( xmlDocPtr doc, const std::string &EncodedDocPath )
+{
+ std::string aStdStr_EncodedDocPathURL = getEncodedPath( EncodedDocPath );
+
+ if( m_xsltStylesheetPtrCaption )
+ {
+ xmlDocPtr resCaption = xsltApplyStylesheet( m_xsltStylesheetPtrCaption, doc, NULL );
+ xmlNodePtr pResNodeCaption = resCaption->xmlChildrenNode;
+ if( pResNodeCaption )
+ {
+ fs::path fsCaptionPureTextFile_docURL = m_fsCaptionFilesDirName / aStdStr_EncodedDocPathURL;
+ std::string aCaptionPureTextFileStr_docURL = fsCaptionPureTextFile_docURL.native_file_string();
+#ifdef WNT //We need _wfopen to support long file paths on Windows XP
+ FILE* pFile_docURL = _wfopen(
+ fsCaptionPureTextFile_docURL.native_file_string_w(), L"w" );
+#else
+ FILE* pFile_docURL = fopen(
+ fsCaptionPureTextFile_docURL.native_file_string().c_str(), "w" );
+#endif
+ if( pFile_docURL )
+ {
+ fprintf( pFile_docURL, "%s\n", pResNodeCaption->content );
+ fclose( pFile_docURL );
+ }
+ }
+ xmlFreeDoc(resCaption);
+ }
+
+ if( m_xsltStylesheetPtrContent )
+ {
+ xmlDocPtr resContent = xsltApplyStylesheet( m_xsltStylesheetPtrContent, doc, NULL );
+ xmlNodePtr pResNodeContent = resContent->xmlChildrenNode;
+ if( pResNodeContent )
+ {
+ fs::path fsContentPureTextFile_docURL = m_fsContentFilesDirName / aStdStr_EncodedDocPathURL;
+#ifdef WNT //We need _wfopen to support long file paths on Windows XP
+ FILE* pFile_docURL = _wfopen(
+ fsContentPureTextFile_docURL.native_file_string_w(), L"w" );
+#else
+ FILE* pFile_docURL = fopen(
+ fsContentPureTextFile_docURL.native_file_string().c_str(), "w" );
+#endif
+ if( pFile_docURL )
+ {
+ fprintf( pFile_docURL, "%s\n", pResNodeContent->content );
+ fclose( pFile_docURL );
+ }
+ }
+ xmlFreeDoc(resContent);
+ }
+}
+
+struct Data
+{
+ std::vector<std::string> _idList;
+ typedef std::vector<std::string>::const_iterator cIter;
+
+ void append(const std::string &id)
+ {
+ _idList.push_back(id);
+ }
+
+ std::string getString() const
+ {
+ std::string ret;
+ cIter aEnd = _idList.end();
+ for (cIter aIter = _idList.begin(); aIter != aEnd; ++aIter)
+ ret += *aIter + ";";
+ return ret;
+ }
+};
+
+void writeKeyValue_DBHelp( FILE* pFile, const std::string& aKeyStr, const std::string& aValueStr )
+{
+ if( pFile == NULL )
+ return;
+ char cLF = 10;
+ unsigned int nKeyLen = aKeyStr.length();
+ unsigned int nValueLen = aValueStr.length();
+ fprintf( pFile, "%x ", nKeyLen );
+ if( nKeyLen > 0 )
+ {
+ if (fwrite( aKeyStr.c_str(), 1, nKeyLen, pFile ) != nKeyLen)
+ fprintf(stderr, "fwrite to db failed\n");
+ }
+ if (fprintf( pFile, " %x ", nValueLen ) < 0)
+ fprintf(stderr, "fwrite to db failed\n");
+ if( nValueLen > 0 )
+ {
+ if (fwrite( aValueStr.c_str(), 1, nValueLen, pFile ) != nValueLen)
+ fprintf(stderr, "fwrite to db failed\n");
+ }
+ if (fprintf( pFile, "%c", cLF ) < 0)
+ fprintf(stderr, "fwrite to db failed\n");
+}
+
+class HelpKeyword
+{
+private:
+ typedef std::hash_map<std::string, Data, pref_hash> DataHashtable;
+ DataHashtable _hash;
+
+public:
+ void insert(const std::string &key, const std::string &id)
+ {
+ Data &data = _hash[key];
+ data.append(id);
+ }
+
+ void dump_DBHelp( const fs::path& rFileName )
+ {
+#ifdef WNT //We need _wfopen to support long file paths on Windows XP
+ FILE* pFile = _wfopen( rFileName.native_file_string_w(), L"wb" );
+#else
+ FILE* pFile = fopen( rFileName.native_file_string().c_str(), "wb" );
+#endif
+ if( pFile == NULL )
+ return;
+
+ DataHashtable::const_iterator aEnd = _hash.end();
+ for (DataHashtable::const_iterator aIter = _hash.begin(); aIter != aEnd; ++aIter)
+ writeKeyValue_DBHelp( pFile, aIter->first, aIter->second.getString() );
+
+ fclose( pFile );
+ }
+};
+
+class HelpLinker
+{
+public:
+ void main(std::vector<std::string> &args,
+ std::string* pExtensionPath = NULL,
+ std::string* pDestination = NULL,
+ const rtl::OUString* pOfficeHelpPath = NULL )
+
+ throw( HelpProcessingException );
+
+ HelpLinker()
+ : init(true)
+ , m_pIndexerPreProcessor(NULL)
+ {}
+ ~HelpLinker()
+ { delete m_pIndexerPreProcessor; }
+
+private:
+ int locCount, totCount;
+ Stringtable additionalFiles;
+ HashSet helpFiles;
+ fs::path sourceRoot;
+ fs::path embeddStylesheet;
+ fs::path idxCaptionStylesheet;
+ fs::path idxContentStylesheet;
+ fs::path zipdir;
+ fs::path outputFile;
+ std::string extsource;
+ std::string extdestination;
+ std::string module;
+ std::string lang;
+ std::string extensionPath;
+ std::string extensionDestination;
+ bool bExtensionMode;
+ fs::path indexDirName;
+ fs::path indexDirParentName;
+ bool init;
+ IndexerPreProcessor* m_pIndexerPreProcessor;
+ void initIndexerPreProcessor();
+ void link() throw( HelpProcessingException );
+ void addBookmark( FILE* pFile_DBHelp, std::string thishid,
+ const std::string& fileB, const std::string& anchorB,
+ const std::string& jarfileB, const std::string& titleB );
+};
+
+namespace URLEncoder
+{
+ static std::string encode(const std::string &rIn)
+ {
+ const char *good = "!$&'()*+,-.=@_";
+ static const char hex[17] = "0123456789ABCDEF";
+
+ std::string result;
+ for (size_t i=0; i < rIn.length(); ++i)
+ {
+ unsigned char c = rIn[i];
+ if (isalnum (c) || strchr (good, c))
+ result += c;
+ else {
+ result += '%';
+ result += hex[c >> 4];
+ result += hex[c & 0xf];
+ }
+ }
+ return result;
+ }
+}
+
+void HelpLinker::addBookmark( FILE* pFile_DBHelp, std::string thishid,
+ const std::string& fileB, const std::string& anchorB,
+ const std::string& jarfileB, const std::string& titleB)
+{
+ HCDBG(std::cerr << "HelpLinker::addBookmark " << thishid << " " <<
+ fileB << " " << anchorB << " " << jarfileB << " " << titleB << std::endl);
+
+ thishid = URLEncoder::encode(thishid);
+
+ int fileLen = fileB.length();
+ if (!anchorB.empty())
+ fileLen += (1 + anchorB.length());
+ int dataLen = 1 + fileLen + 1 + jarfileB.length() + 1 + titleB.length();
+
+ std::vector<unsigned char> dataB(dataLen);
+ size_t i = 0;
+ dataB[i++] = static_cast<unsigned char>(fileLen);
+ for (size_t j = 0; j < fileB.length(); ++j)
+ dataB[i++] = fileB[j];
+ if (!anchorB.empty())
+ {
+ dataB[i++] = '#';
+ for (size_t j = 0; j < anchorB.length(); ++j)
+ dataB[i++] = anchorB[j];
+ }
+ dataB[i++] = static_cast<unsigned char>(jarfileB.length());
+ for (size_t j = 0; j < jarfileB.length(); ++j)
+ dataB[i++] = jarfileB[j];
+
+ dataB[i++] = static_cast<unsigned char>(titleB.length());
+ for (size_t j = 0; j < titleB.length(); ++j)
+ dataB[i++] = titleB[j];
+
+ if( pFile_DBHelp != NULL )
+ {
+ std::string aValueStr( dataB.begin(), dataB.end() );
+ writeKeyValue_DBHelp( pFile_DBHelp, thishid, aValueStr );
+ }
+}
+
+void HelpLinker::initIndexerPreProcessor()
+{
+ if( m_pIndexerPreProcessor )
+ delete m_pIndexerPreProcessor;
+ std::string mod = module;
+ std::transform (mod.begin(), mod.end(), mod.begin(), tolower);
+ m_pIndexerPreProcessor = new IndexerPreProcessor( mod, indexDirParentName,
+ idxCaptionStylesheet, idxContentStylesheet );
+}
+
+/**
+*
+*/
+void HelpLinker::link() throw( HelpProcessingException )
+{
+ bool bIndexForExtension = true;
+
+ if( bExtensionMode )
+ {
+ //indexDirParentName = sourceRoot;
+ indexDirParentName = extensionDestination;
+ }
+ else
+ {
+ indexDirParentName = zipdir;
+ fs::create_directory(indexDirParentName);
+ }
+
+ std::string mod = module;
+ std::transform (mod.begin(), mod.end(), mod.begin(), tolower);
+
+ // do the work here
+ // continue with introduction of the overall process thing into the
+ // here all hzip files will be worked on
+ std::string appl = mod;
+ if (appl[0] == 's')
+ appl = appl.substr(1);
+
+ bool bUse_ = true;
+ if( !bExtensionMode )
+ bUse_ = false;
+
+ fs::path helpTextFileName_DBHelp(indexDirParentName / (mod + (bUse_ ? ".ht_" : ".ht")));
+#ifdef WNT
+ //We need _wfopen to support long file paths on Windows XP
+ FILE* pFileHelpText_DBHelp = _wfopen
+ ( helpTextFileName_DBHelp.native_file_string_w(), L"wb" );
+#else
+
+ FILE* pFileHelpText_DBHelp = fopen
+ ( helpTextFileName_DBHelp.native_file_string().c_str(), "wb" );
+#endif
+
+ fs::path dbBaseFileName_DBHelp(indexDirParentName / (mod + (bUse_ ? ".db_" : ".db")));
+#ifdef WNT
+ //We need _wfopen to support long file paths on Windows XP
+ FILE* pFileDbBase_DBHelp = _wfopen
+ ( dbBaseFileName_DBHelp.native_file_string_w(), L"wb" );
+#else
+ FILE* pFileDbBase_DBHelp = fopen
+ ( dbBaseFileName_DBHelp.native_file_string().c_str(), "wb" );
+#endif
+
+ fs::path keyWordFileName_DBHelp(indexDirParentName / (mod + (bUse_ ? ".key_" : ".key")));
+
+ HelpKeyword helpKeyword;
+
+ // catch HelpProcessingException to avoid locking data bases
+ try
+ {
+
+ // lastly, initialize the indexBuilder
+ if ( (!bExtensionMode || bIndexForExtension) && !helpFiles.empty())
+ initIndexerPreProcessor();
+
+ if( !bExtensionMode )
+ {
+#ifndef OS2 // YD @TODO@ crashes libc runtime :-(
+ std::cout << "Making " << outputFile.native_file_string() <<
+ " from " << helpFiles.size() << " input files" << std::endl;
+#endif
+ }
+
+ // here we start our loop over the hzip files.
+ HashSet::iterator end = helpFiles.end();
+ for (HashSet::iterator iter = helpFiles.begin(); iter != end; ++iter)
+ {
+ if( !bExtensionMode )
+ {
+ std::cout << ".";
+ std::cout.flush();
+ }
+
+ // process one file
+ // streamTable contains the streams in the hzip file
+ StreamTable streamTable;
+ const std::string &xhpFileName = *iter;
+
+ if (!bExtensionMode && xhpFileName.rfind(".xhp") != xhpFileName.length()-4)
+ {
+ // only work on .xhp - files
+ std::cerr <<
+ "ERROR: input list entry '"
+ << xhpFileName
+ << "' has the wrong extension (only files with extension .xhp "
+ << "are accepted)";
+ continue;
+ }
+
+ fs::path langsourceRoot(sourceRoot);
+ fs::path xhpFile;
+
+ if( bExtensionMode )
+ {
+ // langsourceRoot == sourceRoot for extensions
+ std::string xhpFileNameComplete( extensionPath );
+ xhpFileNameComplete.append( '/' + xhpFileName );
+ xhpFile = fs::path( xhpFileNameComplete );
+ }
+ else
+ {
+ langsourceRoot.append('/' + lang + '/');
+ xhpFile = fs::path(xhpFileName, fs::native);
+ }
+
+ HelpCompiler hc( streamTable, xhpFile, langsourceRoot,
+ embeddStylesheet, module, lang, bExtensionMode );
+
+ HCDBG(std::cerr << "before compile of " << xhpFileName << std::endl);
+ bool success = hc.compile();
+ HCDBG(std::cerr << "after compile of " << xhpFileName << std::endl);
+
+ if (!success && !bExtensionMode)
+ {
+ std::stringstream aStrStream;
+ aStrStream <<
+ "\nERROR: compiling help particle '"
+ << xhpFileName
+ << "' for language '"
+ << lang
+ << "' failed!";
+ throw HelpProcessingException( HELPPROCESSING_GENERAL_ERROR, aStrStream.str() );
+ }
+
+ const std::string documentBaseId = streamTable.document_id;
+ std::string documentPath = streamTable.document_path;
+ if (documentPath.find("/") == 0)
+ documentPath = documentPath.substr(1);
+
+ std::string documentJarfile = streamTable.document_module + ".jar";
+
+ std::string documentTitle = streamTable.document_title;
+ if (documentTitle.empty())
+ documentTitle = "<notitle>";
+
+ const std::string& fileB = documentPath;
+ const std::string& jarfileB = documentJarfile;
+ std::string& titleB = documentTitle;
+
+ // add once this as its own id.
+ addBookmark(pFileDbBase_DBHelp, documentPath, fileB, std::string(), jarfileB, titleB);
+
+ const HashSet *hidlist = streamTable.appl_hidlist;
+ if (!hidlist)
+ hidlist = streamTable.default_hidlist;
+ if (hidlist && !hidlist->empty())
+ {
+ // now iterate over all elements of the hidlist
+ HashSet::const_iterator aEnd = hidlist->end();
+ for (HashSet::const_iterator hidListIter = hidlist->begin();
+ hidListIter != aEnd; ++hidListIter)
+ {
+ std::string thishid = *hidListIter;
+
+ std::string anchorB;
+ size_t index = thishid.rfind('#');
+ if (index != std::string::npos)
+ {
+ anchorB = thishid.substr(1 + index);
+ thishid = thishid.substr(0, index);
+ }
+ addBookmark(pFileDbBase_DBHelp, thishid, fileB, anchorB, jarfileB, titleB);
+ }
+ }
+
+ // now the keywords
+ const Hashtable *anchorToLL = streamTable.appl_keywords;
+ if (!anchorToLL)
+ anchorToLL = streamTable.default_keywords;
+ if (anchorToLL && !anchorToLL->empty())
+ {
+ std::string fakedHid = URLEncoder::encode(documentPath);
+ Hashtable::const_iterator aEnd = anchorToLL->end();
+ for (Hashtable::const_iterator enumer = anchorToLL->begin();
+ enumer != aEnd; ++enumer)
+ {
+ const std::string &anchor = enumer->first;
+ addBookmark(pFileDbBase_DBHelp, documentPath, fileB,
+ anchor, jarfileB, titleB);
+ std::string totalId = fakedHid + "#" + anchor;
+ // std::cerr << hzipFileName << std::endl;
+ const LinkedList& ll = enumer->second;
+ LinkedList::const_iterator aOtherEnd = ll.end();
+ for (LinkedList::const_iterator llIter = ll.begin();
+ llIter != aOtherEnd; ++llIter)
+ {
+ helpKeyword.insert(*llIter, totalId);
+ }
+ }
+
+ }
+
+ // and last the helptexts
+ const Stringtable *helpTextHash = streamTable.appl_helptexts;
+ if (!helpTextHash)
+ helpTextHash = streamTable.default_helptexts;
+ if (helpTextHash && !helpTextHash->empty())
+ {
+ Stringtable::const_iterator aEnd = helpTextHash->end();
+ for (Stringtable::const_iterator helpTextIter = helpTextHash->begin();
+ helpTextIter != aEnd; ++helpTextIter)
+ {
+ std::string helpTextId = helpTextIter->first;
+ const std::string& helpTextText = helpTextIter->second;
+
+ helpTextId = URLEncoder::encode(helpTextId);
+
+ if( pFileHelpText_DBHelp != NULL )
+ writeKeyValue_DBHelp( pFileHelpText_DBHelp, helpTextId, helpTextText );
+ }
+ }
+
+ //IndexerPreProcessor
+ if( !bExtensionMode || bIndexForExtension )
+ {
+ // now the indexing
+ xmlDocPtr document = streamTable.appl_doc;
+ if (!document)
+ document = streamTable.default_doc;
+ if (document)
+ {
+ std::string temp = module;
+ std::transform (temp.begin(), temp.end(), temp.begin(), tolower);
+ m_pIndexerPreProcessor->processDocument(document, URLEncoder::encode(documentPath) );
+ }
+ }
+
+ } // while loop over hzip files ending
+ if( !bExtensionMode )
+ std::cout << std::endl;
+
+ } // try
+ catch( const HelpProcessingException& )
+ {
+ // catch HelpProcessingException to avoid locking data bases
+ if( pFileHelpText_DBHelp != NULL )
+ fclose( pFileHelpText_DBHelp );
+ if( pFileDbBase_DBHelp != NULL )
+ fclose( pFileDbBase_DBHelp );
+ throw;
+ }
+
+ if( pFileHelpText_DBHelp != NULL )
+ fclose( pFileHelpText_DBHelp );
+ if( pFileDbBase_DBHelp != NULL )
+ fclose( pFileDbBase_DBHelp );
+
+ helpKeyword.dump_DBHelp( keyWordFileName_DBHelp);
+
+ if( !bExtensionMode )
+ {
+ // New index
+ Stringtable::iterator aEnd = additionalFiles.end();
+ for (Stringtable::iterator enumer = additionalFiles.begin(); enumer != aEnd;
+ ++enumer)
+ {
+ const std::string &additionalFileName = enumer->second;
+ const std::string &additionalFileKey = enumer->first;
+
+ fs::path fsAdditionalFileName( additionalFileName, fs::native );
+ std::string aNativeStr = fsAdditionalFileName.native_file_string();
+ const char* pStr = aNativeStr.c_str();
+ std::cerr << pStr;
+
+ fs::path fsTargetName( indexDirParentName / additionalFileKey );
+
+ fs::copy( fsAdditionalFileName, fsTargetName );
+ }
+ }
+
+}
+
+
+void HelpLinker::main( std::vector<std::string> &args,
+ std::string* pExtensionPath, std::string* pDestination,
+ const rtl::OUString* pOfficeHelpPath )
+ throw( HelpProcessingException )
+{
+ bExtensionMode = false;
+ helpFiles.clear();
+
+ if (args.size() > 0 && args[0][0] == '@')
+ {
+ std::vector<std::string> stringList;
+ std::string strBuf;
+ std::ifstream fileReader(args[0].substr(1).c_str());
+
+ while (fileReader)
+ {
+ std::string token;
+ fileReader >> token;
+ if (!token.empty())
+ stringList.push_back(token);
+ }
+ fileReader.close();
+
+ args = stringList;
+ }
+
+ size_t i = 0;
+ bool bSrcOption = false;
+ while (i < args.size())
+ {
+ if (args[i].compare("-extlangsrc") == 0)
+ {
+ ++i;
+ if (i >= args.size())
+ {
+ std::stringstream aStrStream;
+ aStrStream << "extension source missing" << std::endl;
+ throw HelpProcessingException( HELPPROCESSING_GENERAL_ERROR, aStrStream.str() );
+ }
+ extsource = args[i];
+ }
+ else if (args[i].compare("-extlangdest") == 0)
+ {
+ //If this argument is not provided then the location provided in -extsource will
+ //also be the destination
+ ++i;
+ if (i >= args.size())
+ {
+ std::stringstream aStrStream;
+ aStrStream << "extension destination missing" << std::endl;
+ throw HelpProcessingException( HELPPROCESSING_GENERAL_ERROR, aStrStream.str() );
+ }
+ extdestination = args[i];
+ }
+ else if (args[i].compare("-src") == 0)
+ {
+ ++i;
+ if (i >= args.size())
+ {
+ std::stringstream aStrStream;
+ aStrStream << "sourceroot missing" << std::endl;
+ throw HelpProcessingException( HELPPROCESSING_GENERAL_ERROR, aStrStream.str() );
+ }
+ bSrcOption = true;
+ sourceRoot = fs::path(args[i], fs::native);
+ }
+ else if (args[i].compare("-sty") == 0)
+ {
+ ++i;
+ if (i >= args.size())
+ {
+ std::stringstream aStrStream;
+ aStrStream << "embeddingStylesheet missing" << std::endl;
+ throw HelpProcessingException( HELPPROCESSING_GENERAL_ERROR, aStrStream.str() );
+ }
+
+ embeddStylesheet = fs::path(args[i], fs::native);
+ }
+ else if (args[i].compare("-zipdir") == 0)
+ {
+ ++i;
+ if (i >= args.size())
+ {
+ std::stringstream aStrStream;
+ aStrStream << "idxtemp missing" << std::endl;
+ throw HelpProcessingException( HELPPROCESSING_GENERAL_ERROR, aStrStream.str() );
+ }
+
+ zipdir = fs::path(args[i], fs::native);
+ }
+ else if (args[i].compare("-idxcaption") == 0)
+ {
+ ++i;
+ if (i >= args.size())
+ {
+ std::stringstream aStrStream;
+ aStrStream << "idxcaption stylesheet missing" << std::endl;
+ throw HelpProcessingException( HELPPROCESSING_GENERAL_ERROR, aStrStream.str() );
+ }
+
+ idxCaptionStylesheet = fs::path(args[i], fs::native);
+ }
+ else if (args[i].compare("-idxcontent") == 0)
+ {
+ ++i;
+ if (i >= args.size())
+ {
+ std::stringstream aStrStream;
+ aStrStream << "idxcontent stylesheet missing" << std::endl;
+ throw HelpProcessingException( HELPPROCESSING_GENERAL_ERROR, aStrStream.str() );
+ }
+
+ idxContentStylesheet = fs::path(args[i], fs::native);
+ }
+ else if (args[i].compare("-o") == 0)
+ {
+ ++i;
+ if (i >= args.size())
+ {
+ std::stringstream aStrStream;
+ aStrStream << "outputfilename missing" << std::endl;
+ throw HelpProcessingException( HELPPROCESSING_GENERAL_ERROR, aStrStream.str() );
+ }
+
+ outputFile = fs::path(args[i], fs::native);
+ }
+ else if (args[i].compare("-mod") == 0)
+ {
+ ++i;
+ if (i >= args.size())
+ {
+ std::stringstream aStrStream;
+ aStrStream << "module name missing" << std::endl;
+ throw HelpProcessingException( HELPPROCESSING_GENERAL_ERROR, aStrStream.str() );
+ }
+
+ module = args[i];
+ }
+ else if (args[i].compare("-lang") == 0)
+ {
+ ++i;
+ if (i >= args.size())
+ {
+ std::stringstream aStrStream;
+ aStrStream << "language name missing" << std::endl;
+ throw HelpProcessingException( HELPPROCESSING_GENERAL_ERROR, aStrStream.str() );
+ }
+
+ lang = args[i];
+ }
+ else if (args[i].compare("-hid") == 0)
+ {
+ ++i;
+ throw HelpProcessingException( HELPPROCESSING_GENERAL_ERROR, "obsolete -hid argument used" );
+ }
+ else if (args[i].compare("-add") == 0)
+ {
+ std::string addFile, addFileUnderPath;
+ ++i;
+ if (i >= args.size())
+ {
+ std::stringstream aStrStream;
+ aStrStream << "pathname missing" << std::endl;
+ throw HelpProcessingException( HELPPROCESSING_GENERAL_ERROR, aStrStream.str() );
+ }
+
+ addFileUnderPath = args[i];
+ ++i;
+ if (i >= args.size())
+ {
+ std::stringstream aStrStream;
+ aStrStream << "pathname missing" << std::endl;
+ throw HelpProcessingException( HELPPROCESSING_GENERAL_ERROR, aStrStream.str() );
+ }
+ addFile = args[i];
+ if (!addFileUnderPath.empty() && !addFile.empty())
+ additionalFiles[addFileUnderPath] = addFile;
+ }
+ else
+ helpFiles.push_back(args[i]);
+ ++i;
+ }
+
+ //We can be called from the helplinker executable or the extension manager
+ //In the latter case extsource is not used.
+ if( (pExtensionPath && pExtensionPath->length() > 0 && pOfficeHelpPath)
+ || !extsource.empty())
+ {
+ bExtensionMode = true;
+ if (!extsource.empty())
+ {
+ //called from helplinker.exe, pExtensionPath and pOfficeHelpPath
+ //should be NULL
+ sourceRoot = fs::path(extsource, fs::native);
+ extensionPath = sourceRoot.toUTF8();
+
+ if (extdestination.empty())
+ {
+ std::stringstream aStrStream;
+ aStrStream << "-extlangdest is missing" << std::endl;
+ throw HelpProcessingException( HELPPROCESSING_GENERAL_ERROR, aStrStream.str() );
+ }
+ else
+ {
+ //Convert from system path to file URL!!!
+ fs::path p(extdestination, fs::native);
+ extensionDestination = p.toUTF8();
+ }
+ }
+ else
+ { //called from extension manager
+ extensionPath = *pExtensionPath;
+ sourceRoot = fs::path(extensionPath);
+ extensionDestination = *pDestination;
+ }
+ //check if -src option was used. This option must not be used
+ //when extension help is compiled.
+ if (bSrcOption)
+ {
+ std::stringstream aStrStream;
+ aStrStream << "-src must not be used together with -extsource missing" << std::endl;
+ throw HelpProcessingException( HELPPROCESSING_GENERAL_ERROR, aStrStream.str() );
+ }
+ }
+
+ if (!bExtensionMode && zipdir.empty())
+ {
+ std::stringstream aStrStream;
+ aStrStream << "no index dir given" << std::endl;
+ throw HelpProcessingException( HELPPROCESSING_GENERAL_ERROR, aStrStream.str() );
+ }
+
+ if (!bExtensionMode && idxCaptionStylesheet.empty()
+ || !extsource.empty() && idxCaptionStylesheet.empty())
+ {
+ //No extension mode and extension mode using commandline
+ //!extsource.empty indicates extension mode using commandline
+ // -idxcaption paramter is required
+ std::stringstream aStrStream;
+ aStrStream << "no index caption stylesheet given" << std::endl;
+ throw HelpProcessingException( HELPPROCESSING_GENERAL_ERROR, aStrStream.str() );
+ }
+ else if ( bExtensionMode && extsource.empty())
+ {
+ //This part is used when compileExtensionHelp is called from the extensions manager.
+ //If extension help is compiled using helplinker in the build process
+ rtl::OUString aIdxCaptionPathFileURL( *pOfficeHelpPath );
+ aIdxCaptionPathFileURL += rtl::OUString::createFromAscii( "/idxcaption.xsl" );
+
+ rtl::OString aOStr_IdxCaptionPathFileURL( rtl::OUStringToOString
+ ( aIdxCaptionPathFileURL, fs::getThreadTextEncoding() ) );
+ std::string aStdStr_IdxCaptionPathFileURL( aOStr_IdxCaptionPathFileURL.getStr() );
+
+ idxCaptionStylesheet = fs::path( aStdStr_IdxCaptionPathFileURL );
+ }
+
+ if (!bExtensionMode && idxContentStylesheet.empty()
+ || !extsource.empty() && idxContentStylesheet.empty())
+ {
+ //No extension mode and extension mode using commandline
+ //!extsource.empty indicates extension mode using commandline
+ // -idxcontent paramter is required
+ std::stringstream aStrStream;
+ aStrStream << "no index content stylesheet given" << std::endl;
+ throw HelpProcessingException( HELPPROCESSING_GENERAL_ERROR, aStrStream.str() );
+ }
+ else if ( bExtensionMode && extsource.empty())
+ {
+ //If extension help is compiled using helplinker in the build process
+ //then -idxcontent must be supplied
+ //This part is used when compileExtensionHelp is called from the extensions manager.
+ rtl::OUString aIdxContentPathFileURL( *pOfficeHelpPath );
+ aIdxContentPathFileURL += rtl::OUString::createFromAscii( "/idxcontent.xsl" );
+
+ rtl::OString aOStr_IdxContentPathFileURL( rtl::OUStringToOString
+ ( aIdxContentPathFileURL, fs::getThreadTextEncoding() ) );
+ std::string aStdStr_IdxContentPathFileURL( aOStr_IdxContentPathFileURL.getStr() );
+
+ idxContentStylesheet = fs::path( aStdStr_IdxContentPathFileURL );
+ }
+ if (!bExtensionMode && embeddStylesheet.empty())
+ {
+ std::stringstream aStrStream;
+ aStrStream << "no embedding resolving file given" << std::endl;
+ throw HelpProcessingException( HELPPROCESSING_GENERAL_ERROR, aStrStream.str() );
+ }
+ if (sourceRoot.empty())
+ {
+ std::stringstream aStrStream;
+ aStrStream << "no sourceroot given" << std::endl;
+ throw HelpProcessingException( HELPPROCESSING_GENERAL_ERROR, aStrStream.str() );
+ }
+ if (!bExtensionMode && outputFile.empty())
+ {
+ std::stringstream aStrStream;
+ aStrStream << "no output file given" << std::endl;
+ throw HelpProcessingException( HELPPROCESSING_GENERAL_ERROR, aStrStream.str() );
+ }
+ if (module.empty())
+ {
+ std::stringstream aStrStream;
+ aStrStream << "module missing" << std::endl;
+ throw HelpProcessingException( HELPPROCESSING_GENERAL_ERROR, aStrStream.str() );
+ }
+ if (!bExtensionMode && lang.empty())
+ {
+ std::stringstream aStrStream;
+ aStrStream << "language missing" << std::endl;
+ throw HelpProcessingException( HELPPROCESSING_GENERAL_ERROR, aStrStream.str() );
+ }
+ link();
+}
+
+int main(int argc, char**argv)
+{
+ sal_uInt32 starttime = osl_getGlobalTimer();
+ std::vector<std::string> args;
+ for (int i = 1; i < argc; ++i)
+ args.push_back(std::string(argv[i]));
+ try
+ {
+ HelpLinker* pHelpLinker = new HelpLinker();
+ pHelpLinker->main( args );
+ delete pHelpLinker;
+ }
+ catch( const HelpProcessingException& e )
+ {
+ std::cerr << e.m_aErrorMsg;
+ exit(1);
+ }
+ sal_uInt32 endtime = osl_getGlobalTimer();
+#ifndef OS2 // YD @TODO@ crashes libc runtime :-(
+ std::cout << "time taken was " << (endtime-starttime)/1000.0 << " seconds" << std::endl;
+#endif
+ return 0;
+}
+
+// Variable to set an exception in "C" StructuredXMLErrorFunction
+static const HelpProcessingException* GpXMLParsingException = NULL;
+
+extern "C" void StructuredXMLErrorFunction(void *userData, xmlErrorPtr error)
+{
+ (void)userData;
+ (void)error;
+
+ std::string aErrorMsg = error->message;
+ std::string aXMLParsingFile;
+ if( error->file != NULL )
+ aXMLParsingFile = error->file;
+ int nXMLParsingLine = error->line;
+ HelpProcessingException* pException = new HelpProcessingException( aErrorMsg, aXMLParsingFile, nXMLParsingLine );
+ GpXMLParsingException = pException;
+
+ // Reset error handler
+ xmlSetStructuredErrorFunc( NULL, NULL );
+}
+
+HelpProcessingErrorInfo& HelpProcessingErrorInfo::operator=( const struct HelpProcessingException& e )
+{
+ m_eErrorClass = e.m_eErrorClass;
+ rtl::OString tmpErrorMsg( e.m_aErrorMsg.c_str() );
+ m_aErrorMsg = rtl::OStringToOUString( tmpErrorMsg, fs::getThreadTextEncoding() );
+ rtl::OString tmpXMLParsingFile( e.m_aXMLParsingFile.c_str() );
+ m_aXMLParsingFile = rtl::OStringToOUString( tmpXMLParsingFile, fs::getThreadTextEncoding() );
+ m_nXMLParsingLine = e.m_nXMLParsingLine;
+ return *this;
+}
+
+
+// Returns true in case of success, false in case of error
+HELPLINKER_DLLPUBLIC bool compileExtensionHelp
+(
+ const rtl::OUString& aOfficeHelpPath,
+ const rtl::OUString& aExtensionName,
+ const rtl::OUString& aExtensionLanguageRoot,
+ sal_Int32 nXhpFileCount, const rtl::OUString* pXhpFiles,
+ const rtl::OUString& aDestination,
+ HelpProcessingErrorInfo& o_rHelpProcessingErrorInfo
+)
+{
+ bool bSuccess = true;
+
+ std::vector<std::string> args;
+ args.reserve(nXhpFileCount + 2);
+ args.push_back(std::string("-mod"));
+ rtl::OString aOExtensionName = rtl::OUStringToOString( aExtensionName, fs::getThreadTextEncoding() );
+ args.push_back(std::string(aOExtensionName.getStr()));
+
+ for( sal_Int32 iXhp = 0 ; iXhp < nXhpFileCount ; ++iXhp )
+ {
+ rtl::OUString aXhpFile = pXhpFiles[iXhp];
+
+ rtl::OString aOXhpFile = rtl::OUStringToOString( aXhpFile, fs::getThreadTextEncoding() );
+ args.push_back(std::string(aOXhpFile.getStr()));
+ }
+
+ rtl::OString aOExtensionLanguageRoot = rtl::OUStringToOString( aExtensionLanguageRoot, fs::getThreadTextEncoding() );
+ const char* pExtensionPath = aOExtensionLanguageRoot.getStr();
+ std::string aStdStrExtensionPath = pExtensionPath;
+ rtl::OString aODestination = rtl::OUStringToOString(aDestination, fs::getThreadTextEncoding());
+ const char* pDestination = aODestination.getStr();
+ std::string aStdStrDestination = pDestination;
+
+ // Set error handler
+ xmlSetStructuredErrorFunc( NULL, (xmlStructuredErrorFunc)StructuredXMLErrorFunction );
+ try
+ {
+ HelpLinker* pHelpLinker = new HelpLinker();
+ pHelpLinker->main( args, &aStdStrExtensionPath, &aStdStrDestination, &aOfficeHelpPath );
+ delete pHelpLinker;
+ }
+ catch( const HelpProcessingException& e )
+ {
+ if( GpXMLParsingException != NULL )
+ {
+ o_rHelpProcessingErrorInfo = *GpXMLParsingException;
+ delete GpXMLParsingException;
+ GpXMLParsingException = NULL;
+ }
+ else
+ {
+ o_rHelpProcessingErrorInfo = e;
+ }
+ bSuccess = false;
+ }
+ // Reset error handler
+ xmlSetStructuredErrorFunc( NULL, NULL );
+
+ // i83624: Tree files
+ ::rtl::OUString aTreeFileURL = aExtensionLanguageRoot;
+ aTreeFileURL += rtl::OUString::createFromAscii( "/help.tree" );
+ osl::DirectoryItem aTreeFileItem;
+ osl::FileBase::RC rcGet = osl::DirectoryItem::get( aTreeFileURL, aTreeFileItem );
+ osl::FileStatus aFileStatus( FileStatusMask_FileSize );
+ if( rcGet == osl::FileBase::E_None &&
+ aTreeFileItem.getFileStatus( aFileStatus ) == osl::FileBase::E_None &&
+ aFileStatus.isValid( FileStatusMask_FileSize ) )
+ {
+ sal_uInt64 ret, len = aFileStatus.getFileSize();
+ char* s = new char[ int(len) ]; // the buffer to hold the installed files
+ osl::File aFile( aTreeFileURL );
+ aFile.open( OpenFlag_Read );
+ aFile.read( s, len, ret );
+ aFile.close();
+
+ XML_Parser parser = XML_ParserCreate( 0 );
+ int parsed = XML_Parse( parser, s, int( len ), true );
+
+ if( parsed == 0 )
+ {
+ XML_Error nError = XML_GetErrorCode( parser );
+ o_rHelpProcessingErrorInfo.m_eErrorClass = HELPPROCESSING_XMLPARSING_ERROR;
+ o_rHelpProcessingErrorInfo.m_aErrorMsg = rtl::OUString::createFromAscii( XML_ErrorString( nError ) );;
+ o_rHelpProcessingErrorInfo.m_aXMLParsingFile = aTreeFileURL;
+ // CRAHSES!!! o_rHelpProcessingErrorInfo.m_nXMLParsingLine = XML_GetCurrentLineNumber( parser );
+ bSuccess = false;
+ }
+
+ XML_ParserFree( parser );
+ delete[] s;
+ }
+
+ return bSuccess;
+}
+
Propchange: openoffice/branches/l10n/main/l10ntools/source/help/HelpLinker.cxx
------------------------------------------------------------------------------
svn:executable = *
Added: openoffice/branches/l10n/main/l10ntools/source/help/compilehelp.hxx
URL: http://svn.apache.org/viewvc/openoffice/branches/l10n/main/l10ntools/source/help/compilehelp.hxx?rev=1437973&view=auto
==============================================================================
--- openoffice/branches/l10n/main/l10ntools/source/help/compilehelp.hxx (added)
+++ openoffice/branches/l10n/main/l10ntools/source/help/compilehelp.hxx Thu Jan 24 12:21:38 2013
@@ -0,0 +1,75 @@
+/**************************************************************
+ *
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (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.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ *
+ *************************************************************/
+
+
+
+#ifndef COMPILE_HXX
+#define COMPILE_HXX
+
+#include "sal/types.h"
+
+#if defined(HELPLINKER_DLLIMPLEMENTATION)
+#define HELPLINKER_DLLPUBLIC SAL_DLLPUBLIC_EXPORT
+#else
+#define HELPLINKER_DLLPUBLIC SAL_DLLPUBLIC_IMPORT
+#endif
+#define HELPLINKER_DLLPRIVATE SAL_DLLPRIVATE
+
+
+//#include <helplinkerdllapi.h>
+#include <rtl/ustring.hxx>
+
+enum HelpProcessingErrorClass
+{
+ HELPPROCESSING_NO_ERROR,
+ HELPPROCESSING_GENERAL_ERROR, // Missing files, options etc.
+ HELPPROCESSING_INTERNAL_ERROR, // Unexpected problems
+ HELPPROCESSING_XMLPARSING_ERROR // Errors thrown by libxml
+};
+
+struct HelpProcessingErrorInfo
+{
+ HelpProcessingErrorClass m_eErrorClass;
+ rtl::OUString m_aErrorMsg;
+ rtl::OUString m_aXMLParsingFile;
+ sal_Int32 m_nXMLParsingLine;
+
+ HelpProcessingErrorInfo( void )
+ : m_eErrorClass( HELPPROCESSING_NO_ERROR )
+ , m_nXMLParsingLine( -1 )
+ {}
+
+ HelpProcessingErrorInfo& operator=( const struct HelpProcessingException& e );
+};
+
+
+// Returns true in case of success, false in case of error
+HELPLINKER_DLLPUBLIC bool compileExtensionHelp
+(
+ const rtl::OUString& aOfficeHelpPath,
+ const rtl::OUString& aExtensionName,
+ const rtl::OUString& aExtensionLanguageRoot,
+ sal_Int32 nXhpFileCount, const rtl::OUString* pXhpFiles,
+ const rtl::OUString& aDestination,
+ HelpProcessingErrorInfo& o_rHelpProcessingErrorInfo
+);
+
+#endif
Propchange: openoffice/branches/l10n/main/l10ntools/source/help/compilehelp.hxx
------------------------------------------------------------------------------
svn:executable = *
Added: openoffice/branches/l10n/main/l10ntools/source/help/helplinker.pmk
URL: http://svn.apache.org/viewvc/openoffice/branches/l10n/main/l10ntools/source/help/helplinker.pmk?rev=1437973&view=auto
==============================================================================
--- openoffice/branches/l10n/main/l10ntools/source/help/helplinker.pmk (added)
+++ openoffice/branches/l10n/main/l10ntools/source/help/helplinker.pmk Thu Jan 24 12:21:38 2013
@@ -0,0 +1,27 @@
+#**************************************************************
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (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.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+#**************************************************************
+
+
+
+# define HELPLINKER_DLLIMPLEMENTATION (see @ inc/xmlhelp/helplinkerdllapi.h)
+CDEFS += -DHELPLINKER_DLLIMPLEMENTATION
+
+VISIBILITY_HIDDEN=TRUE
Propchange: openoffice/branches/l10n/main/l10ntools/source/help/helplinker.pmk
------------------------------------------------------------------------------
svn:executable = *
Added: openoffice/branches/l10n/main/l10ntools/source/help/makefile.mk
URL: http://svn.apache.org/viewvc/openoffice/branches/l10n/main/l10ntools/source/help/makefile.mk?rev=1437973&view=auto
==============================================================================
--- openoffice/branches/l10n/main/l10ntools/source/help/makefile.mk (added)
+++ openoffice/branches/l10n/main/l10ntools/source/help/makefile.mk Thu Jan 24 12:21:38 2013
@@ -0,0 +1,108 @@
+#**************************************************************
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (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.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+#**************************************************************
+
+
+
+PRJ = ..$/..
+PRJNAME = l10ntools
+TARGET = HelpLinker
+LIBBASENAME = helplinker
+PACKAGE = com$/sun$/star$/help
+TARGETTYPE=CUI
+
+# --- Settings -----------------------------------------------------
+
+.INCLUDE : settings.mk
+.INCLUDE : helplinker.pmk
+
+.IF "$(SYSTEM_LIBXSLT)" == "YES"
+CFLAGS+= $(LIBXSLT_CFLAGS)
+.ELSE
+LIBXSLTINCDIR=external$/libxslt
+CFLAGS+= -I$(SOLARINCDIR)$/$(LIBXSLTINCDIR)
+.ENDIF
+
+.IF "$(SYSTEM_EXPAT)" == "YES"
+CFLAGS+=-DSYSTEM_EXPAT
+.ENDIF
+
+OBJFILES=\
+ $(OBJ)$/HelpLinker.obj \
+ $(OBJ)$/HelpCompiler.obj
+SLOFILES=\
+ $(SLO)$/HelpLinker.obj \
+ $(SLO)$/HelpCompiler.obj
+
+EXCEPTIONSFILES=\
+ $(OBJ)$/HelpLinker.obj \
+ $(OBJ)$/HelpCompiler.obj \
+ $(SLO)$/HelpLinker.obj \
+ $(SLO)$/HelpCompiler.obj
+.IF "$(OS)" == "MACOSX" && "$(CPU)" == "P" && "$(COM)" == "GCC"
+# There appears to be a GCC 4.0.1 optimization error causing _file:good() to
+# report true right before the call to writeOut at HelpLinker.cxx:1.12 l. 954
+# but out.good() to report false right at the start of writeOut at
+# HelpLinker.cxx:1.12 l. 537:
+NOOPTFILES=\
+ $(OBJ)$/HelpLinker.obj \
+ $(SLO)$/HelpLinker.obj
+.ENDIF
+
+APP1TARGET= $(TARGET)
+APP1OBJS=\
+ $(OBJ)$/HelpLinker.obj \
+ $(OBJ)$/HelpCompiler.obj
+
+APP1STDLIBS+=$(SALLIB) $(XSLTLIB) $(EXPATASCII3RDLIB)
+
+SHL1TARGET =$(LIBBASENAME)$(DLLPOSTFIX)
+SHL1LIBS= $(SLB)$/$(TARGET).lib
+SHL1IMPLIB =i$(LIBBASENAME)
+SHL1DEF =$(MISC)$/$(SHL1TARGET).def
+SHL1STDLIBS =$(SALLIB) $(XSLTLIB) $(EXPATASCII3RDLIB)
+SHL1USE_EXPORTS =ordinal
+
+DEF1NAME =$(SHL1TARGET)
+DEFLIB1NAME =$(TARGET)
+
+JAVAFILES = \
+ HelpIndexerTool.java \
+ HelpFileDocument.java
+
+
+JAVACLASSFILES = \
+ $(CLASSDIR)$/$(PACKAGE)$/HelpIndexerTool.class \
+ $(CLASSDIR)$/$(PACKAGE)$/HelpFileDocument.class
+
+.IF "$(SYSTEM_LUCENE)" == "YES"
+EXTRAJARFILES += $(LUCENE_CORE_JAR) $(LUCENE_ANALYZERS_JAR)
+.ELSE
+JARFILES += lucene-core-2.9.4-dev.jar lucene-analyzers-2.9.4-dev.jar
+.ENDIF
+JAVAFILES = $(subst,$(CLASSDIR)$/$(PACKAGE)$/, $(subst,.class,.java $(JAVACLASSFILES)))
+
+JARCLASSDIRS = $(PACKAGE)/*
+JARTARGET = HelpIndexerTool.jar
+JARCOMPRESS = TRUE
+
+# --- Targets ------------------------------------------------------
+
+.INCLUDE : target.mk
Propchange: openoffice/branches/l10n/main/l10ntools/source/help/makefile.mk
------------------------------------------------------------------------------
svn:executable = *
Added: openoffice/branches/l10n/main/l10ntools/source/helpex.cxx
URL: http://svn.apache.org/viewvc/openoffice/branches/l10n/main/l10ntools/source/helpex.cxx?rev=1437973&view=auto
==============================================================================
--- openoffice/branches/l10n/main/l10ntools/source/helpex.cxx (added)
+++ openoffice/branches/l10n/main/l10ntools/source/helpex.cxx Thu Jan 24 12:21:38 2013
@@ -0,0 +1,286 @@
+/**************************************************************
+ *
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (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.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ *
+ *************************************************************/
+
+
+
+// MARKER(update_precomp.py): autogen include statement, do not remove
+#include "precompiled_l10ntools.hxx"
+#include <stdio.h>
+#include <stdlib.h>
+
+// local includes
+#include "helpmerge.hxx"
+
+// defines to parse command line
+#define STATE_NON 0x0001
+#define STATE_INPUT 0x0002
+#define STATE_OUTPUT 0x0003
+#define STATE_PRJ 0x0004
+#define STATE_ROOT 0x0005
+#define STATE_SDFFILE 0x0006
+#define STATE_ERRORLOG 0x0007
+#define STATE_BREAKHELP 0x0008
+#define STATE_UNMERGE 0x0009
+#define STATE_UTF8 0x000A
+#define STATE_LANGUAGES 0x000B
+#define STATE_FORCE_LANGUAGES 0x000C
+#define STATE_OUTPUTX 0xfe
+#define STATE_OUTPUTY 0xff
+
+// set of global variables
+ByteString sInputFile;
+sal_Bool bEnableExport;
+sal_Bool bMergeMode;
+sal_Bool bErrorLog;
+sal_Bool bUTF8;
+ByteString sPrj;
+ByteString sPrjRoot;
+ByteString sOutputFile;
+ByteString sOutputFileX;
+ByteString sOutputFileY;
+ByteString sSDFFile;
+
+/*****************************************************************************/
+sal_Bool ParseCommandLine( int argc, char* argv[])
+/*****************************************************************************/
+{
+ bEnableExport = sal_False;
+ bMergeMode = sal_False;
+ bErrorLog = sal_True;
+ bUTF8 = sal_True;
+ sPrj = "";
+ sPrjRoot = "";
+ Export::sLanguages = "";
+ Export::sForcedLanguages = "";
+
+ sal_uInt16 nState = STATE_NON;
+ sal_Bool bInput = sal_False;
+
+ // parse command line
+ for( int i = 1; i < argc; i++ ) {
+ if ( ByteString( argv[ i ]).ToUpperAscii() == "-I" ) {
+ nState = STATE_INPUT; // next tokens specifies source files
+ }
+ else if ( ByteString( argv[ i ]).ToUpperAscii() == "-O" ) {
+ nState = STATE_OUTPUT; // next token specifies the dest file
+ }
+ else if ( ByteString( argv[ i ]).ToUpperAscii() == "-X" ) {
+ nState = STATE_OUTPUTX; // next token specifies the dest file
+ }
+ else if ( ByteString( argv[ i ]).ToUpperAscii() == "-Y" ) {
+ nState = STATE_OUTPUTY; // next token specifies the dest file
+ }
+ else if ( ByteString( argv[ i ]).ToUpperAscii() == "-P" ) {
+ nState = STATE_PRJ; // next token specifies the cur. project
+ }
+ else if ( ByteString( argv[ i ]).ToUpperAscii() == "-LF" ) {
+ nState = STATE_FORCE_LANGUAGES;
+ }
+
+ else if ( ByteString( argv[ i ]).ToUpperAscii() == "-R" ) {
+ nState = STATE_ROOT; // next token specifies path to project root
+ }
+ else if ( ByteString( argv[ i ]).ToUpperAscii() == "-M" ) {
+ nState = STATE_SDFFILE; // next token specifies the merge database
+ }
+ else if ( ByteString( argv[ i ]).ToUpperAscii() == "-E" ) {
+ nState = STATE_ERRORLOG;
+ bErrorLog = sal_False;
+ }
+ else if ( ByteString( argv[ i ]).ToUpperAscii() == "-UTF8" ) {
+ nState = STATE_UTF8;
+ bUTF8 = sal_True;
+ }
+ else if ( ByteString( argv[ i ]).ToUpperAscii() == "-NOUTF8" ) {
+ nState = STATE_UTF8;
+ bUTF8 = sal_False;
+ }
+ else if ( ByteString( argv[ i ]).ToUpperAscii() == "-L" ) {
+ nState = STATE_LANGUAGES;
+ }
+ else {
+ switch ( nState ) {
+ case STATE_NON: {
+ return sal_False; // no valid command line
+ }
+ //break;
+ case STATE_INPUT: {
+ sInputFile = argv[ i ];
+ bInput = sal_True; // source file found
+ }
+ break;
+ case STATE_OUTPUT: {
+ sOutputFile = argv[ i ]; // the dest. file
+ }
+ break;
+ case STATE_OUTPUTX: {
+ sOutputFileX = argv[ i ]; // the dest. file
+ }
+ break;
+ case STATE_OUTPUTY: {
+ sOutputFileY = argv[ i ]; // the dest. file
+ }
+ break;
+ case STATE_PRJ: {
+ sPrj = argv[ i ];
+// sPrj.ToLowerAscii(); // the project
+ }
+ break;
+ case STATE_ROOT: {
+ sPrjRoot = argv[ i ]; // path to project root
+ }
+ break;
+ case STATE_SDFFILE: {
+ sSDFFile = argv[ i ];
+ bMergeMode = sal_True; // activate merge mode, cause merge database found
+ }
+ break;
+ case STATE_LANGUAGES: {
+ Export::sLanguages = argv[ i ];
+ }
+ case STATE_FORCE_LANGUAGES:{
+ Export::sForcedLanguages = argv[ i ];
+ }
+ break;
+ }
+ }
+ }
+
+ if ( bInput ) {
+ // command line is valid
+ bEnableExport = sal_True;
+ return sal_True;
+ }
+
+ // command line is not valid
+ return sal_False;
+}
+
+
+/*****************************************************************************/
+void Help()
+/*****************************************************************************/
+{
+ fprintf( stdout, "Syntax: HELPEX[-p Prj][-r PrjRoot]-i FileIn ( -o FileOut | -x path -y relfile )[-m DataBase][-e][-b][-u][-L l1,l2,...] -LF l1,l2 \n" );
+ fprintf( stdout, " Prj: Project\n" );
+ fprintf( stdout, " PrjRoot: Path to project root (..\\.. etc.)\n" );
+ fprintf( stdout, " FileIn: Source file (*.lng)\n" );
+ fprintf( stdout, " FileOut: Destination file (*.*)\n" );
+ fprintf( stdout, " DataBase: Mergedata (*.sdf)\n" );
+ fprintf( stdout, " -L: Restrict the handled languages. l1,l2,... are elements of (en-US,fr,de...)\n" );
+ fprintf( stdout, " A fallback language can be defined like this: l1=f1.\n" );
+ fprintf( stdout, " f1, f2,... are also elements of (en-US,fr,de...)\n" );
+ fprintf( stdout, " Example: -L fr=en-US\n" );
+ fprintf( stdout, " Restriction to fr, en-US will be fallback for fr\n" );
+ fprintf( stdout, " -LF: Force the creation of that languages\n" );
+
+}
+
+/*****************************************************************************/
+#ifndef TESTDRIVER
+
+#if defined(UNX) || defined(OS2)
+int main( int argc, char *argv[] )
+#else
+int _cdecl main( int argc, char *argv[] )
+#endif
+/*****************************************************************************/
+{
+
+ if ( !ParseCommandLine( argc, argv )) {
+ Help();
+ return 1;
+ }
+ //sal_uInt32 startfull = Export::startMessure();
+
+ bool hasInputList = sInputFile.GetBuffer()[0]=='@';
+// printf("x = %s , y = %s , o = %s\n", sOutputFileX.GetBuffer(), sOutputFileY.GetBuffer() , sOutputFile.GetBuffer() );
+ bool hasNoError = true;
+
+ if ( sOutputFile.Len() ){ // Merge single file ?
+ //printf("DBG: Inputfile = %s\n",sInputFile.GetBuffer());
+ HelpParser aParser( sInputFile, bUTF8 , false );
+
+ if ( bMergeMode )
+ {
+
+ //sal_uInt64 startreadloc = Export::startMessure();
+ MergeDataFile aMergeDataFile( sSDFFile, sInputFile , sal_False, RTL_TEXTENCODING_MS_1252 );
+ //MergeDataFile aMergeDataFile( sSDFFile, sInputFile , sal_False, RTL_TEXTENCODING_MS_1252, false );
+ //Export::stopMessure( ByteString("read localize.sdf") , startreadloc );
+
+ hasNoError = aParser.Merge( sSDFFile, sOutputFile , Export::sLanguages , aMergeDataFile );
+ }
+ else
+ hasNoError = aParser.CreateSDF( sOutputFile, sPrj, sPrjRoot, sInputFile, new XMLFile( '0' ), "help" );
+ }else if ( sOutputFileX.Len() && sOutputFileY.Len() && hasInputList ) { // Merge multiple files ?
+ if ( bMergeMode ){
+
+ ifstream aFStream( sInputFile.Copy( 1 , sInputFile.Len() ).GetBuffer() , ios::in );
+
+ if( !aFStream ){
+ cerr << "ERROR: - helpex - Can't open the file " << sInputFile.Copy( 1 , sInputFile.Len() ).GetBuffer() << "\n";
+ exit(-1);
+ }
+
+ vector<ByteString> filelist;
+ rtl::OStringBuffer filename;
+ sal_Char aChar;
+ while( aFStream.get( aChar ) )
+ {
+ if( aChar == ' ' || aChar == '\n')
+ filelist.push_back( ByteString( filename.makeStringAndClear().getStr() ) );
+ else
+ filename.append( aChar );
+ }
+ if( filename.getLength() > 0 )
+ filelist.push_back( ByteString ( filename.makeStringAndClear().getStr() ) );
+
+ aFStream.close();
+ ByteString sHelpFile(""); // dummy
+ //MergeDataFile aMergeDataFile( sSDFFile, sHelpFile , sal_False, RTL_TEXTENCODING_MS_1252, false );
+ MergeDataFile aMergeDataFile( sSDFFile, sHelpFile , sal_False, RTL_TEXTENCODING_MS_1252 );
+
+ //aMergeDataFile.Dump();
+ std::vector<ByteString> aLanguages;
+ HelpParser::parse_languages( aLanguages , aMergeDataFile );
+
+ bool bCreateDir = true;
+ for( vector<ByteString>::iterator pos = filelist.begin() ; pos != filelist.end() ; ++pos )
+ {
+ sHelpFile = *pos;
+ cout << ".";cout.flush();
+
+ HelpParser aParser( sHelpFile , bUTF8 , true );
+ hasNoError = aParser.Merge( sSDFFile , sOutputFileX , sOutputFileY , true , aLanguages , aMergeDataFile , bCreateDir );
+ bCreateDir = false;
+ }
+ }
+ } else
+ cerr << "helpex ERROR: Wrong input parameters!\n";
+
+ //Export::stopMessure( ByteString("full cycle") , startfull );
+ if( hasNoError )
+ return 0;
+ else
+ return 1;
+}
+#endif
Propchange: openoffice/branches/l10n/main/l10ntools/source/helpex.cxx
------------------------------------------------------------------------------
svn:executable = *