Fckeditor完美结合Struts2【转载】

做如下几点说明: 
1.         本文所指的FckEditor是2.6.4,所指的Struts2是2.1.6 
2.         有关FckEditor的源代码分析,见:http://nileader.blog.51cto.com/1381108/301614 
3.         网上很多关于FckEditor在Jsp中的配置的文章,本文也是在笔者看了传智播客的fck视频后,有所改进的完成的。但是,笔者的观点的是现在纯Jsp的网站不是很多,因此Fck和Struts2的结合更为多见。如果纯jsp的小网站,建议163的编辑器大可搞定。 http://nileader.blog.51cto.com/1381108/302744 
4.         本文是作者一步一步配置的过程,并记录了作者在和Struts2过程中碰到的一些问题和解决方 法,供参考。
5.  建议和这篇文章一起看,效果更佳 http://nileader.blog.51cto.com/1381108/303234


5.       项目源代码: http://down.51cto.com/download.php?do=attachment&aid=120763&k=6b8f9716a1f697186a152ee7e03a68b3&t=1271986205 
Struts2环境构建 
网上关于如何构建Struts2环境的文章铺天盖地,这里不再赘述,只是提供给读者Struts2.1.6的一些jar包。 
  

下载地址是:http://down.51cto.com/download.php?do=attachment&aid=120757&k=2adb78a2c041f917b548ff1e6a58e53c&t=1271983135 
加入FckEditor 
Step1、下载Fckeditor2.6.4,下载地址是:http://down.51cto.com/download.php?do=attachment&aid=120751&k=f5b36d01d190c945186ec94b138e380b&t=1271981326 
Step2、解压后,把里面的fckeditor目录导入到项目的WebRoot目录下,结构如图: 

Step3、这步相当关键。 
导入fckeditor-java-core的jar包到项 目的WEB-INF/lib目录下,下载地址是:http://down.51cto.com/download.php?do=attachment&aid=120752&k=74632b54f5df3e3415f74b2a20c871e3&t=1271982128

导入以下4个文件: 

这里先别急,说明几点:

1.         这里的commons-fileupload-1.2.1.jar已经在上面Struts2中有所导入,所以不用导入。 
2.         这里的slf4j-api-1.5.8.jar和slf4j-simple-1.5.8必须保持版本一致。 
  
这里的三个包的下载地址是 : 
http://img1.51cto.com/attachment/201004/1381108_1271985600.rar 
Step4、在jsp页面中,添加如下标签声明: 
<%@ taglib uri="http://java.fckeditor.net" prefix="FCK"%> 
Body标签中加入你要放 置的fckeditor的位置:
<FCK:editor instanceName="articleAddEditor" basePath="/fckeditor" value=" " ></FCK:editor> 

好的,现在可以看到Fckeditor的真面目了。 


 Step1.   要上传文件,首先要配置  Web.xml
配置如下:

 

 
 
  1. <?xml version="1.0" encoding="UTF-8"?> 
  2.  
  3. <web-app version="2.4" 
  4. xmlns="http://java.sun.com/xml/ns/j2ee" 
  5.  
  6. xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
  7. xsi:schemaLocation="http://java.sun.com/xml/ns/j2ee 
  8. http://java.sun.com/xml/ns/j2ee/web-app_2_4.xsd"> 
  9.  
  10. <filter> 
  11. <filter-name>struts2</filter-name> 
  12. <!-- 控制器 --> 
  13. <filter-class> 
  14. org.apache.struts2.dispatcher.FilterDispatcher 
  15. </filter-class> 
  16.  
  17. </filter> 
  18.  
  19. <filter-mapping> 
  20. <filter-name>struts2</filter-name> 
  21. <!-- 任何请求均有过滤器 --> 
  22. <url-pattern>/*</url-pattern> 
  23. </filter-mapping> 
  24.  
  25. <servlet> 
  26. <servlet-name>Connector</servlet-name> 
  27. <servlet-class> 
  28. net.fckeditor.connector.ConnectorServlet 
  29. </servlet-class> 
  30. <load-on-startup>1</load-on-startup> 
  31. </servlet> 
  32.  
  33. <servlet-mapping> 
  34. <servlet-name>Connector</servlet-name> 
  35. <url-pattern> 
  36. /fckeditor/editor/filemanager/connectors/* 
  37. </url-pattern> 
  38. </servlet-mapping> 
  39. </web-app> 


Step2. 在src目录下新建一个fckeditor.properties文件,内容如下:

 
 
  1. connector.userActionImpl =net.fckeditor.requestcycle.impl.UserActionImpl 



好了,现在可以去页面上看看了,不过出错了:

或者是:

 

出现这个问题的原因是Fckeditor的拦截Servlet和Struts2的Servlet的冲突了。
解决方法是修改web.xml如下

 

 
 
  1. <?xml version="1.0" encoding="UTF-8"?> 
  2.  
  3. <web-app version="2.4" 
  4. xmlns="http://java.sun.com/xml/ns/j2ee" 
  5.  
  6. xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
  7. xsi:schemaLocation="http://java.sun.com/xml/ns/j2ee 
  8. http://java.sun.com/xml/ns/j2ee/web-app_2_4.xsd"> 
  9.  
  10.  
  11.  
  12. <filter> 
  13. <filter-name>struts2</filter-name> 
  14. <!-- 控制器 --> 
  15. <filter-class> 
  16. org.apache.struts2.dispatcher.FilterDispatcher 
  17. </filter-class> 
  18.  
  19. </filter> 
  20.  
  21. <filter-mapping> 
  22. <filter-name>struts2</filter-name> 
  23. <url-pattern>*.action</url-pattern> 
  24. </filter-mapping> 
  25. <filter-mapping> 
  26. <filter-name>struts2</filter-name> 
  27. <url-pattern>*.jsp</url-pattern> 
  28. </filter-mapping> 
  29. <filter-mapping> 
  30. <filter-name>struts2</filter-name> 
  31. <url-pattern>/struts/*</url-pattern> 
  32. </filter-mapping> 
  33. <welcome-file-list> 
  34. <welcome-file>default.jsp</welcome-file> 
  35. </welcome-file-list> 
  36. <servlet> 
  37. <servlet-name>Connector</servlet-name> 
  38. <servlet-class> 
  39. net.fckeditor.connector.ConnectorServlet 
  40. </servlet-class> 
  41. <load-on-startup>1</load-on-startup> 
  42. </servlet> 
  43.  
  44. <servlet-mapping> 
  45. <servlet-name>Connector</servlet-name> 
  46. <url-pattern> 
  47. /fckeditor/editor/filemanager/connectors/* 
  48. </url-pattern> 
  49. </servlet-mapping> 
  50.  
  51.  
  52. </web-app> 

使得Struts2的拦截器只拦截.jsp和.action的请求。

现在再到页面上去看看,可以上传了。

Step3.  改成随机数命名文件。


        由于fckeditor的文件上传功能主要是由web.xml中配置的 net.fckeditor.connector.ConnectorServlet这个类拦截的,所以我们要自己来重命名文件的话,就要修改这个类。
        办法是在net.fckeditor.connector.ConnectorServlet的基础上,建立自己的Servlet。

在项目src目录下建立以下包
cn.nileader.tool
里面建立两个类:

GetCode.java

 

 

 
 
  1. package com.rctraffic110.tool; 
  2.  
  3. import java.text.SimpleDateFormat; 
  4.  
  5. public class GetCode { 
  6.  
  7. /* 
  8. * 获取一个记录编号 
  9. * 格式:12 位时间+业务编号+随即数 
  10. * 例如:100330101028+04+893 (2010-03-30-10:20:28, 业务号是04, 随机数893 ) 
  11. *@param btype 业务类型编号 员工业务01 招聘业务02…… 
  12. *@return code 构造的一个记录编号 
  13. */ 
  14. public static String getNo(String btype){ 
  15. //返回的code 
  16. String code; 
  17. //系统当前时间 12位 
  18.  
  19. SimpleDateFormat sdf=new SimpleDateFormat("yyMMddhhmmss"); 
  20.  
  21. String nowDate=sdf.format(new java.util.Date()); 
  22. //随机数 
  23.  
  24. String iRandom = Math.round(Math.random()*900 )+100 +""; 
  25. //整合一个code 
  26. return nowDate + btype + iRandom ; 

上面这个类是个随机获取编号的方法。

再建立这个类
ConcectorServlet.java
 

 
 
  1. package com.rctraffic110.tool; 
  2.  
  3.  
  4. import java.io.File; 
  5. import java.io.IOException; 
  6. import java.io.PrintWriter; 
  7. import java.util.List; 
  8.  
  9. import javax.servlet.ServletException; 
  10. import javax.servlet.http.HttpServlet; 
  11. import javax.servlet.http.HttpServletRequest; 
  12. import javax.servlet.http.HttpServletResponse; 
  13.  
  14. import net.fckeditor.connector.Messages; 
  15. import net.fckeditor.handlers.CommandHandler; 
  16. import net.fckeditor.handlers.ConnectorHandler; 
  17. import net.fckeditor.handlers.ExtensionsHandler; 
  18. import net.fckeditor.handlers.RequestCycleHandler; 
  19. import net.fckeditor.handlers.ResourceTypeHandler; 
  20. import net.fckeditor.response.UploadResponse; 
  21. import net.fckeditor.response.XmlResponse; 
  22. import net.fckeditor.tool.Utils; 
  23. import net.fckeditor.tool.UtilsFile; 
  24. import net.fckeditor.tool.UtilsResponse; 
  25.  
  26. import org.apache.commons.fileupload.FileItem; 
  27. import org.apache.commons.fileupload.FileItemFactory; 
  28.  
  29. import org.apache.commons.fileupload.disk.DiskFileItemFactory; 
  30.  
  31. import org.apache.commons.fileupload.servlet.ServletFileUpload; 
  32. import org.apache.commons.io.FilenameUtils; 
  33. import org.slf4j.Logger; 
  34. import org.slf4j.LoggerFactory; 
  35.  
  36. public class ConnectorServlet extends HttpServlet { 
  37.  
  38. private static final long serialVersionUID = -5742008970929377161L; 
  39.  
  40. private static final Logger logger = LoggerFactory.getLogger(ConnectorServlet.class); 
  41.  
  42. public void init() throws ServletException, IllegalArgumentException { 
  43.  
  44. String realDefaultUserFilesPath = getServletContext().getRealPath( 
  45.  
  46. ConnectorHandler.getDefaultUserFilesPath()); 
  47.  
  48. File defaultUserFilesDir = new File(realDefaultUserFilesPath); 
  49. UtilsFile.checkDirAndCreate(defaultUserFilesDir); 
  50.  
  51. logger.info("ConnectorServlet successfully initialized!"); 
  52.  
  53. public void doGet(HttpServletRequest request, HttpServletResponse response) 
  54. throws ServletException, IOException { 
  55.  
  56. logger.debug("Entering ConnectorServlet#doGet"); 
  57.  
  58. response.setCharacterEncoding("UTF-8"); 
  59.  
  60. response.setContentType("application/xml; charset=UTF-8"); 
  61.  
  62. response.setHeader("Cache-Control""no-cache"); 
  63.  
  64. PrintWriter out = response.getWriter(); 
  65.  
  66. String commandStr = request.getParameter("Command"); 
  67.  
  68. String typeStr = request.getParameter("Type"); 
  69.  
  70. String currentFolderStr = request.getParameter("CurrentFolder"); 
  71.  
  72. logger.debug("Parameter Command: {}", commandStr); 
  73.  
  74. logger.debug("Parameter Type: {}", typeStr); 
  75.  
  76. logger.debug("Parameter CurrentFolder: {}", currentFolderStr); 
  77.  
  78. XmlResponse xr; 
  79.  
  80. if (!RequestCycleHandler.isEnabledForFileBrowsing(request)) 
  81.  
  82. xr = new XmlResponse(XmlResponse.EN_ERROR, Messages.NOT_AUTHORIZED_FOR_BROWSING); 
  83.  
  84. else if (!CommandHandler.isValidForGet(commandStr)) 
  85.  
  86. xr = new XmlResponse(XmlResponse.EN_ERROR, Messages.INVALID_COMMAND); 
  87.  
  88. else if (typeStr != null && !ResourceTypeHandler.isValid(typeStr)) 
  89.  
  90. xr = new XmlResponse(XmlResponse.EN_ERROR, Messages.INVALID_TYPE); 
  91.  
  92. else if (!UtilsFile.isValidPath(currentFolderStr)) 
  93.  
  94. xr = new XmlResponse(XmlResponse.EN_ERROR, Messages.INVALID_CURRENT_FOLDER); 
  95. else { 
  96.  
  97. CommandHandler command = CommandHandler.getCommand(commandStr); 
  98.  
  99. ResourceTypeHandler resourceType = ResourceTypeHandler.getDefaultResourceType(typeStr); 
  100.  
  101. String typePath = UtilsFile.constructServerSidePath(request, resourceType); 
  102.  
  103. String typeDirPath = getServletContext().getRealPath(typePath); 
  104.  
  105. File typeDir = new File(typeDirPath); 
  106. UtilsFile.checkDirAndCreate(typeDir); 
  107.  
  108. File currentDir = new File(typeDir, currentFolderStr); 
  109.  
  110. if (!currentDir.exists()) 
  111.  
  112. xr = new XmlResponse(XmlResponse.EN_INVALID_FOLDER_NAME); 
  113. else { 
  114.  
  115. xr = new XmlResponse(command, resourceType, currentFolderStr, UtilsResponse 
  116.  
  117. .constructResponseUrl(request, resourceType, currentFolderStr, true
  118. ConnectorHandler.isFullUrl())); 
  119.  
  120. if (command.equals(CommandHandler.GET_FOLDERS)) 
  121. xr.setFolders(currentDir); 
  122.  
  123. else if (command.equals(CommandHandler.GET_FOLDERS_AND_FILES)) 
  124. xr.setFoldersAndFiles(currentDir); 
  125.  
  126. else if (command.equals(CommandHandler.CREATE_FOLDER)) { 
  127.  
  128. String newFolderStr = UtilsFile.sanitizeFolderName(request 
  129.  
  130. .getParameter("NewFolderName")); 
  131.  
  132. logger.debug("Parameter NewFolderName: {}", newFolderStr); 
  133.  
  134. File newFolder = new File(currentDir, newFolderStr); 
  135.  
  136. int errorNumber = XmlResponse.EN_UKNOWN; 
  137.  
  138. if (newFolder.exists()) 
  139.  
  140. errorNumber = XmlResponse.EN_ALREADY_EXISTS; 
  141.  
  142. else { 
  143.  
  144. try { 
  145.  
  146. errorNumber = (newFolder.mkdir()) ? XmlResponse.EN_OK 
  147. : XmlResponse.EN_INVALID_FOLDER_NAME; 
  148.  
  149. catch (SecurityException e) { 
  150.  
  151. errorNumber = XmlResponse.EN_SECURITY_ERROR; 
  152. xr.setError(errorNumber); 
  153.  
  154. out.print(xr); 
  155. out.flush(); 
  156. out.close(); 
  157.  
  158. logger.debug("Exiting ConnectorServlet#doGet"); 
  159.  
  160. @SuppressWarnings("unchecked"
  161.  
  162. public void doPost(HttpServletRequest request, HttpServletResponse response) 
  163. throws ServletException, IOException { 
  164.  
  165. logger.debug("Entering Connector#doPost"); 
  166.  
  167. response.setCharacterEncoding("UTF-8"); 
  168.  
  169. response.setContentType("text/html; charset=UTF-8"); 
  170.  
  171. response.setHeader("Cache-Control""no-cache"); 
  172.  
  173. PrintWriter out = response.getWriter(); 
  174.  
  175. String commandStr = request.getParameter("Command"); 
  176.  
  177. String typeStr = request.getParameter("Type"); 
  178.  
  179. String currentFolderStr = request.getParameter("CurrentFolder"); 
  180.  
  181. logger.debug("Parameter Command: {}", commandStr); 
  182.  
  183. logger.debug("Parameter Type: {}", typeStr); 
  184.  
  185. logger.debug("Parameter CurrentFolder: {}", currentFolderStr); 
  186.  
  187. UploadResponse ur; 
  188.  
  189. // if this is a QuickUpload request, 'commandStr' and 'currentFolderStr' 
  190.  
  191. // are empty 
  192.  
  193. if (Utils.isEmpty(commandStr) && Utils.isEmpty(currentFolderStr)) { 
  194. commandStr = "QuickUpload"
  195.  
  196. currentFolderStr = "/"
  197.  
  198. if (!RequestCycleHandler.isEnabledForFileUpload(request)) 
  199.  
  200. ur = new UploadResponse(UploadResponse.SC_SECURITY_ERROR, nullnull
  201. Messages.NOT_AUTHORIZED_FOR_UPLOAD); 
  202. else if (!CommandHandler.isValidForPost(commandStr)) 
  203.  
  204. ur = new UploadResponse(UploadResponse.SC_ERROR, nullnull, Messages.INVALID_COMMAND); 
  205.  
  206. else if (typeStr != null && !ResourceTypeHandler.isValid(typeStr)) 
  207.  
  208. ur = new UploadResponse(UploadResponse.SC_ERROR, nullnull, Messages.INVALID_TYPE); 
  209.  
  210. else if (!UtilsFile.isValidPath(currentFolderStr)) 
  211.  
  212. ur = UploadResponse.UR_INVALID_CURRENT_FOLDER; 
  213. else { 
  214.  
  215. ResourceTypeHandler resourceType = ResourceTypeHandler.getDefaultResourceType(typeStr); 
  216.  
  217. String typePath = UtilsFile.constructServerSidePath(request, resourceType); 
  218.  
  219. String typeDirPath = getServletContext().getRealPath(typePath); 
  220.  
  221. File typeDir = new File(typeDirPath); 
  222. UtilsFile.checkDirAndCreate(typeDir); 
  223.  
  224. File currentDir = new File(typeDir, currentFolderStr); 
  225.  
  226. if (!currentDir.exists()) 
  227.  
  228. ur = UploadResponse.UR_INVALID_CURRENT_FOLDER; 
  229. else { 
  230.  
  231. String newFilename = null
  232.  
  233. FileItemFactory factory = new DiskFileItemFactory(); 
  234.  
  235. ServletFileUpload upload = new ServletFileUpload(factory); 
  236.  
  237. upload.setHeaderEncoding("UTF-8"); 
  238. try { 
  239.  
  240. List<FileItem> items = upload.parseRequest(request); 
  241.  
  242. // We upload only one file at the same time 
  243.  
  244. FileItem uplFile = items.get(0); 
  245.  
  246. String rawName = UtilsFile.sanitizeFileName(uplFile.getName()); 
  247.  
  248. String filename = FilenameUtils.getName(rawName); 
  249.  
  250. String baseName = FilenameUtils.removeExtension(filename); 
  251.  
  252. String extension = FilenameUtils.getExtension(filename); 
  253.  
  254. filename = GetCode.getNo("1104" )+"."+extension; 
  255.  
  256. if (!ExtensionsHandler.isAllowed(resourceType, extension)) 
  257.  
  258. ur = new UploadResponse(UploadResponse.SC_INVALID_EXTENSION); 
  259.  
  260. else { 
  261.  
  262. // construct an unique file name 
  263.  
  264. File pathToSave = new File(currentDir, filename); 
  265. int counter = 1
  266.  
  267. while (pathToSave.exists()) { 
  268.  
  269. newFilename = baseName.concat("(").concat(String.valueOf(counter)) 
  270.  
  271. .concat(")").concat(".").concat(extension); 
  272.  
  273. pathToSave = new File(currentDir, newFilename); 
  274. counter++; 
  275.  
  276. if (Utils.isEmpty(newFilename)) 
  277.  
  278. ur = new UploadResponse(UploadResponse.SC_OK, UtilsResponse 
  279.  
  280. .constructResponseUrl(request, resourceType, currentFolderStr, 
  281.  
  282. true, ConnectorHandler.isFullUrl()).concat(filename)); 
  283. else 
  284.  
  285. ur = new UploadResponse(UploadResponse.SC_RENAMED, 
  286.  
  287. UtilsResponse.constructResponseUrl(request, resourceType, 
  288.  
  289. currentFolderStr, true, ConnectorHandler.isFullUrl()) 
  290.  
  291. .concat(newFilename), newFilename); 
  292.  
  293. // secure image check 
  294.  
  295. if (resourceType.equals(ResourceTypeHandler.IMAGE) 
  296.  
  297. && ConnectorHandler.isSecureImageUploads()) { 
  298.  
  299. if (UtilsFile.isImage(uplFile.getInputStream())) 
  300. uplFile.write(pathToSave); 
  301.  
  302. else { 
  303. uplFile.delete(); 
  304.  
  305. ur = new UploadResponse(UploadResponse.SC_INVALID_EXTENSION); 
  306.  
  307. else 
  308. uplFile.write(pathToSave); 
  309.  
  310.  
  311. catch (Exception e) { 
  312.  
  313. ur = new UploadResponse(UploadResponse.SC_SECURITY_ERROR); 
  314.  
  315.  
  316. out.print(ur); 
  317. out.flush(); 
  318. out.close(); 
  319.  
  320. logger.debug("Exiting Connector#doPost"); 
  321.  


目录结构为:


再修改web.xml中的Servlet如下:

 
 
  1. <servlet> 
  2. <servlet-name>Connector</servlet-name> 
  3. <servlet-class> 
  4. cn.nileader.tool.ConnectorServlet 
  5. </servlet-class> 
  6. <load-on-startup>1</load-on-startup> 
  7. </servlet> 



效果如下:

 

 

 

 

下载地址 :http://download.csdn.net/user/advance1989 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
FCKEDITOR中文使用说明 ==============================首先,FCKEDITOR的性能是非常好的,用户只需很少的时间就可以载入FCKEDITOR所需文件.对于其他在线编辑器来说,这几乎是个很难解决的难题,因为在开启编辑器时需要装载太多的文件.比如CUTEEDITOR,虽然功能比FCKEDITOR还要强大,可是,它本身也够庞大了,至于FREETEXTBOX等,其易用性与FCKEDITOR相比,尚有差距,可以说,FCKEDITOR是一个别具匠心的在线编辑器,它里面融入了作者高深的面向对象的JAVASCRIPT功力,集易用性与强大的功能与一体..与编辑器相关的所有图像,脚本以及调用页.语言文件.编辑器的皮肤文件.工具样的贴图等这些将导致在服务器和客户端间产生相当的流量.如果有许多文件被调用,那么即便每个文件很小.也会让用户等得不耐烦.在2.0版中,开发人员有两种方法来解决这个问题.那就是指定装载顺序和脚本压缩装载顺序从2.0版开始,编辑器按以下步骤装载资源:.基本页(就是编辑器所在页)以及装入编辑器的JS脚本.用来建立编辑器的脚本.编辑器的语言和皮肤..建立编辑器..载入预置的编辑文档内容..从现在开始,用户可以阅读和编辑文档了,不过,拖拽支持以及工具栏都是不可用的.载入编辑器引擎脚本.建立工具栏,并且可用.从现在开始,编辑器的所有功能都已经完整.载入工具栏图标脚本压缩在打包任何新版本时,编辑器的JS脚本将会进行预处理.预处理步骤如下:.移除所有代码注释.移除所有无用的空白字符..将脚本合并成几个文件使用上面的方法,我们可以将脚本文件的大小压缩到原来的50%.压缩后,原始的代码仍然存在于一个名为_Source的文件夹中
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值