用 Elixir 重写 WebRTC 语音聊天室,自带集群扩容 - V2EX
V2EX = way to explore
V2EX 是一个关于分享和探索的地方
现在注册
已注册用户请  登录
爱意满满的作品展示区。
bmpidev2019
V2EX    分享创造

用 Elixir 重写 WebRTC 语音聊天室,自带集群扩容

  •  3
     
  •   bmpidev2019
    PRO
    madawei2699 2022-10-17 23:35:47 +08:00 6177 次点击
    这是一个创建于 1090 天前的主题,其中的信息可能已经有所发展或是发生改变。

    之前写过一个帖子在这里: https://v2ex.com/t/828646

    Repo: https://github.com/madawei2699/free4chat

    最近花了一周时间重写了 http://free4.chat ,加入了文字聊天功能(花费 1 天时间)。新的技术栈:

    • 后端:Elixir + Phoenix
    • 前端:Nexitjs + Tailwindcss + RxJS

    后端用 Elixir/Erlang 的好处是自带集群功能,目前两台服务器组建集群,客户端随机负载均衡策略选择某个服务器做接入,同一房间的用户可以分布在不同节点的服务器,相比之前 Go 语言的版本,有了极大的 Scale 能力。Elixir/Erlang 还有极其强大的可观测能力,可以在运行时 remote 到 VM 中查看 process 的状态。

    前端用 NextJS 和 Tailwindcss 的好处在于大量的组件可以拿来即用,Tailwindcss 相比之前一些 UI 库好用到爆,可以让我这种前端小白在短时间糊出来还不错的页面,强烈推荐! RxJS 做组件间的通信工具,感觉比 Redux 要简单多了,Redux 是有点复杂。

    DevOps 的话,后端部署是用 GitHub Actions 将 Docker 容器远程部署在 AWS EC2 上。前端是部署在 @Cloudflare Pages ,后端 API 服务器没有用 Nginx ,通过 iptables 将 80/443 端口流量转发至容器监听的端口,HTTPS/TLS 是由 @Cloudflare 自动配置的。

    监控的话就用 Elixir hoenix 的 LiveDashboard 了。

    30 条回复    2024-08-18 18:17:41 +08:00
    Aloento
        1
    Aloento  
       2022-10-17 23:47:24 +08:00
    这前端太好看了吧
    DeWjjj
        2
    DeWjjj  
       2022-10-18 08:26:51 +08:00
    学习了,非常有用。
    aeli
        3
    aeli  
       2022-10-18 09:30:22 +08:00
    为什么会想用 ELixir 重写,而不是继续改进 Golang 版本?
    bmpidev2019
        4
    bmpidev2019  
    OP
    PRO
       2022-10-18 09:33:08 +08:00 via iPhone   1
    @aeli 不喜欢 go 的语法,开发效率没有 elixir 高,更重要的是因为 turn 单体的约束,很难搞集群,但在 erlang/otp 的加持下,集群是个自带的功能。当然 go 的库更多一些,elixir 可能需要自己封装一些库,不过也不是啥难事
    penzi
        5
    penzi  
       2022-10-18 10:41:22 +08:00 via Android
    @bmpidev2019 turn 和 kraken 是分开的吧,只需要在 kraken 的 turn 接口多配置几个 coturn 返回就行了
    bmpidev2019
        6
    bmpidev2019  
    OP
    PRO
       2022-10-18 11:14:23 +08:00 via iPhone
    @maggch97 这也算个方法,但不是我期望的 scale ,这种方法也解决不了同一个房间用户分布在多个节点上的问题,但这些问题在 elixir 版本中都已经解决了,相比 go 有着更少的内存使用(默认 80MB 的内存开销),erlang 的基于 process 的内存回收效率也比 go 的 gc 要高效(之前 go 版本用户几十人时可能会达到几百 MB 的开销,用户降低时内存并没有随之回收,导致我有时候不得不重启服务器,服务器 1G 内存)。还有就是 go 的 debug 比较复杂,这和 webrtc 本身协议众多也有关系,但 elixir 我直接 remote 到 vm 上去看 process 的信息,看状态,发消息,这种 debug 太方便了。
    cgpiao
        7
    cgpiao  
       2022-10-19 11:23:45 +08:00 via iPhone
    erlang otp 的 scale 能力是相当的令人印象深刻。
    elixir 优点和缺点都在于 erlang ,可以不用自己创造基磐,但你不会用 erlang 的话 elixir 也很难玩转。学习相当需要时间和锻炼。
    shawndev
        8
    shawndev  
       2022-10-19 11:51:28 +08:00
    好看
    bmpidev2019
        9
    bmpidev2019  
    OP
    PRO
       2022-10-19 15:50:10 +08:00 via iPhone
    @cgpiao 门槛还是有的,但 elixir 可以直接调用 erlang-otp 的库,一般不需要造轮子,顶多封装下。
    zealinux
        10
    zealinux  
       2022-10-20 19:53:02 +08:00
    @bmpidev2019

    你说的“Elixir/Erlang 的好处是 [自带集群功能] ”,这个是什么意思?

    有关键字吗?我去搜一下什么原理。
    chancat
        11
    chancat  
       2022-10-20 21:28:57 +08:00 via Android
    额。。这个项目,有哪些场景会用到吗?
    bmpidev2019
        12
    bmpidev2019  
    OP
    PRO
       2022-10-20 22:24:04 +08:00 via iPhone
    @zealinux 直接看 erlang 的介绍就知道了
    moose123
        13
    moose123  
       2022-10-21 10:33:52 +08:00
    这个界面是 elixir 的 phoenix 自带的,这方面开箱即用确实爽,elixir 擅长的还是 message 方面的应用,不过我们也拿来做其他的,如多人 h5 页游,很多东西也是开箱即用,之前也想过用 golang 做,看了下要处理太多 ws 的东西,还是用 phonex 搞吧,这样只关心业务,不用担心 scale ,并发等问题....
    bmpidev2019
        14
    bmpidev2019  
    OP
    PRO
       2022-10-21 14:22:21 +08:00 via iPhone
    @moose123 如果一个应用最终要关系 scale 和容错的问题,那用 elixir 搞肯定是一个好的选择,如果用其他语言,scale 用 k8s 之类方案可以搞,但总是带来一定复杂度,甚至在细粒度的控制方面是不如 elixir/erlang-otp 的。还有如果要做实时通信类的应用,elixir 也不错,phoenix 自带 websocket 。公司项目技术栈有很多考量,但个人项目用 elixir 搞是很爽的。
    moose123
        15
    moose123  
       2022-10-21 21:13:22 +08:00   1
    @bmpidev2019 elixir+phoenix 适合一人一公司的技术栈,提供一些开箱即用的东西,可以快速把东西搞出来,我拿来搞 crm,cms,电商这些....
    bmpidev2019
        16
    bmpidev2019  
    OP
    PRO
       2022-10-22 07:29:03 +08:00 via iPhone
    @moose123 相当于实时通信 Web ( real-time )的 Python+Django 组合,迅速出活,实时交互。所以 free4.chat 这个项目我设计了三大 feature:Real-time Communicating ,基于语音的实时聊天; Real-time Collaborating:基于白板的实时协作; Real-time Contesting:与其他人实时比赛,玩一些基于语音的游戏,比如可以通过语音与他人练习口语。这一切的底层都是实时与自动扩容,这些都得益于 Elixir/Erlang-otp 的支持,让开发效率变得无比快捷,服务器资源要求也很低。
    xieren58
        17
    xieren58  
       2022-10-22 12:10:44 +08:00
    rust 走起.
    bmpidev2019
        18
    bmpidev2019  
    OP
    PRO
       2022-10-22 15:04:22 +08:00 via iPhone
    @xieren58 用 rust 搞明年也上线不了
    moose123
        19
    moose123  
       2022-10-23 11:51:17 +08:00
    @bmpidev2019 选用 elixir 其实就是快速出东西,phoenix+ecto 都很方便,再加上 erlang 的稳定性,在创业前中期完全够用了,唯一的问题就是人员跟不上,基本上需要自己培养。
    bmpidev2019
        20
    bmpidev2019  
    OP
    PRO
       2022-10-23 12:55:50 +08:00 via iPhone
    @moose123 小众语言招聘难是个绊脚石,只能招学习能力好的培养了,好在入门也很快,起码比 rust 快多了另外工作机会少也导致大家不愿意投资这个技术,作为 side project 倒很好,出活快。
    moose123
        21
    moose123  
       2022-10-24 14:26:05 +08:00
    @bmpidev2019 Elixir 更适合创业者、小团队,如果想学习一门语言养家糊口的,自然会选择 java 这些了,就是因为有更多的选择才好玩,现在微服务这么流行,某些服务用 Elixir ,某些服务用 java 也没啥问题。
    bmpidev2019
        22
    bmpidev2019  
    OP
    PRO
       2022-10-24 21:18:23 +08:00 via iPhone
    @moose123 团队用完 elixir 就回不去了
    moose123
        23
    moose123  
       2022-10-27 15:37:35 +08:00
    @bmpidev2019 你们集群有多少个节点啊?
    bmpidev2019
        24
    bmpidev2019  
    OP
    PRO
       2022-10-27 16:04:56 +08:00 via iPhone
    @moose123 我现在就 2 个
    penzi
        25
    penzi  
       2022-11-26 12:44:42 +08:00   1
    @bmpidev2019 挖个坟,我当时很怀疑比较更接近底层的 Golang 怎么会有更差的内存占用。直到我最近也部署了 kraken 的服务,遇到了一样的内存占用问题。

    我看了一下代码。这不是 Golang 的问题,而是 kraken 本身实现问题。它的所有房间信息以及所有用户连接的资源并没有被正确释放,所有断开的连接仅仅被标记了一个 delete 的 id 。

    issue: https://github.com/MixinNetwork/kraken/issues/32
    bmpidev2019
        26
    bmpidev2019  
    OP
    PRO
       2022-11-26 14:33:08 +08:00 via iPhone
    @maggch97 应该不是 golang 的问题,是 sfu 实现的问题,pion 本身应该也 OK ,不过调试真困难是真的
    penzi
        27
    penzi  
       2022-11-29 23:00:51 +08:00
    @bmpidev2019 更新一下,使用修复后的代码,36 个活跃用户服务器占用 66M ,内存泄漏的问题也没有了。
    bmpidev2019
        28
    bmpidev2019  
    OP
    PRO
       2022-11-30 16:01:25 +08:00 via iPhone
    @maggch97 这个开销才正常一些但你怎么统计实时用户的?
    penzi
        29
    penzi  
       2022-11-30 16:49:36 +08:00 via Android
    @bmpidev2019 rpc 里面有一个 info method 的
    dwu8555
        30
    dwu8555  
       2024-08-18 18:17:41 +08:00
    网站居然还能打开
    关于     帮助文档     自助推广系统     博客     API     FAQ     Solana     1388 人在线   最高记录 6679       Select Language
    创意工作者们的社区
    World is powered by solitude
    VERSION: 3.9.8.5 24ms UTC 16:49 PVG 00:49 LAX 09:49 JFK 12:49
    Do have faith in what you're doing.
    ubao snddm index pchome yahoo rakuten mypaper meadowduck bidyahoo youbao zxmzxm asda bnvcg cvbfg dfscv mmhjk xxddc yybgb zznbn ccubao uaitu acv GXCV ET GDG YH FG BCVB FJFH CBRE CBC GDG ET54 WRWR RWER WREW WRWER RWER SDG EW SF DSFSF fbbs ubao fhd dfg ewr dg df ewwr ewwr et ruyut utut dfg fgd gdfgt etg dfgt dfgd ert4 gd fgg wr 235 wer3 we vsdf sdf gdf ert xcv sdf rwer hfd dfg cvb rwf afb dfh jgh bmn lgh rty gfds cxv xcv xcs vdas fdf fgd cv sdf tert sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf shasha9178 shasha9178 shasha9178 shasha9178 shasha9178 liflif2 liflif2 liflif2 liflif2 liflif2 liblib3 liblib3 liblib3 liblib3 liblib3 zhazha444 zhazha444 zhazha444 zhazha444 zhazha444 dende5 dende denden denden2 denden21 fenfen9 fenf619 fen619 fenfe9 fe619 sdf sdf sdf sdf sdf zhazh90 zhazh0 zhaa50 zha90 zh590 zho zhoz zhozh zhozho zhozho2 lislis lls95 lili95 lils5 liss9 sdf0ty987 sdft876 sdft9876 sdf09876 sd0t9876 sdf0ty98 sdf0976 sdf0ty986 sdf0ty96 sdf0t76 sdf0876 df0ty98 sf0t876 sd0ty76 sdy76 sdf76 sdf0t76 sdf0ty9 sdf0ty98 sdf0ty987 sdf0ty98 sdf6676 sdf876 sd876 sd876 sdf6 sdf6 sdf9876 sdf0t sdf06 sdf0ty9776 sdf0ty9776 sdf0ty76 sdf8876 sdf0t sd6 sdf06 s688876 sd688 sdf86