์•ˆ์ •์ ์ธ ๋ฐ์ดํ„ฐ ์ „์†ก์˜ ๊ธฐ๋ณธ

์•ˆ์ •์ ์ธ ๋ฐ์ดํ„ฐ ์ „์†ก์˜ ๊ธฐ๋ณธ

ํ•˜๋Š” ๋ถ„๋“ค์—๊ฒŒ ์ถ”๊ตฌํ•˜๋‹ค ๋„คํŠธ์›Œํฌ์™€ ํ”„๋กœํ† ์ฝœ์„ ์ดํ•ดํ•˜๋Š” ๋ฐ ์ „๋…ํ•ฉ๋‹ˆ๋‹ค.

๊ฐ„๋‹จํžˆ

์ด ๊ธฐ์‚ฌ์—์„œ๋Š” ์•ˆ์ •์ ์ธ ๋ฐ์ดํ„ฐ ์ „์†ก์˜ ๊ธฐ๋ณธ ์‚ฌํ•ญ์„ ๋…ผ์˜ํ•˜๊ณ  ์ด์— ๋Œ€ํ•œ ์˜ˆ๋ฅผ ๊ตฌํ˜„ํ•ฉ๋‹ˆ๋‹ค. GoUDP์™€ TCP๋ฅผ ํฌํ•จํ•ฉ๋‹ˆ๋‹ค. ๊ธฐ๋ฐ˜์œผ๋กœ ์‹œ๊ฐ„, ะดะฒะฐ, ์„ธ ๊ทธ๋ฆฌ๊ณ  "์ปดํ“จํ„ฐ ๋„คํŠธ์›Œํฌ: ์ƒํ–ฅ์‹ ์ ‘๊ทผ๋ฒ•"์ด๋ผ๋Š” ์ฑ…์ด ์žˆ๋Š”๋ฐ, ๊ทธ ์™ธ์—๋Š” ๋ชจ๋‘๊ฐ€ ํƒ„๋„จ๋ฐ”์›€๊ณผ ์˜ฌ๋ฆฌํŽ˜๋กœํ”„์— ๋Œ€ํ•ด์„œ๋งŒ ๋…ผ์˜ํ•ฉ๋‹ˆ๋‹ค.

์ „์†ก ๊ณ„์ธต ํ”„๋กœํ† ์ฝœ

์„œ๋กœ ๋‹ค๋ฅธ ํ˜ธ์ŠคํŠธ์—์„œ ์‹คํ–‰๋˜๋Š” ์• ํ”Œ๋ฆฌ์ผ€์ด์…˜ ํ”„๋กœ์„ธ์Šค ๊ฐ„์— ๋…ผ๋ฆฌ์  ์—ฐ๊ฒฐ์„ ์ œ๊ณตํ•ฉ๋‹ˆ๋‹ค. ์• ํ”Œ๋ฆฌ์ผ€์ด์…˜ ๊ด€์ ์—์„œ ๋…ผ๋ฆฌ์  ์—ฐ๊ฒฐ์€ ํ”„๋กœ์„ธ์Šค๋ฅผ ์ง์ ‘ ์—ฐ๊ฒฐํ•˜๋Š” ์ฑ„๋„๋กœ ๋‚˜ํƒ€๋‚ฉ๋‹ˆ๋‹ค.

์•ˆ์ •์ ์ธ ๋ฐ์ดํ„ฐ ์ „์†ก์˜ ๊ธฐ๋ณธ

์ „์†ก ๊ณ„์ธต ํ”„๋กœํ† ์ฝœ ์ตœ์ข… ์‹œ์Šคํ…œ์—์„œ๋Š” ์ง€์›๋˜์ง€๋งŒ ๋„คํŠธ์›Œํฌ ๋ผ์šฐํ„ฐ์—์„œ๋Š” ์ง€์›๋˜์ง€ ์•Š์Œ(์˜ˆ์™ธ - DPI). ์†ก์‹ ์ž ์ธก์—์„œ ์ „์†ก ๊ณ„์ธต์€ ์ „์†ก ์• ํ”Œ๋ฆฌ์ผ€์ด์…˜ ํ”„๋กœ์„ธ์Šค๋กœ๋ถ€ํ„ฐ ์ˆ˜์‹ ํ•œ ์• ํ”Œ๋ฆฌ์ผ€์ด์…˜ ๊ณ„์ธต ๋ฐ์ดํ„ฐ๋ฅผ ์„ธ๊ทธ๋จผํŠธ๋ผ๊ณ  ํ•˜๋Š” ์ „์†ก ๊ณ„์ธต ํŒจํ‚ท์œผ๋กœ ๋ณ€ํ™˜ํ•ฉ๋‹ˆ๋‹ค.

์•ˆ์ •์ ์ธ ๋ฐ์ดํ„ฐ ์ „์†ก์˜ ๊ธฐ๋ณธ

์ด๋Š” (ํ•„์š”ํ•œ ๊ฒฝ์šฐ) ์• ํ”Œ๋ฆฌ์ผ€์ด์…˜ ๊ณ„์ธต ๋ฉ”์‹œ์ง€๋ฅผ ์กฐ๊ฐ์œผ๋กœ ๋‚˜๋ˆ„๊ณ  ๊ฐ ์กฐ๊ฐ์— ์ „์†ก ๊ณ„์ธต ํ—ค๋”๋ฅผ ์ถ”๊ฐ€ํ•˜์—ฌ ์ˆ˜ํ–‰๋ฉ๋‹ˆ๋‹ค.

์•ˆ์ •์ ์ธ ๋ฐ์ดํ„ฐ ์ „์†ก์˜ ๊ธฐ๋ณธ

๊ทธ๋Ÿฐ ๋‹ค์Œ ์ „์†ก ๊ณ„์ธต์€ ์„ธ๊ทธ๋จผํŠธ๋ฅผ ์†ก์‹ ์ž์˜ ๋„คํŠธ์›Œํฌ ๊ณ„์ธต์œผ๋กœ ์ „๋‹ฌํ•˜๊ณ , ์—ฌ๊ธฐ์„œ ์„ธ๊ทธ๋จผํŠธ๋Š” ๋„คํŠธ์›Œํฌ ๊ณ„์ธต ํŒจํ‚ท(๋ฐ์ดํ„ฐ๊ทธ๋žจ)์— ์บก์Аํ™”๋˜์–ด ์ „์†ก๋ฉ๋‹ˆ๋‹ค. ์ˆ˜์‹  ์ธก์—์„œ๋Š” ๋„คํŠธ์›Œํฌ ๊ณ„์ธต์ด ๋ฐ์ดํ„ฐ๊ทธ๋žจ์—์„œ ์ „์†ก ๊ณ„์ธต ์„ธ๊ทธ๋จผํŠธ๋ฅผ ์ถ”์ถœํ•˜์—ฌ ์ „์†ก ๊ณ„์ธต์œผ๋กœ ์ „๋‹ฌํ•ฉ๋‹ˆ๋‹ค. ๊ทธ๋Ÿฐ ๋‹ค์Œ ์ „์†ก ๊ณ„์ธต์€ ์ˆ˜์‹ ๋œ ์„ธ๊ทธ๋จผํŠธ๋ฅผ ์ฒ˜๋ฆฌํ•˜์—ฌ ํ•ด๋‹น ๋ฐ์ดํ„ฐ๋ฅผ ์ˆ˜์‹  ์• ํ”Œ๋ฆฌ์ผ€์ด์…˜์—์„œ ์‚ฌ์šฉํ•  ์ˆ˜ ์žˆ๋„๋ก ํ•ฉ๋‹ˆ๋‹ค.

์•ˆ์ •์ ์ธ ๋ฐ์ดํ„ฐ ์ „์†ก์˜ ๊ธฐ๋ณธ

์•ˆ์ „ํ•œ ๋ฐ์ดํ„ฐ ์ „์†ก์˜ ์›์น™

์™„์ „ํžˆ ์•ˆ์ „ํ•œ ์ฑ„๋„์„ ํ†ตํ•œ ์•ˆ์ •์ ์ธ ๋ฐ์ดํ„ฐ ์ „์†ก

๊ฐ€์žฅ ๊ฐ„๋‹จํ•œ ๊ฒฝ์šฐ. ์†ก์‹ ์ธก์€ ์ƒ์œ„ ๊ณ„์ธต์—์„œ ๋ฐ์ดํ„ฐ๋ฅผ ์ˆ˜์‹ ํ•˜๊ณ , ์ด๋ฅผ ํฌํ•จํ•˜๋Š” ํŒจํ‚ท์„ ์ƒ์„ฑํ•˜์—ฌ ์ฑ„๋„์„ ํ†ตํ•ด ์ „์†กํ•ฉ๋‹ˆ๋‹ค.

์„œ๋ฒ„

package main

import (
    "log"
    "net"
)

func main() {
    // IP-ะฐะดั€ะตั ัะตั€ะฒะตั€ะฐ ะธ ะฟะพั€ั‚
    serverAddr, err := net.ResolveUDPAddr("udp", "127.0.0.1:12000")
    if err != nil {
        log.Fatal(err)
    }

    // ัะพะทะดะฐะตะผ ัะพะบะตั‚ ั ะฟะพั€ั‚ะพะผ
    serverConn, err := net.ListenUDP("udp", serverAddr)
    if err != nil {
        log.Fatal(err)
    }
    // ะพั‚ะปะพะถะตะฝะฝะพะต ะทะฐะบั€ั‹ั‚ะธะต ัะพะตะดะธะฝะตะฝะธั
    defer serverConn.Close()

    // ัะพะทะดะฐะตะผ ะฑัƒั„ะตั€ ะดะปั ะดะฐะฝะฝั‹ั…
    buf := make([]byte, 1024)

    // ะถะดะตะผ ัะพะตะดะธะฝะตะฝะธะต
    for {
        // ั‡ะธั‚ะฐะตะผ ะทะฐะฟั€ะพั
        n, addr, err := serverConn.ReadFromUDP(buf)
        // ะฟะตั€ะตะดะฐะตะผ ะดะฐะฝะฝั‹ะต ะฒ ะ’ะ•ะ ะฅะะ˜ะ™ ัƒั€ะพะฒะตะฝัŒ: ะฒ ะฝะฐัˆะตะผ ัะปัƒั‡ะฐะต stdout
        println(string(buf[0:n]), " form ", addr.IP.String())
        if err != nil {
            log.Fatal(err)
        }
        // ะพั‚ะฒะตั‚ะฐ ะฝะตั‚, ั‚.ะบ. ัั‚ะพ UDP + ะฝะฐะดะตะถะฝั‹ะน ะบะฐะฝะฐะป
    }
}

ํด๋ผ์ด์–ธํŠธ

package main

import (
    "fmt"
    "log"
    "net"
    "time"
)

func main() {
    // IP-ะฐะดั€ะตั ัะตั€ะฒะตั€ะฐ ะธ ะฟะพั€ั‚
    serverAddr, err := net.ResolveUDPAddr("udp", "127.0.0.1:12000")
    if err != nil {
        log.Fatal(err)
    }
    // ะปะพะบะฐะปัŒะฝั‹ะน IP-ะฐะดั€ะตั ะธ ะฟะพั€ั‚
    localAddr, err := net.ResolveUDPAddr("udp", "127.0.0.1:0")
    if err != nil {
        log.Fatal(err)
    }
    // ัƒัั‚ะฐะฝะพะฒะบะฐ ัะพะตะดะธะฝะตะฝะธั
    conn, err := net.DialUDP("udp", localAddr, serverAddr)
    if err != nil {
        log.Fatal(err)
    }
    // ะพั‚ะปะพะถะตะฝะฝะพะต ะทะฐะบั€ั‹ั‚ะธะต ัะพะตะดะธะฝะตะฝะธั
    defer conn.Close()

    for {
        // ะฟะพะปัƒั‡ะตะฝะธะต ะดะฐะฝะฝั‹ั… ะพั‚ ะ’ะ•ะ ะฅะะ•ะ“ะž ัƒั€ะพะฒะฝั
        fmt.Print("ะ’ะฒะตะดะธั‚ะต ัั‚ั€ะพั‡ะฝะพะต ะฟั€ะตะดะปะพะถะตะฝะธะต > ")
        var msg string
        _, err := fmt.Scanf("%s", &msg)
        if err != nil {
            log.Fatal(err)
        }
        // ะฟะตั€ะตะดะฐะตั‚ัั ะฟะพั‚ะพะบ ะฑะฐะนั‚, ะฐ ะฝะต ัั‚ั€ะพะบะฐ
        buf := []byte(msg)
        // ะทะฐะฟะธััŒ (ะฟะตั€ะตะดะฐั‡ะฐ) ะฒ ัะพะตะดะธะฝะตะฝะธะต
        _, err = conn.Write(buf)
        if err != nil {
            log.Fatal(err)
        }
        // 1 ัะตะบัƒะฝะดะพั‡ะบัƒ
        time.Sleep(time.Second * 1)
    }
}

์˜ค๋ฅ˜๊ฐ€ ๋ฐœ์ƒํ•  ์ˆ˜ ์žˆ๋Š” ์ฑ„๋„์„ ํ†ตํ•œ ์•ˆ์ •์ ์ธ ๋ฐ์ดํ„ฐ ์ „์†ก

๋‹ค์Œ ๋‹จ๊ณ„๋Š” ์ „์†ก๋œ ๋ชจ๋“  ํŒจํ‚ท์ด ๋ณด๋‚ธ ์ˆœ์„œ๋Œ€๋กœ ์ˆ˜์‹ ๋˜์—ˆ์ง€๋งŒ ์ฑ„๋„์ด ๋•Œ๋•Œ๋กœ ์™œ๊ณก๋œ ๋ฐ์ดํ„ฐ๋ฅผ ์ „์†กํ•˜๊ธฐ ๋•Œ๋ฌธ์— ํŒจํ‚ท์˜ ๋น„ํŠธ๊ฐ€ ์†์ƒ๋  ์ˆ˜ ์žˆ๋‹ค๊ณ  ๊ฐ€์ •ํ•˜๋Š” ๊ฒƒ์ž…๋‹ˆ๋‹ค.

์•ˆ์ •์ ์ธ ๋ฐ์ดํ„ฐ ์ „์†ก์˜ ๊ธฐ๋ณธ

์ด ๊ฒฝ์šฐ, ๋‹ค์Œ๊ณผ ๊ฐ™์€ ๋ฉ”์ปค๋‹ˆ์ฆ˜์ด ์ ์šฉ๋ฉ๋‹ˆ๋‹ค.

  • ์˜ค๋ฅ˜ ๊ฐ์ง€
  • ํ”ผ๋“œ๋ฐฑ;
  • ์žฌ์ „์†ก.

์ด๋Ÿฌํ•œ ์—ฌ๋Ÿฌ ๋ฒˆ์˜ ์ „์†ก ๋ฐ˜๋ณต์„ ์œ„ํ•œ ๋ฉ”์ปค๋‹ˆ์ฆ˜์„ ๊ฐ–์ถ˜ ์•ˆ์ •์ ์ธ ๋ฐ์ดํ„ฐ ์ „์†ก ํ”„๋กœํ† ์ฝœ์„ ARQ(Automatic Repeat reQuest) ํ”„๋กœํ† ์ฝœ์ด๋ผ๊ณ  ํ•ฉ๋‹ˆ๋‹ค.
๋˜ํ•œ, ์ˆ˜์‹ ์ž๊ฐ€ ๋งˆ์ง€๋ง‰ ํŒจํ‚ท์˜ ์ „์†ก ๊ฒฐ๊ณผ์— ๋Œ€ํ•œ ์ •๋ณด๋ฅผ ์ „ํ˜€ ๋ฐ›์ง€ ๋ชปํ•  ๊ฒฝ์šฐ ์˜์ˆ˜์ฆ์— ์˜ค๋ฅ˜๊ฐ€ ์žˆ์„ ๊ฐ€๋Šฅ์„ฑ์„ ๊ณ ๋ คํ•ด ๋ณผ ๊ฐ€์น˜๊ฐ€ ์žˆ์Šต๋‹ˆ๋‹ค.
์ด ๋ฌธ์ œ๋ฅผ ํ•ด๊ฒฐํ•˜๊ธฐ ์œ„ํ•œ ๋ฐฉ๋ฒ•์€ TCP ๋“ฑ์—์„œ ์‚ฌ์šฉ๋˜๋Š”๋ฐ, ํŒจํ‚ท์˜ ์ผ๋ จ ๋ฒˆํ˜ธ๊ฐ€ ํฌํ•จ๋œ ์ƒˆ๋กœ์šด ํ•„๋“œ๋ฅผ ๋ฐ์ดํ„ฐ ํŒจํ‚ท์— ์ถ”๊ฐ€ํ•˜๋Š” ๊ฒƒ์ž…๋‹ˆ๋‹ค.

์•ˆ์ •์ ์ธ ๋ฐ์ดํ„ฐ ์ „์†ก์˜ ๊ธฐ๋ณธ

ํŒจํ‚ท ์™œ๊ณก ๋ฐ ์†์‹ค์„ ํ—ˆ์šฉํ•˜๋Š” ์‹ ๋ขฐํ•  ์ˆ˜ ์—†๋Š” ์ฑ„๋„์„ ํ†ตํ•œ ์•ˆ์ •์ ์ธ ๋ฐ์ดํ„ฐ ์ „์†ก

๋ถˆํ–‰ํžˆ๋„ ์™œ๊ณก๊ณผ ํ•จ๊ป˜ ๋„คํŠธ์›Œํฌ์—์„œ ํŒจํ‚ท ์†์‹ค๋„ ๋ฐœ์ƒํ•ฉ๋‹ˆ๋‹ค.
๊ทธ๋ฆฌ๊ณ  ์ด ๋ฌธ์ œ๋ฅผ ํ•ด๊ฒฐํ•˜๊ธฐ ์œ„ํ•ด์„œ๋Š” ๋‹ค์Œ๊ณผ ๊ฐ™์€ ๋ฉ”์ปค๋‹ˆ์ฆ˜์ด ํ•„์š”ํ•ฉ๋‹ˆ๋‹ค.

  • ํŒจํ‚ท ์†์‹ค์˜ ์‚ฌ์‹ค ํ™•์ธ
  • ์†์‹ค๋œ ํŒจํ‚ท์„ ์ˆ˜์‹  ๋‹น์‚ฌ์ž์—๊ฒŒ ๋‹ค์‹œ ์ „๋‹ฌํ•ฉ๋‹ˆ๋‹ค.

๋˜ํ•œ, ํŒจํ‚ค์ง€์˜ ๋ถ„์‹ค๋ฟ๋งŒ ์•„๋‹ˆ๋ผ ์˜์ˆ˜์ฆ์˜ ๋ถ„์‹ค ๊ฐ€๋Šฅ์„ฑ, ๋˜๋Š” ์•„๋ฌด๊ฒƒ๋„ ๋ถ„์‹ค๋˜์ง€ ์•Š์€ ๊ฒฝ์šฐ ๋ฐฐ์†ก์ด ์ƒ๋‹นํžˆ ์ง€์—ฐ๋  ๊ฐ€๋Šฅ์„ฑ์— ๋Œ€ํ•œ ๋Œ€๋น„๋„ ํ•„์š”ํ•ฉ๋‹ˆ๋‹ค. ๋ชจ๋“  ๊ฒฝ์šฐ์— ๋™์ผํ•œ ์ผ์ด ์ผ์–ด๋‚ฉ๋‹ˆ๋‹ค. ํŒจํ‚ท์ด ๋‹ค์‹œ ์ „์†ก๋ฉ๋‹ˆ๋‹ค. ์‹œ๊ฐ„์„ ์ œ์–ดํ•˜๊ธฐ ์œ„ํ•ด ์ด ๋ฉ”์ปค๋‹ˆ์ฆ˜์€ ์นด์šดํŠธ๋‹ค์šด ํƒ€์ด๋จธ๋ฅผ ์‚ฌ์šฉํ•˜๋Š”๋ฐ, ์ด๋ฅผ ํ†ตํ•ด ๋Œ€๊ธฐ ๊ฐ„๊ฒฉ์˜ ๋์„ ๊ฒฐ์ •ํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค. ๊ทธ๋ž˜์„œ ํŒจํ‚ค์ง€์— ๊ทธ๋ฌผ TCPKeepAlive๋Š” ๊ธฐ๋ณธ์ ์œผ๋กœ 15์ดˆ๋กœ ์„ค์ •๋ฉ๋‹ˆ๋‹ค.

// defaultTCPKeepAlive is a default constant value for TCPKeepAlive times
// See golang.org/issue/31510
const (
    defaultTCPKeepAlive = 15 * time.Second
)

์†ก์‹  ์ธก์—์„œ๋Š” ํŒจํ‚ท์ด ์ „์†ก๋  ๋•Œ๋งˆ๋‹ค(์ฒซ ๋ฒˆ์งธ์™€ ๋‘ ๋ฒˆ์งธ ๋ชจ๋‘) ํƒ€์ด๋จธ๋ฅผ ์‹œ์ž‘ํ•ด์•ผ ํ•˜๊ณ , ํƒ€์ด๋จธ์˜ ์ธํ„ฐ๋ŸฝํŠธ๋ฅผ ์ฒ˜๋ฆฌํ•˜๊ณ , ํƒ€์ด๋จธ๋ฅผ ์ค‘์ง€ํ•ด์•ผ ํ•ฉ๋‹ˆ๋‹ค.

์ด์ œ ์šฐ๋ฆฌ๋Š” ์•ˆ์ •์ ์ธ ๋ฐ์ดํ„ฐ ์ „์†ก ํ”„๋กœํ† ์ฝœ์˜ ํ•ต์‹ฌ ๊ฐœ๋…์— ์ต์ˆ™ํ•ด์กŒ์Šต๋‹ˆ๋‹ค.

  • ์ฒดํฌ์„ฌ;
  • ํŒจํ‚ค์ง€์˜ ์ผ๋ จ๋ฒˆํ˜ธ
  • ํƒ€์ด๋จธ;
  • ๊ธ์ •์  ๋ฐ ๋ถ€์ •์  ์˜์ˆ˜์ฆ.

ํ•˜์ง€๋งŒ ๊ทธ๊ฒŒ ์ „๋ถ€๊ฐ€ ์•„๋‹ˆ์ฃ !

ํŒŒ์ดํ”„๋ผ์ธ์„ ์‚ฌ์šฉํ•œ ์•ˆ์ •์ ์ธ ๋ฐ์ดํ„ฐ ์ „์†ก ํ”„๋กœํ† ์ฝœ

์šฐ๋ฆฌ๊ฐ€ ์ด๋ฏธ ๊ณ ๋ คํ•œ ๋ฒ„์ „์—์„œ๋Š” ์•ˆ์ •์ ์ธ ์ „๋‹ฌ ํ”„๋กœํ† ์ฝœ์ด ๋งค์šฐ ๋น„ํšจ์œจ์ ์ž…๋‹ˆ๋‹ค. RTT๊ฐ€ ์ฆ๊ฐ€ํ•จ์— ๋”ฐ๋ผ ํ†ต์‹  ์ฑ„๋„์—์„œ ์ œ๊ณต๋˜๋Š” ์ „์†ก ์†๋„๊ฐ€ "๋А๋ ค์ง€๊ธฐ" ์‹œ์ž‘ํ•ฉ๋‹ˆ๋‹ค. ํšจ์œจ์„ฑ์„ ๋†’์ด๊ณ  ํ†ต์‹  ์ฑ„๋„ ์šฉ๋Ÿ‰์„ ๋” ์ž˜ ํ™œ์šฉํ•˜๊ธฐ ์œ„ํ•ด ํŒŒ์ดํ”„๋ผ์ธ์ด ์‚ฌ์šฉ๋ฉ๋‹ˆ๋‹ค.

์•ˆ์ •์ ์ธ ๋ฐ์ดํ„ฐ ์ „์†ก์˜ ๊ธฐ๋ณธ

ํŒŒ์ดํ”„๋ผ์ธ์„ ์‚ฌ์šฉํ•˜๋ฉด ๋‹ค์Œ๊ณผ ๊ฐ™์€ ๊ฒฐ๊ณผ๊ฐ€ ๋ฐœ์ƒํ•ฉ๋‹ˆ๋‹ค.

  • ๋ชจ๋“  ์ „์†ก ํŒจํ‚ท(์žฌ์ „์†ก ์ œ์™ธ)์ด ๊ณ ์œ ํ•˜๊ฒŒ ์‹๋ณ„๋˜์–ด์•ผ ํ•˜๋ฏ€๋กœ ์ˆœ์„œ ๋ฒˆํ˜ธ์˜ ๋ฒ”์œ„๋ฅผ ๋Š˜๋ฆฝ๋‹ˆ๋‹ค.
  • ์†ก์‹  ๋ฐ ์ˆ˜์‹  ์ธก์˜ ๋ฒ„ํผ๋ฅผ ๋Š˜๋ ค์•ผ ํ•  ํ•„์š”์„ฑ.

์‹œํ€€์Šค ๋ฒˆํ˜ธ์˜ ๋ฒ”์œ„์™€ ๋ฒ„ํผ ํฌ๊ธฐ ์š”๊ตฌ ์‚ฌํ•ญ์€ ํŒจํ‚ท ์†์ƒ, ์†์‹ค ๋ฐ ์ง€์—ฐ์— ๋Œ€์‘ํ•˜์—ฌ ํ”„๋กœํ† ์ฝœ์ด ์ทจํ•˜๋Š” ์กฐ์น˜์— ๋”ฐ๋ผ ๋‹ฌ๋ผ์ง‘๋‹ˆ๋‹ค. ํŒŒ์ดํ”„๋ผ์ธ์˜ ๊ฒฝ์šฐ ์˜ค๋ฅ˜ ์ˆ˜์ • ๋ฐฉ๋ฒ•์€ ๋‘ ๊ฐ€์ง€๊ฐ€ ์žˆ์Šต๋‹ˆ๋‹ค.

  • N๊ฐœ์˜ ํŒจํ‚ท์„ ๋‹ค์‹œ ๋ฐ˜ํ™˜ํ•ฉ๋‹ˆ๋‹ค.
  • ์„ ํƒ์  ๋ฐ˜๋ณต.

์—ญ๋ฐฉํ–ฅ N ํŒจํ‚ท - ์Šฌ๋ผ์ด๋”ฉ ์œˆ๋„์šฐ ํ”„๋กœํ† ์ฝœ

์•ˆ์ •์ ์ธ ๋ฐ์ดํ„ฐ ์ „์†ก์˜ ๊ธฐ๋ณธ

๋ฐœ์‹ ์ž๋Š” ์„ธ ๊ฐ€์ง€ ์œ ํ˜•์˜ ์ด๋ฒคํŠธ๋ฅผ ์ง€์›ํ•ด์•ผ ํ•ฉ๋‹ˆ๋‹ค.

  • ์ƒ์œ„ ๋ ˆ๋ฒจ ํ”„๋กœํ† ์ฝœ์— ์˜ํ•œ ํ˜ธ์ถœ. "์œ„์—์„œ" ๋ฐ์ดํ„ฐ ์ „์†ก ํ•จ์ˆ˜๊ฐ€ ํ˜ธ์ถœ๋˜๋ฉด, ์ „์†ก ์ธก์—์„œ๋Š” ๋จผ์ € ์ฐฝ์ด ์ฑ„์›Œ์ง„ ์ •๋„(์ฆ‰, ์ˆ˜์‹  ํ™•์ธ์„ ๊ธฐ๋‹ค๋ฆฌ๋Š” N๊ฐœ์˜ ์ „์†ก๋œ ๋ฉ”์‹œ์ง€๊ฐ€ ์žˆ๋Š”์ง€)๋ฅผ ํ™•์ธํ•ฉ๋‹ˆ๋‹ค. ์ฐฝ์ด ์ฑ„์›Œ์ง€์ง€ ์•Š์œผ๋ฉด ์ƒˆ๋กœ์šด ํŒจํ‚ท์ด ํ˜•์„ฑ๋˜์–ด ์ „์†ก๋˜๊ณ , ๋ณ€์ˆ˜์˜ ๊ฐ’์ด ์—…๋ฐ์ดํŠธ๋ฉ๋‹ˆ๋‹ค. ๊ทธ๋ ‡์ง€ ์•Š์œผ๋ฉด, ์†ก์‹ ์ธก์€ ์ƒ์œ„ ๊ณ„์ธต์œผ๋กœ ๋ฐ์ดํ„ฐ๋ฅผ ๋ฐ˜ํ™˜ํ•˜๋Š”๋ฐ, ์ด๋Š” ์ฐฝ์ด ๊ฐ€๋“ ์ฐผ๋‹ค๋Š” ์•”๋ฌต์ ์ธ ํ‘œ์‹œ์ž…๋‹ˆ๋‹ค. ์ผ๋ฐ˜์ ์œผ๋กœ ์ƒ์œ„ ๊ณ„์ธต์€ ์ผ์ • ์‹œ๊ฐ„์ด ์ง€๋‚œ ํ›„์— ๋ฐ์ดํ„ฐ ์ „์†ก์„ ๋‹ค์‹œ ์‹œ๋„ํ•ฉ๋‹ˆ๋‹ค. ์‹ค์ œ ์• ํ”Œ๋ฆฌ์ผ€์ด์…˜์—์„œ ์†ก์‹ ์ž๋Š” ๋ฐ์ดํ„ฐ๋ฅผ ์ฆ‰์‹œ ์ „์†กํ•˜๋Š” ๋Œ€์‹  ๋ฒ„ํผ๋งํ•˜๊ฑฐ๋‚˜, ์ฐฝ์ด ๊ฐ€๋“ ์ฐจ์ง€ ์•Š์•˜์„ ๋•Œ๋งŒ ์ƒ์œ„ ๊ณ„์ธต์—์„œ ์ „์†ก ํ•จ์ˆ˜๋ฅผ ํ˜ธ์ถœํ•  ์ˆ˜ ์žˆ๋„๋ก ํ•˜๋Š” ๋™๊ธฐํ™” ๋ฉ”์ปค๋‹ˆ์ฆ˜(์„ธ๋งˆํฌ์–ด๋‚˜ ํ”Œ๋ž˜๊ทธ ๋“ฑ)์„ ๊ฐ€์งˆ ๊ฐ€๋Šฅ์„ฑ์ด ๋†’์Šต๋‹ˆ๋‹ค.
  • ํ™•์ธ์„ ๋ฐ›์Œ. ํ”„๋กœํ† ์ฝœ์—์„œ ์ผ๋ จ ๋ฒˆํ˜ธ๊ฐ€ N์ธ ํŒจํ‚ท์— ๋Œ€ํ•ด์„œ๋Š” ์ผ๋ฐ˜ ํ™•์ธ์ด ๋ฐœํ–‰๋˜์–ด ์ผ๋ จ ๋ฒˆํ˜ธ๊ฐ€ N๋ณด๋‹ค ์•ž์„  ๋ชจ๋“  ํŒจํ‚ท์ด ์„ฑ๊ณต์ ์œผ๋กœ ์ˆ˜์‹ ๋˜์—ˆ์Œ์„ ๋‚˜ํƒ€๋ƒ…๋‹ˆ๋‹ค.
  • ์ œํ•œ ์‹œ๊ฐ„์ด ๋งŒ๋ฃŒ๋˜์—ˆ์Šต๋‹ˆ๋‹ค. ์ด ํ”„๋กœํ† ์ฝœ์€ ํƒ€์ด๋จธ๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ ํŒจํ‚ท๊ณผ ์ˆ˜์‹  ์†์‹ค ๋ฐ ์ง€์—ฐ์„ ๊ฐ์ง€ํ•ฉ๋‹ˆ๋‹ค. ์‹œ๊ฐ„ ์ดˆ๊ณผ ๊ฐ„๊ฒฉ์ด ๋งŒ๋ฃŒ๋˜๋ฉด ์†ก์‹  ์ธก์€ ์ „์†ก๋œ ๋ชจ๋“  ํ™•์ธ๋˜์ง€ ์•Š์€ ํŒจํ‚ท์„ ๋‹ค์‹œ ์ „์†กํ•ฉ๋‹ˆ๋‹ค.

์„ ํƒ์  ๋ฐ˜๋ณต

์ฐฝ ํฌ๊ธฐ์™€ ์ฒ˜๋ฆฌ๋Ÿ‰-์ง€์—ฐ ๊ณฑ์ด ํฌ๋ฉด ํŒŒ์ดํ”„๋ผ์ธ์— ๋งŽ์€ ์ˆ˜์˜ ํŒจํ‚ท์ด ์žˆ์„ ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค. ์ด๋Ÿฐ ๊ฒฝ์šฐ, ๋‹จ์ผ ํŒจํ‚ท์˜ ์˜ค๋ฅ˜๋กœ ์ธํ•ด ๋งŽ์€ ์ˆ˜์˜ ํŒจํ‚ท์ด ์žฌ์ „์†ก๋˜์–ด์•ผ ํ•˜๋ฉฐ, ๊ทธ ์ค‘ ๋Œ€๋ถ€๋ถ„์€ ํ•„์š”ํ•˜์ง€ ์•Š์€ ํŒจํ‚ท์ž…๋‹ˆ๋‹ค.

์˜ˆ

์ƒ๋‹จ ์ด๋ก ์ ์ธ ์‹ค์ œ ๊ตฌํ˜„์„ ์œ„ํ•œ ์‚ฌ๋ก€ ์ˆ˜์ง‘ TCP. ๊ทธ๋ฆฌ๊ณ  ๋ˆ„๊ตฐ๊ฐ€๊ฐ€ ๋” ์ž˜ ์•Œ๊ณ  ์žˆ๋‹ค๋ฉด - ํ™˜์˜.

์„œ๋ฒ„

package main

import (
    "bufio"
    "fmt"
    "log"
    "net"
    "strings"
)

func main() {
    // ัะพะทะดะฐะตะผ ัะพะบะตั‚ ั ะฟะพั€ั‚ะพะผ 
    ln, err := net.Listen("tcp", ":8081")
    if err != nil {
        log.Fatalln(err)
    }
    // ะพะถะธะดะฐะฝะธะต ะฒั‹ะทะพะฒะฐ
    conn, _ := ln.Accept()

    for {
        // ัั‡ะธั‚ั‹ะฒะฐะฝะธะต ะดะฐะฝะฝั‹ั…
        msg, err := bufio.NewReader(conn).ReadString('n')
        if err != nil {
            log.Fatalln(err)
        }
        // ะฒั‹ะฒะพะด ัะพะพะฑั‰ะตะฝะธั ะฒ stdout
        fmt.Print("Message Received:", string(msg))
        // ะฟะตั€ะตะฒะพะด ัั‚ั€ะพะบะธ ะฒ ะฒะตั€ั…ะฝะธะน ั€ะตะณะธัั‚ั€
        newMsg := strings.ToUpper(msg)
        // ะพั‚ะฟั€ะฐะฒะบะฐ ะดะฐะฝะฝั‹ั…
        conn.Write([]byte(newMsg + "n"))
    }
}

ํด๋ผ์ด์–ธํŠธ

package main

import (
    "bufio"
    "fmt"
    "log"
    "net"
    "os"
)

func main() {
    // ัƒัั‚ะฐะฝะพะฒะบะฐ ัะพะตะดะธะฝะตะฝะธั
    conn, err := net.Dial("tcp", "127.0.0.1:8081")
    if err != nil {
        log.Fatalln(err)
    }

    for {
        // ัั‡ะธั‚ั‹ะฒะฐะฝะธะต ะดะฐะฝะฝั‹ั… ั stdin
        reader := bufio.NewReader(os.Stdin)
        fmt.Print("Text to send: ")
        // ะฟะพัั‚ั€ะพั‡ะฝะพ
        text, err := reader.ReadString('n')
        if err != nil {
            log.Fatalln(err)
        }
        // ะพั‚ะฟั€ะฐะฒะบะฐ
        fmt.Fprintf(conn, text+"n")
        // ะฟั€ะธะตะผ
        msg, err := bufio.NewReader(conn).ReadString('n')
        if err != nil {
            log.Fatalln(err)
        }
        // ะฒั‹ะฒะพะด ะฟะพะปัƒั‡ะตะฝะฝะพะณะพ ะพั‚ะฒะตั‚ะฐ
        fmt.Print("Msg from Server: " + msg)
    }
}

์ถœ๋ ฅ

์•ˆ์ •์ ์ธ ๋ฐ์ดํ„ฐ ์ „์†ก ๋ฐ ์‚ฌ์šฉ์„ ๋ณด์žฅํ•˜๋Š” ๋ฉ”์ปค๋‹ˆ์ฆ˜

๊ธฐ๊ตฌ
์‹ ์ฒญ, ์˜๊ฒฌ

์ฒดํฌ์„ฌ
์ „์†ก๋œ ํŒจํ‚ท์˜ ๋น„ํŠธ ์˜ค๋ฅ˜๋ฅผ โ€‹โ€‹๊ฐ์ง€ํ•˜๋Š” ๋ฐ ์‚ฌ์šฉ๋ฉ๋‹ˆ๋‹ค.

ํƒ€์ด๋จธ
์‹œ๊ฐ„ ์ดˆ๊ณผ ๊ฐ„๊ฒฉ์„ ์นด์šดํŠธ๋‹ค์šดํ•˜๊ณ  ๋งŒ๋ฃŒ์ผ์„ ํ‘œ์‹œํ•ฉ๋‹ˆ๋‹ค. ํ›„์ž๋Š” ํŒจํ‚ท์ด๋‚˜ ๊ทธ ์ˆ˜์‹ ์ด ์ „์†ก ์ค‘์— ์†์‹ค๋˜์—ˆ์„ ๊ฐ€๋Šฅ์„ฑ์ด ๋†’๋‹ค๋Š” ๊ฒƒ์„ ์˜๋ฏธํ•ฉ๋‹ˆ๋‹ค. ํŒจํ‚ท์ด ์ง€์—ฐ๋˜์–ด ์ „๋‹ฌ๋˜์—ˆ์ง€๋งŒ ์†์‹ค๋˜์ง€ ์•Š์€ ๊ฒฝ์šฐ(ํƒ€์ž„์•„์›ƒ ๊ฐ„๊ฒฉ์ด ์กฐ๊ธฐ์— ๋งŒ๋ฃŒ๋จ) ๋˜๋Š” ์ˆ˜์‹ ์ด ์†์‹ค๋œ ๊ฒฝ์šฐ, ์žฌ์ „์†ก์„ ์ˆ˜ํ–‰ํ•˜๋ฉด ์ˆ˜์‹  ์ธก์—์„œ ์ค‘๋ณต ํŒจํ‚ท์ด ์ƒ์„ฑ๋ฉ๋‹ˆ๋‹ค.

์ผ๋ จ ๋ฒˆํ˜ธ
์†ก์‹ ์ž๋กœ๋ถ€ํ„ฐ ์ˆ˜์‹ ์ž์—๊ฒŒ ์ „์†ก๋˜๋Š” ๋ฐ์ดํ„ฐ ํŒจํ‚ท์— ์ˆœ์ฐจ์ ์œผ๋กœ ๋ฒˆํ˜ธ๋ฅผ ๋งค๊ธฐ๋Š” ๋ฐ ์‚ฌ์šฉ๋ฉ๋‹ˆ๋‹ค. ์ˆ˜์‹ ๋œ ํŒจํ‚ท์˜ ์‹œํ€€์Šค ๋ฒˆํ˜ธ์— ์ฐจ์ด๊ฐ€ ์žˆ์œผ๋ฉด ์ˆ˜์‹ ๊ธฐ๊ฐ€ ํŒจํ‚ท ์†์‹ค์„ ๊ฐ์ง€ํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค. ํŒจํ‚ท์˜ ์‹œํ€€์Šค ๋ฒˆํ˜ธ๊ฐ€ ๋™์ผํ•˜๋‹ค๋Š” ๊ฒƒ์€ ํŒจํ‚ท์ด ์„œ๋กœ ์ค‘๋ณต๋œ๋‹ค๋Š” ๊ฒƒ์„ ์˜๋ฏธํ•ฉ๋‹ˆ๋‹ค.

ํ™•์ธ
์ˆ˜์‹  ๋‹น์‚ฌ์ž๊ฐ€ ์ƒ์„ฑํ•˜๋ฉฐ, ํ•ด๋‹น ํŒจํ‚ท์ด๋‚˜ ํŒจํ‚ท ๊ทธ๋ฃน์ด ์„ฑ๊ณต์ ์œผ๋กœ ์ˆ˜์‹ ๋˜์—ˆ์Œ์„ ์†ก์‹  ๋‹น์‚ฌ์ž์—๊ฒŒ ์•Œ๋ฆฝ๋‹ˆ๋‹ค. ์ผ๋ฐ˜์ ์œผ๋กœ ํ™•์ธ ๋ฉ”์‹œ์ง€์—๋Š” ์„ฑ๊ณต์ ์œผ๋กœ ์ˆ˜์‹ ๋œ ํŒจํ‚ท์˜ ์ˆœ์„œ ๋ฒˆํ˜ธ๊ฐ€ ํฌํ•จ๋ฉ๋‹ˆ๋‹ค. ํ”„๋กœํ† ์ฝœ์— ๋”ฐ๋ผ ๊ฐœ์ธ ํ™•์ธ๊ณผ ๋‹จ์ฒด ํ™•์ธ์ด ๊ตฌ๋ถ„๋ฉ๋‹ˆ๋‹ค.

๋ถ€์ •์  ํ™•์ธ
์ˆ˜์‹ ์ž๊ฐ€ ํŒจํ‚ท์„ ์ž˜๋ชป ์ˆ˜์‹ ํ–ˆ์Œ์„ ๋ฐœ์‹ ์ž์—๊ฒŒ ์•Œ๋ฆฌ๋Š” ๋ฐ ์‚ฌ์šฉ๋ฉ๋‹ˆ๋‹ค. ๋ถ€์ •์  ํ™•์ธ์—๋Š” ์ผ๋ฐ˜์ ์œผ๋กœ ์˜ฌ๋ฐ”๋ฅด๊ฒŒ ์ˆ˜์‹ ๋˜์ง€ ์•Š์€ ํŒจํ‚ท์˜ ์‹œํ€€์Šค ๋ฒˆํ˜ธ๊ฐ€ ํฌํ•จ๋ฉ๋‹ˆ๋‹ค.

์ฐฝ๋ฌธ, ํŒŒ์ดํ”„๋ผ์ธ
ํŒจํ‚ท์„ ์ „์†กํ•˜๋Š” ๋ฐ ์‚ฌ์šฉํ•  ์ˆ˜ ์žˆ๋Š” ์ˆœ์„œ ๋ฒˆํ˜ธ์˜ ๋ฒ”์œ„๋ฅผ ์ œํ•œํ•ฉ๋‹ˆ๋‹ค. ๋ฉ€ํ‹ฐ์บ์ŠคํŠธ์™€ ํ•ธ๋“œ์…ฐ์ดํฌ ์ „์†ก์€ ํ™•์ธ์„ ๊ธฐ๋‹ค๋ฆฌ๋Š” ๋ชจ๋“œ์— ๋น„ํ•ด ํ”„๋กœํ† ์ฝœ์˜ ์ฒ˜๋ฆฌ๋Ÿ‰์„ ํฌ๊ฒŒ ๋†’์ผ ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค. ๋ณด์‹œ๋‹ค์‹œํ”ผ, ์ฐฝ ํฌ๊ธฐ๋Š” ์ˆ˜์‹ ๋‹จ์˜ ์ˆ˜์‹  ๋ฐ ๋ฒ„ํผ๋ง ๊ธฐ๋Šฅ๊ณผ ๋„คํŠธ์›Œํฌ ๋ถ€ํ•˜ ์ˆ˜์ค€์„ ๊ธฐ๋ฐ˜์œผ๋กœ ๊ณ„์‚ฐ๋  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

๋” ๋งŽ์€ Go ๋„คํŠธ์›Œํ‚น ์˜ˆ์‹œ

ะ’ ์ €์žฅ์†Œ.

์ถœ์ฒ˜ : habr.com

์ฝ”๋ฉ˜ํŠธ๋ฅผ ์ถ”๊ฐ€