001: // translator.java
002: // -------------------------------------
003: // part of YACY
004: // (C) by Michael Peter Christen; mc@anomic.de
005: // first published on http://www.anomic.de
006: // Frankfurt, Germany, 2004
007: //
008: // This file ist contributed by Alexander Schier
009: // last major change: 25.05.2005
010: //
011: // $LastChangedDate: 2008-01-29 10:12:48 +0000 (Di, 29 Jan 2008) $
012: // $LastChangedRevision: 4414 $
013: // $LastChangedBy: orbiter $
014: //
015: // This program is free software; you can redistribute it and/or modify
016: // it under the terms of the GNU General Public License as published by
017: // the Free Software Foundation; either version 2 of the License, or
018: // (at your option) any later version.
019: //
020: // This program is distributed in the hope that it will be useful,
021: // but WITHOUT ANY WARRANTY; without even the implied warranty of
022: // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
023: // GNU General Public License for more details.
024: //
025: // You should have received a copy of the GNU General Public License
026: // along with this program; if not, write to the Free Software
027: // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
028: //
029: // Using this software in any meaning (reading, learning, copying, compiling,
030: // running) means that you agree that the Author(s) is (are) not responsible
031: // for cost, loss of data or any harm that may be caused directly or indirectly
032: // by usage of this softare or this documentation. The usage of this software
033: // is on your own risk. The installation and usage (starting/running) of this
034: // software may allow other people or application to access your computer and
035: // any attached devices and is highly dependent on the configuration of the
036: // software which must be done by the user of the software; the author(s) is
037: // (are) also not responsible for proper configuration and usage of the
038: // software, even if provoked by documentation provided together with
039: // the software.
040: //
041: // Any changes to this file according to the GPL as documented in the file
042: // gpl.txt aside this file in the shipment you received can be done to the
043: // lines that follows this copyright notice here, but changes must not be
044: // done inside the copyright notive above. A re-distribution must contain
045: // the intact and unchanged copyright notice.
046: // Contributions and changes to the program code must be marked as such.
047:
048: package de.anomic.data;
049:
050: import java.io.BufferedReader;
051: import java.io.BufferedWriter;
052: import java.io.File;
053: import java.io.FileInputStream;
054: import java.io.FileOutputStream;
055: import java.io.FileWriter;
056: import java.io.IOException;
057: import java.io.InputStreamReader;
058: import java.io.OutputStreamWriter;
059: import java.io.PrintWriter;
060: import java.util.ArrayList;
061: import java.util.Enumeration;
062: import java.util.HashMap;
063: import java.util.Hashtable;
064: import java.util.Iterator;
065: import java.util.Vector;
066: import java.util.regex.Matcher;
067: import java.util.regex.Pattern;
068:
069: import de.anomic.server.serverSwitch;
070: import de.anomic.server.logging.serverLog;
071: import de.anomic.tools.yFormatter;
072:
073: /**
074: * Wordlist based translator
075: *
076: * Uses a Property like file with phrases or single words to translate a string or a file
077: * */
078: public class translator {
079: public static String translate(String source,
080: Hashtable<String, String> translationList) {
081: Enumeration<String> keys = translationList.keys();
082: String result = source;
083: String key = "";
084: while (keys.hasMoreElements()) {
085: key = keys.nextElement();
086: Pattern pattern = Pattern.compile(key);
087: Matcher matcher = pattern.matcher(result);
088: if (matcher.find()) {
089: result = matcher.replaceAll(translationList.get(key));
090: } else {
091: //Filename not available, but it will be printed in Log
092: //after all untranslated Strings as "Translated file: "
093: serverLog
094: .logFine("TRANSLATOR", "Unused String: " + key);
095: }
096: }
097: return result;
098: }
099:
100: /**
101: * Load multiple translationLists from one File. Each List starts with #File: relative/path/to/file
102: * @param translationFile the File, which contains the Lists
103: * @return a Hashtable, which contains for each File a Hashtable with translations.
104: */
105: public static Hashtable<String, Hashtable<String, String>> loadTranslationsLists(
106: File translationFile) {
107: Hashtable<String, Hashtable<String, String>> lists = new Hashtable<String, Hashtable<String, String>>(); //list of translationLists for different files.
108: Hashtable<String, String> translationList = new Hashtable<String, String>(); //current Translation Table
109:
110: ArrayList<String> list = listManager
111: .getListArray(translationFile);
112: Iterator<String> it = list.iterator();
113: String line = "";
114: String[] splitted;
115: String forFile = "";
116:
117: while (it.hasNext()) {
118: line = (String) it.next();
119: if (!line.startsWith("#")) {
120: splitted = line.split("==", 2);
121: if (splitted.length == 2) {
122: translationList.put(splitted[0], splitted[1]);
123: } else { //Invalid line
124: }
125: } else if (line.startsWith("#File: ")) {
126: if (!forFile.equals("")) {
127: lists.put(forFile, translationList);
128: }
129: if (line.charAt(6) == ' ') {
130: forFile = line.substring(7);
131: } else {
132: forFile = line.substring(6);
133: }
134: if (lists.containsKey(forFile)) {
135: translationList = lists.get(forFile);
136: } else {
137: translationList = new Hashtable<String, String>();
138: }
139: }
140: }
141: lists.put(forFile, translationList);
142: return lists;
143: }
144:
145: public static boolean translateFile(File sourceFile, File destFile,
146: File translationFile) {
147: Hashtable<String, String> translationList = loadTranslationsLists(
148: translationFile).get(sourceFile.getName());
149: return translateFile(sourceFile, destFile, translationList);
150: }
151:
152: public static boolean translateFile(File sourceFile, File destFile,
153: Hashtable<String, String> translationList) {
154:
155: String content = "";
156: String line = "";
157: BufferedReader br = null;
158: try {
159: br = new BufferedReader(new InputStreamReader(
160: new FileInputStream(sourceFile), "UTF-8"));
161: while ((line = br.readLine()) != null) {
162: content += line
163: + de.anomic.server.serverCore.CRLF_STRING;
164: }
165: br.close();
166: } catch (IOException e) {
167: return false;
168: } finally {
169: if (br != null)
170: try {
171: br.close();
172: } catch (Exception e) {
173: }
174: }
175:
176: content = translate(content, translationList);
177: BufferedWriter bw = null;
178: try {
179: bw = new BufferedWriter(new OutputStreamWriter(
180: new FileOutputStream(destFile), "UTF-8"));
181: bw.write(content);
182: bw.close();
183: } catch (IOException e) {
184: return false;
185: } finally {
186: if (bw != null)
187: try {
188: bw.close();
189: } catch (Exception e) {
190: }
191: }
192:
193: return true;
194: }
195:
196: public static boolean translateFiles(File sourceDir, File destDir,
197: File baseDir, File translationFile, String extensions) {
198: Hashtable<String, Hashtable<String, String>> translationLists = loadTranslationsLists(translationFile);
199: return translateFiles(sourceDir, destDir, baseDir,
200: translationLists, extensions);
201: }
202:
203: public static boolean translateFiles(
204: File sourceDir,
205: File destDir,
206: File baseDir,
207: Hashtable<String, Hashtable<String, String>> translationLists,
208: String extensions) {
209: destDir.mkdirs();
210: File[] sourceFiles = sourceDir.listFiles();
211: Vector<String> exts = listManager.string2vector(extensions);
212: boolean rightExtension;
213: Iterator<String> it;
214: String relativePath;
215: for (int i = 0; i < sourceFiles.length; i++) {
216: it = exts.iterator();
217: rightExtension = false;
218: while (it.hasNext()) {
219: if (sourceFiles[i].getName().endsWith(
220: (String) it.next())) {
221: rightExtension = true;
222: break;
223: }
224: }
225: if (rightExtension) {
226: try {
227: relativePath = sourceFiles[i]
228: .getAbsolutePath()
229: .substring(
230: baseDir.getAbsolutePath().length() + 1); //+1 to get the "/"
231: relativePath = relativePath.replace(
232: File.separatorChar, '/');
233: } catch (IndexOutOfBoundsException e) {
234: serverLog.logSevere("TRANSLATOR",
235: "Error creating relative Path for "
236: + sourceFiles[i].getAbsolutePath());
237: relativePath = "wrong path"; //not in translationLists
238: }
239: if (translationLists.containsKey(relativePath)) {
240: serverLog.logInfo("TRANSLATOR",
241: "Translating file: " + relativePath);
242: if (!translateFile(sourceFiles[i], new File(
243: destDir, sourceFiles[i].getName().replace(
244: '/', File.separatorChar)),
245: translationLists.get(relativePath))) {
246: serverLog.logSevere("TRANSLATOR",
247: "File error while translating file "
248: + relativePath);
249: }
250: } else {
251: //serverLog.logInfo("TRANSLATOR", "No translation for file: "+relativePath);
252: }
253: }
254:
255: }
256: return true;
257: }
258:
259: public static boolean translateFilesRecursive(File sourceDir,
260: File destDir, File translationFile, String extensions,
261: String notdir) {
262: ArrayList<File> dirList = listManager.getDirsRecursive(
263: sourceDir, notdir);
264: dirList.add(sourceDir);
265: Iterator<File> it = dirList.iterator();
266: File file = null;
267: File file2 = null;
268: while (it.hasNext()) {
269: file = it.next();
270: //cuts the sourcePath and prepends the destPath
271: file2 = new File(destDir, file.getPath().substring(
272: sourceDir.getPath().length()));
273: if (file.isDirectory() && !file.getName().equals(notdir)) {
274: translateFiles(file, file2, sourceDir, translationFile,
275: extensions);
276: }
277: }
278: return true;
279: }
280:
281: public static HashMap<String, String> langMap(serverSwitch env) {
282: String[] ms = env.getConfig("locale.lang", "").split(",");
283: HashMap<String, String> map = new HashMap<String, String>();
284: int p;
285: for (int i = 0; i < ms.length; i++) {
286: p = ms[i].indexOf("/");
287: if (p > 0)
288: map.put(ms[i].substring(0, p), ms[i].substring(p + 1));
289: }
290: return map;
291: }
292:
293: public static boolean changeLang(serverSwitch env, String langPath,
294: String lang) {
295: if ((lang.equals("default")) || (lang.equals("default.lng"))) {
296: env.setConfig("locale.language", "default");
297: return true;
298: }
299: String htRootPath = env.getConfig("htRootPath", "htroot");
300: File sourceDir = new File(env.getRootPath(), htRootPath);
301: File destDir = new File(env.getConfigPath(
302: "locale.translated_html", "DATA/LOCALE/htroot"), lang
303: .substring(0, lang.length() - 4));// cut
304: // .lng
305: //File destDir = new File(env.getRootPath(), htRootPath + "/locale/" + lang.substring(0, lang.length() - 4));// cut
306: // .lng
307: File translationFile = new File(langPath, lang);
308:
309: //if (translator.translateFiles(sourceDir, destDir, translationFile, "html")) {
310: if (translator.translateFilesRecursive(sourceDir, destDir,
311: translationFile, "html,template,inc", "locale")) {
312: env.setConfig("locale.language", lang.substring(0, lang
313: .length() - 4));
314: yFormatter
315: .setLocale(env.getConfig("locale.language", "en"));
316: try {
317: BufferedWriter bw = new BufferedWriter(new PrintWriter(
318: new FileWriter(new File(destDir, "version"))));
319: bw.write(env.getConfig("svnRevision",
320: "Error getting Version"));
321: bw.close();
322: } catch (IOException e) {
323: // Error
324: }
325: return true;
326: }
327: return false;
328: }
329: }
|