程序员求职经验分享与学习资料整理平台

网站首页 > 文章精选 正文

go errgroup 获取gorouting错误信息

balukai 2025-07-14 14:50:12 文章精选 3 ℃

errgroup 是 Go 官方 x/sync/errgroup 包提供的一个用于并发任务处理的工具,它可以帮你同时启动多个 goroutine,并收集它们的错误,只要有任意一个出错,其他任务会尽早终止(如果你写得配合得当)

基本示例:并发执行多个任务

package main

import (
	"errors"
	"fmt"
	"golang.org/x/sync/errgroup"
	"time"
)

func main() {
	var g errgroup.Group

	// 启动多个 goroutine
	for i := 1; i <= 3; i++ {
		i := i // 避免闭包引用问题
		g.Go(func() error {
			if i == 2 {
				return errors.New("任务2出错了")
			}
			fmt.Printf("任务%d完成\n", i)
			return nil
		})
	}

	// 等待所有任务完成(或中途失败)
	if err := g.Wait(); err != nil {
		fmt.Println("发生错误:", err)
	} else {
		fmt.Println("全部任务成功完成")
	}
}

带取消机制的版本(配合 context)

如果你希望出错时立刻取消其它任务,可以配合 context 使用:

package main

import (
	"context"
	"fmt"
	"golang.org/x/sync/errgroup"
	"time"
)

func main() {
	ctx := context.Background()

	// 创建带取消的 group 和 ctx
	g, ctx := errgroup.WithContext(ctx)

	for i := 1; i <= 3; i++ {
		i := i
		g.Go(func() error {
			// 模拟长任务
			select {
			case <-time.After(time.Duration(i) * time.Second):
				if i == 2 {
					return fmt.Errorf("任务%d出错了", i)
				}
				fmt.Printf("任务%d完成\n", i)
				return nil
			case <-ctx.Done():
				// 如果 context 被取消,退出
				fmt.Printf("任务%d被取消\n", i)
				return ctx.Err()
			}
		})
	}

	// 等待所有 goroutine 完成
	if err := g.Wait(); err != nil {
		fmt.Println("发生错误:", err)
	}
}

总结:errgroup 的优点

特性

描述

g.Go(func) error

启动 goroutine,并自动收集错误

g.Wait()

等待所有 goroutine 完成或其中之一返回错误

WithContext(ctx)

出错时,自动取消其它 goroutine

内部 panic 捕获

自动 recover panic,转为 error

Tags:

最近发表
标签列表