go 简单实现分布式锁

简介: 单一执行,通过分布式锁实现

有多个客户端请求服务端,业务规定,某个任务只能单一执行

例如:有a,b,c,d 4个客户端同时访问服务端,都竞争任务执行资格,谁竞争到了这个资格,这个任务就由它执行,其它人即使执行也是无效的,如果它出故障了,服务端判断一定时间任务没有执行,就会释放这个资格,其它客户端就可以继续竞争这个任务执行资格了。

如何实现这种业务场景呢?

代码例子

packagemainimport (
"fmt""github.com/gin-gonic/gin""sync""time")
typeFstruct {
NamestringTint64}
varfFvarmsync.Mutexfuncmain() {
//起一个go协程去检查单一任务是否离线,10秒gofunc() {
for {
iff.Name!=""&&time.Now().Unix()-f.T>10 {
m.Lock()
f.Name=""m.Unlock()
            } else {
fmt.Println("目前锁的持有者是:", f.Name)
            }
time.Sleep(1*time.Second)
        }
    }()
r :=gin.Default()
r.GET("/ping", task)
r.GET("/hello", hello)
r.Run() // listen and serve on 0.0.0.0:8080}
funchello(c*gin.Context) {
c.JSON(200, gin.H{
"message": "hello,world",
    })
}
functask(c*gin.Context) {
ifc.Query("name") !="" {
iff.Name=="" {
m.Lock()
f.Name=c.Query("name")
f.T=time.Now().Unix()
m.Unlock()
c.JSON(200, gin.H{
"message": "get lock ok",
            })
        } else {
ifc.Query("name") ==f.Name {
//更新心跳时间f.T=time.Now().Unix()
c.JSON(200, gin.H{
"message": "单一任务执行者",
                })
            } else {
c.JSON(200, gin.H{
"message": "不需要额外的任务执行者",
                })
            }
        }
    } else {
c.JSON(400, gin.H{
"message": "miss  name query",
        })
    }
}


执行效果

jiangyd:fenbu jiangyd$ curl http://127.0.0.1:8080/ping?name=ee
{"message":"get lock ok"}
jiangyd:fenbu jiangyd$ curl http://127.0.0.1:8080/ping?name=bb
{"message":"不需要额外的任务执行者"}
jiangyd:fenbu jiangyd$ curl http://127.0.0.1:8080/ping?name=cc
{"message":"不需要额外的任务执行者"}
jiangyd:fenbu jiangyd$ curl http://127.0.0.1:8080/ping?name=ee
{"message":"单一任务执行者"}
jiangyd:fenbu jiangyd$ curl http://127.0.0.1:8080/ping?name=ee
{"message":"单一任务执行者"}
jiangyd:fenbu jiangyd$ curl http://127.0.0.1:8080/ping?name=bb
{"message":"不需要额外的任务执行者"}
jiangyd:fenbu jiangyd$ curl http://127.0.0.1:8080/ping?name=bb
{"message":"不需要额外的任务执行者"}
jiangyd:fenbu jiangyd$ curl http://127.0.0.1:8080/ping?name=bb
{"message":"不需要额外的任务执行者"}
jiangyd:fenbu jiangyd$ curl http://127.0.0.1:8080/ping?name=bb
{"message":"不需要额外的任务执行者"}
jiangyd:fenbu jiangyd$ curl http://127.0.0.1:8080/ping?name=bb
{"message":"不需要额外的任务执行者"}
jiangyd:fenbu jiangyd$ curl http://127.0.0.1:8080/ping?name=bb
{"message":"不需要额外的任务执行者"}
jiangyd:fenbu jiangyd$ curl http://127.0.0.1:8080/ping?name=bb
{"message":"不需要额外的任务执行者"}
jiangyd:fenbu jiangyd$ curl http://127.0.0.1:8080/ping?name=bb
{"message":"不需要额外的任务执行者"}
jiangyd:fenbu jiangyd$ curl http://127.0.0.1:8080/ping?name=bb
{"message":"不需要额外的任务执行者"}
jiangyd:fenbu jiangyd$ curl http://127.0.0.1:8080/ping?name=bb
{"message":"不需要额外的任务执行者"}
jiangyd:fenbu jiangyd$ curl http://127.0.0.1:8080/ping?name=bb
{"message":"不需要额外的任务执行者"}
jiangyd:fenbu jiangyd$ curl http://127.0.0.1:8080/ping?name=bb
{"message":"不需要额外的任务执行者"}
jiangyd:fenbu jiangyd$ curl http://127.0.0.1:8080/ping?name=bb
{"message":"get lock ok"}
jiangyd:fenbu jiangyd$ curl http://127.0.0.1:8080/ping?name=bb
{"message":"单一任务执行者"}
jiangyd:fenbu jiangyd$ curl http://127.0.0.1:8080/ping?name=bb
{"message":"单一任务执行者"}
jiangyd:fenbu jiangyd$ curl http://127.0.0.1:8080/ping?name=ee
{"message":"不需要额外的任务执行者"}
jiangyd:fenbu jiangyd$ curl http://127.0.0.1:8080/ping?name=ee
{"message":"不需要额外的任务执行者"}


应用日志

目前锁的持有者是: 
目前锁的持有者是: 
目前锁的持有者是: 
[GIN] 2021/11/18 - 14:38:11 | 200 |     166.817µs |       127.0.0.1 | GET      "/ping?name=ee"
目前锁的持有者是: ee
目前锁的持有者是: ee
[GIN] 2021/11/18 - 14:38:13 | 200 |      132.71µs |       127.0.0.1 | GET      "/ping?name=bb"
目前锁的持有者是: ee
目前锁的持有者是: ee
[GIN] 2021/11/18 - 14:38:16 | 200 |     156.544µs |       127.0.0.1 | GET      "/ping?name=cc"
目前锁的持有者是: ee
目前锁的持有者是: ee
[GIN] 2021/11/18 - 14:38:18 | 200 |      60.798µs |       127.0.0.1 | GET      "/ping?name=ee"
目前锁的持有者是: ee
目前锁的持有者是: ee
[GIN] 2021/11/18 - 14:38:19 | 200 |      57.979µs |       127.0.0.1 | GET      "/ping?name=ee"
目前锁的持有者是: ee
目前锁的持有者是: ee
[GIN] 2021/11/18 - 14:38:21 | 200 |      59.946µs |       127.0.0.1 | GET      "/ping?name=bb"
[GIN] 2021/11/18 - 14:38:22 | 200 |      53.904µs |       127.0.0.1 | GET      "/ping?name=bb"
目前锁的持有者是: ee
[GIN] 2021/11/18 - 14:38:23 | 200 |      45.606µs |       127.0.0.1 | GET      "/ping?name=bb"
目前锁的持有者是: ee
[GIN] 2021/11/18 - 14:38:23 | 200 |      46.552µs |       127.0.0.1 | GET      "/ping?name=bb"
目前锁的持有者是: ee
[GIN] 2021/11/18 - 14:38:24 | 200 |       49.45µs |       127.0.0.1 | GET      "/ping?name=bb"
目前锁的持有者是: ee
[GIN] 2021/11/18 - 14:38:25 | 200 |      76.116µs |       127.0.0.1 | GET      "/ping?name=bb"
[GIN] 2021/11/18 - 14:38:26 | 200 |      105.55µs |       127.0.0.1 | GET      "/ping?name=bb"
目前锁的持有者是: ee
[GIN] 2021/11/18 - 14:38:27 | 200 |      79.018µs |       127.0.0.1 | GET      "/ping?name=bb"
目前锁的持有者是: ee
[GIN] 2021/11/18 - 14:38:27 | 200 |      66.346µs |       127.0.0.1 | GET      "/ping?name=bb"
目前锁的持有者是: ee
[GIN] 2021/11/18 - 14:38:28 | 200 |      76.468µs |       127.0.0.1 | GET      "/ping?name=bb"
[GIN] 2021/11/18 - 14:38:29 | 200 |      50.744µs |       127.0.0.1 | GET      "/ping?name=bb"
目前锁的持有者是: ee
[GIN] 2021/11/18 - 14:38:30 | 200 |      96.843µs |       127.0.0.1 | GET      "/ping?name=bb"
目前锁的持有者是: 
[GIN] 2021/11/18 - 14:38:31 | 200 |      109.12µs |       127.0.0.1 | GET      "/ping?name=bb"
目前锁的持有者是: bb
目前锁的持有者是: bb
目前锁的持有者是: bb
[GIN] 2021/11/18 - 14:38:34 | 200 |     140.095µs |       127.0.0.1 | GET      "/ping?name=bb"
目前锁的持有者是: bb
[GIN] 2021/11/18 - 14:38:35 | 200 |      52.475µs |       127.0.0.1 | GET      "/ping?name=bb"
目前锁的持有者是: bb
目前锁的持有者是: bb
目前锁的持有者是: bb
目前锁的持有者是: bb
[GIN] 2021/11/18 - 14:38:39 | 200 |      57.742µs |       127.0.0.1 | GET      "/ping?name=ee"
目前锁的持有者是: bb
[GIN] 2021/11/18 - 14:38:40 | 200 |      61.668µs |       127.0.0.1 | GET      "/ping?name=ee"
[GIN] 2021/11/18 - 14:38:41 | 200 |      46.113µs |       127.0.0.1 | GET      "/ping?name=ee"
目前锁的持有者是: bb
目前锁的持有者是: bb
目前锁的持有者是: bb
目前锁的持有者是: bb
目前锁的持有者是: bb
目前锁的持有者是: 
目前锁的持有者是: 


这样就可以达到要求了。

目录
相关文章
|
5月前
|
安全 算法 Java
Go语言在分布式系统中的优势与挑战
【2月更文挑战第20天】Go语言作为一种高效且简洁的编程语言,在分布式系统领域展现出了显著的优势。然而,随着系统复杂性的增加,Go语言也面临着一些挑战。本文将从Go语言在分布式系统中的优势出发,深入探讨其在实际应用中遇到的挑战,并给出相应的解决策略,以期为开发人员在分布式系统中使用Go语言提供有益的参考。
|
5月前
|
监控 安全 Java
应对Go语言在分布式系统中挑战的策略
【2月更文挑战第20天】Go语言在分布式系统中的应用日益广泛,但随之而来的挑战也不容忽视。本文将从内存管理、性能优化、安全性与可靠性等方面,探讨应对Go语言在分布式系统中挑战的策略,旨在为开发人员提供实用的解决方案和思路。
|
5月前
|
安全 大数据 Go
Go语言在分布式系统中的应用
【2月更文挑战第20天】Go语言,以其独特的语言特性和出色的性能,逐渐成为分布式系统开发领域的热门选择。本文将深入探讨Go语言在分布式系统中的应用,分析其优势及实际应用案例,旨在为开发人员提供有价值的参考与启示。
|
2月前
|
算法 Go
[go 面试] 雪花算法与分布式ID生成
[go 面试] 雪花算法与分布式ID生成
|
2月前
|
监控 Go API
带你十天轻松搞定 Go 微服务之大结局(分布式事务)
带你十天轻松搞定 Go 微服务之大结局(分布式事务)
|
2月前
|
存储 NoSQL 算法
Go 分布式令牌桶限流 + 兜底保障
Go 分布式令牌桶限流 + 兜底保障
|
2月前
|
Go API 数据库
[go 面试] 分布式事务框架选择与实践
[go 面试] 分布式事务框架选择与实践
|
2月前
|
消息中间件 SQL 关系型数据库
go-zero微服务实战系列(十、分布式事务如何实现)
go-zero微服务实战系列(十、分布式事务如何实现)
|
2月前
|
Kubernetes Go 数据库
go-zero 分布式事务最佳实践
go-zero 分布式事务最佳实践
|
2月前
|
NoSQL Go Redis
用 Go + Redis 实现分布式锁
用 Go + Redis 实现分布式锁
下一篇
无影云桌面