Golang开发中Azure App Service无法正常工作的解决方案

Golang开发中Azure App Service无法正常工作的解决方案 我已经尝试了好几天将Go应用部署到Azure,但都没有成功。于是我创建了一个测试应用:

test-go-api.azurewebsites.net/test

发布流水线配置:

  • 适用于Go的应用服务
  • Ubuntu代理池

代码

func main() {
router := mux.NewRouter()
router.HandleFunc("/test", GetTest).Methods("GET")
log.Fatal(http.ListenAndServe(":8008", router))
}

func GetTest(w http.ResponseWriter, r *http.Request) {
json.NewEncoder(w).Encode("Hello")
}

构建流水线

# Go
# 构建你的Go项目。
# 添加测试、保存构建产物、部署等步骤:
# https://docs.microsoft.com/azure/devops/pipelines/languages/go

# trigger:
# - master

pool:
vmImage: 'Ubuntu-16.04'

variables:
GOBIN:  '$(GOPATH)/bin' # Go二进制文件路径
GOROOT: '/usr/local/go1.11' # Go安装路径
GOPATH: '$(system.defaultWorkingDirectory)/gopath' # Go工作区路径
modulePath: '$(GOPATH)/src/github.com/$(build.repository.name)' # 模块代码路径

steps:

- script: |
mkdir -p '$(GOBIN)'
mkdir -p '$(GOPATH)/pkg'
mkdir -p '$(modulePath)'
shopt -s extglob
shopt -s dotglob
mv !(gopath) '$(modulePath)'
echo '##vso[task.prependpath]$(GOBIN)'
echo '##vso[task.prependpath]$(GOROOT)/bin'
displayName: '设置Go工作区'

- script: |
go version
go get -v -t -d ./...
if [ -f Gopkg.toml ]; then
curl https://raw.githubusercontent.com/golang/dep/master/install.sh | sh
dep ensure
fi
go build -v .
workingDirectory: '$(modulePath)'
displayName: '获取依赖项,然后构建'

- task: CopyFiles@2
inputs:
SourceFolder: '$(modulePath)'
Contents: |
web.config
test
TargetFolder: '$(Build.ArtifactStagingDirectory)'

- task: PublishBuildArtifacts@1
inputs:
PathtoPublish: '$(Build.ArtifactStagingDirectory)'

我从Azure控制台应用服务使用ls命令看到了这两个文件,但URL分别返回"指定的CGI应用程序遇到错误,服务器终止了进程"和没有任何响应。

请问有人能帮忙吗?

谢谢。


更多关于Golang开发中Azure App Service无法正常工作的解决方案的实战教程也可以访问 https://www.itying.com/category-94-b0.html

1 回复

更多关于Golang开发中Azure App Service无法正常工作的解决方案的实战系列教程也可以访问 https://www.itying.com/category-94-b0.html


在Azure App Service中部署Go应用时,常见问题通常与端口配置和启动命令有关。Azure App Service默认使用PORT环境变量来指定应用监听的端口,而不是硬编码的端口号(如8008)。以下是修正后的代码和配置建议。

修改Go应用代码

将硬编码端口改为从环境变量读取:

package main

import (
    "encoding/json"
    "log"
    "net/http"
    "os"
    "github.com/gorilla/mux"
)

func main() {
    router := mux.NewRouter()
    router.HandleFunc("/test", GetTest).Methods("GET")
    
    // 从环境变量获取端口,默认为8008用于本地测试
    port := os.Getenv("PORT")
    if port == "" {
        port = "8008"
    }
    
    log.Printf("服务器启动在端口 %s", port)
    log.Fatal(http.ListenAndServe(":" + port, router))
}

func GetTest(w http.ResponseWriter, r *http.Request) {
    w.Header().Set("Content-Type", "application/json")
    json.NewEncoder(w).Encode("Hello")
}

构建流水线调整

确保构建步骤正确生成可执行文件,并复制所有必要文件到产物目录。以下是优化后的流水线YAML配置:

pool:
  vmImage: 'ubuntu-latest'

variables:
  GOBIN: '$(GOPATH)/bin'
  GOROOT: '/usr/local/go1.21'  # 更新到较新的Go版本
  GOPATH: '$(system.defaultWorkingDirectory)/gopath'
  modulePath: '$(GOPATH)/src/github.com/$(build.repository.name)'

steps:
- script: |
    mkdir -p '$(GOBIN)'
    mkdir -p '$(GOPATH)/pkg'
    mkdir -p '$(modulePath)'
    shopt -s extglob
    shopt -s dotglob
    mv !(gopath) '$(modulePath)'
    echo '##vso[task.prependpath]$(GOBIN)'
    echo '##vso[task.prependpath]$(GOROOT)/bin'
  displayName: '设置Go工作区'

- script: |
    go version
    go mod tidy  # 如果使用Go模块,确保依赖项整理
    go build -o app .  # 明确指定输出文件名
  workingDirectory: '$(modulePath)'
  displayName: '构建Go应用'

- task: CopyFiles@2
  inputs:
    SourceFolder: '$(modulePath)'
    Contents: |
      app
      web.config  # 确保web.config存在以配置IIS(如果需要)
    TargetFolder: '$(Build.ArtifactStagingDirectory)'
  displayName: '复制文件到产物目录'

- task: PublishBuildArtifacts@1
  inputs:
    PathtoPublish: '$(Build.ArtifactStagingDirectory)'
    ArtifactName: 'drop'
  displayName: '发布构建产物'

关键点说明

  1. 端口配置:Azure通过PORT环境变量注入端口号,应用必须使用该端口。硬编码端口(如8008)会导致启动失败。
  2. 可执行文件:构建步骤中go build -o app .生成名为app的可执行文件,Azure默认会执行此文件。
  3. web.config:如果应用服务基于Windows,可能需要web.config文件来配置IIS。对于Linux应用服务,通常不需要,但检查应用服务设置以确保使用正确栈(如Go 1.21 on Linux)。

部署后,通过Azure门户的应用服务日志流监控启动日志,确认应用是否在正确端口启动。如果问题持续,检查应用服务配置中的环境变量和启动命令。

回到顶部