blob: 2e32636b58ab3f9e8e8e02926e8347bb7d73f2dd [file] [log] [blame]
package org.eclipse.wtp.releng.tools.pii.internal;
import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.File;
import java.io.FileReader;
import java.io.FileWriter;
import java.io.IOException;
import java.util.Collection;
import java.util.Enumeration;
import java.util.HashSet;
import java.util.Hashtable;
import java.util.Iterator;
import java.util.Vector;
public class KeyUtils
{
public Hashtable findUnusedKeys( String pathName, String[] excludes )
{
File startPath = new File( pathName );
Hashtable results = new Hashtable();
if( startPath == null || !startPath.isDirectory() )
{
System.out.println( "Error: The first parameter must specify a plugins directory!" );
return results;
}
File[] pluginDirs = startPath.listFiles();
// Find all the property files and files containing strings.
for( int index = 0; index < pluginDirs.length; index++ )
{
Vector propertyFiles = new Vector();
Vector srcFiles = new Vector();
File pluginDir = pluginDirs[index];
getFiles( pluginDir, propertyFiles, "properties", excludes );
// For now we only check java, jsp, and xml files.
getFiles( pluginDir, srcFiles, "java", new String[0] );
getFiles( pluginDir, srcFiles, "jsp", new String[0] );
getFiles( pluginDir, srcFiles, "xml", new String[0] );
HashSet srcKeys = new HashSet();
// Loop over all string source files.
for( int srcIndex = 0; srcIndex < srcFiles.size(); srcIndex++ )
{
File srcFile = (File)srcFiles.elementAt( srcIndex );
String[] srcLines = readLines( srcFile );
for( int lineIndex = 0; lineIndex < srcLines.length; lineIndex++ )
{
findStrings( srcLines[lineIndex], srcKeys );
}
}
// Loop over all the property files to find unused keys.
for( int propIndex = 0; propIndex < propertyFiles.size(); propIndex++ )
{
File propFile = (File)propertyFiles.elementAt( propIndex );
String[] lines = readLines( propFile );
int lineIndex = 0;
while( lineIndex < lines.length )
{
String line = lines[lineIndex].trim();
boolean validKey = isLineKey( srcKeys, line );
boolean hasKey = line.indexOf( '=' ) != -1;
boolean comment = line.startsWith( "#" );
if( !comment && !validKey && hasKey )
{
addUnusedKey( results, propFile, line );
}
boolean continuation = false;
// Skip over continuation lines.
while( lineIndex < lines.length && lines[lineIndex].endsWith( "\\" ) )
{
lineIndex++;
continuation = true;
}
if( !continuation )
{
lineIndex++;
}
}
}
}
return results;
}
private void addUnusedKey( Hashtable table, File propFile, String line )
{
int equalIndex = line.indexOf( '=' );
String key = line.substring( 0, equalIndex );
Vector entry = (Vector)table.get( propFile );
if( entry == null )
{
entry = new Vector();
table.put( propFile, entry );
}
entry.add( key );
}
private void findStrings( String line, HashSet keys )
{
int quotestart = line.indexOf( '"' );
int quoteend = line.indexOf( '"', quotestart + 1 );
while( quotestart != -1 && quoteend != -1 && quotestart < quoteend )
{
// Find last real ending quote.
while( quotestart != -1 && quoteend != -1 && line.charAt( quoteend-1 ) == '\\' )
{
quoteend = line.indexOf( '"', quoteend + 1 );
}
if( quotestart == -1 || quoteend == -1 || quotestart > quoteend ) break;
String key = line.substring( quotestart+1, quoteend );
if( key.startsWith( "%" ) )
{
// Remove the leading percent sign.
keys.add( key.substring( 1 ) );
}
else
{
keys.add( key );
}
quotestart = line.indexOf( '"', quoteend+1 );
quoteend = line.indexOf( '"', quotestart+1 );
}
}
private String[] readLines( File file )
{
Vector files = new Vector();
BufferedReader reader = null;
try
{
reader = new BufferedReader( new FileReader( file ) );
String line = reader.readLine();
while( line != null )
{
files.add( line );
line = reader.readLine();
}
}
catch( Exception exc )
{
System.out.println( "Problem opening file:" + file );
exc.printStackTrace();
}
finally
{
try
{
if( reader != null ) reader.close();
}
catch( Exception exc )
{
exc.printStackTrace();
}
}
return (String[])files.toArray( new String[0] );
}
private String[] readLines( String file )
{
return readLines( new File( file ) );
}
private void getFiles( File file, Vector files, String fileSuffix, String[] excludeFiles )
{
if( stringInArray( file.getName(), excludeFiles ) )
{
// do nothing
}
else if( file.isDirectory() )
{
File[] dirfiles = file.listFiles();
for( int index = 0; index < dirfiles.length; index++ )
{
getFiles( dirfiles[index], files, fileSuffix, excludeFiles );
}
}
else if( file.getName().endsWith( fileSuffix ) )
{
files.add( file );
}
}
private boolean stringInArray( String name, String[] names )
{
boolean found = false;
for( int index = 0; index < names.length; index++ )
{
if( name.equals( names[index] ))
{
found = true;
break;
}
}
return found;
}
private boolean isLineKey( Collection keys, String line )
{
boolean result = false;
Iterator iter = keys.iterator();
int equalIndex = line.indexOf( '=' );
String key = null;
if( equalIndex != -1 && !line.startsWith( "#" ))
{
key = line.substring( 0, equalIndex ).trim();
}
while( iter.hasNext() && key != null )
{
String collectionKey = (String)iter.next();
if( key.equals( collectionKey ) )
{
result = true;
break;
}
}
return result;
}
public static void main( String[] args )
{
KeyUtils utils = new KeyUtils();
String pathName = args.length > 0 ? args[0] : "";
String outputDir = args.length > 1 ? args[1] : "";
String[] excludes = args.length > 1 ? new String[args.length - 1] : new String[0];
if (excludes.length > 0)
System.arraycopy(args, 0, excludes, 0, excludes.length);
Hashtable results = utils.findUnusedKeys( pathName, excludes );
Enumeration keys = results.keys();
while( keys.hasMoreElements() )
{
File file = (File)keys.nextElement();
Vector keyList = (Vector)results.get( file );
String absOutputPath = new File ( outputDir ).getAbsolutePath();
StringBuffer sb = new StringBuffer( absOutputPath );
if ( !absOutputPath.endsWith( "/" ) && !absOutputPath.endsWith( "\\" ) )
sb.append( '/' );
String absPath = file.getAbsolutePath();
sb.append( absPath.substring( pathName.length(), absPath.length() ) );
BufferedWriter bw = null;
try
{
File outputFile = new File( sb.toString() );
outputFile.getParentFile().mkdirs();
bw = new BufferedWriter( new FileWriter( outputFile ) );
for( int index = 0; index < keyList.size(); index++ )
{
bw.write( keyList.elementAt( index ).toString() );
bw.newLine();
}
}
catch (IOException e)
{
e.printStackTrace();
}
finally
{
if ( bw != null )
{
try
{
bw.close();
}
catch (IOException e)
{
e.printStackTrace();
}
}
}
}
}
}