Web Client #11
1
.gitignore
vendored
1
.gitignore
vendored
@ -26,3 +26,4 @@ server-*.tar
|
||||
/tmp/
|
||||
|
||||
.env
|
||||
.env.prod
|
||||
|
74
Dockerfile
Normal file
74
Dockerfile
Normal file
@ -0,0 +1,74 @@
|
||||
ARG ELIXIR_VERSION=1.14.0
|
||||
ARG OTP_VERSION=25.2.1
|
||||
ARG DEBIAN_VERSION=bullseye-20230109-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
|
||||
|
||||
# install build dependencies
|
||||
RUN apt-get update -y && apt-get install -y build-essential git \
|
||||
&& apt-get clean && rm -f /var/lib/apt/lists/*_*
|
||||
|
||||
# prepare build dir
|
||||
WORKDIR /app
|
||||
|
||||
# install hex + rebar
|
||||
RUN mix local.hex --force && \
|
||||
mix local.rebar --force
|
||||
|
||||
# set build ENV
|
||||
ENV MIX_ENV="prod"
|
||||
|
||||
# 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/${MIX_ENV}.exs config/
|
||||
RUN mix deps.compile
|
||||
|
||||
COPY priv priv
|
||||
|
||||
# Compile the release
|
||||
COPY lib lib
|
||||
|
||||
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
|
||||
|
||||
# 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 libstdc++6 openssl libncurses5 locales \
|
||||
&& 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 "/app"
|
||||
RUN chown nobody /app
|
||||
|
||||
# set runner ENV
|
||||
ENV MIX_ENV="prod"
|
||||
|
||||
# Only copy the final release from the build stage
|
||||
COPY --from=builder --chown=nobody:root /app/_build/${MIX_ENV}/rel/chessh ./
|
||||
COPY --from=builder --chown=nobody:root /app/priv /app/priv
|
||||
|
||||
USER nobody
|
||||
|
||||
CMD /app/bin/chessh eval "Chessh.Release.migrate" && /app/bin/chessh start
|
23
build.sh
Normal file → Executable file
23
build.sh
Normal file → Executable file
@ -1,11 +1,16 @@
|
||||
#!/usr/bin/env bash
|
||||
# Initial setup
|
||||
mix deps.get --only prod
|
||||
MIX_ENV=prod mix compile
|
||||
#!/bin/bash
|
||||
|
||||
# Remove the existing release directory and build the release
|
||||
rm -rf "_build"
|
||||
MIX_ENV=prod mix release
|
||||
env_file=.env.prod
|
||||
started_in=$PWD
|
||||
|
||||
# for auto DB migration upon deploy
|
||||
MIX_ENV=prod mix ecto.migrate
|
||||
export $(cat $env_file | xargs)
|
||||
|
||||
cd front
|
||||
docker build \
|
||||
--build-arg REACT_APP_GITHUB_OAUTH=${REACT_APP_GITHUB_OAUTH} \
|
||||
--build-arg REACT_APP_SSH_SERVER=${REACT_APP_SSH_SERVER} \
|
||||
--build-arg REACT_APP_SSH_PORT=${REACT_APP_SSH_PORT} \
|
||||
. -t chessh/frontend
|
||||
|
||||
cd $started_in
|
||||
docker build . -t chessh/server
|
||||
|
55
deploy.sh
Executable file
55
deploy.sh
Executable file
@ -0,0 +1,55 @@
|
||||
#!/bin/bash
|
||||
|
||||
datestamp=$(date +%Y%m%d-%H%M)
|
||||
env_file=.env.prod
|
||||
project_name=chessh
|
||||
port=8080
|
||||
host=127.0.0.1
|
||||
|
||||
container_names=("chessh-database" "chessh-server" "chessh-frontend")
|
||||
|
||||
for name in ${container_names[@]}; do
|
||||
docker stop $name
|
||||
docker rm $name
|
||||
done
|
||||
|
||||
# Create network for chessh
|
||||
docker network ls | grep -q $project_name || docker network create --driver bridge $project_name
|
||||
|
||||
# Start postgres container
|
||||
# Firstly create pg volume if it does not exist
|
||||
docker volume ls | grep -q $project_name-pgdata || docker volume create $project_name-pgdata
|
||||
|
||||
# Then run the pg container
|
||||
docker run \
|
||||
-d \
|
||||
--restart unless-stopped \
|
||||
--env-file $env_file \
|
||||
--network $project_name \
|
||||
--name $project_name-database \
|
||||
--net-alias database \
|
||||
--volume $project_name-pgdata:/var/lib/postgresql/data/ \
|
||||
postgres
|
||||
|
||||
# Start backend container
|
||||
# Check if running; if so, stop, and rename
|
||||
docker run \
|
||||
-d \
|
||||
--restart unless-stopped \
|
||||
--env-file $env_file \
|
||||
--network $project_name \
|
||||
--name $project_name-server \
|
||||
--net-alias server \
|
||||
chessh/server
|
||||
|
||||
# Start frontend container
|
||||
# Check if running; if so, stop, and rename
|
||||
docker run \
|
||||
-d \
|
||||
--restart unless-stopped \
|
||||
--env-file $env_file \
|
||||
--network $project_name \
|
||||
--name $project_name-frontend \
|
||||
--publish "${host}:${port}:80/tcp" \
|
||||
--net-alias frontend \
|
||||
chessh/frontend
|
1
front/.dockerignore
Normal file
1
front/.dockerignore
Normal file
@ -0,0 +1 @@
|
||||
node_modules
|
28
front/Dockerfile
Normal file
28
front/Dockerfile
Normal file
@ -0,0 +1,28 @@
|
||||
# Builder
|
||||
FROM node:16-alpine as build
|
||||
|
||||
WORKDIR /usr/app
|
||||
|
||||
COPY package-lock.json package.json ./
|
||||
RUN npm ci
|
||||
|
||||
COPY . /usr/app
|
||||
|
||||
ARG REACT_APP_GITHUB_OAUTH
|
||||
ARG REACT_APP_SSH_SERVER
|
||||
ARG REACT_APP_SSH_PORT
|
||||
ENV REACT_APP_GITHUB_OAUTH $REACT_APP_GITHUB_OAUTH
|
||||
ENV REACT_APP_SSH_SERVER $REACT_APP_SSH_SERVER
|
||||
ENV REACT_APP_SSH_PORT $REACT_APP_SSH_PORT
|
||||
RUN npm run build
|
||||
|
||||
# Runner
|
||||
FROM nginx:alpine
|
||||
|
||||
EXPOSE 80
|
||||
COPY nginx.conf /etc/nginx/conf.d/
|
||||
COPY --from=build /usr/app/build /usr/share/nginx/html
|
||||
|
||||
RUN chown -R nginx:nginx /usr/share/nginx/html
|
||||
|
||||
ENTRYPOINT ["nginx", "-g", "daemon off;"]
|
13
front/nginx.conf
Normal file
13
front/nginx.conf
Normal file
@ -0,0 +1,13 @@
|
||||
server {
|
||||
listen 80;
|
||||
|
||||
location / {
|
||||
root /usr/share/nginx/html/;
|
||||
index index.html index.htm index.nginx-debian.html;
|
||||
try_files $uri $uri/ /index.html;
|
||||
}
|
||||
|
||||
location /api {
|
||||
proxy_pass http://server:8080;
|
||||
}
|
||||
}
|
@ -13,8 +13,10 @@ const useStorage = (storage, keyPrefix) => (storageKey, fallbackState) => {
|
||||
|
||||
if (storedString !== null) parsedObject = JSON.parse(storedString);
|
||||
|
||||
// eslint-disable-next-line react-hooks/rules-of-hooks
|
||||
const [value, setValue] = useState(parsedObject ?? fallbackState);
|
||||
|
||||
// eslint-disable-next-line react-hooks/rules-of-hooks
|
||||
useEffect(() => {
|
||||
storage.setItem(keyPrefix + storageKey, JSON.stringify(value));
|
||||
}, [value, storageKey]);
|
||||
@ -22,6 +24,7 @@ const useStorage = (storage, keyPrefix) => (storageKey, fallbackState) => {
|
||||
return [value, setValue];
|
||||
};
|
||||
|
||||
// eslint-disable-next-line react-hooks/rules-of-hooks
|
||||
export const useLocalStorage = useStorage(
|
||||
window.localStorage,
|
||||
STORAGE_KEYS_PREFIX
|
||||
|
@ -174,7 +174,8 @@ textarea {
|
||||
border-radius: 4px;
|
||||
border: 1px solid var(--primary-text-color);
|
||||
}
|
||||
input,textarea: focus {
|
||||
input:focus,
|
||||
textarea:focus {
|
||||
border: 1px solid var(--gold-color);
|
||||
}
|
||||
|
||||
|
19
lib/chessh/release.ex
Normal file
19
lib/chessh/release.ex
Normal file
@ -0,0 +1,19 @@
|
||||
defmodule Chessh.Release do
|
||||
@app :chessh
|
||||
|
||||
def migrate do
|
||||
for repo <- repos() do
|
||||
{:ok, _, _} = Ecto.Migrator.with_repo(repo, &Ecto.Migrator.run(&1, :up, all: true))
|
||||
end
|
||||
end
|
||||
|
||||
def rollback(repo, version) do
|
||||
{:ok, _, _} = Ecto.Migrator.with_repo(repo, &Ecto.Migrator.run(&1, :down, to: version))
|
||||
end
|
||||
|
||||
defp repos do
|
||||
Application.load(@app)
|
||||
Application.fetch_env!(@app, :ecto_repos)
|
||||
end
|
||||
end
|
||||
|
@ -1,5 +1,7 @@
|
||||
#!/bin/sh
|
||||
|
||||
if [ ! -d "keys" ]
|
||||
then
|
||||
mkdir keys
|
||||
chmod 700 keys
|
||||
cd keys
|
||||
@ -7,3 +9,4 @@ cd keys
|
||||
ssh-keygen -N "" -b 256 -t ecdsa -f ssh_host_ecdsa_key
|
||||
ssh-keygen -N "" -b 1024 -t dsa -f ssh_host_dsa_key
|
||||
ssh-keygen -N "" -b 2048 -t rsa -f ssh_host_rsa_key
|
||||
fi
|
||||
|
Loading…
Reference in New Issue
Block a user