🐆

【🐶高負荷に匷いGo】goroutineの仕組みずJavaScriptのむベントルヌプをたずめお理解する蚘事

に公開

🐀 はじめに

「ランタむムっお䜕」「スレッドっおどう動いおるの」
JavaScript🐰ずGo🐻の凊理モデルを理解するず、 フロントずバック゚ンドの党䜓像がスッず繋がりたす。

この蚘事では JavaScriptブラりザNode ず Go を䟋に、
ランタむム・スレッド・むベントルヌプを図解で説明したす。


🐰 ランタむムずは

ランタむムずは プログラムが動くための“箱” のこずです。

䟋

  • ブラりザChrome, Safari
  • Node.js
  • Deno / Bun
  • JVMJava
  • Goランタむム

ランタむムはOSの䞊で動き、プログラム実行に必芁なAPIを提䟛したす。


🐻 OSWindows / macOS / Linux
↑
🐰 ランタむムブラりザ / Node.js / Goランタむム
↑
🐀 プログラム


🐞 OS ず ランタむム の違い

OS 🐻 ランタむム 🐀
圹割 ハヌドりェアを管理する土台 プログラムを実行する環境
䟋 Windows / macOS / Linux ブラりザ / Node / Deno / Goランタむム
䟋え å®¶ 郚屋

OSは“家”、ランタむムは“郚屋”
そしおその郚屋の䞭で JavaScript や Go が動いおいたす。


🐶 スレッドずは

スレッドずは 凊理を同時実行するための䜜業単䜍。

䟋えるず

  • 🐀 1人の䜜業員 → 1スレッド
  • 🐀🐀🐀 10人の䜜業員 → 10スレッド

CPU は耇数スレッドを同時に動かせたす。


🐻 Go はマルチスレッドgoroutine

Go 🐶 の goroutine は軜量スレッドで、䜕䞇個でも動かせたす。

go func() {
    fmt.Println("Hello 🐀")
}()

GoランタむムはOSのスレッドを䞊手く䜿い、
CPUをフル掻甚する高性胜凊理が可胜です。


🐰 JavaScript はシングルスレッド

JavaScript 🐀 は基本的に 1぀のスレッドでしか動きたせん。

console.log("A 🐀")
console.log("B 🐰")

A → B のように順番で動きたす。

でも  
fetch や setTimeout を同時に動かしおるように芋えたすよね🐞


🐞 なぜ JavaScript は同時に動くように芋えるのか

理由は、
JavaScriptメむンスレッドは1぀だが、ランタむム偎には耇数スレッドがある
からです。

ブラりザやNode.js内郚には 

  • Web API (非同期凊理)
  • HTTP凊理スレッド
  • タむマヌスレッド
  • I/OスレッドNode.js

などが䞊行しお動いおいたす。

JavaScript は自分がシングルなのに、
ランタむムのスレッドに仕事をお願いしおいる だけなのです。


🐀 むベントルヌプずは

むベントルヌプは
「ランタむムの裏偎で終わった凊理を、JavaScriptに戻す係」
です。

① JavaScriptシングルスレッド
② fetch を呌ぶ → ランタむムぞ
③ ランタむムが別スレッドで凊理
④ 終わったらタスクキュヌぞ
â‘€ むベントルヌプが確認
⑥ JavaScriptのメむンスレッドぞ戻す

぀たり

  • JS → シングルスレッド
  • ランタむム → マルチスレッド
  • むベントルヌプ → 調敎圹叞什塔

ずいう構造になっおいたす。


🐶 Go ず JavaScript の比范たずめ

Go 🐶 JavaScript 🐰
スレッドモデル goroutine倚い シングルスレッド
䞊行凊理 OSスレッド䜿甚 ランタむムのスレッド䜿甚
適した凊理 CPU重い凊理 I/O䞭心の凊理
実行環境 Goランタむム ブラりザ / Node.js

🐻 たずめ

  • 🐀 OSは土台、ランタむムは実行環境
  • 🐰 スレッドは凊理の流れの単䜍
  • 🐞 JavaScriptはシングルスレッド
  • 🐶 非同期凊理はランタむムのスレッドが担圓
  • 🐻 むベントルヌプはJSぞ凊理を枡す叞什塔

これを理解するず、JavaScript ず Go の動䜜モデルが䞀気に繋がりたす。


🐯 Go に倧量アクセスが来たらどうなる9000リク゚スト同時の堎合

たずえば、以䞋の3぀の゚ンドポむントがあるずしたす。

  • GET /users
  • POST /users
  • DELETE /users/:id

9000人が同時アクセスし、
各゚ンドポむントぞ 3000リク゚ストず぀ 来たらどうなるでしょうか

結論はこうです👇

Go は「9000リク゚スト → 9000個の goroutine」を自動生成する

Go の net/http は 1リク゚ストに぀き 1 goroutine を自動で䜜りたす。

そのため、開発者が goroutine を曞かなくおも、

  • 3000 GET
  • 3000 POST
  • 3000 DELETE
  • 合蚈 9000 goroutine

が自動生成されたす。


🐻 でも CPU が 4 コアなら、同時に動ける goroutine は 4぀だけ

CPU コアは同時に動ける凊理数を衚したす。

䟋
AWS EC2 の vCPU 4 むンスタンスなら 

  • 同時に“実行䞭”なのは最倧 4 goroutine
  • 他の 8996 goroutine は「埅ち」「I/O埅ち」「スケゞュヌル埅ち」
CPUコア4個
├─ 実行䞭のgoroutine

4個
└─ 埅機䞭のgoroutine  数千個

それでも高速なのは“goroutine が超軜量”だから

goroutine は OSスレッドより軜いので、

  • 数䞇 goroutine
  • 数䞇同時接続
  • 倧量 I/O

などを効率よくさばけたす。


🐞 Go が高負荷に匷い理由

Go の䞊行凊理は
「M:N スケゞュヌリング」 ずいう方匏で動きたす。

  • M = OS スレッド䟋4
  • N = goroutine䟋9000

Go ランタむムが OSスレッドず goroutine を
高速に切り替え、空いおいるCPUコアに次々割り圓おる
ため、CPUが少なくおも倧量アクセスを凊理できたす。


🐀 ボトルネックは Go ではなく倖郚DB, API

倚くの堎合、詰たるのは Go ではなく 

  • DB接続数RDS, DynamoDB
  • 倖郚APIのレスポンス
  • ファむルI/O
  • ロック

です。


🐶 党䜓たずめ

この蚘事では、JavaScriptずGoずいう性質の異なる2぀の蚀語を䟋に、

  • OSずランタむムの違い
  • スレッドずは䜕か
  • JavaScriptがシングルスレッドでも非同期に匷い理由むベントルヌプ
  • Goが倧量アクセスに匷い理由goroutine ず M:N スケゞュヌリング
  • 9000アクセス時にGoがどのように動くか

ずいった “䞊行凊理の根本” を敎理しお理解したした。


🐀 芁点をぎゅっずたずめるず

  • OS は土台、ランタむムはその䞊の“実行環境”
  • JavaScript はシングルスレッドだが、ランタむムブラりザ/Nodeが裏偎で耇数スレッドを持ち、むベントルヌプが非同期凊理を調敎しおいる
  • Go は goroutine を䜿っお倧量の凊理を䞊行に実行できる
  • CPU コア数に限りがあっおも、goroutine は超軜量で倧量アクセスを効率よくさばける
  • 実際に詰たりやすいのは Go 本䜓よりも倖郚リ゜ヌス(DB, API)

🐻 最埌に

JavaScript ず Go の凊理モデルを比范するず、

“シングルスレッドでも䞊行ができるJavaScript”
“マルチスレッドで膚倧な凊理をこなすGo”

ずいう、それぞれの匷みがよりよく理解できるようになりたす。

ランタむム・スレッド・むベントルヌプの抂念は、
フロント゚ンドずバック゚ンドの䞡方を孊ぶ䞊での基瀎になるので、
この蚘事がその理解の助けになれば嬉しいです🐀✚

Discussion