diff --git a/.dockerignore b/.dockerignore
new file mode 100644
index 0000000..12c776b
--- /dev/null
+++ b/.dockerignore
@@ -0,0 +1,33 @@
+.dockerignore
+docker-compose.yml
+docker-compose.*.yml
+
+# Ignore git, but keep git HEAD and refs to access current commit hash if needed:
+#
+# $ cat .git/HEAD | awk '{print ".git/"$2}' | xargs cat
+# d0b8727759e1e0e7aa3d41707d12376e373d5ecc
+.git
+!.git/HEAD
+!.git/refs
+
+# Common development/test artifacts
+/cover/
+/doc/
+/test/
+/tmp/
+/.elixir_ls
+/.elixir-tools/
+
+# Mix artifacts
+/_build/
+/deps/
+*.ez
+
+# Generated on crash by the VM
+erl_crash.dump
+
+# Static artifacts - These should be fetched and built inside the Docker image
+/assets/node_modules/
+/priv/plts/
+/priv/static/assets/
+/priv/static/cache_manifest.json
diff --git a/.gitignore b/.gitignore
index 92ca450..c63085e 100644
--- a/.gitignore
+++ b/.gitignore
@@ -1,4 +1,6 @@
 # paths
+/.elixir_ls/
+/.elixir-tools/
 /_build/
 /cover/
 /report/
@@ -13,5 +15,5 @@ erl_crash.dump
 *.ez
 wabanex-*.tar
 docker-compose.*.yml
-priv/docker/pgcli/history
-priv/docker/pgcli/log
+/priv/docker/pgcli/history
+/priv/docker/pgcli/log
diff --git a/Dockerfile b/Dockerfile
index f0578c2..c8360d6 100644
--- a/Dockerfile
+++ b/Dockerfile
@@ -1,10 +1,70 @@
-FROM hexpm/elixir:1.17.2-erlang-27.0.1-debian-bookworm-20240701-slim AS builder
+ARG ELIXIR_VERSION=1.17.3
+ARG OTP_VERSION=27.1
+ARG DEBIAN_VERSION=bookworm-20240904-slim
+ARG BUILDER_IMAGE="hexpm/elixir:${ELIXIR_VERSION}-erlang-${OTP_VERSION}-debian-${DEBIAN_VERSION}"
+ARG RUNNER_IMAGE="debian:${DEBIAN_VERSION}"
 
+FROM ${BUILDER_IMAGE} AS builder
 RUN apt-get update \
-  && apt-get -y install git make
-
+  && apt-get -y install \
+    build-essential \
+    git \
+    make \
+  && apt-get clean \
+  && rm -rf /var/lib/ap/lists/*_*
 WORKDIR /opt/app
+# install hex + rebar
+RUN mix do local.hex --force, local.rebar --force
+# set build ENV
+ARG BUILD_MIX_ENV=prod
+ENV MIX_ENV=${BUILD_MIX_ENV}
+# install mix dependencies
+COPY mix.exs mix.lock ./
+RUN mix deps.get --only ${MIX_ENV}
+RUN mkdir config
+# copy compile-time config files before we compile dependencies
+# to ensure any relevant config change will trigger the dependencies
+# to be re-compiled.
+COPY config/config.exs config/${BUILD_MIX_ENV}.exs config/
+RUN mix deps.compile
+COPY priv priv
+COPY lib lib
+# Compile the release
+RUN mix compile
+# Changes to config/runtime.exs don't require recompiling the code
+COPY config/runtime.exs config/
+COPY rel rel
+RUN mix release
 COPY ./mix.exs ./
-COPY ./mix.lock ./
-RUN mix do local.hex --force, local.rebar --force \
-  && mix do deps.get, deps.compile
+EXPOSE 4000
+ENTRYPOINT ["./priv/docker/service/docker-entrypoint.sh"]
+CMD ["sample-cookie"]
+
+# start a new build stage so that the final image will only contain
+# the compiled release and other runtime necessities
+FROM ${RUNNER_IMAGE}
+RUN apt-get update -y \
+  && apt-get install -y \
+    ca-certificates \
+    libncurses5 \
+    libstdc++6 \
+    locales \
+    openssl \
+    tini \
+  && apt-get clean && rm -f /var/lib/apt/lists/*_*
+# Set the locale
+RUN sed -i '/en_US.UTF-8/s/^# //g' /etc/locale.gen && locale-gen
+ENV LANG en_US.UTF-8
+ENV LANGUAGE en_US:en
+ENV LC_ALL en_US.UTF-8
+WORKDIR /opt/app
+RUN chown nobody /opt/app
+# set runner ENV
+ARG BUILD_MIX_ENV=prod
+ENV MIX_ENV=${BUILD_MIX_ENV}
+# Only copy the final release from the build stage
+COPY --from=builder --chown=nobody:root /app/_build/${BUILD_MIX_ENV}/rel/wabanex ./
+USER nobody
+EXPOSE 4000
+ENTRYPOINT ["tini", "--"]
+CMD ["/app/bin/server"]
diff --git a/Makefile b/Makefile
index ab5f641..9e7f75f 100644
--- a/Makefile
+++ b/Makefile
@@ -32,21 +32,17 @@ test:  ## run tests
 compose_up:  ## start containers for this service
 	@$(COMPOSE) up -d
 
-.PHONY: compose_deps_upgrade
-compose_deps_upgrade:  ## install/upgrade deps
-	@$(COMPOSE) run --entrypoint mix app do deps.get, deps.compile, compile
-
-.PHONY: compose_test
-compose_test:  ## run tests in containers
-	@$(COMPOSE) run -e MIX_ENV=test --entrypoint make app test
+.PHONY: compose_watch
+compose_watch:  ## start containers for this service watching for updates in filesystem
+	@$(COMPOSE) up -w
 
 .PHONY: compose_database_create
 compose_database_create:
-	@$(COMPOSE) --profile setup run db_setup
+	@$(COMPOSE) run --rm --entrypoint mix app ecto.create
 
 .PHONY: compose_database_migrate
 compose_database_migrate:  ## apply migrations to our database
-	@$(COMPOSE) --profile migrate run db_migrate
+	@$(COMPOSE) run --rm --entrypoint mix app ecto.migrate
 
 .PHONY: compose_database_setup
 compose_database_setup: compose_database_create compose_database_migrate  ## create and apply migrations
@@ -55,6 +51,10 @@ compose_database_setup: compose_database_create compose_database_migrate  ## cre
 compose_ps:  ## status of containers
 	@$(COMPOSE) ps
 
+.PHONY: compose_remote
+compose_remote:  ## connect to remote node
+	@$(COMPOSE) exec app ./priv/docker/service/docker-remote.sh
+
 .PHONY: help
 help:
 	@grep -E '^[a-zA-Z_-]+:.*?## .*$$' $(MAKEFILE_LIST) | sort | awk 'BEGIN {FS = ":.*?## "}; {printf "\033[36m%-30s\033[0m %s\n", $$1, $$2}'
diff --git a/config/config.exs b/config/config.exs
index 0702aa3..387793c 100644
--- a/config/config.exs
+++ b/config/config.exs
@@ -1,10 +1,3 @@
-# This file is responsible for configuring your application
-# and its dependencies with the aid of the Mix.Config module.
-#
-# This configuration file is loaded before any dependency and
-# is restricted to this project.
-
-# General application configuration
 import Config
 
 config :wabanex,
@@ -21,7 +14,6 @@ config :wabanex, Wabanex.PromEx,
   grafana: :disabled,
   metrics_server: :disabled
 
-# Configures the endpoint
 config :wabanex, WabanexWeb.Endpoint,
   url: [host: "localhost"],
   secret_key_base: "wkyuhU+mCGwXUSBYVKZSRGoFmDYCbOFzdokbVmBBI9JgCWOqGPfuA/3JI5/b4Wdl",
@@ -29,14 +21,10 @@ config :wabanex, WabanexWeb.Endpoint,
   pubsub_server: Wabanex.PubSub,
   live_view: [signing_salt: "SXtw7DzV"]
 
-# Configures Elixir's Logger
 config :logger, :console,
   format: "$time $metadata[$level] $message\n",
   metadata: [:request_id]
 
-# Use Jason for JSON parsing in Phoenix
 config :phoenix, :json_library, Jason
 
-# Import environment specific config. This must remain at the bottom
-# of this file so it overrides the configuration defined above.
 import_config "#{config_env()}.exs"
diff --git a/config/dev.exs b/config/dev.exs
index 1faf08e..9cea01d 100644
--- a/config/dev.exs
+++ b/config/dev.exs
@@ -1,17 +1,14 @@
 import Config
 
-# Configure your database
+config :wabanex,
+  dns_cluster_query: :ignore,
+  dns_cluster_resolver: Wabanex.DevDNSClusterResolver
+
 config :wabanex, Wabanex.Repo,
   database: "wabanex_dev",
   show_sensitive_data_on_connection_error: true,
   pool_size: 10
 
-# For development, we disable any cache and enable
-# debugging and code reloading.
-#
-# The watchers configuration can be used to run external
-# watchers to your application. For example, we use it
-# with webpack to recompile .js and .css sources.
 config :wabanex, WabanexWeb.Endpoint,
   http: [port: 4000],
   debug_errors: true,
@@ -19,36 +16,8 @@ config :wabanex, WabanexWeb.Endpoint,
   check_origin: false,
   watchers: []
 
-# ## SSL Support
-#
-# In order to use HTTPS in development, a self-signed
-# certificate can be generated by running the following
-# Mix task:
-#
-#     mix phx.gen.cert
-#
-# Note that this task requires Erlang/OTP 20 or later.
-# Run `mix help phx.gen.cert` for more information.
-#
-# The `http:` config above can be replaced with:
-#
-#     https: [
-#       port: 4001,
-#       cipher_suite: :strong,
-#       keyfile: "priv/cert/selfsigned_key.pem",
-#       certfile: "priv/cert/selfsigned.pem"
-#     ],
-#
-# If desired, both `http:` and `https:` keys can be
-# configured to run both http and https servers on
-# different ports.
-
-# Do not include metadata nor timestamps in development logs
 config :logger, :console, format: "[$level] $message\n"
 
-# Set a higher stacktrace during development. Avoid configuring such
-# in production as building large stacktraces may be expensive.
 config :phoenix, :stacktrace_depth, 20
 
-# Initialize plugs at runtime for faster development compilation
 config :phoenix, :plug_init_mode, :runtime
diff --git a/config/prod.exs b/config/prod.exs
index 10f9447..9671347 100644
--- a/config/prod.exs
+++ b/config/prod.exs
@@ -1,55 +1,7 @@
 import Config
 
-# For production, don't forget to configure the url host
-# to something meaningful, Phoenix uses this information
-# when generating URLs.
-#
-# Note we also include the path to a cache manifest
-# containing the digested version of static files. This
-# manifest is generated by the `mix phx.digest` task,
-# which you should run after static files are built and
-# before starting your production server.
 config :wabanex, WabanexWeb.Endpoint,
   url: [host: "example.com", port: 80],
   cache_static_manifest: "priv/static/cache_manifest.json"
 
-# Do not print debug messages in production
 config :logger, level: :info
-
-# ## SSL Support
-#
-# To get SSL working, you will need to add the `https` key
-# to the previous section and set your `:url` port to 443:
-#
-#     config :wabanex, WabanexWeb.Endpoint,
-#       ...
-#       url: [host: "example.com", port: 443],
-#       https: [
-#         port: 443,
-#         cipher_suite: :strong,
-#         keyfile: System.get_env("SOME_APP_SSL_KEY_PATH"),
-#         certfile: System.get_env("SOME_APP_SSL_CERT_PATH"),
-#         transport_options: [socket_opts: [:inet6]]
-#       ]
-#
-# The `cipher_suite` is set to `:strong` to support only the
-# latest and more secure SSL ciphers. This means old browsers
-# and clients may not be supported. You can set it to
-# `:compatible` for wider support.
-#
-# `:keyfile` and `:certfile` expect an absolute path to the key
-# and cert in disk or a relative path inside priv, for example
-# "priv/ssl/server.key". For all supported SSL configuration
-# options, see https://hexdocs.pm/plug/Plug.SSL.html#configure/1
-#
-# We also recommend setting `force_ssl` in your endpoint, ensuring
-# no data is ever sent via http, always redirecting to https:
-#
-#     config :wabanex, WabanexWeb.Endpoint,
-#       force_ssl: [hsts: true]
-#
-# Check `Plug.SSL` for all available options in `force_ssl`.
-
-# Finally import the config/prod.secret.exs which loads secrets
-# and configuration from environment variables.
-import_config "prod.secret.exs"
diff --git a/config/runtime.exs b/config/runtime.exs
index 7120844..bc5dec1 100644
--- a/config/runtime.exs
+++ b/config/runtime.exs
@@ -1,5 +1,35 @@
 import Config
 
+# [warn] Conditional IPv6 support missing from runtime configuration.
+#
+# Add the following to your config/runtime.exs:
+#
+#     maybe_ipv6 = if System.get_env("ECTO_IPV6") in ~w(true 1), do: [:inet6], else: []
+#
+#     config :wabanex, Wabanex.Repo,
+#       ...,
+#       socket_options: maybe_ipv6
+#
+# [warn] Conditional server startup is missing from runtime configuration.
+#
+# Add the following to the top of your config/runtime.exs:
+#
+#     if System.get_env("PHX_SERVER") do
+#       config :wabanex, WabanexWeb.Endpoint, server: true
+#     end
+#
+# [warn] Environment based URL export is missing from runtime configuration.
+#
+# Add the following to your config/runtime.exs:
+#
+#     host = System.get_env("PHX_HOST") || "example.com"
+#
+#     config :wabanex, WabanexWeb.Endpoint,
+#       ...,
+#       url: [host: host, port: 443]
+
+config :wabanex, dns_cluster_query: System.get_env("DNS_CLUSTER_QUERY") || :ignore
+
 config :wabanex, Wabanex.Repo,
   username: System.get_env("POSTGRES_USER") || "postgres",
   password: System.get_env("POSTGRES_PASS") || "postgres",
diff --git a/config/test.exs b/config/test.exs
index c5b87de..4b124fa 100644
--- a/config/test.exs
+++ b/config/test.exs
@@ -1,21 +1,13 @@
 import Config
 
-# Configure your database
-#
-# The MIX_TEST_PARTITION environment variable can be used
-# to provide built-in test partitioning in CI environment.
-# Run `mix help test` for more information.
 config :wabanex, Wabanex.Repo,
   database: "wabanex_test#{System.get_env("MIX_TEST_PARTITION")}",
   pool: Ecto.Adapters.SQL.Sandbox
 
-# We don't run a server during test. If one is required,
-# you can enable the server option below.
 config :wabanex, WabanexWeb.Endpoint,
   http: [port: 4002],
   server: false
 
-# Print only warnings and errors during test
 config :logger, level: :warning
 
 config :junit_formatter,
diff --git a/docker-compose.yml b/docker-compose.yml
index 077d0d8..05612ac 100644
--- a/docker-compose.yml
+++ b/docker-compose.yml
@@ -7,59 +7,52 @@ services:
     environment:
       POSTGRES_USER: &db_user postgres
       POSTGRES_PASSWORD: &db_pass postgres
-      POSTGRES_DB: &db_name postgres
+      POSTGRES_DB: postgres
     volumes:
       - './priv/docker/postgres/init.sql:/docker-entrypoint-initdb.d/init.sql'
       - 'db_data:/var/lib/postgresql/data'
     restart: unless-stopped
   app:
-    image: &app_image 'joaodubas/ex_trainer:${EX_TRAINER_TAG:-dev}'
+    image: 'joaodubas/ex_trainer:${EX_TRAINER_TAG:-dev}'
     build:
       target: builder
       context: .
-    hostname: app
+      args:
+        BUILD_MIX_ENV: dev
+    hostname: &app_host ex_trainer
     depends_on:
       - db
     init: true
-    environment: &app_environment
+    develop:
+      watch:
+        - path: ./
+          ignore:
+            - ./build/
+            - ./deps/
+          target: /opt/app
+          action: sync
+        - path: ./config/
+          target: /opt/app
+          action: sync+restart
+        - path: ./lib/wabanex/application.ex
+          target: /opt/app
+          action: sync+restart
+        - path: ./mix.exs
+          target: /opt/app
+          action: sync+restart
+        - path: ./mix.lock
+          action: rebuild
+    environment:
+      DNS_CLUSTER_QUERY: *app_host
       POSTGRES_HOST: *db_host
       POSTGRES_USER: *db_user
       POSTGRES_PASS: *db_pass
       POSTGRES_NAME: wabanex_dev
-    volumes: &app_volumes
-      - '.:/opt/app'
-      - 'app_build:/opt/app/_build'
-      - 'app_deps:/opt/app/deps'
     working_dir: /opt/app
     restart: unless-stopped
-    entrypoint: sleep
-    command: infinity
-  db_setup:
-    image: *app_image
-    depends_on:
-      - db
-    profiles:
-      - setup
-    environment: *app_environment
-    volumes: *app_volumes
-    restart: 'no'
-    command: |
-      mix ecto.setup \
-      && MIX_ENV=test mix ecto.setup
-  db_migrate:
-    image: *app_image
-    depends_on:
-      - db
-    profiles:
-      - migrate
-    environment: *app_environment
-    volumes: *app_volumes
-    restart: 'no'
-    command: |
-      mix ecto.migrate \
-      && MIX_ENV=test mix.ecto.migrate
+    scale: 3
+    entrypoint: ./priv/docker/service/docker-entrypoint.sh
+    command: local-cookie
 
 volumes:
   db_data: {}
-  app_build: {}
-  app_deps: {}
diff --git a/lib/wabanex/application.ex b/lib/wabanex/application.ex
index 2960117..346d587 100644
--- a/lib/wabanex/application.ex
+++ b/lib/wabanex/application.ex
@@ -1,34 +1,25 @@
 defmodule Wabanex.Application do
-  # See https://hexdocs.pm/elixir/Application.html
-  # for more information on OTP Applications
   @moduledoc false
 
   use Application
 
   def start(_type, _args) do
     children = [
-      # Start the PromEx supervisor
       Wabanex.PromEx,
-      # Start the Ecto repository
       Wabanex.Repo,
-      # Start the Telemetry supervisor
       WabanexWeb.Telemetry,
-      # Start the PubSub system
       {Phoenix.PubSub, name: Wabanex.PubSub},
-      # Start the Endpoint (http/https)
+      {DNSCluster,
+       query: Application.get_env(:wabanex, :dns_cluster_query) || :ignore,
+       log: :info,
+       resolver: Application.get_env(:wabanex, :dns_cluster_resolver) || DNSCluster.Resolver},
       WabanexWeb.Endpoint
-      # Start a worker by calling: Wabanex.Worker.start_link(arg)
-      # {Wabanex.Worker, arg}
     ]
 
-    # See https://hexdocs.pm/elixir/Supervisor.html
-    # for other strategies and supported options
     opts = [strategy: :one_for_one, name: Wabanex.Supervisor]
     Supervisor.start_link(children, opts)
   end
 
-  # Tell Phoenix to update the endpoint configuration
-  # whenever the application is updated.
   def config_change(changed, _new, removed) do
     WabanexWeb.Endpoint.config_change(changed, removed)
     :ok
diff --git a/lib/wabanex/dev_dns_cluster_resolver.ex b/lib/wabanex/dev_dns_cluster_resolver.ex
new file mode 100644
index 0000000..a802fe0
--- /dev/null
+++ b/lib/wabanex/dev_dns_cluster_resolver.ex
@@ -0,0 +1,26 @@
+defmodule Wabanex.DevDNSClusterResolver do
+  @moduledoc """
+  Local DNS resolver for cluster query.
+  """
+  require Record
+
+  Record.defrecord(:hostent, Record.extract(:hostent, from_lib: "kernel/include/inet.hrl"))
+
+  def basename(node_name) when is_atom(node_name) do
+    [basename, _] = node_name |> to_string() |> String.split("@")
+    basename
+  end
+
+  def connect_node(node_name) when is_atom(node_name) do
+    Node.connect(node_name)
+  end
+
+  def list_nodes, do: Node.list(:visible)
+
+  def lookup(query, type) when is_binary(query) and type in [:a, :aaaa] do
+    case :inet_res.getbyname(~c"#{query}", type) do
+      {:ok, hostent(h_addr_list: addr_list)} -> addr_list
+      {:error, _} -> []
+    end
+  end
+end
diff --git a/lib/wabanex/release.ex b/lib/wabanex/release.ex
new file mode 100644
index 0000000..10ba398
--- /dev/null
+++ b/lib/wabanex/release.ex
@@ -0,0 +1,28 @@
+defmodule Wabanex.Release do
+  @moduledoc """
+  Used for executing DB release tasks when run in production without Mix
+  installed.
+  """
+  @app :wabanex
+
+  def migrate do
+    load_app()
+
+    for repo <- repos() do
+      {:ok, _, _} = Ecto.Migrator.with_repo(repo, &Ecto.Migrator.run(&1, :up, all: true))
+    end
+  end
+
+  def rollback(repo, version) do
+    load_app()
+    {:ok, _, _} = Ecto.Migrator.with_repo(repo, &Ecto.Migrator.run(&1, :down, to: version))
+  end
+
+  defp repos do
+    Application.fetch_env!(@app, :ecto_repos)
+  end
+
+  defp load_app do
+    Application.load(@app)
+  end
+end
diff --git a/mix.exs b/mix.exs
index edb04fb..3323f16 100644
--- a/mix.exs
+++ b/mix.exs
@@ -36,6 +36,7 @@ defmodule Wabanex.MixProject do
       {:credo, "~> 1.7.0", only: [:dev, :test], runtime: false},
       {:crudry, "~> 2.4.0"},
       {:dialyxir, "~> 1.4.0", only: [:dev, :test], runtime: false},
+      {:dns_cluster, "~> 0.1.1"},
       {:ecto_sql, "~> 3.12.0"},
       {:gettext, "~> 0.25.0"},
       {:jason, "~> 1.4.0"},
diff --git a/mix.lock b/mix.lock
index 6a6d8e5..e75b24d 100644
--- a/mix.lock
+++ b/mix.lock
@@ -11,6 +11,7 @@
   "db_connection": {:hex, :db_connection, "2.7.0", "b99faa9291bb09892c7da373bb82cba59aefa9b36300f6145c5f201c7adf48ec", [:mix], [{:telemetry, "~> 0.4 or ~> 1.0", [hex: :telemetry, repo: "hexpm", optional: false]}], "hexpm", "dcf08f31b2701f857dfc787fbad78223d61a32204f217f15e881dd93e4bdd3ff"},
   "decimal": {:hex, :decimal, "2.1.1", "5611dca5d4b2c3dd497dec8f68751f1f1a54755e8ed2a966c2633cf885973ad6", [:mix], [], "hexpm", "53cfe5f497ed0e7771ae1a475575603d77425099ba5faef9394932b35020ffcc"},
   "dialyxir": {:hex, :dialyxir, "1.4.3", "edd0124f358f0b9e95bfe53a9fcf806d615d8f838e2202a9f430d59566b6b53b", [:mix], [{:erlex, ">= 0.2.6", [hex: :erlex, repo: "hexpm", optional: false]}], "hexpm", "bf2cfb75cd5c5006bec30141b131663299c661a864ec7fbbc72dfa557487a986"},
+  "dns_cluster": {:hex, :dns_cluster, "0.1.3", "0bc20a2c88ed6cc494f2964075c359f8c2d00e1bf25518a6a6c7fd277c9b0c66", [:mix], [], "hexpm", "46cb7c4a1b3e52c7ad4cbe33ca5079fbde4840dedeafca2baf77996c2da1bc33"},
   "ecto": {:hex, :ecto, "3.12.0", "9014a3ccac7f91e680b9d237d461ebe3d4e16d62ca8e355d540e2c6afdc28309", [:mix], [{:decimal, "~> 2.0", [hex: :decimal, repo: "hexpm", optional: false]}, {:jason, "~> 1.0", [hex: :jason, repo: "hexpm", optional: true]}, {:telemetry, "~> 0.4 or ~> 1.0", [hex: :telemetry, repo: "hexpm", optional: false]}], "hexpm", "41e781a76e131093af8e1edf68b1319bf320878faff58da41ffa4b10fc6ff678"},
   "ecto_sql": {:hex, :ecto_sql, "3.12.0", "73cea17edfa54bde76ee8561b30d29ea08f630959685006d9c6e7d1e59113b7d", [:mix], [{:db_connection, "~> 2.4.1 or ~> 2.5", [hex: :db_connection, repo: "hexpm", optional: false]}, {:ecto, "~> 3.12", [hex: :ecto, repo: "hexpm", optional: false]}, {:myxql, "~> 0.7", [hex: :myxql, repo: "hexpm", optional: true]}, {:postgrex, "~> 0.19 or ~> 1.0", [hex: :postgrex, repo: "hexpm", optional: true]}, {:tds, "~> 2.1.1 or ~> 2.2", [hex: :tds, repo: "hexpm", optional: true]}, {:telemetry, "~> 0.4.0 or ~> 1.0", [hex: :telemetry, repo: "hexpm", optional: false]}], "hexpm", "dc9e4d206f274f3947e96142a8fdc5f69a2a6a9abb4649ef5c882323b6d512f0"},
   "erlex": {:hex, :erlex, "0.2.7", "810e8725f96ab74d17aac676e748627a07bc87eb950d2b83acd29dc047a30595", [:mix], [], "hexpm", "3ed95f79d1a844c3f6bf0cea61e0d5612a42ce56da9c03f01df538685365efb0"},
diff --git a/priv/docker/service/docker-entrypoint.sh b/priv/docker/service/docker-entrypoint.sh
new file mode 100755
index 0000000..f359da7
--- /dev/null
+++ b/priv/docker/service/docker-entrypoint.sh
@@ -0,0 +1,2 @@
+#!/usr/bin/env bash
+elixir --name ${HOSTNAME}@$(hostname -i | cut -d ' ' -f1) --cookie ${1} -S mix phx.server
diff --git a/priv/docker/service/docker-remote.sh b/priv/docker/service/docker-remote.sh
new file mode 100755
index 0000000..1a543ec
--- /dev/null
+++ b/priv/docker/service/docker-remote.sh
@@ -0,0 +1,2 @@
+#!/usr/bin/env bash
+iex --name ex_trainer_remote@127.0.0.1 --hidden --cookie local-cookie --remsh ${HOSTNAME}@$(hostname -i | cut -d ' ' -f1)
diff --git a/rel/overlays/bin/migrate b/rel/overlays/bin/migrate
new file mode 100755
index 0000000..1d0884e
--- /dev/null
+++ b/rel/overlays/bin/migrate
@@ -0,0 +1,5 @@
+#!/bin/sh
+set -eu
+
+cd -P -- "$(dirname -- "$0")"
+exec ./wabanex eval Wabanex.Release.migrate
diff --git a/rel/overlays/bin/migrate.bat b/rel/overlays/bin/migrate.bat
new file mode 100755
index 0000000..b065b42
--- /dev/null
+++ b/rel/overlays/bin/migrate.bat
@@ -0,0 +1 @@
+call "%~dp0\wabanex" eval Wabanex.Release.migrate
diff --git a/rel/overlays/bin/server b/rel/overlays/bin/server
new file mode 100755
index 0000000..36cba5a
--- /dev/null
+++ b/rel/overlays/bin/server
@@ -0,0 +1,5 @@
+#!/bin/sh
+set -eu
+
+cd -P -- "$(dirname -- "$0")"
+PHX_SERVER=true exec ./wabanex start
diff --git a/rel/overlays/bin/server.bat b/rel/overlays/bin/server.bat
new file mode 100755
index 0000000..5c38da8
--- /dev/null
+++ b/rel/overlays/bin/server.bat
@@ -0,0 +1,2 @@
+set PHX_SERVER=true
+call "%~dp0\wabanex" start