package com.steering.common;

import java.lang.reflect.Field;
import java.lang.reflect.Method;
import java.lang.reflect.Type;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.Iterator;
import java.util.Map;
import java.util.regex.Matcher;
import net.sf.json.JSONObject;

/**
 * ʵ���๤��
 * 
 * @author Administrator
 * 
 */
public class EntityTool {

	/**
	 * ��ʵ�����ֵ�滻Sql�ж���� #�ֶ���# ����
	 * 
	 * @param sql
	 *            sql���
	 * @param obj
	 *            ʵ�������
	 * @return �滻���sql��䡣
	 */
	public static String fillSqlByEntity(String sql, Object obj) {
		String sql2 = sql;
		Class<?> cls = obj.getClass();
		Field[] fields = cls.getDeclaredFields();
		for (Field field : fields) {
			if (field.getGenericType().toString()
					.equals("class java.lang.String")) {
				try {
					String fieldName = getMethodName(field.getName());
					Method m = (Method) obj.getClass().getMethod(
							"get" + fieldName);
					String val = (String) m.invoke(obj);//
					val = val == null ? "" : val;
					String sqlFieldName = "#" + getSqlFieldName(fieldName)
							+ "#";
					val = val.replaceAll("'", "''");
					sql2 = sql2.replaceAll(sqlFieldName, Matcher.quoteReplacement(val));
				} catch (Exception e) {
					continue;
				}
			}
		}

		return sql2;
	}

	// ���磺 StdCodeת��Ϊ STD_CODE
	private static String getSqlFieldName(String fieldName) {
		StringBuilder sb = new StringBuilder(fieldName);
		for (int i = 1; i < sb.length(); i++) {
			char ch = sb.charAt(i);
			if (Character.isUpperCase(ch)) {
				sb.insert(i, '_');
				i++;
			}
		}

		return sb.toString().toUpperCase();
	}

	private static String getMethodName(String fildeName) throws Exception {
		byte[] items = fildeName.getBytes();
		items[0] = (byte) ((char) items[0] - 'a' + 'A');
		return new String(items);
	}

	/**
	 * ��ȡʵ���༯��
	 * 
	 * @param rs
	 *            ���
	 * @param cls
	 *            ʵ���������
	 * @return ʵ���༯��
	 */
	public static <T> ArrayList<T> getEntitysByRs(ResultSet rs, Class<T> cls) {
		ArrayList<T> list = new ArrayList<T>();
		Method[] methods = cls.getMethods();
		try {
			while (rs.next()) {
				T obj = cls.newInstance();
				for (int i = 0; i < methods.length; i++) {
					try {
						Method method = methods[i];
						String methodName = method.getName();
						if (methodName.startsWith("set")) {
							String entityName = methodName.substring(3,
									methodName.length());
							String fieldName = getSqlFieldName(entityName);
							String val = rs.getString(fieldName) == null ? "" : rs.getString(fieldName);
							method.invoke(obj, val);
						}
					} catch (Exception e) {
					}
				}
				list.add(obj);
			}
		} catch (Exception e) {
			return list;
		}
		return list;
	}
	
	/**
	 * ͨ��sql��ȡʵ���༯�ϣ����ر�Connection��
	 * @param sql
	 * @param con
	 * @param cls
	 * @return
	 */
	public static <T> ArrayList<T> getEntitysBySqlNoClsCon(String sql, Connection con,
			Class<T> cls) {
		PreparedStatement ps = null;
		ResultSet rs = null;
		try {
			ps = con.prepareStatement(sql);
			rs = ps.executeQuery();
			return getEntitysByRs(rs, cls);
		} catch (SQLException e) {
			
		}
		finally{
			if(rs != null){
				try{
				rs.close();
				}catch(Exception ex){}
			}
			if(ps != null){
				try{
				ps.close();
				}catch(Exception ex){}
			}
		}
		return null;
	}

	/**
	 * ͨ����RS��ȡ����ʵ����
	 * @param rs
	 * @param cls
	 * @return
	 */
	public static <T> T getEntityByRs(ResultSet rs, Class<T> cls) {
		T list = null;
		Method[] methods = cls.getMethods();
		HashMap<String, Method> map = new HashMap<String, Method>();

		for (int i = 0; i < methods.length; i++) {
			try {
				Method method = methods[i];
				String methodName = method.getName();
				if (methodName.startsWith("set")) {
					String entityName = methodName.substring(3,
							methodName.length());
					String fieldName = getSqlFieldName(entityName);
					if (rs.findColumn(fieldName) > 0) {
						map.put(fieldName, method);
					}
				}
			}
			catch (Exception e) {
			}
		}

		try {
			if (rs.next()) {
				T obj = cls.newInstance();
				Iterator<Map.Entry<String, Method>> iter = map.entrySet()
						.iterator();
				while (iter.hasNext()) {
					Map.Entry<String, Method> entry = iter.next();
					String key = entry.getKey();
					Method val = entry.getValue();
					String strValue = rs.getString(key);
					strValue = strValue == null ? "" : strValue;
					val.invoke(obj, strValue);
				}
				list = obj;
			}
		}
		catch (Exception e) {
			return list;
		}
		return list;
	}

	/**
	 * ͨ��sql��ȡʵ���༯�ϣ��ر�Connection��
	 * @param sql
	 * @param con
	 * @param cls
	 * @return
	 */
	public static <T> ArrayList<T> getEntitysBySql(String sql, Connection con,
			Class<T> cls) {
		PreparedStatement ps = null;
		ResultSet rs = null;
		try {
			ps = con.prepareStatement(sql);
			rs = ps.executeQuery();
			return getEntitysByRs(rs, cls);
		} catch (SQLException e) {
			
		}
		finally{
			if(rs != null){
				try{
				rs.close();
				}catch(Exception ex){}
			}
			if(ps != null){
				try{
				ps.close();
				}catch(Exception ex){}
			}
			if(con != null){
				try{
					con.close();
				}catch(Exception ex){}
			}
		}
		return null;
	}
	
	@SuppressWarnings("unchecked")
	public static <T> T getEntityByJSONStr(String strJSON, Class<T> cls){
		JSONObject obj = JSONObject.fromObject(strJSON);
		T tEntity = (T)JSONObject.toBean(obj, cls);
		
		return tEntity;
	}
	
	/**
	 * ����������NULLת��Ϊ���ַ�
	 * 
	 * @param obj
	 */
	public static void nullConverNullString(Object obj) {
		if (obj != null) {

			Class<? extends Object> classz = obj.getClass();
			// ��ȡ���иö��������ֵ
			Field fields[] = classz.getDeclaredFields();
			// ��������ֵ��ȡ����������Ϊ null ֵ��
			for (Field field : fields) {
				try {
					Type t = field.getGenericType();
					if (!t.toString().equals("boolean")) {
						Method m = classz.getMethod("get"
								+ change(field.getName()));
						Object name = m.invoke(obj);// ���ø��ֶε�get����
						if (name == null) {

							Method mtd = classz.getMethod(
									"set" + change(field.getName()),
									new Class[] { String.class });// ȡ��������ķ�������
							mtd.invoke(obj, new Object[] { "" });// ִ����Ӧ��ֵ����
						}
					}

				} catch (Exception e) {
					e.printStackTrace();
				}
			}
		}
	}
	
	/**
	 * @param src
	 *            Դ�ַ�
	 * @return �ַ���src�ĵ�һ����ĸת��Ϊ��д��srcΪ��ʱ����null
	 */
	public static String change(String src) {
		if (src != null) {
			StringBuffer sb = new StringBuffer(src);
			sb.setCharAt(0, Character.toUpperCase(sb.charAt(0)));
			return sb.toString();
		} else {
			return null;
		}
	}
	
/////TZH 10.30 ZL add
	public static String underlineToCamel(String str) {
		StringBuilder result = new StringBuilder();
		String[] words = str.split("_");
		for (int i = 0; i < words.length; i++) {
			String word = words[i];
			if (i == 0) {
				result.append(word.toLowerCase());
			} else {
				result.append(Character.toUpperCase(word.charAt(0)) + word.substring(1).toLowerCase());
			}
		}
		return result.toString();
	}
/////
}
