向Golang应用程序发出请求时,Postman上的套接字挂起

xhv8bpkk  于 2023-09-28  发布在  Go
关注(0)|答案(1)|浏览(162)

我已经在golang中构建了一个CRUD应用程序,遵循本教程:https://www.youtube.com/live/aLVJY-1dKz8?feature=shared
我已经连接到数据库并使用PgAdmin创建了postgres表。
服务使用Docker Compose启动。
但是 Postman 的请求不起作用。
我收到“错误:socket hang up”on postman和“dial tcp 127.0.0.1:5432:connect:connection refused”。
以下是此应用程序的两个文件:
docker-compose.yml

version: '3'

services:
  dicane-service:
    build:
      context: ./../dicane-service
      dockerfile: ./../dicane-service/dicane-service.dockerfile
    restart: always
    ports:
      - "8000:8000"
    deploy:
      mode: replicated
      replicas: 1
    environment:
      DSN: "host=postgres port=5432 user=postgres password=password dbname=postgres sslmode=disable timezone=UTC connect_timeout=5"
    depends_on:
      - postgres
      
  postgres:
    image: 'postgres:14.0'
    ports:
      - "5432:5432"
    restart: always
    deploy:
      mode: replicated
      replicas: 1
    environment:
      POSTGRES_USER: postgres
      POSTGRES_PASSWORD: password
      POSTGRES_DB: postgres
    volumes:
      - ./db-data/postgres/:/var/lib/postgresql/data/
  
  pg-admin:
    image: dpage/pgadmin4:7
    environment:
      - [email protected]
      - PGADMIN_DEFAULT_PASSWORD=password
      - PGADMIN_LISTEN_PORT=5050
    ports:
      - "5050:5050"

main.go

package main

import (
    "database/sql"
    "encoding/json"
    "log"
    "net/http"
    "os"
    "time"

    "github.com/gorilla/mux"
    _ "github.com/lib/pq"
)

type Sale struct {
    Sale_id                    string    `json:"sale_id"`
    removed the other fields to make this code sample smaller...
    Images                     []string  `json:"images"`
}

func main() {
    // connect to database
    db, err := sql.Open("postgres", os.Getenv("DATABASE_URL"))
    if err != nil {
        log.Fatal(err)
    }
    defer db.Close()

    //create router
    router := mux.NewRouter()
    router.HandleFunc("/sales", getSales(db)).Methods("GET")
    router.HandleFunc("/sales/{id}", getSale(db)).Methods("GET")
    router.HandleFunc("/sales", createSale(db)).Methods("POST")
    router.HandleFunc("/sales/{id}", updateSale(db)).Methods("PUT")
    router.HandleFunc("/sales/{id}", deleteSale(db)).Methods("DELETE")

    // start server
    log.Fatal(http.ListenAndServe(":8000", jsonContentTypeMiddleware(router)))

}

func jsonContentTypeMiddleware(next http.Handler) http.Handler {
    return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
        w.Header().Set("Content-Type", "application/json")
        next.ServeHTTP(w, r)
    })
}

func getSales(db *sql.DB) http.HandlerFunc {
    return func(w http.ResponseWriter, r *http.Request) {
        rows, err := db.Query("SELECT * FROM sales")
        if err != nil {
            log.Fatal(err)
        }
        defer rows.Close()

        sales := []Sale{}
        for rows.Next() {
            var sale Sale
            if err := rows.Scan(
                &sale.Sale_id,
                ... removed the other fields to make this code sample smaller... 
                &sale.Images,
            ); err != nil {
                log.Fatal(err)
            }
            sales = append(sales, sale)
        }
        if err := rows.Err(); err != nil {
            log.Fatal(err)
        }

        json.NewEncoder(w).Encode(sales)
    }
}

func getSale(db *sql.DB) http.HandlerFunc {
    print("getSale")
    return func(w http.ResponseWriter, r *http.Request) {
        vars := mux.Vars(r)
        id := vars["sale_id"]

        var sale Sale
        err := db.QueryRow("SELECT * FROM sales WHERE sale_id = $1", id).Scan(
            &sale.Sale_id,
            ... removed the other fields to make this code sample smaller... 
            &sale.Images,
        )
        if err != nil {
            log.Fatal(err)
        }

        json.NewEncoder(w).Encode(sale)
    }
}

func createSale(db *sql.DB) http.HandlerFunc {
    return func(w http.ResponseWriter, r *http.Request) {
        var sale Sale
        json.NewDecoder(r.Body).Decode(&sale)

        err := db.QueryRow("INSERT INTO sales ("+
            ... removed the other fields to make this code sample smaller... 
            " images)"+
            " VALUES ($1, $2, $3, $4, $5, $6, $7, $8, $9, $10, $11, $12, $13, $14, $15, $16, $17, $18, $21, $22, $23)"+
            " RETURNING sale_id",
            ... removed the other fields to make this code sample smaller... 
            ).Scan(&sale.Sale_id)
        if err != nil {
            log.Fatal(err)
        }
        json.NewEncoder(w).Encode(sale)
    }
}

func updateSale(db *sql.DB) http.HandlerFunc {
    return func(w http.ResponseWriter, r *http.Request) {
        var sale Sale
        json.NewDecoder(r.Body).Decode(&sale)

        vars := mux.Vars(r)
        saleId := vars["sale_id"]

        _, err := db.Exec("UPDATE sales SET"+
            ... removed the other fields to make this code sample smaller... 
            )+"WHERE id = $24",
            ... removed the other fields to make this code sample smaller... 
            saleId,
        )
        if err != nil {
            log.Fatal(err)
        }

        json.NewEncoder(w).Encode(sale)
    }
}

func deleteSale(db *sql.DB) http.HandlerFunc {
    return func(w http.ResponseWriter, r *http.Request) {
        vars := mux.Vars(r)
        saleId := vars["sale_id"]

        var sale Sale
        err := db.QueryRow("SELECT * FROM sales WHERE sale_id = $1", saleId).Scan(
            &sale.Sale_id,
            ... removed the other fields to make this code sample smaller
            &sale.Images,
        )
        if err != nil {
            w.WriteHeader(http.StatusNotFound)
            return
        } else {
            _, err := db.Exec("DELETE FROM sales WHERE sale_id = $1", saleId)
            if err != nil {
                //todo : fix error handling
                w.WriteHeader(http.StatusNotFound)
                return
            }

            json.NewEncoder(w).Encode("User deleted")
        }
    }
}
vlju58qv

vlju58qv1#

我在os.Getenv(DATABASE_URL)函数中得到了错误的值。
它应该与docker-compose.yml中声明的环境变量相匹配,该环境变量为:

environment:
      DSN: "host=postgres port=5432 user=postgres password=password dbname=postgres sslmode=disable timezone=UTC connect_timeout=5"

我刚刚从DSN改为DATABASE_URL

environment:
      DATABASE_URL: "host=postgres port=5432 user=postgres password=password dbname=postgres sslmode=disable timezone=UTC connect_timeout=5"

现在它正在工作:)

相关问题