﻿<?xml version="1.0" encoding="utf-8" standalone="yes"?><rss version="2.0" xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:trackback="http://madskills.com/public/xml/rss/module/trackback/" xmlns:wfw="http://wellformedweb.org/CommentAPI/" xmlns:slash="http://purl.org/rss/1.0/modules/slash/"><channel><title>BlogJava-hengheng123456789-随笔分类-JAVA-Common</title><link>http://www.blogjava.net/hengheng123456789/category/18808.html</link><description /><language>zh-cn</language><lastBuildDate>Wed, 10 Oct 2007 16:12:52 GMT</lastBuildDate><pubDate>Wed, 10 Oct 2007 16:12:52 GMT</pubDate><ttl>60</ttl><item><title>Text Format Covert Tool (UltraCodingSwitch)</title><link>http://www.blogjava.net/hengheng123456789/archive/2007/09/03/142352.html</link><dc:creator>哼哼</dc:creator><author>哼哼</author><pubDate>Mon, 03 Sep 2007 08:00:00 GMT</pubDate><guid>http://www.blogjava.net/hengheng123456789/archive/2007/09/03/142352.html</guid><wfw:comment>http://www.blogjava.net/hengheng123456789/comments/142352.html</wfw:comment><comments>http://www.blogjava.net/hengheng123456789/archive/2007/09/03/142352.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.blogjava.net/hengheng123456789/comments/commentRss/142352.html</wfw:commentRss><trackback:ping>http://www.blogjava.net/hengheng123456789/services/trackbacks/142352.html</trackback:ping><description><![CDATA[<br />
a good tool can convert text code to UTF8/GBK and so on. alse can convert Windows format to Unix.
<img src ="http://www.blogjava.net/hengheng123456789/aggbug/142352.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.blogjava.net/hengheng123456789/" target="_blank">哼哼</a> 2007-09-03 16:00 <a href="http://www.blogjava.net/hengheng123456789/archive/2007/09/03/142352.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>Subversion(SVN)安装使用指南</title><link>http://www.blogjava.net/hengheng123456789/archive/2007/09/03/142351.html</link><dc:creator>哼哼</dc:creator><author>哼哼</author><pubDate>Mon, 03 Sep 2007 07:56:00 GMT</pubDate><guid>http://www.blogjava.net/hengheng123456789/archive/2007/09/03/142351.html</guid><wfw:comment>http://www.blogjava.net/hengheng123456789/comments/142351.html</wfw:comment><comments>http://www.blogjava.net/hengheng123456789/archive/2007/09/03/142351.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.blogjava.net/hengheng123456789/comments/commentRss/142351.html</wfw:commentRss><trackback:ping>http://www.blogjava.net/hengheng123456789/services/trackbacks/142351.html</trackback:ping><description><![CDATA[<p align="center">&nbsp; <br />
Subversion(SVN)安装使用指南</p>
<p>From：http://blog.csdn.net/mervyn/articles/928589.aspx</p>
<p>※简述※</p>
<p>Subversion是近期在开源社区中非常流行的一款版本控制软件，它是CVS的替代产物。</p>
<p>它的主要特征有：</p>
<p>CVS大部分的功能。 <br />
支持&#8220;目录&#8221;级别的版本管理，并且解决了CVS中迟迟未能解决的文件重命名和移动等问题。甚至对文件或文件夹的属性都提供了版本管理。 <br />
&#8220;提交（commit）&#8221;实现了真正意义上的原子操作。也就是类似数据库中的事务的功能。 <br />
版本号依据每次提交而改变，不再针对每个文件。日志信息也是针对每次提交而设置。所以看到版本号是几百或者几千也不用太惊讶，表示方式不一样罢了。 <br />
通过WebDAV/DeltaV协议，可以与Apache的网络服务无缝衔接（通过Apache来运行）。这样就能提供一些额外的功能，例如：认证，压缩传输，以及数据仓库（Repository，见下）的浏览等。 <br />
也可以作为独立服务器运行，但这样的话提供的功能较为简单薄弱。 <br />
两种运行模式都支持SSH（当然需要各自的支持和配置） <br />
降低了分支（Branch）和标签（tag）上的时间消耗。底层设计理念和实现上的不同，不细说了。 <br />
时间消耗依据的是文件改变部分的大小，而不是数据总量。 <br />
创建数据仓库时，用户可以指定是使用内嵌的 BerkeleyDB 数据库，还是特定格式的文件系统。 <br />
其他还有些零星的小功能，具体可以参阅： http://subversion.tigris.org/roadmap.html</p>
<p>这里解释一下数据仓库的概念：<br />
一个数据仓库对应的可以是一个项目，也可以是多个项目。SVN是基于数据仓库进行管理的。<br />
按照用户习惯，可以只在每个数据仓库内仅放置一个项目的内容。</p>
<p>※下载※</p>
<p>Subversion 1.2.3:<br />
http://subversion.tigris.org/project_packages.html<br />
（SVN的Server端，分不同操作系统的版本，这里我下载的是for windows及for linux的）</p>
<p>TortoiseSVN:<br />
http://tortoisesvn.tigris.org/download.html<br />
（windows下的SVN客户端，以shell方式集成在系统右键菜单中）</p>
<p>Apache 2.0.55:<br />
http://httpd.apache.org/download.cgi<br />
（视操作系统而下）</p>
<p>※安装使用※</p>
<p>下面说一下安装，分两种平台（windows，linux）及两种模式（与Apache绑定 vs. Stand-alone）<br />
具体在Apache上的配置倒是大同小异。</p>
<p>另外，SVN是支持SSL的，但是这个配置牵涉到其他太多东西，本文就不过多涉及了。真的有需要可以参考SVN的手册（英文）。</p>
<p>方便起见，用几个变量代表具体的值，请自行加以调整：</p>
<p>%SystemRoot% — windows的系统所在目录，一般类似这样：C:"WINNT<br />
%SVN_HOME% — SVN的安装目录<br />
%SVN_REPO_PARENT% — SVN所有数据仓库的根目录（就是存放全部版本文件的总目录）<br />
%PROJECT_NAME% — 项目名，严格的来说它对应的是一个数据仓库，但是这里遵从用户习惯，以项目名称方式来命名。<br />
%SERVER_NAME_OR_IP% — 服务器名或IP地址<br />
%APACHE_HOME% — Apache2的安装路径</p>
<p>另外，安装过程默认使用文件系统做后台数据库，文中不再加以说明。如需使用BerkeleyDB，请自行参考SVN文档。</p>
<p>Windows上的服务器端安装<br />
____________________________________________</p>
<p>1.双击下载得来的&#8221;svn-1.2.3-setup.exe&#8221;并安装到&#8221;%SVN_HOME%&#8221;</p>
<p>2.安装完毕后，&#8221;%SVN_HOME%"bin&#8221;应该已经自动加入到系统路径（%PATH%）中。如果没有，请手工添加。</p>
<p>3.用命令行来测试安装结果是否正确：</p>
<p>1.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; cmd</p>
<p>2.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; svnadmin</p>
<p>如果返回这样的错误信息：&#8221;svnadmin.exe - Unable To Locate DLL&#8221;，那就需要尝试一下步骤的中的一种或几种：<br />
安装VC++ 6.0（主要是安装VC的运行库）<br />
或者直接从别的机器上拷贝一个&#8221;msvcp60.dll&#8221;文件到本机的&#8221;%SystemRoot%"system32&#8243;下</p>
<p>4.使用以下命令创建一个数据仓库，用来存放项目的源代码和其他文件：</p>
<p>1.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; cmd</p>
<p>2.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; svnadmin create%SVN_REPO_PARENT%"%PROJECT_NAME%</p>
<p>5.其中%SVN_REPO_PARENT%是包含所有数据仓库的目录，%PROJECT_NAME%是所创建的数据仓库对应的项目名。</p>
<p><br />
*************************<br />
* 以 Stand-alone 模式运行 *<br />
*************************</p>
<p>6.从命令行启动SVN Server：</p>
<p>1.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; cmd</p>
<p>2.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; svnserve -d -r %SVN_REPO_PARENT%</p>
<p>注意里面的参数 r 限定了浏览全部数据仓库的根目录</p>
<p>当然如果觉得每次这样启动太麻烦的话，也有SVN Serveice的包装程序（http://dark.clansoft.dk/~mbn/svnservice/）。通过它能够以windows service的方式运行SVN Server（其本质还是Stand-alone），运行起来相对比较方便。</p>
<p>7.创建用户数据库（其实就是一个txt文本，就叫它&#8221;users.conf&#8221;吧，你也可以改名），保存到<br />
%SVN_REPO_PARENT%"%PROJECT_NAME%"conf<br />
目录（那个conf子文件夹在创建数据仓库时已被自动创建好），然后在这个文件内添加需要的用户名和密码。基本的样例如下：</p>
<p>1.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; [users]</p>
<p>2.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; your_username = your_password</p>
<p>注意这里密码是明文存放的，所以也是这种方式的不足之处。</p>
<p>8.在&#8221;%SVN_REPO_PARENT%"%PROJECT_NAME%"conf&#8221;目录下找到这个&#8221;svnserve.conf&#8221;文件，用任何文本编辑器打开，为刚才创建的那些用户添加读写权限：</p>
<p>1.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; [general]</p>
<p>2.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; anon-access = none&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; # 匿名访问权限</p>
<p>3.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; auth-access = write&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; # 认证用户的权限</p>
<p>4.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; password-db = users.conf&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; # 认证用户数据库</p>
<p>5.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; realm = Anything youwant, butgenerallyweuse "%PROJECT_NAME%"&nbsp;&nbsp; # 在用户认证界面上出现的提示语句</p>
<p>里面的&#8221;users.conf&#8221;就是刚才在第7步创建的用户文件。</p>
<p>9.最后，重启SVN Server（什么？你不知道怎么重启？关掉窗口再重新用命令行启动啦；包装成Service的话么就更加简单了）</p>
<p>现在已经可以使用客户端来连接SVN Server，进行import等操作了。<br />
连接Server的URL应该是类似这样的：</p>
<p>1.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; svn://%SERVER_NAME_OR_IP%/%PROJECT_NAME%</p>
<p>具体步骤，请参阅第20步。</p>
<p><br />
************************<br />
* 以Apache的模块方式运行 *<br />
************************</p>
<p>10.首先要了解的是SVN设计的时候只考虑了兼容Apache2.x，所以在Apache1.x下是不能正常工作的。</p>
<p>11.安装Apache2<br />
如果事先启动了IIS之类的其他webserver，请先停止那些服务（端口被占用会导致Apache安装失败）。<br />
其他问题可以参考Apache的安装手册。<br />
这里假设安装目录为：%APACHE_HOME%</p>
<p>12.检查Apache2的安装是否成功<br />
打开浏览器，访问： http://localhost/<br />
如果出现的是默认的欢迎页面，那就没有问题了。否则请仔细检查，重新安装。</p>
<p>13.打开Apache的配置文件： &#8220;%APACHE_HOME%"conf"httpd.conf&#8221;<br />
查找&#8221;LoadModule&#8221;这个关键字，找到导入模块的区块（section）<br />
反注释掉下面这样，从而加载Subversion所需要的DAV模块：</p>
<p>1.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; # LoadModule dav_module modules/mod_dav.so</p>
<p>完成之后看起来应该是这样：</p>
<p>1.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; LoadModuledav_modulemodules/mod_dav.so</p>
<p>另外在这行下面再添加两行（请注意把路径中的&#8221;"&#8221;替换成&#8221;/&#8221;）：</p>
<p>1.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; LoadModuledav_svn_module%SVN_HOME%/bin/mod_dav_svn.so</p>
<p>2.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; LoadModule authz_svn_module%SVN_HOME%/bin/mod_authz_svn.so</p>
<p>特别需要注意的是：由于模块依赖关系，这三行的出现顺序千万不能颠倒。</p>
<p>14.再来配置一下&#8221;httpd.conf&#8221;的其他部分，告诉Apache2 SVN的数据仓库所在。<br />
（为避免不必要的麻烦，所有路径中的&#8221;"&#8221;都请替换成&#8221;/&#8221;）<br />
注意：</p>
<p>按照下述配置，所有数据仓库将共享密码文件及权限文件 <br />
如果需要为每个数据仓库创建独立的设置，请查阅SVN的文档（&#8221;Authorization Option&#8221;章节） <br />
添加下述内容：</p>
<p>1.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; &lt;Location /svn&gt;</p>
<p>2.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </p>
<p>3.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; DAV svn</p>
<p>4.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; SVNParentPath %SVN_REPO_PARENT%</p>
<p>5.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </p>
<p>6.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; #设置通过浏览器访问Repository时的XML格式文件，可以省略</p>
<p>7.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; SVNIndexXSLT "/svnindex.xsl"</p>
<p>8.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </p>
<p>9.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; # 存取权限控制文件所在地</p>
<p>10.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; AuthzSVNAccessFile %SVN_REPO_PARENT%/AccessFile</p>
<p>11.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </p>
<p>12.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; # 先尝试匿名操作，如有必要再转向用户认证</p>
<p>13.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; Satisfy Any</p>
<p>14.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; Require valid-user</p>
<p>15.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </p>
<p>16.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; # 如何验证用户</p>
<p>17.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; AuthType Basic</p>
<p>18.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; AuthName "Anything youwant, butgenerallyweuse %PROJECT_NAME%"</p>
<p>19.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; AuthUserFile %SVN_REPO_PARENT%/passwd</p>
<p>20.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </p>
<p>21.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; #输出时调用Apache的Deflate模块，必须有启用此模块才能这样配，否则删除此行</p>
<p>22.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; SetOutputFilter DEFLATE</p>
<p>23.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </p>
<p>24.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; &lt;/Location&gt;</p>
<p>这里涉及到两个文件: &#8220;%SVN_REPO_PARENT%/AccessFile&#8221; 及 &#8220;%SVN_REPO_PARENT%/passwd&#8221;.<br />
并不一定非要放到&#8221;%SVN_REPO_PARENT%&#8221;目录下，我图方便而已。觉得不安全可以移到另外地方。<br />
这两个文件里面具体内容的设置请参考第16和17步。</p>
<p>15.保存&#8221;httpd.conf&#8221;并退出，这里Apache2的配置告一段落。</p>
<p>16.&#8221;%SVN_REPO_PARENT%/AccessFile&#8221;文件的内容</p>
<p>1.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; [/]</p>
<p>2.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; * = r</p>
<p>3.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; user1 = rw</p>
<p>4.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; user2 = r</p>
<p>5.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; admin = rw</p>
<p>6.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </p>
<p>7.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; [%PROJECT_NAME%:/src/test]</p>
<p>8.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; user2 = rw</p>
<p>其中：</p>
<p>[/] 指代所有数据仓库的根目录，匿名用户默认的权限为只读。 <br />
对于&#8221;user1&#8243;和&#8221;admin&#8221;，他们对所有数据仓库都有读写权限。 <br />
对于&#8221;user2&#8243;，它对所有数据仓库仅有只读权限。但是下方又额外指定了他对&#8221;%PROJECT_NAME%:/src/test&#8221;目录具有读写权限。 <br />
综上，他对&#8217;test&#8217;目录及其子目录（自动继承，除非特别指定）具有读写权限，其他则均为只读权限。 <br />
你可以根据需要来设定不同的权限，更详细的说明还需要参考SVN文档中的权限设置章节。</p>
<p>17.&#8221;%SVN_REPO_PARENT%/passwd&#8221;文件的内容<br />
这个文件是通过&#8221;%APACHE_HOME%"bin"htpasswd.exe&#8221;自动生成的：</p>
<p>1.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; cmd</p>
<p>2.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; cd /D %APACHE_HOME%"bin</p>
<p>3.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; # 参数c仅在第一次运行时使用，用来创建一个新文件</p>
<p>4.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; htpasswd &#8211;cm %SVN_REPO_PARENT%"passwd user1</p>
<p>5.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; # 以后添加用户可用此命令，参数m表明需要加密</p>
<p>6.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; htpasswd &#8211;m %SVN_REPO_PARENT%"passwd user2</p>
<p>此时用文本编辑器打开&#8221;%SVN_REPO_PARENT%/passwd&#8221;，可以看到里面内容是类似这样的：</p>
<p>1.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; admin:$apr1$HLWV7/..$upZwVGvge0sc28fEp7mGM0</p>
<p>2.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; user1:$apr1$8sbRo...$hNMdkTvO4t8POVmOkV3Vg.</p>
<p>3.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; user2:$apr1$ZXzcE/..$5Ir0V8VQQtNYTNnnOp.EU1</p>
<p>18.把SVN自带的XSLT文件拷贝到网站根目录，<br />
然后设置合理权限（windows平台则不必考虑）</p>
<p>1.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; #这里假设你的网站根目录是&nbsp; /var/www/html</p>
<p>2.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; mv /tmp/subversion-1.2.3/tools/xslt/svnindex* /var/www/html</p>
<p>3.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; chown apache:apache /var/www/html/svnindex*</p>
<p>4.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; chmod 644 /var/www/html/svnindex*</p>
<p>5.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </p>
<p>6.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; #设置所有者和权限(将权限赋给apache运行的用户身份)</p>
<p>7.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; chown -R apache:apache%SVN_REPO_PARENT%</p>
<p>8.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; chmod -R 766%SVN_REPO_PARENT%</p>
<p>19. 重启Apache2服务：</p>
<p>1.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; cmd</p>
<p>2.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; net stopApache2</p>
<p>3.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; net startApache2</p>
<p>20.打开浏览器，访问：http://%SERVER_NAME_OR_IP%/svn/<br />
如果返回的页面是&#8221;403 Forbidden&#8221;，可能是由于Apache2默认没有打开目录的浏览权限（Option Indexes，参阅Apache2文档），但这并不影响使用。<br />
现在已经可以用客户端导入项目并开始使用了。<br />
具体步骤，请参阅第20步。</p>
<p><br />
***********************************************<br />
* 注意：以下步骤/命令需要在装有SVN客户端的机器上执行 *<br />
* Windows下安装服务器端的时候已经同时安装了客户端 *<br />
* Linux下尚待查证。 *<br />
***********************************************</p>
<p>21.和CVS一样，SVN在最初的时候需要将已有项目导入到数据库中。<br />
从命令行执行以下命令（Stand-alone）：</p>
<p>1.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; svnimportc:"temp"myprojectsvn://%SERVER_NAME_OR_IP%/%PROJECT_NAME% -m"initial import" --usernameyour_username --passwordyour_password</p>
<p>或者（Apache2 module）：</p>
<p>1.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; svnimportc:"temp"myprojecthttp://%SERVER_NAME_OR_IP%/svn/%PROJECT_NAME% -m"initial import" --usernameyour_username --passwordyour_password</p>
<p>其中：<br />
A) c:"temp"myproject里面包含了你所要导入的项目文件的内容<br />
B) %SERVER_NAME_OR_IP%是SVN Server的名字或者IP地址，上面存有第5步中创建的数据仓库<br />
C) %PROJECT_NAME%是要导入到的数据仓库名称，这里选择跟项目名一致<br />
D) 参数 m 表明此次导入操作的注释，SVN的注释是按每次提交来定义的，导入也是提交的一种。<br />
E) your_username和your_password是第7和17步创建的用户及密码，注意该用户必须对上面的%PROJECT_NAME%数据仓库有写权限才能成功。</p>
<p>22.然后，需要从Server端再次checkout到本地：<br />
（这点感觉不是太方便，为啥不做成import的时候有个选项，本地目录可以自动生成版本信息呢？）</p>
<p>1.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; cmd</p>
<p>2.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; cd /D anywhere_you_want_to_put_your_versioned_project_files</p>
<p>3.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; svn co svn://myserver/myproject/trunk . --username your_username --passwordyour_password</p>
<p>注意：<br />
&#8220;co&#8221;是&#8221;checkout&#8221;的一个别名<br />
那个点[.]代表当前目录，checkout出来的文件会自动放到这个目录下。也可以改为某个绝对路径。</p>
<p>23.对于向SVN Serer增加，移动，删除，或者修改后提交某些文件，参考使用以下命令：</p>
<p>1.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; Add:&nbsp;&nbsp;&nbsp; svnaddsrc/myfile.java -m"adding a file"</p>
<p>2.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; Move:&nbsp;&nbsp;&nbsp; svn movesrc/myfile.javasrc/mynewfile.java -m"moved myfile.java to mynewfile.java"</p>
<p>3.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; Delete:&nbsp;&nbsp;&nbsp; svn deletesrc/myfile.java -m"removing a file"</p>
<p>4.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; Commit:&nbsp;&nbsp;&nbsp; svn commitsrc/myfile.java -m"the message"</p>
<p>对于上面的客户端操作，如果安装了TortoiseSVN，一切就变得简单多了。<br />
不过这个就要抓图来说明了。等有空的时候再放上来。</p>
<p>※总结※</p>
<p>使用Eclipse的朋友还可以参考这里： http://subclipse.tigris.org/<br />
它以插件的形式向Eclipse提供了SVN的支持。</p>
<p>另外，具体的设置，参数说明等还是需要自己去查阅SVN的文档（在安装server端的时候已经附带）</p>
<p>参考文献及资料：<br />
_________________________________________</p>
<p>http://subversion.tigris.org/<br />
http://www-128.ibm.com/developerworks/cn/opensource/os-subversion/<br />
http://www.javayou.com/showlog.jspe?log_id=972<br />
</p>
<img src ="http://www.blogjava.net/hengheng123456789/aggbug/142351.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.blogjava.net/hengheng123456789/" target="_blank">哼哼</a> 2007-09-03 15:56 <a href="http://www.blogjava.net/hengheng123456789/archive/2007/09/03/142351.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>Java Crash</title><link>http://www.blogjava.net/hengheng123456789/archive/2007/09/03/142348.html</link><dc:creator>哼哼</dc:creator><author>哼哼</author><pubDate>Mon, 03 Sep 2007 07:52:00 GMT</pubDate><guid>http://www.blogjava.net/hengheng123456789/archive/2007/09/03/142348.html</guid><wfw:comment>http://www.blogjava.net/hengheng123456789/comments/142348.html</wfw:comment><comments>http://www.blogjava.net/hengheng123456789/archive/2007/09/03/142348.html#Feedback</comments><slash:comments>2</slash:comments><wfw:commentRss>http://www.blogjava.net/hengheng123456789/comments/commentRss/142348.html</wfw:commentRss><trackback:ping>http://www.blogjava.net/hengheng123456789/services/trackbacks/142348.html</trackback:ping><description><![CDATA[&nbsp;
<p style="text-align: center" align="center">Java Crash</p>
<p style="background: white; text-align: left" align="left"><span style="font-size: 12pt; font-family: 宋体">如果是</span><span style="font-size: 12pt; font-family: Arial">Java</span><span style="font-size: 12pt; font-family: 宋体">进程不知道什么原因退出或被杀死，想要分析具体原因，一般来说分下面几步：</span></p>
<p style="margin-top: 7.5pt; background: white; text-align: left" align="left"><span style="font-size: 12pt; font-family: Arial">1 </span><span style="font-size: 12pt; font-family: 宋体">拿到</span><span style="font-size: 12pt; font-family: Arial">Java</span><span style="font-size: 12pt; font-family: 宋体">应用程序的日志文件。</span><span style="font-size: 12pt; font-family: Arial"><br />
</span><span style="font-size: 12pt; font-family: 宋体">一般来说日志文件中会有很应用相关的错误信息。</span><span style="font-size: 12pt; font-family: Arial">Java</span><span style="font-size: 12pt; font-family: 宋体">进程异常退出的原因最有可能就是应用程序本身的问题。因此检查</span><span style="font-size: 12pt; font-family: Arial">Java</span><span style="font-size: 12pt; font-family: 宋体">应用程序的日志文件可能是最快定位到错误的方法。</span></p>
<p style="margin-top: 7.5pt; background: white; text-align: left" align="left"><span style="font-size: 12pt; font-family: Arial">2 </span><span style="font-size: 12pt; font-family: 宋体">查找</span><span style="font-size: 12pt; font-family: Arial">JVM</span><span style="font-size: 12pt; font-family: 宋体">的致命错误日志</span><span style="font-size: 12pt; font-family: Arial"><br />
</span><span style="font-size: 12pt; font-family: 宋体">如果应用程序日志文件中没有发现什么线索。那么还可以查看</span><span style="font-size: 12pt; font-family: Arial"> JVM</span><span style="font-size: 12pt; font-family: 宋体">的致命错误日志。有些致命的错误，比如</span><span style="font-size: 12pt; font-family: Arial">JNI</span><span style="font-size: 12pt; font-family: 宋体">或虚拟机本身产生的错误，可能使得</span><span style="font-size: 12pt; font-family: Arial">Java</span><span style="font-size: 12pt; font-family: 宋体">应用程序来不及写日志就退出了。这时候可以查一个以</span><span style="font-size: 12pt; font-family: Arial"> "hs_err_pid" </span><span style="font-size: 12pt; font-family: 宋体">开头的日志名，例如</span><span style="font-size: 12pt; font-family: Arial">hs_err_pid1125.log</span><span style="font-size: 12pt; font-family: 宋体">，其中</span><span style="font-size: 12pt; font-family: Arial">1125</span><span style="font-size: 12pt; font-family: 宋体">是进程号。这个文件中也记录了一些宝贵的信息来提供一些线索，特别是</span><span style="font-size: 12pt; font-family: Arial">Java</span><span style="font-size: 12pt; font-family: 宋体">自身的一些</span><span style="font-size: 12pt; font-family: Arial">Bug</span><span style="font-size: 12pt; font-family: 宋体">。这个文件一般为于当前的工作目录中。用户可以用</span><span style="font-size: 12pt; font-family: Arial">find</span><span style="font-size: 12pt; font-family: 宋体">命令自己搜索到。</span></p>
<p style="margin-top: 7.5pt; background: white; text-align: left" align="left"><span style="font-size: 12pt; font-family: Arial">3 </span><span style="font-size: 12pt; font-family: 宋体">查找操作系统的</span><span style="font-size: 12pt; font-family: Arial">core dump</span><span style="font-size: 12pt; font-family: 宋体">文件</span><span style="font-size: 12pt; font-family: Arial"><br />
</span><span style="font-size: 12pt; font-family: 宋体">作为被操作系统所调度的进程，</span><span style="font-size: 12pt; font-family: Arial">Java</span><span style="font-size: 12pt; font-family: 宋体">进程也会在不同的信号下产生</span><span style="font-size: 12pt; font-family: Arial">Core Dump</span><span style="font-size: 12pt; font-family: 宋体">文件，例如</span><span style="font-size: 12pt; font-family: Arial">Sig_ill</span><span style="font-size: 12pt; font-family: 宋体">和</span><span style="font-size: 12pt; font-family: Arial">Seg_segv</span><span style="font-size: 12pt; font-family: 宋体">。这些非常严重的错误的确会使得</span><span style="font-size: 12pt; font-family: Arial">Java</span><span style="font-size: 12pt; font-family: 宋体">虚拟机根本来不及产生任何日志就宕了。拿到</span><span style="font-size: 12pt; font-family: Arial">core dump</span><span style="font-size: 12pt; font-family: 宋体">文件就可以使用很多工具来分析具体原因了，例如</span><span style="font-size: 12pt; font-family: Arial">jmap, jstack</span><span style="font-size: 12pt; font-family: 宋体">等等都可以友好的进行</span><span style="font-size: 12pt; font-family: Arial">Java</span><span style="font-size: 12pt; font-family: 宋体">进程的</span><span style="font-size: 12pt; font-family: Arial">Core</span><span style="font-size: 12pt; font-family: 宋体">文件的分析。一般来说，</span><span style="font-size: 12pt; font-family: Arial">Core</span><span style="font-size: 12pt; font-family: 宋体">文件也放到进程的当前工作目录，用户可以用</span><span style="font-size: 12pt; font-family: Arial">find</span><span style="font-size: 12pt; font-family: 宋体">命令搜索</span><span style="font-size: 12pt; font-family: Arial"> &#8220;core&#8221;</span><span style="font-size: 12pt; font-family: 宋体">。另外可以用</span><span style="font-size: 12pt; font-family: Arial">coreadm</span><span style="font-size: 12pt; font-family: 宋体">来预先指定</span><span style="font-size: 12pt; font-family: Arial">core</span><span style="font-size: 12pt; font-family: 宋体">文件存放的地方以及文件名的格式，例如：</span><span style="font-size: 12pt; font-family: Arial">coreadm -g /var/core/core.%f.%p.%t</span></p>
<p style="margin-top: 7.5pt; background: white; text-align: left" align="left"><span style="font-size: 12pt; font-family: Arial">4</span><span style="font-size: 12pt; font-family: 宋体">使用</span><span style="font-size: 12pt; font-family: Arial">Dtrace</span><span style="font-size: 12pt; font-family: 宋体">查找</span><span style="font-size: 12pt; font-family: Arial">&#8220;</span><span style="font-size: 12pt; font-family: 宋体">是谁杀死了</span><span style="font-size: 12pt; font-family: Arial">Java</span><span style="font-size: 12pt; font-family: 宋体">进程</span><span style="font-size: 12pt; font-family: Arial">&#8221;<br />
</span><span style="font-size: 12pt; font-family: 宋体">但是，有很多情况，进程被杀死的原因很复杂。有可能被别的进程以外杀掉，或被一些脚本不小心</span><span style="font-size: 12pt; font-family: Arial">kill</span><span style="font-size: 12pt; font-family: 宋体">掉，或者被管理员（或入侵者</span><span style="font-size: 12pt; font-family: Arial">kill -9</span><span style="font-size: 12pt; font-family: 宋体">）处理掉。这些情况都不会产生日志文件和</span><span style="font-size: 12pt; font-family: Arial">core dump</span><span style="font-size: 12pt; font-family: 宋体">文件。这些情况很难跟踪。但如果是</span><span style="font-size: 12pt; font-family: Arial">Solaris10</span><span style="font-size: 12pt; font-family: 宋体">下，可以使用下面的</span><span style="font-size: 12pt; font-family: Arial">Dtrace</span><span style="font-size: 12pt; font-family: 宋体">脚本来确定</span><span style="font-size: 12pt; font-family: Arial">&#8220;</span><span style="font-size: 12pt; font-family: 宋体">是谁杀死了</span><span style="font-size: 12pt; font-family: Arial">Java</span><span style="font-size: 12pt; font-family: 宋体">进程</span><span style="font-size: 12pt; font-family: Arial">&#8221;</span></p>
<p style="margin-top: 7.5pt; background: white; text-align: left" align="left"><span style="font-size: 12pt; font-family: Arial"><br />
#!/usr/sbin/dtrace -qs</span></p>
<p style="margin-top: 7.5pt; background: white; text-align: left" align="left"><span style="font-size: 12pt; font-family: Arial">proc:::signal-send<br />
/args[1]-&gt;pr_pid == $1/<br />
{<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; printf("%s(pid:%d) is sending signal %d to %s"n", execname, pid, args[2],args[1]-&gt;pr_fname);<br />
}</span></p>
<p><span style="font-size: 12pt; font-family: 宋体">如何运行（</span><span style="font-size: 12pt; font-family: Arial">1125</span><span style="font-size: 12pt; font-family: 宋体">）是进程号</span><span style="font-size: 12pt; font-family: Arial"><br />
$ ./sig1.d 1125<br />
sched(pid:0) is sending signal 24 to bc<br />
sched(pid:0) is sending signal 24 to bc<br />
bash(pid:3987) is sending signal 15 to bc<br />
bash(pid:3987) is sending signal 15 to bc<br />
bash(pid:3987) is sendg signal 9 to bc</span></p>
<p style="text-align: left" align="left"><span style="font-size: 12pt; font-family: 宋体">Java</span><span style="font-size: 12pt; font-family: 宋体">的应用有时候会因为各种原因Crash，这时候会产生一个类似java_errorpid.log的错误日志。可以拿到了这个日志，怎样分析Crash的原因呢？下面我们来详细讨论如何分析java_error<em>pid</em>.log的错误日志。<br />
一</span><span style="font-size: 12pt; font-family: sans-serif">. </span><span style="font-size: 12pt; font-family: 宋体">如何得到这个日志文件如果有一个严重的错误引起</span><span style="font-size: 12pt; font-family: serif">Java</span><span style="font-size: 12pt; font-family: 宋体">进程非正常退出，我们叫</span><span style="font-size: 12pt; font-family: serif">Crash</span><span style="font-size: 12pt; font-family: 宋体">，这时候会产生一个日志文件。缺省情况下，这个文件会产生在工作目录下。但是，可以在</span><span style="font-size: 12pt; font-family: serif">Java</span><span style="font-size: 12pt; font-family: 宋体">启动参数通过下面的设置，来改变这个文件的位置和命名规则。例如：</span><span style="font-size: 12pt; font-family: serif"><br />
java -XX:ErrorFile=/var/log/java/java_error_%p.log<br />
</span><span style="font-size: 12pt; font-family: 宋体">就将这个错误文件放在</span><span style="font-size: 12pt; font-family: serif">/var/log/java</span><span style="font-size: 12pt; font-family: 宋体">下，并且以</span><span style="font-size: 12pt; font-family: serif">java_error_<em>pid</em>.log</span><span style="font-size: 12pt; font-family: 宋体">的形式出现。<br />
<br />
二</span><span style="font-size: 12pt; font-family: sans-serif">.</span><span style="font-size: 12pt; font-family: 宋体">产生错误的原因造成严重错误的原因有多种可能性。</span><span style="font-size: 12pt; font-family: serif">Java</span><span style="font-size: 12pt; font-family: 宋体">虚拟机自身的</span><span style="font-size: 12pt; font-family: serif">Bug</span><span style="font-size: 12pt; font-family: 宋体">是原因之一，但是这种可能不是很大。在绝大多数情况下，是由于系统的库文件、</span><span style="font-size: 12pt; font-family: serif">API</span><span style="font-size: 12pt; font-family: 宋体">或第三方的库文件造成的；系统资源的短缺也有可能造成这种严重的错误。在发生了</span><span style="font-size: 12pt; font-family: serif">Crash</span><span style="font-size: 12pt; font-family: 宋体">之后，如果无法定位根本原因，也应该迅速找到</span><span style="font-size: 12pt; font-family: serif">Work Around</span><span style="font-size: 12pt; font-family: 宋体">的方法。<br />
<br />
三</span><span style="font-size: 12pt; font-family: sans-serif">.</span><span style="font-size: 12pt; font-family: 宋体">对日志文件的分析首先要检查日志的文件头：例如，下面是从一个客户发过来的错误日志的文件头<br />
－－－－－－－－－－－－－－－－－－－－－－－－－－－－－－－－－－－－－<br />
</span><span style="font-size: 12pt; font-family: serif">#<br />
# An unexpected error has been detected by HotSpot Virtual Machine:<br />
#<br />
# EXCEPTION_ACCESS_VIOLATION (0xc0000005) at pc=0x0815e87e, pid=7268, tid=4360<br />
#<br />
# Java VM: Java HotSpot(TM) Server VM (1.4.2_13-b06 mixed mode)<br />
# Problematic frame:<br />
# V [jvm.dll+0x15e87e]<br />
#<br />
</span><span style="font-size: 12pt; font-family: 宋体">－－－－－－－－－－－－－－－－－－－－－－－－－－－－－－－－－－－－－－<br />
<br />
<br />
文件头中有很多有用的信息，&#8220;</span><span style="font-size: 12pt; font-family: serif">EXCEPTION_ACCESS_VIOLATION &#8221;</span><span style="font-size: 12pt; font-family: 宋体">意味着</span><span style="font-size: 12pt; font-family: serif">Java</span><span style="font-size: 12pt; font-family: 宋体">应用</span><span style="font-size: 12pt; font-family: serif">Crash</span><span style="font-size: 12pt; font-family: 宋体">的时候，正在运行</span><span style="font-size: 12pt; font-family: serif">JVM</span><span style="font-size: 12pt; font-family: 宋体">自己的代码，而不是外部的</span><span style="font-size: 12pt; font-family: serif">Java</span><span style="font-size: 12pt; font-family: 宋体">代码或其他类库代码。这种情况很可能是</span><span style="font-size: 12pt; font-family: serif">JVM</span><span style="font-size: 12pt; font-family: 宋体">的</span><span style="font-size: 12pt; font-family: serif">Bug</span><span style="font-size: 12pt; font-family: 宋体">，但是也不一定。除了&#8220;</span><span style="font-size: 12pt; font-family: serif">EXCEPTION_ACCESS_VIOLATION &#8221;</span><span style="font-size: 12pt; font-family: 宋体">，还有可能是别的信息，例如&#8220;</span><span style="font-size: 12pt; font-family: serif">SIGSEGV(0xb)&#8221;</span><span style="font-size: 12pt; font-family: 宋体">，意味着</span><span style="font-size: 12pt; font-family: serif">JVM</span><span style="font-size: 12pt; font-family: 宋体">正在执行本地或</span><span style="font-size: 12pt; font-family: serif">JNI</span><span style="font-size: 12pt; font-family: 宋体">的代码</span><span style="font-size: 12pt; font-family: serif">;[font=Thorndale, serif]&#8220;EXCEPTION_STACK_OVERFLOW&#8221;</span><span style="font-size: 12pt; font-family: 宋体">[/font]</span><span style="font-size: 12pt; font-family: 宋体">意味着这是个栈溢出的错误。<br />
<br />
<br />
另外一个有用的信息就是：<br />
</span><span style="font-size: 12pt; font-family: serif"># Problematic frame:<br />
# V [jvm.dll+0x15e87e]</span><span style="font-size: 12pt; font-family: 宋体"><br />
<br />
</span><span style="font-size: 12pt; font-family: 宋体">它说明</span><span style="font-size: 12pt; font-family: serif">Crash</span><span style="font-size: 12pt; font-family: 宋体">的时候，</span><span style="font-size: 12pt; font-family: serif">JVM</span><span style="font-size: 12pt; font-family: 宋体">正在从哪个库文件执行代码。除了&#8220;</span><span style="font-size: 12pt; font-family: serif">V&#8221;</span><span style="font-size: 12pt; font-family: 宋体">以外，还有可能是&#8220;</span><span style="font-size: 12pt; font-family: serif">C&#8221;</span><span style="font-size: 12pt; font-family: 宋体">、&#8220;</span><span style="font-size: 12pt; font-family: serif">j&#8221;</span><span style="font-size: 12pt; font-family: 宋体">、&#8220;</span><span style="font-size: 12pt; font-family: serif">v&#8221;</span><span style="font-size: 12pt; font-family: 宋体">、&#8220;</span><span style="font-size: 12pt; font-family: serif">J&#8221;</span><span style="font-size: 12pt; font-family: 宋体">。具体的表示意思如下：<br />
</span><span style="font-size: 12pt; font-family: serif">FrameType Description</span><span style="font-size: 12pt; font-family: 宋体">：</span><span style="font-size: 12pt; font-family: MyriadPro-SemiboldSemiCn"><br />
</span><span style="font-size: 12pt; font-family: serif">C: Native C frame<br />
j: Interpreted Java frame<br />
V: VMframe<br />
v: VMgenerated stub frame<br />
J: Other frame types, including compiled Java frames</span><span style="font-size: 12pt; font-family: 宋体"><br />
<br />
</span><span style="font-size: 12pt; font-family: 宋体">文件头之后，是当前线程的</span><span style="font-size: 12pt; font-family: serif">DUMP</span><span style="font-size: 12pt; font-family: 宋体">信息，线程之后是</span><span style="font-size: 12pt; font-family: serif">JVM</span><span style="font-size: 12pt; font-family: 宋体">进程的</span><span style="font-size: 12pt; font-family: serif">DUMP</span><span style="font-size: 12pt; font-family: 宋体">信息，包括所有线程的状态、地址和</span><span style="font-size: 12pt; font-family: serif">ID</span><span style="font-size: 12pt; font-family: 宋体">。最后还有</span><span style="font-size: 12pt; font-family: serif">JVM</span><span style="font-size: 12pt; font-family: 宋体">状态，</span><span style="font-size: 12pt; font-family: serif">Heap</span><span style="font-size: 12pt; font-family: 宋体">状态，动态连接库等等的信息。这些烦乱的信息中，包含有非常有用的信息。下面我们根据几个具体的实例来分析</span><span style="font-size: 12pt; font-family: serif">Java</span><span style="font-size: 12pt; font-family: 宋体">虚拟机</span><span style="font-size: 12pt; font-family: serif">Crash</span><span style="font-size: 12pt; font-family: 宋体">的典型例子。<br />
<br />
四</span><span style="font-size: 12pt; font-family: sans-serif">.</span><span style="font-size: 12pt; font-family: 宋体">内存回收引起的</span><span style="font-size: 12pt; font-family: sans-serif">Crash</span><span style="font-size: 12pt; font-family: 宋体">内存回收引起的</span><span style="font-size: 12pt; font-family: serif">Crash</span><span style="font-size: 12pt; font-family: 宋体">有以下的特点：在日志文件头一般有&#8220; </span><span style="font-size: 12pt; font-family: serif">EXCEPTION_ACCESS _VIOLATION&#8221;</span><span style="font-size: 12pt; font-family: 宋体">和&#8220;</span><span style="font-size: 12pt; font-family: serif"># Problematic frame: # V [jvm.dll+....&#8221;</span><span style="font-size: 12pt; font-family: 宋体">的信息，意味着这是在</span><span style="font-size: 12pt; font-family: serif">JVM</span><span style="font-size: 12pt; font-family: 宋体">内部处理，而且多半是</span><span style="font-size: 12pt; font-family: serif">JVM</span><span style="font-size: 12pt; font-family: 宋体">的</span><span style="font-size: 12pt; font-family: serif">Bug</span><span style="font-size: 12pt; font-family: 宋体">。对于这类问题，最快的方法就是绕过它。<br />
另外，在</span><span style="font-size: 12pt; font-family: serif">Thread</span><span style="font-size: 12pt; font-family: 宋体">的</span><span style="font-size: 12pt; font-family: serif">DUMP</span><span style="font-size: 12pt; font-family: 宋体">信息最后，还能看到有关内存回收的行为例如：<br />
</span><span style="font-size: 12pt; font-family: serif">--------------- T H R E A D ---------------<br />
Current thread (0x00a56668): VMThread [id=4360]<br />
siginfo: ExceptionCode=0xc0000005, reading address 0x00000057<br />
Registers:<br />
........<br />
<br />
Stack: [0x03cf0000,0x03d30000), sp=0x03d2fc18, free space=255k<br />
Native frames: (J=compiled Java code, j=interpreted, Vv=VM code, C=native code)<br />
V [jvm.dll+0x15e87e]<br />
<br />
VM_Operation (0x063efbac): <span style="color: red">full generation collection</span>, mode: safepoint, requested by thread 0x040f83f8<br />
------------------------------------------------------------<br />
</span><span style="font-size: 12pt; font-family: 宋体"><br />
</span><span style="font-size: 12pt; font-family: 宋体">可以清楚的看到</span><span style="font-size: 12pt; font-family: serif">JVM</span><span style="font-size: 12pt; font-family: 宋体">正在做 &#8220;</span><span style="font-size: 12pt; color: red; font-family: serif">full generation collection</span><span style="font-size: 12pt; font-family: serif">&#8221;</span><span style="font-size: 12pt; font-family: 宋体">。另外还有可能看到，其他的回收行为：</span></p>
<ul type="disc">
    <li style="text-align: left; tab-stops: list 36.0pt"><span style="font-size: 12pt; font-family: serif">generation collection for allocation</span></li>
    <li style="text-align: left; tab-stops: list 36.0pt"><span style="font-size: 12pt; font-family: serif">full generation collection</span></li>
    <li style="text-align: left; tab-stops: list 36.0pt"><span style="font-size: 12pt; font-family: serif">parallel gc failed allocation</span></li>
    <li style="text-align: left; tab-stops: list 36.0pt"><span style="font-size: 12pt; font-family: serif">parallel gc failed permanent allocation</span></li>
    <li style="text-align: left; tab-stops: list 36.0pt"><span style="font-size: 12pt; font-family: serif">parallel gc system gc</span></li>
</ul>
<p><span style="font-size: 12pt; font-family: 宋体"><br />
</span><span style="font-size: 12pt; font-family: 宋体">对于内存回收的错误，一般采取改变回收的算法和参数的方法来绕过去。例如，来自客户的日志除了上面的日志信息，在日志中</span><span style="font-size: 12pt; font-family: serif">Heap</span><span style="font-size: 12pt; font-family: 宋体">信息中还能发现一些其他信息：<br />
--------------------------------------------------------------<br />
</span><span style="font-size: 12pt; font-family: serif">Heap<br />
def new generation total 22592K, used 19530K [0x10010000, 0x11890000, 0x138f0000)<br />
eden space 20096K, 97% used [0x10010000, 0x11322bd8, 0x113b0000)<br />
from space 2496K, 0% used [0x113b0000, 0x113b0000, 0x11620000)<br />
to space 2496K, 0% used [0x11620000, 0x11620000, 0x11890000)<br />
tenured generation total 190696K, used 100019K [0x138f0000, 0x1f32a000, 0x30010000)<br />
the space 190696K, 52% used [0x138f0000, 0x19a9cf38, 0x19a9d000, 0x1f32a000)<br />
<span style="color: red">compacting perm gen total 38656K, used 38588K </span>[0x30010000, 0x325d0000, 0x34010000)<br />
<span style="color: #ff6666">the space 38656K, 99% used</span> [0x30010000, 0x325bf038, 0x325bf200, 0x325d0000)<br />
----------------------------------------------------------------<br />
</span><span style="font-size: 12pt; font-family: 宋体"><br />
</span><span style="font-size: 12pt; font-family: 宋体">上面的信息能看出在</span><span style="font-size: 12pt; font-family: serif">Crash</span><span style="font-size: 12pt; font-family: 宋体">的时候，</span><span style="font-size: 12pt; font-family: serif">JVM</span><span style="font-size: 12pt; font-family: 宋体">的</span><span style="font-size: 12pt; font-family: serif">PermSize</span><span style="font-size: 12pt; font-family: 宋体">空间几乎已经消耗完了，并且回收算法在压缩Perm空间的时候出了错。因此，建议改变内存回收的算法，或扩大</span><span style="font-size: 12pt; font-family: serif">PermSize</span><span style="font-size: 12pt; font-family: 宋体">和</span><span style="font-size: 12pt; font-family: serif">MaxPermSize</span><span style="font-size: 12pt; font-family: 宋体">的数值。<br />
<br />
五</span><span style="font-size: 12pt; font-family: sans-serif">.</span><span style="font-size: 12pt; font-family: 宋体">栈溢出引起的</span><span style="font-size: 12pt; font-family: sans-serif">Crash</span><span style="font-size: 12pt; font-family: serif">Java</span><span style="font-size: 12pt; font-family: 宋体">代码引起的栈溢出，通常不会引起</span><span style="font-size: 12pt; font-family: serif">JVM</span><span style="font-size: 12pt; font-family: 宋体">的</span><span style="font-size: 12pt; font-family: serif">Crash</span><span style="font-size: 12pt; font-family: 宋体">，而是抛</span><span style="font-size: 12pt; font-family: 宋体">出一个</span><span style="font-size: 12pt; font-family: serif">[font=Thorndale, serif]Java</span><span style="font-size: 12pt; font-family: 宋体">[/font]</span><span style="font-size: 12pt; font-family: 宋体">异常：</span><span style="font-size: 12pt; font-family: serif">[font=Thorndale, serif]java.lang.StackOverflowError</span><span style="font-size: 12pt; font-family: 宋体">[/font]</span><span style="font-size: 12pt; font-family: 宋体">。但是在</span><span style="font-size: 12pt; font-family: serif">[font=Thorndale, serif]Java</span><span style="font-size: 12pt; font-family: 宋体">[/font]</span><span style="font-size: 12pt; font-family: 宋体">虚拟机中，</span><span style="font-size: 12pt; font-family: serif">[font=Thorndale, serif]Java</span><span style="font-size: 12pt; font-family: 宋体">[/font]</span><span style="font-size: 12pt; font-family: 宋体">的代码和本地</span><span style="font-size: 12pt; font-family: serif">[font=Thorndale, serif]C</span><span style="font-size: 12pt; font-family: 宋体">[/font]</span><span style="font-size: 12pt; font-family: 宋体">或</span><span style="font-size: 12pt; font-family: serif">[font=Thorndale, serif]C++</span><span style="font-size: 12pt; font-family: 宋体">[/font]</span><span style="font-size: 12pt; font-family: 宋体">代码公用相同的</span><span style="font-size: 12pt; font-family: serif">[font=Thorndale, serif]Stack</span><span style="font-size: 12pt; font-family: 宋体">[/font]</span><span style="font-size: 12pt; font-family: 宋体">。这样，在执行本地代码所造成的栈溢出，就有可能引起</span><span style="font-size: 12pt; font-family: serif">[font=Thorndale, serif]JVM</span><span style="font-size: 12pt; font-family: 宋体">[/font]</span><span style="font-size: 12pt; font-family: 宋体">的</span><span style="font-size: 12pt; font-family: serif">[font=Thorndale, serif]Crash</span><span style="font-size: 12pt; font-family: 宋体">[/font]</span><span style="font-size: 12pt; font-family: 宋体">了。</span><span style="font-size: 12pt; font-family: 宋体"><br />
</span><span style="font-size: 12pt; font-family: 宋体">栈溢出引起的</span><span style="font-size: 12pt; font-family: serif">Crash</span><span style="font-size: 12pt; font-family: 宋体">会在日志的文件头中看到</span><span style="font-size: 12pt; font-family: serif">&#8220;EXCEPTION_STACK_OVERFLOW&#8221;</span><span style="font-size: 12pt; font-family: 宋体">字样。另外，在当前线程的</span><span style="font-size: 12pt; font-family: serif">Stack</span><span style="font-size: 12pt; font-family: 宋体">信息中也能发现一些信息。例如下面的例子：</span><span style="font-size: 12pt; font-family: 宋体"><br />
</span><span style="font-size: 12pt; font-family: serif">-----------------------------------------------------------------------------------<br />
<br />
</span><span style="font-size: 12pt; font-family: 宋体">在上面的信息中，可以发现这是个栈溢出的错误。并且当前栈剩余的空间已经很小了</span><span style="font-size: 12pt; font-family: serif">(free space =4k)</span><span style="font-size: 12pt; font-family: 宋体">。因此建议将</span><span style="font-size: 12pt; font-family: serif">JVM</span><span style="font-size: 12pt; font-family: 宋体">的</span><span style="font-size: 12pt; font-family: serif">Stack</span><span style="font-size: 12pt; font-family: 宋体">的尺寸调大，主要设计两个参数：</span><span style="font-size: 12pt; font-family: serif">&#8220;-Xss&#8221; </span><span style="font-size: 12pt; font-family: 宋体">和</span><span style="font-size: 12pt; font-family: serif">&#8220;[font=Thorndale, serif]-XX:StackShadowPages=<em>n&#8221;</em>[/font]</span><span style="font-size: 12pt; font-family: 宋体">。</span><span style="font-size: 12pt; font-family: 宋体">但是，将栈的尺寸调大，也意味着在有限的内存资源中，能打开的最大线程数会减少。</span><span style="font-size: 12pt; font-family: serif"><br />
<br />
</span><span style="font-size: 12pt; font-family: 宋体">六</span><span style="font-size: 12pt; font-family: sans-serif">.</span><span style="font-size: 12pt; font-family: 宋体">动态编译引起的</span><span style="font-size: 12pt; font-family: sans-serif">Crash</span><span style="font-size: 12pt; font-family: 宋体">未完，待续</span></p>
<img src ="http://www.blogjava.net/hengheng123456789/aggbug/142348.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.blogjava.net/hengheng123456789/" target="_blank">哼哼</a> 2007-09-03 15:52 <a href="http://www.blogjava.net/hengheng123456789/archive/2007/09/03/142348.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>Java Excel API Beginning</title><link>http://www.blogjava.net/hengheng123456789/archive/2007/09/03/142346.html</link><dc:creator>哼哼</dc:creator><author>哼哼</author><pubDate>Mon, 03 Sep 2007 07:51:00 GMT</pubDate><guid>http://www.blogjava.net/hengheng123456789/archive/2007/09/03/142346.html</guid><wfw:comment>http://www.blogjava.net/hengheng123456789/comments/142346.html</wfw:comment><comments>http://www.blogjava.net/hengheng123456789/archive/2007/09/03/142346.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.blogjava.net/hengheng123456789/comments/commentRss/142346.html</wfw:commentRss><trackback:ping>http://www.blogjava.net/hengheng123456789/services/trackbacks/142346.html</trackback:ping><description><![CDATA[&nbsp;&nbsp;&nbsp;&nbsp; 摘要: &nbsp;Java Excel API Beginninghttp://www.yesky.com/18/1886018.shtml　　使用Windows操作系统的朋友对Excel（电子表格）一定不会陌生，但是要使用Java语言来操纵Excel文件并不是一件容易的事。在Web应用日益盛行的今天，通过Web来操作Excel文件的需求越来越强烈，目前较为流行的操作是在JSP或Servle...&nbsp;&nbsp;<a href='http://www.blogjava.net/hengheng123456789/archive/2007/09/03/142346.html'>阅读全文</a><img src ="http://www.blogjava.net/hengheng123456789/aggbug/142346.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.blogjava.net/hengheng123456789/" target="_blank">哼哼</a> 2007-09-03 15:51 <a href="http://www.blogjava.net/hengheng123456789/archive/2007/09/03/142346.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>Docbook Beginning</title><link>http://www.blogjava.net/hengheng123456789/archive/2007/09/03/142345.html</link><dc:creator>哼哼</dc:creator><author>哼哼</author><pubDate>Mon, 03 Sep 2007 07:50:00 GMT</pubDate><guid>http://www.blogjava.net/hengheng123456789/archive/2007/09/03/142345.html</guid><wfw:comment>http://www.blogjava.net/hengheng123456789/comments/142345.html</wfw:comment><comments>http://www.blogjava.net/hengheng123456789/archive/2007/09/03/142345.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.blogjava.net/hengheng123456789/comments/commentRss/142345.html</wfw:commentRss><trackback:ping>http://www.blogjava.net/hengheng123456789/services/trackbacks/142345.html</trackback:ping><description><![CDATA[&nbsp;&nbsp;&nbsp;&nbsp; 摘要: &nbsp;Docbook Beginninghttp://blog.csdn.net/mickeyrat/archive/2005/02/04/281050.aspx编写技术文档，我想谁都遇到过。很多人都用MS Word，不可否认Word的功能确实非常强大，但是用Word有一些缺点无法避免：1) 写文档的时候，不得不兼顾文档的格式，这是件很头痛的事情，至少对我来说。经常是最后...&nbsp;&nbsp;<a href='http://www.blogjava.net/hengheng123456789/archive/2007/09/03/142345.html'>阅读全文</a><img src ="http://www.blogjava.net/hengheng123456789/aggbug/142345.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.blogjava.net/hengheng123456789/" target="_blank">哼哼</a> 2007-09-03 15:50 <a href="http://www.blogjava.net/hengheng123456789/archive/2007/09/03/142345.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>Java 编程技术中汉字问题的分析及解决</title><link>http://www.blogjava.net/hengheng123456789/archive/2007/09/03/142342.html</link><dc:creator>哼哼</dc:creator><author>哼哼</author><pubDate>Mon, 03 Sep 2007 07:49:00 GMT</pubDate><guid>http://www.blogjava.net/hengheng123456789/archive/2007/09/03/142342.html</guid><wfw:comment>http://www.blogjava.net/hengheng123456789/comments/142342.html</wfw:comment><comments>http://www.blogjava.net/hengheng123456789/archive/2007/09/03/142342.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.blogjava.net/hengheng123456789/comments/commentRss/142342.html</wfw:commentRss><trackback:ping>http://www.blogjava.net/hengheng123456789/services/trackbacks/142342.html</trackback:ping><description><![CDATA[&nbsp;
<p style="text-align: center" align="center">Java <span style="font-family: 宋体">编程技术中汉字问题的分析及解决</span></p>
<p><span style="font-family: 宋体">现在</span> Java <span style="font-family: 宋体">编程语言已经广泛应用于互联网世界，早在</span> Sun <span style="font-family: 宋体">公司开发</span> Java <span style="font-family: 宋体">语言的时候，就已经考虑到对非英文字符的支持了。</span>Sun <span style="font-family: 宋体">公司公布的</span> Java <span style="font-family: 宋体">运行环境（</span>JRE<span style="font-family: 宋体">）本身就分英文版和国际版，但只有国际版才支持非英文字符。不过在</span> Java <span style="font-family: 宋体">编程语言的应用中，对中文字符的支持并非如同</span> Java Soft <span style="font-family: 宋体">的标准规范中所宣称的那样完美，因为中文字符集不只一个，而且不同的操作系统对中文字符的支持也不尽相同，所以会有许多和汉字编码处理有关的问题在我们进行应用开发中困扰着我们。有很多关于这些问题的解答，但都比较琐碎，并不能够满足大家迫切解决问题的愿望，关于</span> Java <span style="font-family: 宋体">中文问题的系统研究并不多，本文从汉字编码常识出发，分析</span> Java <span style="font-family: 宋体">中文问题，希望对大家解决这个问题有所帮助。</span></p>
<p><strong><span style="font-family: 宋体">汉字编码的常识</span></strong></p>
<p><span style="font-family: 宋体">我们知道，英文字符一般是以一个字节来表示的，最常用的编码方法是</span> ASCII <span style="font-family: 宋体">。但一个字节最多只能区分</span>256<span style="font-family: 宋体">个字符，而汉字成千上万，所以现在都以双字节来表示汉字，为了能够与英文字符分开，每个字节的最高位一定为</span>1<span style="font-family: 宋体">，这样双字节最多可以表示</span>64K<span style="font-family: 宋体">格字符。我们经常碰到的编码方式有</span> GB2312<span style="font-family: 宋体">、</span>BIG5<span style="font-family: 宋体">、</span>UNICODE <span style="font-family: 宋体">等。关于具体编码方式的详细资料，有兴趣的读者可以查阅相关资料。我肤浅谈一下和我们关系密切的</span> GB2312 <span style="font-family: 宋体">和</span> UNICODE<span style="font-family: 宋体">。</span>GB2312 <span style="font-family: 宋体">码，中华人民共和国国家标准汉字信息交换用编码，是一个由中华人民共和国国家标准总局发布的关于简化汉字的编码，通行于中国大陆地区及新加坡，简称国标码。两个字节中，第一个字节（高字节）的值为区号值加</span>32<span style="font-family: 宋体">（</span>20H<span style="font-family: 宋体">），第二个字节（低字节）的值为位号值加</span>32<span style="font-family: 宋体">（</span>20H<span style="font-family: 宋体">），用这两个值来表示一个汉字的编码。</span>UNICODE <span style="font-family: 宋体">码是微软提出的解决多国字符问题的多字节等长编码，它对英文字符采取前面加&#8220;</span>0<span style="font-family: 宋体">&#8221;字节的策略实现等长兼容。如</span> <span style="font-family: 宋体">&#8220;</span>A<span style="font-family: 宋体">&#8221;</span> <span style="font-family: 宋体">的</span> ASCII <span style="font-family: 宋体">码为</span>0x41<span style="font-family: 宋体">，</span>UNICODE <span style="font-family: 宋体">就为</span>0x00<span style="font-family: 宋体">，</span>0x41<span style="font-family: 宋体">。利用特殊的工具各种编码之间可以互相转换。</span></p>
<p><strong>Java </strong><strong><span style="font-family: 宋体">中文问题的初步认识</span></strong></p>
<p><span style="font-family: 宋体">我们基于</span> Java <span style="font-family: 宋体">编程语言进行应用开发时，不可避免地要处理中文。</span>Java <span style="font-family: 宋体">编程语言默认的编码方式是</span> UNICODE<span style="font-family: 宋体">，而我们通常使用的数据库及文件都是基于</span> GB2312 <span style="font-family: 宋体">编码的，我们经常碰到这样的情况：浏览基于</span> JSP <span style="font-family: 宋体">技术的网站看到的是乱码，文件打开后看到的也是乱码，被</span> Java <span style="font-family: 宋体">修改过的数据库的内容在别的场合应用时无法继续正确地提供信息。</span></p>
<p>String sEnglish = &#8220;apple&#8221;;</p>
<p>String sChinese = <span style="font-family: 宋体">&#8220;苹果&#8221;</span>;</p>
<p>String s = <span style="font-family: 宋体">&#8220;苹果</span> apple <span style="font-family: 宋体">&#8221;</span>;</p>
<p>sEnglish <span style="font-family: 宋体">的长度是</span>5<span style="font-family: 宋体">，</span>sChinese<span style="font-family: 宋体">的长度是</span>4<span style="font-family: 宋体">，而</span> s <span style="font-family: 宋体">默认的长度是</span>14<span style="font-family: 宋体">。对于</span> sEnglish<span style="font-family: 宋体">来说，</span> Java <span style="font-family: 宋体">中的各个类都支持得非常好，肯定能够正确显示。但对于</span> sChinese <span style="font-family: 宋体">和</span> s <span style="font-family: 宋体">来说，虽然</span> Java Soft <span style="font-family: 宋体">声明</span> Java <span style="font-family: 宋体">的基本类已经考虑到对多国字符的支持（默认</span> UNICODE <span style="font-family: 宋体">编码），但是如果操作系统的默认编码不是</span> UNICODE <span style="font-family: 宋体">，而是国标码等。从</span> Java <span style="font-family: 宋体">源代码到得到正确的结果，要经过</span> <span style="font-family: 宋体">&#8220;</span>Java <span style="font-family: 宋体">源代码</span>-&gt; Java <span style="font-family: 宋体">字节码</span>-&gt; ;<span style="font-family: 宋体">虚拟机</span>-&gt;<span style="font-family: 宋体">操作系统</span>-&gt;<span style="font-family: 宋体">显示设备&#8221;的过程。在上述过程中的每一步骤，我们都必须正确地处理汉字的编码，才能够使最终的显示结果正确。</span></p>
<p><span style="font-family: 宋体">&#8220;</span> Java <span style="font-family: 宋体">源代码</span>-&gt; Java <span style="font-family: 宋体">字节码&#8221;，标准的</span> Java <span style="font-family: 宋体">编译器</span> javac <span style="font-family: 宋体">使用的字符集是系统默认的字符集，比如在中文</span> Windows <span style="font-family: 宋体">操作系统上就是</span> GBK ,<span style="font-family: 宋体">而在</span> Linux <span style="font-family: 宋体">操作系统上就是</span>ISO-8859-1<span style="font-family: 宋体">，所以大家会发现在</span> Linux <span style="font-family: 宋体">操作系统上编译的类中源文件中的中文字符都出了问题，解决的办法就是在编译的时候添加</span> encoding <span style="font-family: 宋体">参数，这样才能够与平台无关。用法是</span></p>
<p>javac ?Cencoding GBK<span style="font-family: 宋体">。</span></p>
<p><span style="font-family: 宋体">&#8220;</span> Java <span style="font-family: 宋体">字节码</span>-&gt;<span style="font-family: 宋体">虚拟机</span>-&gt;<span style="font-family: 宋体">操作系统&#8221;，</span> Java <span style="font-family: 宋体">运行环境</span> <span style="font-family: 宋体">（</span>JRE<span style="font-family: 宋体">）</span> <span style="font-family: 宋体">分英文版和国际版，但只有国际版才支持非英文字符。</span> Java <span style="font-family: 宋体">开发工具包</span> <span style="font-family: 宋体">（</span>JDK<span style="font-family: 宋体">）</span> <span style="font-family: 宋体">肯定支持多国字符，但并非所有的计算机用户都安装了</span> JDK <span style="font-family: 宋体">。很多操作系统及应用软件为了能够更好的支持</span> Java <span style="font-family: 宋体">，都内嵌了</span> JRE <span style="font-family: 宋体">的国际版本，为自己支持多国字符提供了方便。</span></p>
<p><span style="font-family: 宋体">&#8220;操作系统</span>-&gt;<span style="font-family: 宋体">显示设备&#8221;，对于汉字来说，操作系统必须支持并能够显示它。英文操作系统如果不搭配特殊的应用软件的话，是肯定不能够显示中文的。</span></p>
<p><span style="font-family: 宋体">还有一个问题，就是在</span> Java <span style="font-family: 宋体">编程过程中，对中文字符进行正确的编码转换。例如，向网页输出中文字符串的时候，不论你是用</span></p>
<p>out.println(string);<span style="font-family: 宋体">还是用</span></p>
<p>&lt;%=string%&gt;<span style="font-family: 宋体">，都必须作</span> UNICODE <span style="font-family: 宋体">到</span> GBK <span style="font-family: 宋体">的转换，或者手动，或者自动。在</span> JSP 1.0<span style="font-family: 宋体">中，可以定义输出字符集，从而实现内码的自动转换。用法是</span></p>
<p>&lt;%@page contentType=&#8221;text/html;charset=gb2312&#8221; %&gt;</p>
<p><span style="font-family: 宋体">但是在一些</span> JSP <span style="font-family: 宋体">版本中并没有提供对输出字符集的支持，（例如</span> JSP 0.92<span style="font-family: 宋体">），这就需要手动编码输出了，方法非常多。最常用的方法是</span></p>
<p>String s1 = request.getParameter(&#8220;keyword&#8221;);</p>
<p>String s2 = new String(s1.getBytes(&#8220;ISO-8859-1&#8221;),&#8221;GBK&#8221;);</p>
<p>getBytes <span style="font-family: 宋体">方法用于将中文字符以&#8220;</span>ISO-8859-1<span style="font-family: 宋体">&#8221;编码方式转化成字节数组，而&#8220;</span>GBK<span style="font-family: 宋体">&#8221;</span> <span style="font-family: 宋体">是目标编码方式。我们从以</span>ISO-8859-1<span style="font-family: 宋体">方式编码的数据库中读出中文字符串</span> s1 <span style="font-family: 宋体">，经过上述转换过程，在支持</span> GBK <span style="font-family: 宋体">字符集的操作系统和应用软件中就能够正确显示中文字符串</span> s2 <span style="font-family: 宋体">。</span></p>
<p><strong>Java </strong><strong><span style="font-family: 宋体">中文问题的表层分析及处理</span></strong></p>
<p><span style="font-family: 宋体">背景</span>&nbsp;</p>
<p><span style="font-family: 宋体">开发环境</span>&nbsp;JDK1.15&nbsp;Vcafe2.0&nbsp;JPadPro&nbsp;</p>
<p><span style="font-family: 宋体">服务器端</span>&nbsp;NT IIS&nbsp;Sybase System&nbsp;Jconnect<span style="font-family: 宋体">（</span>JDBC<span style="font-family: 宋体">）</span>&nbsp;</p>
<p><span style="font-family: 宋体">客户端</span>&nbsp;IE5.0&nbsp;Pwin98&nbsp;?span &gt;&nbsp;</p>
<p>.CLASS <span style="font-family: 宋体">文件存放在服务器端，由客户端的浏览器运行</span> APPLET <span style="font-family: 宋体">，</span> APPLET <span style="font-family: 宋体">只起调入</span> FRAME <span style="font-family: 宋体">类等主程序的作用。界面包括</span> Textfield <span style="font-family: 宋体">，</span>TextArea<span style="font-family: 宋体">，</span>List<span style="font-family: 宋体">，</span>Choice <span style="font-family: 宋体">等。</span></p>
<p>I.<span style="font-family: 宋体">用</span> JDBC <span style="font-family: 宋体">执行</span> SELECT <span style="font-family: 宋体">语句从服务器端读取数据（中文）后，将数据用</span> APPEND <span style="font-family: 宋体">方法加到</span> TextArea<span style="font-family: 宋体">（</span>TA<span style="font-family: 宋体">）</span> <span style="font-family: 宋体">，不能正确显示。但加到</span> List <span style="font-family: 宋体">中时，大部分汉字却可正确显示。</span></p>
<p><span style="font-family: 宋体">将数据按&#8220;</span>ISO-8859-1<span style="font-family: 宋体">&#8221;</span> <span style="font-family: 宋体">编码方式转化为字节数组，再按系统缺省编码方式</span> <span style="font-family: 宋体">（</span>Default Character Encoding<span style="font-family: 宋体">）</span> <span style="font-family: 宋体">转化为</span> STRING <span style="font-family: 宋体">，即可在</span> TA <span style="font-family: 宋体">和</span> List <span style="font-family: 宋体">中正确显示。</span></p>
<p><span style="font-family: 宋体">程序段如下：</span></p>
<p>dbstr2 = results.getString(1);</p>
<p>//After reading the result from DB server<span style="font-family: 宋体">，</span>converting it to string.</p>
<p>dbbyte1 = dbstr2.getBytes(&#8220;iso-8859-1&#8221;);</p>
<p>dbstr1 = new String(dbbyte1); </p>
<p><span style="font-family: 宋体">在转换字符串时不采用系统默认编码方式，而直接采用&#8220;</span> GBK<span style="font-family: 宋体">&#8221;</span> <span style="font-family: 宋体">或者</span> <span style="font-family: 宋体">&#8220;</span>GB2312<span style="font-family: 宋体">&#8221;</span> ,<span style="font-family: 宋体">在</span> A <span style="font-family: 宋体">和</span> B <span style="font-family: 宋体">两种情况下，从数据库取数据都没有问题。</span></p>
<p>II.<span style="font-family: 宋体">处理方式与&#8220;取中文&#8221;相逆，先将</span> SQL <span style="font-family: 宋体">语句按系统缺省编码方式转化为字节数组，再按&#8220;</span>ISO-8859-1<span style="font-family: 宋体">&#8221;编码方式转化为</span> STRING <span style="font-family: 宋体">，最后送去执行，则中文信息可正确写入数据库。</span></p>
<p><span style="font-family: 宋体">程序段如下：</span></p>
<p>sqlstmt = tf_input.getText();</p>
<p>//Before sending statement to DB server<span style="font-family: 宋体">，</span>converting it to sql statement.</p>
<p>dbbyte1 = sqlstmt.getBytes();</p>
<p>sqlstmt = newString(dbbyte1,&#8221;iso-8859-1&#8221;);</p>
<p>_stmt = _con.createStatement();</p>
<p>_stmt.executeUpdate(sqlstmt);</p>
<p><span style="font-family: 宋体">&#8230;&#8230;</span></p>
<p><span style="font-family: 宋体">问题：如果客户机上存在</span> CLASSPATH <span style="font-family: 宋体">指向</span> JDK <span style="font-family: 宋体">的</span> CLASSES.ZIP <span style="font-family: 宋体">时（称为</span> A <span style="font-family: 宋体">情况），上述程序代码可正确执行。但是如果客户机只有浏览器，而没有</span> JDK <span style="font-family: 宋体">和</span> CLASSPATH <span style="font-family: 宋体">时（称为</span> B <span style="font-family: 宋体">情况），则汉字无法正确转换。</span></p>
<p><span style="font-family: 宋体">我们的分析：</span></p>
<p>1.<span style="font-family: 宋体">经过测试，在</span> A <span style="font-family: 宋体">情况下，程序运行时系统的缺省编码方式为</span> GBK <span style="font-family: 宋体">或者</span> GB2312 <span style="font-family: 宋体">。在</span> B <span style="font-family: 宋体">情况下，程序启动时浏览器的</span> JAVA <span style="font-family: 宋体">控制台中出现如下错误信息：</span></p>
<p>Can't find resource for sun.awt.windows.awtLocalization_zh_CN </p>
<p><span style="font-family: 宋体">然后系统的缺省编码方式为&#8220;</span>8859-1<span style="font-family: 宋体">&#8221;。</span></p>
<p>2.<span style="font-family: 宋体">如果在转换字符串时不采用系统缺省编码方式，而是直接采用</span> <span style="font-family: 宋体">&#8220;</span>GBK<span style="font-family: 宋体">&#8221;</span> <span style="font-family: 宋体">或&#8220;</span>GB2312<span style="font-family: 宋体">&#8221;，则在</span> A <span style="font-family: 宋体">情况下程序仍然可正常运行，在</span> B <span style="font-family: 宋体">情况下，系统出现错误：</span></p>
<p>UnsupportedEncodingException<span style="font-family: 宋体">。</span></p>
<p>3.<span style="font-family: 宋体">在客户机上，把</span> JDK <span style="font-family: 宋体">的</span> CLASSES.ZIP <span style="font-family: 宋体">解压后，放在另一个目录中，</span> CLASSPATH <span style="font-family: 宋体">只包含该目录。然后一边逐步删除该目录中的</span> .CLASS <span style="font-family: 宋体">文件，另一边运行测试程序，最后发现在一千多个</span> CLASS <span style="font-family: 宋体">文件中，只有一个是必不可少的，该文件是：</span></p>
<p>sun.io.CharToByteDoubleByte.class<span style="font-family: 宋体">。</span></p>
<p><span style="font-family: 宋体">将该文件拷到服务器端和其它的类放在一起，并在程序的开头</span> IMPORT <span style="font-family: 宋体">它，在</span> B <span style="font-family: 宋体">情况下程序仍然无法正常运行。</span></p>
<p>4.<span style="font-family: 宋体">在</span> A <span style="font-family: 宋体">情况下，如果在</span> CLASSPTH <span style="font-family: 宋体">中去掉</span> sun.io.CharToByteDoubleByte.class <span style="font-family: 宋体">，则程序运行时测得默认编码方式为&#8220;</span>8859-1<span style="font-family: 宋体">&#8221;，否则为</span> <span style="font-family: 宋体">&#8220;</span>GBK<span style="font-family: 宋体">&#8221;</span> <span style="font-family: 宋体">或</span> <span style="font-family: 宋体">&#8220;</span>GB2312<span style="font-family: 宋体">&#8221;</span> <span style="font-family: 宋体">。</span></p>
<p><span style="font-family: 宋体">如果</span> JDK <span style="font-family: 宋体">的版本为</span>1.2<span style="font-family: 宋体">以上的话，在</span> B <span style="font-family: 宋体">情况下遇到的问题得到了很好的解决，测试的步骤同上，有兴趣的读者可以尝试一下。</span></p>
<p><strong>Java </strong><strong><span style="font-family: 宋体">中文问题的根源分析及解决</span></strong></p>
<p><span style="font-family: 宋体">在简体中文</span> MS Windows 98 + JDK 1.3 <span style="font-family: 宋体">下，可以用</span> System.getProperties() <span style="font-family: 宋体">得到</span> Java <span style="font-family: 宋体">运行环境的一些基本属性，类</span> PoorChinese <span style="font-family: 宋体">可以帮助我们得到这些属性。</span></p>
<p><span style="font-family: 宋体">类</span> PoorChinese <span style="font-family: 宋体">的源代码：</span></p>
<p>public class PoorChinese {</p>
<p>} </p>
<p><span style="font-family: 宋体">执行</span> java PoorChinese <span style="font-family: 宋体">后，我们会得到</span>:</p>
<p><span style="font-family: 宋体">系统变量</span> file.encoding <span style="font-family: 宋体">的值为</span> GBK <span style="font-family: 宋体">，</span>user.language <span style="font-family: 宋体">的值为</span> zh <span style="font-family: 宋体">，</span> user.region <span style="font-family: 宋体">的值为</span> CN <span style="font-family: 宋体">，这些系统变量的值决定了系统默认的编码方式是</span> GBK <span style="font-family: 宋体">。</span></p>
<p><span style="font-family: 宋体">在上述系统中，下面的代码将</span> GB2312 <span style="font-family: 宋体">文件转换成</span> Big5 <span style="font-family: 宋体">文件，它们能够帮助我们理解</span> Java <span style="font-family: 宋体">中汉字编码的转化</span>:</p>
<p>?</p>
<p>import java.io.*;</p>
<p>import java.util.*;</p>
<p>?</p>
<p>public class gb2big5 {</p>
<p>?</p>
<p>static int iCharNum=0;</p>
<p>?</p>
<p>public static void main(String[] args) {</p>
<p>System.out.println("Input GB2312 file, output Big5 file.");</p>
<p>if (args.length!=2) {</p>
<p>System.err.println("Usage: jview gb2big5 gbfile big5file");</p>
<p>System.exit(1);</p>
<p>String inputString = readInput(args[0]);</p>
<p>writeOutput(inputString,args[1]);</p>
<p>System.out.println("Number of Characters in file: "+iCharNum+".");</p>
<p>}</p>
<p>?</p>
<p>static void writeOutput(String str, String strOutFile) {</p>
<p>try {</p>
<p>FileOutputStream fos = new FileOutputStream(strOutFile);</p>
<p>Writer out = new OutputStreamWriter(fos, "Big5");</p>
<p>out.write(str);</p>
<p>out.close();</p>
<p>}</p>
<p>catch (IOException e) {</p>
<p>e.printStackTrace();</p>
<p>e.printStackTrace();</p>
<p>}</p>
<p>}</p>
<p>?</p>
<p>static String readInput(String strInFile) {</p>
<p>StringBuffer buffer = new StringBuffer();</p>
<p>try {</p>
<p>FileInputStream fis = new FileInputStream(strInFile);</p>
<p>InputStreamReader isr = new InputStreamReader(fis, "GB2312");</p>
<p>Reader in = new BufferedReader(isr);</p>
<p>int ch;</p>
<p>while ((ch = in.read()) &gt; -1) {</p>
<p>iCharNum += 1;</p>
<p>buffer.append((char)ch);</p>
<p>}</p>
<p>in.close();</p>
<p>return buffer.toString();</p>
<p>}</p>
<p>catch (IOException e) {</p>
<p>e.printStackTrace();</p>
<p>return null;</p>
<p>}</p>
<p>}</p>
<p>}</p>
<p>?</p>
<p>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; &nbsp;</p>
<p><span style="font-family: 宋体">编码转化的过程如下：</span></p>
<p>GB2312------------------&gt;Unicode-------------&gt;Big5</p>
<p><span style="font-family: 宋体">执行</span> java gb2big5 gb.txt big5.txt <span style="font-family: 宋体">，如果</span> gb.txt <span style="font-family: 宋体">的内容是&#8220;今天星期三&#8221;，则得到的文件</span> big5.txt <span style="font-family: 宋体">中的字符能够正确显示；而如果</span> gb.txt <span style="font-family: 宋体">的内容是&#8220;情人节快乐&#8221;，则得到的文件</span> big5.txt <span style="font-family: 宋体">中对应于&#8220;节&#8221;和&#8220;乐&#8221;的字符都是符号&#8220;？&#8221;（</span>0x3F<span style="font-family: 宋体">），可见</span> sun.io.ByteToCharGB2312 <span style="font-family: 宋体">和</span> sun.io.CharToByteBig5 <span style="font-family: 宋体">这两个基本类并没有编好。</span></p>
<p><span style="font-family: 宋体">正如上例一样，</span> Java <span style="font-family: 宋体">的基本类也可能存在问题。由于国际化的工作并不是在国内完成的，所以在这些基本类发布之前，没有经过严格的测试，所以对中文字符的支持并不像</span> Java Soft <span style="font-family: 宋体">所声称的那样完美。前不久，我的一位技术上的朋友发信给我说，他终于找到了</span> Java Servlet <span style="font-family: 宋体">中文问题的根源。两周以来，他一直为</span> Java Servlet <span style="font-family: 宋体">的中文问题所困扰，因为每面对一个含有中文字符的字符串都必须进行强制转换才能够得到正确的结果（这好象是大家公认的唯一的解决办法）。后来，他确实不想如此继续安分下去了，因为这样的事情确实不应该是高级程序员所要做的工作，他就找出</span> Servlet <span style="font-family: 宋体">解码的源代码进行分析，因为他怀疑问题就出在解码这部分。经过四个小时的奋斗，他终于找到了问题的根源所在。原来他的怀疑是正确的，</span> Servlet <span style="font-family: 宋体">的解码部分完全没有考虑双字节，直接把</span> %XX <span style="font-family: 宋体">当作一个字符。（原来</span> Java Soft <span style="font-family: 宋体">也会犯这幺低级的错误！）</span></p>
<p><span style="font-family: 宋体">如果你对这个问题有兴趣或者遇到了同样的烦恼的话，你可以按照他的步骤</span> <span style="font-family: 宋体">对</span>Servlet.jar <span style="font-family: 宋体">进行修改：</span></p>
<p><span style="font-family: 宋体">找到源代码</span> HttpUtils <span style="font-family: 宋体">中的</span> static private String parseName <span style="font-family: 宋体">，在返回前将</span> sb<span style="font-family: 宋体">（</span>StringBuffer<span style="font-family: 宋体">）</span> <span style="font-family: 宋体">复制成</span> byte bs[] <span style="font-family: 宋体">，然后</span> return new String(bs,<span style="font-family: 宋体">&#8221;</span>GB2312<span style="font-family: 宋体">&#8221;</span>)<span style="font-family: 宋体">。作上述修改后就需要自己解码了：</span></p>
<p>HashTable form=HttpUtils .parseQueryString(request.getQueryString())<span style="font-family: 宋体">或者</span></p>
<p>form=HttpUtils.parsePostData(&#8230;&#8230;)</p>
<p><span style="font-family: 宋体">千万别忘了编译后放到</span> Servlet.jar <span style="font-family: 宋体">里面。</span></p>
<p><strong><span style="font-family: 宋体">关于</span> Java </strong><strong><span style="font-family: 宋体">中文问题的总结</span></strong></p>
<p>Java <span style="font-family: 宋体">编程语言成长于网络世界，这就要求</span> Java <span style="font-family: 宋体">对多国字符有很好的支持。</span> Java <span style="font-family: 宋体">编程语言适应了计算的网络化的需求，为它能够在网络世界迅速成长奠定了坚实的基础。</span> Java <span style="font-family: 宋体">的缔造者</span> <span style="font-family: 宋体">（</span>Java Soft<span style="font-family: 宋体">）</span> <span style="font-family: 宋体">已经考虑到</span> Java <span style="font-family: 宋体">编程语言对多国字符的支持，只是现在的解决方案有很多缺陷在里面，需要我们付诸一些补偿性的措施。而世界标准化组织也在努力把人类所有的文字统一在一种编码之中，其中一种方案是</span> ISO10646 <span style="font-family: 宋体">，它用四个字节来表示一个字符。当然，在这种方案未被采用之前，还是希望</span> Java Soft <span style="font-family: 宋体">能够严格地测试它的产品，为用户带来更多的方便。</span></p>
<p><span style="font-family: 宋体">附一个用于从数据库和网络中取出</span> <span style="font-family: 宋体">中文乱码的处理函数，入参是有问题的字符串，出参是问题已经解决了的字符串。</span></p>
<p><span style="font-family: 宋体">技术应用者提供解决方案</span></p>
<p><span style="font-family: 宋体">关于作者</span></p>
<p>&nbsp;<span style="font-family: 宋体">段明辉</span> has co-authored this article</p>
<p style="text-align: left" align="left"><span style="font-size: 8.5pt; color: blue; font-family: 宋体">编译代码文件</span><span style="font-size: 8.5pt; color: blue; font-family: Verdana">,</span><span style="font-size: 8.5pt; color: blue; font-family: 宋体">要用</span></p>
<p style="text-align: left" align="left"><span style="font-size: 8.5pt; color: blue; font-family: Verdana">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; javac -encoding GBK&nbsp;&nbsp; xxxxxx.java </span></p>
<p style="text-align: left" align="left"><span style="font-size: 8.5pt; color: blue; font-family: Verdana">&nbsp; &nbsp;</span><span style="font-size: 8.5pt; color: blue; font-family: 宋体">如果是用</span><span style="font-size: 8.5pt; color: blue; font-family: Verdana">ant</span><span style="font-size: 8.5pt; color: blue; font-family: 宋体">工具</span><span style="font-size: 8.5pt; color: blue; font-family: Verdana">,</span></p>
<p style="text-align: left" align="left"><span style="font-size: 8.5pt; color: blue; font-family: Verdana">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; &lt;target name="compile" depends="prepare" description="complie All Java source"&gt;<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; &nbsp;&lt;copy todir="${build.dir}"&gt;<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; &nbsp;&lt;fileset dir="${src.dir}" includes="**/*.properties" /&gt;<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; &lt;/copy&gt;<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; &lt;javac srcdir="${src.dir}" destdir="${build.dir}" encoding="<strong><span style="background: yellow">GBK</span></strong>"&gt;<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; &nbsp;&lt;classpath refid="project.classpath" /&gt;<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&lt;/javac&gt;</span></p>
<p style="text-align: left" align="left"><span style="font-size: 8.5pt; color: blue; font-family: Verdana">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; &lt;/target&gt;</span></p>
<img src ="http://www.blogjava.net/hengheng123456789/aggbug/142342.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.blogjava.net/hengheng123456789/" target="_blank">哼哼</a> 2007-09-03 15:49 <a href="http://www.blogjava.net/hengheng123456789/archive/2007/09/03/142342.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>java中文解决大全</title><link>http://www.blogjava.net/hengheng123456789/archive/2007/09/03/142343.html</link><dc:creator>哼哼</dc:creator><author>哼哼</author><pubDate>Mon, 03 Sep 2007 07:49:00 GMT</pubDate><guid>http://www.blogjava.net/hengheng123456789/archive/2007/09/03/142343.html</guid><wfw:comment>http://www.blogjava.net/hengheng123456789/comments/142343.html</wfw:comment><comments>http://www.blogjava.net/hengheng123456789/archive/2007/09/03/142343.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.blogjava.net/hengheng123456789/comments/commentRss/142343.html</wfw:commentRss><trackback:ping>http://www.blogjava.net/hengheng123456789/services/trackbacks/142343.html</trackback:ping><description><![CDATA[&nbsp;&nbsp;&nbsp;&nbsp; 摘要: &nbsp;java中文解决大全说明：本文为作者原创，作者联系地址为：josserchai@yahoo.com。由于Java编程中的中文问题是一个老生常谈的问题，在阅读了许多关于Java中文问题解决方法之后，结合作者的编程实践，我发现过去谈的许多方法都不能清晰地说明问题及解决问题，尤其是跨平台时的中文问题。于是我给出此篇文章，内容包括对控制台运行的class、Servelets、JSP及E...&nbsp;&nbsp;<a href='http://www.blogjava.net/hengheng123456789/archive/2007/09/03/142343.html'>阅读全文</a><img src ="http://www.blogjava.net/hengheng123456789/aggbug/142343.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.blogjava.net/hengheng123456789/" target="_blank">哼哼</a> 2007-09-03 15:49 <a href="http://www.blogjava.net/hengheng123456789/archive/2007/09/03/142343.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>制作Java安装程序</title><link>http://www.blogjava.net/hengheng123456789/archive/2007/09/03/142341.html</link><dc:creator>哼哼</dc:creator><author>哼哼</author><pubDate>Mon, 03 Sep 2007 07:48:00 GMT</pubDate><guid>http://www.blogjava.net/hengheng123456789/archive/2007/09/03/142341.html</guid><wfw:comment>http://www.blogjava.net/hengheng123456789/comments/142341.html</wfw:comment><comments>http://www.blogjava.net/hengheng123456789/archive/2007/09/03/142341.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.blogjava.net/hengheng123456789/comments/commentRss/142341.html</wfw:commentRss><trackback:ping>http://www.blogjava.net/hengheng123456789/services/trackbacks/142341.html</trackback:ping><description><![CDATA[&nbsp;
<p style="text-align: center" align="center"><strong><span style="font-family: 宋体">制作</span>Java</strong><strong><span style="font-family: 宋体">安装程序</span></strong></p>
<p><a href="http://zeroliu.blogdriver.com/zeroliu/1183916.html">http://zeroliu.blogdriver.com/zeroliu/1183916.html</a></p>
<p><span style="font-family: 宋体">这个工具利用</span> ANT <span style="font-family: 宋体">来制作在</span> Windows, MacOS X, Unix <span style="font-family: 宋体">平台上可执行的文件，比如</span> exe<span style="font-family: 宋体">，</span>zip<span style="font-family: 宋体">，</span>jar<span style="font-family: 宋体">。</span>ROXES ANT Tasks <span style="font-family: 宋体">基于</span> GPL <span style="font-family: 宋体">发布。</span>&nbsp;</p>
<p>&nbsp;http://www.roxes.com/produkte/rat.html </p>
<p>&nbsp;<span style="font-family: 宋体">企业开源参考架构</span></p>
<p>Java Web<span style="font-family: 宋体">应用产品安装程序制作方案</span></p>
<p><span style="font-family: 宋体">目录：</span></p>
<p><span style="font-family: 宋体">一．背景</span></p>
<p><span style="font-family: 宋体">二．开源工具</span></p>
<p><span style="font-family: 宋体">三．环境准备</span></p>
<p><span style="font-family: 宋体">四．技术准备</span></p>
<p>4.1. Jsmooth</p>
<p>4.1.1. Jsmooth<span style="font-family: 宋体">简介</span></p>
<p>4.1.2.<span style="font-family: 宋体">工作原理</span></p>
<p>4.2. IzPack</p>
<p>4.2.1.IzPack<span style="font-family: 宋体">简介</span></p>
<p>4.2.2.<span style="font-family: 宋体">工作原理</span></p>
<p><span style="font-family: 宋体">五．方案实例</span></p>
<p><span style="font-family: 宋体">六．结束</span></p>
<p><span style="font-family: 宋体">一．</span> <span style="font-family: 宋体">背景：</span></p>
<p><span style="font-family: 宋体">随着</span>Java<span style="font-family: 宋体">在应用产品开发中的广泛应用，基于</span>Java<span style="font-family: 宋体">的应用产品也就越来越多，那么如何为基于</span>Java<span style="font-family: 宋体">的应用产品制作安装程序的需求就产生了。以前人们一般都是使用</span>InstallShield<span style="font-family: 宋体">与</span>InstallAnyWhere<span style="font-family: 宋体">进行产品安装程序的制作，这是两个功能非常强大、易用的安装盘制作工具，尤其是</span>InstallAnyWhere<span style="font-family: 宋体">，它还支持</span>Java<span style="font-family: 宋体">应用产品安装制作，例如：大名鼎鼎的</span>Jbuilder<span style="font-family: 宋体">安装程序就是由它制作的。</span></p>
<p><span style="font-family: 宋体">本文并不准备对这些商业的安装制作工具进行讨论，本文将就如何利用开源的安装制作工具来进行</span>Java Web<span style="font-family: 宋体">应用产品程序制作进行一些探讨。</span></p>
<p><span style="font-family: 宋体">二．</span> <span style="font-family: 宋体">开源工具：</span></p>
<p><span style="font-family: 宋体">目前用于支持</span>Java<span style="font-family: 宋体">应用安装程序制作的开源工具非常丰富，本人将要本人在研究过程中所遇到的罗列一二以供参考：</span></p>
<p>Packlet</p>
<p>Packlet<span style="font-family: 宋体">是一个简单的</span>Java<span style="font-family: 宋体">安装制作工具。它将</span>Java Application<span style="font-family: 宋体">打包成一个可以发布的类似于</span>zip<span style="font-family: 宋体">或</span>tgz<span style="font-family: 宋体">的压缩文件中。这个压缩文件被简为</span>packlet<span style="font-family: 宋体">，它可以在安装有</span>Java 2 Runtime Environment<span style="font-family: 宋体">的操作系统上执行</span>. <span style="font-family: 宋体">通过执行</span>packlet<span style="font-family: 宋体">将会给用户提供一个图形化的安装配置界面并解压应用。</span></p>
<p>Go To Packlet </p>
<p>IzPack</p>
<p>IzPack<span style="font-family: 宋体">是一个用于</span>Java<span style="font-family: 宋体">平台的安装程序生成器。它用于产生一个轻量级、能运行于所有安装了</span>JVM<span style="font-family: 宋体">的任何的操作系统的安装程序。生成的安装程序可以通过双击或在</span>Command Line<span style="font-family: 宋体">通过</span>java <span style="font-family: 宋体">&#8211;</span>jar install.jar<span style="font-family: 宋体">命令进行启动，安装程序运行的方式具体将看操作系统的支持方式。</span>IzPack<span style="font-family: 宋体">的主要好处就是能够生成运行于任意操作系统的安装程序。</span></p>
<p>Go To IzPack </p>
<p>JSmooth</p>
<p>Jsmooth<span style="font-family: 宋体">可以将</span>Java<span style="font-family: 宋体">可执行应用</span>Wrapper<span style="font-family: 宋体">成</span>window<span style="font-family: 宋体">可执行</span>Exe<span style="font-family: 宋体">程序。通过</span>Jsmooth<span style="font-family: 宋体">生成的</span>Exe<span style="font-family: 宋体">程序会自动按制作时定义的顺序寻找合适的</span>JVM<span style="font-family: 宋体">，如果能不查找到</span>JVM<span style="font-family: 宋体">，安装程序会提示用户并能根据定义好的</span>URL<span style="font-family: 宋体">启动</span>Web Browser<span style="font-family: 宋体">让用户下载</span>JVM. <span style="font-family: 宋体">注意：</span>Jsmooth<span style="font-family: 宋体">并不是纯</span>Java<span style="font-family: 宋体">应用。</span></p>
<p>Go To JSmooth </p>
<p>VAInstall</p>
<p>VAInsall<span style="font-family: 宋体">是一个用</span>Java<span style="font-family: 宋体">写的多平台安装程序工具。它是基于</span>GNU GPL2.0<span style="font-family: 宋体">许可。通过一个简单的配置文件，它允许安装程序打包工具由不同的目录下收集程序包，这与一般情况下安装程序制作工具只能由一个根目录开始相比更为灵活。由</span>VAInstall<span style="font-family: 宋体">生成的安装程序允许先择不同的安装模式</span>(graphic,text<span style="font-family: 宋体">或</span>ansi)<span style="font-family: 宋体">。</span></p>
<p>Go To VAInstall </p>
<p>Java Service Wrapper</p>
<p><span style="font-family: 宋体">用于将</span>Java Application<span style="font-family: 宋体">安装成为</span>Window NT Service.<span style="font-family: 宋体">同时与之附带的</span>scripts<span style="font-family: 宋体">能够很容易将</span>Java Application<span style="font-family: 宋体">安装成为</span>UNIX<span style="font-family: 宋体">的后台进程。</span></p>
<p>Go To Java Service Wrapper </p>
<p>Lift Off Java Installer</p>
<p>Lift Off Java Installer<span style="font-family: 宋体">的最大特色就是：自解压</span>class <span style="font-family: 宋体">文件，对目标系统要求低以及跨平台性。</span></p>
<p>Go To Lift Off Java Installer </p>
<p>Toolshed</p>
<p><span style="font-family: 宋体">一个小巧、简单、纯</span>Java<span style="font-family: 宋体">实现的安装程序制作工作。</span></p>
<p>Go To Toolshed </p>
<p>Launch4J</p>
<p>Lauch4J<span style="font-family: 宋体">也是一个</span>Java<span style="font-family: 宋体">应用</span>Window Exe<span style="font-family: 宋体">封装工具。通过</span>Lauch4J<span style="font-family: 宋体">，可以提供</span>splash screen, <span style="font-family: 宋体">图标，自动查询</span>JRE<span style="font-family: 宋体">或内置</span>JRE<span style="font-family: 宋体">等功能，同时还支持启动失败反馈以及命令行参数。</span></p>
<p>Go To Launch4J </p>
<p>AntInstaller</p>
<p>AntInstaller<span style="font-family: 宋体">是一个安装程序框架，它利用一个简单的</span>XML<span style="font-family: 宋体">定义安装界面，并以</span>Ant<span style="font-family: 宋体">执行安装过程。基于</span>AntInstaller<span style="font-family: 宋体">的安装程序可以打包成自解压</span>jar<span style="font-family: 宋体">通过</span>command line<span style="font-family: 宋体">执行可</span>Swing GUI<span style="font-family: 宋体">来执行。</span></p>
<p>Go To AntInstaller </p>
<p>Antigen</p>
<p>Antigen----<span style="font-family: 宋体">即</span>Ant Installer Generator<span style="font-family: 宋体">。它主要的目的就是根据</span>Ant<span style="font-family: 宋体">脚本创建图形化安装程序。</span></p>
<p>Go To Antigen </p>
<p>FreeInstaller</p>
<p>FreeInstaller<span style="font-family: 宋体">是一个开源项目，完全用</span>Java<span style="font-family: 宋体">编写。它将应用程序打包成一个自解压的</span>Java<span style="font-family: 宋体">应用。通过</span>FreeInstaller<span style="font-family: 宋体">可以将</span>Java<span style="font-family: 宋体">或非</span>Java<span style="font-family: 宋体">的应用安装到</span>UNIX,LINUX<span style="font-family: 宋体">以及</span>window NT<span style="font-family: 宋体">系统中。</span></p>
<p>Go To FreeInstaller </p>
<p>Mini Installer</p>
<p><span style="font-family: 宋体">一个简单的</span>Java<span style="font-family: 宋体">安装程序制作工具。整个制作过程是通过脚本完成的，最终生成一个可以通过双击方式执行的</span>jar<span style="font-family: 宋体">文件。</span></p>
<p>Go To Mini Installer </p>
<p><span style="font-family: 宋体">通过对如上各产品的初步探索，本人最终选择了利用</span>izpack + jsmooth<span style="font-family: 宋体">作为</span>Java Web<span style="font-family: 宋体">应用产品的安装程序制作方案。选择这两种工具并不代表其它开源工具不好，只是本人自已结合自已项目的需求</span>(<span style="font-family: 宋体">本人负责公司一企业应用开发平台的研发工作</span>)<span style="font-family: 宋体">及本人的偏好作出的选择。</span></p>
<p><span style="font-family: 宋体">由于本人所在公司为商业公司，所以本文描述的方案并不是企业应用开发系统平台的实现模式，本文只是提供一个解决办法，关于如何与自已的框架或平台进行有效的整合，请读者自行考虑。</span></p>
<p><span style="font-family: 宋体">三．</span> <span style="font-family: 宋体">环境准备：</span></p>
<p><span style="font-family: 宋体">你需要安装</span>J2SDK1.4.1+<span style="font-family: 宋体">版本；关于</span>J2SDK<span style="font-family: 宋体">请由</span>Sun<span style="font-family: 宋体">公司下载；</span></p>
<p><span style="font-family: 宋体">你需要安装</span>Ant1.6.2<span style="font-family: 宋体">版本，理论上其它版本也行，只是本人用的是</span>1.6.2<span style="font-family: 宋体">；</span></p>
<p><span style="font-family: 宋体">请下载并安装</span>izpack<span style="font-family: 宋体">；设定定装到</span>IZPACK_HOME</p>
<p><span style="font-family: 宋体">请下载并安装</span>jsmooth<span style="font-family: 宋体">；设定安装到</span>JSMOOTH_HOME</p>
<p><span style="font-family: 宋体">四．</span> <span style="font-family: 宋体">技术准备：</span></p>
<p><span style="font-family: 宋体">为了便于理解，你需要对</span>Java<span style="font-family: 宋体">进行应用的开发有一定的基础，本例将以</span>Web<span style="font-family: 宋体">应用的安装程序制作为背景进行相关介绍，所以需要你对</span>Web <span style="font-family: 宋体">应用开发以及其发布方式有一定的基础；另外，本方案将会以</span>Ant<span style="font-family: 宋体">作为应用</span>build<span style="font-family: 宋体">的工具，所以你需要有一定的</span>Ant<span style="font-family: 宋体">技术；对于如上相关知识本部分不准备介绍。下面本部分将主要对</span>izpack<span style="font-family: 宋体">及</span>jsmooth<span style="font-family: 宋体">进行简单的介绍。</span></p>
<p>4.1. jsmooth<span style="font-family: 宋体">：</span></p>
<p>4.1.1 Jsmooth <span style="font-family: 宋体">简介：</span></p>
<p>Jsmooth<span style="font-family: 宋体">，一个</span>Java<span style="font-family: 宋体">可执行应用封装器</span>(Wrapper)<span style="font-family: 宋体">，即将</span>Java<span style="font-family: 宋体">可执行应用程序</span>(<span style="font-family: 宋体">即可执行</span>jar)<span style="font-family: 宋体">封装为</span>Window<span style="font-family: 宋体">可执行文件</span>------exe<span style="font-family: 宋体">文件的工具。</span></p>
<p><span style="font-family: 宋体">通过</span>Jsmooth<span style="font-family: 宋体">将可执行</span>jar<span style="font-family: 宋体">封装为</span>Exe<span style="font-family: 宋体">文件，使得用户执行</span>Java<span style="font-family: 宋体">应用就如同执行一般的</span>Window<span style="font-family: 宋体">应用程序一样，重用用户经验。</span></p>
<p>Jsmooth<span style="font-family: 宋体">对</span>jar<span style="font-family: 宋体">进行封装时可以设定</span>classpath<span style="font-family: 宋体">，</span>JVM<span style="font-family: 宋体">参数，命令行参数，</span>JVM<span style="font-family: 宋体">版本及位置，这样用户在执行</span>exe<span style="font-family: 宋体">时不用关心</span>JVM,Classpath<span style="font-family: 宋体">等问题，这样就简化了</span>Java<span style="font-family: 宋体">应用执行。</span></p>
<p>4.1.2 <span style="font-family: 宋体">工作原理：</span></p>
<p><span style="font-family: 宋体">通过</span>Jsmooth<span style="font-family: 宋体">生成的</span>Window Exe<span style="font-family: 宋体">文件通常定义为&#8220;</span>Jsmooth Application<span style="font-family: 宋体">&#8221;；</span></p>
<p><span style="font-family: 宋体">要想生成</span>Jsmooth Application<span style="font-family: 宋体">，我们需要一个</span>JsmoothGen <span style="font-family: 宋体">项目文件</span>-----.jsmooth<span style="font-family: 宋体">文件，后面我们将其称为&#8220;</span>.jsmooth<span style="font-family: 宋体">文件&#8221;；</span>.jsmooth<span style="font-family: 宋体">文件实际上是一个</span>xml<span style="font-family: 宋体">文件，用于描述</span>/<span style="font-family: 宋体">定义</span>Jsmooth Application<span style="font-family: 宋体">的相关属性，例如：</span>classpath, JVM<span style="font-family: 宋体">，</span>Java main<span style="font-family: 宋体">方法类，以及其它与</span>Java<span style="font-family: 宋体">应用运行相关的各种设定等；通常你可以通过</span>Jsmooth<span style="font-family: 宋体">提供的</span>JsmoothGen.exe--------Windows Project Editor<span style="font-family: 宋体">来创建和编辑这个文件，这个</span>Editor<span style="font-family: 宋体">如下图所示：</span></p>
<p>(<span style="font-family: 宋体">图</span>-1)Widnow Project Editor</p>
<p>(<span style="font-family: 宋体">图</span>-2)Widnow Project Editor</p>
<p>(<span style="font-family: 宋体">图</span>-3)Widnow Project Editor</p>
<p><span style="font-family: 宋体">在</span>.jsmooth<span style="font-family: 宋体">文件生成之后，就可以通过如下方式生成目标</span>Jsmooth Application<span style="font-family: 宋体">，即</span>Exe<span style="font-family: 宋体">文件：</span></p>
<p>(1)<span style="font-family: 宋体">。</span>Window Project Editor<span style="font-family: 宋体">：</span></p>
<p><span style="font-family: 宋体">你可以直接在如上图所示的编辑器通过工具条来生成：</span>Project<span style="font-family: 宋体">&#224;</span>Create Exe<span style="font-family: 宋体">。</span></p>
<p>(2)<span style="font-family: 宋体">。</span>Command Line<span style="font-family: 宋体">：</span></p>
<p><span style="font-family: 宋体">你也可以进入。</span>jsmooth<span style="font-family: 宋体">文件所以目录，通过如下命令来生成目标</span>Exe<span style="font-family: 宋体">文件：</span></p>
<p><span style="font-family: 宋体">&#8230;&#8230;&#8230;</span>&gt; %jsmooth_home%"jsmoothcmd.exe yourproject.jsmooth</p>
<p>(3)<span style="font-family: 宋体">。通过</span>Ant<span style="font-family: 宋体">任务调用生成目标</span>Exe<span style="font-family: 宋体">：</span></p>
<p><span style="font-family: 宋体">首先你需要在你的</span>build<span style="font-family: 宋体">文件中加入</span>jsmooth Ant <span style="font-family: 宋体">任务定义：</span></p>
<p>&lt;&gt;&nbsp;</p>
<p>classname="net.charabia.jsmoothgen.ant.JSmoothGen" </p>
<p>classpath="${jsmooth_home}/lib/jsmoothgen-ant.jar"/&gt;</p>
<p><span style="font-family: 宋体">然后，通过</span>jsmoothgen<span style="font-family: 宋体">任务来执行生成</span>Exe<span style="font-family: 宋体">的工作：</span></p>
<p>skeletonroot=&#8221;${jsmooth_home}/skeletons&#8221;/&gt;</p>
<p><span style="font-family: 宋体">所以通过</span>Jsmooth<span style="font-family: 宋体">我们可以很容易将</span>Java Application<span style="font-family: 宋体">制作</span>Windows Exe<span style="font-family: 宋体">应用。</span></p>
<p><span style="font-family: 宋体">关于</span>Jsmooth<span style="font-family: 宋体">的详细介绍请参考</span>http://jsmooth.sourceforge.net</p>
<p>4.2. izpack<span style="font-family: 宋体">：</span></p>
<p>4.2.1. izpack<span style="font-family: 宋体">简介：</span></p>
<p>izpack<span style="font-family: 宋体">是基于</span>Apache Software License 2.0<span style="font-family: 宋体">许可的开源项目；</span></p>
<p>izpack<span style="font-family: 宋体">是纯</span>Java<span style="font-family: 宋体">，对部分特性有针对不同平台版本的</span>Library<span style="font-family: 宋体">。例如：快捷键的创建。</span></p>
<p>izpack<span style="font-family: 宋体">是一个用于解决安装程序制作的</span>Builder<span style="font-family: 宋体">工具；</span></p>
<p><span style="font-family: 宋体">通过</span>izpack<span style="font-family: 宋体">制作的安装程序可以运行于不同的操作系统，</span>Windows, Linux, Unix<span style="font-family: 宋体">等，只要安装了</span>JDK1.4<span style="font-family: 宋体">以及其后版本即可；</span></p>
<p>izpack<span style="font-family: 宋体">优秀的模块化设计可以允许你定制安装程序外观、安装过程等；同时允许你通过其提供</span>API<span style="font-family: 宋体">调整</span>izpack<span style="font-family: 宋体">安装过程。</span></p>
<p>izpack<span style="font-family: 宋体">的主要功能包括</span>(<span style="font-family: 宋体">但不限于</span>)<span style="font-family: 宋体">：</span></p>
<p><span style="font-family: 宋体">&#183;</span> XML based installation files </p>
<p><span style="font-family: 宋体">&#183;</span> easy internationalization using XML files (10 translations are already available) </p>
<p><span style="font-family: 宋体">&#183;</span> Ant integration, command-line compiler </p>
<p><span style="font-family: 宋体">&#183;</span> easy customization with the panels and a rich API (even an XML parser is included !) </p>
<p><span style="font-family: 宋体">&#183;</span> powerful variable substitution system that you can use to customize scripts and more generally any text-based file </p>
<p><span style="font-family: 宋体">&#183;</span> different kinds of installers (standard, web-based, ...) </p>
<p><span style="font-family: 宋体">&#183;</span> launching of external executables during the installation process and Unix executable flag support (useful for the scripts for instance) </p>
<p><span style="font-family: 宋体">&#183;</span> layout of the installation files in packs (some can be optional) </p>
<p><span style="font-family: 宋体">&#183;</span> native code integration facilities </p>
<p><span style="font-family: 宋体">&#183;</span> jar files nesting support </p>
<p><span style="font-family: 宋体">&#183;</span> ... more things to discover and create !. </p>
<p>(<span style="font-family: 宋体">图</span>-4)IzPack<span style="font-family: 宋体">制作的安装界面示例－选择安装的</span>Pack.</p>
<p>4.2.2. <span style="font-family: 宋体">原理及过程</span></p>
<p><span style="font-family: 宋体">利用</span>izpack<span style="font-family: 宋体">制作安装程序的主要有两步：</span></p>
<p><span style="font-family: 宋体">第一步：创建并描述安装定义文件；</span></p>
<p><span style="font-family: 宋体">第二步：通过</span>izpack<span style="font-family: 宋体">提供</span>CommandLine<span style="font-family: 宋体">工具或</span>Ant Task<span style="font-family: 宋体">对安装定义文件进行编译，编译的结果即是生成一个可执行的</span>jar<span style="font-family: 宋体">文件，其中包括了整个安装过程的实现以及安装数据；</span></p>
<p><span style="font-family: 宋体">安装定义文件：</span></p>
<p><span style="font-family: 宋体">安装过程定义文件是一个</span>XML<span style="font-family: 宋体">文件，</span>installation<span style="font-family: 宋体">是根元素，表示定义的开始。定义主要由如下几部分组成：</span></p>
<p>1<span style="font-family: 宋体">．&#8230;</span>.</p>
<p><span style="font-family: 宋体">用于定义安装程序的基本信息；</span></p>
<p><span style="font-family: 宋体">产品中文名称</span></p>
<p><span style="font-family: 宋体">产品版本号，例如：</span>1.0-062312</p>
<p><span style="font-family: 宋体">公司网址</span></p>
<p>JDK<span style="font-family: 宋体">版本号：</span>1.4.2 </p>
<p>2<span style="font-family: 宋体">．&#8230;&#8230;</span></p>
<p><span style="font-family: 宋体">用于定义安装程序界面信息，例如：</span></p>
<p>3.&#8230;&#8230;..</p>
<p><span style="font-family: 宋体">定义变量或配置信息，变量在整个安装制作的过程中非常重要，变量两种用途：其一：作为配置用，例如可以通过按照一定的命名称规则为某个变量设定一个值，</span>izpack<span style="font-family: 宋体">在执行安装过程中将会读取某个变量的值来决定某个安装向导窗口是否可见等；例如：我们可以通过定义</span>compareToVariable.<span style="font-family: 宋体">、</span>compareToOperator.<span style="font-family: 宋体">与</span>compareToValue.<span style="font-family: 宋体">的组合决定第个用户自定义的向导窗口在安装时是否可见，这样就可以通过上个窗口用户选择来决定下个窗口是否可见；其二：作为替换变量用，通常安装过程中收集的信息存放在变量中，然后，在安装程序进行到最后，利用变量的值来替换安装目标文件中的内容。</span></p>
<p>4. &#8230;.</p>
<p><span style="font-family: 宋体">决定，安装程序界面所支持的语言。</span></p>
<p>5. &#8230;&#8230;..</p>
<p><span style="font-family: 宋体">用于为安装界面指定图片或图标</span></p>
<p><span style="font-family: 宋体">用于指定用户自定义安装向导窗口定义</span>XML<span style="font-family: 宋体">文件的位置</span></p>
<p><span style="font-family: 宋体">用于指定安装向导窗口中国际化资源</span>XML<span style="font-family: 宋体">文件的位置</span></p>
<p><span style="font-family: 宋体">等等，例如：</span></p>
<p>&lt;resources&gt;</p>
<p>&lt;res src="langsel.jpg" id="installer.langsel.img" /&gt;</p>
<p>&lt;res src="readme.html" id="HTMLInfoPanel.info" parse="yes" type="plain" encoding="GB2312" /&gt;</p>
<p>&lt;res src="readme_chn.html" id="HTMLInfoPanel.info_chn" parse="yes" type="plain" encoding="GB2312" /&gt;</p>
<p>&lt;res src="license.html" id="HTMLLicencePanel.licence" parse="yes" type="plain" encoding="GB2312" /&gt;</p>
<p>&lt;res src="license_chn.html" id="HTMLLicencePanel.licence_chn" parse="yes" type="plain" encoding="GB2312" /&gt;</p>
<p>&lt;res src="shortcutSpec.xml" id="shortcutSpec.xml" parse="yes" type="xml" encoding="GB2312" /&gt;</p>
<p>&lt;res src="Unix_shortcutSpec.xml" id="Unix_shortcutSpec.xml" parse="yes" type="xml" encoding="GB2312" /&gt;</p>
<p>&lt;res src="packsLang.xml" id="packsLang.xml" /&gt;</p>
<p>&lt;res src="packsLang_chn.xml" id="packsLang.xml_chn" /&gt;</p>
<p>&lt;res src="UserInputSpec.xml" id="userInputSpec.xml" /&gt;</p>
<p>&lt;res src="UserInputLang.xml" id="userInputLang.xml" /&gt;</p>
<p>&lt;res src="UserInputLang_chn.xml" id="userInputLang.xml_chn" /&gt;</p>
<p>resources&gt; </p>
<p>6. &#8230;&#8230;. </p>
<p><span style="font-family: 宋体">本部分用于定义整个安装过程，每个</span>panel<span style="font-family: 宋体">即是一个安装向导窗口，</span>panel<span style="font-family: 宋体">是按顺序由</span>IzPack<span style="font-family: 宋体">调用的。</span>IzPack<span style="font-family: 宋体">内置了很多的</span>Panel<span style="font-family: 宋体">，另外它还支持用户自定义的功能，主要是通过</span>UserInputPanel<span style="font-family: 宋体">来实现的，你可以通过在&#8230;&#8230;中定义的</span>ID<span style="font-family: 宋体">为</span>UserInputSpec.xml<span style="font-family: 宋体">的资源</span>(XML)<span style="font-family: 宋体">中定义</span>UserInputPanel<span style="font-family: 宋体">窗口中用户录入项目及相关存放的变量。另外，</span>Izpack<span style="font-family: 宋体">支持条件用户自定义</span>Panel,<span style="font-family: 宋体">即</span>ConditionalUserInputPanel<span style="font-family: 宋体">，你可以在&#8230;</span>.<span style="font-family: 宋体">中通过变量来控制这样的向导窗口的可见性。当安装过程执行到</span>InstallPanel<span style="font-family: 宋体">时</span>IzPack<span style="font-family: 宋体">开始解压安装包到硬盘中，所以，一般来说所有的配置信息</span>(<span style="font-family: 宋体">例如，安装目录，安装包的选择等</span>)<span style="font-family: 宋体">都应在</span>InstallPanel<span style="font-family: 宋体">之前完成。在</span>InstallPanel<span style="font-family: 宋体">之后可以通过</span>ShortcutPanel<span style="font-family: 宋体">来显示快捷方式创建窗口，另外还可以通过</span>ProcessPanel<span style="font-family: 宋体">来执行一些后续操作。</span></p>
<p>&lt;panels&gt;</p>
<p>&lt;panel classname="HTMLLicencePanel" /&gt;</p>
<p>&lt;panel classname="HTMLInfoPanel" /&gt;</p>
<p>&lt;panel classname="TargetPanel" /&gt;</p>
<p>&lt;panel classname="PacksPanel" /&gt;</p>
<p>&lt;panel classname="UserInputPanel" /&gt;</p>
<p>&lt;panel classname="SummaryPanel" /&gt;</p>
<p>&lt;panel classname="InstallPanel" /&gt;</p>
<p>&lt;panel classname="ShortcutPanel" /&gt;</p>
<p>&lt;panel classname="SimpleFinishPanel" /&gt;</p>
<p>panels&gt; </p>
<p>7. &#8230;&#8230;. </p>
<p><span style="font-family: 宋体">本部分主要用于定义安装包，即将哪些文件进行打包，以及将来安装时如何进行安装。通过可以将应用程序文件分解成不同的安装包，可以指定哪些</span>pack<span style="font-family: 宋体">是必须安装的，哪些是可选的。</span></p>
<p><span style="font-family: 宋体">前边我们讲过，我们可以在中加入自定义向导窗口来允许用户指定一些配置，这些配置信息被存放到变量中，我们可以利用用户指定的值来替换应用程序中部分文件中的内容。那么在定义</span>pack<span style="font-family: 宋体">时，就可以指定哪些文件在安装时需要进行解析</span>(parseable)<span style="font-family: 宋体">。需要注意的，你需要指定需要解析的方式</span>(xml, javaprop, plain,shell)<span style="font-family: 宋体">，如查将</span>javaprop<span style="font-family: 宋体">类型的文件解析类型设定为</span>plain<span style="font-family: 宋体">的话，可以就有问题，例如：如果变量的值为路径，那么在可能就会有问题。</span></p>
<p><span style="font-family: 宋体">另，对于每一个</span>Pack<span style="font-family: 宋体">在它安装</span>(copy<span style="font-family: 宋体">文件</span>)<span style="font-family: 宋体">之后，可以定义它执行一个程序，例如脚本程序。你可以利用这种功能来做一些工作，例如：你可执行脚本程序来导入数据库数据等。</span></p>
<p><span style="font-family: 宋体">下面是一个示例：</span></p>
<p>&lt;packs&gt;</p>
<p>&lt;pack id="ToolKit" name="ToolKit" required="yes"&gt;</p>
<p><span style="font-family: 宋体">&#8230;&#8230;&#8230;&#8230;</span></p>
<p>pack&gt;</p>
<p>&lt;pack id="Core" name="Core" required="yes"&gt;</p>
<p>&lt;description&gt;<span style="font-family: 宋体">在</span>packsLang.xml<span style="font-family: 宋体">和</span>packsLang.xml_chn<span style="font-family: 宋体">中描述了</span>.description&gt;</p>
<p>&lt;fileset dir="app" targetdir="$INSTALL_PATH"app"&gt;</p>
<p>&lt;include name="*" /&gt;</p>
<p>&lt;include name="**" /&gt;</p>
<p>fileset&gt;</p>
<p>&lt;fileset dir="native" targetdir="$INSTALL_PATH"native"&gt;</p>
<p>&lt;include name="*" /&gt;</p>
<p>&lt;include name="**" /&gt;</p>
<p>fileset&gt;</p>
<p>&lt;file src="clear.db.splash.gif" targetdir="$INSTALL_PATH" /&gt;</p>
<p>&lt;file src="init.db.splash.gif" targetdir="$INSTALL_PATH" /&gt;</p>
<p>&lt;file src="installer.properties" targetdir="$INSTALL_PATH" /&gt;</p>
<p>&lt;file src="installer.xml" targetdir="$INSTALL_PATH" /&gt;</p>
<p>&lt;file src="installer.bat" targetdir="$INSTALL_PATH" /&gt;</p>
<p>&lt;file src="uninstaller.bat" targetdir="$INSTALL_PATH" /&gt;</p>
<p>&lt;parsable targetfile="$INSTALL_PATH/installer.properties" </p>
<p>type="javaprop" /&gt;</p>
<p>&amp; </p>
<img src ="http://www.blogjava.net/hengheng123456789/aggbug/142341.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.blogjava.net/hengheng123456789/" target="_blank">哼哼</a> 2007-09-03 15:48 <a href="http://www.blogjava.net/hengheng123456789/archive/2007/09/03/142341.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>Java中调用其它的程序</title><link>http://www.blogjava.net/hengheng123456789/archive/2007/09/03/142335.html</link><dc:creator>哼哼</dc:creator><author>哼哼</author><pubDate>Mon, 03 Sep 2007 07:44:00 GMT</pubDate><guid>http://www.blogjava.net/hengheng123456789/archive/2007/09/03/142335.html</guid><wfw:comment>http://www.blogjava.net/hengheng123456789/comments/142335.html</wfw:comment><comments>http://www.blogjava.net/hengheng123456789/archive/2007/09/03/142335.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.blogjava.net/hengheng123456789/comments/commentRss/142335.html</wfw:commentRss><trackback:ping>http://www.blogjava.net/hengheng123456789/services/trackbacks/142335.html</trackback:ping><description><![CDATA[&nbsp;
<p style="text-align: center" align="center">Java<span style="font-family: 宋体">中调用其它的程序</span></p>
<p>1<span style="font-family: 宋体">、运行外部程序：</span></p>
<p>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; Runtime.getRuntime().exec("notepad");</p>
<p>2<span style="font-family: 宋体">、运行系统内部命令：</span></p>
<p>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; Runtime.getRuntime().exec("command.com /c dir");</p>
<p>Runtime.getRuntime().exec("cmd xxx");</p>
<img src ="http://www.blogjava.net/hengheng123456789/aggbug/142335.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.blogjava.net/hengheng123456789/" target="_blank">哼哼</a> 2007-09-03 15:44 <a href="http://www.blogjava.net/hengheng123456789/archive/2007/09/03/142335.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>SVN Beginning</title><link>http://www.blogjava.net/hengheng123456789/archive/2007/09/03/142330.html</link><dc:creator>哼哼</dc:creator><author>哼哼</author><pubDate>Mon, 03 Sep 2007 07:40:00 GMT</pubDate><guid>http://www.blogjava.net/hengheng123456789/archive/2007/09/03/142330.html</guid><wfw:comment>http://www.blogjava.net/hengheng123456789/comments/142330.html</wfw:comment><comments>http://www.blogjava.net/hengheng123456789/archive/2007/09/03/142330.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.blogjava.net/hengheng123456789/comments/commentRss/142330.html</wfw:commentRss><trackback:ping>http://www.blogjava.net/hengheng123456789/services/trackbacks/142330.html</trackback:ping><description><![CDATA[&nbsp;
<p style="text-align: center" align="center">SVN Beginning</p>
<p><a href="http://blog.doesite.net/read.php?save_215">http://blog.doesite.net/read.php?save_215</a></p>
<p>1.<span style="font-family: 宋体">安装</span> subversion</p>
<p># apt-get install subversion subversion-tools</p>
<p><span style="font-family: 宋体">创建一个新的储存库：</span></p>
<p>#svnadmin create /svn/repository</p>
<p><span style="font-family: 宋体">在</span>/svn<span style="font-family: 宋体">目录创建一个新的空储存库，数据储存方式默认采用</span>Berkeley DB<span style="font-family: 宋体">。</span></p>
<p><span style="font-family: 宋体">导入你的源码：</span></p>
<p># svn import /svn/repository file:///data/svn/ldap</p>
<p><span style="font-family: 宋体">把</span>/data/ldap<span style="font-family: 宋体">整个目录导入到储存库中的</span>repository<span style="font-family: 宋体">目录中，储存库的</span>repository<span style="font-family: 宋体">目录会自动创建。</span></p>
<p><span style="font-family: 宋体">显示储存库内容：</span></p>
<p>mt@mtmt:~$ svn list file:///svn/repository</p>
<p>.cache/</p>
<p>.project</p>
<p>.projectOptions</p>
<p>.settings/</p>
<p>bbscnmo/</p>
<p>newcnmo/</p>
<p><span style="font-family: 宋体">显示目录内容，成功导入。</span></p>
<p><span style="font-family: 宋体">上面使用了</span>file:///<span style="font-family: 宋体">形式的</span>URL<span style="font-family: 宋体">来访问</span>Subversion<span style="font-family: 宋体">库，这表示在本地通过文件系统访问。但我们的</span>Subversion<span style="font-family: 宋体">库可能需要通过网络被其它用户访问，这就需要用到其它的协议，下表是</span>Subversion<span style="font-family: 宋体">支持的各种访问协议：</span></p>
<p><span style="font-family: 宋体">访问协议</span></p>
<p><span style="font-family: 宋体">协议</span> <span style="font-family: 宋体">访问方法</span></p>
<p>file:/// <span style="font-family: 宋体">通过本地磁盘访问。</span></p>
<p>http:// <span style="font-family: 宋体">与</span>Apache<span style="font-family: 宋体">组合，通过</span>WebDAV<span style="font-family: 宋体">协议访问。</span></p>
<p>https:// <span style="font-family: 宋体">同上，但支持</span>SSL<span style="font-family: 宋体">协议加密连接。</span></p>
<p>svn:// <span style="font-family: 宋体">通过</span>svnserve<span style="font-family: 宋体">服务自定义的协议访问。</span></p>
<p>svn+ssh:// <span style="font-family: 宋体">同上，但通过</span>SSH<span style="font-family: 宋体">协议加密连接。</span></p>
<p>2.<span style="font-family: 宋体">配置</span> subversion <span style="font-family: 宋体">与</span>Apache<span style="font-family: 宋体">组合通过</span>WebDAV<span style="font-family: 宋体">方式访问</span>Subversion<span style="font-family: 宋体">库</span></p>
<p># apt-get install apache2 libapache2-svn</p>
<p><span style="font-family: 宋体">配置文件位于</span>/etc/apache2/mods-enabled/<span style="font-family: 宋体">目录下，配置文件共有两个，分别是</span>dav_svn.conf<span style="font-family: 宋体">和</span>dav_svn.load<span style="font-family: 宋体">，</span>dav_svn.load<span style="font-family: 宋体">文件负责装载必要的模块，内容如下：</span></p>
<p># Load mod_dav_svn when apache starts</p>
<p>LoadModule dav_svn_module /usr/lib/apache2/modules/mod_dav_svn.so</p>
<p>LoadModule authz_svn_module /usr/lib/apache2/modules/mod_authz_svn.so</p>
<p><span style="font-family: 宋体">在装载</span>mod_dav_svn.so<span style="font-family: 宋体">前，必须先装载</span>mod_dav.so<span style="font-family: 宋体">模块。它由</span>dav.load<span style="font-family: 宋体">文件控制，内容如下：</span></p>
<p>LoadModule dav_module /usr/lib/apache2/modules/mod_dav.so</p>
<p>dav_svn.conf<span style="font-family: 宋体">是</span>mod_dav_svn.so<span style="font-family: 宋体">模块的配置文件，内容如下：</span></p>
<p># dav_svn.conf - Example Subversion/Apache configuration</p>
<p>#</p>
<p># For details and further options see the Apache user manual and</p>
<p># the Subversion book.</p>
<p># &#8230;</p>
<p># URL controls how the repository appears to the outside world.</p>
<p># In this example clients access the repository as http://hostname/svn/</p>
<p>#<span style="font-family: 宋体">设置访问路径</span></p>
<p># Uncomment this to enable the repository,</p>
<p>DAV svn #<span style="font-family: 宋体">启用</span>by siko</p>
<p># Set this to the path to your repository</p>
<p>SVNPath /data/subversion #<span style="font-family: 宋体">设置储存库路径，仅支持单个储存库，该路径要可被</span>Apache<span style="font-family: 宋体">进程访问。</span></p>
<p>#SVNParentPath /data/subversion #<span style="font-family: 宋体">如果</span>subversion<span style="font-family: 宋体">下有多个储存库，则用</span>SVNParentPath</p>
<p># The following allows for basic http authentication. Basic authentication</p>
<p># should not be considered secure for any particularly rigorous definition of</p>
<p># secure.</p>
<p># to create a passwd file #<span style="font-family: 宋体">按下面的步骤创建</span>Apache<span style="font-family: 宋体">用户验证文件</span></p>
<p># # rm -f /etc/apache2/dav_svn.passwd</p>
<p># # htpasswd2 -c /etc/apache2/dav_svn.passwd dwhedon</p>
<p># New password:</p>
<p># Re-type new password:</p>
<p># Adding password for user dwhedon</p>
<p># #</p>
<p># Uncomment the following 3 lines to enable Basic Authentication</p>
<p>AuthType Basic #<span style="font-family: 宋体">启用</span>Apache<span style="font-family: 宋体">基础验证</span></p>
<p>AuthName <span style="font-family: 宋体">&#8220;</span>Subversion Repository<span style="font-family: 宋体">&#8221;</span> #<span style="font-family: 宋体">设置验证框标题</span></p>
<p>AuthUserFile /etc/apache2/dav_svn.passwd #<span style="font-family: 宋体">指定验证用户文件名</span></p>
<p># Uncomment the following line to enable Authz Authentication</p>
<p>AuthzSVNAccessFile /etc/apache2/dav_svn.authz #<span style="font-family: 宋体">启用目录级别授权，</span>dav_svn.authz<span style="font-family: 宋体">是授权配置文档</span></p>
<p># The following three lines allow anonymous read, but make</p>
<p># committers authenticate themselves.</p>
<p>#</p>
<p>#<span style="font-family: 宋体">允许匿名访问，不允许</span>Commit<span style="font-family: 宋体">，不能与</span>AuthzSVNAccessFile<span style="font-family: 宋体">同时使用</span></p>
<p>Require valid-user</p>
<p>#</p>
<p><span style="font-family: 宋体">修改</span>/data/subversion<span style="font-family: 宋体">目录访问权限使它可被</span>Apache<span style="font-family: 宋体">进程访问，我的</span>Apache<span style="font-family: 宋体">是用</