Google App Engine ModuleHostname: не контекст App Engine

Я пытаюсь обнаружить другие развернутые службы в App Engine. Нечто подобное предлагает эта статья.

Вот как выглядит мой код:

import (
    "fmt"
    "net/http"

    "google.golang.org/appengine"
)

func ServiceHostname(serviceName string, r *http.Request) (string, error) {
    ctx := appengine.NewContext(r)
    hostname, err := appengine.ModuleHostname(ctx, serviceName, "", "")
    if err != nil {
        return "", fmt.Errorf("unable to find service %s: %v", serviceName, err)
    }
    return hostname, nil
}

Я вызываю эту функцию в обычном http-обработчике. Я получил ошибку: not an App Engine context,

Единственная разница между моим кодом и ссылочной статьей в версии движка приложения. Я использую новый go111 где он использует go1 во время выполнения.

Вы знаете, как преодолеть проблему?

2 ответа

Решение

Я нашел решение. Вам нужно позвонить appengine.Main() в вашем основном файле, хотя это не должно быть необходимо делать в новом go111 во время выполнения.

Таким образом, рассматриваемый код остается тем же, вам нужно зарегистрировать ваши обработчики так же, как в go1.9 во время выполнения.

func main() {
    http.HandleFunc("/serveurl", handle)
    appengine.Main()
}

Источник: https://groups.google.com/d/msg/google-appengine-go/ZcASFMWJKpE/7iwGirNiBgAJ

Это также упоминается в разделе " Написание основного пакета":

  • Или, если ваш сервис использует google.golang.org/appengine пакет, включите звонок в appengine.Main(),

Насколько я понимаю, эта ошибка возвращается, когда ваше приложение AppEngine имеет среду выполнения, установленную на go111, и приложение импортирует любой из пакетов "google.golang.org/appengine", например log, urlfetch, memcache и т. Д., Но приложение не вызовите метод "appengine.Main".

Поэтому вы можете выбрать любую реализацию ниже:

import (
    "fmt"
    "net/http"

    "google.golang.org/appengine"
)

func init() {
    // register handlers
    http.HandleFunc(“/“, indexHandler)

    appengine.Main()
}

func indexHandler(w http.ResponseWriter, r *http.Request) {
    ctx := appengine.NewContext(r)
.......handle the request.......
}

func ServiceHostname(serviceName string, r *http.Request) (string, error) {
    ctx := appengine.NewContext(r)
    hostname, err := appengine.ModuleHostname(ctx, serviceName, "", "")
    if err != nil {
        return "", fmt.Errorf("unable to find service %s: %v", serviceName, err)
    }
    return hostname, nil
}

Или откажитесь от всех пакетов appengine:

import (
    "fmt"
    “log”
    "net/http"
    “os”
)

func main() {
    port := os.Getenv(“PORT”)
    if port == “” {
        port = “8080”
    }

    http.HandleFunc(“/“, indexHandler)

    log.Fatal(http.ListenAndServe(“:”+port, Nil)
}

func indexHandler(w http.ResponseWriter, r *http.Request) {
    ctx := r.Context()
.....handle request....
}

Статья, на которую вы ссылались, была написана с учетом стандартной среды 1-го поколения, 2-го поколения (go111) в то время не было:

10 октября 2018 г.

Go runtime notes

Среда выполнения Go 1.11 для стандартной среды App Engine сейчас находится в стадии бета-тестирования. Доступно руководство по переносу приложений с Go 1.9 на Go 1.11.

Различия между двумя поколениями значительны (для всех языков, а не только для го). В разделе Миграция из App Engine Go SDK (необязательно) руководства по миграции я заметил:

  • использование request.Context() или ваш предпочтительный контекст вместо использования appengine.NewContext,

Что может быть связано с вашей ошибкой. Но я на самом деле не пользователь Go, это всего лишь теория:)

Другие вопросы по тегам