Skip to content

Commit c3d9cf5

Browse files
committed
create docker image and document instructions
1 parent 3596625 commit c3d9cf5

File tree

10 files changed

+131
-59
lines changed

10 files changed

+131
-59
lines changed

.dockerignore

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,2 @@
1+
.idea
2+
node_modules

.env

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
REACT_APP_ENV={}

.gitignore

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,8 @@
11
# See https://help.github.com/articles/ignoring-files/ for more about ignoring files.
22

3+
# IDE
4+
*.idea
5+
36
# dependencies
47
/node_modules
58
/.pnp

Dockerfile

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
FROM node:11.6.0-alpine as base
2+
3+
USER node
4+
WORKDIR /home/node
5+
6+
COPY package.json yarn.lock ./
7+
RUN yarn
8+
9+
COPY public public
10+
COPY src src
11+
RUN yarn build
12+
13+
FROM nginx:1.15.2-alpine as release
14+
RUN apk add --no-cache jq
15+
16+
COPY --from=base /home/node/build /var/www
17+
COPY nginx.conf /etc/nginx/nginx.conf
18+
EXPOSE 80
19+
20+
COPY docker-entrypoint.sh /
21+
ENTRYPOINT ["/docker-entrypoint.sh"]
22+
CMD ["nginx", "-g", "daemon off;"]

README.md

Lines changed: 27 additions & 54 deletions
Original file line numberDiff line numberDiff line change
@@ -1,68 +1,41 @@
1-
This project was bootstrapped with [Create React App](https://github.com/facebook/create-react-app).
1+
# create-react-app-docker-environment-variables
22

3-
## Available Scripts
3+
`create-react-app` has a whole [section](https://facebook.github.io/create-react-app/docs/adding-custom-environment-variables) about how to work with environment variables. The used approach is to replace the environment variables at build time. So the generated assets (.js, .html) already have the variables replaced.
44

5-
In the project directory, you can run:
5+
The problem with this approach is that you need to rebuild the whole application every time you want to assign a different value to a variable.
66

7-
### `npm start`
7+
This is an example of how to use environment variables at **runtime** assuming that you are using docker to deploy your application. The main benefit of this approach is that you are going to be able to use the same image in multiple environments.
88

9-
Runs the app in the development mode.<br>
10-
Open [http://localhost:3000](http://localhost:3000) to view it in the browser.
9+
### Try it
1110

12-
The page will reload if you make edits.<br>
13-
You will also see any lint errors in the console.
11+
Build the docker image
1412

15-
### `npm test`
13+
```
14+
docker build --tag cra-docker-env .
15+
```
1616

17-
Launches the test runner in the interactive watch mode.<br>
18-
See the section about [running tests](https://facebook.github.io/create-react-app/docs/running-tests) for more information.
17+
Run the image passing some environment variables prefixed with `REACT_APP_`
1918

20-
### `npm run build`
19+
```
20+
docker run \
21+
-e REACT_APP_API='http://api.com' \
22+
-e REACT_APP_TOKEN='123' \
23+
-p8080:80 \
24+
cra-docker-env
25+
```
2126

22-
Builds the app for production to the `build` folder.<br>
23-
It correctly bundles React in production mode and optimizes the build for the best performance.
27+
Every environment variable prefixed with `REACT_APP_` will be available in `window.ENV`.
2428

25-
The build is minified and the filenames include the hashes.<br>
26-
Your app is ready to be deployed!
29+
Open `http://localhost:8000`. You will see the list of you environment variables.
2730

28-
See the section about [deployment](https://facebook.github.io/create-react-app/docs/deployment) for more information.
31+
### How does this works?
2932

30-
### `npm run eject`
33+
The `index.html` contains the code the initialize the `window.ENV` variable
3134

32-
**Note: this is a one-way operation. Once you `eject`, you can’t go back!**
35+
```html
36+
<script>
37+
var ENV = %REACT_APP_ENV%;
38+
</script>
39+
```
3340

34-
If you aren’t satisfied with the build tool and configuration choices, you can `eject` at any time. This command will remove the single build dependency from your project.
35-
36-
Instead, it will copy all the configuration files and the transitive dependencies (Webpack, Babel, ESLint, etc) right into your project so you have full control over them. All of the commands except `eject` will still work, but they will point to the copied scripts so you can tweak them. At this point you’re on your own.
37-
38-
You don’t have to ever use `eject`. The curated feature set is suitable for small and middle deployments, and you shouldn’t feel obligated to use this feature. However we understand that this tool wouldn’t be useful if you couldn’t customize it when you are ready for it.
39-
40-
## Learn More
41-
42-
You can learn more in the [Create React App documentation](https://facebook.github.io/create-react-app/docs/getting-started).
43-
44-
To learn React, check out the [React documentation](https://reactjs.org/).
45-
46-
### Code Splitting
47-
48-
This section has moved here: https://facebook.github.io/create-react-app/docs/code-splitting
49-
50-
### Analyzing the Bundle Size
51-
52-
This section has moved here: https://facebook.github.io/create-react-app/docs/analyzing-the-bundle-size
53-
54-
### Making a Progressive Web App
55-
56-
This section has moved here: https://facebook.github.io/create-react-app/docs/making-a-progressive-web-app
57-
58-
### Advanced Configuration
59-
60-
This section has moved here: https://facebook.github.io/create-react-app/docs/advanced-configuration
61-
62-
### Deployment
63-
64-
This section has moved here: https://facebook.github.io/create-react-app/docs/deployment
65-
66-
### `npm run build` fails to minify
67-
68-
This section has moved here: https://facebook.github.io/create-react-app/docs/troubleshooting#npm-run-build-fails-to-minify
41+
The `%REACT_APP_ENV%` will be replaced at runtime by the `docker-entrypoint.sh` file.

docker-entrypoint.sh

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
#!/usr/bin/env sh
2+
set -eu
3+
4+
ENV_JSON=$(env | grep '^REACT_APP_*' | jq -c '. | split("\n") | map(select(. != "")) | map(split("=") | { (.[0]) : .[1] }) | reduce .[] as $item ({}; . * $item)' -R -s)
5+
ESCAPED_ENV_JSON=$(echo $ENV_JSON | sed 's/\"/\\\"/g' | sed 's/\//\\\//g' | tr -d '\n' | tr -d '[[:blank:]]')
6+
sed -i 's/%REACT_APP_ENV%/'"$ESCAPED_ENV_JSON"'/g' /var/www/index.html
7+
8+
exec "$@"

nginx.conf

Lines changed: 58 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,58 @@
1+
# auto detects a good number of processes to run
2+
worker_processes auto;
3+
4+
#Provides the configuration file context in which the directives that affect connection processing are specified.
5+
events {
6+
# Sets the maximum number of simultaneous connections that can be opened by a worker process.
7+
worker_connections 8000;
8+
# Tells the worker to accept multiple connections at a time
9+
multi_accept on;
10+
}
11+
12+
13+
http {
14+
# what times to include
15+
include /etc/nginx/mime.types;
16+
# what is the default one
17+
default_type application/octet-stream;
18+
19+
# Sets the path, format, and configuration for a buffered log write
20+
log_format compression '$remote_addr - $remote_user [$time_local] '
21+
'"$request" $status $upstream_addr '
22+
'"$http_referer" "$http_user_agent"';
23+
24+
server {
25+
# listen on port 80
26+
listen 80;
27+
# save logs here
28+
access_log /var/log/nginx/access.log compression;
29+
30+
# where the root here
31+
root /var/www;
32+
# what file to server as index
33+
index index.html index.htm;
34+
35+
location / {
36+
# First attempt to serve request as file, then
37+
# as directory, then fall back to redirecting to index.html
38+
try_files $uri $uri/ /index.html;
39+
add_header Cache-Control "no-cache, no-store, must-revalidate no";
40+
etag off;
41+
}
42+
43+
# Media: images, icons, video, audio, HTC
44+
location ~* \.(?:jpg|jpeg|gif|png|ico|cur|gz|svg|svgz|mp4|ogg|ogv|webm|htc)$ {
45+
expires 1M;
46+
access_log off;
47+
add_header Cache-Control "public";
48+
}
49+
50+
# Javascript and CSS files
51+
location ~* \.(?:css|js)$ {
52+
try_files $uri =404;
53+
expires 1y;
54+
access_log off;
55+
add_header Cache-Control "public";
56+
}
57+
}
58+
}

public/index.html

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,11 @@
2222
work correctly both with client-side routing and a non-root public URL.
2323
Learn how to configure a non-root public URL by running `npm run build`.
2424
-->
25+
26+
<script>
27+
var ENV = %REACT_APP_ENV%;
28+
</script>
29+
2530
<title>React App</title>
2631
</head>
2732
<body>

src/App.js

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -8,9 +8,9 @@ class App extends Component {
88
<div className="App">
99
<header className="App-header">
1010
<img src={logo} className="App-logo" alt="logo" />
11-
<p>
12-
Edit <code>src/App.js</code> and save to reload.
13-
</p>
11+
<pre>
12+
{JSON.stringify(window.ENV, null, 2)}
13+
</pre>
1414
<a
1515
className="App-link"
1616
href="https://reactjs.org"

yarn.lock

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -7901,7 +7901,7 @@ react-dev-utils@^7.0.1:
79017901
strip-ansi "4.0.0"
79027902
text-table "0.2.0"
79037903

7904-
7904+
react-dom@^16.7.0:
79057905
version "16.7.0"
79067906
resolved "https://registry.yarnpkg.com/react-dom/-/react-dom-16.7.0.tgz#a17b2a7ca89ee7390bc1ed5eb81783c7461748b8"
79077907
integrity sha512-D0Ufv1ExCAmF38P2Uh1lwpminZFRXEINJe53zRAbm4KPwSyd6DY/uDoS0Blj9jvPpn1+wivKpZYc8aAAN/nAkg==
@@ -7971,7 +7971,7 @@ [email protected]:
79717971
optionalDependencies:
79727972
fsevents "1.2.4"
79737973

7974-
7974+
react@^16.7.0:
79757975
version "16.7.0"
79767976
resolved "https://registry.yarnpkg.com/react/-/react-16.7.0.tgz#b674ec396b0a5715873b350446f7ea0802ab6381"
79777977
integrity sha512-StCz3QY8lxTb5cl2HJxjwLFOXPIFQp+p+hxQfc8WE0QiLfCtIlKj8/+5tjjKm8uSTlAW+fCPaavGFS06V9Ar3A==

0 commit comments

Comments
 (0)