gt: 				if (output && ncmlDoc != null && !ncmlDoc.isEmpty()) {
context: /////////////////////////////////////////////////////////////////////////////
  //
  // Copyright (c) 2010 OPeNDAP, Inc.
  // Author: James Gallagher  <jgallagher@opendap.org>
  //
  // This library is free software; you can redistribute it and/or
  // modify it under the terms of the GNU Lesser General Public
  // License as published by the Free Software Foundation; either
  // version 2.1 of the License, or (at your option) any later version.
  //
  // This library 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
  // Lesser General Public License for more details.
  //
  // You should have received a copy of the GNU Lesser General Public
  // License along with this library; if not, write to the Free Software
  // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
  //
  // You can contact OPeNDAP, Inc. at PO Box 112, Saunderstown, RI. 02874-0112.
  /////////////////////////////////////////////////////////////////////////////
  
  package opendap.metacat;
  
  import java.io.FileWriter;
  import java.io.PrintStream;
  import java.text.SimpleDateFormat;
  import java.util.ArrayList;
  import java.util.Date;
  import java.util.HashMap;
  import java.util.HashSet;
  import java.util.List;
  import java.util.Map;
  
  import opendap.metacat.Equivalence.SortedValues;
  import opendap.metacat.URLGroup.Equivalences;
  
  import org.apache.commons.cli.CommandLine;
  import org.apache.commons.cli.CommandLineParser;
  import org.apache.commons.cli.HelpFormatter;
  import org.apache.commons.cli.Options;
  import org.apache.commons.cli.PosixParser;
  import org.slf4j.Logger;
  import org.slf4j.LoggerFactory;
  
  public class NCMLWriter {
      private static Logger log = LoggerFactory.getLogger(NCMLWriter.class);
  
  	private static final HashSet<String> likelyServerNames = new HashSet<String>();
  	
  	private static Map<URLGroup, URLGroupFacts> factBase = null;
  	
  	private static NCMLBuilder multifileNCMLBuilder = null;
  	
      /// These are used to format dates so they are human- and xslt-usable
      final static SimpleDateFormat iso_8601_sdf = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ssZ");
      final static SimpleDateFormat infoLogSdf = new SimpleDateFormat("HH:mm:ss");        
  	
  	public static void main(String[] args) {
  		// There has to be a better way...
  		likelyServerNames.add("opendap");
  		likelyServerNames.add("hyrax");
  		likelyServerNames.add("dap");
  		likelyServerNames.add("data");
  		
  		CommandLineParser parser = new PosixParser();
  
  		Options options = new Options();
  
  		options.addOption("v", "verbose", false, "Write info to stdout");
  		options.addOption("V", "very-verbose", false, "Write NCML to stdout");
  		options.addOption("h", "help", false, "Usage information");
  		
  		options.addOption("n", "groups-name", true, "URLGroups name prefix");
  		options.addOption("o", "output", false, "Write NCML files using the groupName name and a counter.");
  		// options.addOption("d", "dir", true, "Write NCML files to this directory.");
  		
  		try {
  		    CommandLine line = parser.parse( options, args );
  
  			if (line.hasOption("help")) {
  				HelpFormatter formatter = new HelpFormatter();
  				formatter.printHelp("NCMLWriter [options] --groups-name <name prefix>", options);
  				return;
  			}
  
  		    boolean verbose = line.hasOption("verbose");
  		    boolean veryVerbose = line.hasOption("very-verbose");
  		    PrintStream ps = System.out;
  		    
  		    // Extract options
  		    String groupsName = line.getOptionValue("groups-name");
  		    if (groupsName == null || groupsName.isEmpty())
  		    	throw new Exception("The calssifier must have a URLGroups file name.");
  		    if (verbose)
  		    	ps.println("Groups file: " + groupsName);
  		    		    		    
  		    boolean output = line.hasOption("output");
  		    
  		    // Build objects
      		DDXRetriever ddxRetriever = new DDXRetriever(true, groupsName);
      		
      		multifileNCMLBuilder = new NCMLBuilder(groupsName, "many_ddx2ncml-1.0.xsl");
      		
  			if (verbose)
  				ps.println("(" + infoLogSdf.format(new Date()) + ") Reading groups");
  
  		    URLGroups groups = new URLGroups();
  		    groups.restoreState(groupsName);
  		    
  		    factBase = new HashMap<URLGroup, URLGroupFacts>();
  		    
  			if (verbose)
  				ps.println("(" + infoLogSdf.format(new Date()) + ") Begining analysis of groups");
  
  		    // initialize the fact base.
  		    Integer count = 0;
  		    for (URLGroup group: groups) {
  		    	String ddxURL = group.getURLs().get(0).getTheURL();
  		    	factBase.put(group, new URLGroupFacts(ddxURL, ddxRetriever.getDDXDoc(ddxURL)));
  		    	count++;
  		    }
  		    
  		    // Look at each group and decide if it can be aggregated.
  		    /*
  		    for (URLGroup group: groups) {
  		    	
  		    }
  		    */
  		    
  		    if (verbose)
  		    	ps.println("(" + infoLogSdf.format(new Date()) + ") " + count.toString() + " groups.");
  		    
  		    // Find multifile groups
  		    count = 0;
  		    for (URLGroup group: groups) {
  		    	if (group.getURLs().size() > 1) {
  		    		factBase.get(group).setIsMultiFile(true);
  		    		count++;
  		    	}
  		    }
  		    	
  		    if (verbose)
  		    	ps.println("(" + infoLogSdf.format(new Date()) + ") " + count.toString() + " multifile groups.");
  		    
  		    // Find multifile groups with a date equivalence
  		    count = 0;
  		    for (URLGroup group: groups) {
  		    	if (factBase.get(group).getIsMultiFile() && group.getDateEquivalence() != null) {
  		    		factBase.get(group).setIsTimeSeries(true);
  		    		
  		    		SortedValues sortedDates = group.getDateEquivalence().getSortedValues();
  	    			  
  					DateString first = sortedDates.get(0);
  					DateString last = sortedDates.get(sortedDates.size() - 1);
  					
  					factBase.get(group).setFirstDate(iso_8601_sdf.format(first.getDate()));
  					factBase.get(group).setLastDate(iso_8601_sdf.format(last.getDate()));
  					
  					count++;
  		    	}
  		    }
  		    
  		    if (verbose)
  		    	ps.println("(" + infoLogSdf.format(new Date()) + ") " + count.toString() + " multifile groups with date equivalence classes.");
  		    
  		    // For groups that have multiple files, find various pathnames
  			for (URLGroup group : groups) {
  				String DDXURL = factBase.get(group).getFirstDDXURL();
  				int serverNameEndPosition = findServerNameEnd(DDXURL);
  				log.debug("serverNameEndPosition: " + serverNameEndPosition);
  
  				int serverRootPosition = findServerRootPosition(group, serverNameEndPosition);
  				log.debug("serverRootPosition: " + serverRootPosition);
  
  				factBase.get(group).setServerRootPosition(serverRootPosition);
  
  				int dataRootPosition = findDataRootPosition(group, serverNameEndPosition);
  				log.debug("dataRootPosition: " + dataRootPosition);
  
  				log.debug("DDX (length: " + DDXURL.length() + "): " + DDXURL);
  				int len = DDXURL.length();
  				// The monkey shines here guard against the case where a single
  				// file dataset's dataRootPosition is past the en of the URL.
  				String dataRoot = DDXURL.substring(serverRootPosition, (dataRootPosition > len) ? len : dataRootPosition);
  				log.debug("DDX: " + DDXURL + "; dataset scan: " + dataRoot);
  
  				factBase.get(group).setDatasetRoot(dataRoot);
  			}
  
  		    // Check for things that are unique, like dataRoot - for each group
  		    // is its value of dataRoot Unique?
  			
  			// Put all the dataRoot paths in a list
  		    List<String> dataRootList= new ArrayList<String>();;
  		    for (URLGroup group: groups) {
  		    	dataRootList.add(factBase.get(group).getDatasetRoot());
  		    }
  		    
  		    // ... now test to see if the first and last occurrence are the same
  		    for (URLGroup group: groups) {
  		    	String dr = factBase.get(group).getDatasetRoot();
  		    	if (dataRootList.indexOf(dr) == dataRootList.lastIndexOf(dr))
  		    		factBase.get(group).setIsDatasetRootUnique(true);
  		    	else
  		    		factBase.get(group).setIsDatasetRootUnique(false);
  		    }
  		    
  		    // now build some NCML
  			if (verbose)
  				ps.println("(" + infoLogSdf.format(new Date()) + ") Building NCML");
  
  		    Integer output_counter = 0;
  		    for (URLGroup group: groups) {
  		    	String ncmlDoc = null;
  		    	
  		    	if (factBase.get(group).getIsTimeSeries()) {
  		    		if (verbose)
  		    			ps.println("(" + infoLogSdf.format(new Date()) + ") Start building NCML");
  		    		
  		    		ncmlDoc = buildExplicitNCMLForTimeSeries(group);
  			    	
  		    		if (verbose)
  		    			ps.println("(" + infoLogSdf.format(new Date()) + ") End building NCML");
  
  		    		if (veryVerbose)
  						ps.println("(" + infoLogSdf.format(new Date()) + ") NCML: " + ncmlDoc);
  		    	}
  				
  