Skip to content

Commit

Permalink
update section56
Browse files Browse the repository at this point in the history
  • Loading branch information
gleaming9 committed Nov 13, 2024
1 parent 3b53ca6 commit a8fe1f5
Show file tree
Hide file tree
Showing 4 changed files with 111 additions and 2 deletions.
2 changes: 1 addition & 1 deletion _chapter14/section55/main.go
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
package main
package section55

import (
"context"
Expand Down
2 changes: 1 addition & 1 deletion _chapter14/section55/main_test.go
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
package main
package section55

import (
"context"
Expand Down
56 changes: 56 additions & 0 deletions _chapter14/section56/main.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,56 @@
package main

import (
"context"
"fmt"
"golang.org/x/sync/errgroup"
"log"
"net"
"net/http"
"os"
)

func run(ctx context.Context, l net.Listener) error {
s := &http.Server{
// 인수로 받은 net.Listener를 이용하므로 Addr 필드는 지정하지 않습니다.
Handler: http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
fmt.Fprintf(w, "Hello, %s!", r.URL.Path[1:])
}),
}
eg, ctx := errgroup.WithContext(ctx)
eg.Go(func() error {
// Serve 메서드로 변경합니다.
if err := s.Serve(l); err != nil &&
err != http.ErrServerClosed {
log.Printf("failed to close: %+v", err)
return err
}
return nil
})

<-ctx.Done()
if err := s.Shutdown(context.Background()); err != nil {
log.Printf("failed to shutdown: %+v", err)
}

return eg.Wait()
}

func main() {
// go run . 18080
if len(os.Args) != 2 {
log.Printf("need port number\n")
os.Exit(1)
}

p := os.Args[1]
l, err := net.Listen("tcp", ":"+p)
if err != nil {
log.Fatalf("failed to listen port %s: %v", p, err)
}

if err := run(context.Background(), l); err != nil {
log.Printf("failed to terminate server: %v", err)
os.Exit(1)
}
}
53 changes: 53 additions & 0 deletions _chapter14/section56/main_test.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,53 @@
package main

import (
"context"
"fmt"
"golang.org/x/sync/errgroup"
"io"
"net"
"net/http"
"testing"
)

func TestRun(t *testing.T) {
// net/http 에서는 포트 번호에 0을 지정하면 사용 가능한 포트 번호를 동적으로 선택합니다.
l, err := net.Listen("tcp", "localhost:0")
if err != nil {
t.Fatalf("failed to listen port %v", err)
}
ctx, cancel := context.WithCancel(context.Background())
eg, ctx := errgroup.WithContext(ctx)
eg.Go(func() error {
return run(ctx, l)
})

in := "message"
url := fmt.Sprintf("http://%s/%s", l.Addr().String(), in)
// 어떤 포트 번호로 리슨중인지 확인합니다.
t.Logf("try request to %q", url)
rsp, err := http.Get(url)

// 이후 코드 동일
if err != nil {
t.Errorf("failed to get: %+v", err)
}
defer rsp.Body.Close()

got, err := io.ReadAll(rsp.Body)
if err != nil {
t.Fatalf("failed to read body: %v", err)
}

// HTTP 서버의 반환값을 검증합니다.
want := fmt.Sprintf("Hello, %s!", in)
if string(got) != want {
t.Errorf("want %q, but got %q", want, got)
}

// run 함수를 종료합니다.
cancel()
if err := eg.Wait(); err != nil {
t.Fatal(err)
}
}

0 comments on commit a8fe1f5

Please sign in to comment.