# The App Engine SDK and workspaces (GOPATH)
9 Jan 2013
Tags: appengine, tools, gopath
Summary: When we released Go 1 we introduced the [go tool](https://golang.org/cmd/go/) and, with it, the concept of workspaces. Workspaces (specified by the GOPATH environment variable) are a convention for organizing code that simplifies fetching, building, and installing Go packages. If you're not familiar with workspaces, please read [this article](https://golang.org/doc/code.html) or watch [this screencast](http://www.youtube.com/watch?v=XCsL89YtqCs) before reading on.

Andrew Gerrand

## Introduction

When we released Go 1 we introduced the [go tool](https://golang.org/cmd/go/) and,
with it, the concept of workspaces.
Workspaces (specified by the GOPATH environment variable) are a convention
for organizing code that simplifies fetching,
building, and installing Go packages.
If you're not familiar with workspaces, please read [this article](https://golang.org/doc/code.html)
or watch [this screencast](http://www.youtube.com/watch?v=XCsL89YtqCs) before reading on.

Until recently, the tools in the App Engine SDK were not aware of workspaces.
Without workspaces the "[go get](https://golang.org/cmd/go/#hdr-Download_and_install_packages_and_dependencies)"
command cannot function,
and so app authors had to install and update their app dependencies manually. It was a pain.

This has all changed with version 1.7.4 of the App Engine SDK.
The [dev\_appserver](https://developers.google.com/appengine/docs/go/tools/devserver)
and [appcfg](https://developers.google.com/appengine/docs/go/tools/uploadinganapp)
tools are now workspace-aware.
When running locally or uploading an app,
these tools now search for dependencies in the workspaces specified by the
GOPATH environment variable.
This means you can now use "go get" while building App Engine apps,
and switch between normal Go programs and App Engine apps without changing
your environment or habits.

For example, let's say you want to build an app that uses OAuth 2.0 to authenticate
with a remote service.
A popular OAuth 2.0 library for Go is the [oauth2](https://godoc.org/golang.org/x/oauth2) package,
which you can install to your workspace with this command:

	go get golang.org/x/oauth2

When writing your App Engine app, import the oauth package just as you would in a regular Go program:

	import "golang.org/x/oauth2"

Now, whether running your app with the dev\_appserver or deploying it with appcfg,
the tools will find the oauth package in your workspace. It just works.

## Hybrid stand-alone/App Engine apps

The Go App Engine SDK builds on Go's standard [net/http](https://golang.org/pkg/net/http/)
package to serve web requests and,
as a result, many Go web servers can be run on App Engine with only a few changes.
For example, [godoc](https://golang.org/cmd/godoc/) is included in the
Go distribution as a stand-alone program,
but it can also run as an App Engine app (godoc serves [golang.org](https://golang.org/) from App Engine).

But wouldn't it be nice if you could write a program that is both a stand-alone
web server and an App Engine app? By using [build constraints](https://golang.org/pkg/go/build/#hdr-Build_Constraints), you can.

Build constraints are line comments that determine whether a file should
be included in a package.
They are most often used in code that handles a variety of operating systems
or processor architectures.
For instance, the [path/filepath](https://golang.org/pkg/path/filepath/)
package includes the file [symlink.go](https://golang.org/src/pkg/path/filepath/symlink.go),
which specifies a build constraint to ensure that it is not built on Windows
systems (which do not have symbolic links):

	// +build !windows

The App Engine SDK introduces a new build constraint term: "appengine". Files that specify

	// +build appengine

will be built by the App Engine SDK and ignored by the go tool. Conversely, files that specify

	// +build !appengine

are ignored by the App Engine SDK, while the go tool will happily build them.

The [goprotobuf](http://code.google.com/p/goprotobuf/) library uses this
mechanism to provide two implementations of a key part of its encode/decode machinery:
[pointer\_unsafe.go](http://code.google.com/p/goprotobuf/source/browse/proto/pointer_unsafe.go)
is the faster version that cannot be used on App Engine because it uses
the [unsafe package](https://golang.org/pkg/unsafe/),
while [pointer\_reflect.go](http://code.google.com/p/goprotobuf/source/browse/proto/pointer_reflect.go)
is a slower version that avoids unsafe by using the [reflect package](https://golang.org/pkg/reflect/) instead.

Let's take a simple Go web server and turn it into a hybrid app. This is main.go:

	package main

	import (
	    "fmt"
	    "net/http"
	)

	func main() {
	    http.HandleFunc("/", handler)
	    http.ListenAndServe("localhost:8080", nil)
	}

	func handler(w http.ResponseWriter, r *http.Request) {
	    fmt.Fprint(w, "Hello!")
	}

Build this with the go tool and you'll get a stand-alone web server executable.

The App Engine infrastructure provides its own main function that runs its
equivalent to ListenAndServe.
To convert main.go to an App Engine app, drop the call to ListenAndServe
and register the handler in an init function (which runs before main). This is app.go:

	package main

	import (
	    "fmt"
	    "net/http"
	)

	func init() {
	    http.HandleFunc("/", handler)
	}

	func handler(w http.ResponseWriter, r *http.Request) {
	    fmt.Fprint(w, "Hello!")
	}

To make this a hybrid app, we need to split it into an App Engine-specific part,
an stand-alone binary-specific part, and the parts common to both versions.
In this case, there is no App Engine-specific part,
so we split it into just two files:

app.go specifies and registers the handler function.
It is identical to the code listing above,
and requires no build constraints as it should be included in all versions of the program.

main.go runs the web server. It includes the "!appengine" build constraint,
as it must only included when building the stand-alone binary.

	// +build !appengine

	package main

	import "net/http"

	func main() {
	    http.ListenAndServe("localhost:8080", nil)
	}

To see a more complex hybrid app, take a look at the [present tool](https://godoc.org/golang.org/x/tools/present).

## Conclusions

We hope these changes will make it easier to work on apps with external dependencies,
and to maintain code bases that contain both stand-alone programs and App Engine apps.
