diff --git a/mengyaconnect-backend/Dockerfile b/mengyaconnect-backend/Dockerfile index df15b00..5940ee7 100644 --- a/mengyaconnect-backend/Dockerfile +++ b/mengyaconnect-backend/Dockerfile @@ -1,33 +1,33 @@ -FROM golang:1.21-alpine AS builder - -WORKDIR /app - -RUN apk add --no-cache ca-certificates - -COPY go.mod go.sum ./ -RUN go mod download - -COPY . . - -RUN CGO_ENABLED=0 GOOS=linux GOARCH=amd64 go build -o mengyaconnect-backend . - -FROM alpine:3.19 - -WORKDIR /app - -RUN apk add --no-cache ca-certificates && \ - adduser -D -H appuser - -COPY --from=builder /app/mengyaconnect-backend /app/mengyaconnect-backend - -ENV DATA_DIR=/app/data -ENV PORT=8080 - -RUN mkdir -p "$DATA_DIR" && chown -R appuser:appuser /app - -USER appuser - -EXPOSE 8080 - -CMD ["/app/mengyaconnect-backend"] - +FROM golang:1.21-alpine AS builder + +WORKDIR /app + +RUN apk add --no-cache ca-certificates + +COPY go.mod go.sum ./ +RUN go mod download + +COPY . . + +RUN CGO_ENABLED=0 GOOS=linux GOARCH=amd64 go build -o mengyaconnect-backend . + +FROM alpine:3.19 + +WORKDIR /app + +RUN apk add --no-cache ca-certificates && \ + adduser -D -H appuser + +COPY --from=builder /app/mengyaconnect-backend /app/mengyaconnect-backend + +ENV DATA_DIR=/app/data +ENV PORT=8080 + +RUN mkdir -p "$DATA_DIR" && chown -R appuser:appuser /app + +USER appuser + +EXPOSE 8080 + +CMD ["/app/mengyaconnect-backend"] + diff --git a/mengyaconnect-backend/config.go b/mengyaconnect-backend/config.go index 0ffdd13..90c832d 100644 --- a/mengyaconnect-backend/config.go +++ b/mengyaconnect-backend/config.go @@ -1,78 +1,78 @@ -package main - -import ( - "errors" - "net/http" - "os" - "path/filepath" - "strings" - - "github.com/gin-gonic/gin" -) - -// 数据目录辅助 -func dataBasePath() string { return getEnv("DATA_DIR", "data") } -func sshDir() string { return filepath.Join(dataBasePath(), "ssh") } -func cmdFilePath() string { return filepath.Join(dataBasePath(), "command", "command.json") } -func scriptDir() string { return filepath.Join(dataBasePath(), "script") } - -// sanitizeName 防止路径穿越攻击 -func sanitizeName(name string) (string, error) { - base := filepath.Base(name) - if base == "" || base == "." || base == ".." { - return "", errors.New("invalid name") - } - return base, nil -} - -func corsMiddleware() gin.HandlerFunc { - return func(c *gin.Context) { - c.Writer.Header().Set("Access-Control-Allow-Origin", "*") - c.Writer.Header().Set("Access-Control-Allow-Methods", "GET, POST, PUT, PATCH, DELETE, OPTIONS") - c.Writer.Header().Set("Access-Control-Allow-Headers", "Content-Type, Authorization") - if c.Request.Method == http.MethodOptions { - c.AbortWithStatus(http.StatusNoContent) - return - } - c.Next() - } -} - -func isOriginAllowed(origin string, allowed []string) bool { - if origin == "" { - return true - } - if len(allowed) == 0 { - return true - } - for _, item := range allowed { - if item == "*" || strings.EqualFold(strings.TrimSpace(item), origin) { - return true - } - } - return false -} - -func parseListEnv(name string) []string { - raw := strings.TrimSpace(os.Getenv(name)) - if raw == "" { - return nil - } - parts := strings.Split(raw, ",") - out := make([]string, 0, len(parts)) - for _, part := range parts { - part = strings.TrimSpace(part) - if part != "" { - out = append(out, part) - } - } - return out -} - -func getEnv(key, fallback string) string { - if val := strings.TrimSpace(os.Getenv(key)); val != "" { - return val - } - return fallback -} - +package main + +import ( + "errors" + "net/http" + "os" + "path/filepath" + "strings" + + "github.com/gin-gonic/gin" +) + +// 数据目录辅助 +func dataBasePath() string { return getEnv("DATA_DIR", "data") } +func sshDir() string { return filepath.Join(dataBasePath(), "ssh") } +func cmdFilePath() string { return filepath.Join(dataBasePath(), "command", "command.json") } +func scriptDir() string { return filepath.Join(dataBasePath(), "script") } + +// sanitizeName 防止路径穿越攻击 +func sanitizeName(name string) (string, error) { + base := filepath.Base(name) + if base == "" || base == "." || base == ".." { + return "", errors.New("invalid name") + } + return base, nil +} + +func corsMiddleware() gin.HandlerFunc { + return func(c *gin.Context) { + c.Writer.Header().Set("Access-Control-Allow-Origin", "*") + c.Writer.Header().Set("Access-Control-Allow-Methods", "GET, POST, PUT, PATCH, DELETE, OPTIONS") + c.Writer.Header().Set("Access-Control-Allow-Headers", "Content-Type, Authorization") + if c.Request.Method == http.MethodOptions { + c.AbortWithStatus(http.StatusNoContent) + return + } + c.Next() + } +} + +func isOriginAllowed(origin string, allowed []string) bool { + if origin == "" { + return true + } + if len(allowed) == 0 { + return true + } + for _, item := range allowed { + if item == "*" || strings.EqualFold(strings.TrimSpace(item), origin) { + return true + } + } + return false +} + +func parseListEnv(name string) []string { + raw := strings.TrimSpace(os.Getenv(name)) + if raw == "" { + return nil + } + parts := strings.Split(raw, ",") + out := make([]string, 0, len(parts)) + for _, part := range parts { + part = strings.TrimSpace(part) + if part != "" { + out = append(out, part) + } + } + return out +} + +func getEnv(key, fallback string) string { + if val := strings.TrimSpace(os.Getenv(key)); val != "" { + return val + } + return fallback +} + diff --git a/mengyaconnect-frontend/src/App.vue b/mengyaconnect-frontend/src/App.vue index 9cc01c7..44ba600 100644 --- a/mengyaconnect-frontend/src/App.vue +++ b/mengyaconnect-frontend/src/App.vue @@ -1,5 +1,5 @@