{"id":15222343,"url":"https://github.com/googlecloudplatform/jetty-runtime","last_synced_at":"2025-08-18T13:33:09.383Z","repository":{"id":54195122,"uuid":"66016354","full_name":"GoogleCloudPlatform/jetty-runtime","owner":"GoogleCloudPlatform","description":"Google Cloud Platform Jetty Docker image","archived":false,"fork":false,"pushed_at":"2024-10-03T18:14:45.000Z","size":6205,"stargazers_count":44,"open_issues_count":29,"forks_count":33,"subscribers_count":40,"default_branch":"master","last_synced_at":"2024-10-29T18:38:43.630Z","etag":null,"topics":["app-engine","docker","gcp","google","java","jetty","runtime"],"latest_commit_sha":null,"homepage":"","language":"Java","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"apache-2.0","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/GoogleCloudPlatform.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":"CONTRIBUTING.md","funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2016-08-18T17:14:04.000Z","updated_at":"2024-08-06T01:37:07.000Z","dependencies_parsed_at":"2024-09-28T15:11:43.608Z","dependency_job_id":"3922a250-6be7-4e3c-8b9d-61ffb4dacd58","html_url":"https://github.com/GoogleCloudPlatform/jetty-runtime","commit_stats":null,"previous_names":[],"tags_count":19,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/GoogleCloudPlatform%2Fjetty-runtime","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/GoogleCloudPlatform%2Fjetty-runtime/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/GoogleCloudPlatform%2Fjetty-runtime/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/GoogleCloudPlatform%2Fjetty-runtime/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/GoogleCloudPlatform","download_url":"https://codeload.github.com/GoogleCloudPlatform/jetty-runtime/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":230238281,"owners_count":18194988,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["app-engine","docker","gcp","google","java","jetty","runtime"],"created_at":"2024-09-28T15:11:40.734Z","updated_at":"2024-12-18T08:08:55.944Z","avatar_url":"https://github.com/GoogleCloudPlatform.png","language":"Java","funding_links":[],"categories":[],"sub_categories":[],"readme":"# Google Cloud Platform Jetty Docker Image\n\nThis repository contains the source for the Google-maintained Jetty [docker](https://docker.com) image.\nThis image can be used as the base image for running Java web applications on\n[Google App Engine Flexible Environment](https://cloud.google.com/appengine/docs/flexible/java/)\nand [Google Container Engine](https://cloud.google.com/container-engine).\nIt provides the Jetty Servlet container on top of the\n[OpenJDK image](https://github.com/GoogleCloudPlatform/openjdk-runtime).\n\nThis image is mirrored at both `launcher.gcr.io/google/jetty` and `gcr.io/google-appengine/jetty`.\n\nThe layout of this image is intended to mostly mimic the official [docker-jetty](https://github.com/appropriate/docker-jetty) image and unless otherwise noted, the official [docker-jetty documentation](https://github.com/docker-library/docs/tree/master/jetty) should apply.\n\n## Configuring the Jetty image\nArguments passed to the `docker run` command are passed to Jetty, so the \nconfiguration of the jetty server can be seen with a command like:\n```console\ndocker run gcr.io/google-appengine/jetty --list-config\n```\n\nAlternate commands can also be passed to the `docker run` command, so the\nimage can be explored with \n```console\ndocker run -it --rm launcher.gcr.io/google/jetty bash\n```\n\nVarious environment variables (see below) can also be used to set jetty properties, enable modules and\ndisable modules.  These variables may be set either in an `app.yaml` or passed in to a docker run\ncommand eg.\n```console\ndocker run -it --rm -e JETTY_PROPERTIES=jetty.http.idleTimeout=10000 launcher.gcr.io/google/jetty \n```\n\nTo update the server configuration in a derived Docker image, the `Dockerfile` may\nenable additional modules with `RUN` commands like:\n```dockerfile\nWORKDIR $JETTY_BASE\nRUN java -jar \"$JETTY_HOME/start.jar\" --add-to-startd=jmx,stats\n```\nModules may be configured in a `Dockerfile` by editing the properties in the corresponding mod files in `/var/lib/jetty/start.d/` or the module can be deactivated by removing that file.\n\n### Enabling gzip compression\nThe gzip handler is bundled with Jetty but not activated by default. To activate this module you have to set the environment\nvariable `JETTY_MODULES_ENABLE=gzip`\n\nFor example with docker:\n```console\ndocker run -p 8080 -e JETTY_MODULES_ENABLE=gzip gcr.io/yourproject/yourimage\n```\n\nOr with GAE (app.yaml):\n```yaml\nenv_variables:\n  JETTY_MODULES_ENABLE: gzip\n```\n\n### Using Quickstart\nJetty provides [mechanisms](http://www.eclipse.org/jetty/documentation/9.4.x/quickstart-webapp.html) to speed up the start time of your application by pre-scanning its content and generating configuration files.\nIf you are using an [extended image](https://github.com/GoogleCloudPlatform/jetty-runtime/blob/master/README.md#extending-the-image) you can active quickstart by executing `/scripts/jetty/quickstart.sh` in your Dockerfile, after the application WAR is added.\n\n```dockerfile\nFROM launcher.gcr.io/google/jetty\nADD your-application.war $JETTY_BASE/webapps/root.war\n\n# generate quickstart-web.xml\nRUN /scripts/jetty/quickstart.sh\n```\n\n## App Engine Flexible Environment\nWhen using App Engine Flexible, you can use the runtime without worrying about Docker by specifying `runtime: java` in your `app.yaml`:\n```yaml\nruntime: java\nenv: flex\n```\nThe runtime image `launcher.gcr.io/google/jetty` will be automatically selected if you are attempting to deploy a WAR (`*.war` file).\n\nIf you want to use the image as a base for a custom runtime, you can specify `runtime: custom` in your `app.yaml` and then\nwrite the Dockerfile like this:\n\n```dockerfile\nFROM launcher.gcr.io/google/jetty\nADD your-application.war $APP_DESTINATION_WAR\n```\n \nThat will add the WAR in the correct location for the Docker container.\n\nYou can also use exploded-war artifacts:\n\n```dockerfile\nADD your-application $APP_DESTINATION_EXPLODED_WAR\n```\n\nOnce you have this configuration, you can use the Google Cloud SDK to deploy this directory containing the 2 configuration files and the WAR using:\n```\ngcloud app deploy app.yaml\n```\n\n## Container Engine \u0026 other Docker hosts\n\nFor other Docker hosts, you'll need to create a Dockerfile based on this image that copies your application code and installs dependencies. For example:\n\n```dockerfile\nFROM launcher.gcr.io/google/jetty\nCOPY your-application.war $APP_DESTINATION_WAR\n```\nIf your artifact is an exploded-war, then use the `APP_DESTINATION_EXPLODED_WAR` environment variable instead. You can then build the docker container using `docker build` or [Google Cloud Container Builder](https://cloud.google.com/container-builder/docs/).\nBy default, the CMD is set to start the Jetty server. You can change this by specifying your own `CMD` or `ENTRYPOINT`.\n\n## Entry Point Features\nThe [/docker-entrypoint.bash](https://github.com/GoogleCloudPlatform/openjdk-runtime/blob/master/openjdk8/src/main/docker/docker-entrypoint.bash)\nfor the image is inherited from the openjdk-runtime and its capabilities are described in the associated \n[README](https://github.com/GoogleCloudPlatform/openjdk-runtime/blob/master/README.md)\n\nThis image updates the docker `CMD` and adds the \n[/setup-env.d/50-jetty.bash](https://github.com/GoogleCloudPlatform/openjdk-runtime/blob/master/openjdk8/src/main/docker/50-jetty.bash)\nscript to include options and arguments to run the Jetty container, unless an executable argument is passed to the docker image.\nAdditional environment variables are used/set including:\n\n|Env Var           | Maven Prop      | Value/Comment                                        |\n|------------------|-----------------|------------------------------------------------------|\n|`JETTY_VERSION`   |`jetty9.version` |                                                      |\n|`GAE_IMAGE_NAME`  |                 |`jetty`                                               |\n|`GAE_IMAGE_LABEL` |`docker.tag.long`|                                                      |\n|`JETTY_HOME`      |`jetty.home`     |`/opt/jetty-home`                                     |\n|`JETTY_BASE`      |`jetty.base`     |`/var/lib/jetty`                                      |\n|`TMPDIR`          |                 |`/tmp/jetty`                                          |\n|`JETTY_PROPERTIES`|                 |Comma separated list of `name=value` pairs appended to `$JETTY_ARGS` |\n|`JETTY_MODULES_ENABLE`|            |Comma separated list of modules to enable by appending to `$JETTY_ARGS` |\n|`JETTY_MODULES_DISABLE`|           |Comma separated list of modules to disable by removing from `$JETTY_BASE/start.d` |\n|`JETTY_ARGS`      |                 |Arguments passed to jetty's `start.jar`. Any arguments used for custom jetty configuration should be passed here. |\n|`ROOT_WAR`        |                 |`$JETTY_BASE/webapps/root.war`                        |\n|`ROOT_DIR`        |                 |`$JETTY_BASE/webapps/root`                            |\n|`JAVA_OPTS`       |                 |JVM runtime arguments                                 |\n\nIf a WAR file is found at `$ROOT_WAR`, it is unpacked to `$ROOT_DIR` if it is newer than the directory or the directory\ndoes not exist.  If there is no `$ROOT_WAR` or `$ROOT_DIR`, then `/app` is symbolic linked to `$ROOT_DIR`. If \na `$ROOT_DIR` is discovered or made by this script, then it is set as the working directory. \nSee [Extending the image](#extending-the-image) below for some examples of adding an application as a WAR file or directory.\n\n\nThe command line executed is effectively (where $@ are the args passed into the docker entry point):\n```\njava $JAVA_OPTS \\\n     -Djetty.base=$JETTY_BASE \\\n     -jar $JETTY_HOME/start.jar \\\n     \"$@\"\n```\n## Logging\nThis image is configured to use [Java Util Logging](https://docs.oracle.com/javase/8/docs/api/java/util/logging/package-summary.html)(JUL) to capture all logging from \nthe container and its dependencies.  Applications that also use the JUL API will inherit the same logging configuration.\n\nBy default JUL is configured to use a [ConsoleHandler](https://docs.oracle.com/javase/8/docs/api/java/util/logging/ConsoleHandler.html) to send logs to the `stderr` of the container process. When run on as a GCP deployment, all output to `stderr` is captured and is available via the Stackdriver logging console, however more detailed and integrated logs are available if the Stackdriver logging mechanism is used directly (see below).\n\nTo alter logging configuration a new `logging.properties` file must be provided to the image that among other things can: alter log levels generated by Loggers; alter log levels accepted by handlers; add/remove/configure log handlers. \n\n\n### Providing `logging.properties` via the web application\nA new logging configuration file can be provided as part of the application (typically at `WEB-INF/logging.properties`)\nand the Java System Property `java.util.logging.config.file` updated to reference it.\n\nWhen running in a GCP environment, the system property can be set in `app.yaml`:\n```yaml\nenv_variables:\n  JETTY_ARGS: -Djava.util.logging.config.file=WEB-INF/logging.properties\n```\n\nIf the image is run directly, then a `-e` argument to the `docker run` command can be used to set the system property:\n\n```bash\ndocker run \\\n  -e JETTY_ARGS=-Djava.util.logging.config.file=WEB-INF/logging.properties \\\n  ...\n```\n\n### Providing `logging.properties` via a custom image\nIf this image is being used as the base of a custom image, then the following `Dockerfile` commands can be used to add either replace the existing logging configuration file or to add a new  `logging.properties` file.\n\nThe default logging configuration file is located at `/var/lib/jetty/etc/java-util-logging.properties`, which can be replaced in a custom image is built. The default configuration can be replaced with a `Dockerfile` like:\n\n```Dockerfile\nFROM gcr.io/google-appengine/jetty\nADD logging.properties /var/lib/jetty/etc/java-util-logging.properties\n...\n```\n\nAlternately an entirely new location for the file can be provided and the environment amended in a `Dockerfile` like:\n\n```Dockerfile\nFROM gcr.io/google-appengine/jetty\nADD logging.properties /etc/logging.properties\nENV JETTY_ARGS -Djava.util.logging.config.file=/etc/logging.properties\n...\n```\n\n### Providing `logging.properties` via docker run \nA `logging.properties` file may be added to an existing images using the `docker run` command if the deployment environment allows for the run arguments to be modified. The `-v` option can be used to bind a new `logging.properties` file to the running instance and the `-e` option can be used to set the system property to point to it:\n```shell \ndocker run -it --rm \\\n-v /mylocaldir/logging.properties:/etc/logging.properties \\\n-e JETTY_ARGS=\"-Djava.util.logging.config.file=/etc/logging.properties\" \\\n...\n```\n\n### Enhanced Stackdriver Logging (BETA)\nWhen running on the Google Cloud Platform Flex environment, the Java Util Logging can be configured to send logs to Google Stackdriver Logging by providing a `logging.properties` file that configures a [LoggingHandler](http://googlecloudplatform.github.io/google-cloud-java/0.10.0/apidocs/com/google/cloud/logging/LoggingHandler.html) as follows:\n```\nhandlers=com.google.cloud.logging.LoggingHandler\n\n# Optional configuration\n.level=INFO\ncom.google.cloud.logging.LoggingHandler.level=FINE\ncom.google.cloud.logging.LoggingHandler.log=gae_app.log\ncom.google.cloud.logging.LoggingHandler.formatter=java.util.logging.SimpleFormatter\njava.util.logging.SimpleFormatter.format=%3$s: %5$s%6$s\n\n```\nWhen deployed on the GCP Flex environment, an image so configured will automatically be configured with:\n* a [LabelLoggingEnhancer](https://github.com/GoogleCloudPlatform/google-cloud-java/blob/v0.17.2/google-cloud-logging/src/main/java/com/google/cloud/logging/MonitoredResourceUtil.java#L224) instance, that will add labels from the monitored resource to each log entry.\n* a [TraceLoggingEnhancer](https://github.com/GoogleCloudPlatform/google-cloud-java/blob/v0.17.2/google-cloud-logging/src/main/java/com/google/cloud/logging/TraceLoggingEnhancer.java) instance that will add any trace-id set to each log entry.\n* the `gcp` module will be enabled that configures jetty so that the [setCurrentTraceId](https://github.com/GoogleCloudPlatform/google-cloud-java/blob/v0.17.2/google-cloud-logging/src/main/java/com/google/cloud/logging/TraceLoggingEnhancer.java#L40) method is called for any thread handling a request.\n\nWhen deployed in other environments, logging enhancers can be manually configured by setting a comma separated list of class names as the\n`com.google.cloud.logging.LoggingHandler.enhancers` property.\n\nWhen using Stackdriver logging, it is recommended that `io.grpc` and `sun.net` logging level is kept at INFO level, as both these packages are used by Stackdriver internals and can result in verbose and/or initialisation problems. \n\n## Distributed Session Storage\nThe Jetty session mechanism is highly customizable and the options presented below are only a subset of meaningful configurations. Consult the [Jetty Sessions](https://www.eclipse.org/jetty/documentation/9.4.x/session-management.html) documentation for more details.\n### Google Cloud Session Store\nThis image can be configured to use [Google Cloud Datastore](https://cloud.google.com/datastore/docs/) for clustered session storage by enabling the `gcp-datastore-sessions` jetty module. You can do this in your app.yaml:\n```yaml\nenv_variables:\n  JETTY_MODULES_ENABLE: gcp-datastore-sessions\n```\n\nJetty will use the default namespace in Datastore as the store for all session data, or\n`jetty.session.gcloud.namespace` property can be used to set an alternative namespace.   By default gcloud has no request affinity, so all session data will be retrieved and stored from the datastore on every request and no session data will be shared in memory.\n\nNote that the `gcp-datastore-sessions` module is an aggregate module and the same configuration can be achieved by activating it's dependent modules individually:\n```yaml\nenv_variables:\n  JETTY_MODULES_ENABLE: session-cache-null,gcp-datastore,session-store-gcloud\n```\n\n### Cached Google Cloud Session Store\nThe Google Load Balancer can support instance affinity for more efficient session usage.  This can be configured in `app.yaml` with:\n```yaml\nnetwork:\n  session_affinity: true\n\nenv_variables:\n  JETTY_MODULES_ENABLE: session-cache-hash,gcp-datastore,session-store-gcloud\n```\nSessions will be retrieved from the in memory session cache and multiple requests can share a session instance. The Google Data Cloud is only accessed for unknown sessions (if affinity changes) or if a session is modified.\nSession cache behaviour can be further configured by following the [Jetty Session Cache](https://www.eclipse.org/jetty/documentation/9.4.x/session-configuration-sessioncache.html) documentation.  Note that affinity is achieved by the Google Load Balancer setting a `GCLB` cookie rather than tracking the `JSESSIONID` cookie.\n\n### Memcached Google Cloud Session Store (Alpha)\nSessions can be cached in memcache (without need for affinity) and backed by Google Cloud Datastore.  This can be configured in `app.yaml` with:\n\n```yaml\nenv_variables:\n  JETTY_MODULES_ENABLE: gcp-memcache-datastore-sessions\n```\nNote that the `gcp-memcache-datastore-sessions` module is an aggregate module and the same configuration can be achieved by activating it's dependent modules individually:\n\n```yaml\nenv_variables:\n  JETTY_MODULES_ENABLE: session-cache-null,gcp-datastore,session-store-gcloud,gcp-xmemcached,session-store-cache\n```\nThe `session-cache-null` module may be replaced with the `session-cache-hash` module to achieve 2 levels of caching (in memory and memcache) prior to accessing the Google Cloud Datastore, and network affinity may also be activated as above. \n\n## Extending the image\nThe image produced by this project may be automatically used/extended by the Cloud SDK and/or App Engine maven plugin. \nAlternately it may be explicitly extended with a custom Dockerfile.\n\nThe latest released version of this image is available at `launcher.gcr.io/google/jetty`, alternately you may \nbuild and push your own version with the shell commands:\n```bash\nmvn clean install\ndocker tag jetty:latest gcr.io/your-project-name/jetty:your-label\ngcloud docker -- push gcr.io/your-project-name/jetty:your-label\n```\n\n### Adding the root WAR application to an image\nA standard war file may be deployed as the root context in an extended image by placing the war file \nin the docker build directory and using a `Dockerfile` like:\n```dockerfile\nFROM launcher.gcr.io/google/jetty\nCOPY your-application.war $APP_DESTINATION_WAR\n```\n\nAn exploded-war can also be used:\n```dockerfile\nCOPY your-application $APP_DESTINATION_EXPLODED_WAR\n```\n\n\n### Adding the root application to an image\nIf the application exists as directory (i.e. an expanded war file), then directory must\nbe placed in the docker build directory and using a `Dockerfile` like: \n```dockerfile\nFROM launcher.gcr.io/google/jetty\nCOPY your-application-dir $JETTY_BASE/webapps/root\n```\n\n### Mounting the root application at local runtime\nIf no root WAR or root directory is found, the `docker-entrypoint.bash` script will link the \n`/app` directory as the root application. Thus the root application can be added to the \nimage via a runtime mount:\n```bash\ndocker run -v /some-path/your-application:/app launcher.gcr.io/google/jetty  \n```\n\n### Enabling dry-run\nThe image's default start command will first run the jetty start.jar as a --dry-run to generate the JVM\nstart command before starting the jetty web server. If you wish to generate the start command in your Dockerfile\nrather than at container start-time, you can run the `/scripts/jetty/generate-jetty-start.sh` script to generate it \nfor you, i.e. \n\n```Dockerfile\nRUN /scripts/jetty/generate-jetty-start.sh\n```\n\nNOTE: Make sure that the web application and any additional custom jetty modules have been added to the container\nBEFORE running this script.\n\n## Google Authentication using Jetty OpenID Module\n\nThe Jetty `openid` module adds support for the OpenID Connect authentication protocol over OAuth 2.0. This can be set up so that Jetty authenticates users with Google's Identity Platform allowing users to sign in with their Google account.\n\n### Set Up Application on Google API Console\n\nBefore your application can use Google's OAuth 2.0 authentication system for user login, \nyou must set up a project in the [Google API Console](https://console.developers.google.com/) \nto obtain OAuth 2.0 credentials (clientID and clientSecret), set a redirect URI, and (optionally) customize the \nbranding information that your users see on the user-consent screen.\n\nGuide to setting up Application in Google API Console:\nhttps://developers.google.com/identity/protocols/oauth2/openid-connect#appsetup\n\n### Jetty Configuration\n\nThe Jetty OpenID configuration is usually set in the `openid.ini` file. In this file we must set the values for the OpenID provider, the clientID and clientSecret. The OpenID provider should be set to `https://accounts.google.com`. The clientID and clientSecret should be obtained from the project which was set up in the Google API Console.\n\nSee the Jetty documentation for [OpenID Support](https://www.eclipse.org/jetty/documentation/current/openid-support.html) to get a general overview of how to enable OpenID authentication in your a webapp and how to access the authenticated users information.\n\n### Docker Configuration\n\nSpecial configuration should be added to the Dockerfile to enable the `openid` module and then to copy the `openid.ini` file to `$JETTY_BASE/start.d/`.\n\nExample Dockerfile:\n\n```Dockerfile\nFROM gcr.io/google-appengine/jetty\nRUN java -jar \"$JETTY_HOME/start.jar\" --create-startd\nRUN java -jar \"$JETTY_HOME/start.jar\" --add-to-start=webapp,deploy,http,openid\nCOPY openid.ini $JETTY_BASE/start.d/\nCOPY openid-webapp.war $JETTY_BASE/webapps/\n```\n\n# Development Guide\n\n* See [instructions](DEVELOPING.md) on how to build and test this image.\n\n# Contributing changes\n\n* See [CONTRIBUTING.md](CONTRIBUTING.md)\n\n## Licensing\n\n* See [LICENSE.md](LICENSE)\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fgooglecloudplatform%2Fjetty-runtime","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fgooglecloudplatform%2Fjetty-runtime","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fgooglecloudplatform%2Fjetty-runtime/lists"}