logging-general mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From sde...@apache.org
Subject svn commit: r564112 - /logging/chainsaw/trunk/src/main/java/org/apache/log4j/chainsaw/vfs/VFSLogFilePatternReceiver.java
Date Thu, 09 Aug 2007 06:40:17 GMT
Author: sdeboy
Date: Wed Aug  8 23:40:16 2007
New Revision: 564112

URL: http://svn.apache.org/viewvc?view=rev&rev=564112
Log:
Updating VFSLogFilePatternReceiver to suport remote tailing 
(thanks to Isuru Suriarachchi for the initial work!)

To tail via VFS, a version of commons-vfs is required which 
provides the fileobject.refresh method (added Mar 30 19:16:24 2006)

(not sure if a version of VFS containing this method is available from maven)

Modified:
    logging/chainsaw/trunk/src/main/java/org/apache/log4j/chainsaw/vfs/VFSLogFilePatternReceiver.java

Modified: logging/chainsaw/trunk/src/main/java/org/apache/log4j/chainsaw/vfs/VFSLogFilePatternReceiver.java
URL: http://svn.apache.org/viewvc/logging/chainsaw/trunk/src/main/java/org/apache/log4j/chainsaw/vfs/VFSLogFilePatternReceiver.java?view=diff&rev=564112&r1=564111&r2=564112
==============================================================================
--- logging/chainsaw/trunk/src/main/java/org/apache/log4j/chainsaw/vfs/VFSLogFilePatternReceiver.java
(original)
+++ logging/chainsaw/trunk/src/main/java/org/apache/log4j/chainsaw/vfs/VFSLogFilePatternReceiver.java
Wed Aug  8 23:40:16 2007
@@ -25,6 +25,7 @@
 import java.awt.Toolkit;
 import java.awt.event.ActionEvent;
 import java.awt.event.ActionListener;
+import java.io.BufferedReader;
 import java.io.IOException;
 import java.io.InputStreamReader;
 import java.io.Reader;
@@ -41,12 +42,17 @@
 import org.apache.commons.vfs.FileSystemException;
 import org.apache.commons.vfs.FileSystemManager;
 import org.apache.commons.vfs.FileSystemOptions;
+import org.apache.commons.vfs.RandomAccessContent;
 import org.apache.commons.vfs.VFS;
 import org.apache.commons.vfs.provider.URLFileName;
 import org.apache.commons.vfs.provider.sftp.SftpFileSystemConfigBuilder;
+import org.apache.commons.vfs.util.RandomAccessMode;
 import org.apache.log4j.chainsaw.receivers.VisualReceiver;
 import org.apache.log4j.varia.LogFilePatternReceiver;
 
+import com.jcraft.jsch.UIKeyboardInteractive;
+import com.jcraft.jsch.UserInfo;
+
 /**
  * A VFS-enabled version of org.apache.log4j.varia.LogFilePatternReceiver.
  * 
@@ -167,6 +173,7 @@
   private boolean promptForUserInfo = false;
   private Container container;
   private Object waitForContainerLock = new Object();
+  private String password;
   
   public VFSLogFilePatternReceiver() {
     super();
@@ -231,11 +238,11 @@
     	  synchronized(waitForContainerLock) {
     		  while (container == null) {
     			  try {
-    				  waitForContainerLock.wait();
+    				  waitForContainerLock.wait(1000);
     			  } catch (InterruptedException ie){}
     		  }
     	  }
- 
+    	      	  
     	  Frame containerFrame1;
     	  synchronized(waitForContainerLock) {
     		  //loop until the container has a frame
@@ -245,71 +252,136 @@
     			  } catch (InterruptedException ie) {}
     		  }
     	  }
-    	  final Frame containerFrame = containerFrame1;
-
-    	  //create the dialog
-		  SwingUtilities.invokeLater(new Runnable() {
-    		  public void run() {
-    			  final UserNamePasswordDialog f = new UserNamePasswordDialog(containerFrame);
-    			  f.pack();
-    			  Dimension d = Toolkit.getDefaultToolkit().getScreenSize();
-    			  f.setLocation(d.width /2, d.height/2);
-    			  f.setVisible(true);
-					if (null == f.getUserName() || null == f.getPassword()) {
-						getLogger().warn("No username or password provided - not loading file " + getFileURL());
-					} else {
-						int index = getFileURL().indexOf("://");
-						String firstPart = getFileURL().substring(0, index);
-						String lastPart = getFileURL().substring(index + "://".length());
-						setFileURL(firstPart + "://" + f.getUserName()+ ":" + new String(f.getPassword()) +
"@" + lastPart);
-					      new Thread(new VFSReader()).start();
-					}
-    			  }
-    		  });
+    	  		final Frame containerFrame = containerFrame1;
+    	  	  //create the dialog
+    	  	  SwingUtilities.invokeLater(new Runnable() {
+    	  		public void run() {
+    	  			  Frame owner = null;
+    	  			  if (container != null) {
+    	  				  owner = (Frame)SwingUtilities.getAncestorOfClass(Frame.class, containerFrame);
+    	  			  }
+    	  			  final UserNamePasswordDialog f = new UserNamePasswordDialog(owner);
+    	  			  f.pack();
+    	  			  Dimension d = Toolkit.getDefaultToolkit().getScreenSize();
+    	  			  f.setLocation(d.width /2, d.height/2);
+    	  			  f.setVisible(true);
+    	  				if (null == f.getUserName() || null == f.getPassword()) {
+    	  					getLogger().warn("No username or password provided - not loading file " + getFileURL());
+    	  				} else {
+    	  					password = new String(f.getPassword());
+    	  					int index = getFileURL().indexOf("://");
+    	  					String firstPart = getFileURL().substring(0, index);
+    	  					String lastPart = getFileURL().substring(index + "://".length());
+    	  					setFileURL(firstPart + "://" + f.getUserName()+ ":" + new String(password) +
"@" + lastPart);
+    	  				      new Thread(new VFSReader()).start();
+    	  				}
+    	  			  }
+    	  		  });
     		  }}).start();
       } else {
-    	  new Thread(new VFSReader()).start();
+		int index = getFileURL().indexOf("://");
+		String lastPart = getFileURL().substring(index + "://".length());
+		password = lastPart.substring(lastPart.indexOf(":") + 1, lastPart.indexOf("@"));
+   	    new Thread(new VFSReader()).start();
       }
    }
-  
+
   private class VFSReader implements Runnable {
-	  public void run() {
-      while (reader == null) {
-          getLogger().info("attempting to load file: " + getFileURL());
-          try {
-            FileSystemManager fileSystemManager = VFS.getManager();
-            FileSystemOptions opts = new FileSystemOptions();
-            SftpFileSystemConfigBuilder.getInstance().setStrictHostKeyChecking(opts, "no");
-
-            FileObject fileObject = fileSystemManager.resolveFile(getFileURL(), opts);
-            reader = new InputStreamReader(fileObject.getContent().getInputStream());
-            //now that we have a reader, remove additional portions of the file url (sftp
passwords, etc.)
-            //check to see if the name is a URLFileName..if so, set file name to not include
username/pass
-            if (fileObject.getName() instanceof URLFileName) {
-              URLFileName urlFileName = (URLFileName)fileObject.getName();
-          	setHost(urlFileName.getHostName());
-          	setPath(urlFileName.getPath());
+        public void run() {
+        	FileObject fileObject = null;
+            while (reader == null) {
+            	int atIndex = getFileURL().indexOf("@");
+            	int protocolIndex = getFileURL().indexOf("://");
+            	
+            	String loggableFileURL = atIndex > -1? getFileURL().substring(0, protocolIndex
+ "://".length()) + "username:password" + getFileURL().substring(atIndex) : getFileURL();
+                getLogger().info("attempting to load file: " + loggableFileURL);
+                try {
+                    FileSystemManager fileSystemManager = VFS.getManager();
+                    FileSystemOptions opts = new FileSystemOptions();
+                    //if jsch not in classpath, can get NoClassDefFoundError here
+                    try {
+                    	SftpFileSystemConfigBuilder.getInstance().setStrictHostKeyChecking(opts,
"no");
+                    	SftpFileSystemConfigBuilder.getInstance().setUserInfo(opts, new MyUserInfo());
+                    } catch (NoClassDefFoundError ncdfe) {
+                    	getLogger().warn("JSch not on classpath!", ncdfe);
+                    }
+
+                    fileObject = fileSystemManager.resolveFile(getFileURL(), opts);
+                    reader = new InputStreamReader(fileObject.getContent().getInputStream());
+                    //now that we have a reader, remove additional portions of the file url
(sftp passwords, etc.)
+                    //check to see if the name is a URLFileName..if so, set file name to
not include username/pass
+                    if (fileObject.getName() instanceof URLFileName) {
+                        URLFileName urlFileName = (URLFileName) fileObject.getName();
+                        setHost(urlFileName.getHostName());
+                        setPath(urlFileName.getPath());
+                    }
+                } catch (FileSystemException fse) {
+                    getLogger().info("file not available - may be due to incorrect credentials,
but will re-attempt to load in 10 seconds", fse);
+                    synchronized (this) {
+                        try {
+                            wait(10000);
+                        } catch (InterruptedException ie) {}
+                    }
+                }
             }
-          } catch (FileSystemException fse) {
-            getLogger().info("file not available - will try again in 10 seconds");
-            synchronized(this) {
-              try {
-                wait(10000);
-              } catch (InterruptedException ie){}
+            initialize();
+
+            try {
+                long lastFilePointer = 0;
+                long lastFileSize = 0;
+                BufferedReader bufferedReader;
+                createPattern();
+                getLogger().debug("tailing file: " + isTailing());
+
+                do {
+                    FileSystemManager fileSystemManager = VFS.getManager();
+                    FileSystemOptions opts = new FileSystemOptions();
+                    //if jsch not in classpath, can get NoClassDefFoundError here
+                    try {
+                    	SftpFileSystemConfigBuilder.getInstance().setStrictHostKeyChecking(opts,
"no");
+                    	SftpFileSystemConfigBuilder.getInstance().setUserInfo(opts, new MyUserInfo());
+                    } catch (NoClassDefFoundError ncdfe) {
+                    	getLogger().warn("JSch not on classpath!", ncdfe);
+                    }
+
+                    fileObject = fileSystemManager.resolveFile(getFileURL(), opts);
+                    reader = new InputStreamReader(fileObject.getContent().getInputStream());
+
+                    if (fileObject.getContent().getSize() > lastFileSize) {
+                        RandomAccessContent rac = fileObject.getContent().getRandomAccessContent(RandomAccessMode.READ);
+                        rac.seek(lastFilePointer);
+                        reader = new InputStreamReader(rac.getInputStream());
+                        bufferedReader = new BufferedReader(reader);
+                        process(bufferedReader);
+                        lastFilePointer = rac.getFilePointer();
+                        lastFileSize = fileObject.getContent().getSize();
+                        rac.close();
+                    }
+
+                    try {
+                        synchronized (this) {
+                            wait(5000);
+                        }
+                    } catch (InterruptedException ie) {
+                    }
+                    try {
+                    	//available in vfs as of 30 Mar 2006 - will load but not tail if not
available
+                    	fileObject.refresh();
+                    } catch (Error err) {
+                    	getLogger().info("Unable to refresh fileobject", err);
+                    }
+
+                } while (isTailing());
+
+            } catch (IOException ioe) {
+                getLogger().info("stream closed");
             }
-        } 
-        }
-        initialize();
-        
-        try {
-          process(reader);
-        } catch (IOException ioe) {
-          getLogger().info("stream closed");
+            getLogger().debug("processing " + getFileURL() + " complete");
+            shutdown();
         }
-	  }
-  }
+    }
   
-  public class UserNamePasswordDialog extends JDialog{
+  public class UserNamePasswordDialog extends JDialog {
 	  private String userName;
 	  private char[] password;
 	  private UserNamePasswordDialog(Frame containerFrame) {
@@ -381,4 +453,39 @@
 		  return password;
 	  }
   }
-}
\ No newline at end of file
+
+  /**
+   * UserInfo class used to automatically log in if needed - also implemements
+   * UIKeyboardInteractive (UserInfo methods not used, just UIKeyboardInteractive)
+   * 
+   * @author sdeboy
+   */
+  public class MyUserInfo implements UserInfo, UIKeyboardInteractive {
+	public String[] promptKeyboardInteractive(String destination, String loginName, String instruction,
String[] prompt, boolean[] echo) {
+		return new String[]{password};
+	}
+
+	public String getPassphrase() {
+		return null;
+	}
+
+	public String getPassword() {
+		return null;
+	}
+
+	public boolean promptPassphrase(String arg0) {
+		return false;
+	}
+
+	public boolean promptPassword(String arg0) {
+		return false;
+	}
+
+	public boolean promptYesNo(String arg0) {
+		return false;
+	}
+
+	public void showMessage(String arg0) {
+	}
+  }
+}



Mime
View raw message