/*
 *    RegexSearchReplace.java
 *    A task to delete from a given starting nugget to a given ending nugget or the end of the file
 *
 *    Copyright (C) 2005 New Zealand Digital Library, http://www.nzdl.org
 *
 *    This program is free software; you can redistribute it and/or modify
 *    it under the terms of the GNU General Public License as published by
 *    the Free Software Foundation; either version 2 of the License, or
 *    (at your option) any later version.
 *
 *    This program is distributed in the hope that it will be useful,
 *    but WITHOUT ANY WARRANTY; without even the implied warranty of
 *    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 *    GNU General Public License for more details.
 *
 *    You should have received a copy of the GNU General Public License
 *    along with this program; if not, write to the Free Software
 *    Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
 */
package org.greenstone.anttasks;

import org.apache.tools.ant.*;
import org.apache.tools.ant.taskdefs.*;
import java.util.*;
import java.io.*;
import java.util.regex.*;


public class DeleteChunkFromFile extends Task {

	private File file = null;
	private Pattern startTag = null;
	private Pattern endTag = null;
	private boolean leaveTags = false;

	public static void main( String[] args ) {

		DeleteChunkFromFile dcff = new DeleteChunkFromFile();
		dcff.setFile(new File (args[0]));
		dcff.setStartTag(args[1]);
		dcff.setEndTag(args[2]);

		dcff.execute();

	}

	public void execute() {

		if ( file == null ) {
			throw new BuildException( "Error - No file specified !!" );
		}

		if ( startTag == null ) {
			throw new BuildException( "Error - No startTag specified !!" );
		}
		
		System.out.println( "File: " + file );
		System.out.println( "StartTag: " + startTag );
		System.out.println( "EndTag: " + endTag );
		System.out.println( "LeaveTags: " + leaveTags );

		int noReplaces = 0;

		//create the output stream
		BufferedWriter out = null;
		File temp = null;
		try {
			//create temp file.
			temp = File.createTempFile("dcff", ".tmp");

			//delete temp file when program exits.
			temp.deleteOnExit();

			//writer to temp file
			out = new BufferedWriter( new OutputStreamWriter(new FileOutputStream(temp), "UTF8") );

		} catch (IOException e) {
			throw new BuildException( "Error - Couldn't create or open the temp file" );
		}


		//create the input stream
		BufferedReader in = null;
		try {
			in = new BufferedReader( new InputStreamReader(new FileInputStream(file), "UTF8") );
		} catch ( Exception e ) {
			throw new BuildException( "Error - Couldn't open the specified file" );
		}

		//pass the file through, searching and replacing
		String line;
		boolean hasMoreLines = true;
		boolean lookingForStartTag = true;
		String toDefer = null;

		while ( hasMoreLines ) {

			//get the next line - either from the file of the leftovers from the last loop around
			if ( toDefer != null ) {
				line = toDefer;
				toDefer = null;
			} else {
				try {
					line = in.readLine();
				} catch ( Exception e ) {
					throw new BuildException( "Error - Couldn't read from the specified file" );
				}
			}

			if ( line == null ) {
				hasMoreLines = false;
			} else {

				String toWrite = null;
				boolean endLine = false;
				if ( lookingForStartTag ) {
					Matcher m = startTag.matcher(line);
					if ( m.find() ) {
						lookingForStartTag = false;
						toWrite = line.substring(0,leaveTags?m.end():m.start());
						toDefer = line.substring(m.end());
					} else {
						toWrite = line;
						endLine = true;
					}
				} else if ( endTag != null ) {
					Matcher m = endTag.matcher(line);
					if ( m.find() ) {
						lookingForStartTag = true;
						toDefer = line.substring(leaveTags?m.start():m.end());
					}
				}

				if ( toWrite != null ) {
					try {
						out.write(toWrite);
						if ( endLine ) {
							out.newLine();
						}
					} catch ( Exception e ) {
						throw new BuildException( "Error - Couldn't write to the temp file" );
					}
				}
			}
		}
			

		try {
			//close them both up
			in.close();
			out.close();
		} catch ( Exception e ) {
			throw new BuildException( "Error - Couldn't close a file" );
		}


		//copy the new file (temp) over the original
		InputStream i;
		OutputStream o;
		try {
			i = new FileInputStream(temp);
			o = new FileOutputStream(file);

		} catch ( Exception e ) {
			throw new BuildException( "Error - Couldn't open the temp file" );
		}

		try {
	
			// Transfer bytes from in to out
			byte[] buf = new byte[1024];
			int len;
			while ((len = i.read(buf)) > 0) {
			   o.write(buf, 0, len);
			}

			//close them up
			i.close();
			o.close();
		} catch ( Exception e ) {
			throw new BuildException( "Error - Couldn't write to the specified file" );
		}

		System.out.println( "Finished" );
	}

   
	public void setFile(File file) {
		this.file = file;
	}

	public void setStartTag(String st) {
		try {
			this.startTag = Pattern.compile(st);
		} catch ( PatternSyntaxException pse ) {
			throw new BuildException( "Invalid start tag!!" );
		}
	}

	public void setEndTag(String et) {
		try {
			this.endTag = Pattern.compile(et);
		} catch ( PatternSyntaxException pse ) {
			throw new BuildException( "Invalid start tag!!" );
		}
	}

	public void setLeaveTags( boolean lt ) {
		this.leaveTags = lt;
	}


}
