sockets - 去吧,tcp打开文件太多调试

标签 sockets tcp go goroutine

这是一个简单的 Go http (tcp) 连接测试脚本

func main() {
    ts := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
        fmt.Fprintln(w, "Hello, client")
    }))
    defer ts.Close()
    var wg sync.WaitGroup
    for i := 0; i < 2000; i++ {
        wg.Add(1)
        go func(i int) {
            defer wg.Done()
            resp, err := http.Get(ts.URL)
            if err != nil {
                panic(err)
            }
            greeting, err := ioutil.ReadAll(resp.Body)
            resp.Body.Close()
            if err != nil {
                panic(err)
            }
            fmt.Printf("%s", i, greeting)
        }(i)
    }
    wg.Wait()
}

如果我在 Ubuntu 中运行它,我会得到:

panic: Get http://127.0.0.1:33202: dial tcp 127.0.0.1:33202: too many open files

其他帖子说要确保 Close 连接,我在这里做这一切。 还有人说用 ulimit 增加最大连接的限制或尝试 sudo sysctl -w fs.inotify.max_user_watches=100000 但仍然不起作用。

如何在单个服务器上运行数百万个 tcp 连接 goroutine? 它仅在 2,000 个连接时崩溃。

谢谢,

最佳答案

我认为您需要更改最大文件描述符。我之前在我的一个开发虚拟机上遇到过同样的问题,需要更改文件描述符最大值,而不是任何 inotify 设置。

FWIW,你的程序在我的虚拟机上运行良好。

·> ulimit -n
120000

但是在我跑完之后

·> ulimit -n 500
·> ulimit -n
500

我明白了:

panic: Get http://127.0.0.1:51227: dial tcp 127.0.0.1:51227: socket: too many open files

** 不要落入 Praveen 做过的陷阱 **

注意 ulimit != ulimit -n.

➜  cmd git:(wip-poop) ✗ ulimit -a
-t: cpu time (seconds)              unlimited
-f: file size (blocks)              unlimited
-d: data seg size (kbytes)          unlimited
-s: stack size (kbytes)             8192
-c: core file size (blocks)         0
-v: address space (kbytes)          unlimited
-l: locked-in-memory size (kbytes)  unlimited
-u: processes                       1418
-n: file descriptors                4864

关于sockets - 去吧,tcp打开文件太多调试,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/32325343/

相关文章:

c - 如何在关闭 TCP 连接之前发送消息 [POSIX]

php - 通过套接字发送 2 个请求

go - 如何分析多个 goroutine

go - 如何将结构分配给接口(interface)

android - Linux 内核模块 unix 域套接字

perl - 来自Fileno和服务器实例的唯一数字连接ID

string - 通过字符串发送二进制数据包有优势吗?

mysql - db.Save()成功后如何查询关联

c - 使用 fread 通过 UDP 发送数据的问题

node.js - ECONNRESET 后重新连接到套接字的正确方法(Nodejs net.Socket)