app.yaml, you can configure your Java application more easily, and with fewer files, than with the standard
You can use
app.yaml as long as your application does not need to be portable to other Java application servers.
Note: If you created your project using the Google Developers Console, your project has a title and an ID. In the instructions that follow, the project title and ID can be used wherever an application title and ID are mentioned. They are the same thing.
- Required elements
- Optional elements
- Static files and resource files
- Enabling sessions
- System properties, environment variables, and context parameters
- Servlet context listeners
- Secure URLs
- Requiring login or administrator status
- The welcome file list
- Skipping files
- Reserved URLs
- Inbound services
- Warmup requests
- Disabling precompilation
- Support for XML directives
- Custom error responses
- Auto ID policy
app.yaml specifies how URL paths correspond to request handlers and static files. It also contains information about the application code, such as the application ID and the latest version identifier. This file is stored in the application's
One of the benefits of using
app.yaml is that it automatically generates
appengine-web.xml for you. It overwrites any content you may have written in those files. If you need to include a feature in
app.yaml doesn't support, simply specify it in
app.yaml using web_xml.
The following is an example of a basic
application: myapp version: alpha-001 runtime: java threadsafe: true handlers: - url: /admin/* login: admin
The syntax of
app.yaml is the YAML format. For more information about this syntax, see the YAML website.
The YAML format supports comments. A line that begins with a pound (
#) character is ignored:
# This is a comment.
URL and file path patterns use POSIX extended regular expression syntax, excluding collating elements and collation classes. Back-references to grouped matches (e.g.
\1) are supported, as are these Perl extensions:
\w \W \s \S \d \D.
app.yaml file must include one of each of the following elements:
The name of the App Engine runtime environment used by this application. To
specify Java, use java. Other runtimes are
available; please refer to the runtime's documentation for more info. Other
JVM languages can customize
app.yaml based on the specified runtime.
Configures your application to use concurrent requests.
threadsafe: [true | false]
handlers define mappings between URL paths and a
jsp that handle requests with those paths. All handler definitions begin by declaring a
Defines the URL pattern for the mapping. This pattern can use an asterisk (
'*') at the beginning or end of the pattern to indicate zero or more of any character. The Java runtime does not support wildcards in the middle of a string, and does not allow multiple wildcards in one pattern. The pattern matches the full path of the URL, starting with and including the forward slash (
'/') following the domain name.
handlers: - url: /red/*
After declaring the URL, define the mapping with the following elements:
Declares a servlet class to map to the specified URL. The servlet is further defined by a name that other elements in the file use to refer to the servlet, and initialization parameters (
init_params). The name for each servlet must be unique within the YAML file. Using unique names, you can declare multiple servlets of the same class with different initialization parameters.
Declares a filter class to map to the specified URL in applications that use the javax.servlet.Filter package. A filter is a class that acts on a request like a servlet, but may allow the handling of the request to continue with other filters or servlets. A filter may perform an auxiliary task such as logging, performing specialized authentication checks, or annotating the request or response objects before calling the servlet. Filters allow you to compose request processing tasks from the deployment descriptor. A single URL mapping can include either a filter or a servlet, but not both.
Declares the initialization parameters for this mapping.
Declares a name used to refer to the servlet by other elements in the file. The name for each servlet must be unique across the deployment descriptor.
Declares a custom mapping to a JSP file from the WAR root. The servlet element for the JSP can contain initialization parameters. Note that App Engine supports automatic compilation and URL mapping for JSPs. A JSP file in the application's WAR (outside of
WEB-INF/), whose filename ends in
.jsp, is compiled into a servlet class automatically, and mapped to the URL path equivalent to the path to the JSP file from the WAR root. For example, if an app has a JSP file named start.jsp in a subdirectory named
register/ in its WAR, App Engine compiles it and maps it to the URL path
/register/start.jsp. You don't need to use this element unless you want more control over how the JSP is mapped to a URL.
The following example demonstrates a handler mapping containing all of these elements:
handlers: - url: /red/* servlet: mysite.server.TeamServlet init_params: teamColor: red bgColor: "#CC0000" name: redteam - url: /blue/* servlet: mysite.server.TeamServlet init_params: teamColor: blue bgColor: "#0000CC" name: blueteam - url: /register/* jsp: /register/start.jsp - url: /*.special filter: mysite.server.LogFilterImpl init_params: logType: special
These two elements may appear in the
The application identifier. This is the identifier you selected when you created the application in the Google Developers Console.
A version specifier for the application code. App Engine retains a copy of your
application for each version used. An administrator can change which major
version of the application is default using the
Google Developers Console, and can test non-default versions before making them default.
(The default version is loaded when no version is specified or an invalid
version is specified.) The version specifier can contain lowercase letters,
digits, and hyphens. It cannot begin with the prefix
ah- and the names
latest are reserved and cannot be used. We recommend that
version names begin with a letter, so they may be easily distinguished from the
numeric instance number in URLs like
Each version of an application retains its own copy of
app.yaml. When an application is uploaded, the version mentioned in the
app.yaml file being uploaded is the version that gets created or replaced by the upload.
Static files and resource files
Files that are accessible by the application code using the filesystem are called resource files. These files are stored on the application servers with the app.
By default, all files in the WAR are treated as both static files and resource files, except for JSP files, which are compiled into servlet classes and mapped to URL paths, and files in the
WEB-INF/ directory, which are never served as static files and always available to the app as resource files.
You can adjust which files are considered static files and which are considered resource files using elements in the
app.yaml file. The
static_files element specifies patterns that match file paths to include and exclude from the list of static files, overriding or amending the default behavior. Similarly, the
resource_files element specifies which files are considered resource files.
Including and excluding files
Path patterns are specified using zero or more
exclude elements. In a pattern,
'*' represents zero or more of any character in a file or directory name, and
** represents zero or more directories in a path. Files and directories matching
exclude patterns will not be uploaded when you deploy your app to App Engine. However, these files and directories will still be accessible to your application when running on the local Development Server.
include element overrides the default behavior of including all files. An
exclude element applies after all
include patterns (as well as the default if no explicit
include is provided).
The following example demonstrates how to designate all
.png files as static files (except those in the
data/ directory and all of its subdirectories):
static_files: - include: /**.png - exclude: /data/**.png
Similarly, the following sample demonstrates how to designate all
.xml files as resource files (except those in the
feeds/ directory and all of its subdirectories):
resource_files: - include: /**.xml - exclude: /feeds/**.xml
You can also set HTTP headers to use when responding to requests to these resources.
static_files: - include: /static/* http_headers: Access-Control-Allow-Origin: http://example.org
Changing the MIME type for static files
By default, static files are served using a MIME type selected based on the filename extension. You can associate custom MIME types with filename extensions for static files in
Changing the root directory
public_root is a directory in your application that contains the static files for your application. When a request for a static file is made, the
public_root for your application is prepended to the request path. This gives the path of an application file containing the content that is being requested.
For example, the following would map the URL path
/index.html to the application file path
Static cache expiration
Unless told otherwise, web proxies and browsers retain files they load from a website for a limited period of time.
You can configure a cache duration for specific static file handlers by providing an
expiration attribute to
static_files include .... The value is a string of numbers and units, separated by spaces, where units can be `d` for days, `h` for hours, `m` for minutes, and `s` for seconds.
"4d 5h" sets cache expiration to 4 days and 5 hours after the file is first requested. If the expiration time is omitted, the production server defaults to 10 minutes.
(Script handlers can set cache durations by returning the appropriate HTTP headers to the browser.)
static_files: - include: /**.png expiration: 4d 5h
App Engine includes an implementation of sessions, using the servlet session interface. The implementation stores session data in the App Engine datastore for persistence, and also uses memcache for speed. As with most other servlet containers, the session attributes that are set with
session.setAttribute() during the request are persisted at the end of the request.
This feature is off by default. To turn it on, add the following to
The implementation creates datastore entities of the kind
_ah_SESSION, and memcache entries using keys with a prefix of
System properties, environment variables, and context parameters
app.yaml file can define system properties, environment variables, and context parameters that are set when the application is running.
system_properties: myapp.maximum-message-length: 140 myapp.notify-every-n-signups: 1000 myapp.notify-url: http://www.example.com/signupnotify env_variables: DEFAULT_ENCODING: UTF-8 context_params: rack.env: production
Servlet context listeners
listeners element maps a servlet context listener to the specified URL, allowing you to set up a static state independent of your various servlets. Note that App Engine does not implement the
contextDestroyed aspect of the listener.
listeners: - com.example.MyListener - com.example.MyOtherListener
Google App Engine supports secure connections via HTTPS for URLs using the
*.appspot.com domain. When a request accesses a URL using HTTPS, and that URL is configured to use HTTPS in the
app.yaml file, both the request data and the response data are encrypted by the sender before they are transmitted, and decrypted by the recipient after they are received. Secure connections are useful for protecting customer data, such as contact information, passwords, and private messages.
To configure a URL to accept secure connections, provide a
secure parameter for the handler:
handlers: - url: /youraccount/* login: required secure: always
To disallow the use of HTTPS for the application, use
ssl_enabled as follows:
There is no way to disallow HTTPS for some URL paths and not others in the Java runtime environment. The development web server does not support HTTPS connections. It ignores the secure parameter, so paths intended for use with HTTPS can be tested using regular HTTP connections to the development web server.
secure has the following possible values:
optional- Both HTTP and HTTPS requests with URLs that match the handler succeed without redirects. The application can examine the request to determine which protocol was used, and respond accordingly. This is the default when
secureis not provided for a handler.
always- Requests for a URL that match this handler that do not use HTTPS are automatically redirected to the HTTPS URL with the same path. Query parameters are preserved for the redirect.
Any URL handler can use the
secure setting, including script handlers and static file handlers.
To access the versioned appspot.com URL for your application, replace the periods that would usually separate the subdomain components of the URL with the string "
-dot-". For instance:
Google Accounts sign-in and sign-out are always performed using a secure connection, unrelated to how the application's URLs are configured.
Requiring login or administrator status
Any URL handler can have a
login setting to restrict visitors to only those users who have signed in, or just those users who are administrators for the application. When a URL handler with a
login setting other than
optional matches a URL, the handler first checks whether the user has signed in to the application using its authentication option. If not, by default, the user is redirected to the sign-in page. You can also use
auth_fail_action to configure the app to simply reject requests for a handler from users who are not properly authenticated, instead of redirecting the user to the sign-in page.
Determines whether the URL handler is restricted to require that the user is signed in. Has three possible values:
optional(the default). Does not require that the user is signed in.
required. If the user has signed in, the handler proceeds normally. Otherwise, the user is redirected to the Google sign-in page, or
/_ah/login_requiredif OpenID authentication is used. (Note that the support for OpenID is experimental.) The user is redirected back to the application URL after signing in or creating an account.
admin. As with
required, redirects to the login page if the user is not signed in. In addition, if the user is not an administrator for the application, they are given an error message. If the user is an administrator, the handler proceeds. Note: the
adminlogin restriction is also satisfied for internal requests for which App Engine sets appropriate
X-Appenginespecial headers. For example,
cronscheduled tasks satisfy the
adminrestriction, because App Engine sets an HTTP header
X-AppEngine-Cron: trueon the respective requests. However, the requests would not satisfy the
requiredadmin restriction, because cron scheduled tasks are not run as any user.
If an application needs different behavior, the application itself can implement the handling of user logins. See the Users API for more information.
The following example requires a login for the
/profile/ directory and an administrator login for the
handlers: - url: /profile/* login: required - url: /admin/* servlet: com.example.AdminServlet login: admin
The welcome file listWhen the URLs for your site represent paths to static files or JSPs in your WAR, it is often a good idea for paths to directories to do something useful as well.
A user visiting the URL path
/help/accounts/password.jsp for information on account passwords may try to visit
/help/accounts/ to find a page introducing the account system documentation. The deployment descriptor can specify a list of filenames that the server should try when the user accesses a path that represents a WAR subdirectory (that is not already explicitly mapped to a servlet). The servlet standard calls this the "welcome file list."
For example, if the user accesses the URL path
/help/accounts/, the following
welcome_file list in
app.yaml tells the server to check for
help/accounts/index.html before reporting that the URL does not exist:
welcome_files: - index.jsp - index.html
Files in your application directory whose paths match a
static_dir path or a
upload path are considered to be static files. All other files in the application directory are considered to be application program and data files.
skip_files element specifies which files in the application directory are not to be uploaded to App Engine. The value is either a regular expression, or a list of regular expressions. Any filename that matches any of the regular expression is omitted from the list of files to upload when the application is uploaded.
skip_files has the following default:
skip_files: - ^(.*/)?#.*#$ - ^(.*/)?.*~$ - ^(.*/)?.*\.py[co]$ - ^(.*/)?.*/RCS/.*$ - ^(.*/)?\..*$
The default pattern excludes Emacs backup files with names of the form
.pyo files, files in an
RCS revision control directory, and Unix hidden files with names beginning with a dot (
If a new value is specified in
app.yaml, it overrides the default value. To extend the above regular express list, copy and paste the above list into your
app.yaml and add your own regular expressions. For example, to skip files whose names end in
.bak in addition to the default patterns, add an entry like this to
skip_files: - ^(.*/)?\.bak$
All URLs that begin with
/_ah/ are reserved by App Engine for features or administrative purposes. Some URLs are routed to App Engine feature handlers, while others are called by App Engine for special purposes and are expected to be mapped to request handlers in your app (for example,
/_ah/warmup for Warm-up Requests).
/form is also reserved by App Engine. Requests for this URL are not routed to the app, and always return a 404 Not Found error.
Before an application can receive email or XMPP messages, the application must be configured to enable the service.
You enable the service for a Java app by including an
inbound_services section in the
For example, you can enable mail and warmup by specifying the following in
inbound_services: - xmpp_message - mail
App Engine uses a "precompilation" process with the Java bytecode of an app to enhance the performance of the app in the Java runtime environment. Precompiled code functions identically to the original bytecode.
If for some reason you prefer that your app not use precompilation, you can turn it off by adding the following to your
App Engine frequently needs to load application code into a fresh instance. This happens when you redeploy the application, when the load pattern has increased beyond the capacity of the current instances, or simply due to maintenance or repairs of the underlying infrastructure or physical hardware.
Loading new application code on a fresh instance can result in loading requests. Loading requests can result in increased request latency for your users, but you can avoid this latency using warmup requests. Warmup requests load application code into a new instance before any live requests reach that instance.
App Engine attempts to detect when your application needs a new instance, and (assuming that warmup requests are enabled for your application) initiates a warmup request to initialize the new instance. However, these detection attempts do not work in every case. As a result, you may encounter loading requests, even if warmup requests are enabled in your app. For example, if your app is serving no traffic, the first request to the app will always be a loading request, not a warmup request.
Warmup requests use instance hours like any other request to your App Engine application. In most cases, you won't notice an increase in instance hours, since your application is simply initializing in a warmup request instead of a loading request. Your instance hour usage will likely increase if you decide to do more work (such as precaching) during a warmup request. If you set a minimum number of idle instances, you may encounter warmup requests when those instances first start, but they will remain available after that time.In Java, warmup requests are disabled by default. To enable them, add
inbound_services: - warmup
This causes the App Engine infrastructure to issue
GET requests to
/_ah/warmup. You can implement handlers in this directory to perform application-specific tasks, such as pre-caching application data. Warmup requests only work if the minimum number of idle instances has been manually set. When this setting is at
Auto, there will be no warmup requests.
Support for XML directives
If you need to use features of the Java
web.xml which are not directly supported in
app.yaml, you can include a block of XML that will be included directly into
web_xml: | <error-page> <error-code>500</error-code> <location>/errors/servererror.jsp</location> </error-page>
Custom error responses
When certain errors occur, App Engine serves a generic error page. You can configure your app to serve a custom static file instead of these generic error pages, so long as the custom error data is less than 10 kilobytes. You can set up different static files to be served for each supported error code by specifying the files in your app's
app.yaml file. To serve custom error pages, add a
error_handlers section to your
app.yaml, as in this example:
error_handlers: - file: default_error.html - error_code: over_quota file: over_quota.html
file entry indicates a static file that should be served in place of the generic error response. The
error_code indicates which error code should cause the associated file to be served. Supported error codes are as follows:
over_quota, which indicates the app has exceeded a resource quota;
dos_api_denial, which is served to any client blocked by your app's DoS Protection configuration;
timeout, served if a deadline is reached before there is a response from your app.
error_code is optional; if it's not specified, the given file is the default error response for your app.
You can optionally specify a
mime_type to use when serving the custom error. See http://www.iana.org/assignments/media-types/ for a complete list of MIME types.
Auto ID policy
If you are setting entity identifiers automatically, you can change the method employed by setting the auto ID policy. You can choose default (default is also applied if you specify nothing) or legacy. Please note however that the legacy option will be deprecated in a future release and will eventually be removed. For more information, see our blog post where we announced the change.