![](/img/trans.png)
[英]VS Code will not build c++ programs with multiple .ccp source files
[英]Multiple go files in Docker build
我正在構建一個 Dockeried 應用程序,在其中將 go 文件拆分為兩個文件。
嘗試運行它時出現以下錯誤:
# command-line-arguments
./server.go:86:63: undefined: indexHandler
indexHandler 位於 server.go 中時工作正常,但我收到錯誤,它位於 handlers.go 中。
有什么建議么?
//server.go
package main
import (
"database/sql"
"fmt"
"log"
"net"
"net/http"
"os"
"os/exec"
"strconv"
"strings"
_ "github.com/go-sql-driver/mysql"
"github.com/gorilla/mux"
"github.com/jimlawless/whereami"
"github.com/rs/cors"
)
type FileSystem struct {
fs http.FileSystem
}
type dbConnection struct {
conn *sql.DB
}
var dbx dbConnection
var Config Configs
type Configs struct {
cookieName string
cookieValue string
cookieMaxAge int
cookieHTTPOnly bool
cookiePath string
domain string
port string
apiKey string
apiVersion string
apiPath string
protocol string
}
func setConfig() {
Config = Configs{}
Config.cookieName = os.Getenv("COOKIE_NAME")
Config.cookieValue = os.Getenv("COOKIE_VALUE")
age, err := strconv.Atoi(os.Getenv("COOKIE_MAX_AGE"))
if err != nil {
log.Println(whereami.WhereAmI(), err.Error())
}
Config.cookieMaxAge = age
Config.cookieHTTPOnly, err = strconv.ParseBool(os.Getenv("COOKIE_HTTP_ONLY"))
if err != nil {
log.Println(whereami.WhereAmI(), err.Error())
}
Config.cookiePath = os.Getenv("COOKIE_PATH")
Config.domain = os.Getenv("DOMAIN")
Config.port = os.Getenv("PORT")
Config.apiKey = os.Getenv("APP_KEY")
Config.apiVersion = os.Getenv("API_VERSION")
Config.apiPath = os.Getenv("API_PATH")
Config.protocol = os.Getenv("PROTOCOL")
}
func main() {
defer recoverPanic()
setConfig()
//db()
fmt.Println(Config)
target := Config.protocol + Config.domain + Config.port
corsOpts := cors.New(cors.Options{
AllowedOrigins: []string{target}, //you service is available and allowed for this base url
AllowedMethods: []string{
http.MethodGet, http.MethodPost, http.MethodPut, http.MethodPatch, http.MethodDelete, http.MethodOptions, http.MethodHead,
},
AllowedHeaders: []string{
"*", //or you can your header key values which you are using in your application
},
})
router := mux.NewRouter()
router.HandleFunc(Config.apiPath+Config.apiVersion+"/index", indexHandler).Methods("GET")
router.PathPrefix("/").Handler(http.FileServer(http.Dir("./")))
http.ListenAndServe(Config.port, corsOpts.Handler(router))
}
/*
func indexHandler(w http.ResponseWriter, req *http.Request) {
addCookie(w, Config.cookieName, Config.cookieValue)
cookie, err := req.Cookie(Config.cookieName)
if err != nil {
log.Println(whereami.WhereAmI(), err.Error())
}
log.Println("Cookie: ", cookie)
w.WriteHeader(http.StatusOK)
fmt.Fprintf(w, "hola")
}
*/
func addCookie(w http.ResponseWriter, name, value string) {
cookie := http.Cookie{
Name: Config.cookieName,
Value: Config.cookieValue,
Domain: Config.domain,
Path: Config.cookiePath,
MaxAge: Config.cookieMaxAge,
HttpOnly: Config.cookieHTTPOnly,
}
http.SetCookie(w, &cookie)
log.Println("Cookie added")
}
func (fs FileSystem) Open(path string) (http.File, error) {
f, err := fs.fs.Open(path)
if err != nil {
return nil, err
}
s, err := f.Stat()
if s.IsDir() {
index := strings.TrimSuffix(path, "/") + "/index.html"
if _, err := fs.fs.Open(index); err != nil {
return nil, err
}
}
return f, nil
}
func db() error {
db, err := sql.Open("mysql", "root:root@tcp(192.168.0.33:4200)/mysql")
if err != nil {
log.Print(err.Error())
} else {
log.Println("DB connected successfully")
}
defer db.Close()
err = db.Ping()
if err != nil {
log.Println("Ping Error: " + err.Error())
} else {
dbx.conn = db
}
return err
}
func recoverPanic() {
if rec := recover(); rec != nil {
err := rec.(error)
log.Println(whereami.WhereAmI(), err.Error())
var l *net.TCPListener
file, err := l.File()
if err != nil {
log.Println(whereami.WhereAmI(), err.Error())
}
path := os.Args
args := []string{"-graceful"}
cmd := exec.Command(path[0], args...)
cmd.Stdout = os.Stdout
cmd.Stderr = os.Stderr
cmd.ExtraFiles = []*os.File{file}
err2 := cmd.Start()
if err2 != nil {
log.Println(whereami.WhereAmI(), err2.Error())
} else {
log.Println(whereami.WhereAmI(), "Restarted...")
}
}
}
//handlers.go
package main
import (
"fmt"
"log"
"net/http"
"github.com/jimlawless/whereami"
)
func indexHandler(w http.ResponseWriter, req *http.Request) {
addCookie(w, Config.cookieName, Config.cookieValue)
cookie, err := req.Cookie(Config.cookieName)
if err != nil {
log.Println(whereami.WhereAmI(), err.Error())
}
log.Println("Cookie: ", cookie)
w.WriteHeader(http.StatusOK)
fmt.Fprintf(w, "hola")
}
注釋掉的行是我嘗試過但失敗的東西。
#Dockerfile
FROM golang:alpine AS builder
RUN mkdir /app
RUN rm -f go.mod go.sum
RUN go mod init xyz.com
RUN rm -f $GOPATH/go.mod
ADD . /app/
WORKDIR /app
COPY ./handlers.go .
COPY ./server.go .
COPY ./favicon.ico .
COPY ./assets /assets
COPY ./go.mod .
COPY ./go.sum .
RUN go mod download
COPY . .
RUN CGO_ENABLED=0 GOOS=linux GOARCH=amd64 go build $(ls -1 *.go)
# command-line-arguments
#./server.go:86:63: undefined: indexHandler
#RUN CGO_ENABLED=0 GOOS=linux GOARCH=amd64 go build .
#RUN CGO_ENABLED=0 GOOS=linux GOARCH=amd64 go build $(ls -1 *.go)
#RUN CGO_ENABLED=0 GOOS=linux GOARCH=amd64 go build -a -o server.go handlers.go
#RUN CGO_ENABLED=0 GOOS=linux GOARCH=amd64 go build -o server.go handlers.go
#RUN CGO_ENABLED=0 GOOS=linux GOARCH=amd64 go build *.go
EXPOSE 9000
#stat /app/*.go: no such file or directory
#CMD ["go", "run", "/app/*.go"]
CMD ["go", "run", "/app/server.go"]
問題在於您的 Dockerfile,特別是 CMD(最后一行)。
我測試了這個,它工作..
# ~ Dockerfile ~
# ...
# CMD ["go", "run", "/app/server.go"] # <- Remove this
CMD ["go", "run", "."] # <- Add this
編輯:發生這種情況的原因是因為您專門運行server.go
。 意思是, handlers.go
沒有與server.go
一起編譯,指定句點告訴go
構建/運行當前目錄中的所有文件。 我不確定你是如何使用go run server.go
在本地工作的(我無法讓它工作,我不得不使用go run.
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.