SpringMvc + Jsp+ 富文本 kindeditor 进行 图片ftp上传nginx服务器 实现
一:html 原生态的附件上传
二:实现逻辑分析;
1.1.1 需求分析
Common.js
1、绑定事件
2、初始化参数
3、上传图片的url:
/pic/upload
4、上图片参数名称:
uploadFile
5、返回结果数据类型json
参考文档:
http://kindeditor.net/docs/upload.html
返回格式(JSON)
1 //成功时 2 3 { 4 5 "error" : 0, 6 7 "url" : "http://www.example.com/path/to/file.ext" 8 9 } 10 11 //失败时 12 13 { 14 15 "error" : 1, 16 17 "message" : "错误信息" 18 19 } 20
6 Service
7: Controller
8:需要引入的jar包的maven 配置参数:
1 <project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 2 xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd"> 3 4 <artifactId>taotao-common</artifactId> 5 <!-- jar包依赖 --> 6 <dependencies> 7 <!-- 时间操作组件 --> 8 <dependency> 9 <groupId>joda-time</groupId> 10 <artifactId>joda-time</artifactId> 11 </dependency> 12 <!-- Apache工具组件 --> 13 14 <dependency> 15 <groupId>org.apache.commons</groupId> 16 <artifactId>commons-io</artifactId> 17 </dependency> 18 <dependency> 19 <groupId>commons-net</groupId> 20 <artifactId>commons-net</artifactId> 21 </dependency> 22 <!-- Jackson Json处理工具包 --> 23 <dependency> 24 <groupId>com.fasterxml.jackson.core</groupId> 25 <artifactId>jackson-databind</artifactId> 26 </dependency> 27 <!-- 文件上传组件 --> 28 <dependency> 29 <groupId>commons-fileupload</groupId> 30 <artifactId>commons-fileupload</artifactId> 31 </dependency> 32 33 </dependencies> 34 35 36 </project>
三:逻辑实现:
1:前端实现:
1 <%@ page language="java" contentType="text/html; charset=UTF-8" pageEncoding="UTF-8"%> 2 <link href="/js/kindeditor-4.1.10/themes/default/default.css" type="text/css" rel="stylesheet"> 3 <script type="text/javascript" charset="utf-8" src="/js/kindeditor-4.1.10/kindeditor-all-min.js"></script> 4 <script type="text/javascript" charset="utf-8" src="/js/kindeditor-4.1.10/lang/zh_CN.js"></script> 5 <div style="padding:10px 10px 10px 10px"> 6 <form id="itemAddForm" class="itemForm" method="post"> 7 <table cellpadding="5"> 8 <tr> 9 <td>商品类目:</td> 10 <td> 11 <a href="javascript:void(0)" class="easyui-linkbutton selectItemCat">选择类目</a> 12 <input type="hidden" name="cid" style="width: 280px;"></input> 13 </td> 14 </tr> 15 <tr> 16 <td>商品标题:</td> 17 <td><input class="easyui-textbox" type="text" name="title" data-options="required:true" style="width: 280px;"></input></td> 18 </tr> 19 <tr> 20 <td>商品卖点:</td> 21 <td><input class="easyui-textbox" name="sellPoint" data-options="multiline:true,validType:'length[0,150]'" style="height:60px;width: 280px;"></input></td> 22 </tr> 23 <tr> 24 <td>商品价格:</td> 25 <td><input class="easyui-numberbox" type="text" name="priceView" data-options="min:1,max:99999999,precision:2,required:true" /> 26 <input type="hidden" name="price"/> 27 </td> 28 </tr> 29 <tr> 30 <td>库存数量:</td> 31 <td><input class="easyui-numberbox" type="text" name="num" data-options="min:1,max:99999999,precision:0,required:true" /></td> 32 </tr> 33 <tr> 34 <td>条形码:</td> 35 <td> 36 <input class="easyui-textbox" type="text" name="barcode" data-options="validType:'length[1,30]'" /> 37 </td> 38 </tr> 39 <tr> 40 <td>商品图片:</td> 41 <td> 42 <a href="javascript:void(0)" class="easyui-linkbutton picFileUpload">上传图片</a> 43 <input type="hidden" name="image"/> 44 </td> 45 </tr> 46 <tr> 47 <td>商品描述:</td> 48 <td> 49 <textarea style="width:800px;height:300px;visibility:hidden;" name="desc"></textarea> 50 </td> 51 </tr> 52 <tr class="params hide"> 53 <td>商品规格:</td> 54 <td> 55 56 </td> 57 </tr> 58 </table> 59 <input type="hidden" name="itemParams"/> 60 </form> 61 <div style="padding:5px"> 62 <a href="javascript:void(0)" class="easyui-linkbutton" onclick="submitForm()">提交</a> 63 <a href="javascript:void(0)" class="easyui-linkbutton" onclick="clearForm()">重置</a> 64 </div> 65 </div> 66 <script type="text/javascript"> 67 var itemAddEditor ; 68 //页面初始化完毕后执行此方法 69 $(function(){ 70 //创建富文本编辑器 71 itemAddEditor = TAOTAO.createEditor("#itemAddForm [name=desc]"); 72 //初始化类目选择和图片上传器 73 TAOTAO.init({fun:function(node){ 74 //根据商品的分类id取商品 的规格模板,生成规格信息。第四天内容。 75 //TAOTAO.changeItemParam(node, "itemAddForm"); 76 }}); 77 }); 78 //提交表单 79 function submitForm(){ 80 //有效性验证 81 if(!$('#itemAddForm').form('validate')){ 82 $.messager.alert('提示','表单还未填写完成!'); 83 return ; 84 } 85 //取商品价格,单位为“分” 86 $("#itemAddForm [name=price]").val(eval($("#itemAddForm [name=priceView]").val()) * 100); 87 //同步文本框中的商品描述 88 itemAddEditor.sync(); 89 //取商品的规格 90 /* 91 var paramJson = []; 92 $("#itemAddForm .params li").each(function(i,e){ 93 var trs = $(e).find("tr"); 94 var group = trs.eq(0).text(); 95 var ps = []; 96 for(var i = 1;i<trs.length;i++){ 97 var tr = trs.eq(i); 98 ps.push({ 99 "k" : $.trim(tr.find("td").eq(0).find("span").text()), 100 "v" : $.trim(tr.find("input").val()) 101 }); 102 } 103 paramJson.push({ 104 "group" : group, 105 "params": ps 106 }); 107 }); 108 //把json对象转换成字符串 109 paramJson = JSON.stringify(paramJson); 110 $("#itemAddForm [name=itemParams]").val(paramJson); 111 */ 112 //ajax的post方式提交表单 113 //$("#itemAddForm").serialize()将表单序列号为key-value形式的字符串 114 $.post("/item/save",$("#itemAddForm").serialize(), function(data){ 115 if(data.status == 200){ 116 $.messager.alert('提示','新增商品成功!'); 117 } 118 }); 119 } 120 121 function clearForm(){ 122 $('#itemAddForm').form('reset'); 123 itemAddEditor.html(''); 124 } 125 </script> 126
commom.js
1 Date.prototype.format = function(format){ 2 var o = { 3 "M+" : this.getMonth()+1, //month 4 "d+" : this.getDate(), //day 5 "h+" : this.getHours(), //hour 6 "m+" : this.getMinutes(), //minute 7 "s+" : this.getSeconds(), //second 8 "q+" : Math.floor((this.getMonth()+3)/3), //quarter 9 "S" : this.getMilliseconds() //millisecond 10 }; 11 if(/(y+)/.test(format)){ 12 format = format.replace(RegExp.$1, (this.getFullYear()+"").substr(4 - RegExp.$1.length)); 13 } 14 for(var k in o) { 15 if(new RegExp("("+ k +")").test(format)){ 16 format = format.replace(RegExp.$1, RegExp.$1.length==1 ? o[k] : ("00"+ o[k]).substr((""+ o[k]).length)); 17 } 18 } 19 return format; 20 }; 21 22 var TT = TAOTAO = { 23 // 编辑器参数 24 kingEditorParams : { 25 //指定上传文件参数名称 26 filePostName : "uploadFile", 27 //指定上传文件请求的url。 28 uploadJson : '/pic/upload', 29 //上传类型,分别为image、flash、media、file 30 dir : "image" 31 }, 32 // 格式化时间 33 formatDateTime : function(val,row){ 34 var now = new Date(val); 35 return now.format("yyyy-MM-dd hh:mm:ss"); 36 }, 37 // 格式化连接 38 formatUrl : function(val,row){ 39 if(val){ 40 return "<a href='"+val+"' target='_blank'>查看</a>"; 41 } 42 return ""; 43 }, 44 // 格式化价格 45 formatPrice : function(val,row){ 46 return (val/1000).toFixed(2); 47 }, 48 // 格式化商品的状态 49 formatItemStatus : function formatStatus(val,row){ 50 if (val == 1){ 51 return '正常'; 52 } else if(val == 2){ 53 return '<span style="color:red;">下架</span>'; 54 } else { 55 return '未知'; 56 } 57 }, 58 59 init : function(data){ 60 // 初始化图片上传组件 61 this.initPicUpload(data); 62 // 初始化选择类目组件 63 this.initItemCat(data); 64 }, 65 // 初始化图片上传组件 66 initPicUpload : function(data){ 67 $(".picFileUpload").each(function(i,e){ 68 var _ele = $(e); 69 _ele.siblings("div.pics").remove(); 70 _ele.after('\ 71 <div class="pics">\ 72 <ul></ul>\ 73 </div>'); 74 // 回显图片 75 if(data && data.pics){ 76 var imgs = data.pics.split(","); 77 for(var i in imgs){ 78 if($.trim(imgs[i]).length > 0){ 79 _ele.siblings(".pics").find("ul").append("<li><a href='"+imgs[i]+"' target='_blank'><img src='"+imgs[i]+"' width='80' height='50' /></a></li>"); 80 } 81 } 82 } 83 //给“上传图片按钮”绑定click事件 84 $(e).click(function(){ 85 var form = $(this).parentsUntil("form").parent("form"); 86 //打开图片上传窗口 87 KindEditor.editor(TT.kingEditorParams).loadPlugin('multiimage',function(){ 88 var editor = this; 89 editor.plugin.multiImageDialog({ 90 clickFn : function(urlList) { 91 var imgArray = []; 92 KindEditor.each(urlList, function(i, data) { 93 imgArray.push(data.url); 94 form.find(".pics ul").append("<li><a href='"+data.url+"' target='_blank'><img src='"+data.url+"' width='80' height='50' /></a></li>"); 95 }); 96 form.find("[name=image]").val(imgArray.join(",")); 97 editor.hideDialog(); 98 } 99 }); 100 }); 101 }); 102 }); 103 }, 104 105 // 初始化选择类目组件 106 initItemCat : function(data){ 107 $(".selectItemCat").each(function(i,e){ 108 var _ele = $(e); 109 if(data && data.cid){ 110 _ele.after("<span style='margin-left:10px;'>"+data.cid+"</span>"); 111 }else{ 112 _ele.after("<span style='margin-left:10px;'></span>"); 113 } 114 _ele.unbind('click').click(function(){ 115 $("<div>").css({padding:"5px"}).html("<ul>") 116 .window({ 117 width:'500', 118 height:"450", 119 modal:true, 120 closed:true, 121 iconCls:'icon-save', 122 title:'选择类目', 123 onOpen : function(){ 124 var _win = this; 125 $("ul",_win).tree({ 126 url:'/item/cat/list', 127 animate:true, 128 onClick : function(node){ 129 if($(this).tree("isLeaf",node.target)){ 130 // 填写到cid中 131 _ele.parent().find("[name=cid]").val(node.id); 132 _ele.next().text(node.text).attr("cid",node.id); 133 $(_win).window('close'); 134 if(data && data.fun){ 135 data.fun.call(this,node); 136 } 137 } 138 } 139 }); 140 }, 141 onClose : function(){ 142 $(this).window("destroy"); 143 } 144 }).window('open'); 145 }); 146 }); 147 }, 148 149 createEditor : function(select){ 150 return KindEditor.create(select, TT.kingEditorParams); 151 }, 152 153 /** 154 * 创建一个窗口,关闭窗口后销毁该窗口对象。<br/> 155 * 156 * 默认:<br/> 157 * width : 80% <br/> 158 * height : 80% <br/> 159 * title : (空字符串) <br/> 160 * 161 * 参数:<br/> 162 * width : <br/> 163 * height : <br/> 164 * title : <br/> 165 * url : 必填参数 <br/> 166 * onLoad : function 加载完窗口内容后执行<br/> 167 * 168 * 169 */ 170 createWindow : function(params){ 171 $("<div>").css({padding:"5px"}).window({ 172 width : params.width?params.width:"80%", 173 height : params.height?params.height:"80%", 174 modal:true, 175 title : params.title?params.title:"", 176 href : params.url, 177 onClose : function(){ 178 $(this).window("destroy"); 179 }, 180 onLoad : function(){ 181 if(params.onLoad){ 182 params.onLoad.call(this); 183 } 184 } 185 }).window("open"); 186 }, 187 188 closeCurrentWindow : function(){ 189 $(".panel-tool-close").click(); 190 }, 191 192 changeItemParam : function(node,formId){ 193 $.getJSON("/item/param/query/itemcatid/" + node.id,function(data){ 194 if(data.status == 200 && data.data){ 195 $("#"+formId+" .params").show(); 196 var paramData = JSON.parse(data.data.paramData); 197 var html = "<ul>"; 198 for(var i in paramData){ 199 var pd = paramData[i]; 200 html+="<li><table>"; 201 html+="<tr><td colspan=\"2\" class=\"group\">"+pd.group+"</td></tr>"; 202 203 for(var j in pd.params){ 204 var ps = pd.params[j]; 205 html+="<tr><td class=\"param\"><span>"+ps+"</span>: </td><td><input autocomplete=\"off\" type=\"text\"/></td></tr>"; 206 } 207 208 html+="</li></table>"; 209 } 210 html+= "</ul>"; 211 $("#"+formId+" .params td").eq(1).html(html); 212 }else{ 213 $("#"+formId+" .params").hide(); 214 $("#"+formId+" .params td").eq(1).empty(); 215 } 216 }); 217 }, 218 getSelectionsIds : function (select){ 219 var list = $(select); 220 var sels = list.datagrid("getSelections"); 221 var ids = []; 222 for(var i in sels){ 223 ids.push(sels[i].id); 224 } 225 ids = ids.join(","); 226 return ids; 227 }, 228 229 /** 230 * 初始化单图片上传组件 <br/> 231 * 选择器为:.onePicUpload <br/> 232 * 上传完成后会设置input内容以及在input后面追加<img> 233 */ 234 initOnePicUpload : function(){ 235 $(".onePicUpload").click(function(){ 236 var _self = $(this); 237 KindEditor.editor(TT.kingEditorParams).loadPlugin('image', function() { 238 this.plugin.imageDialog({ 239 showRemote : false, 240 clickFn : function(url, title, width, height, border, align) { 241 var input = _self.siblings("input"); 242 input.parent().find("img").remove(); 243 input.val(url); 244 input.after("<a href='"+url+"' target='_blank'><img src='"+url+"' width='80' height='50'/></a>"); 245 this.hideDialog(); 246 } 247 }); 248 }); 249 }); 250 } 251 }; 252
2:后台的逻辑实现
2-1: ftp配置文件
1 FTP_ADDRESS=192.168.1.5 2 FTP_PORT=21 3 FTP_USERNAME=ftpuser 4 FTP_PASSWORD=123456 5 FTP_BASEPATH=/home/ftpuser/www/images/ 6 IMAGE_BASE_URL=http://192.168.1.5/images/ 7
引入到SpringMVC.xml配置文件中
2-2:SpringMvc.xml的实现配置
1 2 <!-- 定义文件上传解析器 --> 3 <bean id="multipartResolver" 4 class="org.springframework.web.multipart.commons.CommonsMultipartResolver"> 5 <!-- 设定默认编码 --> 6 <property name="defaultEncoding" value="UTF-8"></property> 7 <!-- 设定文件上传的最大值5MB,5*1024*1024 --> 8 <property name="maxUploadSize" value="5242880"></property> 9 </bean> 10 11
2-3:controller层实现:
1 package com.taotao.controller; 2 3 import java.util.Map; 4 5 import org.springframework.beans.factory.annotation.Autowired; 6 import org.springframework.stereotype.Controller; 7 import org.springframework.web.bind.annotation.RequestMapping; 8 import org.springframework.web.bind.annotation.ResponseBody; 9 import org.springframework.web.multipart.MultipartFile; 10 11 import com.taotao.common.utils.JsonUtils; 12 import com.taotao.service.PictureService; 13 14 /** 15 * 16 * @ClassName: PictureController 17 * @Description:上传图片处理 18 * @author: 刘军/shall_liu(1136808529@qq.com) 19 * @date: 2017年8月26日 下午4:03:42 20 * 21 * @Copyright: 2017 22 */ 23 @Controller 24 public class PictureController { 25 26 @Autowired 27 private PictureService pictureService; 28 29 /** 30 * 31 * @Title: pictureUpload 32 * @Description: 接收图片上传服务 33 * @param: @param uploadFile 34 * @param: @return 35 * @return: Map 36 * @throws 37 */ 38 @RequestMapping("/pic/upload") 39 @ResponseBody 40 public String pictureUpload(MultipartFile uploadFile){ 41 Map result =pictureService.uploadPicture(uploadFile); 42 //为了保证能的兼容性,需要把 Result转换成json格式的字符串 43 String json= JsonUtils.objectToJson(result); 44 return json; 45 } 46 47 48 49 50 } 51
2_-4: service 层实现
1 package com.taotao.service; 2 3 import java.util.Map; 4 5 import org.springframework.web.multipart.MultipartFile; 6 7 /** 8 * 9 * @ClassName: PictureService 10 * @Description: 图片生成接口 11 * 12 * @author: 刘军/shall_liu(1136808529@qq.com) 13 * @date: 2017年8月26日 下午2:29:35 14 * 15 * @Copyright: 2017 16 */ 17 public interface PictureService { 18 19 /** 20 * 21 * @Title: uploadPicture 22 * @Description: 生成图片接口 23 * @param: @param uploadFile 24 * @param: @return 25 * @return: Map 26 * @throws 27 */ 28 Map uploadPicture(MultipartFile uploadFile); 29 30 31 32 } 33
1 package com.taotao.service.impl; 2 3 import java.io.IOException; 4 import java.util.HashMap; 5 import java.util.Map; 6 7 import org.apache.ibatis.annotations.ResultMap; 8 import org.joda.time.DateTime; 9 import org.springframework.beans.factory.annotation.Value; 10 import org.springframework.stereotype.Service; 11 import org.springframework.web.multipart.MultipartFile; 12 13 import com.mysql.jdbc.ResultSetMetaData; 14 import com.taotao.common.utils.FtpUtil; 15 import com.taotao.common.utils.IDUtils; 16 import com.taotao.service.PictureService; 17 /** 18 * 19 * @ClassName: PictureServiceImpl 20 * @Description:图片上传 服务 21 * @author: 刘军/shall_liu(1136808529@qq.com) 22 * @date: 2017年8月26日 下午2:33:25 23 * 24 * @Copyright: 2017 25 */ 26 @Service 27 public class PictureServiceImpl implements PictureService{ 28 /** 29 * 实现原理: 30 * 利用了springMvc的加载properties的一套实现工具的机制 31 * 使用注解@value 自动注入properties的参数信息 32 * 33 * ftp ip 访问地址 34 */ 35 @Value("${FTP_ADDRESS}") 36 private String FTP_ADDRESS; 37 /** 38 * ftp 服务端口 39 */ 40 @Value("${FTP_PORT}") 41 private String FTP_PORT; 42 /** 43 * ftp 登录用户名 44 */ 45 @Value("${FTP_USERNAME}") 46 private String FTP_USERNAME; 47 /** 48 * ftp 登录密码 49 */ 50 @Value("${FTP_PASSWORD}") 51 private String FTP_PASSWORD; 52 /** 53 * ftp 保存文件的跟文件路径 54 */ 55 @Value("${FTP_BASEPATH}") 56 private String FTP_BASEPATH; 57 /** 58 * 图片服务器的基础URL 59 */ 60 @Value("${IMAGE_BASE_URL}") 61 private String IMAGE_BASE_URL; 62 63 64 65 /** 66 * 67 * <p>Title: uploadPicture</p> 68 * <p>Description: </p> 图片上传的实现 69 * @param uploadFile 70 * @return 71 * @see com.taotao.service.PictureService#uploadPicture(org.springframework.web.multipart.MultipartFile) 72 */ 73 @Override 74 public Map uploadPicture(MultipartFile uploadFile) { 75 Map resultMap =new HashMap<>(); 76 try { 77 /* 78 * 生成一个新的文件名 79 */ 80 //取原文件名 81 String oldName=uploadFile.getOriginalFilename(); 82 //生成新文件名 83 String newName = IDUtils.genImageName(); 84 newName=newName+oldName.substring(oldName.indexOf("."), oldName.length()); 85 // 图片上传 86 String imagePath=new DateTime().toString("/yyyy/MM/dd"); 87 System.out.println(FTP_PORT); 88 boolean result= FtpUtil.uploadFile(FTP_ADDRESS,Integer.parseInt(FTP_PORT.trim()) , FTP_USERNAME, FTP_PASSWORD, FTP_BASEPATH, imagePath, newName, uploadFile.getInputStream()); 89 if(!result){ 90 resultMap.put("error", 1); 91 resultMap.put("message", "文件上传失败"); 92 return resultMap; 93 } 94 resultMap.put("error", 0); 95 resultMap.put("url", IMAGE_BASE_URL+imagePath+"/"+newName); 96 97 return resultMap ; 98 } catch (IOException e) { 99 resultMap.put("error", 1); 100 resultMap.put("message", "文件上传发生异常"+e.toString()); 101 return resultMap; 102 } 103 104 105 } 106 107 108 109 110 111 }
2-5: dao 层
无实现
2-6:工具类
1 package com.taotao.common.utils; 2 3 import java.io.File; 4 import java.io.FileInputStream; 5 import java.io.FileNotFoundException; 6 import java.io.FileOutputStream; 7 import java.io.IOException; 8 import java.io.InputStream; 9 import java.io.OutputStream; 10 11 import org.apache.commons.net.ftp.FTP; 12 import org.apache.commons.net.ftp.FTPClient; 13 import org.apache.commons.net.ftp.FTPFile; 14 import org.apache.commons.net.ftp.FTPReply; 15 16 /** 17 * 18 * @ClassName: FtpUtil 19 * @Description: ftp上传下载工具类 20 * 来自传智播客 21 * @author: 刘军/shall_liu(1136808529@qq.com) 22 * @date: 2017年8月26日 下午7:10:41 23 * 24 * @Copyright: 2017 25 */ 26 public class FtpUtil { 27 28 /** 29 * Description: 向FTP服务器上传文件 30 * @param host FTP服务器hostname 31 * @param port FTP服务器端口 32 * @param username FTP登录账号 33 * @param password FTP登录密码 34 * @param basePath FTP服务器基础目录 35 * @param filePath FTP服务器文件存放路径。例如分日期存放:/2015/01/01。文件的路径为basePath+filePath 36 * @param filename 上传到FTP服务器上的文件名 37 * @param input 输入流 38 * @return 成功返回true,否则返回false 39 */ 40 public static boolean uploadFile(String host, int port, String username, String password, String basePath, 41 String filePath, String filename, InputStream input) { 42 boolean result = false; 43 FTPClient ftp = new FTPClient(); 44 try { 45 int reply; 46 ftp.connect(host, port);// 连接FTP服务器 47 // 如果采用默认端口,可以使用ftp.connect(host)的方式直接连接FTP服务器 48 ftp.login(username, password);// 登录 49 reply = ftp.getReplyCode(); 50 if (!FTPReply.isPositiveCompletion(reply)) { 51 ftp.disconnect(); 52 return result; 53 } 54 //切换到上传目录 55 if (!ftp.changeWorkingDirectory(basePath+filePath)) { 56 //如果目录不存在创建目录 57 String[] dirs = filePath.split("/"); 58 String tempPath = basePath; 59 for (String dir : dirs) { 60 if (null == dir || "".equals(dir)) continue; 61 tempPath += "/" + dir; 62 if (!ftp.changeWorkingDirectory(tempPath)) { 63 if (!ftp.makeDirectory(tempPath)) { 64 return result; 65 } else { 66 ftp.changeWorkingDirectory(tempPath); 67 } 68 } 69 } 70 } 71 //设置上传文件的类型为二进制类型 72 ftp.setFileType(FTP.BINARY_FILE_TYPE); 73 //上传文件 74 if (!ftp.storeFile(filename, input)) { 75 return result; 76 } 77 input.close(); 78 ftp.logout(); 79 result = true; 80 } catch (IOException e) { 81 e.printStackTrace(); 82 } finally { 83 if (ftp.isConnected()) { 84 try { 85 ftp.disconnect(); 86 } catch (IOException ioe) { 87 } 88 } 89 } 90 return result; 91 } 92 93 /** 94 * Description: 从FTP服务器下载文件 95 * @param host FTP服务器hostname 96 * @param port FTP服务器端口 97 * @param username FTP登录账号 98 * @param password FTP登录密码 99 * @param remotePath FTP服务器上的相对路径 100 * @param fileName 要下载的文件名 101 * @param localPath 下载后保存到本地的路径 102 * @return 103 */ 104 public static boolean downloadFile(String host, int port, String username, String password, String remotePath, 105 String fileName, String localPath) { 106 boolean result = false; 107 FTPClient ftp = new FTPClient(); 108 try { 109 int reply; 110 ftp.connect(host, port); 111 // 如果采用默认端口,可以使用ftp.connect(host)的方式直接连接FTP服务器 112 ftp.login(username, password);// 登录 113 reply = ftp.getReplyCode(); 114 if (!FTPReply.isPositiveCompletion(reply)) { 115 ftp.disconnect(); 116 return result; 117 } 118 ftp.changeWorkingDirectory(remotePath);// 转移到FTP服务器目录 119 FTPFile[] fs = ftp.listFiles(); 120 for (FTPFile ff : fs) { 121 if (ff.getName().equals(fileName)) { 122 File localFile = new File(localPath + "/" + ff.getName()); 123 124 OutputStream is = new FileOutputStream(localFile); 125 ftp.retrieveFile(ff.getName(), is); 126 is.close(); 127 } 128 } 129 130 ftp.logout(); 131 result = true; 132 } catch (IOException e) { 133 e.printStackTrace(); 134 } finally { 135 if (ftp.isConnected()) { 136 try { 137 ftp.disconnect(); 138 } catch (IOException ioe) { 139 } 140 } 141 } 142 return result; 143 } 144 145 public static void main(String[] args) { 146 try { 147 FileInputStream in=new FileInputStream(new File("D:\\temp\\image\\gaigeming.jpg")); 148 boolean flag = uploadFile("192.168.25.133", 21, "ftpuser", "ftpuser", "/home/ftpuser/www/images","/2015/01/21", "gaigeming.jpg", in); 149 System.out.println(flag); 150 } catch (FileNotFoundException e) { 151 e.printStackTrace(); 152 } 153 } 154 } 155
1 package com.taotao.common.utils; 2 3 import java.util.Random; 4 5 /** 6 * 7 * @ClassName: IDUtils 8 * @Description:各种id生成策略 9 * @author: 刘军/shall_liu(1136808529@qq.com) 10 * @date: 2017年8月26日 下午2:49:33 11 * 12 * @Copyright: 2017 13 */ 14 public class IDUtils { 15 16 /** 17 * 图片名生成 18 */ 19 public static String genImageName() { 20 //取当前时间的长整形值包含毫秒 21 long millis = System.currentTimeMillis();//毫秒 22 //纳秒 1秒=1000毫秒=1000 X 1000 微秒 =1000 X 1000X 1000 纳秒 23 //long millis = System.nanoTime(); 24 //加上三位随机数 25 Random random = new Random(); 26 int end3 = random.nextInt(999); 27 //如果不足三位前面补0 28 String str = millis + String.format("%03d", end3); 29 30 return str; 31 } 32 33 /** 34 * 商品id生成 35 */ 36 public static long genItemId() { 37 //取当前时间的长整形值包含毫秒 38 long millis = System.currentTimeMillis(); 39 //long millis = System.nanoTime(); 40 //加上两位随机数 41 Random random = new Random(); 42 int end2 = random.nextInt(99); 43 //如果不足两位前面补0 44 String str = millis + String.format("%02d", end2); 45 long id = new Long(str); 46 return id; 47 } 48 49 public static void main(String[] args) { 50 for(int i=0;i< 100;i++) 51 System.out.println(genItemId()); 52 } 53 } 54
1 package com.taotao.common.utils; 2 3 import java.util.List; 4 5 import com.fasterxml.jackson.core.JsonProcessingException; 6 import com.fasterxml.jackson.databind.JavaType; 7 import com.fasterxml.jackson.databind.ObjectMapper; 8 9 /** 10 * 淘淘商城自定义响应结构 11 */ 12 public class JsonUtils { 13 14 // 定义jackson对象 15 private static final ObjectMapper MAPPER = new ObjectMapper(); 16 17 /** 18 * 将对象转换成json字符串。 19 * <p>Title: pojoToJson</p> 20 * <p>Description: </p> 21 * @param data 22 * @return 23 */ 24 public static String objectToJson(Object data) { 25 try { 26 String string = MAPPER.writeValueAsString(data); 27 return string; 28 } catch (JsonProcessingException e) { 29 e.printStackTrace(); 30 } 31 return null; 32 } 33 34 /** 35 * 将json结果集转化为对象 36 * 37 * @param jsonData json数据 38 * @param clazz 对象中的object类型 39 * @return 40 */ 41 public static <T> T jsonToPojo(String jsonData, Class<T> beanType) { 42 try { 43 T t = MAPPER.readValue(jsonData, beanType); 44 return t; 45 } catch (Exception e) { 46 e.printStackTrace(); 47 } 48 return null; 49 } 50 51 /** 52 * 将json数据转换成pojo对象list 53 * <p>Title: jsonToList</p> 54 * <p>Description: </p> 55 * @param jsonData 56 * @param beanType 57 * @return 58 */ 59 public static <T>List<T> jsonToList(String jsonData, Class<T> beanType) { 60 JavaType javaType = MAPPER.getTypeFactory().constructParametricType(List.class, beanType); 61 try { 62 List<T> list = MAPPER.readValue(jsonData, javaType); 63 return list; 64 } catch (Exception e) { 65 e.printStackTrace(); 66 } 67 68 return null; 69 } 70 71 } 72
2-7:对于 linux环境下的nginx 服务器和ftp服务器的搭建 请查看以下文章:
《centos7_ linux : Nginx安装手册》、《CentOS7 搭建FTP服务器》、《centos7 nginx图片 服务器可以访问ftp用户上传的图片资源的配置》
四:效果展示:
为人:谦逊、激情、博学、审问、慎思、明辨、 笃行
学问:纸上得来终觉浅,绝知此事要躬行
为事:工欲善其事,必先利其器。
态度:道阻且长,行则将至;行而不辍,未来可期
.....................................................................
------- 桃之夭夭,灼灼其华。之子于归,宜其室家。 ---------------
------- 桃之夭夭,有蕡其实。之子于归,宜其家室。 ---------------
------- 桃之夭夭,其叶蓁蓁。之子于归,宜其家人。 ---------------
=====================================================================
* 博客文章部分截图及内容来自于学习的书本及相应培训课程以及网络其他博客,仅做学习讨论之用,不做商业用途。
* 如有侵权,马上联系我,我立马删除对应链接。 * @author Alan -liu * @Email no008@foxmail.com
转载请标注出处! ✧*꧁一品堂.技术学习笔记꧂*✧. ---> https://www.cnblogs.com/ios9/
学问:纸上得来终觉浅,绝知此事要躬行
为事:工欲善其事,必先利其器。
态度:道阻且长,行则将至;行而不辍,未来可期
.....................................................................
------- 桃之夭夭,灼灼其华。之子于归,宜其室家。 ---------------
------- 桃之夭夭,有蕡其实。之子于归,宜其家室。 ---------------
------- 桃之夭夭,其叶蓁蓁。之子于归,宜其家人。 ---------------
=====================================================================
* 博客文章部分截图及内容来自于学习的书本及相应培训课程以及网络其他博客,仅做学习讨论之用,不做商业用途。
* 如有侵权,马上联系我,我立马删除对应链接。 * @author Alan -liu * @Email no008@foxmail.com
转载请标注出处! ✧*꧁一品堂.技术学习笔记꧂*✧. ---> https://www.cnblogs.com/ios9/