hibernate Synchronizer 是一款生成hibernate cfg、hbm、pojo、dao代码的工具。相比较其它的同类工具,hibernate Synchronizer生成的代码比较优秀,还有它的同步功能,可以为我们省去很多时间,但遗憾的时,他不支持Spring DAO的生成。

hibernate Synchronizer生成的DAO是自带session管理了,如果单纯的给其DAO加上HibernateDaoSupport就是导致混乱。而且发现其DAO是以单例方式存在的。

幸好hibernate Synchronizer 的生成代码方式是基于模版方式,这就给了很大的空间来编写自己的模版,来生成代码。

下面我就贴一个自己写的BaseRootDao,去掉了其自带的Session管理代码,修改了原来的方法,以基于HibernateDaoSupport。

 

import java.io.Serializable;
import java.util.Collection;
import java.util.List;

import org.apache.log4j.Logger;
import org.hibernate.HibernateException;
import org.hibernate.SQLQuery;
import org.hibernate.Session;
import org.hibernate.criterion.DetachedCriteria;
import org.hibernate.criterion.Expression;
import org.hibernate.criterion.Order;
import org.springframework.orm.hibernate3.HibernateCallback;
import org.springframework.orm.hibernate3.support.HibernateDaoSupport;

public abstract class BaseRootDAO extends HibernateDaoSupport {
 /*
 
Logger for this class
  */
 private static final Logger log = Logger.getLogger(BaseRootDAO.class);

 /*
 
Return the specific Object class that will be used for class-specific
  implementation of this DAO.
 

  @return the reference Class
 
/
 protected abstract Class getReferenceClass();

 /*
 
Used by the base DAO classes but here for your modification Get object
  matching the given key and return it.
 
/
 protected Object get(Class refClass, Serializable key) {
  log.debug("get " + refClass + " instance with id: " + key);
  try {
   // 使用getHibernateTemplate()去操作DB。
   return getHibernateTemplate().get(refClass, key);
  } catch (RuntimeException re) {
   log.error("get failed", re);
   throw re;
  }

 }

 /*
 
Used by the base DAO classes but here for your modification Load object
  matching the given key and return it.
 
/
 protected Object load(Class refClass, Serializable key) {
  log.debug("load " + refClass + " instance with id: " + key);
  try {
   // 使用getHibernateTemplate()去操作DB。
   return getHibernateTemplate().load(refClass, key);
  } catch (RuntimeException re) {
   log.error("load failed", re);
   throw re;
  }

 }

 /*
 
Return all objects related to the implementation of this DAO with no
  filter.
 
/
 public java.util.List findAll() {

  return findAll(getDefaultOrder());

 }

 /*
 
Return all objects related to the implementation of this DAO with no
  filter. Use the session given.
 

  @param s
 
            the Session
  */
 public java.util.List findAll(Order defaultOrder) {

  DetachedCriteria crit = DetachedCriteria.forClass(getReferenceClass());
  if (null != defaultOrder)
   crit.addOrder(defaultOrder);
  return getHibernateTemplate().findByCriteria(crit);

 }

 /*
 
@param crit
  @return
 
/
 public java.util.List findByDetachedCriteria(DetachedCriteria crit) {
  return getHibernateTemplate().findByCriteria(crit);
 }

 /*
 
Return all objects related to the implementation of this DAO with a
  filter. Use the session given.
 

  @param propName
 
            the name of the property to use for filtering
  @param filter
 
            the value of the filter
  */
 protected DetachedCriteria findFiltered(String propName, Object filter) {
  return findFiltered(propName, filter, getDefaultOrder());
 }

 /*
 
Return all objects related to the implementation of this DAO with a
  filter. Use the session given.
 

  @param s
 
            the Session
  @param propName
 
            the name of the property to use for filtering
  @param filter
 
            the value of the filter
  @param orderProperty
 
            the name of the property used for ordering
  */
 protected DetachedCriteria findFiltered(String propName, Object filter,
   Order order) {
  DetachedCriteria crit = DetachedCriteria.forClass(getReferenceClass());
  crit.add(Expression.eq(propName, filter));
  if (null != order)
   crit.addOrder(order);
  return crit;
 }

 protected Order getDefaultOrder() {
  return null;
 }

 /*
 
Used by the base DAO classes but here for your modification Persist the
  given transient instance, first assigning a generated identifier. (Or
 
using the current value of the identifier property if the assigned
  generator is used.)
 
/
 protected Serializable save(final Object obj) {
  return getHibernateTemplate().save(obj);
 }

 /*
 
Used by the base DAO classes but here for your modification Either save()
  or update() the given instance, depending upon the value of its
 
identifier property.
  */
 protected void saveOrUpdate(final Object obj) {
  getHibernateTemplate().saveOrUpdate(obj);

 }

 /*
 
Used by the base DAO classes but here for your modification Update the
  persistent state associated with the given identifier. An exception is
 
thrown if there is a persistent instance with the same identifier in the
  current session.
 

  @param obj
 
            a transient instance containing updated state
  */
 protected void update(final Object obj) {

  getHibernateTemplate().update(obj);

 }

 /*
 
Delete all objects returned by the query
  */
 protected int delete(final Collection query) {
  int size = query.size();
  getHibernateTemplate().deleteAll(query);
  return size;
 }

 /*
 
Used by the base DAO classes but here for your modification Remove a
  persistent instance from the datastore. The argument may be an instance
 
associated with the receiving Session or a transient instance with an
  identifier associated with exi
sting persistent state.
 
/
 protected void delete(final Object obj) {
  getHibernateTemplate().delete(obj);
 }

 /*
 
Used by the base DAO classes but here for your modification Re-read the
  state of the given instance from the underlying database. It is
 
inadvisable to use this to implement long-running sessions that span many
  business tasks. This method is, however, useful in certain special
 
circumstances.
  */
 protected void refresh(Object obj) {
  getHibernateTemplate().refresh(obj);

 }

 protected void throwException(Throwable t) {
  if (t instanceof HibernateException)
   throw (HibernateException) t;
  else if (t instanceof RuntimeException)
   throw (RuntimeException) t;
  else
   throw new HibernateException(t);
 }

 // 當遇到HibernateTemplate沒提供,非用session才行的時候,用這種方式寫成HibernateCallback。
 // 原則還是讓session交給Spring去管理。
 public java.util.List findBySQL(final String queryString,
   final String alias, final Class refClass) {
  log.debug("findBySQL queryString " + queryString);
  return (List) getHibernateTemplate().execute(new HibernateCallback() {
   public Object doInHibernate(Session session)
     throws HibernateException {
    SQLQuery sqlQ = session.createSQLQuery(queryString);
    if (alias == null) {
     sqlQ.addEntity(refClass == null ? getReferenceClass()
       : refClass);
    } else {
     sqlQ.addEntity(alias,
       refClass == null ? getReferenceClass() : refClass);
    }
    return sqlQ.list();
   }
  }, true);
 }

 

package infoweb.dao;

import java.util.List;
import java.util.Iterator;

import infoweb.pojo.Info;

import net.sf.hibernate.HibernateException;
import net.sf.hibernate.Query;
import net.sf.hibernate.Session;

import org.springframework.orm.hibernate.HibernateCallback;
import org.springframework.orm.hibernate.support.HibernateDaoSupport;

/**

  • Title:

    *

Description:

*

Copyright: Copyright (c) 2004

*

Company:

  • @version 1.0
    */

public class InfoDAOImpl extends HibernateDaoSupport implements IInfoDAO {
/**

  • 构造函数
    */
    public InfoDAOImpl() {
    super();
    }

    /**

  • 增加记录
  • @param info Info
    */
    public void setInfo(Info info) throws Exception {
    getHibernateTemplate().save(info);
    }

    /**

  • 通过ID取得记录
  • @param id String
  • @return Info
    */
    public Info getInfoById(String id) throws Exception {
    Info info = (Info) getHibernateTemplate().load(Info.class, id);
    return info;
    }

    /**

  • 修改记录
  • @param Info info
    */
    public void modifyInfo(Info info) throws Exception {
    getHibernateTemplate().update(info);
    }

    /**

  • 删除记录
  • @param Info info
    */
    public void removeInfo(Info info) throws Exception {
    getHibernateTemplate().delete(info);
    }

    ////////////////////////////////////////////////////////
    ///// ///
    /////以下部份不带审核功能 ///
    ///// ///
    ////////////////////////////////////////////////////////

    /**

  • 取记录总数
  • @return int
    /
    public int getInfosCount() throws Exception {
    int count = 0;
    String queryString = "select count(
    ) from Info";
    count = ((Integer) getHibernateTemplate().iterate(queryString).next()).

    intValue();
    

    return count;
    }

    /**

  • 取所有记录集合
  • @return Iterator
    */
    public Iterator getAllInfos() throws Exception {
    Iterator iterator = null;
    String queryString = " select info from Info as info order by info.id desc";
    List list = getHibernateTemplate().find(queryString);
    iterator = list.iterator();
    return iterator;
    }

    /**

  • 取记录集合
  • @return Iterator
  • @param int position, int length
    */
    public Iterator getInfos(int position, int length) throws Exception {
    Iterator iterator = null;
    String queryString = " select info from Info as info order by info.id desc";
    Query query = getHibernateTemplate().createQuery(getSession(), queryString);
    //设置游标的起始点
    query.setFirstResult(position);
    //设置游标的长度
    query.setMaxResults(length);
    //记录生成
    List list = query.list();
    //把查询到的结果放入迭代器
    iterator = list.iterator();
    return iterator;
    }

    /**

  • 取第一条记录
  • @throws Exception
  • @return Station
    */
    public Info getFirstInfo() throws Exception {
    Iterator iterator = null;
    Info info = null;
    String queryString = "select info from Info as info order by info.id desc";
    Query query = getHibernateTemplate().createQuery(getSession(), queryString);
    //记录生成
    List list = query.list();
    //把查询到的结果放入迭代器
    iterator = list.iterator();
    if (iterator.hasNext()) {
    info = (Info) iterator.next();
    }
    return info;
    }

    /**

  • 取最后一条记录
  • @throws Exception
  • @return Station
    */
    public Info getLastInfo() throws Exception {
    Iterator iterator = null;
    Info info = null;
    String queryString = "select info from Info as info order by info.id asc";
    Query query = getHibernateTemplate().createQuery(getSession(), queryString);
    //记录生成
    List list = query.list();
    //把查询到的结果放入迭代器
    iterator = list.iterator();
    if (iterator.hasNext()) {
    info = (Info) iterator.next();
    }
    return info;

    }

    ////////////////////////////////////////////////////////
    ///// ///
    ///// 以下部份表中要有特定字段才能正确运行 个人和企业 ///
    ///// ///
    ////////////////////////////////////////////////////////

    /**

  • 取符合条件记录总数, [表中要有 isperson 字段]
  • @return int
  • @param int isPerson
    */

    public int getInfosCountByIsperson(int isPerson) throws Exception {
    int count = 0;
    String queryString =
    "select count(*) from Info as info where info.isperson =" + isPerson;
    count = ((Integer) getHibernateTemplate().iterate(queryString).next()).

    intValue();
    

    return count;
    }

    /**

  • 取所有符合条件记录集合, 模糊查询条件.[表中要有 isperson 字段]
  • @return Iterator
  • @param int isPerson
    */

    public Iterator getAllInfosByIsperson(int isPerson) throws Exception {
    Iterator iterator = null;
    String queryString = " select info from Info as info where info.isperson =" +

    isPerson + " order by info.id desc";
    

    List list = getHibernateTemplate().find(queryString);
    //把查询到的结果放入迭代器
    iterator = list.iterator();
    return iterator;
    }

    /**

  • 取符合条件记录集合, 模糊查询条件.[表中要有 isperson 字段]
  • @return Iterator
  • @param int isPerson,int position, int length
    */

    public Iterator getInfosByIsperson(int isPerson, int position, int length) throws
    Exception {
    Iterator iterator = null;
    String queryString = " select info from Info as info where info.isperson =" +

    isPerson + " order by info.id desc";
    

    //创建查询
    Query query = getHibernateTemplate().createQuery(getSession(), queryString);
    //设置游标的起始点
    query.setFirstResult(position);
    //设置游标的长度
    query.setMaxResults(length);
    //记录生成
    List list = query.list();
    //把查询到的结果放入迭代器
    iterator = list.iterator();
    return iterator;
    }

    ////////////////////////////////////////////////////////
    /////

    ///
    

    ///// 以下部份表中要有特定字段才能正确运行 查询部份 ///
    ///// ///
    ///////////////////////////////////////////////////////
    /**

  • 取符合条件记录总数, 模糊查询条件.[表中要有 title 字段]
  • @return int
  • @param String text
    /
    public int getInfosCount(String text) throws Exception {
    int count = 0;
    count = ((Integer) getHibernateTemplate().iterate(
    "select count(
    ) from Info as info where info.title like ‘%" + text +
    "%’").next()).intValue();
    return count;
    }

    /**

  • 取所有符合条件记录集合, 模糊查询条件.[表中要有 title 字段]
  • @return Iterator
  • @param String text
    */

    public Iterator getAllInfos(String text) throws Exception {
    Iterator iterator = null;
    String queryString =
    " select info from Info as info where info.title like ‘%" + text +
    "%’ order by info.id desc";
    //创建查询
    Query query = getHibernateTemplate().createQuery(getSession(), queryString);
    //记录生成
    List list = query.list();
    //把查询到的结果放入迭代器
    iterator = list.iterator();
    return iterator;
    }

    /**

  • 取符合条件记录集合, 模糊查询条件.[表中要有 title 字段]
  • @return Iterator
  • @param String text,int position, int length
    */
    public Iterator getInfos(String text, int position, int length) throws
    Exception {
    Iterator iterator = null;
    String queryString =
    " select info from Info as info where info.title like ‘%" + text +
    "%’ order by info.id desc";

    //创建查询
    Query query = getHibernateTemplate().createQuery(getSession(), queryString);
    //设置游标的起始点
    query.setFirstResult(position);
    //设置游标的长度
    query.setMaxResults(length);
    //记录生成
    List list = query.list();
    //把查询到的结果放入迭代器
    iterator = list.iterator();
    return iterator;
    }

    ////////////////////////////////////////////////////////
    ///// ///
    ///// 以下部份表中要有特定字段才能正确运行 注册相关 ///
    ///// ///
    ////////////////////////////////////////////////////////

    /**

  • 取符合条件记录总数.[ 表中要有 registername 字段]
  • @return int
  • @param String text
    /
    public int getInfosCountByRegisterName(String registerName) throws Exception {
    int count = 0;
    count = ((Integer) getHibernateTemplate().iterate(
    "select count(
    ) from Info as info where info.registername = ‘" +
    registerName + "’").next()).intValue();
    return count;
    }

    /**

  • 通过注册名取得一条记录,如有多条,只取第一条.[表中要有 registername字段]
  • @param registername String
  • @return Info
    */
    public Info getInfoByRegisterName(String registerName) throws Exception {
    Iterator iterator = null;
    Info info = null;
    String queryString =
    " select info from Info as info where info.registername=’" +
    registerName + "’ order by info.id desc";
    //创建查询
    Query query = getHibernateTemplate().createQuery(getSession(), queryString);
    //记录生成
    List list = query.list();
    //把查询到的结果放入迭代器
    iterator = list.iterator();
    if (iterator.hasNext()) {
    info = (Info) iterator.next();
    }
    return info;
    }

    /**

  • 通过注册名取得所有记录集合.[表中要有 registername字段]
  • @param registername String
  • @return Iterator
    */
    public Iterator getAllInfosByRegisterName(String registerName) throws
    Exception {
    Iterator iterator = null;
    String queryString =
    " select info from Info as info where info.registername=’" +
    registerName + "’ order by info.id desc";
    //创建查询
    Query query = getHibernateTemplate().createQuery(getSession(), queryString);
    //记录生成
    List list = query.list();
    //把查询到的结果放入迭代器
    iterator = list.iterator();
    return iterator;
    }

    /**

  • 通过注册名取得记录列表.[表中要有 registername字段]
  • @param registername String
  • @return Iterator
    */
    public Iterator getInfosByRegisterName(String registerName, int position,

    int length) throws Exception {
    

    Iterator iterator = null;
    String queryString =
    " select info from Info as info where info.registername=’" +
    registerName + "’ order by info.id desc";
    //创建查询
    Query query = getHibernateTemplate().createQuery(getSession(), queryString);
    //设置游标的起始点
    query.setFirstResult(position);
    //设置游标的长度
    query.setMaxResults(length);
    //记录生成
    List list = query.list();
    //把查询到的结果放入迭代器
    iterator = list.iterator();
    return iterator;
    }

    ////////////////////////////////////////////////////////
    ///// ///
    ///// 以下部份表中要有特定字段才能正确运行 树型版块 ///
    ///// ///
    ////////////////////////////////////////////////////////

    /**

  • 取记录总数.[ 表中要有 board_id 字段]
  • @return int
  • @param String boardId
    */
    public int getInfosCountByBoard(String boardId) throws Exception {
    int count = 0;

    count = ((Integer) getHibernateTemplate().iterate(
    "select count(*) from Info as info where info.boardId = ‘" + boardId +
    "’").next()).intValue();

    return count;
    }

    /**

  • 通过版块名取得所有记录集合.[表中要有 board_id字段]
  • @param BoardId String
  • @return Iterator
    */
    public Iterator getAllInfosByBoard(String boardId) throws Exception {
    Iterator iterator = null;
    String queryString = " select info from Info as info where info.boardId=’" +

    boardId + "' order by info.id desc";
    

    //创建查询
    Query query = getHibernateTemplate().createQuery(getSession(), queryString);
    //记录生成
    List list = query.list();
    //把查询到的结果放入迭代器

    iterator = list.iterator();
    return iterator;
    }

    /**

  • 通过版块名取得记录列表.[表中要有 board_id字段]
  • @param BoardId String
  • @return Iterator
    */
    public Iterator getInfosByBoard(String boardId, int position, int length) throws
    Exception {
    Iterator iterator = null;
    String queryString = " select info from Info as info where info.boardId=’" +

    boardId + "' order by info.id desc";
    

    //创建查询
    Query query = getHibernateTemplate().createQuery(getSession(), queryString);
    //设置游标的起始点
    query.setFirstResult(position);
    //设置游标的长度
    query.setMaxResults(length);
    //记录生成
    List list = query.list();
    //把查询到的结果放入迭代器
    iterator = list.iterator();

    return iterator;

    }

    /**

  • 取符合条件记录总数.[ 表中要有 board_id 字段,title] 模糊查询title
  • @return int
  • @param String boardId ,String text
    */
    public int getInfosCountByBoard(String boardId, String text) throws Exception {
    int count = 0;

    count = ((Integer) getHibernateTemplate().iterate(
    "select count(*) from Info as info where info.boardId=’" + boardId +
    "’ and info.title like ‘%" + text + "%’").next()).intValue();

    return count;

    }

    /**

  • 通过版块名取得记录列表.[表中要有 board_id字段] 模糊查询title
  • @param String boardID,int position, int length
  • @return Iterator
    */
    public Iterator getInfosByBoard(String boardId, int position, int length,

    String text) throws Exception {
    

    Iterator iterator = null;
    String queryString = " select info from Info as info where info.boardId=’" +

    boardId + "' and info.title like '%" + text +
    "%' order by info.id desc";
    

    //创建查询
    Query query = getHibernateTemplate().createQuery(getSession(), queryString);
    //设置游标的起始点
    query.setFirstResult(position);
    //设置游标的长度
    query.setMaxResults(length);
    //记录生成
    List list = query.list();
    //把查询到的结果放入迭代器
    iterator = list.iterator();
    return iterator;

    }

    ////////////////////////////////////////////////////////
    ///// ///
    /////以下部份带有审核功能 ///
    ///// ///
    ////////////////////////////////////////////////////////

    /**

  • 取记录总数
  • @return int
  • @param int isAuditing
    */
    public int getInfosCount(int isAuditing) throws Exception {
    int count = 0;

    count = ((Integer) getHibernateTemplate().iterate(
    "select count(*) from Info as info where info.isauditing=" +
    isAuditing).next()).intValue();
    return count;
    }

    /**

  • 取所有记录集合
  • @return Iterator
  • @param int position, int length,int isAuditing
    */
    public Iterator getAllInfos(int isAuditing) throws Exception {
    Iterator iterator = null;
    String queryString =
    " select info from Info as info where info.isauditing=" + isAuditing +
    " order by info.id desc";
    Query query = getHibernateTemplate().createQuery(getSession(), queryString);
    //记录生成
    List list = query.list();
    //把查询到的结果放入迭代器
    iterator = list.iterator();
    return iterator;
    }

    /**

  • 取记录集合
  • @return Iterator
  • @param int position, int length,int isAuditing
    */
    public Iterator getInfos(int position, int length, int isAuditing) throws
    Exception {
    Iterator iterator = null;
    String queryString =
    " select info from Info as info where info.isauditing=" + isAuditing +
    " order by info.id desc";

    Query query = getHibernateTemplate().createQuery(getSession(), queryString);
    //设置游标的起始点
    query.setFirstResult(position);
    //设置游标的长度
    query.setMaxResults(length);
    //记录生成
    List list = query.list();
    //把查询到的结果放入迭代器
    iterator = list.iterator();

    return iterator;
    }

    ////////////////////////////////////////////////////////////////
    ///// ///
    ///// 以下部份表中要有特定字段才能正确运行 有审核功能 个人和企业 ///
    ///// ///
    ///////////////////////////////////////////////////////////////

    /**

  • 取符合条件记录总数, [表中要有 isperson isAuditing 字段]
  • @return int
  • @param int isPerson,int isAuditing
    */

    public int getInfosCountByIsperson(int isPerson, int isAuditing) throws
    Exception {
    int count = 0;

    count = ((Integer) getHibernateTemplate().iterate(
    "select count(*) from Info as info where info.isperson =" + isPerson +
    " and info.isauditing=" + isAuditing).next()).intValue();

    return count;
    }

    /**

  • 取所有符合条件记录集合, 模糊查询条件.[表中要有 isperson isAuditing 字段]
  • @return Iterator
  • @param int isPerson,int isAuditing
    */

    public Iterator getAllInfosByIsperson(int isPerson, int isAuditing) throws
    Exception {
    Iterator iterator = null;
    String queryString = " select info from Info as info where info.isperson =" +

    isPerson + " and info.isauditing=" + isAuditing +
    " order by info.id desc";
    

    Query query = getHibernateTemplate().createQuery(getSession(), queryString);
    //记录生成
    List list = query.list();
    //把查询到的结果放入迭代器
    iterator = list.iterator();

    return iterator;
    }

    /**

  • 取符合条件记录集合, 模糊查询条件.[表中要有 isperson isAuditing 字段]
  • @return Iterator
  • @param int isPerson,int position, int length,int isAuditing
    */

    public Iterator getInfosByIsperson(int isPerson, int position, int length,

    int isAuditing) throws Exception {
    

    Iterator iterator = null;
    String queryString = " select info from Info as info where info.isperson =" +

    i
    

sPerson + " and info.isauditing=" + isAuditing +
" order by info.id desc";

Query query = getHibernateTemplate().createQuery(getSession(), queryString);
//设置游标的起始点
query.setFirstResult(position);
//设置游标的长度
query.setMaxResults(length);
//记录生成
List list = query.list();
//把查询到的结果放入迭代器
iterator = list.iterator();

return iterator;

}

////////////////////////////////////////////////////////
///// ///
///// 要有特定字段才能正确运行 有审核功能 查询部份 ///
///// ///
///////////////////////////////////////////////////////
/**

  • 取符合条件记录总数, 模糊查询条件.[表中要有 title 字段]
  • @return int
  • @param String text,int isAuditing
    */
    public int getInfosCount(String text, int isAuditing) throws Exception {
    int count = 0;

    count = ((Integer) getHibernateTemplate().iterate(
    "select count(*) from Info as info where info.isauditing=" +
    isAuditing + " and info.title like ‘%" + text + "%’").next()).

    intValue();
    

    return count;
    }

    /**

  • 取所有符合条件记录集合, 模糊查询条件.[表中要有 title 字段]
  • @return Iterator
  • @param String text,int isAuditing
    */

    public Iterator getAllInfos(String text, int isAuditing) throws Exception {
    Iterator iterator = null;
    String queryString =
    " select info from Info as info where info.isauditing=" + isAuditing +
    " and info.title like ‘%" + text + "%’ order by info.id desc";

    Query query = getHibernateTemplate().createQuery(getSession(), queryString);
    //记录生成
    List list = query.list();
    //把查询到的结果放入迭代器
    iterator = list.iterator();

    return iterator;
    }

    /**

  • 取符合条件记录集合, 模糊查询条件.[表中要有 title 字段]
  • @return Iterator
  • @param String text,int position, int length,int isAuditing
    */
    public Iterator getInfos(String text, int position, int length,

    int isAuditing) throws Exception {
    

    Iterator iterator = null;
    String queryString =
    " select info from Info as info where info.isauditing=" + isAuditing +
    " and info.title like ‘%" + text + "%’ order by info.id desc";

    //创建查询
    Query query = getHibernateTemplate().createQuery(getSession(), queryString);
    //设置游标的起始点
    query.setFirstResult(position);
    //设置游标的长度
    query.setMaxResults(length);
    //记录生成
    List list = query.list();
    //把查询到的结果放入迭代器
    iterator = list.iterator();

    return iterator;
    }

    ////////////////////////////////////////////////////////
    ///// ///
    ///// 要有特定字段才能正确运行 有审核功能 注册相关 ///
    ///// ///
    ////////////////////////////////////////////////////////

    /**

  • 取符合条件记录总数.[ 表中要有 registername isauditing字段]
  • @return int
  • @param String text,int isAuditing
    */
    public int getInfosCountByRegisterName(String registerName, int isAuditing) throws
    Exception {
    int count = 0;

    count = ((Integer) getHibernateTemplate().iterate(
    "select count(*) from Info as info where info.isauditing=" +
    isAuditing + " and info.registername = ‘" + registerName + "’").next()).

    intValue();
    

    return count;
    }

    /**

  • 通过注册名取得一条记录,如有多条,只取第一条.[表中要有 registername isauditing字段]
  • @param registername String,int isAuditing
  • @return Info
    */
    public Info getInfoByRegisterName(String registerName, int isAuditing) throws
    Exception {
    Iterator iterator = null;
    Info info = null;

    String queryString =
    " select info from Info as info where info.isauditing=" + isAuditing +
    " and info.registername=’" + registerName + "’ order by info.id desc";

    Query query = getHibernateTemplate().createQuery(getSession(), queryString);
    //记录生成
    List list = query.list();
    //把查询到的结果放入迭代器
    iterator = list.iterator();
    if (iterator.hasNext()) {
    info = (Info) iterator.next();
    }

    return info;
    }

    /**

  • 通过注册名取得所有记录集合.[表中要有 registername isauditing字段]
  • @param registername String,int isAuditing
  • @return Iterator
    */
    public Iterator getAllInfosByRegisterName(String registerName, int isAuditing) throws
    Exception {
    Iterator iterator = null;

    String queryString =
    " select info from Info as info where info.isauditing=" + isAuditing +
    " and info.registername=’" + registerName + "’ order by info.id desc";

    Query query = getHibernateTemplate().createQuery(getSession(), queryString);
    //记录生成
    List list = query.list();
    //把查询到的结果放入迭代器
    iterator = list.iterator();

    return iterator;
    }

    /**

  • 通过注册名取得记录列表.[表中要有 registername isauditing字段]
  • @param registername String,int isAuditing
  • @return Iterator
    */
    public Iterator getInfosByRegisterName(String registerName, int position,

    int length, int isAuditing) throws
    

    Exception {
    Iterator iterator = null;
    String queryString =
    " select info from Info as info where info.isauditing=" + isAuditing +
    " and info.registername=’" + registerName + "’ order by info.id desc";

    //创建查询
    Query query = getHibernateTemplate().createQuery(getSession(), queryString);
    //设置游标的起始点
    query.setFirstResult(position);
    //设置游标的长度
    query.setMaxResults(length);
    //记录生成
    List list = query.list();
    //把查询到的结果放入迭代器
    iterator = list.iterator();

    return iterator;
    }

    ////////////////////////////////////////////////////////
    ///// ///
    ///// 要有特定字段才能正确运行 有审核功能 树

型版块 ///
///// ///
////////////////////////////////////////////////////////

/**

  • 取记录总数.[ 表中要有 board_id isauditing字段]
  • @return int
  • @param String boardId,int isAuditing
    */
    public int getInfosCountByBoard(String boardId, int isAuditing) throws
    Exception {
    int count = 0;

    count = ((Integer) getHibernateTemplate().iterate(
    "select count(*) from Info as info where info.isauditing=" +
    isAuditing + " and info.boardId = ‘" + boardId + "’").next()).intValue();

    return count;
    }

    /**

  • 通过版块名取得所有记录集合.[表中要有 board_id isauditing字段]
  • @param BoardId String,int isAuditing
  • @return Iterator
    */
    public Iterator getAllInfosByBoard(String boardId, int isAuditing) throws
    Exception {
    Iterator iterator = null;

    String queryString =
    " select info from Info as info where info.isauditing=" + isAuditing +
    " and info.boardId=’" + boardId + "’ order by info.id desc";

    Query query = getHibernateTemplate().createQuery(getSession(), queryString);
    //记录生成
    List list = query.list();
    //把查询到的结果放入迭代器
    iterator = list.iterator();
    return iterator;
    }

    /**

  • 通过版块名取得记录列表.[表中要有 board_id isauditing字段]
  • @param BoardId String,int isAuditing
  • @return Iterator
    */
    public Iterator getInfosByBoard(String boardId, int position, int length,

    int isAuditing) throws Exception {
    

    Iterator iterator = null;
    String queryString =
    " select info from Info as info where info.isauditing=" + isAuditing +
    " and info.boardId=’" + boardId + "’ order by info.id desc";

    //创建查询
    Query query = getHibernateTemplate().createQuery(getSession(), queryString);
    //设置游标的起始点
    query.setFirstResult(position);
    //设置游标的长度
    query.setMaxResults(length);
    //记录生成
    List list = query.list();
    //把查询到的结果放入迭代器
    iterator = list.iterator();

    return iterator;

    }

    /**

  • 取符合条件记录总数.[ 表中要有 board_id isauditing字段,title] 模糊查询title
  • @return int
  • @param String boardId ,String text,int isAuditing
    */
    public int getInfosCountByBoard(String boardId, String text, int isAuditing) throws
    Exception {
    int count = 0;

    count = ((Integer) getHibernateTemplate().iterate(
    "select count(*) from Info as info where info.isauditing=" +
    isAuditing + " and info.boardId=’" + boardId +
    "’ and info.title like ‘%" +
    text + "%’").next()).intValue();

    return count;

    }

    /**

  • 通过版块名取得记录列表.[表中要有 board_id字段 isauditing] 模糊查询title
  • @param String boardId,int position, int length,int isAuditing
  • @return Iterator
    */
    public Iterator getInfosByBoard(String boardId, int position, int length,

    String text, int isAuditing) throws Exception {
    

    Iterator iterator = null;
    String queryString =
    " select info from Info as info where info.isauditing=" + isAuditing +
    " and info.boardId=’" + boardId + "’ and info.title like ‘%" + text +
    "%’ order by info.id desc";

    //创建查询
    Query query = getHibernateTemplate().createQuery(getSession(), queryString);
    //设置游标的起始点
    query.setFirstResult(position);
    //设置游标的长度
    query.setMaxResults(length);
    //记录生成
    List list = query.list();
    //把查询到的结果放入迭代器
    iterator = list.iterator();

    return iterator;

    }

}

本文使用软件的下载地址

(1)Windows 2000 Service Pack 3.exe 下载地址:

http://download.microsoft.com/download/win2000platform/SP/SP3/NT5/CN/W2Ksp3.exe

(2)j2sdk-1_4_1_02-windows-i586.exe 下载地址:

http://java.sun.com/webapps/download/Redirect/32167382/584747937728280705350560724608606933322
8071972022813600060132859339008063305596058473206-3865/j2sdk-1_4_1_02-windows-i586.exe

(3)jakarta-tomcat-4.1.18-LE-jdk14.exe 下载地址:

http://apache.linuxforum.net/dist/jakarta/tomcat-4/binaries/tomcat-4.1.18-LE-jdk14.exe

(4)apache_2.0.44-win32-x86-no_ssl.msi下载地址:

http://apache.linuxforum.net/dist/httpd/binaries/win32/apache_2.0.44-win32-x86-no_ssl.msi

(5)mod_jk2-2.0.43.dll下载地址:

http://jakarta.apache.org/builds/jakarta-tomcat-connectors/jk2/release/v2.0.1/bin/win32/mod_jk2-2.0.43.dll

前言:用mod_jk2来整合Tomcat服务器和Apache服务器,简单多了。

一、安装Windows 2000 Professional

安装完Windows 2000 Professional后,强烈建议安装Windows 2000 Service Pack 3,因为在Windows 2000下安装
最新的JDK时需要事先安装Windows 2000 Service Pack 3。

二、安装Java的JDK(j2sdk-1_4_1_02-windows-i586.exe)

安装时按照默认目录: C:\j2sdk1.4.1_02,JDK安装完成后需要设置系统变量。在桌面上右击"我的电脑",点"属性",
选择"高级",点"系统变量",在"系统变量"中做如下设置:

(1)找到PATH,点"编辑",只在"变量值"里最后添加: C:\j2sdk1.4.1_02\bin;

然后点"确定"。

(2)点"新建",在"变量名"里输入: CLASSPATH

在"变量值"里输入: .;C:\j2sdk1.4.1_02\lib\tools.jar;

然后点"确定",注意前面那个点,它表示当前目录,包含了该目录后,就可以到任意目录下去执行需要用到该目录下某个
类的 Java 程序。

三、安装Tomcat(jakarta-tomcat-4.1.18-LE-jdk14.exe)

安装时只改变安装目录,设置为 C:\Tomcat 4.1,其余全为默认,密码自己设定。Tomcat安装完成后也需要设置系统变量,
在桌面上右击"我的电脑",点"属性",选择"高级",点"系统变量",在"系统变量"中做如下设置:

(1) 点"新建",在"变量名"里输入: JAVA_HOME

在"变量值"里输入: C:\j2sdk1.4.1_02

然后点"确定"保存。

(2) 点"新建",在"变量名"里输入: TOMCAT_HOME

在"变量值"里输入: C:\Tomcat 4.1

然后点"确定"保存。

四、测试Tomcat

(1)启动Tomcat服务器,在"开始" -> "程序" -> "Apache Tomcat 4.1"中点"Start Tomcat" (出现一个"命令提示符"

窗口,不要关闭它),Tomcat服务器就开始运行了。

(2)在IE中输入 http://localhost:8080/ 后,看到Tomcat的首页(上面有只小猫)表示安装成功。

(3)关闭Tomcat服务器,在"开始"-> "程序" ->" Apache Tomcat 4.1"中点"Stop Tomcat" (原来开服务器时的"命令提示

符"窗口便自动关闭),Tomcat服务器就停止运行了。

五、建立虚拟目录

Tomcat服务器有默认的虚拟目录(C:\Tomcat 4.1\ webapps),但是我们开发网站时一般放在自建的文件夹下,如果想把一般

文件夹变成Tomcat认识的虚拟目录,我们需要自己配置。现在结合实例介绍配置Tomcat虚拟目录的方法:

(1)在D盘建立Zgtt文件夹,然后在文件夹下做个简单的JSP文件(用于测试),命名为index.jsp  ,内容如下:  

      <html>  

      <head>  

      <title>Hello</title>  

      </head>  

      <body>  

      <%  out.println("Hello  World!");  %>  

      </body>  

</html>

(2)关闭Tomcat服务器(方法见"四、测试Tomcat"中(3)说明)。

(3)在C盘下,打开"Tomcat 4.1"文件夹,然后再打开子目录"conf"找到"server.xml"文件,用记事本打开它并查找"</Host>",

在</Host>前面添加这句代码:<Context path="/zgtt" docBase="D:\Zgtt" debug="0" reloadable="true"

crossContext="true"></Context> ,然后保存文件。

(4)启动Tomcat服务器(方法见"四、测试Tomcat"中(1)说明)。

(5)在IE中输入 http://localhost:8080/zgtt/index.jsp 链接后,如果看到"Hello World! " 后表示虚拟目录zgtt设置成功。

六、安装Apache(apache_2.0.44-win32-x86-no_ssl.msi)

(1)安装时改变安装目录,设置为 C:\。

(2)参数设置可以任意取值(注意要按照提示的格式填写)。

(3)修改一个小错误:

Apache2.0.44有一个小问题,默认安装成功后,在Apache2主目录下的htdocs目录中没有index.html文件,我们须将该目录

下的index.html.en改名为index.html。

(4)解决不自动显示中文:编辑C:\Apache2\conf目录下配置文件httpd.conf。用记事本打开它并查找"AddDefaultCharset

ISO-8859-1",注释掉"AddDefaultCharset ISO-8859-1",即在"AddDefaultCharset ISO-8859-1"前加个"#"字符。

然后在"#AddDefaultCharset ISO-8859-1"下面添加如下三行:

AddDefaultCharset GB2312

DefaultLanguage GB2312

AddLanguage zh-cn .cn

七、测试Apache

安装配置完Apache服务器后,我们需要测试一下,看看是否安装成功。

(1)启动Apache服务器:点"开始" -> "程序" -> "Apache HTTP Server 2.0.44" -> "Control Apache Server" ->

"Monitor Apache Servers",如果在系统“拖盘”处看见Apache的羽毛图标上出现绿色小三角.则表示Apache服务器成功启动了。

(2)在IE中输入"http://l
ocalhost
"后,看到Apache的带有羽毛的apache首页,表示安装成功。

(3)关闭Apache服务器:单击系统“拖盘”里Apache的图标,选"Stop",如果在系统“拖盘”处看见Apache的羽毛图标上出现红色的

圆点.则表示Apache服务器成功关闭了。

八、整合Apache服务器和Tomcat服务器

这是最关键的一步,一定要仔细按照步骤配置:

(1)关掉Apache服务器(方法见"七、测试Apache"中(3)说明)。

(2)关掉Tomcat服务器. (方法见"四、测试Tomcat"中(3)说明)。

(3)将mod_jk2-2.0.43.dll复制到C:\Apache2\modules子目录下。

(4)编辑C:\Apache2\conf目录下配置文件httpd.conf。在此文件的最后添加以

下几行:

    LoadModule  jk2_module  modules/mod_jk2-2.0.43.dll    

    &lt;VirtualHost  *&gt;    

    ServerAdmin  [webmaster@dummy-host.example.com](mailto:webmaster@dummy-host.example.com)    

    DocumentRoot  &quot;C:/Tomcat  4.1/webapps&quot;    

    ServerName  dummy-host.example.com    

    DirectoryIndex  index.htm  index.html  index.jsp    

    ErrorLog  logs/dummy-host.example.com-error_log    

    CustomLog  logs/dummy-host.example.com-access_log  common    

    &lt;/VirtualHost&gt;    

注意DocumentRoot一行要与自己的TOMCAT安装目录一致。    

DirectoryIndex一行是为了自动解释JSP类型的文件。

(5)在C:\Apache2\conf目录下新建一个文件,一定命名为workers2.properties。 workers2.properties内容如下:

[shm]

file=${serverRoot}/logs/shm.file

size=1048576

Example socket channel, override port and host.

[channel.socket:localhost:8009]

port=8009

host=127.0.0.1

define the worker

[ajp13:localhost:8009]

channel=channel.socket:localhost:8009

Uri mapping

[uri:/*]

worker=ajp13:localhost:8009

九、测试Apache服务器和Tomcat服务器整合

(1)启动Apache服务器(方法见"7.测试Apache"中(1)说明)。

(2)启动Tomcat服务器(方法见"4.测试Tomcat"中(1)说明)。

(3)在IE中输入"http://localhost:8080/zgtt/index.jsp"。链接后,如果看到"Hello World! ",表明Tomcat启动成功。

(4)在IE中输入"http://localhost/zgtt/index.jsp"。链接后,如果再次看到"Hello World! ",则表明Apache服务器和Tomcat服
务器整合成功。

 

注:
然后安装。(我的安装在G:\Program Files\Apache Group下
G:\Program Files\Apache Group\Apache2
G:\Program Files\Apache Group\Tomcat 5.0.7)
然后把mod_jk_2.0.46.dll复制到G:\Program Files\Apache Group\Apache2\modules下。

先开始修改 G:\Program Files\Apache Group\Apache2\conf\http.conf:
查找"DirectoryIndex",在index.html后添加index.jsp
成下面这样:
DirectoryIndex index.html index.jsp index.html.var
查找 "Listen",修改端口号成下面这样:

#Listen 12.34.56.78:80
Listen 80
在http.conf的结尾加上以下内容:
LoadModule jk_module modules/mod_jk_2.0.46.dll
JkWorkersFile "G:/Program Files/Apache Group/Tomcat 5.0.7/conf/workers.properties"
JkLogFile "G:/Program Files/Apache Group/Tomcat 5.0.7/logs/mod_jk2.log"
JkLogLevel info
<VirtualHost >
ServerAdmin lnboy@delphibbs.com
DocumentRoot "G:/Program Files/Apache Group/Tomcat 5.0.7/webapps/ROOT"
ServerName www.delphibbs.com
DirectoryIndex index.html index.htm index.jsp
ErrorLog logs/shsc-error_log.txt
CustomLog logs/shsc-access_log.txt common
JkMount /servlet/
ajp13 #让Apache支持对servlet传送,用以Tomcat解析
JkMount /*.jsp ajp13 #让Apache支持对jsp传送,用以Tomcat解析
</VirtualHost>
保存http.conf。

再在G:\Program Files\Apache Group\Tomcat 5.0.7\conf下新建workers.properties。

写入以下内容:
workers.tomcat_home=G:\Program Files\Apache Group\Tomcat 5.0.7
workers.java_home=G:\JBuilder9\jdk1.4
ps=\
worker.list=ajp13
worker.ajp13.port=8009
worker.ajp13.host=localhost
worker.ajp13.type=ajp13
worker.ajp13.lbfactor=1

保存workers.properties。

最后是先启动tomcat,再启动Apache,就成功了 。
分别打开http://127.0.0.1/http://127.0.0.1:8080/都可以看见tomcat的欢迎画面。
在G:\Program Files\Apache Group\Tomcat 5.0.7\webapps\ROOT下新建一个demo.htm文件,
里面写上hello,world!!!,然后保存。
再打开http://127.0.0.1/demo.htmhttp://127.0.0.1:8080/demo.htm
都可以看见刚才新建的页面。

但是此时如果打开http://127.0.0.1/jsp-examples/是会出现404错误,
http://127.0.0.1:8080/jsp-examples/则正常。
接下来我们需要在http.conf里添加虚拟目录的映射。

http.conf里
查找:"Alias",再继续找 "icons",找到下面这样的一段:
Alias /icons/ "G:/Program Files/Apache Group/Apache2/icons/"

<Directory "G:/Program Files/Apache Group/Apache2/icons">
Options Indexes MultiViews
AllowOverride None
Order allow,deny
Allow from all
</Directory>

添加我需要的虚拟目录:
Alias /jsp-examples/ "G:\Program Files\Apache Group\Tomcat 5.0.7\webapps\servlets-examples"

<Directory "G:\Program Files\Apache Group\Tomcat 5.0.7\webapps\servlets-examples">
Options Indexes MultiViews
AllowOverride None
Order allow,deny
Allow from all
</Directory>
重新启动apache,这下http://127.0.0.1/jsp-examples/可以打开了
(注意和tomcat下打开有所不同,这是因为apache的默认文档不包含index.html)

我总算明白,以前参考了n篇我以前从来没有成搞成功,其中一个原因就是:
http.conf里"G:/Program Files/Apache Group/Tomcat 5.0.7/webapps/ROOT"这样含有空格的路径没有用引号引起来,导致apache无法正确解析,所以一直出错:(,而给出的例子大多都是装在
C:\apache,c:\tomcat5之类的路径,所以不会碰到这样的错误。

版权声明:可以任意转载,转载时请务必以超链接形式标明文章原始出处和作者信息及本声明
http://www.chedong.com/tech/google_url.html

关键词:"url rewrite" mod_rewrite isapi rewrite path_info iis "search engine friendly"

内容摘要:不得不承认,将动态网页链接rewriting成静态链接是最保险和稳定的面向搜索引擎优化方式

此外随着互联网上的内容以惊人速度的增长也越来越突出了搜索引擎的重要性,如果网站想更好地被搜索引擎收录,网站设计除了面向用户友好(User Friendly)外,搜索引擎友好(Search Engine Friendly)的设计也是非常重要的。进入搜索引擎的页面内容越多,则被用户用不同的关键词找到的几率越大。在Google的算法调查一文中提到一个站点被Google索引页面的数量其实对PageRank也是有一定影响的。由于Google 突出的是整个网络中相对静态的部分(动态网页索引量比较小),链接地址相对固定的静态网页比较适合被Google索引(怪不得很多大网站的邮件列表归档和BLOG按日期归档的文档很容被搜的到),因此很多关于面向搜索引擎 URL设计优化(URI Pretty)的文章中提到了很多利用一定机制将动态网页参数变成像静态网页的形式:
比如可以将:
http://phpunixman.sourceforge.net/index.php?mode=man&parameter=ls

变成:
http://phpunixman.sourceforge.net/index.php/man/ls

实现方式主要有2种:

把URI地址用作参数传递:URL REWRITE

最简单的是基于各种WEB服务器中的URL重写转向(Rewrite)模块的URL转换:
这样几乎可以不修改程序的实现将 news.asp?id=234 这样的链接映射成 news/234.html,从外面看上去和静态链接一样。Apache服务器上有一个模块(非缺省):mod_rewrite:URL REWRITE功能之强大足够写上一本书。

当我需要将将news.asp?id=234的映射成news/234.html时,只需设置:
RewriteRule /news/(\d+).html /news.asp\?id=$1 [N,I]
这样就把 /news/234.html 这样的请求映射成了 /news.asp?id=234
当有对/news/234.html的请求时:web服务器会把实际请求转发给/news.asp?id=234

而在IIS也有相应的REWRITE模块:比如ISAPI REWRITEIIS REWRITE,语法都是基于正则表达式,因此配置几乎和apache的mod_rewrite是相同的:

比对于某一个简单应用可以是:
RewriteRule /news/(\d+).html /news/news.php\?id=$1 [N,I]
这样就把 http://www.chedong.com/news/234.html 映射到了 http://www.chedong.com/news/news.php?id=234

一个更通用的能够将所有的动态页面进行参数映射的表达式是:
http://www.myhost.com/foo.php?a=A&b=B&c=C
表现成 http://www.myhost.com/foo.php/a/A/b/B/c/C。
RewriteRule (.?.php)(\?[^/])?/([^/])/([^/])(.+?)?$1(?2$2&:\?)$3=$4?5$5: [N,I]

以下是针对phpBB的一个Apache mod_rewrite配置样例:

    RewriteEngine On
    RewriteRule /forum/topic_(.+)\.html$  /forum/viewtopic.php?t=$1 [L]
    RewriteRule /forum/forum_(.+)\.html$ /forum/viewforum.php?f=$1 [L]
    RewriteRule /forum/user_(.+)\.html$  /forum/profile.php?mode=viewprofile&u=$1  [L]

这样设置后就可以通过topic_1234.html forum_2.html user_34.html这样的链接访问原来的动态页面了。

通过URL REWRITE还有一些好处:
mod_rewrite和isapirewrite基本兼容,但是还是有些不同,比如:isapirewrite中"?"需要转义成"\?",mod_rewrite不用,isapirewrite支持 "\d+" (全部数字),mod_rewrite不支持

  • 隐藏后台实现:这在后台应用平台的迁移时非常有用:当从asp迁移到java平台时,对于前台用户来说,根本感受不到后台应用的变化;* 简化数据校验:因为像(\d+)这样的参数,可以有效的控制数字的格式甚至位数;

比如我们需要将应用从news.asp?id=234迁移成news.php?query=234时,前台的表现可以一直保持为 news/234.html。从实现应用和前台表现的分离:保持了URL的稳定性,而使用mod_rewrite甚至可以把请求转发到其他后台服务器上。

基于PATH_INFO的URL美化

Url美化的另外一个方式就是基于PATH_INFO:
PATH_INFO是一个CGI 1.1的标准,经常发现很多跟在CGI后面的"/value_1/value_2"就是PATH_INFO参数:
比如:http://phpunixman.sourceforge.net/index.php/man/ls 中:$PATH_INFO = "/man/ls"

PATH_INFO是CGI标准,因此PHP Servlet等都有的支持。比如Servlet中就有request.getPathInfo()方法。
注意:/myapp/servlet/Hello/foo的 getPathInfo()返回的是/foo,而/myapp/dir/hello.jsp/foo的getPathInfo()将返回的 /hello.jsp,从这里你也可以知道jsp其实就是一个Servlet的PATH_INFO参数。ASP不支持PATH_INFO
PHP中基于PATH_INFO的参数解析的例子如下:
//注意:参数按"/"分割,第一个参数是空的:从/param1/param2中解析出$param1 $param2这2个参数
if ( isset($_SERVER["PATH_INFO"]) ) {
list($nothing, $param1, $param2) = explode(‘/‘, $_SERVER["PATH_INFO"]);
}

如何隐蔽应用:例如 .php,的扩展名:
在APACHE中这样配置:
<FilesMatch "^app_name$">
ForceType application/x-httpd-php
</FilesMatch>

如何更像静态页面:app_name/my/app.html
解析的PATH_INFO参数的时候,把最后一个参数的最后5个字符“.html”截断即可。
注意:APACHE2中缺省是不允许PATH_INFO的,需要设置 AcceptPathInfo on

特别是针对使用虚拟主机用户,无权安装和配置mod_rewrite的时候,PATH_INFO往往就成了唯一的选择。

OK,这样以后看见类似于http://www.example.com/article/234这样的网页你就知道可能是 article/show.php?id=234这个php程序生成的动态网页,很多站点表面看上去可能有很多静态目录,其实很有可能都是使用1,2个程序实现的内容发布。比如很多WIKIWIKI系统都使用了这个机制:整个系统就一个简单的wiki程序,而看上去的目录其实都是这个应用拿后面的地址作为参数的查询结果。

利用基于MOD_REWRITE/PATH_INFO + CACHE服务器的解决方案对原有的动态发布系统进行改造,也可以大大降低旧有系统升级到新的内容管理系统的成本。并且方便了搜索引擎收录入索引。

附:如何在IIS上利用PHP支持PATH_INFO

PHP的ISAPI模式安装备忘:只试成 php-4.2.3-Win32

解包目录

php-4.2.3-Win32.zip c:\php

PHP.INI初始化文件

复制:c:\php\php.ini-dist 到 c:\winnt\php.ini

配置文件关联

按照install.txt中的说明配置文件关联

运行库文件

复制 c:\php\php4ts.dll 到 c:\winnt\system32\php4ts.dll

这样运行后:会发现php把PATH_INFO映射到了物理路径上
Warning: Unknown(C:\CheDong\Downloads\ariadne\www\test.php\path): failed to create stream: No such file or directory in Unknown on line 0

Warning: Unknown(): Failed opening ‘C:\CheDong\Downloads\ariadne\www\test.php\path’ for inclusion (include_path=’.;c:\php4\pear’) in Unknown on line 0

安装ariadne的PATCH

停止IIS服务
net stop iisadmin
ftp://ftp.muze.nl/pub/ariadne/win/iis/php-4.2.3/php4isapi.dll
覆盖原有的c:\php\sapi\php4isapi.dll

注:
ariadne是一个基于PATH_INFO的内容发布系统,
PHP 4.3.2 RC2中CGI模式的PATH_INFO已经修正,照常安装即可。

参考资料:
URL Rewrite文档:
ISAPI REWRITE文档
IIS的ISAPI REWRITE下载(免费)
http://httpd.apache.org/docs/mod/mod_rewrite.html
http://httpd.apache.org/docs-2.0/mod/mod_rewrite.html

搜索引擎友好的URL设计
http://www.sitepoint.com/article/485
说不定这个URL原来就是articel.php?id=485

一个基于PATH_INFO的开源内容管理系统
http://typo3.com/

Google的PageRank算法说明:
http://pr.efactory.de/

表A























































































声明


描述


CREATE PROCEDURE


建立一个存放在MySQL数据库的表格的存储过程。


CREATE FUNCTION


建立一个用户自定义的函数,尤其是返回数据的存储过程。


ALTER PROCEDURE


更改用CREATE PROCEDURE 建立的预先指定的存储过程,其不会影响相关存储过程或存储功能。.


ALTER FUNCTION


更改用CREATE FUNCTION 建立的预先指定的存储过程,其不会影响相关存储过程或存储功能。.


DROP PROCEDURE


从MySQL的表格中删除一个或多个存储过程。


DROP FUNCTION


从MySQL的表格中删除一个或多个存储函数。


SHOW CREATE PROCEDURE


返回使用CREATE PROCEDURE
建立的预先指定的存储过程的文本。这一声明是SQL:2003规范的一个MySQL扩展。


SHOW CREATE FUNCTION


返回使用CREATE
FUNCTION建立的预先指定的存储过程的文本。这一声明是SQL:2003规范的一个MySQL扩展。


SHOW PROCEDURE STATUS


返回一个预先指定的存储过程的特性,包括名称、类型、建立者、建立日期、以及更改日期。这一声明是SQL:2003规范的一个MySQL扩展。


SHOW FUNCTION STATUS


返回一个预先指定的存储函数的特性,包括名称、类型、建立者、建立日期、以及更改日期。这一声明是SQL:2003规范的一个MySQL扩展。


CALL


调用一个使用CREATE PROCEDURE建立的预先指定的存储过程。


BEGIN … END


包含一组执行的多声明。


DECLARE


用于指定当地变量、环境、处理器,以及指针。


SET


用于更改当地和全局服务器变量的值。


SELECT … INTO


用于存储显示变量的纵列。


OPEN


用于打开一个指针。


FETCH


使用特定指针来获得下一列。


CLOSE


用于关闭和打开指针。


IF


一个An if-then-else-end if 声明。


CASE … WHEN


一个 case声明的结构


LOOP


一个简单的循环结构;可以使用LEAVE 语句来退出。


LEAVE


用于退出IF,CASE,LOOP,REPEAT以及WHILE 语句。


ITERATE


用于重新开始循环。


REPEAT


在结束时测试的循环。


WHILE


在开始时测试的循环。


RETURNS


返回一个存储过程的值。


MySQL 5.0支持存储过程语句。





一.创建存储过程

1.基本语法:

create procedure sp_name()
begin
………
end
2.参数传递
二.调用存储过程

1.基本语法:call sp_name()
注意:存储过程名称后面必须加括号,哪怕该存储过程没有参数传递
三.删除存储过程

1.基本语法:
drop procedure sp_name//
2.注意事项
(1)不能在一个存储过程中删除另一个存储过程,只能调用另一个存储过程
四.区块,条件,循环

1.区块定义,常用
begin
……
end;
也可以给区块起别名,如:
lable:begin
………..
end lable;
可以用leave lable;跳出区块,执行区块以后的代码
2.条件语句


if 条件 then
statement
else
statement
end if;

3.循环语句
(1).while循环


[label:] WHILE expression DO

statements

END WHILE [label] ;


(2).loop循环


[label:] LOOP

statements

END LOOP [label];


(3).repeat until循环


[label:] REPEAT

statements

UNTIL expression

END REPEAT [label] ;

五.其他常用命令

1.show procedure status
显示数据库中所有存储的存储过程基本信息,包括所属数据库,存储过程名称,创建时间等
2.show create procedure sp_name

存储过程创建语法:





CREATE PROCEDURE procedure_name ([parameter[,…])

[LANGUAGE SQL]

[ [NOT] DETERMINISTIC ]

[{CONTAINS SQL|MODIFIES SQL DATA|READS SQL DATA|NO SQL}]

[SQL SECURITY {DEFINER|INVOKER} ]

[COMMENT comment_string]

procedure_statements



可用SHOW PROCEDURE STATUS 或 SHOW CREATE PROCEDURE
来查看存储过程信息
另,系统表INFORMATION_SCHEMA.ROUTINES也包含了存储过程的一些信息
同样地,函数也可以使用同样方式查看(SHOW
FUNCTION STATUS)

函数的创建





CREATE FUNCTION function_name (parameter[,…])

RETURNS datatype

[LANGUAGE SQL]

[ [NOT] DETERMINISTIC ]

[ {CONTAINS SQL | NO SQL | MODIFIES SQL DATA | READS SQL DATA} ]

[ SQL SECURITY {DEFINER|INVOKER} ]

[ COMMENT comment_string ]

语句体



函数与存储过程基本一样,其区别主要有:
1、 要使用RETURNS指定返回类型
2、
函数必须返回值,且在语句体中使用RETURN返回(注意:指定返回类型用RETURNS,返回值用RETURN)
3、
参数不区分IN,OUT,全部为IN类形

例:
CREATE FUNCTION cust_status(in_status CHAR(1))
RETURNS
VARCHAR(20)
BEGIN
DECLARE long_status VARCHAR(20);
IF in_status
= ‘O’ THEN SET long_status=’Overdue’;
ELSEIF in_status = ‘U’
THEN SET long_status=’Up to date’;
ELSEIF in_status = ‘N’ THEN SET
long_status=’New’;
END IF;

RETURN(long_status);
END;

调用:
SELECT
cust_status(‘O’);

触发器





CREATE [DEFINER={user|CURRENT_USER}] TRIGGER trigger_name

{BEFORE|AFTER} {UPDATE|INSERT|DELETE}

ON table_name

FOR EACH ROW

trigger_statements



意义:当对表table_name执行update,insert,delete操作之前(before)或之后(after)时触发语句trigger_statements操作

例:
mysql> CREATE TRIGGER account_balance_au
AFTER UPDATE ON
account_balance FOR EACH ROW
BEGIN
DECLARE dummy INT;
IF
NEW.balance<0 THEN
SET NEW.balance=NULL;
END
IF;
END

上述触发器表示:当更新表account_balance之后,如果更新的值balance小于0,则将它改为NULL,
注:如果为OLD.balance则表示更新前的原值

最近工作比较忙,都怎么游戏,现在写一点游戏希望能唤起我游戏的心!!!!

最近干了熟女(圣女贞德),和FFT相像的系统,画面(系统和FFT还是有很大的差距的),画面还是不错的,剧情….看不懂,据说很符合事实….反正对这个没啥感觉,如果出了美版或许还看得懂..系统加入了XX系统(不知道叫啥,就是打了背后的人可以重击)和技能合成系统(咋觉得和格兰迪亚很想的系统),可是每个人只能带6个技能就太不爽了,系统来说在PSP上还是不错的,LV5出品的…不过听说FFT要复刻PSP了…这个我喜欢….在游戏中期,去打了几次龙,结果任务等级立马提升很多,和剧情等级太不相称,以致于后面的游戏太没挑战,兴趣落了一大半,而且变身后的技能,都差不多,只不过颜色变了变,也没啥收集的欲望,简单来说熟女还算不错的SRPG,玩玩还可以.消遣消遣

然后又一起干了地牢围攻,觉得这次PSP版的太简单,真的太简单,我选的是女人,总的来说太强,拿弓箭的时候敌人进不了身,那双刀的时候,秒杀敌人(连最终BOSS也被我秒了),而且觉得传了衣服都太难看..(头像画的还可以),不过装备还是不错的,而且魔法的效果做的也不错,是psp上值得玩的一款游戏.

KILLZONE,在ps2上玩的FPS就是KILLZONE和BLACK,用手柄玩FPS还是有难度的(习惯了还好,不过在PSP上玩荣誉勋章…我晕),SONY曾经打算用KILLZONE来做HALO杀手的,不过显然没成功..-..-!!,不过这次的psp上的killzone还是不错的,记得有人评价为:不玩对不起自己…看的出做的还是听用心的.不错的画面,任务设计的也还可以,也有一定的难度,虽然单人战役有点短,不过在多人连线和挑战任务上还是可以发费很多时间的.推荐.

ACE X 从PS 到PS2 到PSP 皇牌空战基本每作我都要去尝试(GBA上的没玩过),这次的ACE X和以往的没啥大的革新,基本属于稳定的续作,操作也没怎么改变(除了那个口键用法稍有不同),PSP上的画面表现力还是不错的,比PS的好,驾驶战斗机的感觉还是不错的.嘻嘻,而且有人汉化了…嘻嘻

还有LOCO ROCO..嘻嘻 hoho

在一个Liunx下运行JasperReportS总是抛出Error initializing graphic environment的异常,跟踪JasperReports的源代码发现在net.sf.jasperreports.engine.util.JRGraphEnvInitializer中抛出异常,是GraphicsEnvironment.getLocalGraphicsEnvironment().getAvailableFontFamilyNames()这个方法出错,单写一个servlet测试抛出

Exception in thread "main" java.lang.IllegalArgumentException
at java.nio.Buffer.position(Buffer.java:218)
at sun.font.TrueTypeFont.lookupName(TrueTypeFont.java:818)
at sun.font.TrueTypeFont.getFamilyName(TrueTypeFont.java:884)
at sun.java2d.SunGraphicsEnvironment.getAvailableFontFamilyNames(SunGraphicsEnvironment.java:476)
at sun.java2d.SunGraphicsEnvironment.getAvailableFontFamilyNames(SunGraphicsEnvironment.java:494)

这样的异常

Google一下发现这个问题还挺多的(JasperReports直接抛这个异常不就好了么,还自己抛一个出来,害我绕了很多圈圈)

这是一个Java的字体设置问题造成的

简单一个 export LANG=en_US.UTF-8

一般来说要设置 Linux 系统的环境变量只需要在 /etc/profile (全局) 或者 ~/.bashrc (单个用户) 即可。但是对于 LANG 变量来说,有时候你即使在所有这些初始化脚本里面 export 过了,LANG 的值还是纹丝不动。实际上,你需要去修改 /etc/sysconfig/i18n 文件里面的内容。

Ok问题解决了,看来当LANG设置为中文时就是出现这个问题,治本的方法还得改font.conf,不知那位大侠能倾囊相授.嘻嘻

今天早上来看到了6.0的特性。收藏了。

初探Java SE 6: 一个桌面赢家

一个有着丰富的Java经验的开发者试用了一下Java SE 6 Beta,并且认为Java SE 6 有希望成为桌面开发的一次革命。

by Eric Bruno (Translated by Xu Ting)

刚刚发布的Java Standard Edition 6 (Java SE
6,也被称为Mustang)beta版完整的包括了预定的新特性,对于主流的应用来说,已经足够稳定。我在第一时间下载并尝试了这个新?动物?,并且被
它全新的桌面特性所震撼。除了Java平台一贯以来的命名方式上的改变(去掉了2),它还包含了包含了很多值得探索一下的新特性。这些新特性可以分为两
类:桌面和核心。

桌面上的改进主要集中在用户界面(UI)性能,以及,用本地化的接口与OS的桌面整合。核心部分则集中在提高开发人员的生产性,以及Java程序的可管理性上。Sun的Mustang团队也对Web Service以及安全性方面作出了显著的改进。

不管怎么样,无论你是一个应用程序开发人员,还是一个系统管理者,或者提供独立的工具,或者是一个安全专家,Java SE 6都为你准备了些东西。这片文章主要是详细讨论了一些我试用过了的有趣的特性。

有关Java核心的新特性以及改进。

关于Java 核心部分,我们认为是部分((语言和工具)对所有的Java而言都是很基础的东西,包括从界面API到服务端API库。下面我将按照不同的分类来讨论这些与Java核心相关的特性。

开发人员的生产性

新的Java编译器API允许你从一个Java应用程序中去编译另外的Java源程序。在这样的编译的过程中,应用程序将根据计算出来的依赖关系去
访问那些相关的API库文件,这个过程也会产生Warning,Error以及其他一些在编译的时候会产生的消息。虽然这个功能是我不太会常去用的,但是
我很快发现了一种用法。比如:我在我的应用程序A中,快速的用这个特性来编译A的数据访问层代码。我可以用我的代码去生成并且编译我在A程序中要去访问的
数据库表的类,最终的结果可以是一个从Ant脚本中生成出来的JAR文件。这样最显而易见的一个事实就是我可以在自己的程序中去重新编译生成这些重要的文
件,至少我可以不需要改动应用程序。

Java Scripting,是在Java
SE6中实现了的JSR223。这是一个脚本框架,提供了让脚本语言来访问Java内部的方法。你可以在运行的时候找到脚本引擎,然后调用这个引擎去执行
脚本。这个脚本API允许你为脚本语言提供Java支持。另外,Web Scripting
Framework允许脚本代码在任何的Servlet容器(例如Tomcat)中生成Web内容。

对于调试,Java平台的调试器(JPDA)已经提供了死锁诊测,并且可以为产生了死锁的对象生成堆栈信息。另外,Java SE 6允许在一个运行中的JVM上,添加不同的诊断工具 。

应用程序管理

Java SE
6中对内存泄漏增强了分析以及诊断能力。当遇到java.lang.OutOfMemory异常的时候,可以得到一个完整的堆栈信息,并且当堆已经满了的
时候,会产生一个Log文件来记录这个致命错误。另外,JVM还添加了一个选项,允许你在堆满的时候运行脚本。(这也就是提供了另外一种方法来诊断错误)

增强的JMX 监视API在MBean的属性值传入了一个特定的参数的时候,允许这个应用程序发送一个事件通告。(这里的属性值可以在很复杂的类型中)

对于Solaris 10的用户,为Solaris提供的Hotspot JVM中,提供了一种通过Solaris
DTrace(这是个系统的调试工具)来追踪显示JVM内部的活动情况,包括垃圾收集,类装载,线程,锁等等。我在JavaOne上得到了一个第一手的
DEMO,这个DEMO所显示的能追踪到的详细情况简直是太棒了。比如,当一个应用程序运行的时候,DTrace允许可以在任何地方中止代码,查看所有被
载入内存的库(不仅仅是Java的类库,甚至是系统级别的库),并且可以单部跟踪到Solaris的内核中去,甚至可以直达硬件!Java新提供的这个工
具为全世界提供了一种系统级别的追踪调试手段。我还记得以前我在Solaris的JVM上经常会收到一些Signal8这样的错误,这个特性将会省去我许
多的猜测。

Web services

Java SE 6 包含了一些支持Web Services的新API。XML 数字签名API,允许你为基于Java上的Web
Services数据提供加密的可能。Java-XML Web Services
(JAX-WS)2.0API更新的以前称为JAX-RPC的API库。增强的Java-XML Binding
(JAXB)2.0包含了对XMLSchema的支持,以及将某个Class绑定到一个Schema上去。最后, Streaming API for
XML
(STaX)提供了一个双向API,这个API可以通过一个事件流来读取或者写入XML,其中包括跳过某个部分,然后直接关注与文档中的另外一个小部分的
能力。

安全

Java SE 6的安全部分,整合了GSS/Kerberos的操作API,LDAP上的JAAS认证,以及一个?请求安全认证?的框架,这个框架允许应用程序从一系列的协议中选择一种?请求安全认证?所用的协议。

桌面特性以及改进

Java长久以来,一直被认为是一个一流的服务器端软件的语言,但是桌面GUI应用上只能是二流地位。
Sun的Java桌面工作小组正在努力改变这个现状。通过调用系统的GUI接口,来更好的显示Java 的GUI应用。他们的努力不仅改善了Java
SE 6中的GUI性能,也改变了一些Java GUI应用程序的行为。(比如提供了DnD的支持)

Java SE 6中的桌面新特性,大部分 都来自于JDesktop Integration
Components(JDIC)项目。JDIC项目为Java的应用程序提供了访问OS底层本地桌面GUI接口的方法,例如浏览器,Email编辑器,
文件类型绑定,系统托盘,阴应用程序启动,打印等等。 下面是那些Java SE 6中最显著的一些桌面特性。

* 启动界面的支持。启动界面(Splash Screens)是一个应用程序启动的时候,用户等待的时候给用户看的界面。Java SE 6中的启动界面甚至可以在JVM启动之前显示出来。

* JFC以及Swing中的改进:

      o Java SE 6通过调用Windows的API,不仅提高了 GUI的性能,也保证了在当前以及以后的Windows版本中的兼容

      o 增强的布局管理包含了一个可定制的布局管理,另外还包含了一些使得GUI元素布局的时候更加简单的方法。

      o Java SE 6中显著的增强了Swing控件的托拽功能,并且是可以定制的。

      o 真正的双缓冲,提供了快速,平滑的图形效果。

*
系统托盘的支持。在java.awt包中,增加了SystemTray和TrayIcon两个类,它们允许你在Windows或者使用GNome
的Linux的系统托盘区,添加图标,提示信息,弹出菜单。系统托盘区是所有的应用程序都共享的区域,通常在屏幕的右下角。通过系统的动作和事件可以允许
你的Java应用程序去相应在托盘区的鼠标事件。我发现这个特性也同样对我的服务器程序非常有用,比如,我可以通过桌面API,非常轻松的启动一个浏览
器,并且打开这个服务器程序的管理界面(当然,是HTML页面)。在Linux或者Window上,我再也不需要自己输入管理界面的URL和端口号了,只
要简单的点击一下托盘图标就可以:)

* JTable支持打印了

* Java 2D方面增强了许多。 主要是在字符显示上,尤其在LCD的显示屏上。整合了许多字体反锯齿的设定来保证平滑的显示文字。
  • 新的java.awt.Desktop包。Java SE 6中这个新的包目标是让Java
    的GUI应用程序成为?一等公民?。有了这个包,Java的应用程序可以启动默认的浏览器和邮件客户端,并且整合了一些通用桌面应用程序的启动。例如启动
    OpenOffice,然后打开,编辑,打印一些制定的类型。Desktop包通过action事件来实现的,你可以将这些Action整合到你的应用程
    序中去。

    • 国际化。Java SE 6提供了一些本地化特性的可扩充性,比如日期格式,Unicode文字的一致性,资源簇等等。

一场Java桌面革命

Java SE 6提供了许多的特性,改进,bug修改等
(这些可以参考我的另外一篇翻译),本文旨在对Java这个即将到来的重要版本之前做一个历史的记录。 这个改动涉及到了Java
SE如此多的方面,乃至几乎所有的Java应用程序都会被波及到,包括那些Java EE的应用程序。

Java SE 6有潜力成就一场桌面革命,就如同Java 2成就了一场服务器革命。最好是现在就为这场即将到来的风暴做好准备,让你自己成为革命的先锋人员。

Eric Bruno is a New York-based consultant who has built high-volume
Web applications, database systems, and real-time transactional systems
in Java and C++. Visit www.ericbruno.com for more about him.

Posted in Java Tech | No Comments »

New features in Java SE 6.0

Monday, March 6th, 2006

A few days ago, Sun just released Java SE 6.0 Beta. And I had viewed
the release notes and some articles discussed the new features .

Here is a translation about the new features and enhancement list
provided by Sun officially. And I had translated this to
Chinese(Simplified Chinese.)

The original document is placed HERE.

Here is the translation.

#Thanks to Zou, he helped me review this translation.

#There are some features about the compiler and VM are remained as
original, because I am short at this areas. If you have any
suggestions, please leave your comments of send a mail to my mailbox:
tonny.xugmail.com

TOTO.net braket

Just another WordPress weblog

Blog Technical Articles Photos Resume

Java SE 6.0(代号?Mustang")是即将面世的下一版本Java。相比较J2SE 5.0,添加了许多重要的特性和增强功能,这些新特性和增强功能如下面的列表。

所有的条目都按照涉及范围以及所属的组件分类。第一列表示了修改涉及的范围。

* JSR - 表示这是实现了某一项JSR(Java标准需求)的重大特性

* API - 表示新添加的API

* IMP - 表示没有增加新的API,只是作了一些类似性能增强的改进。

请注意:这是个Beta里程碑,?Mustang?还在继续开发中。这些都是JSR270中的内容。JSR270本身并没有定义新的特性,但是它列
举了一系列的其他JSR或者是正在进行评审中的需求。?Mustang?的最终发布版的目标是包含JSR270中所有的特性,但是不保证(有些已经商议通
过的特性可能最终不会在?野马?版本中实现)。