Loading [MathJax]/jax/output/CommonHTML/config.js
首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >专栏 >go语言中利用函数闭包实现中间件

go语言中利用函数闭包实现中间件

原创
作者头像
言志志
修改于 2023-10-10 12:46:34
修改于 2023-10-10 12:46:34
1.1K3
举报
文章被收录于专栏:Go语言学习笔记Go语言学习笔记

前言

本文是探讨的是"go语言中的中间件"

此文章是个人学习归纳的心得, 如有不对, 还望指正, 感谢!

判断

为了判断你是否有阅读本文的必要,请你在脑海中快速实现一个中间件的代码结构?

什么叫做中间件?

中间件设计模式是一种常见的软件设计模式,它在许多编程语言和框架中被广泛应用,包括Go、Node.js、Python等。

中间件模式的核心思想是将一系列的处理逻辑组合在一起,形成一个处理链(或称为管道),每个处理逻辑被封装成一个中间件函数。每个中间件函数可以在请求处理的不同阶段添加额外的功能或逻辑,而无需修改原始的处理函数。

中间件模式的优势在于它提供了一种可插拔、可组合的方式来扩展和定制请求处理过程。以下是中间件模式的一些关键特点:

  1. 可插拔性(Pluggability):中间件模式允许将中间件函数插入到处理链中,以添加新的功能或逻辑。这种可插拔性使得我们可以根据需要动态地添加、移除或替换中间件,而无需修改原始的处理函数。
  2. 复用性(Reusability):中间件模式可以将通用的功能或逻辑封装成可复用的中间件函数。这些中间件函数可以在不同的请求处理中重复使用,提高了代码的复用性。
  3. 可组合性(Composability):中间件模式允许将多个中间件函数按照特定的顺序组合在一起,形成一个处理链。每个中间件函数可以在调用原始处理函数之前、之后或两者之间执行自己的逻辑。这种可组合性使得我们可以构建复杂的处理逻辑,将各个中间件函数按需组合,形成一个完整的请求处理流程。
  4. 责任链(Chain of Responsibility):中间件模式的处理链形成了一个责任链结构,每个中间件函数都有机会处理请求或将处理传递给下一个中间件。这种责任链结构可以根据实际需求动态调整中间件的顺序,实现不同的处理流程。

中间件模式在Web开发中得到了广泛应用,特别是在处理HTTP请求的过程中。常见的中间件功能包括身份验证、日志记录、请求解析、缓存、错误处理、压缩等。通过将这些功能封装成中间件函数,并按照需要组合起来,我们可以轻松地构建灵活、可扩展的Web应用程序。

利用函数闭包实现一个简单的中间件

下面我以求两数之和为例,实现一个简单的中间件,可以看如下代码

代码语言:go
AI代码解释
复制
package main



import "log"



func sum(a, b int) int {

   return a + b

}



func Zh(f func(a, b int) int) func(a, b int) int {

   return func(a, b int) int {

      log.Printf("日志中间件,记录操作数: a: %d b: %d\n", a, b)

      return f(a, b)

   }

}



func main(){



   addWithLogging := Zh(sum)

   

   result := addWithLogging(2, 3)



   result2 := addWithLogging(5, 6)



   fmt.Println(result,result2)



}

上面的代码,可以被认为是一个中间件函数的实现,我们在sum函数执行之前,先进行了日志的记录,并且又不影响原函数的执行,就像添加了一个过程一样,这个中间件函数可以被插入到处理链中,在执行原始函数之前记录操作数的日志,其实你可以发现,我不过就是相当于将传入的函数进行封装了一下

当然,我们还可以更加优雅,那就是抽象为一个函数类型,并且我们可以发现,Zh中间件处理后的返回值,还可以继续被它处理。

代码语言:go
AI代码解释
复制
// 优雅地处理

type F func(func(a, b int) int

对了,上面的函数是利用闭包实现的,首先闭包是指函数内部定义的函数可以访问其外部函数的变量。

而在这个例子中,匿名函数func(a, b int) int是在Zh函数内部定义的,并且可以访问外部函数的参数f

具体来说,Zh函数接受一个函数类型的参数f,并返回一个具有相同函数签名的函数。在返回的函数内部,它使用了log.Printf打印日志,并调用了外部函数的参数f

由于返回的函数是在Zh函数内部定义的,它可以访问Zh函数的参数f,即使Zh函数已经执行完毕并返回了。这是因为闭包函数捕获了其外部函数的变量,形成了一个闭包环境,使得返回的函数仍然可以访问外部函数的变量。

当然,我只是想通过这个简单的样例让你知道,什么是中间件

像go中的gin框架中的中间件的使用就很成熟,gin巧妙的把具体实现过程进行了隐藏,让你只要写好一个函数,然后插入使用即可,非常优雅,而本文的样例,其实是把隐藏的过程进行了展示,详情请看gin的源码。

我正在参与2023腾讯技术创作特训营第二期有奖征文,瓜分万元奖池和键盘手表

原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。

如有侵权,请联系 cloudcommunity@tencent.com 删除。

原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。

如有侵权,请联系 cloudcommunity@tencent.com 删除。

评论
登录后参与评论
3 条评论
热度
最新
所以中间件就是对本来要做的事,进行了封装?
所以中间件就是对本来要做的事,进行了封装?
221举报
也可以这么理解
也可以这么理解
回复回复点赞举报
貌似是的
貌似是的
回复回复点赞举报
推荐阅读
编辑精选文章
换一批
更优的框架中间件实现
前几个周前前后后阅读了4个go框架(iris、gin、echo、beego)的生命周期,阅读过程中对它们在框架中间件的实现颇有印象,总觉着实现的都不是很完美。
用户1093396
2020/10/29
9040
更优的框架中间件实现
你需要掌握的 Koa 洋葱模型和中间件
Koa 是一个 nodejs 框架,经常用于写 web 后端服务。它是 Express 框架的原班人马开发的新一代 web 框架,使用了 async / await 来优雅处理无处不在的异步逻辑。
前端西瓜哥
2022/12/21
6710
你需要掌握的 Koa 洋葱模型和中间件
Golang Gin 实战(十三)| 中间件详解看这一篇就够了
在Gin的整个实现中,中间件可谓是Gin的精髓。一个个中间件组成一条中间件链,对HTTP Request请求进行拦截处理,实现了代码的解耦和分离,并且中间件之间相互不用感知到,每个中间件只需要处理自己需要处理的事情即可。今天我们就通过这篇文章,详细的介绍Gin中间的使用和原理。
飞雪无情
2020/06/30
5K0
Go语言中的中间件设计与实现
在Go语言中,中间件是一个强大的工具,用于在处理HTTP请求和响应之间插入逻辑层。中间件模式在Web开发中广泛使用,因为它允许我们灵活地添加日志、认证、限流等功能,而不会让核心路由代码变得复杂。
Jimaks
2024/05/04
3830
Go 语言 Web 编程系列(六)—— 基于 gorilla/mux 包实现路由匹配:路由中间件
和 Laravel 路由一样,Mux 也支持在路由中使用中间件,并且按照顺序匹配执行。如果你对中间件不太了解,可以先去看下我们在 Laravel 中间件文档中的简单介绍:https://xueyuanjun.com/post/19926。和 Laravel 一样,在 Go Web 编程中,中间件的典型使用场景包括认证、日志、请求头操作和 ResponseWriter “劫持”等。
学院君
2020/01/17
1.4K0
Go 语言 Web 编程系列(六)—— 基于 gorilla/mux 包实现路由匹配:路由中间件
浅谈Go语言中闭包的使用
闭包(Closure),又称词法闭包(Lexical Closure)或函数闭包(function closures),是引用了自由变量的函数。这个被引用的自由变量将和这个函数一同存在,即使已经离开了创造它的环境也不例外。所以,有另一种说法认为闭包是由函数和与其相关的引用环境组合而成的实体。 ——Google搜索引擎维基百科 当然,上面那段看上去多少有点拗口了。 说得简单点,闭包实际上就是一种语法糖机制,而这种语法糖机制可以简化编程,从而可以提高代码的可读性。比如,有时候对外部的局部变量进行访问,没这种
企鹅号小编
2018/01/12
2.6K0
浅谈Go语言中闭包的使用
【Go语言学习】匿名函数与闭包
入坑 Go 语言已经大半年了,却没有写过一篇像样的技术文章,每次写一半就搁笔,然后就烂尾了。
弗兰克的猫
2020/07/27
8120
从零实现Web框架Geo教程-中间件-05
中间件(middlewares),简单说,就是非业务的技术类组件。Web 框架本身不可能去理解所有的业务,因而不可能实现所有的功能。因此,框架需要有一个插口,允许用户自己定义功能,嵌入到框架中,仿佛这个功能是框架原生支持的一样。因此,对中间件而言,需要考虑2个比较关键的点:
大忽悠爱学习
2022/09/26
2360
Go 函数式编程篇(七):基于管道技术实现函数的流式调用
管道(Pipeline)这一术语来源是 Unix 的 Shell 命令行,我们可以使用管道连接符 | 通过组合简单的命令实现强大的功能,比如我们想要从系统进程列表中筛选出 nginx 进程,可以这么做:
学院君
2023/03/03
6720
Go 函数式编程篇(七):基于管道技术实现函数的流式调用
「Go框架」深入理解web框架的中间件运行机制
大家好,我是渔夫子。本号新推出「Go工具箱」系列,意在给大家分享使用go语言编写的、实用的、好玩的工具。同时了解其底层的实现原理,以便更深入地了解Go语言。
Go学堂
2023/01/31
7340
【ASP.NET Core 基础知识】--中间件--什么是中间件
本篇文章作为中间件单元的开篇文章,通过这篇文章可以了解什么是中间件、内置中间件的使用以及怎么创建自定义中间件。我们先来看一下中间件的角色、目的和重要性。
喵叔
2024/01/14
1.2K1
GoFrame框架学习之旅:第四天 - 中间件与请求处理
在Web开发中,中间件(Middleware)扮演着至关重要的角色。它们位于请求处理流程的特定阶段,可以执行诸如身份验证、日志记录、请求/响应处理等任务。GoFrame框架提供了灵活的中间件机制,使得开发者能够轻松地扩展和自定义请求处理流程。今天,我们将一起学习GoFrame中的中间件以及如何使用它们来处理HTTP请求。
china马斯克
2024/09/24
3900
Go语言中间件框架 Negroni 的静态文件处理源码分析
Negroni是一个非常棒的中间件,尤其是其中间件调用链优雅的设计,以及对GO HTTP 原生处理器的兼容。我以前写过两篇文章,对Negroni进行了专门的分析,没有看过的朋友可以在看下。
飞雪无情
2018/10/10
5540
go语言中闭包与匿名函数是什么?
(非函数式编程不推荐使用,内存管理复杂且难以运维!个人更推荐采用全局变量、全局结构体的字段等方法进行状态保持)
闻说社
2024/08/07
1250
go语言中闭包与匿名函数是什么?
Koa的洋葱中间件,Redux的中间件,Axios的拦截器,一个精简版的就彻底搞懂了。
前端中的库很多,开发这些库的作者会尽可能的覆盖到大家在业务中千奇百怪的需求,但是总有无法预料到的,所以优秀的库就需要提供一种机制,让开发者可以干预插件中间的一些环节,从而完成自己的一些需求。
ssh_晨曦时梦见兮
2020/04/11
2.1K0
Koa的洋葱中间件,Redux的中间件,Axios的拦截器,一个精简版的就彻底搞懂了。
100天精通Golang(基础入门篇)——第15天:深入解析Go语言中函数的应用:从基础到进阶,助您精通函数编程!(进阶)
本篇文章是《100天精通Golang(基础入门篇)》系列的第15天,我们将继续深入解析Go语言中函数的应用。通过对函数的基础知识、参数传递、多返回值、作用域、匿名函数、闭包、延迟执行、错误处理、函数的高级特性以及Go语言函数与Java函数的区别进行探讨,我们将更全面地理解和应用函数的相关知识点。
猫头虎
2024/04/08
2760
100天精通Golang(基础入门篇)——第15天:深入解析Go语言中函数的应用:从基础到进阶,助您精通函数编程!(进阶)
每日一库:Gin Middleware开发
Gin是一个用Go语言编写的Web框架,它提供了一种简单的方式来创建HTTP路由和处理HTTP请求。中间件是Gin框架中的一个重要概念,它可以用来处理HTTP请求和响应,或者在处理请求之前和之后执行一些操作。
孟斯特
2023/10/16
4550
每日一库:Gin Middleware开发
深入浅出node中间件原理
中间件是介于应用系统和系统软件之间的一类软件,它使用系统软件所提供的基础服务(功能),衔接网络上应用系统的各个部分或不同的应用,能够达到资源共享、功能共享的目的。
徐小夕
2020/11/09
6090
深入浅出node中间件原理
Gin源码解析和例子——中间件(middleware)
        在《Gin源码解析和例子——路由》一文中,我们已经初识中间件。本文将继续探讨这个技术。(转载请指明出于breaksoftware的csdn博客)
方亮
2019/01/16
1K0
Gin框架入门系列-中间件
在Gin框架中,中间件(Middleware)指的是可以拦截http请求-响应生命周期的特殊函数,在请求-响应生命周期中可以注册多个中间件,每个中间件执行不同的功能,一个中间执行完再轮到下一个中间件执行。
用户10002156
2023/11/20
2990
Gin框架入门系列-中间件
推荐阅读
相关推荐
更优的框架中间件实现
更多 >
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档