前往:如何处理库API更改?

I originally wrote my project with Go v1.9, which includes the os.LookupEnv function.

Now I need to build with Go v1.4, but that function is missing -- it only has os.Getenv which has slightly different behavior.

In Python, I could provide a compatibility function, something like this:

if 'LookupEnv' not in os:
    def myLookupEnv(k):
        v = os.Getenv(k)
        return v, v!=''
    os.LookupEnv = myLookupEnv

How can I handle these kinds of API changes in Go?

Use build constraints. A build constraint is a line comment that begins

// +build

that lists the conditions under which a file should be included in the package. See Build Constraints in Package build for details.

For example, for Go 1.5 and later (// +build go1.5), forward LookupEnv to os.LookupEnv. For Go 1.4 and earlier (// +build !go1.5), implement LookupEnv.

src/lookup/lookup.go:

package main

import (
    "fmt"
    "runtime"
)

func main() {
    fmt.Println("version:", runtime.Version())
    key := "HOME"
    value, found := LookupEnv(key)
    fmt.Printf("key: %q value %q found: %t
", key, value, found)
}

src/lookup/env.go:

// +build go1.5

// Forward LookupEnv to os.LookupEnv

package main

import "os"

// LookupEnv retrieves the value of the environment variable named
// by the key. If the variable is present in the environment the
// value (which may be empty) is returned and the boolean is true.
// Otherwise the returned value will be empty and the boolean will
// be false.
func LookupEnv(key string) (string, bool) {
    return os.LookupEnv(key)
}

src/lookup/env_1.4.go:

// +build !go1.5

// Implement LookupEnv

package main

import "syscall"

// LookupEnv retrieves the value of the environment variable named
// by the key. If the variable is present in the environment the
// value (which may be empty) is returned and the boolean is true.
// Otherwise the returned value will be empty and the boolean will
// be false.
func LookupEnv(key string) (string, bool) {
    return syscall.Getenv(key)
}

Output:

$ go build && ./lookup
version: devel +fd7331a821 Tue Feb 6 05:00:01 2018 +0000
key: "HOME" value "/home/peter" found: true
$

$ go1.4 build && ./lookup
version: go1.4-bootstrap-20170531
key: "HOME" value "/home/peter" found: true
$