package osm.jp.coverage.busstop;
import osm.jp.api.HttpPOST;

import javax.xml.parsers.*;
import javax.xml.transform.TransformerException;

import org.w3c.dom.*;
import org.xml.sax.*;

import java.io.*;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
import java.text.SimpleDateFormat;
import java.util.ArrayList;

import jp.co.areaweb.tools.database.*;

public class Busstop {

	String filter = "";
	String urlStr = "";

	public static final boolean DB_INIT = false;

	// 近くのバス停を探す範囲（バス停を中心としたNEER×２ｍ四方の領域
	static final int NEER = 150;		// 150m(0.15km)
	static boolean nocheck = false;
	
	public static SimpleDateFormat timeStampFmt = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss'Z'");

	/**
	 * メイン
	 *
	 *	java -cp .:ConvBusstop.jar:hayashi_0225.jar:hsqldb_2.2.9.jar osm.jp.ConvBusstop <option>
	 *		OPTION: -nocheck	OSMデータ上に既存のバス停が存在するかどうかをチェックしない
	 *		OPTION: -check	OSMデータ上に既存のバス停が存在するかどうかをチェックする
	 *
	 * @throws IOException
	 * @throws SQLException
	 * @throws ClassNotFoundException
	 * @throws FileNotFoundException
	 * @throws TransformerException
	 * @throws SAXException
	 * @throws ParserConfigurationException */
	public static void main(String[] args) throws FileNotFoundException, ClassNotFoundException, SQLException, IOException, ParserConfigurationException, SAXException, TransformerException
	{
		int index = 0;
		if (args.length > index) {
			if (args[index].equals("-check")) {
				Busstop.nocheck = false;
				index++;
			}
			else if (args[index].equals("-nocheck")) {
				Busstop.nocheck = true;
				index++;
			}
		}

		// HSQLディレクトリがなければ作る
		File dbdir = new File("database");
		if (!dbdir.isDirectory()) {
			dbdir.mkdir();
		}

		Connection con = DatabaseTool.openDb("database");
		Busstop.initDb(con);
		
		try {
			/**
			 * 都道府県ごとのGMLディレクトリの処理
			 */
			int fcounter = 0;
			File dir = new File(".");
			File[] files = dir.listFiles();
			for (File iDir : files) {
				if (checkGMLdir(iDir)) {
					// GMLディレクトリを処理する
					new Busstop(con, iDir);
					fcounter++;
				}
			}
			System.out.println("["+ fcounter +"]つのファイルをインポートしました。");
		}
		finally {
			DatabaseTool.closeDb(con);
		}
	}
	
	/**
	 * 個別の都道府県「GMLディレクトリ」を処理
	 * 
	 * @param con
	 * @param gmldir
	 * @throws SQLException
	 * @throws FileNotFoundException
	 * @throws ClassNotFoundException
	 * @throws IOException
	 * @throws ParserConfigurationException
	 * @throws SAXException
	 * @throws TransformerException
	 */
	public Busstop(Connection con, File gmldir) throws SQLException, FileNotFoundException, ClassNotFoundException, IOException, ParserConfigurationException, SAXException, TransformerException {
		int areacode = Integer.parseInt(gmldir.getName().substring(GML_DIR_PREFIX.length(), GML_DIR_PREFIX.length()+2));

		ToPostgis postgis = null;
		
		File[] files = gmldir.listFiles();
		for (File iFile : files) {
			// 対象のファイルが「数値地図情報のGMLデータファイル」の時のみ処理を行う。
			if (!checkFile(iFile, areacode)) {
				continue;
			}

			Busstop.clearDb(con);
			inputFile(con, iFile, areacode);

			/**
			 * 既存のOSMバス停を読み込む
			 * 		--> 'existing.xml'
			 */
			if (!Busstop.nocheck) {
				/*
				 * 既存のOSMデータファイルがなければ、新たにダウンロードする。
				 * OSMデータファイルがあるときは、ダウンロードしないでそれを使う。
				 */
				File existingFile = new File(gmldir, String.format("existing_%02d.xml", areacode));
				if (!existingFile.isFile()) {
					/**
					 * インポートしたデータの緯度経度範囲を読み取る
					 */
					double maxLat = -90.0D;
					double minLat = 90.0D;
					double maxLon = -180.0D;
					double minLon = 180.0D;
					PreparedStatement ps8 = con.prepareStatement("SELECT lat,lon FROM bus_stop");
					ResultSet rset8 = ps8.executeQuery();
					while (rset8.next()) {
						Double lat = rset8.getDouble("lat");
						Double lon = rset8.getDouble("lon");

						if (lat > maxLat) {
							maxLat = lat;
						}
						if (lon > maxLon) {
							maxLon = lon;
						}
						if (lat < minLat) {
							minLat = lat;
						}
						if (lon < minLon) {
							minLon = lon;
						}
					}
					rset8.close();
					
					/**
					 * OSM OverPassAPI を使って、既存のOSMバス停のデータを取得して、「existing.xml」に出力する
					 */
					HttpPOST.getCapabilities(existingFile, minLat, maxLat, minLon, maxLon);
				}
				readExistingFile(con, existingFile);
				
				PreparedStatement ps1 = con.prepareStatement("SELECT idref,name,lat,lon FROM bus_stop WHERE area=?");
				PreparedStatement ps2 = con.prepareStatement("SELECT SUM(score) FROM existing_data where (lat > ?) and (lat < ?) and (lon > ?) and (lon < ?)");
				PreparedStatement ps3 = con.prepareStatement("UPDATE bus_stop SET fixed=? WHERE idref=?");
				PreparedStatement ps4 = con.prepareStatement("SELECT SUM(score) FROM existing_data where (lat > ?) and (lat < ?) and (lon > ?) and (lon < ?) and (name = ?)");
				ps1.setInt(1, areacode);
				ResultSet rset1 = ps1.executeQuery();
				while (rset1.next()) {
					String idref = rset1.getString("idref");
					String name = rset1.getString("name");
					Double lat = rset1.getDouble("lat");
					Double lon = rset1.getDouble("lon");
					
					// 指定の緯度経度を中心とする半径150x2m四方の矩形領域
					System.out.print(idref + "("+ name + ") ....");
					RectArea rect = new RectArea(lat, lon, NEER);		// 300m 四方
					ps2.setDouble(1, rect.minlat);
					ps2.setDouble(2, rect.maxlat);
					ps2.setDouble(3, rect.minlon);
					ps2.setDouble(4, rect.maxlon);
					ResultSet rset2 = ps2.executeQuery();
					if (rset2.next()) {
						int score = rset2.getInt(1);
						if (score > 0) {
							System.out.println("."+ score);
							ps3.setInt(1, score);
							ps3.setString(2, idref);
							ps3.executeUpdate();
						}
						else {
							// 指定の緯度経度を中心とする半径150x4m四方の矩形領域
							System.out.print("***");
							rect = new RectArea(lat, lon, NEER*2);		// 600m 四方
							ps4.setDouble(1, rect.minlat);
							ps4.setDouble(2, rect.maxlat);
							ps4.setDouble(3, rect.minlon);
							ps4.setDouble(4, rect.maxlon);
							ps4.setString(5, name);
							ResultSet rset4 = ps4.executeQuery();
							if (rset4.next()) {
								score = rset4.getInt(1);
								System.out.println(".."+ score);
								ps3.setInt(1, score);
								ps3.setString(2, idref);
								ps3.executeUpdate();
							}
							rset4.close();
						}
					}
					rset2.close();
				}
				rset1.close();
				ps3.close();
				ps2.close();
				ps1.close();
			}
			
			// ローカルデータベース内の情報をPostGIS用の「busstop.sql」に出力する
			postgis = new ToPostgis(gmldir);
			postgis.outputDb(con);
			postgis.close();
		}
	}

	static String[] shiftArgs(String[] args) {
		String[] values = new String[args.length - 1];
		for (int i=1; i < args.length; i++) {
			values[i - 1] = new String(args[i]);
		}
		return values;
	}

	public static void readExistingFile (Connection con, File existingFile) throws FileNotFoundException, ClassNotFoundException, SQLException, IOException, ParserConfigurationException, SAXException {
		int iCounter = 0;

		DocumentBuilderFactory factory;
		DocumentBuilder        builder;
		Node root;

		iCounter = 0;
		factory = DocumentBuilderFactory.newInstance();
		builder = factory.newDocumentBuilder();
		factory.setIgnoringElementContentWhitespace(true);
		factory.setIgnoringComments(true);
		factory.setValidating(true);
		root    = builder.parse(existingFile);

		iCounter += readExistingNodes(con, root);
		System.out.println("既存バス停数["+ iCounter +"]");
	}
	
	static int readExistingNodes(Connection con, Node node) throws IOException, SQLException {
		int iCounter = 0;
		
		NodeList nodes = node.getChildNodes();
		for (int i = 0; i < nodes.getLength(); i++) {
			Node node2 = nodes.item(i);
			if (node2.getNodeName().equals("node")) {
				iCounter++;
				importExistingNode(con, node2);
			}
			else {
				iCounter += readExistingNodes(con, node2);
			}
		}
		return iCounter;
	}

	static void importExistingNode(Connection con, Node node) throws IOException, SQLException {
		String idrefStr = "";
		String latStr = "";
		String lonStr = "";
		String nameStr = "";
		String fixmeStr = "";
		int	score = 0;
		PreparedStatement ps5 = con.prepareStatement("INSERT INTO existing_data (idref,lat,lon, name, score) VALUES (?,?,?,?,?)");

		NamedNodeMap nodeMap = node.getAttributes();
		if (null != nodeMap) {
			for (int j=0; j < nodeMap.getLength(); j++) {
				if (nodeMap.item(j).getNodeName().equals("id")) {
					idrefStr = nodeMap.item(j).getNodeValue();
				}
				else if (nodeMap.item(j).getNodeName().equals("lat")) {
					latStr = nodeMap.item(j).getNodeValue();
				}
				else if (nodeMap.item(j).getNodeName().equals("lon")) {
					lonStr = nodeMap.item(j).getNodeValue();
				}
			}
			
			NodeList nodes = node.getChildNodes();
			for (int i = 0; i < nodes.getLength(); i++) {
				Node node2 = nodes.item(i);
				if (node2.getNodeName().equals("tag")) {
					NamedNodeMap nodeMap2 = node2.getAttributes();
					if (null != nodeMap2) {
						String key = null;
						String value = null;
						for (int j=0; j < nodeMap2.getLength(); j++) {
							if (nodeMap2.item(j).getNodeName().equals("k")) {
								key = nodeMap2.item(j).getNodeValue();
							}
							else if (nodeMap2.item(j).getNodeName().equals("v")) {
								value = nodeMap2.item(j).getNodeValue();
							}
						}
						
						if ((key != null) && key.toLowerCase().equals("name") && (value != null)) {
							nameStr = value;
						}
						if ((key != null) && key.toLowerCase().equals("fixme") && (value != null)) {
							fixmeStr = value;
						}
					}
				}
			}
			
			score = 50;
			if (nameStr.equals("")) {
				score = 1;
			}
			if (!fixmeStr.equals("")) {
				score = 1;
			}

			// idref と nameStr をデータベースに格納する
			System.out.println("import existing_data : "+ idrefStr +" ("+ latStr +","+ lonStr+")["+ Integer.toString(score) +"]"+ nameStr);
			ps5.setString(1, idrefStr);
			ps5.setDouble(2, Double.parseDouble(latStr));
			ps5.setDouble(3, Double.parseDouble(lonStr));
			ps5.setString(4, nameStr);
			ps5.setInt(5, score);
			ps5.executeUpdate();
			ps5.close();
		}
	}
	
	/**
	 * 数値地図情報のGMLデータファイルを読み取ってローカルベータベースへ記録する
	 * @param con
	 * @param iFile
	 * @throws FileNotFoundException
	 * @throws ClassNotFoundException
	 * @throws SQLException
	 * @throws IOException
	 * @throws ParserConfigurationException 
	 * @throws SAXException 
	 */
	public static void inputFile (Connection con, File iFile, int areacode) throws FileNotFoundException, ClassNotFoundException, SQLException, IOException, ParserConfigurationException, SAXException {
		int iCounter = 0;
		String timeStampStr = null;

		String iStr = iFile.getName();

		DocumentBuilderFactory factory;
		DocumentBuilder        builder;
		Node root;

		iCounter = 0;
		factory = DocumentBuilderFactory.newInstance();
		builder = factory.newDocumentBuilder();
		factory.setIgnoringElementContentWhitespace(true);
		factory.setIgnoringComments(true);
		factory.setValidating(true);
		root    = builder.parse(iFile);

		iCounter += showNodes(con, root, iStr.substring(0, iStr.length() - 4), timeStampStr, areacode);
		System.out.println("バス停数["+ iCounter +"]");
	}

	public static void clearDb(Connection con) throws SQLException {
		Statement stmt = con.createStatement();
		long count = stmt.executeUpdate("delete from bus_stop");
		System.out.println("'Database.bus_stop'から "+ count +" 件のデータを削除しました。");
	    
	    count = stmt.executeUpdate("delete from existing_data");
	    System.out.println("'Database.existing_data'から "+ count +" 件のデータを削除しました。");

	    count = stmt.executeUpdate("delete from bus_course");
	    System.out.println("'Database.bus_course'から "+ count +" 件のデータを削除しました。");

	    count = stmt.executeUpdate("delete from bus_ref");
	    System.out.println("'Database.bus_ref'から "+ count +" 件のデータを削除しました。");
	    stmt.close();
	}

	public static void initDb(Connection con) throws SQLException {
		// 'table.BUS_STOP'を新規に作る
		DbBusstop.create(con);
	}


	/**
	 *
	 * @param con
	 * @param node
	 * @param iFileName		// ソースファイル名（拡張子を含まない）
	 * @param timeStampStr
	 * @return
	 * @throws IOException
	 * @throws SQLException
	 */
	public static int showNodes(Connection con, Node node, String iFileName, String timeStampStr, int areacode) throws IOException, SQLException {
		int iCounter = 0;
		NamedNodeMap nodeMap = node.getAttributes();
		if ( null != nodeMap ) {
			for ( int j=0; j < nodeMap.getLength(); j++ ) {
				if (nodeMap.item(j).getNodeName().equals("timeStamp")) {
					timeStampStr = nodeMap.item(j).getNodeValue();
				}
			}
		}

		NodeList nodes = node.getChildNodes();
		for (int i=0; i<nodes.getLength(); i++) {
			Node node2 = nodes.item(i);
			if (node2.getNodeName().equals("jps:GM_Point")) {
				showGmPoint(con, node2);
			}
			else if (node2.getNodeName().equals("gml:Point")) {
				showGmlPoint(con, node2, areacode);
			}

			else if (node2.getNodeName().equals("ksj:ED01")) {
				iCounter++;
				showED01(con, node2, iFileName);
			}
			else if (node2.getNodeName().equals("ksj:BusStop")) {
				iCounter++;
				showBusStop(con, node2, iFileName);
			}

			else {
				iCounter += showNodes(con, node2, iFileName, timeStampStr, areacode);
			}
		}
		return iCounter;
	}

	/**
	 *
	 * @param con
	 * @param node
	 * @param iFileName		// ソースファイル名（拡張子を含まない）
	 * @throws IOException
	 * @throws SQLException
	 */
	public static void showED01(Connection con, Node node, String iFileName) throws IOException, SQLException {
		String idrefStr = "";
		String nameStr = "";
		PreparedStatement ps1 = con.prepareStatement("SELECT idref FROM bus_stop WHERE idref=?");
		PreparedStatement ps2 = con.prepareStatement("INSERT INTO bus_stop (idref,name,ifile) VALUES (?,?,?)");
		PreparedStatement ps3 = con.prepareStatement("SELECT code FROM bus_course WHERE course=? AND corp=? AND ifile=?");
		PreparedStatement ps4 = con.prepareStatement("INSERT INTO bus_course (code,type,corp,course,ifile) VALUES (?,?,?,?,?)");
		PreparedStatement ps5 = con.prepareStatement("INSERT INTO bus_ref (idref,code) VALUES (?,?)");
		PreparedStatement ps6 = con.prepareStatement("SELECT max(code) FROM bus_course WHERE ifile=?");

		ArrayList<String[]> bris = new ArrayList<String[]>();
		NodeList nodes = node.getChildNodes();
		for (int i=0; i < nodes.getLength(); i++) {
			Node node2 = nodes.item(i);
			if (node2.getNodeName().equals("ksj:POS")) {
				NamedNodeMap nodeMap = node2.getAttributes();
				if (null != nodeMap) {
					for ( int j=0; j < nodeMap.getLength(); j++ ) {
						if (nodeMap.item(j).getNodeName().equals("idref")) {
							idrefStr = nodeMap.item(j).getNodeValue();
							System.out.println("found idref='"+ idrefStr +"'");
							break;
						}
					}
				}
			}
			else if (node2.getNodeName().equals("ksj:BSN")) {
				nameStr = node2.getTextContent();
			}
			else if (node2.getNodeName().equals("ksj:BRI")) {
				String[] rtn = anaComm(node2);
				if (rtn != null) {
					bris.add(rtn);
				}
			}
		}

		// idref と nameStr をデータベースに格納する
		boolean insert = true;
		ps1.setString(1, idrefStr);
		ResultSet rset = ps1.executeQuery();
		if (rset.next()) {
			insert = false;
		}
		rset.close();

		if (insert) {
			ps2.setString(1, idrefStr);
			ps2.setString(2, nameStr);
			ps2.setString(3, iFileName);
			System.out.println("INSERT INTO bus_stop (idref,name,ifile) VALUES ('"+ idrefStr +"','"+ nameStr +"','"+ iFileName +"')");
			ps2.executeUpdate();
		}

		for (String[] rtn : bris) {
			int code = 0;
			ps3.setString(1, rtn[1]);
			ps3.setString(2, rtn[2]);
			ps3.setString(3, iFileName);
			rset = ps3.executeQuery();
			if (rset.next()) {
				code = rset.getInt(1);
			}
			rset.close();

			if (code == 0) {
				ps6.setString(1, iFileName);
				ResultSet rset6 = ps6.executeQuery();
				if (rset6.next()) {
					code = rset6.getInt(1);
				}
				rset6.close();
				code++;

				System.out.println("code="+code);
				ps4.setInt(1, code);
				ps4.setInt(2, Integer.parseInt(rtn[0]));
				ps4.setString(3, rtn[2]);
				ps4.setString(4, rtn[1]);
				ps4.setString(5, iFileName);
				ps4.executeUpdate();
			}

			ps5.setString(1, idrefStr);
			ps5.setInt(2, code);
			ps5.executeUpdate();
		}

		ps1.close();
		ps2.close();
		ps3.close();
		ps4.close();
		ps5.close();
	}

	/**
	 * <ksj:BusStop gml:id="ED01_1">
	 * 	<ksj:position xlink:href="#n1"/>
	 * 	<ksj:busStopName>城堀</ksj:busStopName>
	 * 	<ksj:busRouteInformation>
	 * 		<ksj:BusRouteInformation>
	 * 			<ksj:busType>1</ksj:busType>
	 * 			<ksj:busOperationCompany>箱根登山バス</ksj:busOperationCompany>
	 * 			<ksj:busLineName>小01</ksj:busLineName>
	 * 		</ksj:BusRouteInformation>
	 * 	</ksj:busRouteInformation>
	 * 	<ksj:busRouteInformation>
	 * 		<ksj:BusRouteInformation>
	 * 			<ksj:busType>1</ksj:busType>
	 * 			<ksj:busOperationCompany>箱根登山バス</ksj:busOperationCompany>
	 * 			<ksj:busLineName>湯07</ksj:busLineName>
	 * 		</ksj:BusRouteInformation>
	 * 	</ksj:busRouteInformation>
	 * 	<ksj:busRouteInformation>
	 * 		<ksj:BusRouteInformation>
	 * 			<ksj:busType>1</ksj:busType>
	 * 			<ksj:busOperationCompany>箱根登山バス</ksj:busOperationCompany>
	 * 			<ksj:busLineName>湯11</ksj:busLineName>
	 * 		</ksj:BusRouteInformation>
	 * 	</ksj:busRouteInformation>
	 * </ksj:BusStop>
	 *
	 * @param con
	 * @param node
	 * @param iFileName		// ソースファイル名（拡張子を含まない）
	 * @throws IOException
	 * @throws SQLException
	 */
	public static void showBusStop(Connection con, Node node, String iFileName) throws IOException, SQLException {
		String idrefStr = "";
		String nameStr = "";
		PreparedStatement ps2 = con.prepareStatement("UPDATE bus_stop SET name=?,ifile=? WHERE idref=?");
		PreparedStatement ps3 = con.prepareStatement("SELECT code FROM bus_course WHERE course=? AND corp=? AND ifile=?");
		PreparedStatement ps4 = con.prepareStatement("INSERT INTO bus_course (code,type,corp,course,ifile) VALUES (?,?,?,?,?)");
		PreparedStatement ps5 = con.prepareStatement("INSERT INTO bus_ref (idref,code) VALUES (?,?)");
		PreparedStatement ps6 = con.prepareStatement("SELECT max(code) FROM bus_course WHERE ifile=?");

		ArrayList<String[]> bris = new ArrayList<String[]>();
		NodeList nodes = node.getChildNodes();
		for (int i=0; i < nodes.getLength(); i++) {
			Node node2 = nodes.item(i);
			if (node2.getNodeName().equals("ksj:position")) {
				NamedNodeMap nodeMap = node2.getAttributes();
				if (null != nodeMap) {
					for ( int j=0; j < nodeMap.getLength(); j++ ) {
						if (nodeMap.item(j).getNodeName().equals("xlink:href")) {
							idrefStr = nodeMap.item(j).getNodeValue();
							idrefStr = idrefStr.substring(1);
							System.out.println("found idref='"+ idrefStr +"'");
							break;
						}
					}
				}
			}
			else if (node2.getNodeName().equals("ksj:busStopName")) {
				nameStr = node2.getTextContent();
			}
			else if (node2.getNodeName().equals("ksj:busRouteInformation")) {
				String[] rtn = anaCommJGD(node2);
				if (rtn != null) {
					bris.add(rtn);
				}
			}
		}

		// idref と nameStr をデータベースに格納する
		ps2.setString(1, nameStr);
		ps2.setString(2, iFileName);
		ps2.setString(3, idrefStr);
		ps2.executeUpdate();

		for (String[] rtn : bris) {
			int code = 0;
			ps3.setString(1, rtn[1]);
			ps3.setString(2, rtn[2]);
			ps3.setString(3, iFileName);
			ResultSet rset = ps3.executeQuery();
			if (rset.next()) {
				code = rset.getInt(1);
			}
			rset.close();

			if (code == 0) {
				ps6.setString(1, iFileName);
				ResultSet rset6 = ps6.executeQuery();
				if (rset6.next()) {
					code = rset6.getInt(1);
				}
				rset6.close();
				code++;

				System.out.println("bus_course="+ code +" : "+ rtn[0] +" : "+ rtn[1] +" : "+ rtn[2] );
				ps4.setInt(1, code);
				ps4.setInt(2, Integer.parseInt(rtn[0]));
				ps4.setString(3, rtn[2]);
				ps4.setString(4, rtn[1]);
				ps4.setString(5, iFileName);
				ps4.executeUpdate();
			}

			System.out.println("bus_ref=("+ idrefStr +", "+ code +")");
			ps5.setString(1, idrefStr);
			ps5.setInt(2, code);
			ps5.executeUpdate();
		}

		ps2.close();
		ps3.close();
		ps4.close();
		ps5.close();
	}

	public static String[] anaComm(Node briNode) {
		String[] rtn = new String[3];
		rtn[0] = "";	// corp type
		rtn[1] = "";	// course name
		rtn[2] = "";	// corp name

		NodeList nodes = briNode.getChildNodes();
		for (int i=0; i < nodes.getLength(); i++) {
			Node node2 = nodes.item(i);
			if (node2.getNodeName().equals("ksj:BSC")) {
				rtn[0] = node2.getTextContent();
			}
			else if (node2.getNodeName().equals("ksj:BLN")) {
				rtn[1] = node2.getTextContent();
			}
			else if (node2.getNodeName().equals("ksj:BOC")) {
				rtn[2] = node2.getTextContent();
			}
		}
		return rtn;
	}

	/**
	 *
	 * 	<ksj:busRouteInformation>
	 * 		<ksj:BusRouteInformation>
	 * 			<ksj:busType>1</ksj:busType>
	 * 			<ksj:busOperationCompany>箱根登山バス</ksj:busOperationCompany>
	 * 			<ksj:busLineName>小01</ksj:busLineName>
	 * 		</ksj:BusRouteInformation>
	 * 	</ksj:busRouteInformation>
	 *
	 * @param briNode
	 * @return
	 */
	public static String[] anaCommJGD(Node briNode) {
		String[] rtn = new String[3];
		int vcnt = 0;

		NodeList nodes2 = briNode.getChildNodes();
		for (int i=0; i < nodes2.getLength(); i++) {
			Node node2 = nodes2.item(i);
			if (node2.getNodeName().equals("ksj:BusRouteInformation")) {
				NodeList nodes3 = node2.getChildNodes();
				for (int j=0; j < nodes3.getLength(); j++) {
					Node node3 = nodes3.item(j);
					if (node3.getNodeName().equals("ksj:busType")) {
						rtn[0] = new String(node3.getTextContent());
						vcnt++;
					}
					else if (node3.getNodeName().equals("ksj:busLineName")) {
						rtn[1] = new String(node3.getTextContent());
						vcnt++;
					}
					else if (node3.getNodeName().equals("ksj:busOperationCompany")) {
						rtn[2] = new String(node3.getTextContent());
						vcnt++;
					}
				}
			}
		}

		if (vcnt > 0) {
			return rtn;
		}
		return null;
	}

	public static void showGmPoint(Connection con, Node node) throws IOException, SQLException {
		String positionStr = "";
		String latStr = "";
		String lonStr = "";
		String idStr = "";

		NamedNodeMap nodeMap = node.getAttributes();
		if ( null != nodeMap ) {
			for ( int j=0; j<nodeMap.getLength(); j++ ) {
				if (nodeMap.item(j).getNodeName().equals("id")) {
					idStr = nodeMap.item(j).getNodeValue();
				}
			}
		}

		NodeList nodes = node.getChildNodes();
		for (int i=0; i < nodes.getLength(); i++) {
			Node node2 = nodes.item(i);
			if (node2.getNodeName().equals("jps:GM_Point.position")) {
				NodeList nodes3 = node2.getChildNodes();
				for (int j=0; j < nodes3.getLength(); j++) {
					Node node3 = nodes3.item(j);
					if (node3.getNodeName().equals("jps:DirectPosition")) {
						NodeList nodes4 = node3.getChildNodes();
						for (int k=0; k < nodes4.getLength(); k++) {
							Node node4 = nodes4.item(k);
							if (node4.getNodeName().equals("DirectPosition.coordinate")) {
								positionStr = node4.getTextContent();
								String[] str4Ary = positionStr.split(" ");
								latStr = str4Ary[0];
								lonStr = str4Ary[1];
								break;
							}
						}
						break;
					}
				}

				PreparedStatement ps6 = con.prepareStatement("UPDATE bus_stop SET lat=?,lon=?,fixed=? WHERE idref=?");
				double lat = Double.parseDouble(latStr);
				double lon = Double.parseDouble(lonStr);
				ps6.setDouble(1, lat);
				ps6.setDouble(2, lon);
				// ps6.setInt(3, (ConvBusstop.nocheck ? 0 : HttpGET.getMap(lat, lon, NEER)));
				ps6.setInt(3, 0);
				ps6.setString(4, idStr);
				System.out.println("UPDATE bus_stop("+ idStr +") lat="+ lat +", lon="+ lon +", fixed=0");
				ps6.executeUpdate();
				ps6.close();
			}
		}
	}

	/**
	 * <gml:Point gml:id="n1">
	 * 	<gml:pos>35.14591397 139.10569573</gml:pos>
	 * </gml:Point>
	 *
	 * @param con
	 * @param node
	 * @throws IOException
	 * @throws SQLException
	 */
	public static void showGmlPoint(Connection con, Node node, int areacode) throws IOException, SQLException {
		String positionStr = "";
		String latStr = "";
		String lonStr = "";
		String idStr = "";

		NamedNodeMap nodeMap = node.getAttributes();
		if ( null != nodeMap ) {
			for ( int j=0; j<nodeMap.getLength(); j++ ) {
				if (nodeMap.item(j).getNodeName().equals("gml:id")) {
					idStr = nodeMap.item(j).getNodeValue();
				}
			}
		}

		NodeList nodes = node.getChildNodes();
		for (int i=0; i < nodes.getLength(); i++) {
			Node node2 = nodes.item(i);
			if (node2.getNodeName().equals("gml:pos")) {
				positionStr = node2.getTextContent().trim();
				String[] str4Ary = positionStr.split(" ");
				latStr = str4Ary[0];
				lonStr = str4Ary[1];
				
				PreparedStatement ps6 = con.prepareStatement("INSERT INTO bus_stop (lat,lon,fixed, area,idref) VALUES (?,?,?,?,?)");
				double lat = Double.parseDouble(latStr);
				double lon = Double.parseDouble(lonStr);
				System.out.println("INSERT INTO bus_stop (lat,lon,fixed,area, idref) VALUES ('"+ latStr +"','"+ lonStr +"','0',"+ areacode +",'"+ idStr +"')");

				ps6.setDouble(1, lat);
				ps6.setDouble(2, lon);
				//ps6.setInt(3, (ConvBusstop.nocheck ? 0 : HttpGET.getMap(lat, lon, NEER)));
				ps6.setInt(3, 0);
				ps6.setInt(4, areacode);
				ps6.setString(5, idStr);
				ps6.executeUpdate();
				ps6.close();
			}
		}
	}

	/**
	 * 数値地図情報のGMLデータファイルかどうかを見極める
	 * @param f
	 * @return
	 */
	static boolean checkFile(File f, int areacode) {
		String name = f.getName();
		if (!name.startsWith(GML_DIR_PREFIX)) {
			return false;
		}
		if (!name.toUpperCase().endsWith(".XML")) {
			return false;
		}
		if (Integer.parseInt(name.substring(GML_DIR_PREFIX.length(), GML_DIR_PREFIX.length()+2)) == areacode) {
			return true;
		}
		return false;
	}
	
	/**
	 * 数値地図情報のデータディレクトリかどうかを見極める
	 * @param f
	 * @return
	 */
	public static boolean checkGMLdir(File f) {
		if (!f.isDirectory()) {
			return false;
		}
		String name = f.getName();
		if (!name.startsWith(GML_DIR_PREFIX)) {
			return false;
		}
		if (!name.toUpperCase().endsWith(GML_DIR_PRIFIX)) {
			return false;
		}
		return true;
	}

	public static final String GML_DIR_PREFIX = "P11-10_";
	public static final String GML_DIR_PRIFIX = "_GML";

}