001: /*
002: * Copyright 2001 Sun Microsystems, Inc. All rights reserved.
003: * PROPRIETARY/CONFIDENTIAL. Use of this product is subject to license terms.
004: */
005:
006: package com.sun.portal.search.admin.cli;
007:
008: import com.sun.portal.search.admin.CSConfig;
009: import com.sun.portal.search.util.SearchConfig;
010: import com.sun.portal.log.common.PortalLogger;
011:
012: import java.lang.*;
013: import java.io.*;
014: import java.util.*;
015: import java.util.logging.Level;
016: import java.util.logging.Logger;
017: import javax.servlet.*;
018: import java.net.*;
019: import java.text.*;
020:
021: public class RobotController {
022:
023: static public void main(String[] args) {
024: if (args.length != 2) {
025: System.out
026: .println("Usage:RobotController server_root action");
027: return;
028: }
029: CSConfig.init(args[0]);
030:
031: RobotController rc = new RobotController(CSConfig
032: .getServerRoot(), CSConfig.getBinPath(), CSConfig
033: .getLibDir(), CSConfig.getLibPath(), null, null, null);
034: if (args[1].startsWith("q:")) {
035: rc.query(args[1].substring(2));
036: } else {
037: System.out.print("Executing Robot command:" + args[1]
038: + "....");
039: if (rc.command(args[1])) {
040: System.out.println("Success.");
041: } else {
042: System.out.println("Failed.");
043: }
044: }
045: }
046:
047: static final String ROBOT_CMD = "robot";
048: static final String CATPING_CMD = "catping";
049: static final String RDREGISTER_CMD = "rdregister";
050:
051: private String[] r_env = null;
052: private boolean isValid = false;
053: private boolean isRunning = false;
054: private boolean isQuery = false;
055: static final String rCmd = "cmd";
056: static final String rQuery = "query";
057: private String binDir = "";
058: private String libDir = "";
059: private String libPath = "";
060: private String serverRoot = "";
061: private String configDir = "";
062: private String logDir = "";
063: private String statusDir = "robot";
064:
065: // Create a Logger for this class
066: private static Logger debugLogger = PortalLogger
067: .getLogger(RobotController.class);
068:
069: public RobotController(String in_serverRootPath, String in_binPath,
070: String in_libDir, String in_libPath, String in_configPath,
071: String in_logPath, String in_statusPath) {
072: if (in_serverRootPath != null) {
073: serverRoot = in_serverRootPath;
074: }
075: if (in_binPath != null) {
076: binDir = in_binPath;
077: }
078: if (in_libPath != null) {
079: libPath = in_libPath;
080: }
081: if (in_libDir != null) {
082: libDir = in_libDir;
083: }
084: if (in_configPath != null) {
085: configDir = in_configPath;
086: } else {
087: configDir = this .serverRoot + File.separator + "config";
088: }
089: if (in_logPath != null) {
090: logDir = in_logPath;
091: } else {
092: logDir = this .serverRoot + File.separator + "logs";
093: }
094: if (in_statusPath != null) {
095: statusDir = in_statusPath;
096: } else {
097: statusDir = CSConfig.getRobotConfig().processConf
098: .get("robot-state-dir");
099: if (statusDir == null) {
100: statusDir = serverRoot + File.separator + "robot";
101: }
102: }
103:
104: debugLogger.log(Level.FINER, "PSSH_CSPSAC0004", System
105: .getProperty("os.name"));
106: if (System.getProperty("os.name").startsWith("Windows")) {
107: String winDir = "C:\\WINNT";
108: if (System.getProperty("os.name").equals("Windows XP"))
109: winDir = "C:\\WINDOWS";
110: r_env = new String[7];
111: r_env[0] = "LD_LIBRARY_PATH=" + libPath;
112: r_env[1] = "CS_CONFIG_PATH=" + configDir;
113: r_env[2] = "CS_LOGDIR=" + logDir;
114: r_env[3] = "PATH=" + libPath + ";" + binDir;
115: r_env[4] = "SHLIB_PATH=" + libPath;
116: //Setting Windows specific env vars
117: //SYSTEMROOT var is used by robot nspr socket libraries
118: String SYSTEMROOT = "SYSTEMROOT";
119: String sysRootVal = System.getProperty(SYSTEMROOT);
120: debugLogger.log(Level.FINER, "PSSH_CSPSAC0014",
121: new String[] { SYSTEMROOT, sysRootVal });
122: if (sysRootVal == null)
123: sysRootVal = winDir;
124:
125: //ComSpec var is used by rdregister to run rdmgr.bat
126: String COMSPEC = "COMSPEC";
127: String comSpecVal = System.getProperty(COMSPEC);
128: debugLogger.log(Level.FINER, "PSSH_CSPSAC0005",
129: new String[] { COMSPEC, comSpecVal });
130: if (comSpecVal == null)
131: comSpecVal = winDir + "\\system32\\cmd.exe";
132: r_env[5] = SYSTEMROOT + "=" + sysRootVal;
133: r_env[6] = COMSPEC + "=" + comSpecVal;
134: } else {
135: r_env = new String[5];
136: r_env[0] = "LD_LIBRARY_PATH=/usr/lib:" + libPath;
137: r_env[1] = "CS_CONFIG_PATH=" + configDir;
138: r_env[2] = "CS_LOGDIR=" + logDir;
139: r_env[3] = "PATH=" + libPath + ":" + binDir;
140: r_env[4] = "SHLIB_PATH=/usr/lib:" + libPath;
141: }
142:
143: }
144:
145: public boolean command(String action) {
146: if (action.compareToIgnoreCase("Start") == 0) {
147: return start();
148: } else if (action.compareToIgnoreCase("Stop") == 0) {
149: return stop();
150: } else if (action.compareToIgnoreCase("pause") == 0) {
151: pause();
152: } else if (action.compareToIgnoreCase("resume") == 0) {
153: resume();
154: } else if (action.compareToIgnoreCase("freshstart") == 0) {
155: remove_status_files();
156: } else { //for CLI
157: byte[] result = this .robotURLGet(rCmd, action);
158: if (result != null) {
159: String rs = new String(result);
160: System.out.println(rs);
161: }
162: }
163: return true;
164:
165: }
166:
167: public void query(String action) {
168: byte[] result = this .robotURLGet(rQuery, action);
169: if (result != null) {
170: String rs = new String(result);
171: System.out.println(rs);
172: }
173: }
174:
175: public boolean start_rdregister() {
176: String rdProcName = "rdregister";
177: if (System.getProperty("os.name").startsWith("Windows"))
178: rdProcName = "rdregister.exe";
179: if (isRunning("rdregister.pid", rdProcName)) {
180: return true;
181: }
182: try {
183: String robot_path = (String) CSConfig.getRobotConfig().processConf
184: .get("robot-state-dir");
185: if (robot_path == null) {
186: robot_path = serverRoot + File.separator + "robot";
187: }
188: File file = new File(robot_path);
189: if (!file.exists()) {
190: debugLogger.log(Level.FINER, "PSSH_CSPSAC0006",
191: robot_path);
192: return false;
193: }
194: ArrayList al = new ArrayList();
195: al.add(libDir + File.separator + RDREGISTER_CMD);
196: al.add("-f");
197: al.add(this .configDir + File.separator
198: + SearchConfig.SEARCH_CONF);
199: al.add("-p");
200: al.add(robot_path);
201: String rdregisterCommandOption = (String) CSConfig
202: .getRobotConfig().processConf
203: .get("rdregister-command-option");
204: if (rdregisterCommandOption != null
205: && !rdregisterCommandOption.equals("")) {
206: al.add("-c");
207: al.add(rdregisterCommandOption);
208: }
209: String[] commands = (String[]) al.toArray(new String[al
210: .size()]);
211: String commandDebugString = "";
212: for (int i = 0; i < commands.length; i++) {
213: commandDebugString = commandDebugString + commands[i]
214: + " ";
215: }
216: try {
217: debugLogger.log(Level.FINER, "PSSH_CSPSAC0001",
218: commandDebugString.trim());
219: Runtime rt = Runtime.getRuntime();
220: Process ps = rt.exec(commands, r_env, new File(
221: serverRoot));
222: } catch (IOException e) {
223: debugLogger.log(Level.INFO, "PSSH_CSPSA0003", e
224: .getMessage());
225: return false;
226: }
227: } catch (Exception e) {
228: debugLogger.log(Level.INFO, "PSSH_CSPSA0003", e
229: .getMessage());
230: return false;
231: }
232: return true;
233: }
234:
235: public boolean generate_filter_conf_run(String fc, String fcr) {
236: try {
237: File file = new File(fc);
238: if (!file.exists()) {
239: return false;
240: }
241: Runtime rt = Runtime.getRuntime();
242: String cmd = this .libDir + File.separator + "rcpp " + fc
243: + " " + fcr;
244: String cmds[] = { this .libDir + File.separator + "rcpp",
245: fc, fcr };
246: try {
247: Process ps = rt.exec(cmds, r_env, new File(serverRoot));
248: ps.waitFor();
249: if (ps.exitValue() != 0) {
250: return false;
251: }
252: } catch (IOException e) {
253: debugLogger.log(Level.INFO, "PSSH_CSPSA0003", e
254: .getMessage());
255: return false;
256: }
257: } catch (Exception e) {
258: debugLogger.log(Level.INFO, "PSSH_CSPSA0003", e
259: .getMessage());
260: return false;
261: }
262: return true;
263: }
264:
265: class RobotStatusFileFilter implements FileFilter {
266: public boolean accept(File path) {
267: if (path.getName().startsWith("__db.")
268: || path.getName().endsWith(".db")) {
269: return true;
270: }
271: return false;
272: }
273: }
274:
275: public synchronized boolean remove_status_files() {
276: debugLogger.finer("PSSH_CSPSAC0007");
277: boolean status = true;
278: if (this .isRunning())
279: return false;
280: File f = new File(statusDir);
281: if (f.isDirectory()) {
282: RobotStatusFileFilter ff = new RobotStatusFileFilter();
283: File[] files = f.listFiles(ff);
284: for (int i = 0; i < files.length; i++) {
285: if (!files[i].delete()) {
286: status = false;
287: }
288: }
289: }
290: return status;
291: }
292:
293: public synchronized boolean start() {
294: debugLogger.finer("PSSH_CSPSAC0008");
295: if (this .isRunning())
296: return true;
297: if (!this .generate_filter_conf_run(this .configDir
298: + File.separator + "filter.conf", this .configDir
299: + File.separator + "filter.conf.run")) {
300: debugLogger.finer("PSSH_CSPSAC0009");
301: return false;
302: }
303: if (!this .start_rdregister()) {
304: debugLogger.finer("PSSH_CSPSAC0010");
305: return false;
306: }
307: Runtime rt = Runtime.getRuntime();
308: try {
309: String cmds[] = { libDir + File.separator + ROBOT_CMD };
310: rt.exec(cmds, r_env, new File(serverRoot));
311:
312: for (int i = 0; i < 10; i++) {
313: try {
314: this .wait(1000);
315: } catch (Exception e) {
316: debugLogger.log(Level.INFO, "PSSH_CSPSA0003", e
317: .getMessage());
318: }
319: if (isRunning()) {
320: byte[] result = robotURLGet(rQuery, "run-status");
321: if (result != null) {
322: return true;
323: }
324: }
325: }
326: return false;
327: } catch (IOException e) {
328: debugLogger.log(Level.INFO, "PSSH_CSPSA0003", e
329: .getMessage());
330: return false;
331: }
332: }
333:
334: private String Read1stLine(String filename) {
335: try {
336: FileReader in = new FileReader(CSConfig.getServerRoot()
337: + File.separator + "logs" + File.separator
338: + filename);
339: BufferedReader lr = new BufferedReader(in);
340: String firstLine = lr.readLine();
341: return firstLine;
342: } catch (Exception e) {
343: debugLogger.log(Level.INFO, "PSSH_CSPSA0003", e
344: .getMessage());
345: return null;
346: }
347: }
348:
349: public boolean isPaused() {
350: byte[] result = this .robotURLGet(rQuery, "run-status");
351: if (result == null) {
352: return false;
353: }
354: String rs = new String(result);
355: int ndx = rs.indexOf("Robot Status:");
356: if (ndx > 0) {
357: String status = rs.substring(ndx + 14);
358: if (status.startsWith("Paused")) {
359: return true;
360: } else {
361: return false;
362: }
363: }
364: return false;
365: }
366:
367: public boolean isRunning() {
368: String robotProcName = "robot.exe";
369: if (System.getProperty("os.name").startsWith("Windows"))
370: robotProcName = "robot.exe";
371: return isRunning("robot.pid", robotProcName);
372: }
373:
374: public boolean isRunning(String pidFilePath, String cmd) {
375: String pid = Read1stLine(pidFilePath);
376: String catping = null;
377: if (pid == null) {
378: debugLogger.log(Level.FINER, "PSSH_CSPSAC0011", "null");
379: return false;
380: }
381: debugLogger.log(Level.FINER, "PSSH_CSPSAC0011", pid);
382: Runtime rt = Runtime.getRuntime();
383: try {
384: catping = libDir + File.separator + CATPING_CMD + " " + pid
385: + " " + cmd;
386: String cmds[] = { libDir + File.separator + CATPING_CMD,
387: pid, cmd };
388: Process p = rt.exec(cmds, r_env);
389: try {
390: p.waitFor();
391: } catch (java.lang.InterruptedException e) {
392: }
393: int exitValue = p.exitValue();
394: debugLogger.log(Level.FINER, "PSSH_CSPSAC0013", Integer
395: .toString(exitValue));
396: if (exitValue == 1) {
397: return false;
398: }
399: } catch (IOException e) {
400: debugLogger.log(Level.INFO, "PSSH_CSPSA0003", e
401: .getMessage());
402: return false;
403: }
404: return true;
405: }
406:
407: public synchronized boolean stop() {
408: byte[] result = this .robotURLGet(rCmd, "stop");
409: if (result != null) {
410: String rs = new String(result);
411: }
412: for (int i = 0; i < 10; i++) {
413: try {
414: this .wait(1000);
415: } catch (Exception e) {
416: debugLogger.log(Level.INFO, "PSSH_CSPSA0003", e
417: .getMessage());
418: }
419: if (!isRunning()) {
420: return true;
421: }
422: }
423: return false;
424: }
425:
426: public void pause() {
427: byte[] result = this .robotURLGet(rCmd, "pause");
428: if (result != null) {
429: String rs = new String(result);
430: System.out.println(rs);
431: }
432: }
433:
434: public void resume() {
435: byte[] result = this .robotURLGet(rCmd, "resume");
436: if (result != null) {
437: String rs = new String(result);
438: System.out.println(rs);
439: }
440: }
441:
442: public String[] getRobotStates() {
443: /* STATUS_URLPOOL,STATUS_EXTRACTING,STATUS_FILTERLING,STATUS_INDEXING,
444: STATUS_EXCLUDE_BY_FILTER,STATUS_EXCLUDE_BY_ERROE,STATUS_RD_NUM,
445: STATUS_RD_SIZE,STATUS_URL_RETRIEVED,STATUS_RD_AVE_SIZE,STATUS_RUNNING_TIME, ROBOT_STATUS*/
446: String states[] = { "", "", "", "", "", "", "", "", "", "", "",
447: "" };
448:
449: int url_waiting = 0, processed = 0;
450: int retrieved = 0;
451: int rej_filter = 0, rej_error = 0;
452: int generated = 0;
453: long generated_bytes = 0;
454: long run_time = 0;
455: byte[] result = this .robotURLGet(rQuery, "robot-states");
456: if (result != null) {
457: String rs = new String(result);
458: StringTokenizer st = new StringTokenizer(rs, "\n");
459: while (st.hasMoreTokens()) {
460: String t = st.nextToken();
461: if (t.startsWith("Robot Status:")) {
462: states[11] = t.substring(13).trim();
463: } else if (t.startsWith("url-waiting=")) {
464: url_waiting = Integer.parseInt(t.substring(12));
465: } else if (t.startsWith("processed=")) {
466: processed = Integer.parseInt(t.substring(10));
467: } else if (t.startsWith("retrieved=")) {
468: retrieved = Integer.parseInt(t.substring(10));
469: } else if (t.startsWith("reject-by-filter=")) {
470: rej_filter = Integer.parseInt(t.substring(17));
471: } else if (t.startsWith("reject-by-error=")) {
472: rej_error = Integer.parseInt(t.substring(16));
473: } else if (t.startsWith("generated=")) {
474: generated = Integer.parseInt(t.substring(10));
475: } else if (t.startsWith("generated-bytes=")) {
476: generated_bytes = Long.parseLong(t.substring(16));
477: } else if (t.startsWith("run-time=")) {
478: run_time = Long.parseLong(t.substring(9));
479: }
480: }
481: }
482: NumberFormat nf = NumberFormat.getInstance();
483: nf.setMaximumFractionDigits(2);
484: states[0] = nf.format(url_waiting);
485: if (run_time > 0) {
486: states[1] = nf.format((float) retrieved / (float) run_time);
487: states[3] = nf.format((float) generated / (float) run_time);
488: }
489: states[2] = nf.format(rej_filter + rej_error);
490: states[4] = nf.format(rej_filter);
491: states[5] = nf.format(rej_error);
492: states[6] = nf.format(generated);
493: states[7] = Long.toString(generated_bytes); //need for parsing later
494: states[8] = nf.format(retrieved);
495: if (generated > 0) {
496: states[9] = nf.format((float) generated_bytes
497: / (float) generated);
498: }
499: states[10] = Long.toString(run_time); //need for parsing later
500:
501: return states;
502: }
503:
504: public byte[] robotURLGet(String cmd, String fn) {
505: return robotURLGet(cmd + "?fn=" + fn);
506: }
507:
508: public byte[] robotURLGet(String cmd) {
509: InputStream in;
510: int n;
511: try {
512: debugLogger.log(Level.FINER, "PSSH_CSPSAC0001", cmd);
513: String base = Read1stLine("robotbase.cmd");
514: if (base == null) {
515: return null;
516: }
517: URL command_url = new URL("http://" + base + "/robot/"
518: + cmd);
519: URLConnection url_conn = command_url.openConnection();
520: int len = 1024;
521: int offset = 0;
522: byte buff[] = new byte[len];
523: ByteArrayOutputStream bos = new ByteArrayOutputStream();
524: try {
525: in = new BufferedInputStream(url_conn.getInputStream());
526: } catch (Exception e) {
527: debugLogger.log(Level.INFO, "PSSH_CSPSA0003", e
528: .getMessage());
529: return null;
530: }
531: try {
532: while ((n = in.read(buff, 0, len)) >= 0)
533: bos.write(buff, 0, n);
534: } catch (Exception e) {
535: debugLogger.log(Level.INFO, "PSSH_CSPSA0003", e
536: .getMessage());
537: return null;
538: }
539: try {
540: in.close();
541: } catch (Exception e) {
542: debugLogger.log(Level.INFO, "PSSH_CSPSA0003", e
543: .getMessage());
544: return null;
545: }
546: return bos.toByteArray();
547: } catch (Exception e) {
548: debugLogger.log(Level.INFO, "PSSH_CSPSA0003", e
549: .getMessage());
550: return null;
551: }
552: }
553:
554: }
|