首頁  >  文章  >  web前端  >  Node+UDP實作圖片裁切功能

Node+UDP實作圖片裁切功能

青灯夜游
青灯夜游轉載
2021-03-10 10:13:171492瀏覽

本篇文章跟大家介紹一下Nodejs UDP實作圖片裁切功能的方法。有一定的參考價值,有需要的朋友可以參考一下,希望對大家有幫助。

Node+UDP實作圖片裁切功能

相關推薦:《nodejs 教學

說起來UDP,可能最吸引人的就是【UDP伺服器】了吧。

UDP伺服器可以用於一些特殊資料的(高效)傳輸,例如圖片、視訊和音訊資訊等

我見過一些大佬用UDP來和C server交互,主要目的是希望將PHP無法處理的邏輯業務,透過UDP伺服器傳送給其他server來處理。

所以,能不能有這樣一個需求:我們有兩個伺服器A、B,我們希望A處理所有的業務邏輯,而B只去做資料庫作業(例如更新)。

有多個設計想法可以解決上面的問題,最簡單的就是透過HTTP發送請求的方式,將A處理後的參數透過HTTP方式傳遞給B伺服器,然後B伺服器取得參數後更新資料庫。 —— 這種方式對於Node.js 來說非常簡單,但是HTTP是一個TCP協議,對於我們自己的兩台可信賴的伺服器,我們更希望使用UDP來傳送協議,避免TCP中不必要的資料傳輸。

接下來我們要介紹的一個應用,就是使用Node.js來處理圖片上傳切割(圖片處理),並透過客戶端顯示所有的經過處理後的圖片列表,而這個功能也將應用UDP模組來實現。

應用程式分析

本應用程式包含兩個部分,一個是圖片上傳的網路服務功能模組、圖片處理後的頁面展示功能;另外一個則是圖片的處理,主要是圖片的切割保存。而作為用戶,希望是這樣的一個工具,上傳一個圖片,並指定其需要切割的長和寬,通過系統處理後返回給用戶一個切割好的圖片,並通過頁面返回展示。

根據以上的需求的分析,我們將上面的需求轉換為如圖4-5所示的系統運作流程圖。根據應用程式的分析,我們會設計兩個伺服器,一個是Web伺服器,另一個則是圖片處理伺服器,兩者透過UDP協定進行互動:
Node+UDP實作圖片裁切功能
圖片上傳頁面,主要是圖片的上傳和預覽功能頁面;圖片展示頁面,展示透過圖片處理後返回的圖片; HTTP Web伺服器主要的作用是文件上傳和圖片展示;圖片處理伺服器,將Web伺服器的資料透過UDP協定傳遞給圖片處理伺服器,圖片處理伺服器做-定的處理後返回對應的資料到Web伺服器。

UDP Server端實作- 圖片處理伺服器

根據上面的分析,本應用程式需要實作的3個功能模組分別是,UDP Server端、UDP Client端(Web Server) 和Jade頁面。
那麼首先我們從該應用的UDPServer端程式碼實作原理開始介紹(也就是圖片處理伺服器)。圖片處理伺服器作為UDP的server端,要應用UDP模組實作UDP server, 由於該UDP server依賴圖片處理工具,因此在UDP服務程式中會應用github中的一個開源Node.js圖片處理工具一node -imagemagick來輔助實現圖片處理功能。根據上面的分析,我們簡單設計出UDP Server的程式碼框架,程式碼如下:

const dgram=require('dgram');   //UDPconst server=dgram.createSocket("udp4");server.on("message",function(msg,rinfo){
	//监听消息事件后处理})server.on("listening",function(){
	var address=server.address();
	console.log("server listening "+address.address+":"+address.port);})server.bind("监听端口号");

會發現,UDP其實似乎跟socket.io差不多?都是採用的監聽訊息流機制。而http沒有這樣做,所以幾乎不用http去做這些高互動的事情 —— 這固然和他們的內部實現有關。

監聽完了,該做正事了:我們需要一個函數去處理圖片。這個函數的觸發時間要在事件流之後:

npm install imagemagick

需要注意的是,在使用該工具時,必須安裝imagemagick-cli系統工具軟體:sudo apt-get install imagemagick --fix -missing(否則會在運行期間拋出異常)

/**
	url:图片源路径
	width:图片压缩宽
	height:图片压缩高
	newName:图片处理后存储路径
**/function resizeImage(url,width,height,newName,callback){
	var im=require('imagemagick');
	im.resize({
		srcPath: url,
		dstPath: newName,
		width: width,
		height: height	}, function(err,stdout,stderr){
		if(err){
			callback(-1);
		}else{
			callback(stdout);
		}
	})}

然後在udp的onmessage回調函數中調用:

server.on("message",function(msg,rinfo){
	var imageObject=JSON.parse(msg);
	resizeImage(imageObject.url, imageObject.width, imageObject.height, imageObject.new_name, function(ret){
		var retJson;
		if(ret==-1){
			retJson={'code':-1,'msg':'some error in resize image','data':{}}
		}else{
			retJson={'code':0,'msg':'success','data':{'name':imageObject.new_name}}
		}
		//将json对象转为json字符串
		var retStr=JSON.stringify(retJson);
		//转为buffer对象,用于UDP传输
		var message=new Buffer(retStr);
		server.send(message,0,message.length,rinfo.port,rinfo.address);
	})})

server.on("message", callback(msg, rinfo))回呼函數中有msg和rinfo參數,其中msg為客戶端發送的訊息數據,而rinfo則為客戶端訊息,伺服器端根據客戶端資訊中的連接埠port和IP位址address, 應用server.send回應資料到客戶端即可。到這裡我們就實作了一個圖片處理的UDP伺服器,接下來介紹Web伺服器端是如何與其互動的。

UDP Client端 —— 前台服务器

npm install express jade formidable body-parser
const jade=require('jade');const express=require('express');const bodyParser=require('body-parser');const fs=require('fs');const VIEW=__dirname+"/view/";var app=express();app.set('view engine','jade');app.use(bodyParser.urlencoded({extended: true}))app.get('/',function(req,res,next){
	//http响应文件上传页面
	res.render(VIEW+'index.jade');};//文件上传处理逻辑app.post('/upload',function(req,res,next){
	var now=Date.parse(new Date())/1000;
	var form=new formidable.IncomingForm(),
		fields=[],
		baseName=__dirname+'/uploadFile/'+now,
		imageName=baseName+'.png',   //源图片路径
		newName=baseName+'_small'+'.png',   //新文件路径
		pathName='/uploadFile/'+now+'_small'+'.png';
	form.on('field',function(field,value){
		fields.push([field,value]);
	});
	form.parse(req,function(error,fields,files){
		var size=''+fields.width+'x'+fields.height
		fs.renameSync(files.image.path,imageName);
		imageResize(fields.width, fields.height, imageName, newName,res);
	})};app.listen('监听端口号');
form.parse(request, [callback]) 该方法会转换请求中所包含的表单数据,callback会包含所有字段域和文件信息

文件上传功能同样是应用formidable 模块,当然这里还应用到其获取POST数据的方法。formidable 模块提供了获取field参数的API form.on的field 事件,监听POST数据传递。所有的POST数据都需要应用form.parse 进行解析,解析返回fields对象和文件对象files。根据获取的width和height,调用imageResize对图片进行相应的压缩处理。

然后去实现imageResize函数:imageResize函数的主要功能是应用UDP模块连接UDPServer,将相应的参数数据转化为json字符通过UDP协议传递到UDPServer,并将UDPServer响应的数据通过res.render直接返回显示到相应的页面

function imageResize(width,height,imagePath,newName,res){
	var imageJson={
		'width':width,
		'height':height,
		'url':imagePath,
		'new_name':newName	};
	var jsonStr=JSON.stringify(imageJson);
	var client=dgram.createSocket("udp4");
	var message=new Buffer(jsonStr);
	client.send(message,0,message.length,Server端监听的端口号,"域名",function(){
		client.on("message",function(msg,rinfo){
			var retJson=JSON.parse(msg);
			if(retJson.code===0){
				res.render(VIEW+'main.jade',{'url':pathName,'err':'ok'});
			}else{
				res.render(VIEW+'main.jade',{'url':'','err':'error'});
			}
		})
	})}

前端模板jade部分就先省去。。。

更多编程相关知识,请访问:编程视频!!

以上是Node+UDP實作圖片裁切功能的詳細內容。更多資訊請關注PHP中文網其他相關文章!

陳述:
本文轉載於:csdn.net。如有侵權,請聯絡admin@php.cn刪除