From 7fc38a6e22991477a231ce556a7f2860623afb67 Mon Sep 17 00:00:00 2001 From: Nikolche Mihajlovski Date: Mon, 23 Jan 2017 23:55:06 +0100 Subject: [PATCH] Add an official image for Rapidoid (#705) * Added documentation for the Rapidoid image. * Shorter description. * Replaced the "ADD" command with "COPY". * Referencing the MySQL container by name, instead of ID. * New logo for Rapidoid. --- rapidoid/README-short.txt | 1 + rapidoid/content.md | 135 ++++++++++++++++++++++++++++++++++++++ rapidoid/github-repo | 1 + rapidoid/license.md | 1 + rapidoid/logo.png | Bin 0 -> 17104 bytes 5 files changed, 138 insertions(+) create mode 100644 rapidoid/README-short.txt create mode 100644 rapidoid/content.md create mode 100644 rapidoid/github-repo create mode 100644 rapidoid/license.md create mode 100644 rapidoid/logo.png diff --git a/rapidoid/README-short.txt b/rapidoid/README-short.txt new file mode 100644 index 000000000..c3c94fb2a --- /dev/null +++ b/rapidoid/README-short.txt @@ -0,0 +1 @@ +Rapidoid is a high-performance HTTP server and modern Java web framework / application container. \ No newline at end of file diff --git a/rapidoid/content.md b/rapidoid/content.md new file mode 100644 index 000000000..c337697ac --- /dev/null +++ b/rapidoid/content.md @@ -0,0 +1,135 @@ +# What is Rapidoid? + +Rapidoid is an extremely fast HTTP server and modern Java web framework / application container, with a strong focus on high productivity and high performance. + +> [www.rapidoid.org](http://www.rapidoid.org) + +%%LOGO%% + +# How to use this image + +To quickly start Rapidoid and display some basic usage help, run: + +```console +$ docker run --rm %%REPO%% --help +``` + +Rapidoid can be used in different ways: + +- as a web tool, to quickly prototype RESTful web services from the command line +- as a HTTP server, to serve static resources +- as a Java web application framework/container, to deploy a web application JAR + +## Quickly prototyping SQL-powered RESTful web services + +To quickly prototype SQL-powered RESTful web services from the command line, you need to link the database container to the Rapidoid container. The MySQL containers should be linked under name `mysql`, and PostgreSQL containers under name `postgres`. + +This example starts a new MySQL container and links it under name `mysql` in the Rapidoid container, where a RESTful service is defined by specifying SQL query for the route `GET /users`. The service returns the result (a list of MySQL users) in JSON format. + +```console +docker run -d --name some-mysql -e MYSQL_ROOT_PASSWORD=db-pass mysql + +docker run -it --rm \ + -p 8888:8888 \ + --link some-mysql:mysql \ + %%REPO%% \ + profiles=mysql \ + jdbc.password=db-pass \ + '/users <= SELECT user FROM mysql.user' +``` + +**Note:** Please wait for several seconds for the MySQL database to initialize, and then you can visit [http://localhost:8888/users](http://localhost:8888/users) (or `http://your-host:8888/users`) in your web browser. + +**Syntax for the service prototyping arguments**: + +```console +'[GET|POST|PUT|DELETE|PATCH] <= ' +``` + +## Serving static files + +Rapidoid will automatically serve static files from the folders: `/app/static` (or `/app/public`, which is deprecated). To serve the contents of the `/your-www-root` directory, please mount it as `/app/static`: + +```console +$ docker run -it --rm \ + -p 8888:8888 \ + -v /your-www-root:/app/static \ + %%REPO%% +``` + +## Configuration + +Rapidoid will try to read the configuration from `/app/config.yml`. The configuration can also be specified with command-line arguments or environment variables. + +To configure a custom port (by default `8888`) for the default and the Admin server, run the following command. If `admin.port` is not configured, the default server is also used as Admin server, so only one port will be opened (`on.port`). + +```console +$ docker run -it --rm \ + -p 4444:4444 \ + -p 9999:9999 \ + %%REPO%% \ + on.port=4444 \ + admin.port=9999 \ + app.services=ping \ + admin.services=status +``` + +Then you can visit [http://localhost:4444/\_ping](http://localhost:4444/_ping) (or `http://your-host:4444/_ping`) and [http://localhost:9999/\_status](http://localhost:9999/_status) (or `http://your-host:9999/_status`) in your web browser. + +The same setup can be configured with environment variables: + +```console +$ docker run -it --rm \ + -p 4444:4444 \ + -p 9999:9999 \ + -e ON_PORT=4444 \ + -e ADMIN_PORT=9999 \ + %%REPO%% \ + app.services=ping \ + admin.services=status +``` + +For more details, please see the [full list of configuration options and their default values](http://www.rapidoid.org/the-default-configuration.html). + +## Security + +Rapidoid's HMAC-based security token mechanism requires all containers to share the same secret key when scaling out a web application: + +```console +$ docker run -it --rm \ + -p 8888:8888 \ + -e SECRET=your-secret-key \ + %%REPO%% +``` + +While this is an easy way to get started, for security reasons it is recommended to store the secret key in the `/app/config.yml` file, with proper permissions. + +**Note:** For production use, you must replace `your-secret-key` with a real, private secret key. + +**Note:** If no secret key is specified, a random secret key will be generated, which is acceptable when deploying a single container. + +## Full bootstrap of Rapidoid's Admin Center + +To bootstrap a full-blown Admin Center in Rapidoid, you will also need to configure a password for the built-in `admin` user: + +```console +$ docker run -d \ + --restart=always \ + -p 8888:8888 \ + -e SECRET=your-secret-key \ + -e USERS_ADMIN_PASSWORD=admin-pass \ + %%REPO%% \ + admin.services=center +``` + +Please replace `admin-pass` with a real password for the `admin` user. Then you can login to the Admin Center by visiting [http://localhost:8888/\_](http://localhost:8888/_) (or `http://your-host:8888/_`) in your web browser. + +**Note:** For production use, you must replace `your-secret-key` with a real, private secret key (please see the `Security` section). + +# How to extend this image (application JAR deployment) + +To use this image as base image for your web application, simply add your application JAR as `/app/app.jar`: + +```dockerfile +COPY /app/app.jar +``` diff --git a/rapidoid/github-repo b/rapidoid/github-repo new file mode 100644 index 000000000..5d641cbbf --- /dev/null +++ b/rapidoid/github-repo @@ -0,0 +1 @@ +https://github.com/rapidoid/docker-rapidoid diff --git a/rapidoid/license.md b/rapidoid/license.md new file mode 100644 index 000000000..625f0d256 --- /dev/null +++ b/rapidoid/license.md @@ -0,0 +1 @@ +View [license information](https://www.apache.org/licenses/LICENSE-2.0) for the software contained in this image. diff --git a/rapidoid/logo.png b/rapidoid/logo.png new file mode 100644 index 0000000000000000000000000000000000000000..9ca829262b18c84c5593612b44307c09f68c9ea6 GIT binary patch literal 17104 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 literal 0 HcmV?d00001