当一个服务操作访问不同的数据库资源,又希望对它们的访问具有事务特性时,就需要采用分布式事务来协调所有的事务参与者。 在一个跨服务的分布式事务中,事务的发起者和提交均系同一个,它可以是整个调用的客户端,也可以是客户端最先调用的那个服务 X/Open XA 协议 最早的分布式事务模型是 X/Open 国际联盟提出的 X/Open Distributed Transaction Processing(DTP)模型,也就是大家常说的 X/Open XA 协议,简称XA 协议
DTP 模型中包含一个全局事务管理器(TM,Transaction Manager)和多个资源管理器(RM,Resource Manager)。全局事务管理器负责管理全局事务状态与参与的资源,协同资源一起提交或回滚;资源管理器则负责具体的资源操作。
什么是异地多活 异地多活一般是指在不同城市建立独立的数据中心,“活”是相对于冷备份而言的,冷备份是备份全量数据,平时不支撑业务需求,只有在主机房出现故障的时候才会切换到备用机房,而多活,是指这些机房在日常的业务中也需要走流量,做业务支撑。冷备份的主要问题是成本高,不跑业务,当主机房出问题的时候,也不一定能成功把业务接管过来。
//加锁,注意锁要以指针的形式传进来,不然只是拷贝 func total1(num *int, mu *sync.Mutex, ch chan bool) { mu.Lock(); for i := 0; i < 1000; i++ { *num += i; } ch <- true; mu.Unlock(); } //Lock、Unlock与RLock、RUnlock不能嵌套使用 func printNum(num int, cond *sync.Cond) { cond.L.Lock(); if num < 5 { //num小于5时,进入等待状态 cond.Wait(); } //大于5的正常输出 fmt.Println(num); cond.L.Unlock(); } //Once.Do()保证多次调用只执行一次 once := sync.Once{}; ch := make(chan bool, 3); for i := 0; i < 3; i++ { go func(n int) { once.Do(func() { //只会执行一次,因为闭包引用了变量n,最后的值为2 fmt.Println(n)
//读写锁,多了读锁定,和读解锁,让多个goroutine同时读取对象 rwmutex := sync.RWMutex{}; //组等待,等待一组goroutine的结束 wg := sync.WaitGroup{}; //增加计数器 wg.Add(10); for i:= 0; i< 10; i++ { go func(n int) { fmt.Print(n, “ “); //这里表示该goroutine执行完成 wg.Done(); }(i); } //等待所有线程执行完成 wg.Wait(); 无论是互斥锁,还是自旋锁,在任何时刻,最多只能有一个保持者,也就说,在任何时刻最多只能有一个执行单元获得锁。但是两者在调度机制上略有不同。对于互斥锁,如果资源已经被占用,资源申请者只能进入睡眠状态。但是自旋锁不会引起调用者睡眠,如果自旋锁已经被别的执行单元保持,调用者就一直循环在那里看是否该自旋锁的保持者已经释放了锁,”自旋”一词就是因此而得名。