Compare commits

...

183 Commits

Author SHA1 Message Date
David Bomba
d75b8e3616 Merge pull request #789 from benbrummer/debian
Workaround: Disable SSL for mariadb-client for compatibility with MySQL
2025-09-02 06:22:16 +10:00
benbrummer
085df042c1 Workaround: Disable SSL for mariadb-client for compatibility with MySQL 2025-09-01 21:36:45 +02:00
David Bomba
b67f49b9ba Merge pull request #784 from benbrummer/debian
HEALTHCHECK, mariadb-client and PHP 8.4
2025-08-29 22:02:27 +10:00
benbrummer
d1621f0fe5 PHP 8.4
Signed-off-by: benbrummer <info@benjamin-brummer.de>
2025-08-29 12:57:55 +02:00
benbrummer
61728ec89b Fix mariadb-client connection to mysql
Debian Trixie has a new mariadb-client, with encryption by default

Signed-off-by: benbrummer <info@benjamin-brummer.de>
2025-08-29 12:51:27 +02:00
benbrummer
1bda3e5809 Use health endpoint for HEALTHCHECK
Signed-off-by: benbrummer <info@benjamin-brummer.de>
2025-08-29 08:02:56 +02:00
David Bomba
6a16f6f4de Merge pull request #770 from TheNewSound/debian
Use default supervisord config as baseline
2025-08-12 08:34:16 +10:00
v
68cfe612ee Start supervisord using /etc/supervisor/supervisord.conf so that a socket at /var/run is created (default supervisord config). 2025-08-01 15:45:54 +02:00
David Bomba
ed9c23d9c7 Merge pull request #753 from benbrummer/debian
saxon defaults now to 12.5.0
2025-05-11 09:44:26 +10:00
benbrummer
f6fa32f606 saxon defaults now to 12.5.0
Signed-off-by: benbrummer <info@benjamin-brummer.de>
2025-05-10 10:59:13 +02:00
David Bomba
a0454d3998 Merge pull request #745 from benbrummer/debian
remove bootstrap/cache volume
2025-04-05 06:49:13 +11:00
benbrummer
04f4dbe248 remove bootstrap/cache volume
align with docker hub tutorial about laravel
* https://docs.docker.com/guides/frameworks/laravel/
* https://github.com/dockersamples/laravel-docker-examples/blob/main/compose.prod.yaml#L14

Signed-off-by: benbrummer <info@benjamin-brummer.de>
2025-04-04 11:43:33 +02:00
benbrummer
a7822987b2 Merge pull request #744 from gianluigitrontini/debian
Fixes #743: Move conditionals for chromium/google chrome before artisan optimize
2025-04-03 16:47:12 +02:00
Gianluigi Trontini
7b7f3df710 Fixes #743: Move conditionals for chromium/google chrome at the top of the file 2025-04-03 15:37:52 +02:00
benbrummer
a9b3a8a8a4 Merge pull request #737 from RichyHBM/patch-1
Create required dirs if missing
2025-03-29 09:55:16 +01:00
Richy HBM
a53b702c45 Create required dirs if missing
Signed-off-by: Richy HBM <RichyHBM@users.noreply.github.com>
2025-03-27 16:04:35 +00:00
David Bomba
39c546e270 remove default prop for snappdf pay 2025-03-25 12:03:04 +11:00
David Bomba
9c0e00edb3 Add conditionals for chromium/google chrome 2025-03-25 12:02:47 +11:00
David Bomba
1f28106e43 Merge pull request #731 from benbrummer/debian
use github latest url, tar.gz without top level repository
2025-03-19 10:05:15 +11:00
David Bomba
c4513a868a Merge pull request #733 from fabiomanz/patch-1
Upgrade from old docker-compose syntax to v2 docker compose syntax
2025-03-18 02:54:22 +11:00
Fabio
856d47217e Upgrade from old docker-compose syntax to v2 docker compose syntax
Signed-off-by: Fabio <fabio.manz@t-online.de>
2025-03-17 13:57:36 +01:00
Benjamin Brummer
be0ec204d4 use github latest url, tar.gz without top level repository 2025-03-15 06:35:12 +00:00
David Bomba
9d99120693 Merge pull request #713 from turbo124/debian
Fixes for publish image regression - force 22.04
2025-01-24 16:12:59 +11:00
David Bomba
a5204ccb7d Fixes for publish image regression - force 22.04 2025-01-24 16:12:25 +11:00
David Bomba
995d70ab60 Merge pull request #706 from turbo124/debian
Fixes for php extension installer
2025-01-24 12:59:21 +11:00
David Bomba
11855e0701 Fixes for php extension installer 2025-01-24 12:58:04 +11:00
David Bomba
42816b6282 Require mbstring 2025-01-24 09:23:10 +11:00
David Bomba
2ad607fa2d Create auto-close-issues.yml
Signed-off-by: David Bomba <turbo124@gmail.com>
2025-01-21 13:47:56 +11:00
David Bomba
2c25caf627 Merge pull request #694 from benbrummer/debian
Fix for reap logging
2025-01-15 08:56:09 +11:00
benbrummer
a2b64d2060 Merge branch 'invoiceninja:debian' into debian 2025-01-14 22:32:43 +01:00
Benjamin Brummer
b58d4e1259 fix for reaps 2025-01-14 21:31:50 +00:00
Benjamin Brummer
a7683ada33 log to stdout 2025-01-14 21:19:38 +00:00
Benjamin Brummer
3e8a6c72a7 healthcheck for php-fpm master process 2025-01-14 21:19:25 +00:00
David Bomba
3b0f7c463a Merge pull request #691 from benbrummer/debian
php optimization
2025-01-15 08:18:25 +11:00
Benjamin Brummer
c00d44380c log worker to stdout/stderr 2025-01-13 16:34:49 +00:00
Benjamin Brummer
cb4120fc54 Multistage, single init.sh 2025-01-13 16:31:39 +00:00
Benjamin Brummer
f2c5a1f842 composer is not needed, permissions are already correct in the image 2025-01-13 13:11:50 +00:00
Benjamin Brummer
029bc57fac download invoiceninja.tar.gz 2025-01-13 13:09:33 +00:00
Benjamin Brummer
d60bf39950 set correct file-extension 2025-01-13 12:52:28 +00:00
Benjamin Brummer
31eb278f0d prefer files from image 2025-01-13 12:30:06 +00:00
Benjamin Brummer
44b460bf13 php optimization opcache and realpath 2025-01-13 12:22:01 +00:00
Benjamin Brummer
7bae300fd2 disable preload for artisan tinker 2025-01-13 12:20:03 +00:00
David Bomba
3394694ffc Merge pull request #676 from benbrummer/debian
arm64 image with chromium
2024-12-24 18:28:05 +11:00
Benjamin Brummer
99f280319c saxon is available for arm64 and amd64 2024-12-21 20:38:44 +01:00
Benjamin Brummer
470a3d036d EXPOSE is already inherited from base image 2024-12-21 20:37:47 +01:00
Benjamin Brummer
514ebb74c6 No need to have arm64 and amd64 for php extensions 2024-12-21 20:37:16 +01:00
Benjamin Brummer
dc3b87140f Install chromium for arm64 2024-12-21 20:36:20 +01:00
Benjamin Brummer
c0afd971e1 mariadb is the default on debian 2024-12-21 20:32:22 +01:00
Benjamin Brummer
677cc44a15 remove gosu 2024-12-21 20:31:42 +01:00
David Bomba
91c7b1ea2a Merge pull request #673 from turbo124/debian
Updates for github actions
2024-12-11 09:55:32 +11:00
David Bomba
a508ccc41e Updates for github actions 2024-12-11 09:53:54 +11:00
David Bomba
d42f66617c Merge pull request #672 from brdns/debian
Remove nginx `[warn]` log when uploading
2024-12-10 06:10:58 +11:00
brdns
8746015041 Removes nginx logs when uploading: [warn] a client request body is buffered to a temporary file
[warn] a client request body is buffered to a temporary file
Was already fixed with commit bfc61fb64e
Then got reverted by commit 66408fccb2
2024-12-09 18:02:44 +01:00
David Bomba
53c38b65f9 Merge pull request #664 from benbrummer/debian-dev
dockerfile cleanup, apt reduction, php module configuration, allow to run custom CMD
2024-12-06 08:49:18 +11:00
Benjamin Brummer
473e38259f Merge remote-tracking branch 'origin/debian' into debian-dev
CMD was not properly handled
2024-12-05 13:57:10 +01:00
Benjamin Brummer
d538666600 final fix for if statement 2024-12-05 13:47:42 +01:00
Benjamin Brummer
0ace427585 - supervisord.conf defines nodaemon already
- Fix if statement
2024-12-05 13:35:32 +01:00
benbrummer
8c1357fc4c Merge branch 'debian' into debian-dev
Signed-off-by: benbrummer <info@benjamin-brummer.de>
2024-12-05 10:52:43 +01:00
Benjamin Brummer
806a340a00 - make it possible to run a custom CMD
- rename volume according to their origin
- Add arguments for required, suggested and extra php-modules
2024-12-05 10:34:45 +01:00
Benjamin Brummer
d437dab72c remove upload folder 2024-12-04 10:24:10 +01:00
Benjamin Brummer
d64ed83abf temporarly install gpg 2024-12-03 23:57:20 +01:00
Benjamin Brummer
337f38e0dc remove default values 2024-12-03 10:53:13 +01:00
David Bomba
5d5c036175 Merge pull request #667 from turbo124/debian
Patches for copying files
2024-12-03 15:01:54 +11:00
David Bomba
d5ed1935f7 set port 80 2024-12-03 15:01:08 +11:00
David Bomba
5e40e34943 run local init.sh file 2024-12-03 14:59:41 +11:00
David Bomba
c4e1d0e3a5 Updates for copy files 2024-12-03 14:49:58 +11:00
David Bomba
84dcb8caab Merge pull request #665 from turbo124/debian
Update dockerfile
2024-12-03 12:40:39 +11:00
Benjamin Brummer
733e72d5dd curl is already installed 2024-12-02 12:56:24 +01:00
Benjamin Brummer
7eaf6968d2 - fonts-noto-cjk-extra depends on fonts-noto-cjk
- *-dev packages are not required
- fonts depends on libpng16-16 (no dev)
2024-12-02 12:30:17 +01:00
Benjamin Brummer
66408fccb2 align php settings with recommendations opcache/jit from php.net (aligned for php 8.3 and 8.4), increased buffernumber to allow parallel requests without writing to file 2024-12-02 11:53:27 +01:00
Benjamin Brummer
79647d4f8c Fix do not delete public folder on container restart 2024-12-02 11:29:40 +01:00
Benjamin Brummer
067b5eb194 remove value, which matches default 2024-12-01 14:53:48 +01:00
Benjamin Brummer
eed358c32b extended gzip configuration 2024-12-01 14:38:48 +01:00
Benjamin Brummer
71909c73e0 configure chrome during installation 2024-12-01 13:46:58 +01:00
Benjamin Brummer
fab57c9db3 Ensure permissions on volumes are correct
mv public directory inside a single RUN to not increase the image
2024-12-01 12:11:57 +01:00
Benjamin Brummer
e7bc565745 Set correct owner, file and directory permissions. 2024-12-01 10:39:40 +01:00
Benjamin Brummer
87092bb8bd All directories apart of "uploads" exist already 2024-12-01 10:27:06 +01:00
Benjamin Brummer
5abd297c7f switch to user www-data before running tar. tar -o will set correct ownership afterwards. 2024-12-01 09:48:12 +01:00
Benjamin Brummer
8be252781f google-chrome only needs to have ownership for /var/www, which is by default owned by root 2024-12-01 09:42:29 +01:00
David Bomba
f281b33ea1 Update dockerfile 2024-11-30 22:05:28 +11:00
Benjamin Brummer
22d170a4e5 shrink directory configuration 2024-11-29 13:40:46 +01:00
Benjamin Brummer
f722c91d21 Merge chrome related configuration into one RUN 2024-11-29 11:04:11 +01:00
Benjamin Brummer
641b527702 fix if else 2024-11-29 10:48:14 +01:00
Benjamin Brummer
d139a48303 move google-chrome-stable related apt packages to arm64 2024-11-29 10:26:46 +01:00
benbrummer
a75b6f0a00 Merge branch 'invoiceninja:debian' into debian 2024-11-29 09:45:20 +01:00
David Bomba
113c700754 Merge pull request #663 from turbo124/debian
Corrective fixes for new dockerfile
2024-11-29 13:57:39 +11:00
David Bomba
b6be06c977 Corrective fixes for new dockerfile 2024-11-29 13:56:46 +11:00
benbrummer
8c53895c97 Merge branch 'invoiceninja:debian' into debian 2024-11-28 21:52:35 +01:00
Benjamin Brummer
8204465048 cleanup 2024-11-28 21:35:05 +01:00
David Bomba
baad65c737 Merge pull request #661 from benbrummer/debian
php 8.3 and apt package optimization
2024-11-29 07:17:52 +11:00
benbrummer
9fd35b874d second try for nginx
Signed-off-by: benbrummer <info@benjamin-brummer.de>
2024-11-28 16:18:05 +01:00
benbrummer
fe4993f8a3 set correct mount destination for nginx
Signed-off-by: benbrummer <info@benjamin-brummer.de>
2024-11-28 15:50:38 +01:00
Benjamin Brummer
b83fb831b9 - Use default laravel nginx and extend it with invoiceninja -specific settings
- Overwrite php.ini/php-fpm.ini settings with customized settings
2024-11-28 14:04:11 +01:00
Benjamin Brummer
687e74c983 Fix: app-1 for supervisor warning redirect_stderr 2024-11-28 10:55:29 +01:00
Benjamin Brummer
7644151370 memory limits are not aligned with php/opcache and cause error 500 2024-11-28 10:26:23 +01:00
Benjamin Brummer
c84f80f9a9 add build context to docker-compose.yml 2024-11-28 10:23:25 +01:00
Benjamin Brummer
6cfdca078f - Update to php 8.3
- Minimal system packages
  - additional packages will be handled as dependencies of google-chrome-stable (amd64
  - arm64 will still install all apt packages
- "--no-install-recommends" for apt-get
2024-11-28 10:22:05 +01:00
David Bomba
74ed1b2432 Merge pull request #659 from benbrummer/debian
install saxon 12.5.0 with install-php-extensions
2024-11-28 11:28:26 +11:00
Benjamin Brummer
b3b7f7b9f0 - install saxon with install-php-extensions
- replace deprecated apt-key
- artisan optimize will handle caches
2024-11-27 13:01:46 +01:00
David Bomba
a6d8f663ae Merge pull request #656 from benbrummer/debian
Use php.ini-production
2024-11-27 19:27:34 +11:00
David Bomba
3024f11a31 Merge pull request #658 from brdns/debian-dev
move client_max_body_size from default.conf to nginx.conf
2024-11-27 19:19:14 +11:00
Benjamin Brummer
6274c432d9 Fix access for nginx to storage/public 2024-11-26 17:16:09 +01:00
Brandon
f5afd3f527 Revert "Prevents swapping on pdf generation with Chrome"
This reverts commit 3ce5983131.
2024-11-26 16:28:04 +01:00
Brandon
3ce5983131 Prevents swapping on pdf generation with Chrome
Increase allowed memory usage of main container from 512M to 1G

This is useful particularly if the server uses a hard drive, which can drastically slow down pdf generation during swap
2024-11-26 16:22:38 +01:00
Brandon
bfc61fb64e client_max_body_size is a parameter of nginx.conf and not of default.conf (https://nginx.org/en/docs/http/ngx_http_core_module.html#client_max_body_size )
add client_body_buffer_size

prevents the following logs: [warn] a client request body is buffered to a temporary file
2024-11-26 16:07:27 +01:00
Benjamin Brummer
535d6d4c06 Refactoring docker-compose.yml 2024-11-26 12:50:59 +01:00
Benjamin Brummer
24d49a4374 refactoring dockerfile 2024-11-26 12:49:12 +01:00
Benjamin Brummer
30ad63f306 Use php.ini-production 2024-11-26 09:46:36 +01:00
David Bomba
60fd0aa79e Merge pull request #655 from turbo124/debian
Set home path for PHP when supervisor boots
2024-11-26 08:31:54 +11:00
David Bomba
d1786100ca Set home path for PHP when supervisor boots 2024-11-26 08:31:18 +11:00
David Bomba
f58ca724c9 Merge pull request #653 from turbo124/debian
Expose storage/ for nginx
2024-11-25 21:38:53 +11:00
David Bomba
53cadbf750 Expose storage/ for nginx 2024-11-25 21:38:26 +11:00
David Bomba
3fca330958 Merge pull request #651 from turbo124/debian
Updates for volume mounts
2024-11-25 11:39:13 +11:00
David Bomba
7d79b39bc2 Updates for volume mounts 2024-11-25 11:38:39 +11:00
David Bomba
aa271a1488 Merge pull request #650 from turbo124/debian
Add index.html to public/
2024-11-25 09:14:58 +11:00
David Bomba
451c1b872f Add index.html to public/ 2024-11-25 09:14:34 +11:00
David Bomba
5c74753da2 Merge pull request #648 from turbo124/debian
Updates for resolving filessystem
2024-11-24 19:58:47 +11:00
David Bomba
83f17aa669 Updates for resolving filessystem 2024-11-24 19:56:02 +11:00
David Bomba
394c4c8b5e Merge pull request #647 from turbo124/debian
Add storage link
2024-11-24 16:17:53 +11:00
David Bomba
9ed63a6762 add storage link 2024-11-24 15:48:15 +11:00
David Bomba
cb6d6d46c2 Merge pull request #646 from turbo124/debian
Adjustments for permissions
2024-11-24 11:51:49 +11:00
David Bomba
3b0e475de6 Adjustments for permissions 2024-11-24 11:50:13 +11:00
David Bomba
d5bb90fa04 Merge pull request #644 from turbo124/debian
Fixes for permissions on container init
2024-11-24 08:44:10 +11:00
David Bomba
1b62d86659 Fixes for permissions on container init 2024-11-24 08:43:50 +11:00
David Bomba
4431abcb88 Merge pull request #643 from turbo124/debian
Updates for permission handling in the container
2024-11-23 21:00:01 +11:00
David Bomba
d05e55a24e Updates for permission handling in the container 2024-11-23 20:58:56 +11:00
David Bomba
34e5043317 Merge pull request #642 from turbo124/debian
Fixes for tar command flags
2024-11-23 19:14:23 +11:00
David Bomba
6f92d1c155 Fixes for tar command flags 2024-11-23 19:13:59 +11:00
David Bomba
11330003a2 Merge pull request #641 from turbo124/debian
Updates for tar extraction
2024-11-23 19:01:32 +11:00
David Bomba
47b015af7c More explicity unpacking of .tar file 2024-11-23 19:00:45 +11:00
David Bomba
c6648a8511 Updates for tar extraction 2024-11-23 18:48:09 +11:00
David Bomba
de2036adff Merge pull request #640 from turbo124/debian
Fixes for tar command flags
2024-11-23 17:07:22 +11:00
David Bomba
ea8c5fed8e Fixes for tar command flags 2024-11-23 17:07:00 +11:00
David Bomba
c2f8cedc4a Merge pull request #639 from turbo124/debian
Enforce latest tags during build
2024-11-23 17:02:05 +11:00
David Bomba
7ddfe8a793 Enforce latest tags 2024-11-23 17:01:28 +11:00
David Bomba
196e66e06d updates for container 2024-11-23 16:57:44 +11:00
David Bomba
7498a94bd1 Merge pull request #638 from turbo124/debian
Update readme
2024-11-23 16:33:49 +11:00
David Bomba
8289c6c65e Update readme 2024-11-23 16:23:14 +11:00
David Bomba
b75ac4fd87 Update directory 2024-11-23 16:09:11 +11:00
David Bomba
94d3f6212e Merge pull request #636 from turbo124/debian
Update github action versions
2024-11-23 16:07:46 +11:00
David Bomba
a940bf2ed2 Update github action versions 2024-11-23 16:07:18 +11:00
David Bomba
76ca42bddb Merge pull request #635 from turbo124/debian
Finalize documentation
2024-11-23 14:26:12 +11:00
David Bomba
84194970b3 Merge branch 'debian' into debian
Signed-off-by: David Bomba <turbo124@gmail.com>
2024-11-23 14:26:06 +11:00
David Bomba
919e15fb40 Readme formatting 2024-11-23 14:24:50 +11:00
David Bomba
2b8bb21d04 Readme formatting 2024-11-23 14:24:14 +11:00
David Bomba
8ff82909c8 Updates for defaults 2024-11-23 14:20:08 +11:00
David Bomba
7ce743bd91 Shield Badges 2024-11-23 14:19:33 +11:00
David Bomba
ffc777d5f1 Shield Badges 2024-11-23 14:17:26 +11:00
David Bomba
1446bfabfc Shield Badges 2024-11-23 14:14:25 +11:00
David Bomba
5ae3240677 Update README.md
Signed-off-by: David Bomba <turbo124@gmail.com>
2024-11-23 14:12:02 +11:00
David Bomba
1fc60549c2 Update README.md
Signed-off-by: David Bomba <turbo124@gmail.com>
2024-11-23 14:10:04 +11:00
David Bomba
a5ad84f22b Merge pull request #634 from turbo124/debian
conditionally build saxon on amd64 only.
2024-11-23 09:44:06 +11:00
David Bomba
e5847a6ff1 Conditionally build saxon on amd64 2024-11-23 09:43:28 +11:00
David Bomba
1c1bc350dc Rename gh action 2024-11-23 08:58:24 +11:00
David Bomba
e83372d437 Merge pull request #633 from turbo124/debian
fixes for amd64 builds
2024-11-23 08:52:09 +11:00
David Bomba
22b2f5416a fixes for amd64 builds 2024-11-23 08:51:42 +11:00
David Bomba
dbb671eeab Merge pull request #632 from turbo124/debian
Fixes for build stages on different architectures.
2024-11-23 08:44:00 +11:00
David Bomba
baf7b2bff7 Conditional builds for google chrome 2024-11-23 08:43:25 +11:00
David Bomba
db7c7de624 Fixes for trailing backslashes 2024-11-23 08:41:54 +11:00
David Bomba
e8b62de217 Merge pull request #631 from turbo124/debian
Remove alpine build from Debian branch
2024-11-23 08:32:54 +11:00
David Bomba
065a7f94e6 Remove alpine build from Debian branch 2024-11-23 08:32:31 +11:00
David Bomba
47c2ee05b9 Merge pull request #630 from turbo124/debian
Fixes for publish release
2024-11-23 08:30:56 +11:00
David Bomba
adeba71a55 Fixes for publish release 2024-11-23 08:30:31 +11:00
David Bomba
65d5904f35 Merge pull request #629 from turbo124/debian
Fixes for publish release
2024-11-23 08:27:31 +11:00
David Bomba
00a346853c Fixes for publish release 2024-11-23 08:27:03 +11:00
David Bomba
ee74e6170c Merge pull request #628 from turbo124/debian
Debian
2024-11-22 19:05:41 +11:00
David Bomba
857eaf86bb Cleanup build iamge 2024-11-22 17:01:40 +11:00
David Bomba
b8dbe76900 Fixes for incorrect build path 2024-11-22 16:43:46 +11:00
David Bomba
bf07c49d31 Fixes for incorrect build path 2024-11-22 16:42:06 +11:00
David Bomba
397d19c06d Fixes for incorrect build path 2024-11-22 16:40:01 +11:00
David Bomba
4d16fb2efc Fixes for incorrect build path 2024-11-22 16:37:41 +11:00
David Bomba
01b30fdb1a Fixes for incorrect build path 2024-11-22 16:35:04 +11:00
David Bomba
814b8bd283 Fixes for incorrect build path 2024-11-22 16:32:19 +11:00
David Bomba
201a229ec7 Remove redundant gh builds 2024-11-22 16:29:10 +11:00
David Bomba
1a144db29a remove duplicate font-liberation 2024-11-22 16:26:32 +11:00
David Bomba
655e7b61ea change image name 2024-11-22 16:09:15 +11:00
David Bomba
113ed64aee Change installation of google-chrome in gh actions 2024-11-22 16:08:26 +11:00
David Bomba
6430ddcb92 Update readme 2024-11-22 16:03:08 +11:00
David Bomba
7a9d5f7187 Add build steps 2024-11-22 15:42:59 +11:00
David Bomba
eeaaf95d47 Complete build pipeline to include debian image 2024-11-22 15:37:45 +11:00
David Bomba
b338ef90cb Enable opcache 2024-11-22 14:01:12 +11:00
David Bomba
1f778c0945 updates for debian 2024-11-22 13:48:50 +11:00
David Bomba
b65257db66 New debian pipe 2024-11-22 10:45:30 +11:00
59 changed files with 528 additions and 3341 deletions

21
.github/workflows/auto-close-issues.yml vendored Normal file
View File

@@ -0,0 +1,21 @@
name: Close stale issues after 5 days
on:
schedule:
# Run this workflow every day at midnight
- cron: '0 0 * * *'
jobs:
close-stale-issues:
runs-on: ubuntu-latest
steps:
- name: Close stale issues
uses: actions/stale@v7
with:
repo-token: ${{ secrets.GITHUB_TOKEN }}
stale-issue-message: "This issue has been automatically closed due to inactivity for 5 days."
days-before-stale: 4 # Number of days before marking an issue as stale
days-before-close: 1 # Number of days after being marked stale before closing
stale-label: "stale" # Label to add to stale issues
exempt-issue-labels: "keep-open,triage,bug" # Prevents issues with this label from being closed
only-issues: true # Only affects issues, not pull requests

View File

@@ -0,0 +1,38 @@
name: Build Debian Container Image
on:
pull_request:
paths:
- "debian/**"
push:
paths:
- "debian/**"
branches:
- master
jobs:
docker:
runs-on: ubuntu-22.04
steps:
- name: Checkout
uses: actions/checkout@v4
- name: Set up QEMU
uses: docker/setup-qemu-action@v3
with:
platforms: all
- name: Set up Docker Buildx
id: buildx
uses: docker/setup-buildx-action@v3
- name: Build
id: docker_build
uses: docker/build-push-action@v5
with:
context: debian
file: debian/Dockerfile
load: true
tags: invoiceninja/invoiceninja-debian:test
cache-from: type=gha
cache-to: type=gha,mode=max

View File

@@ -1,57 +0,0 @@
name: Build Container Image v4
# When its time to do a release do a full cross platform build for all supported
# architectures and push all of them to Docker Hub.
# Only trigger on semver shaped tags.
# Ref: https://github.com/metcalfc/docker-action-examples/blob/main/.github/workflows/release.yml
on:
pull_request:
paths:
- "alpine/4/**"
push:
paths:
- "alpine/4/**"
branches:
- master
jobs:
docker:
runs-on: ubuntu-latest
steps:
- name: Checkout
uses: actions/checkout@v2
- name: Set up QEMU
uses: docker/setup-qemu-action@v1
with:
platforms: all
- name: Set up Docker Buildx
id: buildx
uses: docker/setup-buildx-action@v1
- name: Cache Docker layers
uses: actions/cache@v2
with:
path: /tmp/.buildx-cache
key: ${{ runner.os }}-buildx-4-${{ hashFiles('alpine/5/cache_buster') }}-${{ github.sha }}
restore-keys: |
${{ runner.os }}-buildx-4-${{ hashFiles('alpine/5/cache_buster') }}-
- name: Build
id: docker_build
uses: docker/build-push-action@v2
with:
builder: ${{ steps.buildx.outputs.name }}
context: ./alpine/4/
build-args: INVOICENINJA_VERSION=4.5.42
target: prod
platforms: linux/amd64,linux/arm64
tags: invoiceninja/invoiceninja:cache
cache-from: type=local,src=/tmp/.buildx-cache
cache-to: type=local,dest=/tmp/.buildx-cache-new
- name: Move cache
run: |
rm -rf /tmp/.buildx-cache
mv /tmp/.buildx-cache-new /tmp/.buildx-cache

View File

@@ -1,57 +0,0 @@
name: Build Container Image
# When its time to do a release do a full cross platform build for all supported
# architectures and push all of them to Docker Hub.
# Only trigger on semver shaped tags.
# Ref: https://github.com/metcalfc/docker-action-examples/blob/main/.github/workflows/release.yml
on:
pull_request:
paths:
- "alpine/5/**"
push:
paths:
- "alpine/5/**"
branches:
- master
jobs:
docker:
runs-on: ubuntu-latest
steps:
- name: Checkout
uses: actions/checkout@v2
- name: Set up QEMU
uses: docker/setup-qemu-action@v1
with:
platforms: all
- name: Set up Docker Buildx
id: buildx
uses: docker/setup-buildx-action@v1
- name: Cache Docker layers
uses: actions/cache@v2
with:
path: /tmp/.buildx-cache
key: ${{ runner.os }}-buildx-5-${{ hashFiles('alpine/5/cache_buster') }}-${{ github.sha }}
restore-keys: |
${{ runner.os }}-buildx-5-${{ hashFiles('alpine/5/cache_buster') }}-
- name: Build
id: docker_build
uses: docker/build-push-action@v2
with:
builder: ${{ steps.buildx.outputs.name }}
context: ./alpine/5/
build-args: INVOICENINJA_VERSION=5-develop
target: prod
platforms: linux/amd64,linux/arm64
tags: invoiceninja/invoiceninja:cache
cache-from: type=local,src=/tmp/.buildx-cache
cache-to: type=local,dest=/tmp/.buildx-cache-new
- name: Move cache
run: |
rm -rf /tmp/.buildx-cache
mv /tmp/.buildx-cache-new /tmp/.buildx-cache

View File

@@ -1,9 +1,5 @@
name: Publish Container Image
name: Publish Debian Container Images
# When its time to do a release do a full cross platform build for all supported
# architectures and push all of them to Docker Hub.
# Only trigger on semver shaped tags.
# Ref: https://github.com/metcalfc/docker-action-examples/blob/main/.github/workflows/release.yml
on:
push:
tags-ignore:
@@ -11,15 +7,23 @@ on:
jobs:
docker:
runs-on: ubuntu-latest
runs-on: ubuntu-22.04
strategy:
matrix:
include:
- image: invoiceninja/invoiceninja-debian
context: ./debian
steps:
- name: Checkout
uses: actions/checkout@v2
uses: actions/checkout@v4 # Updated from v2
with:
fetch-depth: 0
- name: Prepare
id: prep
run: |
DOCKER_IMAGE=invoiceninja/invoiceninja
DOCKER_IMAGE=${{ matrix.image }}
VERSION=edge
if [[ $GITHUB_REF == refs/tags/* ]]; then
VERSION=${GITHUB_REF#refs/tags/}
@@ -28,55 +32,44 @@ jobs:
MAJOR="$(echo "${VERSION}" | cut -d. -f1)"
MINOR="$(echo "${VERSION}" | cut -d. -f2)"
TAGS="$TAGS,${DOCKER_IMAGE}:${MAJOR},${DOCKER_IMAGE}:${MAJOR}.${MINOR}"
if [[ $VERSION =~ ^5\.[0-9]{1,3}\.[0-9]{1,3}$ ]]; then
TAGS="$TAGS,${DOCKER_IMAGE}:latest"
fi
echo ::set-output name=tags::${TAGS}
echo ::set-output name=version::${VERSION}
echo ::set-output name=major::${MAJOR}
# Debug output
echo "Current version: ${VERSION}"
echo "Version pattern check: $([[ $VERSION =~ ^5\.[0-9]{1,3}\.[0-9]{1,3}$ ]] && echo "matches" || echo "doesn't match")"
TAGS="$TAGS,${DOCKER_IMAGE}:latest"
echo "tags=${TAGS}" >> $GITHUB_OUTPUT # Updated output syntax
echo "version=${VERSION}" >> $GITHUB_OUTPUT
echo "major=${MAJOR}" >> $GITHUB_OUTPUT
- name: Set up QEMU
uses: docker/setup-qemu-action@v1
uses: docker/setup-qemu-action@v3 # Updated from v1
with:
platforms: all
- name: Set up Docker Buildx
id: buildx
uses: docker/setup-buildx-action@v1
- name: Cache Docker layers
uses: actions/cache@v2
with:
path: /tmp/.buildx-cache
key: ${{ runner.os }}-buildx-${{ steps.prep.outputs.major }}-${{ hashFiles('alpine/${{ steps.prep.outputs.major }}/cache_buster') }}-${{ github.sha }}
restore-keys: |
${{ runner.os }}-buildx-${{ steps.prep.outputs.major }}-${{ hashFiles('alpine/${{ steps.prep.outputs.major }}/cache_buster') }}-
uses: docker/setup-buildx-action@v3 # Updated from v1
- name: Login to DockerHub
if: github.event_name != 'pull_request'
uses: docker/login-action@v1
uses: docker/login-action@v3 # Updated from v1
with:
username: ${{ secrets.DOCKERHUB_USERNAME }}
password: ${{ secrets.DOCKERHUB_PASSWORD }}
- name: Build and push
id: docker_build
uses: docker/build-push-action@v2
uses: docker/build-push-action@v5 # Updated from v2
with:
builder: ${{ steps.buildx.outputs.name }}
context: ./alpine/${{ steps.prep.outputs.major }}/
context: ${{ matrix.context }}
build-args: INVOICENINJA_VERSION=${{ steps.prep.outputs.version }}
target: prod
platforms: linux/amd64,linux/arm64
push: ${{ github.event_name != 'pull_request' }}
tags: ${{ steps.prep.outputs.tags }}
cache-from: type=local,src=/tmp/.buildx-cache
cache-to: type=local,dest=/tmp/.buildx-cache-new
- name: Move cache
run: |
rm -rf /tmp/.buildx-cache
mv /tmp/.buildx-cache-new /tmp/.buildx-cache
cache-from: type=gha # Updated cache type
cache-to: type=gha,mode=max
- name: Image digest
run: echo ${{ steps.docker_build.outputs.digest }}
run: echo ${{ steps.docker_build.outputs.digest }}

View File

@@ -12,7 +12,7 @@ jobs:
runs-on: ubuntu-latest
steps:
- name: Checkout
uses: actions/checkout@v2
uses: actions/checkout@v4
with:
fetch-depth: 0

View File

@@ -12,7 +12,7 @@ jobs:
matrix: ${{ steps.set-matrix.outputs.matrix }}
steps:
- name: Checkout
uses: actions/checkout@v2
uses: actions/checkout@v4
with:
fetch-depth: 0
@@ -55,7 +55,7 @@ jobs:
- "1.23.15"
steps:
- name: Checkout
uses: actions/checkout@v2
uses: actions/checkout@v4
with:
fetch-depth: 0

View File

@@ -1,58 +0,0 @@
ifndef TAG
$(error The TAG variable is missing.)
endif
# Docker Hub namespace
HUB_NAMESPACE="invoiceninja"
# Image name
IMAGE="invoiceninja"
# Check if v5 tag is passed, so that a v5 version should be built
IS_V5=$(shell echo ${TAG} | egrep ^5)
# Version of Invoice Ninja. As the tag can be something like 5.0.4-p1, the version is 5.0.4.
# This supports changes to the Dockerfiles with always the same Invoice Ninja version
VERSION=$(shell echo ${TAG} | sed "s/-.*//")
# Building docker images based on alpine.
# Assigned tags:
# - :4
# - :<RELEASE VERSION>
.PHONY: build-alpine
build-alpine:
ifeq ($(IS_V5),)
$(info Make: Building "$(VERSION)" tagged images from alpine.)
@docker build -t ${HUB_NAMESPACE}/${IMAGE}:${VERSION} --build-arg INVOICENINJA_VERSION=${VERSION} ./alpine/4/
# Tag as 4
@docker tag ${HUB_NAMESPACE}/${IMAGE}:alpine-${VERSION} ${HUB_NAMESPACE}/${IMAGE}:4
$(info Make: Done.)
endif
.PHONY: push-alpine
push-alpine:
ifeq ($(IS_V5),)
$(info Make: Pushing tagged images from alpine.)
@docker push ${HUB_NAMESPACE}/${IMAGE}:${VERSION}
@docker push ${HUB_NAMESPACE}/${IMAGE}:4
$(info Make: Done.)
endif
.PHONY: build-alpine-v5
build-alpine-v5:
ifneq ($(IS_V5),)
$(info Make: Building "$(VERSION)" tagged images from alpine.)
@docker build -t ${HUB_NAMESPACE}/${IMAGE}:${VERSION} --build-arg INVOICENINJA_VERSION=${VERSION} ./alpine/5/
@docker tag ${HUB_NAMESPACE}/${IMAGE}:${VERSION} ${HUB_NAMESPACE}/${IMAGE}:5
@docker tag ${HUB_NAMESPACE}/${IMAGE}:${VERSION} ${HUB_NAMESPACE}/${IMAGE}:latest
$(info Make: Done.)
endif
.PHONY: push-alpine-v5
push-alpine-v5:
ifneq ($(IS_V5),)
$(info Make: Pushing tagged images from alpine.)
@docker push ${HUB_NAMESPACE}/${IMAGE}:${VERSION}
@docker push ${HUB_NAMESPACE}/${IMAGE}:5
@docker push ${HUB_NAMESPACE}/${IMAGE}:latest
endif

120
README.md
View File

@@ -1,38 +1,28 @@
![Docker images](https://github.com/invoiceninja/dockerfiles/workflows/Docker%20images/badge.svg)
[![Docker image, latest](https://img.shields.io/docker/image-size/invoiceninja/invoiceninja/latest?label=latest)](https://hub.docker.com/r/invoiceninja/invoiceninja)
[![Docker image, alpine](https://img.shields.io/docker/image-size/invoiceninja/invoiceninja/alpine?label=alpine)](https://hub.docker.com/r/invoiceninja/invoiceninja)
[![Artifact HUB](https://img.shields.io/endpoint?url=https://artifacthub.io/badge/repository/invoiceninja)](https://artifacthub.io/packages/search?repo=invoiceninja)
[![Pusblish Image](https://github.com/invoiceninja/dockerfiles/actions/workflows/publish-image.yaml/badge.svg)](https://github.com/invoiceninja/dockerfiles/actions/workflows/publish-image.yaml) [![Cache v5 Image](https://github.com/invoiceninja/dockerfiles/actions/workflows/build-image-v5.yaml/badge.svg)](https://github.com/invoiceninja/dockerfiles/actions/workflows/build-image-v5.yaml)
[![Docker Image Size](https://img.shields.io/docker/image-size/invoiceninja/invoiceninja-debian?label=debian)](https://hub.docker.com/r/invoiceninja/invoiceninja-debian)
[![Docker Pulls](https://img.shields.io/docker/pulls/invoiceninja/invoiceninja-debian)](https://hub.docker.com/r/invoiceninja/invoiceninja-debian)
[![Publish Status](https://github.com/invoiceninja/dockerfiles/actions/workflows/publish-image.yaml/badge.svg)](https://github.com/invoiceninja/dockerfiles/actions/workflows/publish-image.yaml)
[![Build Status](https://github.com/invoiceninja/dockerfiles/actions/workflows/build-image-v5.yaml/badge.svg)](https://github.com/invoiceninja/dockerfiles/actions/workflows/build-image-v5.yaml)
# Docker for [Invoice Ninja](https://www.invoiceninja.com/)
# Debian Docker for [Invoice Ninja](https://www.invoiceninja.com/)
:crown: **Features**
:lock: Automatic HTTPS (:heart: [Caddy](https://caddyserver.com/))
:fire: NGINX webserver support [NGINX](https://nginx.org/)
:hammer: Fully production-ready through Helm Chart
:pencil: Adjustable to your needs via environment variable
NGINX webserver support [NGINX](https://nginx.org/)
Built-in Chrome for PDF generation and other features
Saxon XLST 2 engine
OPcache
Multi language support
## Get some Kubernetes + Helm with that!
## Get started with Docker Compose
Introducing our very own [Helm Chart](https://github.com/invoiceninja/dockerfiles/tree/master/charts/invoiceninja) that helps you launch a simple standalone app to a production-ready, highly available Invoice Ninja setup. All you need to do is initialise Kubernetes (available with Docker Desktop), install [Helm](https://helm.sh/docs/intro/install/), and spin up Invoice Ninja using the steps provided [here](https://github.com/invoiceninja/dockerfiles/tree/master/charts/invoiceninja#installing-the-chart).
Other resources:
[Helm Chart](https://github.com/Saddamus/invoiceninja-helm) by @Saddamus
[K8s Manifest](https://github.com/invoiceninja/dockerfiles/issues/94) by @spacepluk
[You Tube installation video by DBTech](https://www.youtube.com/watch?v=xo6a3KtLC2g&ab_channel=DBTech)
## Alternatively get started with Docker Compose
The dockerfile has been revamped to make it easier to get started, by default the base image selected is 5 which will pull in the latest v5 stable image.
This Debian-based image includes Chrome for enhanced PDF generation and other features. To get started:
```bash
git clone https://github.com/invoiceninja/dockerfiles.git
cd dockerfiles
git clone https://github.com/invoiceninja/dockerfiles.git -b debian
cd dockerfiles/debian
```
Instead of defining our environment variables inside our docker-compose.yml file we now define this in the `env` file, open this file up and insert your `APP_URL`, `APP_KEY` and update the rest of the variables as required.
Instead of defining our environment variables inside our docker-compose.yml file we now define this in the `.env` file, open this file up and insert your `APP_URL`, `APP_KEY` and update the rest of the variables as required.
```
APP_URL=http://in.localhost:8003/
@@ -43,65 +33,63 @@ IN_USER_EMAIL=
IN_PASSWORD=
```
If `IN_USER_EMAIL` and `IN_PASSWORD` is not set the default user email and password is "admin@example.com" and "changeme!" respectively. You will use this for the initial login, thereafter, you can delete this two environment variables.
## Initial account setup
The `APP_KEY` can be generated by running
### Primary account setup
Prior to starting the container for the first time, open the .env file and update the IN_USER_EMAIL and IN_PASSWORD variables with your primary account.
This will take care of the initial account setup. You can later remove these .env variables.
> ⚠️ **Warning**
> If `IN_USER_EMAIL` and `IN_PASSWORD` are not set the default user email and password is "admin@example.com" and "changeme!" respectively.
After the container has completed the first startup you can delete these two environment variables.
### Generate a APP_KEY
The `APP_KEY` can be generated by running:
```bash
docker run --rm -it invoiceninja/invoiceninja php artisan key:generate --show
# If you haven't started the containers yet:
docker run --rm -it invoiceninja/invoiceninja-debian php artisan key:generate --show
# Or if your containers are already running:
docker compose exec app php artisan key:generate --show
```
Copy the entire string and insert in the env file at `APP_KEY=base64....`
Copy the entire string and insert in the .env file at `APP_KEY=base64....`
To ensure folder permissions are correct when the container comes up for the first time it is important that you set the correct folder permissions on the `docker` folder.
**Note: For PDF generation using localhost, your domain name MUST end in .test for PDFs to generate correctly due to Chrome's DNS resolver.
From the terminal run
Start the container with:
```bash
chmod 755 docker/app/public
sudo chown -R 1500:1500 docker/app
docker compose up -d
```
### Note for people running the container locally on their PC ###
**Note: When performing the setup, the Database host is ```mysql```
If you are running the container locally, then the container will need to resolve the host, to support this you will want to insert your LAN IP address and the host name in the hosts file located in ```config/hosts```
### Updating the Image
For example, lets say your APP_URL is ```http://in5.test:8000``` and your LAN IP is 192.168.0.124 the hosts file will have an entry looking like this:
```192.168.0.124 in5.test```
**Please note that for PDF generation using local host, your domain name MUST end in .test for your PDFs to generate correctly, this is a DNS resolver issue with chromium.
All that is left to do now is bring up the container
``` docker-compose up -d```
**Note: When performing the setup, the Database host is ```db```
### Running on ARM64 (Raspberry Pi 4)
When deploying on an ARM64 system, you need to comment out the `image: mysql:8` line and uncomment `image: mariadb:10.4` in the `docker-compose.yml` file.
### Updating the Image when using `docker-compose`
As `docker-compose` does not support any form of version control, this git provide updates to `docker-compose.yml` directly.
To upgrade to a newer release image, please make sure to update the `docker-compose.yml` first by running
To upgrade to a newer release image, update your docker-compose.yml first by running:
```bash
git pull
docker compose down
docker compose pull
docker compose up
```
It is recommended to perform a backup before.
You may need to manually merge any changes that cannot be merged automatically by git.
It is recommended to perform a backup before updating.
### Thanks
Massive thank you to [lwj5](https://github.com/lwj5) for the tireless work to continually improve the dockerfile and its associated tooling.
### Support
If you discover a bug, please create an issue. For general queries, visit our [Forum](https://forum.invoiceninja.com/)
## Support
### Todo
If you discover a bug, please create and issue, if you query is general in nature please visit us on our [Forum ](https://forum.invoiceninja.com/)
This is a new image which should provide much better support for all users, however there are some items left to complete
- [ ] Backup script
- [ ] Integrate soketi server
- [ ] Add elastic search for site wide search

View File

@@ -1,73 +0,0 @@
ARG PHP_VERSION=7.3
ARG BAK_STORAGE_PATH=/var/www/app/docker-backup-storage/
ARG BAK_PUBLIC_PATH=/var/www/app/docker-backup-public/
FROM php:${PHP_VERSION}-fpm-alpine as prod
LABEL maintainer="David Bomba <turbo124@gmail.com>"
#####
# SYSTEM REQUIREMENT
#####
ARG INVOICENINJA_VERSION
ARG BAK_STORAGE_PATH
ARG BAK_PUBLIC_PATH
RUN mv /usr/local/etc/php/php.ini-production /usr/local/etc/php/php.ini
# Install PHP extensions
# https://hub.docker.com/r/mlocati/php-extension-installer/tags
COPY --from=mlocati/php-extension-installer:1.1.41 /usr/bin/install-php-extensions /usr/local/bin/
RUN install-php-extensions \
gd \
gmp \
opcache \
pdo_mysql \
zip
# Separate user
ENV INVOICENINJA_USER=invoiceninja
WORKDIR /var/www/app
RUN addgroup --gid=1500 -S "$INVOICENINJA_USER" \
&& adduser --uid=1500 \
--disabled-password \
--gecos "" \
--home "$(pwd)" \
--ingroup "$INVOICENINJA_USER" \
--no-create-home \
"$INVOICENINJA_USER" \
&& chown -R "$INVOICENINJA_USER":"$INVOICENINJA_USER" .
COPY rootfs /
RUN chmod +x /usr/local/bin/docker-entrypoint
USER 1500
# Download and install IN
ENV INVOICENINJA_VERSION="${INVOICENINJA_VERSION}"
ENV BAK_STORAGE_PATH $BAK_STORAGE_PATH
ENV BAK_PUBLIC_PATH $BAK_PUBLIC_PATH
RUN curl -o /tmp/ninja.zip -L https://download.invoiceninja.com/ninja-v${INVOICENINJA_VERSION}.zip \
&& unzip -q /tmp/ninja.zip -d /tmp/ \
&& mv /tmp/ninja/* /var/www/app \
&& rm -rf /tmp/ninja* \
&& mv /var/www/app/storage $BAK_STORAGE_PATH \
&& mv /var/www/app/public $BAK_PUBLIC_PATH \
&& mkdir -p /var/www/app/public/logo /var/www/app/storage \
&& chmod -R 755 /var/www/app/storage \
&& rm -rf /var/www/app/docs /var/www/app/tests
# Override the environment settings from projects .env file
ENV IS_DOCKER true
ENV LOG errorlog
ENV SELF_UPDATER_SOURCE ''
# Use to be mounted into nginx
VOLUME /var/www/app/public
ENTRYPOINT ["docker-entrypoint"]
CMD ["php-fpm"]

View File

@@ -1 +0,0 @@
Fri Jul 2 7:33:22 +00 2021

View File

@@ -1,17 +0,0 @@
; How often (in seconds) to check file timestamps for changes to the shared
; memory storage allocation. ("1" means validate once per second, but only
; once per request. "0" means always validate)
;opcache.revalidate_freq=2
opcache.revalidate_freq=60
# http://symfony.com/doc/current/performance.html
; Duration of time, in seconds for which to cache realpath information for a given
; file or directory. For systems with rarely changing files, consider increasing this
; value.
; http://php.net/realpath-cache-ttl
;realpath_cache_ttl = 120
realpath_cache_ttl = 600
; Maximum allowed size for uploaded files.
; http://php.net/upload-max-filesize
upload_max_filesize = 8M

View File

@@ -1,110 +0,0 @@
#!/usr/bin/env sh
set -e
# logging functions
in_log() {
local type="$1"; shift
printf '%s [%s] [Entrypoint]: %s\n' "$(date -u '+%Y-%m-%dT%H:%M:%SZ')" "$type" "$*"
}
in_error() {
in_log ERROR "$@" >&2
exit 1
}
# Indirect expansion (ie) is not supported in bourne shell. That's why we are using this "magic" here.
ie_gv() {
eval "echo \$$1"
}
# usage: file_env VAR [DEFAULT]
# ie: file_env 'XYZ_DB_PASSWORD' 'example'
# (will allow for "$XYZ_DB_PASSWORD_FILE" to fill in the value of
# "$XYZ_DB_PASSWORD" from a file, especially for Docker's secrets feature)
file_env() {
local var="$1"
local fileVar="${var}_FILE"
local def="${2:-}"
if [ "$(ie_gv ${var})" != "" ] && [ "$(ie_gv ${fileVar})" != "" ]; then
in_error "Both $var and $fileVar are set (but are exclusive)"
fi
local val="$def"
if [ "$(ie_gv ${var})" != "" ]; then
val=$(ie_gv ${var})
elif [ "$(ie_gv ${fileVar})" != "" ]; then
val=`cat $(ie_gv ${fileVar})`
fi
export "$var"="$val"
unset "$fileVar"
}
# first arg is `-f` or `--some-option`
if [ "${1#-}" != "$1" ]; then
set -- php-fpm "$@"
fi
# create storage volume
if [ ! -d /var/www/app/storage ] && [ -d "$BAK_STORAGE_PATH" ]; then
mv "$BAK_STORAGE_PATH" /var/www/app/storage
elif [ -d "$BAK_STORAGE_PATH" ]; then
# copy missing folders in storage
IN_STORAGE_BACKUP="$(ls "$BAK_STORAGE_PATH")"
for path in $IN_STORAGE_BACKUP; do
if [ ! -e "/var/www/app/storage/$path" ]; then
cp -Rp "$BAK_STORAGE_PATH/$path" "/var/www/app/storage/"
fi
done
fi
rm -rf "$BAK_STORAGE_PATH"
# create public volume
if [ ! -d /var/www/app/public ] && [ -d "$BAK_PUBLIC_PATH" ]; then
mv "$BAK_PUBLIC_PATH" /var/www/app/public
elif [ ! -e /var/www/app/public/version ] || [ "$INVOICENINJA_VERSION" != "$(cat /var/www/app/public/version)" ]; then
# version mismatch, update all
cp -au "$BAK_PUBLIC_PATH/"* /var/www/app/public
echo "$INVOICENINJA_VERSION" > /var/www/app/public/version
elif [ ! -d /var/www/app/public/logo ] && [ -d "$BAK_PUBLIC_PATH/logo" ]; then
# missing logo folder only, copy folder
cp -a "$BAK_PUBLIC_PATH/logo" /var/www/app/public/logo
elif [ -d "$BAK_PUBLIC_PATH/logo" ]; then
# copy missing folders in logo
IN_LOGO_BACKUP="$(ls "$BAK_PUBLIC_PATH/logo")"
for path in $IN_LOGO_BACKUP; do
if [ ! -e "/var/www/app/public/logo/$path" ]; then
cp -a "$BAK_PUBLIC_PATH/logo/$path" "/var/www/app/public/logo/"
fi
done
fi
rm -rf "$BAK_PUBLIC_PATH"
# Set permission for web server to create/update files (only <v4)
chown -R "$INVOICENINJA_USER":"$INVOICENINJA_USER" /var/www/app/storage /var/www/app/public /var/www/app/bootstrap
# Initialize values that might be stored in a file
file_env 'APP_KEY'
file_env 'API_SECRET'
file_env 'CLOUDFLARE_API_KEY'
file_env 'DB_USERNAME'
file_env 'DB_USERNAME1'
file_env 'DB_USERNAME2'
file_env 'DB_PASSWORD'
file_env 'DB_PASSWORD1'
file_env 'DB_PASSWORD2'
file_env 'MAIL_USERNAME'
file_env 'MAIL_PASSWORD'
file_env 'MAILGUN_SECRET'
file_env 'S3_KEY'
file_env 'S3_SECRET'
# Run Laravel stuff
if [[ "$1" == "supervisord" ]] || [[ "$1" == "php-fpm" ]]; then
echo "Initialising Laravel..."
. laravel-init.sh
fi
exec docker-php-entrypoint "$@"

View File

@@ -1,5 +0,0 @@
#!/bin/sh
php artisan config:cache
php artisan optimize
php artisan migrate --force

View File

@@ -1,119 +0,0 @@
ARG PHP_VERSION=8.2
ARG BAK_STORAGE_PATH=/var/www/app/docker-backup-storage/
ARG BAK_PUBLIC_PATH=/var/www/app/docker-backup-public/
# Get Invoice Ninja and install nodejs packages
FROM --platform=$BUILDPLATFORM node:lts-alpine as nodebuild
# Download Invoice Ninja
ARG INVOICENINJA_VERSION
ARG REPOSITORY=invoiceninja/invoiceninja
ARG FILENAME=invoiceninja.tar
RUN set -eux; apk add curl unzip grep
RUN DOWNLOAD_URL=$(curl -s "https://api.github.com/repos/invoiceninja/invoiceninja/releases/latest" | grep -o '"browser_download_url": "[^"]*invoiceninja.tar"' | cut -d '"' -f 4) && \
curl -LJO "$DOWNLOAD_URL" && \
mv invoiceninja.tar /tmp/ninja.tar
# Extract Invoice Ninja
RUN mkdir -p /var/www/app \
&& tar -xvf /tmp/ninja.tar -C /var/www/app/ \
&& mkdir -p /var/www/app/public/logo /var/www/app/storage
WORKDIR /var/www/app
# Prepare php image
FROM php:${PHP_VERSION}-fpm-alpine as phpbuild
LABEL maintainer="David Bomba <turbo124@gmail.com>"
# Adding caching_sha2_password.so
# With this we get native support for caching_sha2_password
RUN apk add --no-cache mariadb-connector-c
RUN mv /usr/local/etc/php/php.ini-production /usr/local/etc/php/php.ini
# Install PHP extensions
# https://hub.docker.com/r/mlocati/php-extension-installer/tags
COPY --from=mlocati/php-extension-installer /usr/bin/install-php-extensions /usr/local/bin/
# Install chromium
RUN set -eux; \
apk add --no-cache \
font-isas-misc \
supervisor \
mysql-client \
chromium \
ttf-freefont \
ttf-dejavu
RUN install-php-extensions \
bcmath \
exif \
gd \
gmp \
mysqli \
opcache \
pdo_mysql \
zip \
intl \
@composer \
&& rm /usr/local/bin/install-php-extensions
# Copy files
COPY rootfs /
## Create user
ARG UID=1500
ENV INVOICENINJA_USER invoiceninja
RUN addgroup --gid=$UID -S "$INVOICENINJA_USER" \
&& adduser --uid=$UID \
--disabled-password \
--gecos "" \
--home "/var/www/app" \
--ingroup "$INVOICENINJA_USER" \
"$INVOICENINJA_USER"
WORKDIR /var/www/app
# Set up app
ARG INVOICENINJA_VERSION
ARG BAK_STORAGE_PATH
ARG BAK_PUBLIC_PATH
ENV INVOICENINJA_VERSION $INVOICENINJA_VERSION
ENV BAK_STORAGE_PATH $BAK_STORAGE_PATH
ENV BAK_PUBLIC_PATH $BAK_PUBLIC_PATH
COPY --from=nodebuild --chown=$INVOICENINJA_USER:$INVOICENINJA_USER /var/www/app /var/www/app
RUN rm -rf /var/www/app/ui
USER $UID
WORKDIR /var/www/app
# Do not remove this ENV
ENV IS_DOCKER true
FROM --platform=$BUILDPLATFORM nodebuild AS dependencybuild
WORKDIR /var/www/app
COPY --from=phpbuild /var/www/app /var/www/app
# # Install node packages
ARG BAK_STORAGE_PATH
ARG BAK_PUBLIC_PATH
RUN mv /var/www/app/storage $BAK_STORAGE_PATH \
&& mv /var/www/app/public $BAK_PUBLIC_PATH
FROM phpbuild as prod
COPY --from=dependencybuild --chown=$INVOICENINJA_USER:$INVOICENINJA_USER /var/www/app /var/www/app
# Override the environment settings from projects .env file
ENV APP_ENV production
ENV LOG errorlog
ENV SNAPPDF_EXECUTABLE_PATH /usr/bin/chromium-browser
ENTRYPOINT ["docker-entrypoint"]
CMD ["supervisord"]

View File

@@ -1 +0,0 @@
Fri Jul 4 7:33:22 +00 2023

View File

@@ -1,14 +0,0 @@
#!/bin/sh
php artisan db:seed --force
# Build up array of arguments...
if [[ ! -z "${IN_USER_EMAIL}" ]]; then
email="--email ${IN_USER_EMAIL}"
fi
if [[ ! -z "${IN_PASSWORD}" ]]; then
password="--password ${IN_PASSWORD}"
fi
php artisan ninja:create-account $email $password

View File

@@ -1,42 +0,0 @@
[supervisord]
nodaemon=true
pidfile=/tmp/supervisord.pid
logfile=/dev/null ; nodaemon will cause logs to go to stdout
logfile_maxbytes=0
loglevel=info
[program:php-fpm]
redirect_stderr=true
stdout_logfile=/dev/stdout
stdout_logfile_maxbytes=0
stderr_logfile=/dev/stderr
stderr_logfile_maxbytes=0
command=php-fpm
[program:scheduler]
autorestart=true
redirect_stderr=true
stdout_logfile=/dev/stdout
stdout_logfile_maxbytes=0
stderr_logfile=/dev/stderr
stderr_logfile_maxbytes=0
command=php artisan schedule:work
[program:queue-worker]
process_name=%(program_name)s_%(process_num)02d
autorestart=true
redirect_stderr=true
stdout_logfile=/dev/stdout
stdout_logfile_maxbytes=0
stderr_logfile=/dev/stderr
stderr_logfile_maxbytes=0
numprocs=2
command=php artisan queue:work --sleep=3 --tries=1 --memory=256 --timeout=3600
[eventlistener:shutdown]
command=shutdown.sh
events=PROCESS_STATE_STOPPED, PROCESS_STATE_EXITED, PROCESS_STATE_FATAL
stdout_logfile=/dev/stdout
stdout_logfile_maxbytes=0
stderr_logfile=/dev/stderr
stderr_logfile_maxbytes=0

View File

@@ -1,113 +0,0 @@
#!/usr/bin/env sh
set -e
# logging functions
in_log() {
local type="$1"
shift
printf '%s [%s] [Entrypoint]: %s\n' "$(date -u '+%Y-%m-%dT%H:%M:%SZ')" "$type" "$*"
}
in_error() {
in_log ERROR "$@" >&2
exit 1
}
# Indirect expansion (ie) is not supported in bourne shell. That's why we are using this "magic" here.
ie_gv() {
eval "echo \$$1"
}
# usage: file_env VAR [DEFAULT]
# ie: file_env 'XYZ_DB_PASSWORD' 'example'
# (will allow for "$XYZ_DB_PASSWORD_FILE" to fill in the value of
# "$XYZ_DB_PASSWORD" from a file, especially for Docker's secrets feature)
file_env() {
local var="$1"
local fileVar="${var}_FILE"
local def="${2:-}"
if [ "$(ie_gv ${var})" != "" ]; then
if [ "$(ie_gv ${fileVar})" != "" ]; then
in_error "Both $var and $fileVar are set (but are exclusive)"
fi
unset "$fileVar"
return
fi
if [ "$(ie_gv ${fileVar})" != "" ] && [ -f "$(ie_gv ${fileVar})" ]; then
export "$var"="$(cat $(ie_gv ${fileVar}))"
elif [ ! -z "$def" ]; then
export "$var"="$def"
fi
unset "$fileVar"
}
# first arg is `-f` or `--some-option`
if [ "${1#-}" != "$1" ]; then
set -- supervisord "$@"
fi
# create storage volume
if [ -d "$BAK_STORAGE_PATH" ]; then
if [ ! -d /var/www/app/storage ]; then
mv "$BAK_STORAGE_PATH" /var/www/app/storage
else
# copy missing folders in storage
IN_STORAGE_BACKUP="$(ls "$BAK_STORAGE_PATH")"
for path in $IN_STORAGE_BACKUP; do
if [ ! -e "/var/www/app/storage/$path" ]; then
cp -Rp "$BAK_STORAGE_PATH/$path" "/var/www/app/storage/"
fi
done
fi
rm -rf "$BAK_STORAGE_PATH"
fi
# create public volume
if [ -d "$BAK_PUBLIC_PATH" ]; then
if [ ! -d /var/www/app/public ]; then
mv "$BAK_PUBLIC_PATH" /var/www/app/public
elif [ ! -f /var/www/app/public/version ] || [ "$INVOICENINJA_VERSION" != "$(cat /var/www/app/public/version)" ]; then
# version mismatch, update all
cp -au "$BAK_PUBLIC_PATH/"* /var/www/app/public
echo "$INVOICENINJA_VERSION" >/var/www/app/public/version
elif [ ! -d /var/www/app/public/logo ] && [ -d "$BAK_PUBLIC_PATH/logo" ]; then
# missing logo folder only, copy folder
cp -a "$BAK_PUBLIC_PATH/logo" /var/www/app/public/logo
elif [ -d "$BAK_PUBLIC_PATH/logo" ]; then
# copy missing folders in logo
IN_LOGO_BACKUP="$(ls "$BAK_PUBLIC_PATH/logo")"
for path in $IN_LOGO_BACKUP; do
if [ ! -e "/var/www/app/public/logo/$path" ]; then
cp -a "$BAK_PUBLIC_PATH/logo/$path" "/var/www/app/public/logo/"
fi
done
fi
rm -rf "$BAK_PUBLIC_PATH"
fi
# Initialize values that might be stored in a file
file_env 'APP_KEY'
file_env 'API_SECRET'
file_env 'CLOUDFLARE_API_KEY'
file_env 'DB_USERNAME'
file_env 'DB_USERNAME1'
file_env 'DB_USERNAME2'
file_env 'DB_PASSWORD'
file_env 'DB_PASSWORD1'
file_env 'DB_PASSWORD2'
file_env 'MAIL_USERNAME'
file_env 'MAIL_PASSWORD'
file_env 'MAILGUN_SECRET'
file_env 'S3_KEY'
file_env 'S3_SECRET'
# Run IN/Laravel stuff
if [[ "$1" == "supervisord" ]] || [[ "$1" == "php-fpm" ]]; then
in_log INFO "Initialising Invoice Ninja..."
. invoiceninja-init.sh
fi
exec docker-php-entrypoint "$@"

View File

@@ -1,45 +0,0 @@
#!/bin/sh
# usage: docker_process_init_files [file [file [...]]]
# ie: docker_process_init_files /always-initdb.d/*
# process initializer files, based on file extensions
docker_process_init_files() {
echo
local f
for f; do
case "$f" in
*.sh)
# https://github.com/docker-library/postgres/issues/450#issuecomment-393167936
# https://github.com/docker-library/postgres/pull/452
if [ -x "$f" ]; then
in_log INFO "$0: running $f"
"$f"
else
in_log INFO "$0: sourcing $f"
. "$f"
fi
;;
*) in_log INFO "$0: ignoring $f" ;;
esac
echo
done
}
php artisan config:cache
php artisan optimize
php artisan package:discover
# Check if DB works, if not crash the app.
DB_READY=$(php artisan tinker --execute='echo app()->call("App\Utils\SystemHealth@dbCheck")["success"];')
if [ "$DB_READY" != "1" ]; then
php artisan migrate:status # Print verbose error
in_error "Error connecting to DB"
fi
php artisan migrate --force
# If first IN run, it needs to be initialized
IN_INIT=$(php artisan tinker --execute='echo Schema::hasTable("accounts") && !App\Models\Account::all()->first();')
if [ "$IN_INIT" == "1" ]; then
docker_process_init_files /docker-entrypoint-init.d/*
fi

View File

@@ -1,8 +0,0 @@
#!/bin/sh
printf "READY\n"
while read line; do
echo "Processing Event: $line" >&2
kill -SIGQUIT $PPID
done </dev/stdin

View File

@@ -1,17 +0,0 @@
; How often (in seconds) to check file timestamps for changes to the shared
; memory storage allocation. ("1" means validate once per second, but only
; once per request. "0" means always validate)
;opcache.revalidate_freq=2
opcache.revalidate_freq=60
# http://symfony.com/doc/current/performance.html
; Duration of time, in seconds for which to cache realpath information for a given
; file or directory. For systems with rarely changing files, consider increasing this
; value.
; http://php.net/realpath-cache-ttl
;realpath_cache_ttl = 120
realpath_cache_ttl = 600
; Maximum allowed size for uploaded files.
; http://php.net/upload-max-filesize
upload_max_filesize = 8M

View File

@@ -1,23 +0,0 @@
# Patterns to ignore when building packages.
# This supports shell glob matching, relative path matching, and
# negation (prefixed with !). Only one pattern per line.
.DS_Store
# Common VCS dirs
.git/
.gitignore
.bzr/
.bzrignore
.hg/
.hgignore
.svn/
# Common backup files
*.swp
*.bak
*.tmp
*.orig
*~
# Various IDEs
.project
.idea/
*.tmproj
.vscode/

View File

@@ -1,15 +0,0 @@
dependencies:
- name: common
repository: https://charts.bitnami.com/bitnami
version: 2.2.2
- name: nginx
repository: https://charts.bitnami.com/bitnami
version: 13.2.20
- name: mariadb
repository: https://charts.bitnami.com/bitnami
version: 11.4.2
- name: redis
repository: https://charts.bitnami.com/bitnami
version: 16.13.2
digest: sha256:da0dca54f32ca0465f89744d6247421ad13c907f09cd40fb21985c81888aaef1
generated: "2022-12-23T12:54:52.476889+08:00"

View File

@@ -1,47 +0,0 @@
apiVersion: v2
name: invoiceninja
description: A Helm chart to install Invoice Ninja
# A chart can be either an 'application' or a 'library' chart.
#
# Application charts are a collection of templates that can be packaged into versioned archives
# to be deployed.
#
# Library charts provide useful utilities or functions for the chart developer. They're included as
# a dependency of application charts to inject those utilities and functions into the rendering
# pipeline. Library charts do not define any templates and therefore cannot be deployed.
type: application
# This is the chart version. This version number should be incremented each time you make changes
# to the chart and its templates, including the app version.
# Versions are expected to follow Semantic Versioning (https://semver.org/)
version: 0.10.2
# This is the version number of the application being deployed. This version number should be
# incremented each time you make changes to the application. Versions are not expected to
# follow Semantic Versioning. They should reflect the version the application is using.
appVersion: 5.6.24
keywords:
- invoiceninja
home: https://invoiceninja.github.io/dockerfiles
sources:
- https://github.com/invoiceninja/invoiceninja
- https://github.com/invoiceninja/dockerfiles
dependencies:
- name: common
repository: https://charts.bitnami.com/bitnami
tags:
- bitnami-common
version: 2.x.x
- condition: nginx.enabled
name: nginx
repository: https://charts.bitnami.com/bitnami
version: 13.x.x
- condition: mariadb.enabled
name: mariadb
repository: https://charts.bitnami.com/bitnami
version: 11.4.x
- condition: redis.enabled
name: redis
repository: https://charts.bitnami.com/bitnami
version: 16.x.x
maintainers:
- email: lwj5@hotmail.com
name: lwj5

View File

@@ -1,388 +0,0 @@
# Invoice Ninja Helm Chart
This helm chart installs Invoice Ninja (IN) and its dependencies into a running
Kubernetes cluster.
The chart installs the [Invoice Ninja](https://hub.docker.com/r/invoiceninja/invoiceninja) docker image.
Please read [Upgrading](#upgrading) section before upgrading MAJOR versions.
## Dependencies
- The Bitnami [common](https://github.com/bitnami/charts/tree/master/bitnami/common) helm chart
- The Bitnami [mariadb](https://github.com/bitnami/charts/tree/master/bitnami/mariadb) helm chart
- The Bitnami [nginx](https://github.com/bitnami/charts/tree/master/bitnami/nginx) helm chart
- The Bitnami [redis](https://github.com/bitnami/charts/tree/master/bitnami/redis) helm chart
- Tested on Kubernetes 1.19+
## Installing the Chart
To install the chart with the release name `invoiceninja`:
```bash
helm repo add invoiceninja https://invoiceninja.github.io/dockerfiles
helm install invoiceninja invoiceninja/invoiceninja --set appKey=changeit --set mariadb.auth.rootPassword=changeit --set mariadb.auth.password=changeit --set redis.auth.password=changeit
```
The command deploys Invoice Ninja on the Kubernetes cluster in the default namespace. The [Parameters](#parameters) section lists the parameters that can be configured during installation.
> **Tip**: List all releases using `helm list`
## Uninstalling the Chart
To uninstall/delete the `invoiceninja` deployment:
```bash
helm delete invoiceninja
```
The command removes all the Kubernetes components associated with the chart and deletes the release.
## Parameters
The following table lists the configurable parameters of the Invoice Ninja chart and their default values.
> NOTE: You MUST set any values that default to random or risk losing access after an upgrade. See how [here](#installing-with-arguments)
### Global Configuration
The following table shows the configuration options for the Invoice Ninja helm chart:
### Global parameters
| Parameter | Description | Default |
| ------------------------- | ----------------------------------------------- | ------------------------------------------------------- |
| `global.imageRegistry` | Global Docker image registry | `nil` |
| `global.imagePullSecrets` | Global Docker registry secret names as an array | `[]` (does not add image pull secrets to deployed pods) |
| `global.storageClass` | Global storage class for dynamic provisioning | `nil` |
### Common parameters
| Parameter | Description | Default |
| ------------------- | -------------------------------------------------------------------- | ------------------------------ |
| `nameOverride` | String to partially override common.names.fullname | `nil` |
| `fullnameOverride` | String to fully override common.names.fullname | `nil` |
| `clusterDomain` | Default Kubernetes cluster domain | `cluster.local` |
| `commonLabels` | Labels to add to all deployed objects | `{}` |
| `commonAnnotations` | Annotations to add to all deployed objects | `{}` |
| `kubeVersion` | Force target Kubernetes version (using Helm capabilities if not set) | `nil` |
| `extraDeploy` | Array of extra objects to deploy with the release | `[]` (evaluated as a template) |
### Invoice Ninja container parameters
| Parameter | Description | Default |
| ------------------------ | ----------------------------------------------------------------------------- | ------------------------------------------------------- |
| `image.registry` | Invoice Ninja image registry | `docker.io` |
| `image.repository` | Invoice Ninja image name | `invoiceninja/invoiceninja` |
| `image.tag` | Invoice Ninja image tag | Check `values.yaml` file |
| `image.pullPolicy` | Invoice Ninja image pull policy | `IfNotPresent` |
| `image.pullSecrets` | Specify docker-registry secret names as an array | `[]` (does not add image pull secrets to deployed pods) |
| `image.debug` | Specify if debug logs should be enabled | `false` |
| `debug` | Turn on debug mode on Invoice Ninja | `false` |
| `appKey` | Laravel Application Key (ignored if existing secret is provided) | _random 32 character alphanumeric string_ |
| `appURL` | Override Laravel Application URL (automatically set if blank) | `""` |
| `userEmail` | Initial user email address | `admin@example.com` |
| `userPassword` | Initial user password (ignored if existing secret is provided) | `changeme!` |
| `logChannel` | Name of log channel to use | `nil` |
| `broadcastDriver` | Name of broadcast driver to use | `nil` |
| `cacheDriver` | Name of cache driver to use | `nil` |
| `sessionDriver` | Name of session driver to use | `nil` |
| `queueConnection` | Name of queue connection to use | `nil` |
| `pdfGenerator` | PDF generation method (Allowed values: `snappdf` or `phantom`) | `snappdf` |
| `mailer` | Name of the mailer to use (log, smtp, etc.) | `log` |
| `requireHttps` | Force HTTPS for internal connections to Invoice Ninja (see #349) | `false` |
| `existingSecret` | Use existing secret that contain the keys `APP_KEY` and `IN_PASSWORD` | `nil` |
| `extraEnvVars` | Extra environment variables to be set on Invoice Ninja container | `{}` |
| `extraEnvVarsCM` | Name of existing ConfigMap containing extra env vars | `nil` |
| `extraEnvVarsSecret` | Name of existing Secret containing extra env vars | `nil` |
| `trustedProxy` | List of trusted proxies for Invoice Ninja to communicate with the nginx proxy | `'*'` |
| `extraVolumeMounts` | Additional volume mounts | `[]` |
| `resources` | The resources for the Invoice Ninja container | `{}` |
| `livenessProbe` | Liveness probe configuration for Invoice Ninja | Check `values.yaml` file |
| `readinessProbe` | Readiness probe configuration for Invoice Ninja | Check `values.yaml` file |
| `containerPorts.fastcgi` | FastCGI port to expose at container level | `9000` |
### Inline web server container parameters (only used when `nginx.enabled` is **not** set to true)
| Parameter | Description | Default |
| ------------------------ | -------------------------------------------------------- | ------------------------------------------------------- |
| `http.image.registry` | Nginx image registry | `docker.io` |
| `http.image.repository` | Nginx image name | `invoiceninja/invoiceninja` |
| `http.image.tag` | Nginx image tag | Check `values.yaml` file |
| `http.image.pullPolicy` | Nginx image pull policy | `IfNotPresent` |
| `http.image.pullSecrets` | Specify docker-registry secret names as an array | `[]` (does not add image pull secrets to deployed pods) |
| `http.image.debug` | Specify if debug logs should be enabled | `false` |
| `extraEnvVars` | Extra environment variables to be set on Nginx container | `{}` |
| `extraEnvVarsCM` | Name of existing ConfigMap containing extra env vars | `nil` |
| `extraEnvVarsSecret` | Name of existing Secret containing extra env vars | `nil` |
| `extraVolumeMounts` | Additional volume mounts | `[]` |
| `resources` | The resources for the Nginx container | `{}` |
| `livenessProbe` | Liveness probe configuration for Nginx | Check `values.yaml` file |
| `readinessProbe` | Readiness probe configuration for Nginx | Check `values.yaml` file |
| `containerPorts.http` | HTTP port to expose at container level | `9000` |
| `containerPorts.https` | HTTPS port to expose at container level | `9000` |
### Invoice Ninja deployment parameters
| Parameter | Description | Default |
| --------------------------- | ----------------------------------------------------------------------------------------- | ------------------------------ |
| `replicaCount` | Number of Invoice Ninja Pods to run | `1` |
| `serviceAccountName` | Name of a service account for the Invoice Ninja pods | `default` |
| `containerSecurityContext` | Invoice Ninja containers' Security Context | Check `values.yaml` file |
| `podSecurityContext` | Invoice Ninja pods' Security Context | Check `values.yaml` file |
| `updateStrategy` | Set up update strategy | `RollingUpdate` |
| `podAntiAffinityPreset` | Pod anti-affinity preset. Ignored if `affinity` is set. Allowed values: `soft` or `hard` | `soft` |
| `nodeAffinityPreset.type` | Node affinity preset type. Ignored if `affinity` is set. Allowed values: `soft` or `hard` | `""` |
| `nodeAffinityPreset.key` | Node label key to match. Ignored if `affinity` is set. | `""` |
| `nodeAffinityPreset.values` | Node label values to match. Ignored if `affinity` is set. | `[]` |
| `affinity` | Affinity for pod assignment | `{}` (evaluated as a template) |
| `nodeSelector` | Node labels for pod assignment | `{}` (evaluated as a template) |
| `tolerations` | Tolerations for pod assignment | `[]` (evaluated as a template) |
| `podLabels` | Extra labels for Invoice Ninja pods | `{}` |
| `podAnnotations` | Annotations for Invoice Ninja pods | `{}` |
| `extraVolumes` | Additional volumes | `[]` |
### Volume Permissions parameters
| Parameter | Description | Default |
| ------------------------------------- | -------------------------------------------------------------------------------------------------------------------- | ------------------------------------------------------- |
| `volumePermissions.enabled` | Enable init container that changes the owner and group of the persistent volume(s) mountpoint to `runAsUser:fsGroup` | `false` |
| `volumePermissions.image.registry` | Init container volume-permissions image registry | `docker.io` |
| `volumePermissions.image.repository` | Init container volume-permissions image name | `bitnami/bitnami-shell` |
| `volumePermissions.image.tag` | Init container volume-permissions image tag | `"10"` |
| `volumePermissions.image.pullPolicy` | Init container volume-permissions image pull policy | `Always` |
| `volumePermissions.image.pullSecrets` | Specify docker-registry secret names as an array | `[]` (does not add image pull secrets to deployed pods) |
| `volumePermissions.resources` | Init container volume-permissions resource | `{}` |
### Exposure parameters
#### FastCGI
| Parameter | Description | Default |
| ---------------------------------- | -------------------------------------------------------------------------- | ------------------------------ |
| `service.type` | Kubernetes Service type | `ClusterIP` |
| `service.port` | Service FastCGI port | `9000` |
| `service.nodePort` | Kubernetes FastCGI node port | `""` |
| `service.clusterIP` | Invoice Ninja service clusterIP IP | `None` |
| `service.loadBalancerSourceRanges` | Restricts access for LoadBalancer (only with `service.type: LoadBalancer`) | `[]` |
| `service.loadBalancerIP` | loadBalancerIP if service type is `LoadBalancer` | `nil` |
| `service.externalTrafficPolicy` | Enable client source IP preservation | `Cluster` |
| `service.annotations` | Service annotations | `{}` (evaluated as a template) |
#### Inline web server (only used when `nginx.enabled` is **not** set to true)
| Parameter | Description | Default |
| --------------------------------------- | -------------------------------------------------------------------------- | ------------------------------ |
| `service.http.type` | Kubernetes Service type | `ClusterIP` |
| `service.http.ports.http` | Service HTTP port | `9000` |
| `service.http.ports.https` | Service HTTPS port | `9000` |
| `service.http.nodePorts.http` | Kubernetes HTTP node port | `""` |
| `service.http.nodePorts.https` | Kubernetes HTTPS node port | `""` |
| `service.http.clusterIP` | Invoice Ninja service clusterIP IP | `None` |
| `service.http.loadBalancerSourceRanges` | Restricts access for LoadBalancer (only with `service.type: LoadBalancer`) | `[]` |
| `service.http.loadBalancerIP` | loadBalancerIP if service type is `LoadBalancer` | `nil` |
| `service.http.externalTrafficPolicy` | Enable client source IP preservation | `Cluster` |
| `service.http.annotations` | Service annotations | `{}` (evaluated as a template) |
### Ingress parameters
#### Inline web server (only used when `nginx.enabled` is **not** set to true)
| Parameter | Description | Default |
| -------------------------- | ----------------------------------------------------------------------------------------------------- | ------------------------ |
| `ingress.enabled` | Enable ingress | `true` |
| `ingress.certManager` | Add the corresponding annotations for cert-manager integration | `false` |
| `ingress.pathType` | Ingress path type | `ImplementationSpecific` |
| `ingress.apiVersion` | Force Ingress API version (automatically detected if not set) | `nil` |
| `ingress.ingressClassName` | IngressClass that will be be used to implement the Ingress (Kubernetes 1.18+) | `nil` |
| `ingress.hostname` | Default host for the ingress record | `invoiceninja.local` |
| `ingress.path` | Default path for the ingress record | `/` |
| `ingress.annotations` | Additional custom annotations for the ingress record | `{}` |
| `ingress.tls` | Enable TLS configuration for the host defined at `ingress.hostname` parameter | `false` |
| `ingress.extraHosts` | An array with additional hostname(s) to be covered with the ingress record | `[]` |
| `ingress.extraPaths` | An array with additional arbitrary paths that may need to be added to the ingress under the main host | `[]` |
| `ingress.extraTls` | TLS configuration for additional hostname(s) to be covered with this ingress record | `[]` |
| `ingress.secrets` | Custom TLS certificates as secrets | `[]` |
#### Nginx sub-chart
| Parameter | Description | Default |
| ------------------------------------ | ------------------------------------- | ------------------------------------------------------ |
| `nginx.enabled` | Deploy Nginx sub-chart | `false` |
| `nginx.service.type` | Kubernetes Service type | `ClusterIP` |
| `nginx.ingress.enabled` | Enable ingress controller resource | `true` |
| `nginx.ingress.hostname` | Default host for the ingress resource | `invoiceninja.local` |
| `nginx.existingServerBlockConfigmap` | Custom NGINX server block config map | `{{ include "invoiceninja.nginx.serverBlockName" . }}` |
| `nginx.staticSitePVC` | Name of Invoice Ninja public PVC | `{{ include "invoiceninja.public.storageName" . }}` |
> See [Dependencies](#dependencies) for more.
### Persistence parameters
| Parameter | Description | Default |
| ----------------------------------- | --------------------------------------------------- | ----------------- |
| `persistence.public.enabled` | Enable persistence using PVC | `true` |
| `persistence.public.existingClaim` | Enable persistence using an existing PVC | `nil` |
| `persistence.public.storageClass` | PVC Storage Class | `nil` |
| `persistence.public.accessModes` | PVC Access Modes | `[ReadWriteOnce]` |
| `persistence.public.size` | PVC Storage Request | `1Gi` |
| `persistence.public.dataSource` | PVC data source | `{}` |
| `persistence.storage.enabled` | Enable persistence using PVC (only for FILE driver) | `false` |
| `persistence.storage.existingClaim` | Enable persistence using an existing PVC | `nil` |
| `persistence.storage.storageClass` | PVC Storage Class | `nil` |
| `persistence.storage.accessModes` | PVC Access Modes | `[ReadWriteMany]` |
| `persistence.storage.size` | PVC Storage Request | `5Gi` |
| `persistence.storage.dataSource` | PVC data source | `{}` |
> See `values.yaml` for more details.
### Redis parameters
| Parameter | Description | Default |
| --------------------------------- | -------------------------------------------- | ----------------------------------------- |
| `redis.enabled` | If external redis is used, set it to `false` | `true` |
| `redis.auth.password` | Redis password | _random 10 character alphanumeric string_ |
| `redis.auth.sentinel` | Use password for sentinel containers | `false` |
| `redis.sentinel.enabled` | Enable sentinel containers | `true` |
| `redis.sentinel.quorum` | Sentinel Quorum | `1` |
| `redis.replica.replicaCount` | Number of Redis replicas to deploy | `1` |
| `externalRedis.host` | Host of the external redis | `nil` |
| `externalRedis.port` | Port of the external redis | `6379` |
| `externalRedis.password` | Password for the external redis | `nil` |
| `externalRedis.sentinel` | Using sentinels | `false` |
| `externalRedis.databases.default` | Database to use by default | `0` |
| `externalRedis.databases.cache` | Database to use by cache | `1` |
> See [Dependencies](#dependencies) for more.
### Database parameters
| Parameter | Description | Default |
| --------------------------------- | ------------------------------------------- | ----------------------------------------- |
| `mariadb.enabled` | Deploy MariaDB container(s) | `true` |
| `mariadb.auth.rootPassword` | Password for the MariaDB `root` user | _random 10 character alphanumeric string_ |
| `mariadb.auth.database` | Database name to create | `invoiceninja` |
| `mariadb.auth.username` | Database user to create | `invoiceninja` |
| `mariadb.auth.password` | Password for the database | _random 10 character alphanumeric string_ |
| `externalDatabase.host` | Host of the external database | `nil` |
| `externalDatabase.user` | Existing username in the external db | `invoiceninja` |
| `externalDatabase.password` | Password for the above username | `nil` |
| `externalDatabase.database` | Name of the existing database | `invoiceninja` |
| `externalDatabase.port` | Database port number | `3306` |
| `externalDatabase.existingSecret` | Name of the database existing Secret Object | `nil` |
> See [Dependencies](#dependencies) for more.
### Other parameters
| Parameter | Description | Default |
| -------------------------- | ---------------------------------------- | ------- |
| `autoscaling.enabled` | Enable autoscaling for Invoice Ninja | `false` |
| `autoscaling.minReplicas` | Minimum number of Invoice Ninja replicas | `1` |
| `autoscaling.maxReplicas` | Maximum number of Invoice Ninja replicas | `11` |
| `autoscaling.targetCPU` | Target CPU utilization percentage | `nil` |
| `autoscaling.targetMemory` | Target Memory utilization percentage | `nil` |
## Installing with Arguments
Specify each parameter using the `--set key=value[,key=value]` argument to `helm install`. For example,
```bash
helm install invoiceninja \
--set appKey=changeit \
--set replicaCount=3 \
--set persistence.public.accessModes[0]=ReadWriteMany
--set redis.auth.password=changeit \
--set redis.sentinel.quorum=2 \
--set redis.replica.replicaCount=3 \
--set mariadb.auth.rootPassword=changeit \
--set mariadb.auth.password=changeit \
invoiceninja/invoiceninja
```
The above command sets the number of replicas to 3 for a highly available (HA) setup and uses a `ReadWriteMany` volume. Note that you would need to use an external DB such as MariaDB Galera for a full HA production setup. For a production environment, it is recommended that you spin up the required databases in a separate Helm Chart to decouple the upgrading process.
Alternatively, a YAML file that specifies the values for the parameters can be provided while [installing](https://helm.sh/docs/helm/helm_install/) the chart. For example,
```yaml
# values.yaml
appKey: changeit
persistence:
public:
accessModes:
- ReadWriteMany
redis:
auth:
password: changeit
mariadb:
auth:
rootPassword: changeit
password: changeit
```
```bash
helm install invoiceninja -f values.yaml invoiceninja/invoiceninja
```
## Setting Environment Variables
Should you need to inject any environment variables such as those in [here](https://github.com/invoiceninja/dockerfiles/blob/master/env) into the `invoiceninja` container, you can use the `extraEnvVars` option:
```yaml
# ... values.yaml file
# In this example, we are setting the SMTP MAIL_HOST to be 'smtp.mailtrap.io'
extraEnvVars:
- name: MAIL_HOST
value: 'smtp.mailtrap.io' # all values must be strings, so other types must be surrounded in quotes
```
Alternatively you can provide the name of an existing `configmap` or `secret` object:
```bash
kubectl create configmap examplemap --from-literal=MAIL_HOST='smtp.mailtrap.io'
```
```yaml
# ... values.yaml file
extraEnvVarsCM: examplemap
```
## Inline webserver vs Nginx sub-chart
Since there are many people without access to a `ReadWriteMany` volume, the inline Nginx web server will allow you to use a `ReadWriteOnce` public volume limited to 1 IN replica.
If you have the ability to use `ReadWriteMany` persistent volume, you can choose between the two by setting the `nginx.enabled` parameter. Setting `nginx.enabled` to true will enable the Nginx sub-chart and will provide you with some additional features, such as:
- independent scaling of Nginx and IN pods
- separate resource limits/requests
- other features available from the sub-chart
## Upgrading
### To 0.10.0
The following chart dependencies have been upgraded.
- MariaDB
- Redis
- Nginx
- Bitnami common
Please take note that this upgrade MariaDB from 10.5 to 10.6. Please backup your database before proceeding.
### To 0.8.0
To improve the accessibility of this chart to regular users. Some of the defaults have been changed. This include:
- `persistence.public.accessModes` now defaults to `ReadWriteOnce`.
- `nginx.enabled` now defaults to false.
- `redis.replica.replicaCount` and `redis.sentinel.quorum` now defaults to `1`.
Other changes:
- `snappdf` parameter has been replaced by `pdfGenerator`.
### To 0.7.0
- Redis chart dependency has been upgraded and may not be backwards compatible with previous versions. See [here](https://github.com/bitnami/charts/tree/master/bitnami/redis) for more info.
- Storage persitence defaults to `false`. Set to `true` if not using Redis or using FILE driver

View File

@@ -1,34 +0,0 @@
** Please be patient while the chart is being deployed **
Your controller can be accessed through the following DNS name from within your cluster:
http://{{ include "invoiceninja.nginx.fullname" . }}.{{ .Release.Namespace }}.svc
To access your controller from outside the cluster follow the steps below:
{{- if or .Values.nginx.ingress.enabled }}
Externally through the following DNS name:
http://{{ .Values.nginx.ingress.hostname }}
-- OR --
{{ end }}
{{- if contains "NodePort" .Values.nginx.service.type }}
export NODE_PORT=$(kubectl get --namespace {{ .Release.Namespace }} -o jsonpath="{.spec.ports[0].nodePort}" services {{ include "invoiceninja.nginx.fullname" . }})
export NODE_IP=$(kubectl get nodes --namespace {{ .Release.Namespace }} -o jsonpath="{.items[0].status.addresses[0].address}")
echo http://$NODE_IP:$NODE_PORT
{{- else if contains "LoadBalancer" .Values.nginx.service.type }}
NOTE: It may take a few minutes for the LoadBalancer IP to be available.
You can watch the status of by running 'kubectl get --namespace {{ .Release.Namespace }} svc -w {{ include "invoiceninja.nginx.fullname" . }}'
export SERVICE_IP=$(kubectl get svc --namespace {{ .Release.Namespace }} {{ include "invoiceninja.nginx.fullname" . }} --template "{{"{{ range (index .status.loadBalancer.ingress 0) }}{{.}}{{ end }}"}}")
echo http://$SERVICE_IP:{{ .Values.service.port }}
{{- else if contains "ClusterIP" .Values.nginx.service.type }}
export SVC_NAME=$(kubectl get svc --namespace {{ .Release.Namespace }} -l "app.kubernetes.io/name=nginx,app.kubernetes.io/instance={{ .Release.Name }}" -o jsonpath="{.items[0].metadata.name}")
export SVC_PORT=$(kubectl get svc --namespace {{ .Release.Namespace }} $SVC_NAME -o jsonpath="{.spec.ports[0].port}")
echo "Add the line '127.0.0.1 {{ .Values.nginx.ingress.hostname }}' to your hosts file"
echo "Visit http://{{ .Values.nginx.ingress.hostname }} to use your application"
kubectl -n {{ .Release.Namespace }} port-forward svc/$SVC_NAME 80:$SVC_PORT
{{- end }}

View File

@@ -1,309 +0,0 @@
{{/*
Return the proper image name
*/}}
{{- define "invoiceninja.image" -}}
{{- include "common.images.image" (dict "imageRoot" .Values.image "global" .Values.global) -}}
{{- end -}}
{{/*
Return the proper image name
*/}}
{{- define "invoiceninja.nginx.image" -}}
{{- include "common.images.image" (dict "imageRoot" .Values.http.image "global" .Values.global) -}}
{{- end -}}
{{/*
Return the proper Docker Image Registry Secret Names
*/}}
{{- define "invoiceninja.imagePullSecrets" -}}
{{- include "common.images.pullSecrets" (dict "images" (list .Values.image .Values.http.image .Values.volumePermissions.image) "global" .Values.global) -}}
{{- end -}}
{{/*
Return the proper image name (for the init container volume-permissions image)
*/}}
{{- define "invoiceninja.volumePermissions.image" -}}
{{ include "common.images.image" (dict "imageRoot" .Values.volumePermissions.image "global" .Values.global) }}
{{- end -}}
{{/*
Create a default fully qualified app name.
We truncate at 63 chars because some Kubernetes name fields are limited to this (by the DNS naming spec).
*/}}
{{- define "invoiceninja.mariadb.fullname" -}}
{{- printf "%s-%s" .Release.Name "mariadb" | trunc 63 | trimSuffix "-" -}}
{{- end -}}
{{/*
Create a default fully qualified app name.
We truncate at 63 chars because some Kubernetes name fields are limited to this (by the DNS naming spec).
*/}}
{{- define "invoiceninja.nginx.fullname" -}}
{{- printf "%s-%s" .Release.Name "nginx" | trunc 63 | trimSuffix "-" -}}
{{- end -}}
{{/*
Create a default fully qualified app name.
We truncate at 63 chars because some Kubernetes name fields are limited to this (by the DNS naming spec).
*/}}
{{- define "invoiceninja.redis.fullname" -}}
{{- printf "%s-%s" .Release.Name "redis" | trunc 63 | trimSuffix "-" -}}
{{- end -}}
{{/*
Create the name of the service account to use
*/}}
{{- define "invoiceninja.serviceAccountName" -}}
{{- if .Values.serviceAccount.create }}
{{- default (include "common.names.fullname" .) .Values.serviceAccount.name }}
{{- else -}}
{{- default "default" .Values.serviceAccount.name }}
{{- end -}}
{{- end -}}
{{/*
Return the Invoice Ninja Secret Name
*/}}
{{- define "invoiceninja.secretName" -}}
{{- default (include "common.names.fullname" .) .Values.existingSecret }}
{{- end -}}
{{/*
Return the proper Storage Class
*/}}
{{- define "invoiceninja.public.storageClass" -}}
{{- include "common.storage.class" (dict "persistence" .Values.persistence.public "global" .Values.global) -}}
{{- end -}}
{{/*
Return the proper Storage Class
*/}}
{{- define "invoiceninja.storage.storageClass" -}}
{{- include "common.storage.class" (dict "persistence" .Values.persistence.storage "global" .Values.global) -}}
{{- end -}}
{{/*
Return the proper Storage Name
*/}}
{{- define "invoiceninja.public.storageName" -}}
{{- printf "%s-%s" .Release.Name "public" | trunc 63 | trimSuffix "-" -}}
{{- end -}}
{{/*
Return the proper Storage Name
*/}}
{{- define "invoiceninja.storage.storageName" -}}
{{- printf "%s-%s" .Release.Name "storage" | trunc 63 | trimSuffix "-" -}}
{{- end -}}
{{/*
Return the proper app URL
*/}}
{{- define "invoiceninja.url" -}}
{{- if .Values.appURL }}
{{- printf "%s" .Values.appURL -}}
{{- else if .Values.nginx.ingress.enabled }}
{{- if .Values.nginx.ingress.tls }}
{{- printf "https://%s" .Values.nginx.ingress.hostname -}}
{{- else }}
{{- printf "http://%s" .Values.nginx.ingress.hostname -}}
{{- end }}
{{- else if .Values.ingress.enabled }}
{{- if .Values.ingress.tls }}
{{- printf "https://%s" .Values.ingress.hostname -}}
{{- else }}
{{- printf "http://%s" .Values.ingress.hostname -}}
{{- end }}
{{- else }}
{{- printf "http://%s" (include "common.names.fullname" .) -}}
{{- end }}
{{- end -}}
{{/*
Return the MariaDB Hostname
*/}}
{{- define "invoiceninja.databaseHost" -}}
{{- if .Values.mariadb.enabled }}
{{- if eq .Values.mariadb.architecture "replication" }}
{{- printf "%s-%s" (include "invoiceninja.mariadb.fullname" .) "primary" | trunc 63 | trimSuffix "-" -}}
{{- else -}}
{{- printf "%s" (include "invoiceninja.mariadb.fullname" .) -}}
{{- end -}}
{{- else -}}
{{- printf "%s" .Values.externalDatabase.host -}}
{{- end -}}
{{- end -}}
{{/*
Return the MariaDB Port
*/}}
{{- define "invoiceninja.databasePort" -}}
{{- if .Values.mariadb.enabled }}
{{- printf "3306" -}}
{{- else -}}
{{- printf "%d" (.Values.externalDatabase.port | int ) -}}
{{- end -}}
{{- end -}}
{{/*
Return the MariaDB Database Name
*/}}
{{- define "invoiceninja.databaseName" -}}
{{- if .Values.mariadb.enabled }}
{{- printf "%s" .Values.mariadb.auth.database -}}
{{- else -}}
{{- printf "%s" .Values.externalDatabase.database -}}
{{- end -}}
{{- end -}}
{{/*
Return the MariaDB User
*/}}
{{- define "invoiceninja.databaseUser" -}}
{{- if .Values.mariadb.enabled }}
{{- printf "%s" .Values.mariadb.auth.username -}}
{{- else -}}
{{- printf "%s" .Values.externalDatabase.user -}}
{{- end -}}
{{- end -}}
{{/*
Return the MariaDB Secret Name
*/}}
{{- define "invoiceninja.databaseSecretName" -}}
{{- if .Values.externalDatabase.existingSecret -}}
{{- printf "%s" .Values.externalDatabase.existingSecret -}}
{{- else -}}
{{- if .Values.mariadb.auth.existingSecret -}}
{{- printf "%s" .Values.mariadb.auth.existingSecret -}}
{{- else -}}
{{- printf "%s" (include "invoiceninja.mariadb.fullname" .) -}}
{{- end -}}
{{- end -}}
{{- end -}}
{{/*
Return the Redis Hostname
*/}}
{{- define "invoiceninja.redisHost" -}}
{{- if .Values.redis.enabled }}
{{- if .Values.redis.sentinel.enabled }}
{{- printf "%s-%s" (include "invoiceninja.redis.fullname" .) "headless" | trunc 63 | trimSuffix "-" -}}
{{- else }}
{{- printf "%s-%s" (include "invoiceninja.redis.fullname" .) "master" | trunc 63 | trimSuffix "-" -}}
{{- end -}}
{{- else -}}
{{- printf "%s" .Values.externalRedis.host -}}
{{- end -}}
{{- end -}}
{{/*
Return the Redis Port
*/}}
{{- define "invoiceninja.redisPort" -}}
{{- if .Values.redis.enabled }}
{{- if .Values.redis.sentinel.enabled }}
{{- printf "26379" -}}
{{- else }}
{{- printf "6379" -}}
{{- end -}}
{{- else -}}
{{- printf "%d" (.Values.externalRedis.port | int ) -}}
{{- end -}}
{{- end -}}
{{/*
Return the Redis Database
*/}}
{{- define "invoiceninja.redisDatabase" -}}
{{- if .Values.redis.enabled }}
{{- printf "0" -}}
{{- else -}}
{{- printf "%s" .Values.externalRedis.databases.default -}}
{{- end -}}
{{- end -}}
{{/*
Return the Redis Database
*/}}
{{- define "invoiceninja.redisCacheDatabase" -}}
{{- if .Values.redis.enabled }}
{{- printf "1" -}}
{{- else -}}
{{- printf "%s" .Values.externalRedis.databases.cache -}}
{{- end -}}
{{- end -}}
{{/*
Return the Redis Secret Name
*/}}
{{- define "invoiceninja.redisSecretName" -}}
{{- if .Values.externalRedis.existingSecret -}}
{{- printf "%s" .Values.externalRedis.existingSecret -}}
{{- else -}}
{{- if .Values.redis.auth.existingSecret -}}
{{- printf "%s" .Values.redis.auth.existingSecret -}}
{{- else -}}
{{- printf "%s" (include "invoiceninja.redis.fullname" .) -}}
{{- end -}}
{{- end -}}
{{- end -}}
{{/*
Return the Broadcast Connection Name
*/}}
{{- define "invoiceninja.redisBroadcastConnection" -}}
{{- if or (and .Values.redis.enabled .Values.redis.sentinel.enabled) (and .Values.externalRedis.host .Values.externalRedis.sentinel) }}
{{- printf "sentinel-default" -}}
{{- else -}}
{{- printf "default" -}}
{{- end -}}
{{- end -}}
{{/*
Return the Cache Connection Name
*/}}
{{- define "invoiceninja.redisCacheConnection" -}}
{{- if or (and .Values.redis.enabled .Values.redis.sentinel.enabled) (and .Values.externalRedis.host .Values.externalRedis.sentinel) }}
{{- printf "sentinel-cache" -}}
{{- else -}}
{{- printf "cache" -}}
{{- end -}}
{{- end -}}
{{/*
Return the Queue Connection Name
*/}}
{{- define "invoiceninja.redisQueueConnection" -}}
{{- if or (and .Values.redis.enabled .Values.redis.sentinel.enabled) (and .Values.externalRedis.host .Values.externalRedis.sentinel) }}
{{- printf "sentinel-default" -}}
{{- else -}}
{{- printf "default" -}}
{{- end -}}
{{- end -}}
{{/*
Return the Session Connection Name
*/}}
{{- define "invoiceninja.redisSessionConnection" -}}
{{- if or (and .Values.redis.enabled .Values.redis.sentinel.enabled) (and .Values.externalRedis.host .Values.externalRedis.sentinel) }}
{{- printf "sentinel-default" -}}
{{- else -}}
{{- printf "default" -}}
{{- end -}}
{{- end -}}
{{/*
Server block configmap name for nignx.
We truncate at 63 chars because some Kubernetes name fields are limited to this (by the DNS naming spec).
*/}}
{{- define "invoiceninja.nginx.serverBlockName" -}}
{{- printf "%s-%s" .Release.Name "server-block" | trunc 63 | trimSuffix "-" -}}
{{- end -}}
{{/*
Name of web service for inline web server.
*/}}
{{- define "invoiceninja.http.serviceName" -}}
{{- printf "%s-%s" .Release.Name "web" | trunc 63 | trimSuffix "-" -}}
{{- end -}}

View File

@@ -1,59 +0,0 @@
apiVersion: v1
kind: ConfigMap
metadata:
name: {{ include "common.names.fullname" . }}
labels:
{{- include "common.labels.standard" $ | nindent 4 }}
{{- if .Values.commonLabels }}
{{- include "common.tplvalues.render" ( dict "value" .Values.commonLabels "context" $ ) | nindent 4 }}
{{- end }}
{{- if .Values.commonAnnotations }}
annotations:
{{- include "common.tplvalues.render" ( dict "value" .Values.commonAnnotations "context" $ ) | nindent 4 }}
{{- end }}
data:
APP_URL: {{ include "invoiceninja.url" . | quote }}
APP_DEBUG: {{ .Values.debug | quote }}
DB_HOST: {{ include "invoiceninja.databaseHost" . | quote }}
DB_PORT: {{ include "invoiceninja.databasePort" . | quote }}
DB_USERNAME: {{ include "invoiceninja.databaseUser" . | quote }}
DB_DATABASE: {{ include "invoiceninja.databaseName" . | quote }}
{{- if .Values.logChannel }}
LOG_CHANNEL: {{ .Values.logChannel | quote }}
{{- else }}
LOG_CHANNEL: stderr
{{- end }}
MAIL_MAILER: {{ .Values.mailer | quote }}
{{- if .Values.broadcastDriver }}
BROADCAST_DRIVER: {{ .Values.broadcastDriver | quote }}
{{- else if or .Values.redis.enabled .Values.externalRedis.host }}
BROADCAST_DRIVER: redis
{{- end }}
{{- if .Values.cacheDriver }}
CACHE_DRIVER: {{ .Values.cacheDriver | quote }}
{{- else if or .Values.redis.enabled .Values.externalRedis.host }}
CACHE_DRIVER: redis
{{- end }}
{{- if .Values.sessionDriver }}
SESSION_DRIVER: {{ .Values.sessionDriver | quote }}
{{- else if or .Values.redis.enabled .Values.externalRedis.host }}
SESSION_DRIVER: redis
{{- end }}
{{- if .Values.queueConnection }}
QUEUE_CONNECTION: {{ .Values.queueConnection | quote }}
{{- else if or .Values.redis.enabled .Values.externalRedis.host }}
QUEUE_CONNECTION: redis
{{- end }}
# PHANTOMJS_PDF_GENERATION is deprecated
PHANTOMJS_PDF_GENERATION: "false"
PDF_GENERATOR: {{ .Values.pdfGenerator | quote}}
REDIS_HOST: {{ include "invoiceninja.redisHost" . | quote }}
REDIS_PORT: {{ include "invoiceninja.redisPort" . | quote }}
REDIS_DB: {{ include "invoiceninja.redisDatabase" . | quote }}
REDIS_CACHE_DB: {{ include "invoiceninja.redisCacheDatabase" . | quote }}
REDIS_BROADCAST_CONNECTION: {{ include "invoiceninja.redisBroadcastConnection" . | quote }}
REDIS_CACHE_CONNECTION: {{ include "invoiceninja.redisCacheConnection" . | quote }}
REDIS_QUEUE_CONNECTION: {{ include "invoiceninja.redisQueueConnection" . | quote }}
SESSION_CONNECTION: {{ include "invoiceninja.redisSessionConnection" . | quote }}
REQUIRE_HTTPS: {{ .Values.requireHttps | quote }}
TRUSTED_PROXIES: {{ .Values.trustedProxies | quote }}

View File

@@ -1,274 +0,0 @@
apiVersion: apps/v1
kind: Deployment
metadata:
name: {{ include "common.names.fullname" . }}
labels:
{{- include "common.labels.standard" $ | nindent 4 }}
app.kubernetes.io/component: server
{{- if .Values.commonLabels }}
{{- include "common.tplvalues.render" ( dict "value" .Values.commonLabels "context" $ ) | nindent 4 }}
{{- end }}
{{- if .Values.commonAnnotations }}
annotations:
{{- include "common.tplvalues.render" ( dict "value" .Values.commonAnnotations "context" $ ) | nindent 4 }}
{{- end }}
spec:
{{- if not .Values.autoscaling.enabled }}
replicas: {{ .Values.replicaCount }}
{{- end }}
{{- if .Values.updateStrategy }}
strategy: {{- toYaml .Values.updateStrategy | nindent 4 }}
{{- end }}
selector:
matchLabels:
{{- include "common.labels.matchLabels" $ | nindent 6 }}
app.kubernetes.io/component: server
template:
metadata:
{{- if .Values.podAnnotations }}
annotations:
{{- include "common.tplvalues.render" (dict "value" .Values.podAnnotations "context" $) | nindent 8 }}
{{- end }}
labels:
{{- include "common.labels.standard" $ | nindent 8 }}
app.kubernetes.io/component: server
{{- if .Values.podLabels }}
{{- include "common.tplvalues.render" (dict "value" .Values.podLabels "context" $) | nindent 8 }}
{{- end }}
spec:
{{- include "invoiceninja.imagePullSecrets" . | nindent 6 }}
serviceAccountName: {{ include "invoiceninja.serviceAccountName" . }}
{{- if .Values.affinity }}
affinity: {{- include "common.tplvalues.render" (dict "value" .Values.affinity "context" $) | nindent 8 }}
{{- else }}
affinity:
podAffinity: {{- include "common.affinities.pods" (dict "type" .Values.podAffinityPreset "context" $) | nindent 10 }}
podAntiAffinity: {{- include "common.affinities.pods" (dict "type" .Values.podAntiAffinityPreset "context" $) | nindent 10 }}
nodeAffinity: {{- include "common.affinities.nodes" (dict "type" .Values.nodeAffinityPreset.type "key" .Values.nodeAffinityPreset.key "values" .Values.nodeAffinityPreset.values) | nindent 10 }}
{{- end }}
{{- if .Values.nodeSelector }}
nodeSelector: {{- include "common.tplvalues.render" (dict "value" .Values.nodeSelector "context" $) | nindent 8 }}
{{- end }}
{{- if .Values.tolerations }}
tolerations: {{- include "common.tplvalues.render" (dict "value" .Values.tolerations "context" $) | nindent 8 }}
{{- end }}
securityContext:
{{- toYaml .Values.podSecurityContext | nindent 8 }}
initContainers:
- name: wait-db
image: {{ include "invoiceninja.image" . }}
imagePullPolicy: {{ .Values.image.pullPolicy }}
command:
- /bin/sh
- -cx
- |
COUNTER=0;
[[ -z "${DB_HOST1}" ]] || DB_HOST="${DB_HOST1}";
[[ -z "${DB_PORT1}" ]] || DB_PORT="${DB_PORT1}";
while [ $COUNTER -lt 120 ]; do
if mysqladmin ping -h "$DB_HOST" -P $DB_PORT --connect-timeout=15 --silent; then
exit 0;
fi;
let COUNTER=COUNTER+1;
echo "Waiting for DB... Trying again in 2s";
sleep 2;
done;
echo "Did NOT see a database after 240 secs!";
exit 1;
securityContext:
{{- toYaml .Values.containerSecurityContext | nindent 12 }}
{{- if .Values.resources }}
resources: {{- toYaml .Values.resources | nindent 12 }}
{{- end }}
envFrom:
- configMapRef:
name: {{ include "common.names.fullname" . }}
{{- if .Values.extraEnvVarsCM }}
- configMapRef:
name: {{ include "common.tplvalues.render" (dict "value" .Values.extraEnvVarsCM "context" $) }}
{{- end }}
{{- if .Values.extraEnvVarsSecret }}
- secretRef:
name: {{ include "common.tplvalues.render" (dict "value" .Values.extraEnvVarsSecret "context" $) }}
{{- end }}
env:
{{- if .Values.extraEnvVars }}
{{- include "common.tplvalues.render" (dict "value" .Values.extraEnvVars "context" $) | nindent 12 }}
{{- end }}
{{- if and .Values.podSecurityContext .Values.volumePermissions.enabled (or .Values.persistence.public.enabled .Values.persistence.storage.enabled) }}
- name: volume-permissions
image: {{ include "invoiceninja.volumePermissions.image" . }}
imagePullPolicy: {{ .Values.volumePermissions.image.pullPolicy | quote }}
command:
- /bin/bash
- -ec
- |
chown -R {{ .Values.containerSecurityContext.runAsUser }}:{{ .Values.podSecurityContext.fsGroup }} /var/www/app/{public,storage}
securityContext:
runAsUser: 0
{{- if .Values.volumePermissions.resources }}
resources: {{- toYaml .Values.volumePermissions.resources | nindent 12 }}
{{- end }}
volumeMounts:
- mountPath: /var/www/app/public
name: public
- mountPath: /var/www/app/storage
name: storage
{{- end }}
{{- if .Values.initContainers }}
{{- include "common.tplvalues.render" (dict "value" .Values.initContainers "context" $) | nindent 8 }}
{{- end }}
containers:
- name: {{ .Chart.Name }}
securityContext:
{{- toYaml .Values.containerSecurityContext | nindent 12 }}
image: {{ include "invoiceninja.image" . }}
imagePullPolicy: {{ .Values.image.pullPolicy }}
ports:
- name: fastcgi
containerPort: {{ .Values.containerPorts.fastcgi }}
protocol: TCP
{{- if .Values.livenessProbe.enabled }}
livenessProbe:
initialDelaySeconds: {{ .Values.livenessProbe.initialDelaySeconds }}
periodSeconds: {{ .Values.livenessProbe.periodSeconds }}
timeoutSeconds: {{ $.Values.livenessProbe.timeoutSeconds }}
successThreshold: {{ $.Values.livenessProbe.successThreshold }}
failureThreshold: {{ $.Values.livenessProbe.failureThreshold }}
exec:
command:
- pgrep
- php-fpm
{{- end }}
{{- if .Values.readinessProbe.enabled }}
readinessProbe:
initialDelaySeconds: {{ .Values.readinessProbe.initialDelaySeconds }}
periodSeconds: {{ .Values.readinessProbe.periodSeconds }}
timeoutSeconds: {{ $.Values.readinessProbe.timeoutSeconds }}
successThreshold: {{ $.Values.readinessProbe.successThreshold }}
failureThreshold: {{ $.Values.readinessProbe.failureThreshold }}
tcpSocket:
port: {{ .Values.readinessProbe.port }}
{{- end }}
envFrom:
- configMapRef:
name: {{ include "common.names.fullname" . }}
- secretRef:
name: {{ include "invoiceninja.secretName" . }}
{{- if .Values.extraEnvVarsCM }}
- configMapRef:
name: {{ include "common.tplvalues.render" (dict "value" .Values.extraEnvVarsCM "context" $) }}
{{- end }}
{{- if .Values.extraEnvVarsSecret }}
- secretRef:
name: {{ include "common.tplvalues.render" (dict "value" .Values.extraEnvVarsSecret "context" $) }}
{{- end }}
env:
- name: DB_PASSWORD
valueFrom:
secretKeyRef:
name: {{ include "invoiceninja.databaseSecretName" . }}
key: mariadb-password
{{- if or (and .Values.redis.enabled .Values.redis.auth.enabled) (or .Values.externalRedis.password .Values.externalRedis.existingSecret) }}
- name: REDIS_PASSWORD
valueFrom:
secretKeyRef:
name: {{ include "invoiceninja.redisSecretName" . }}
key: redis-password
{{- end }}
{{- if .Values.userEmail }}
- name: IN_USER_EMAIL
value: {{ .Values.userEmail | quote }}
{{- end }}
{{- if .Values.extraEnvVars }}
{{- include "common.tplvalues.render" (dict "value" .Values.extraEnvVars "context" $) | nindent 12 }}
{{- end }}
resources:
{{- toYaml .Values.resources | nindent 12 }}
volumeMounts:
- mountPath: /var/www/app/public
name: public
- mountPath: /var/www/app/storage
name: storage
{{- if .Values.extraVolumeMounts }}
{{- include "common.tplvalues.render" (dict "value" .Values.extraVolumeMounts "context" $) | nindent 12 }}
{{- end }}
{{- if not .Values.nginx.enabled }}
- name: nginx
securityContext:
{{- toYaml .Values.containerSecurityContext | nindent 12 }}
image: {{ include "invoiceninja.nginx.image" . }}
imagePullPolicy: {{ .Values.http.image.pullPolicy }}
ports:
- name: http
containerPort: {{ .Values.http.containerPorts.http }}
- name: https
containerPort: {{ .Values.http.containerPorts.https }}
{{- if .Values.http.livenessProbe.enabled }}
livenessProbe:
initialDelaySeconds: {{ .Values.http.livenessProbe.initialDelaySeconds }}
periodSeconds: {{ .Values.http.livenessProbe.periodSeconds }}
timeoutSeconds: {{ $.Values.http.livenessProbe.timeoutSeconds }}
successThreshold: {{ $.Values.http.livenessProbe.successThreshold }}
failureThreshold: {{ $.Values.http.livenessProbe.failureThreshold }}
tcpSocket:
port: http
{{- end }}
{{- if .Values.http.readinessProbe.enabled }}
readinessProbe:
initialDelaySeconds: {{ .Values.http.readinessProbe.initialDelaySeconds }}
periodSeconds: {{ .Values.http.readinessProbe.periodSeconds }}
timeoutSeconds: {{ $.Values.http.readinessProbe.timeoutSeconds }}
successThreshold: {{ $.Values.http.readinessProbe.successThreshold }}
failureThreshold: {{ $.Values.http.readinessProbe.failureThreshold }}
tcpSocket:
port: http
{{- end }}
envFrom:
{{- if .Values.http.extraEnvVarsCM }}
- configMapRef:
name: {{ include "common.tplvalues.render" (dict "value" .Values.extraEnvVarsCM "context" $) }}
{{- end }}
{{- if .Values.http.extraEnvVarsSecret }}
- secretRef:
name: {{ include "common.tplvalues.render" (dict "value" .Values.extraEnvVarsSecret "context" $) }}
{{- end }}
env:
{{- if .Values.http.extraEnvVars }}
{{- include "common.tplvalues.render" (dict "value" .Values.extraEnvVars "context" $) | nindent 12 }}
{{- end }}
resources:
{{- toYaml .Values.http.resources | nindent 12 }}
volumeMounts:
- mountPath: /opt/bitnami/nginx/conf/server_blocks
name: nginx-server-block
- mountPath: /app
name: public
{{- if .Values.http.extraVolumeMounts }}
{{- include "common.tplvalues.render" (dict "value" .Values.extraVolumeMounts "context" $) | nindent 12 }}
{{- end }}
{{- end }}
volumes:
- name: public
{{- if .Values.persistence.public.enabled }}
persistentVolumeClaim:
claimName: {{ .Values.persistence.public.existingClaim | default (include "invoiceninja.public.storageName" .) }}
{{- else }}
emptyDir: {}
{{ end }}
- name: storage
{{- if .Values.persistence.storage.enabled }}
persistentVolumeClaim:
claimName: {{ .Values.persistence.storage.existingClaim | default (include "invoiceninja.storage.storageName" .) }}
{{- else }}
emptyDir: {}
{{ end }}
{{- if not .Values.nginx.enabled }}
- name: nginx-server-block
configMap:
defaultMode: 420
name: {{ include "invoiceninja.nginx.serverBlockName" . }}
{{- end }}
{{- if .Values.extraVolumes }}
{{- include "common.tplvalues.render" (dict "value" .Values.extraVolumes "context" $) | nindent 8 }}
{{- end }}

View File

@@ -1,35 +0,0 @@
{{- if .Values.autoscaling.enabled }}
apiVersion: autoscaling/v2beta1
kind: HorizontalPodAutoscaler
metadata:
name: {{ include "common.names.fullname" . }}
labels:
{{- include "common.labels.standard" $ | nindent 4 }}
{{- if .Values.commonLabels }}
{{- include "common.tplvalues.render" ( dict "value" .Values.commonLabels "context" $ ) | nindent 4 }}
{{- end }}
{{- if .Values.commonAnnotations }}
annotations:
{{- include "common.tplvalues.render" ( dict "value" .Values.commonAnnotations "context" $ ) | nindent 4 }}
{{- end }}
spec:
scaleTargetRef:
apiVersion: apps/v1
kind: Deployment
name: {{ include "common.names.fullname" . }}
minReplicas: {{ .Values.autoscaling.minReplicas }}
maxReplicas: {{ .Values.autoscaling.maxReplicas }}
metrics:
{{- if .Values.autoscaling.targetCPUUtilizationPercentage }}
- type: Resource
resource:
name: cpu
targetAverageUtilization: {{ .Values.autoscaling.targetCPUUtilizationPercentage }}
{{- end }}
{{- if .Values.autoscaling.targetMemoryUtilizationPercentage }}
- type: Resource
resource:
name: memory
targetAverageUtilization: {{ .Values.autoscaling.targetMemoryUtilizationPercentage }}
{{- end }}
{{- end }}

View File

@@ -1,63 +0,0 @@
{{- if and ( not .Values.nginx.enabled ) .Values.ingress.enabled }}
apiVersion: {{ include "common.capabilities.ingress.apiVersion" . }}
kind: Ingress
metadata:
name: {{ include "common.names.fullname" . }}
namespace: {{ .Release.Namespace | quote }}
labels: {{- include "common.labels.standard" . | nindent 4 }}
{{- if .Values.commonLabels }}
{{- include "common.tplvalues.render" ( dict "value" .Values.commonLabels "context" $ ) | nindent 4 }}
{{- end }}
annotations:
{{- if .Values.ingress.certManager }}
kubernetes.io/tls-acme: "true"
{{- end }}
{{- if .Values.ingress.annotations }}
{{- include "common.tplvalues.render" ( dict "value" .Values.ingress.annotations "context" $ ) | nindent 4 }}
{{- end }}
{{- if .Values.commonAnnotations }}
{{- include "common.tplvalues.render" ( dict "value" .Values.commonAnnotations "context" $ ) | nindent 4 }}
{{- end }}
spec:
{{- if and .Values.ingress.ingressClassName (eq "true" (include "common.ingress.supportsIngressClassname" .)) }}
ingressClassName: {{ .Values.ingress.ingressClassName | quote }}
{{- end }}
rules:
{{- if .Values.ingress.hostname }}
- host: {{ .Values.ingress.hostname | quote }}
http:
paths:
{{- if .Values.ingress.extraPaths }}
{{- toYaml .Values.ingress.extraPaths | nindent 10 }}
{{- end }}
- path: {{ .Values.ingress.path }}
{{- if eq "true" (include "common.ingress.supportsPathType" .) }}
pathType: {{ .Values.ingress.pathType }}
{{- end }}
backend: {{- include "common.ingress.backend" ( dict "serviceName" (include "invoiceninja.http.serviceName" .) "servicePort" "http" "context" $ ) | nindent 14 }}
{{- end }}
{{- range .Values.ingress.extraHosts }}
- host: {{ .name | quote }}
http:
paths:
- path: {{ default "/" .path }}
{{- if eq "true" (include "common.ingress.supportsPathType" $) }}
pathType: {{ default "ImplementationSpecific" .pathType }}
{{- end }}
backend: {{- include "common.ingress.backend" ( dict "serviceName" (include "invoiceninja.http.serviceName" $) "servicePort" "http" "context" $ ) | nindent 14 }}
{{- end }}
{{- if or .Values.ingress.tls .Values.ingress.extraTls }}
tls:
{{- if .Values.ingress.tls }}
- hosts:
- {{ .Values.ingress.hostname | quote }}
{{- range .Values.ingress.extraHosts }}
- {{ .name | quote }}
{{- end }}
secretName: {{ printf "%s-tls" .Values.ingress.hostname }}
{{- end }}
{{- if .Values.ingress.extraTls }}
{{- include "common.tplvalues.render" ( dict "value" .Values.ingress.extraTls "context" $ ) | nindent 4 }}
{{- end }}
{{- end }}
{{- end }}

View File

@@ -1,64 +0,0 @@
{{- if and .Values.persistence.public.enabled (not .Values.persistence.public.existingClaim) }}
kind: PersistentVolumeClaim
apiVersion: v1
metadata:
name: {{ include "invoiceninja.public.storageName" . }}
labels:
{{- include "common.labels.standard" . | nindent 4 }}
{{- if .Values.commonLabels }}
{{- include "common.tplvalues.render" ( dict "value" .Values.commonLabels "context" $ ) | nindent 4 }}
{{- end }}
{{- if .Values.commonAnnotations }}
annotations:
{{- include "common.tplvalues.render" ( dict "value" .Values.commonAnnotations "context" $ ) | nindent 4 }}
{{- end }}
spec:
accessModes:
{{- if not (empty .Values.persistence.public.accessModes) }}
{{- range .Values.persistence.public.accessModes }}
- {{ . | quote }}
{{- end }}
{{- else }}
- {{ .Values.persistence.public.accessMode | quote }}
{{- end }}
resources:
requests:
storage: {{ .Values.persistence.public.size | quote }}
{{- include "invoiceninja.public.storageClass" . | nindent 2 }}
{{- if .Values.persistence.public.dataSource }}
dataSource: {{- include "common.tplvalues.render" ( dict "value" .Values.persistence.public.dataSource "context" $ ) | nindent 4 }}
{{- end }}
{{- end }}
---
{{- if and .Values.persistence.storage.enabled (not .Values.persistence.storage.existingClaim) }}
kind: PersistentVolumeClaim
apiVersion: v1
metadata:
name: {{ include "invoiceninja.storage.storageName" . }}
labels:
{{- include "common.labels.standard" . | nindent 4 }}
{{- if .Values.commonLabels }}
{{- include "common.tplvalues.render" ( dict "value" .Values.commonLabels "context" $ ) | nindent 4 }}
{{- end }}
{{- if .Values.commonAnnotations }}
annotations:
{{- include "common.tplvalues.render" ( dict "value" .Values.commonAnnotations "context" $ ) | nindent 4 }}
{{- end }}
spec:
accessModes:
{{- if not (empty .Values.persistence.storage.accessModes) }}
{{- range .Values.persistence.storage.accessModes }}
- {{ . | quote }}
{{- end }}
{{- else }}
- {{ .Values.persistence.storage.accessMode | quote }}
{{- end }}
resources:
requests:
storage: {{ .Values.persistence.storage.size | quote }}
{{- include "invoiceninja.storage.storageClass" . | nindent 2 }}
{{- if .Values.persistence.storage.dataSource }}
dataSource: {{- include "common.tplvalues.render" ( dict "value" .Values.persistence.storage.dataSource "context" $ ) | nindent 4 }}
{{- end }}
{{- end }}

View File

@@ -1,65 +0,0 @@
{{- if not (or .Values.mariadb.enabled .Values.externalDatabase.existingSecret) }}
apiVersion: v1
kind: Secret
metadata:
name: {{ include "invoiceninja.mariadb.fullname" . }}
labels:
{{- include "common.labels.standard" $ | nindent 4 }}
{{- if .Values.commonLabels }}
{{- include "common.tplvalues.render" ( dict "value" .Values.commonLabels "context" $ ) | nindent 4 }}
{{- end }}
{{- if .Values.commonAnnotations }}
annotations:
{{- include "common.tplvalues.render" ( dict "value" .Values.commonAnnotations "context" $ ) | nindent 4 }}
{{- end }}
type: Opaque
data:
mariadb-password: {{ .Values.externalDatabase.password | b64enc | quote }}
{{- end }}
---
{{- if not (or .Values.redis.enabled .Values.externalDatabase.existingSecret) }}
apiVersion: v1
kind: Secret
metadata:
name: {{ include "invoiceninja.redis.fullname" . }}
labels:
{{- include "common.labels.standard" $ | nindent 4 }}
{{- if .Values.commonLabels }}
{{- include "common.tplvalues.render" ( dict "value" .Values.commonLabels "context" $ ) | nindent 4 }}
{{- end }}
{{- if .Values.commonAnnotations }}
annotations:
{{- include "common.tplvalues.render" ( dict "value" .Values.commonAnnotations "context" $ ) | nindent 4 }}
{{- end }}
type: Opaque
data:
redis-password: {{ .Values.externalRedis.password | b64enc | quote }}
{{- end }}
---
{{- if not .Values.existingSecret }}
apiVersion: v1
kind: Secret
metadata:
name: {{ include "common.names.fullname" . }}
labels:
{{- include "common.labels.standard" $ | nindent 4 }}
{{- if .Values.commonLabels }}
{{- include "common.tplvalues.render" ( dict "value" .Values.commonLabels "context" $ ) | nindent 4 }}
{{- end }}
{{- if .Values.commonAnnotations }}
annotations:
{{- include "common.tplvalues.render" ( dict "value" .Values.commonAnnotations "context" $ ) | nindent 4 }}
{{- end }}
type: Opaque
data:
{{- if not (empty .Values.appKey) }}
APP_KEY: {{ .Values.appKey | b64enc | quote }}
{{- else }}
APP_KEY: {{ randAlphaNum 32 | b64enc | quote }}
{{- end }}
{{- if .Values.userPassword }}
IN_PASSWORD: {{ .Values.userPassword | b64enc | quote }}
{{- end }}
{{- end }}

View File

@@ -1,40 +0,0 @@
apiVersion: v1
kind: ConfigMap
metadata:
name: {{ include "invoiceninja.nginx.serverBlockName" . }}
labels:
{{- include "common.labels.standard" $ | nindent 4 }}
{{- if .Values.commonLabels }}
{{- include "common.tplvalues.render" ( dict "value" .Values.commonLabels "context" $ ) | nindent 4 }}
{{- end }}
{{- if .Values.commonAnnotations }}
annotations:
{{- include "common.tplvalues.render" ( dict "value" .Values.commonAnnotations "context" $ ) | nindent 4 }}
{{- end }}
data:
server-block.conf: |-
server {
listen 8080 default_server;
listen [::]:8080 default_server;
server_name _;
root /app;
index index.php;
location / {
try_files $uri $uri/ /index.php?$query_string;
}
location = /favicon.ico { access_log off; log_not_found off; }
location = /robots.txt { access_log off; log_not_found off; }
location ~ \.php$ {
fastcgi_split_path_info ^(.+\.php)(/.+)$;
fastcgi_pass {{ include "common.names.fullname" . }}:9000;
fastcgi_index index.php;
include fastcgi_params;
fastcgi_param SCRIPT_FILENAME /var/www/app/public$fastcgi_script_name;
fastcgi_buffer_size 16k;
fastcgi_buffers 4 16k;
}
}

View File

@@ -1,47 +0,0 @@
apiVersion: v1
kind: Service
metadata:
name: {{ include "common.names.fullname" . }}
labels:
{{- include "common.labels.standard" $ | nindent 4 }}
{{- if .Values.commonLabels }}
{{- include "common.tplvalues.render" ( dict "value" .Values.commonLabels "context" $ ) | nindent 4 }}
{{- end }}
{{- if or .Values.service.annotations .Values.commonAnnotations }}
annotations:
{{- if .Values.service.annotations }}
{{- include "common.tplvalues.render" ( dict "value" .Values.service.annotations "context" $ ) | nindent 4 }}
{{- end }}
{{- if .Values.commonAnnotations }}
{{- include "common.tplvalues.render" ( dict "value" .Values.commonAnnotations "context" $ ) | nindent 4 }}
{{- end }}
{{- end }}
spec:
type: {{ .Values.service.type }}
{{- if and .Values.service.clusterIP (eq .Values.service.type "ClusterIP") }}
clusterIP: {{ .Values.service.clusterIP }}
{{- end }}
{{- if (or (eq .Values.service.type "LoadBalancer") (eq .Values.service.type "NodePort")) }}
externalTrafficPolicy: {{ .Values.service.externalTrafficPolicy | quote }}
{{- end }}
{{- if (and (eq .Values.service.type "LoadBalancer") .Values.service.loadBalancerSourceRanges) }}
loadBalancerSourceRanges: {{- toYaml . | nindent 4 }}
{{- end }}
{{- if (and (eq .Values.service.type "LoadBalancer") (not (empty .Values.service.loadBalancerIP))) }}
loadBalancerIP: {{ .Values.service.loadBalancerIP }}
{{- end }}
ports:
{{- if not (empty .Values.service.port) }}
- name: fastcgi
port: {{ .Values.service.port }}
protocol: TCP
targetPort: fastcgi
{{- if (and (or (eq .Values.service.type "NodePort") (eq .Values.service.type "LoadBalancer")) (not (empty .Values.service.nodePort))) }}
nodePort: {{ .Values.service.nodePort }}
{{- else if eq .Values.service.type "ClusterIP" }}
nodePort: null
{{- end }}
{{- end }}
selector:
{{- include "common.labels.matchLabels" . | nindent 4 }}
app.kubernetes.io/component: server

View File

@@ -1,20 +0,0 @@
{{- if .Values.serviceAccount.create -}}
apiVersion: v1
kind: ServiceAccount
metadata:
name: {{ include "invoiceninja.serviceAccountName" . }}
labels:
{{- include "common.labels.standard" $ | nindent 4 }}
{{- if .Values.commonLabels }}
{{- include "common.tplvalues.render" ( dict "value" .Values.commonLabels "context" $ ) | nindent 4 }}
{{- end }}
{{- if or .Values.serviceAccount.annotations .Values.commonAnnotations }}
annotations:
{{- if .Values.serviceAccount.annotations }}
{{- include "common.tplvalues.render" ( dict "value" .Values.serviceAccount.annotations "context" $ ) | nindent 4 }}
{{- end }}
{{- if .Values.commonAnnotations }}
{{- include "common.tplvalues.render" ( dict "value" .Values.commonAnnotations "context" $ ) | nindent 4 }}
{{- end }}
{{- end }}
{{- end }}

View File

@@ -1,60 +0,0 @@
{{- if not .Values.nginx.enabled }}
apiVersion: v1
kind: Service
metadata:
name: {{ include "invoiceninja.http.serviceName" . }}
labels:
{{- include "common.labels.standard" $ | nindent 4 }}
{{- if .Values.commonLabels }}
{{- include "common.tplvalues.render" ( dict "value" .Values.commonLabels "context" $ ) | nindent 4 }}
{{- end }}
{{- if or .Values.service.http.annotations .Values.commonAnnotations }}
annotations:
{{- if .Values.service.http.annotations }}
{{- include "common.tplvalues.render" ( dict "value" .Values.service.http.annotations "context" $ ) | nindent 4 }}
{{- end }}
{{- if .Values.commonAnnotations }}
{{- include "common.tplvalues.render" ( dict "value" .Values.commonAnnotations "context" $ ) | nindent 4 }}
{{- end }}
{{- end }}
spec:
type: {{ .Values.service.http.type }}
{{- if and .Values.service.http.clusterIP (eq .Values.service.http.type "ClusterIP") }}
clusterIP: {{ .Values.service.http.clusterIP }}
{{- end }}
{{- if (or (eq .Values.service.http.type "LoadBalancer") (eq .Values.service.http.type "NodePort")) }}
externalTrafficPolicy: {{ .Values.service.http.externalTrafficPolicy | quote }}
{{- end }}
{{- if (and (eq .Values.service.http.type "LoadBalancer") .Values.service.http.loadBalancerSourceRanges) }}
loadBalancerSourceRanges: {{- toYaml . | nindent 4 }}
{{- end }}
{{- if (and (eq .Values.service.http.type "LoadBalancer") (not (empty .Values.service.http.loadBalancerIP))) }}
loadBalancerIP: {{ .Values.service.http.loadBalancerIP }}
{{- end }}
ports:
{{- if not (empty .Values.service.http.ports.http) }}
- name: http
port: {{ .Values.service.http.ports.http }}
protocol: TCP
targetPort: http
{{- if (and (or (eq .Values.service.http.type "NodePort") (eq .Values.service.http.type "LoadBalancer")) (not (empty .Values.service.http.nodePorts.http))) }}
nodePort: {{ .Values.service.http.nodePorts.http }}
{{- else if eq .Values.service.http.type "ClusterIP" }}
nodePort: null
{{- end }}
{{- end }}
{{- if not (empty .Values.service.http.ports.https) }}
- name: https
port: {{ .Values.service.http.ports.https }}
protocol: TCP
targetPort: https
{{- if (and (or (eq .Values.service.http.type "NodePort") (eq .Values.service.http.type "LoadBalancer")) (not (empty .Values.service.http.nodePorts.https))) }}
nodePort: {{ .Values.service.http.nodePorts.https }}
{{- else if eq .Values.service.http.type "ClusterIP" }}
nodePort: null
{{- end }}
{{- end }}
selector:
{{- include "common.labels.matchLabels" . | nindent 4 }}
app.kubernetes.io/component: server
{{- end }}

View File

@@ -1,692 +0,0 @@
# Default values for invoiceninja.
# This is a YAML-formatted file.
# Declare variables to be passed into your templates.
## Global Docker image parameters
## Please, note that this will override the image parameters, including dependencies, configured to use the global value
## Current available global Docker image parameters: imageRegistry, imagePullSecrets and storageClass
##
# global:
# imageRegistry: myRegistryName
# imagePullSecrets:
# - myRegistryKeySecretName
# storageClass: myStorageClass
## Invoice Ninja image version
## ref: https://github.com/invoiceninja/dockerfiles
##
image:
registry: docker.io
repository: invoiceninja/invoiceninja
tag: 5.6.24
## Defaults to 'Always' if image tag is 'latest', else set to 'IfNotPresent'
## ref: http://kubernetes.io/docs/user-guide/images/#pre-pulling-images
##
pullPolicy: IfNotPresent
## Optionally specify an array of imagePullSecrets.
## Secrets must be manually created in the namespace.
## ref: https://kubernetes.io/docs/tasks/configure-pod-container/pull-image-private-registry/
##
# pullSecrets:
# - myRegistryKeySecretName
## String to turn on debug mode in Invoice Ninja
##
debug: false
## A 32 character long Application Key
##
appKey: ""
## Override app URL
##
appURL: ""
## Email of user to create first run
## If not specified, default user email will be "admin@example.com"
##
userEmail: ""
## Password of user to create on first run
## If not specified, default user password will be "changeme!"
##
userPassword: ""
## Name of log channel to use
##
logChannel: ""
## Name of broadcast driver to use
##
broadcastDriver: ""
## Name of cache driver to use
##
cacheDriver: ""
## Name of session driver to use
##
sessionDriver: ""
## Name of queue connection to use
##
queueConnection: ""
## List of trusted proxies for Invoice Ninja to communicate with the nginx proxy
##
trustedProxies: "*"
## Use local or Phantom JS PDF generation
## Options are `snappdf` or `phantom`
##
pdfGenerator: snappdf
## Name of queue connection to use (use "log" for debug)
## Please check the ref below for any other env you may need to define
## ref: https://github.com/invoiceninja/invoiceninja/blob/v5-stable/config/mail.php
##
mailer: log
## Force HTTPS for all connections to Invoice Ninja
##
requireHttps: false
## Name of existing secret containing IN credentials
## NOTE: Must contain key `APP_KEY` and `IN_PASSWORD`
## NOTE: When it's set, the `appKey` and `userPassword` parameter is ignored
##
existingSecret:
## String to partially override fullname template (will maintain the release name)
##
# nameOverride:
## String to fully override fullname template
##
# fullnameOverride:
## Add labels to all the deployed resources
##
commonLabels: {}
## Add annotations to all the deployed resources
##
commonAnnotations: {}
serviceAccount:
# Specifies whether a service account should be created
create: true
# Annotations to add to the service account
annotations: {}
# The name of the service account to use.
# If not set and create is true, a name is generated using the fullname template
name: ""
## Pod Labels
## ref: https://kubernetes.io/docs/concepts/overview/working-with-objects/labels/
##
podLabels: {}
## Pod annotations
## ref: https://kubernetes.io/docs/concepts/overview/working-with-objects/annotations/
##
podAnnotations: {}
## Pod affinity preset
## ref: https://kubernetes.io/docs/concepts/scheduling-eviction/assign-pod-node/#inter-pod-affinity-and-anti-affinity
## Allowed values: soft, hard
##
podAffinityPreset: ""
## Pod anti-affinity preset
## ref: https://kubernetes.io/docs/concepts/scheduling-eviction/assign-pod-node/#inter-pod-affinity-and-anti-affinity
## Allowed values: soft, hard
##
podAntiAffinityPreset: soft
## Node affinity preset
## ref: https://kubernetes.io/docs/concepts/scheduling-eviction/assign-pod-node/#node-affinity
## Allowed values: soft, hard
##
nodeAffinityPreset:
## Node affinity type
## Allowed values: soft, hard
##
type: ""
## Node label key to match
## E.g.
## key: "kubernetes.io/e2e-az-name"
##
key: ""
## Node label values to match
## E.g.
## values:
## - e2e-az1
## - e2e-az2
##
values: []
## Affinity for pod assignment. Evaluated as a template.
## ref: https://kubernetes.io/docs/concepts/configuration/assign-pod-node/#affinity-and-anti-affinity
## Note: podAffinityPreset, podAntiAffinityPreset, and nodeAffinityPreset will be ignored when it's set
##
affinity: {}
## Node labels for pod assignment. Evaluated as a template.
## ref: https://kubernetes.io/docs/user-guide/node-selection/
##
nodeSelector: {}
## Tolerations for pod assignment. Evaluated as a template.
## ref: https://kubernetes.io/docs/concepts/configuration/taint-and-toleration/
##
tolerations: []
## Configure Pods Security Context
## ref: https://kubernetes.io/docs/tasks/configure-pod-container/security-context/#set-the-security-context-for-a-pod
##
podSecurityContext:
fsGroup: 1500
## Configure Container Security Context (only main container)
## ref: https://kubernetes.io/docs/tasks/configure-pod-container/security-context/#set-the-security-context-for-a-container
##
containerSecurityContext:
runAsNonRoot: true
runAsUser: 1500
# runAsGroup: 1500
# capabilities:
# drop:
# - ALL
# readOnlyRootFilesystem: true
## Init containers parameters:
## volumePermissions: Change the owner and group of the persistent volume mountpoint to runAsUser:fsGroup values from the securityContext section.
##
volumePermissions:
enabled: false
image:
registry: docker.io
repository: bitnami/bitnami-shell
tag: "10"
pullPolicy: Always
## Optionally specify an array of imagePullSecrets.
## Secrets must be manually created in the namespace.
## ref: https://kubernetes.io/docs/tasks/configure-pod-container/pull-image-private-registry/
##
# pullSecrets:
# - myRegistryKeySecretName
resources: {}
## Number of replicas (requires ReadWriteMany PVC support)
##
replicaCount: 1
## Set up update strategy for Invoice Ninja installation. Set to Recreate if you use persistent volume that cannot be mounted by more than one pods to makesure the pods is destroyed first.
## ref: https://kubernetes.io/docs/concepts/workloads/controllers/deployment/#strategy
## Example:
## updateStrategy:
## type: RollingUpdate
## rollingUpdate:
## maxSurge: 25%
## maxUnavailable: 25%
##
updateStrategy:
type: RollingUpdate
## Container ports
##
containerPorts:
fastcgi: 9000
## An array to add extra env vars
## Example:
## extraEnvVars:
## - name: FOO
## value: "bar"
##
extraEnvVars: []
## ConfigMap with extra environment variables
##
extraEnvVarsCM:
## Secret with extra environment variables
##
extraEnvVarsSecret:
## Extra volume mounts to add to the container
##
extraVolumeMounts: []
## Configure extra options for liveness and readiness probes
## This applies to all the Invoice Ninja in the cluster
## ref: https://kubernetes.io/docs/tasks/configure-pod-container/configure-liveness-readiness-probes/#configure-probes)
##
livenessProbe:
enabled: true
initialDelaySeconds: 120
periodSeconds: 10
timeoutSeconds: 5
failureThreshold: 6
successThreshold: 1
readinessProbe:
enabled: true
initialDelaySeconds: 15
periodSeconds: 10
timeoutSeconds: 5
failureThreshold: 6
successThreshold: 1
port: fastcgi
resources:
{}
# We usually recommend not to specify default resources and to leave this as a conscious
# choice for the user. This also increases chances charts run on environments with little
# resources, such as Minikube. If you do want to specify resources, uncomment the following
# lines, adjust them as necessary, and remove the curly braces after 'resources:'.
# limits:
# cpu: 100m
# memory: 128Mi
# requests:
# cpu: 100m
# memory: 128Mi
## Inline http server (this is enabled only if nginx sub chart is disabled).
##
http:
image:
registry: docker.io
repository: bitnami/nginx
tag: 1.22.1-debian-11-r21
## Defaults to 'Always' if image tag is 'latest', else set to 'IfNotPresent'
## ref: http://kubernetes.io/docs/user-guide/images/#pre-pulling-images
##
pullPolicy: IfNotPresent
## Optionally specify an array of imagePullSecrets.
## Secrets must be manually created in the namespace.
## ref: https://kubernetes.io/docs/tasks/configure-pod-container/pull-image-private-registry/
##
# pullSecrets:
# - myRegistryKeySecretName
## Container ports
##
containerPorts:
http: 8080
https: 8443
## An array to add extra env vars
## Example:
## extraEnvVars:
## - name: FOO
## value: "bar"
##
extraEnvVars: []
## ConfigMap with extra environment variables
##
extraEnvVarsCM:
## Secret with extra environment variables
##
extraEnvVarsSecret:
## Extra volume mounts to add to the container
##
extraVolumeMounts: []
## Configure extra options for liveness and readiness probes
## This applies to all the web server in the cluster
## ref: https://kubernetes.io/docs/tasks/configure-pod-container/configure-liveness-readiness-probes/#configure-probes)
##
livenessProbe:
enabled: true
initialDelaySeconds: 10
periodSeconds: 10
timeoutSeconds: 5
failureThreshold: 6
successThreshold: 1
readinessProbe:
enabled: true
initialDelaySeconds: 15
periodSeconds: 10
timeoutSeconds: 5
failureThreshold: 6
successThreshold: 1
resources:
{}
# We usually recommend not to specify default resources and to leave this as a conscious
# choice for the user. This also increases chances charts run on environments with little
# resources, such as Minikube. If you do want to specify resources, uncomment the following
# lines, adjust them as necessary, and remove the curly braces after 'resources:'.
# limits:
# cpu: 100m
# memory: 128Mi
# requests:
# cpu: 100m
# memory: 128Mi
## Extra volumes to add to the deployment
##
extraVolumes: []
## Kubernetes service type
## ref: https://kubernetes.io/docs/concepts/services-networking/service/
## Set this to NodePort, LoadBalancer or ClusterIP
##
service:
## Service type
## ref: https://kubernetes.io/docs/concepts/services-networking/service/#publishing-services-service-types
##
type: ClusterIP
## Service ports
##
port: 9000
## Specify the nodePort value for the LoadBalancer and NodePort service types.
## ref: https://kubernetes.io/docs/concepts/services-networking/service/#type-nodeport
##
nodePort: ""
## Service clusterIP.
##
# clusterIP: None
## Specify the loadBalancerIP value for LoadBalancer service types.
## ref: https://kubernetes.io/docs/concepts/services-networking/service/#loadbalancer
##
# loadBalancerIP:
## Specify the loadBalancerSourceRanges value for LoadBalancer service types.
## ref: https://kubernetes.io/docs/tasks/access-application-cluster/configure-cloud-provider-firewall/#restrict-access-for-loadbalancer-service
##
loadBalancerSourceRanges: []
## Enable client source IP preservation
## ref http://kubernetes.io/docs/tasks/access-application-cluster/create-external-load-balancer/#preserving-the-client-source-ip
##
externalTrafficPolicy: Cluster
## Additional service annotations (evaluate as a template)
## ref: https://kubernetes.io/docs/concepts/overview/working-with-objects/annotations/
##
annotations: {}
## Service for http server
##
http:
## Service type
## ref: https://kubernetes.io/docs/concepts/services-networking/service/#publishing-services-service-types
##
type: ClusterIP
## Service ports
##
ports:
http: 8080
https: 8443
## Specify the nodePort value for the LoadBalancer and NodePort service types.
## ref: https://kubernetes.io/docs/concepts/services-networking/service/#type-nodeport
##
nodePorts:
http: ""
https: ""
## Service clusterIP.
##
# clusterIP: None
## Specify the loadBalancerIP value for LoadBalancer service types.
## ref: https://kubernetes.io/docs/concepts/services-networking/service/#loadbalancer
##
# loadBalancerIP:
## Specify the loadBalancerSourceRanges value for LoadBalancer service types.
## ref: https://kubernetes.io/docs/tasks/access-application-cluster/configure-cloud-provider-firewall/#restrict-access-for-loadbalancer-service
##
loadBalancerSourceRanges: []
## Enable client source IP preservation
## ref http://kubernetes.io/docs/tasks/access-application-cluster/create-external-load-balancer/#preserving-the-client-source-ip
##
externalTrafficPolicy: Cluster
## Additional service annotations (evaluate as a template)
## ref: https://kubernetes.io/docs/concepts/overview/working-with-objects/annotations/
##
annotations: {}
## Configure the ingress resource to access IN (this is enabled only if nginx sub chart is disabled).
## ref: https://kubernetes.io/docs/concepts/services-networking/ingress/
##
ingress:
## Enable ingress
##
enabled: true
## Add the corresponding annotations for cert-manager integration
##
certManager: false
## Ingress path type
##
pathType: ImplementationSpecific
## Force Ingress API version (automatically detected if not set)
##
apiVersion:
## IngressClass that will be be used to implement the Ingress (Kubernetes 1.18+)
## This is supported in Kubernetes 1.18+ and required if you have more than one IngressClass marked as the default for your cluster .
## ref: https://kubernetes.io/blog/2020/04/02/improvements-to-the-ingress-api-in-kubernetes-1.18/
##
ingressClassName:
## Default host for the ingress record
##
hostname: invoiceninja.local
## Default path for the ingress record
## NOTE: You may need to set this to '/*' in order to use this with ALB ingress controllers
##
path: /
## Additional custom annotations for the ingress record
## NOTE: If `ingress.certManager=true`, annotation `kubernetes.io/tls-acme: "true"` will automatically be added
##
annotations: {}
## Enable TLS configuration for the host defined at `ingress.hostname` parameter
## TLS certificates will be retrieved from a TLS secret with name: `{{- printf "%s-tls" .Values.ingress.hostname }}`
## You can:
## - Use the `ingress.secrets` parameter to create this TLS secret
## - Relay on cert-manager to create it by setting `ingress.certManager=true`
## - Relay on Helm to create self-signed certificates by setting `ingress.tls=true` and `ingress.certManager=false`
##
tls: false
## An array with additional hostname(s) to be covered with the ingress record
## e.g:
## extraHosts:
## - name: invoiceninja.local
## path: /
##
extraHosts: []
## An array with additional arbitrary paths that may need to be added to the ingress under the main host
## e.g:
## extraPaths:
## - path: /*
## backend:
## serviceName: ssl-redirect
## servicePort: use-annotation
##
extraPaths: []
## TLS configuration for additional hostname(s) to be covered with this ingress record
## ref: https://kubernetes.io/docs/concepts/services-networking/ingress/#tls
## e.g:
## extraTls:
## - hosts:
## - invoiceninja.local
## secretName: invoiceninja.local-tls
##
extraTls: []
## Custom TLS certificates as secrets
## NOTE: 'key' and 'certificate' are expected in PEM format
## NOTE: 'name' should line up with a 'secretName' set further up
## If it is not set and you're using cert-manager, this is unneeded, as it will create a secret for you with valid certificates
## If it is not set and you're NOT using cert-manager either, self-signed certificates will be created valid for 365 days
## It is also possible to create and manage the certificates outside of this helm chart
## Please see README.md for more information
## e.g:
## secrets:
## - name: invoiceninja.local-tls
## key: |-
## -----BEGIN RSA PRIVATE KEY-----
## ...
## -----END RSA PRIVATE KEY-----
## certificate: |-
## -----BEGIN CERTIFICATE-----
## ...
## -----END CERTIFICATE-----
##
secrets: []
## Enable persistence using Persistent Volume Claims
## ref: http://kubernetes.io/docs/user-guide/persistent-volumes/
##
persistence:
public:
enabled: true
## Invoice Ninja data Persistent Volume Storage Class
## If defined, storageClassName: <storageClass>
## If set to "-", storageClassName: "", which disables dynamic provisioning
## If undefined (the default) or set to null, no storageClassName spec is
## set, choosing the default provisioner. (gp2 on AWS, standard on
## GKE, AWS & OpenStack)
##
# storageClass: "-"
##
## If you want to reuse an existing claim, you can pass the name of the PVC using
## the existingClaim variable
# existingClaim: your-claim
accessMode: ReadWriteOnce
size: 1Gi
## Custom dataSource
##
dataSource: {}
storage:
## Only required when using FILE cache or session driver
enabled: false
## Invoice Ninja data Persistent Volume Storage Class
## If defined, storageClassName: <storageClass>
## If set to "-", storageClassName: "", which disables dynamic provisioning
## If undefined (the default) or set to null, no storageClassName spec is
## set, choosing the default provisioner. (gp2 on AWS, standard on
## GKE, AWS & OpenStack)
##
# storageClass: "-"
##
## If you want to reuse an existing claim, you can pass the name of the PVC using
## the existingClaim variable
# existingClaim: your-claim
accessMode: ReadWriteMany
size: 10Gi
## Custom dataSource
##
dataSource: {}
autoscaling:
enabled: false
minReplicas: 1
maxReplicas: 10
targetCPUUtilizationPercentage: 80
# targetMemoryUtilizationPercentage: 80
## Redis chart configuration
## ref: https://github.com/bitnami/charts/blob/master/bitnami/redis/values.yaml
##
redis:
enabled: true
auth:
sentinel: false
sentinel:
enabled: true
quorum: 1
replica:
replicaCount: 1
## External Redis Configuration
##
## All of these values are only used when redis.enabled is set to false
##
externalRedis:
## Redis/Sentinel host
##
host: ""
## Redis/Sentinel port number
##
port: 6379
## Redis password
##
password: ""
## Use existing secret (ignores previous password)
## must contain key `redis-password`
## NOTE: When it's set, the `externalRedis.password` parameter is ignored
##
# existingSecret:
## Whether Redis Sentinel are used
sentinel: false
## Redis databases
##
databases:
default: "0"
cache: "1"
## MariaDB chart configuration
## ref: https://github.com/bitnami/charts/blob/master/bitnami/mariadb/values.yaml
##
mariadb:
## Whether to deploy a MariaDB server to satisfy the applications database requirements.
## To use an external database set this to false and configure the externaldb parameters
##
enabled: true
## MariaDB Authentication parameters
##
auth:
## MariaDB root password
##
# rootPassword: changeit
## MariaDB custom user and database
##
username: invoiceninja
database: invoiceninja
# password: changeit
## External Database Configuration
##
## All of these values are only used when mariadb.enabled is set to false
##
externalDatabase:
## Database host
##
host: ""
## non-root Username for Invoice Ninja Database
##
user: invoiceninja
## Database password
##
password: ""
## Database name
##
database: invoiceninja
## Database port number
##
port: 3306
## Use existing secret (ignores previous password)
## must contain key `mariadb-password`
## NOTE: When it's set, the `externalDatabase.password` parameter is ignored
##
# existingSecret:
## Nginx chart configuration
## ref: https://github.com/bitnami/charts/blob/master/bitnami/nginx/values.yaml
##
nginx:
enabled: false
service:
## Service type
## ref: https://kubernetes.io/docs/concepts/services-networking/service/#publishing-services-service-types
##
type: ClusterIP
## Configure the ingress resource that allows you to access the Invoice Ninja
## ref: http://kubernetes.io/docs/user-guide/ingress/
##
ingress:
enabled: true
hostname: invoiceninja.local
## Use the serverblock config map from Invoice Ninja
##
existingServerBlockConfigmap: '{{ include "invoiceninja.nginx.serverBlockName" . }}'
## Use the public PVC created by Invoice Ninja
##
staticSitePVC: '{{ include "invoiceninja.public.storageName" . }}'

View File

@@ -1,6 +0,0 @@
{$APP_URL} {
root * /var/www/app/public
php_fastcgi app:9000
encode zstd gzip
file_server browse
}

View File

@@ -1,3 +0,0 @@
#!/usr/bin/env sh
cd /var/www/app; php artisan schedule:run >> /dev/null 2>&1

View File

@@ -1 +0,0 @@
192.168.0.124 in5.test

View File

@@ -1,12 +0,0 @@
FROM mysql:8
# When running on ARM64 use MariaDB instead of MySQL
#FROM mariadb:10.4
ENV force_color_prompt yes
RUN apt-get update;
RUN apt-get install -y cron;
ENTRYPOINT \
service cron start; \
printenv | grep -v "no_proxy" >> /etc/environment; \
docker-entrypoint.sh mysqld

View File

@@ -1,28 +0,0 @@
#!/bin/sh
FREQUENTY=`basename "$0"`
TIMESTAMP=$(date +"%Y-%m-%d")
case $FREQUENTY in
daily)
DAYS=6
;;
weekly)
DAYS=30
find /backups -type f -name $TIMESTAMP-daily.sql.gz -delete
;;
monthly)
DAYS=122
find /backups -type f -name $TIMESTAMP-weekly.sql.gz -delete
;;
esac
mysqldump -u ${MYSQL_USER} -p${MYSQL_PASSWORD} ${MYSQL_DATABASE} | gzip > /backups/$TIMESTAMP-$FREQUENTY.sql.gz
# Remove old backups
find /backups -mtime +${DAYS} -type f -name *-$FREQUENTY.sql.gz -delete
exit 0;

View File

@@ -1,34 +0,0 @@
server {
listen 80 default_server;
server_name _;
server_tokens off;
client_max_body_size 100M;
root /var/www/app/public/;
index index.php;
location / {
try_files $uri $uri/ /index.php?$query_string;
}
location = /favicon.ico { access_log off; log_not_found off; }
location = /robots.txt { access_log off; log_not_found off; }
location ~* /storage/.*\.php$ {
return 503;
}
location ~ \.php$ {
fastcgi_split_path_info ^(.+\.php)(/.+)$;
fastcgi_pass app:9000;
fastcgi_index index.php;
include fastcgi_params;
fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
fastcgi_intercept_errors off;
fastcgi_buffer_size 16k;
fastcgi_buffers 4 16k;
}
}

View File

@@ -1,18 +0,0 @@
session.auto_start = Off
short_open_tag = Off
error_reporting = E_ALL & ~E_NOTICE & ~E_WARNING & ~E_STRICT & ~E_DEPRECATED
; opcache.enable_cli=1
; opcache.fast_shutdown=1
; opcache.memory_consumption=256
; opcache.interned_strings_buffer=8
; opcache.max_accelerated_files=4000
; opcache.revalidate_freq=60
; # http://symfony.com/doc/current/performance.html
; realpath_cache_size = 4096K
; realpath_cache_ttl = 600
memory_limit = 2G
post_max_size = 60M
upload_max_filesize = 50M

View File

@@ -1,21 +0,0 @@
session.auto_start = Off
short_open_tag = Off
error_reporting = E_ALL & ~E_NOTICE & ~E_WARNING & ~E_STRICT & ~E_DEPRECATED
; opcache.enable=1
; opcache.preload=/var/www/app/preload.php
; opcache.preload_user=www-data
; ; The OPcache shared memory storage size.
; opcache.max_accelerated_files=300000
; opcache.validate_timestamps=1
; opcache.revalidate_freq=30
; opcache.jit_buffer_size=256M
; opcache.jit=1205
; opcache.memory_consumption=1024M
post_max_size = 60M
upload_max_filesize = 50M
memory_limit=512M

35
env → debian/.env vendored
View File

@@ -1,6 +1,7 @@
# IN application vars
APP_URL=http://in.localhost:8003
APP_KEY=<insert your generated key in here>
APP_URL=http://localhost:8012
APP_KEY=base64:RR++yx2rJ9kdxbdh3+AmbHLDQu+Q76i++co9Y8ybbno=
APP_ENV=production
APP_DEBUG=true
REQUIRE_HTTPS=false
PHANTOMJS_PDF_GENERATION=false
@@ -8,21 +9,31 @@ PDF_GENERATOR=snappdf
TRUSTED_PROXIES='*'
QUEUE_CONNECTION=database
CACHE_DRIVER=redis
QUEUE_CONNECTION=redis
SESSION_DRIVER=redis
REDIS_HOST=redis
REDIS_PASSWORD=null
REDIS_PORT=6379
FILESYSTEM_DISK=debian_docker
# DB connection
DB_HOST=db
DB_HOST=mysql
DB_PORT=3306
DB_DATABASE=ninja
DB_USERNAME=ninja
DB_PASSWORD=ninja
DB_ROOT_PASSWORD=ninjaAdm1nPassword
DB_CONNECTION=mysql
# Create initial user
# Default to these values if empty
# IN_USER_EMAIL=admin@example.com
# IN_PASSWORD=changeme!
IN_USER_EMAIL=
IN_PASSWORD=
IN_USER_EMAIL=admin@example.com
IN_PASSWORD=changeme!
# IN_USER_EMAIL=
# IN_PASSWORD=
# Mail options
MAIL_MAILER=log
@@ -44,6 +55,8 @@ MYSQL_DATABASE=ninja
NORDIGEN_SECRET_ID=
NORDIGEN_SECRET_KEY=
# V4 env vars
# DB_STRICT=false
# APP_CIPHER=AES-256-CBC
IS_DOCKER=true
SCOUT_DRIVER=null
#SNAPPDF_CHROMIUM_PATH=/usr/bin/google-chrome-stable

89
debian/Dockerfile vendored Normal file
View File

@@ -0,0 +1,89 @@
ARG PHP=8.4
FROM php:${PHP}-fpm AS prepare-app
USER www-data
RUN curl -sL "https://github.com/invoiceninja/invoiceninja/releases/latest/download/invoiceninja.tar.gz" | \
tar -xz -C /var/www/html \
&& ln -s /var/www/html/resources/views/react/index.blade.php /var/www/html/public/index.html \
&& php artisan storage:link \
# Workaround for application updates
&& mv /var/www/html/public /tmp/public
# ==================
# InvoiceNinja image
# ==================
FROM php:${PHP}-fpm
# PHP modules
ARG php_require="bcmath gd mbstring pdo_mysql zip"
ARG php_suggest="exif imagick intl pcntl saxon soap"
ARG php_extra="opcache"
# Install system dependencies
RUN apt-get update && apt-get install -y --no-install-recommends \
libfcgi-bin \
mariadb-client \
gpg \
supervisor \
# Unicode support for PDF
fonts-noto-cjk-extra \
fonts-wqy-microhei \
fonts-wqy-zenhei \
xfonts-wqy \
# Install google-chrome-stable(amd64)/chromium(arm64)
&& if [ "$(dpkg --print-architecture)" = "amd64" ]; then \
mkdir -p /etc/apt/keyrings \
&& curl -fsSL https://dl.google.com/linux/linux_signing_key.pub | \
gpg --dearmor -o /etc/apt/keyrings/google.gpg \
&& echo "deb [arch=amd64 signed-by=/etc/apt/keyrings/google.gpg] https://dl.google.com/linux/chrome/deb/ stable main" > /etc/apt/sources.list.d/google-chrome.list \
&& apt-get update \
&& apt-get install -y --no-install-recommends google-chrome-stable; \
elif [ "$(dpkg --print-architecture)" = "arm64" ]; then \
apt-get install -y --no-install-recommends \
chromium; \
fi \
# Create config directory for chromium/google-chrome-stable
&& mkdir /var/www/.config \
&& chown www-data:www-data /var/www/.config \
# Cleanup
&& apt-get purge -y gpg \
&& apt-get autoremove -y \
&& apt-get clean \
&& rm -rf /var/lib/apt/lists/*
# Install PHP extensions
COPY --from=ghcr.io/mlocati/php-extension-installer /usr/bin/install-php-extensions /usr/local/bin/
RUN install-php-extensions \
${php_require} \
${php_suggest} \
${php_extra}
# Configure PHP
RUN ln -s "$PHP_INI_DIR/php.ini-production" "$PHP_INI_DIR/php.ini"
COPY php/php.ini /usr/local/etc/php/conf.d/invoiceninja.ini
COPY php/php-fpm.conf /usr/local/etc/php-fpm.d/invoiceninja.conf
# Workaround: Disable SSL for mariadb-client for compatibility with MySQL
RUN echo "skip-ssl = true" >> /etc/mysql/mariadb.conf.d/50-client.cnf
# Setup supervisor
COPY supervisor/supervisord.conf /etc/supervisor/conf.d/supervisord.conf
# Setup InvoiceNinja
COPY --from=prepare-app /var/www/html /var/www/html
COPY --from=prepare-app /tmp/public /tmp/public
# Add initialization script
COPY --chmod=0755 scripts/init.sh /usr/local/bin/init.sh
# Health check
HEALTHCHECK --start-period=10s \
CMD REMOTE_ADDR=127.0.0.1 REQUEST_URI=/health REQUEST_METHOD=GET SCRIPT_FILENAME=/var/www/html/public/index.php cgi-fcgi -bind -connect 127.0.0.1:9000 | grep '{"status":"ok","message":"API is healthy"}'
ENTRYPOINT ["/usr/local/bin/init.sh"]
CMD ["supervisord", "-c", "/etc/supervisor/supervisord.conf"]

93
debian/docker-compose.yml vendored Normal file
View File

@@ -0,0 +1,93 @@
x-logging: &default-logging
options:
max-size: "10m"
max-file: "3"
driver: json-file
services:
app:
build:
context: .
image: invoiceninja/invoiceninja-debian:${TAG:-latest}
restart: unless-stopped
env_file:
- ./.env
volumes:
- ./.env:/var/www/html/.env
# - ./php/php.ini:/usr/local/etc/php/conf.d/invoiceninja.ini:ro
# - ./php/php-fpm.conf:/usr/local/etc/php-fpm.d/invoiceninja.conf:ro
# - ./supervisor/supervisord.conf:/etc/supervisor/conf.d/supervisord.conf:ro
- app_public:/var/www/html/public
- app_storage:/var/www/html/storage
networks:
- app-network
depends_on:
mysql:
condition: service_healthy
redis:
condition: service_healthy
logging: *default-logging
nginx:
image: nginx:alpine
restart: unless-stopped
ports:
- "80:80"
volumes:
- ./nginx:/etc/nginx/conf.d:ro
- app_public:/var/www/html/public:ro
- app_storage:/var/www/html/storage:ro
networks:
- app-network
depends_on:
- app
logging: *default-logging
mysql:
image: mysql:8
restart: unless-stopped
env_file:
- ./.env
environment:
MYSQL_DATABASE: ${DB_DATABASE}
MYSQL_USER: ${DB_USERNAME}
MYSQL_PASSWORD: ${DB_PASSWORD}
MYSQL_ROOT_PASSWORD: ${DB_ROOT_PASSWORD}
volumes:
- mysql_data:/var/lib/mysql
networks:
- app-network
healthcheck:
test: [ "CMD", "mysqladmin", "ping", "-h", "localhost", "-u${MYSQL_USER}", "-p${MYSQL_PASSWORD}" ]
interval: 10s
timeout: 5s
retries: 5
logging: *default-logging
redis:
image: redis:alpine
restart: unless-stopped
volumes:
- redis_data:/data
networks:
- app-network
healthcheck:
test: [ "CMD", "redis-cli", "ping" ]
interval: 10s
timeout: 5s
retries: 5
logging: *default-logging
networks:
app-network:
driver: bridge
volumes:
app_public:
driver: local
app_storage:
driver: local
mysql_data:
driver: local
redis_data:
driver: local

14
debian/nginx/invoiceninja.conf vendored Normal file
View File

@@ -0,0 +1,14 @@
# https://nginx.org/en/docs/http/ngx_http_core_module.html
client_max_body_size 10M;
client_body_buffer_size 10M;
server_tokens off;
# https://nginx.org/en/docs/http/ngx_http_fastcgi_module.html
fastcgi_buffers 32 16K;
# https://nginx.org/en/docs/http/ngx_http_gzip_module.html
gzip on;
gzip_comp_level 2;
gzip_min_length 1M;
gzip_proxied any;
gzip_types *;

32
debian/nginx/laravel.conf vendored Normal file
View File

@@ -0,0 +1,32 @@
# https://laravel.com/docs/master/deployment#nginx
server {
listen 80 default_server;
server_name _;
root /var/www/html/public;
add_header X-Frame-Options "SAMEORIGIN";
add_header X-Content-Type-Options "nosniff";
index index.php;
charset utf-8;
location / {
try_files $uri $uri/ /index.php?$query_string;
}
location = /favicon.ico { access_log off; log_not_found off; }
location = /robots.txt { access_log off; log_not_found off; }
error_page 404 /index.php;
location ~ \.php$ {
fastcgi_pass app:9000;
fastcgi_param SCRIPT_FILENAME $realpath_root$fastcgi_script_name;
include fastcgi_params;
}
location ~ /\.(?!well-known).* {
deny all;
}
}

1
debian/php/php-fpm.conf vendored Normal file
View File

@@ -0,0 +1 @@
pm.max_children = 10

23
debian/php/php.ini vendored Normal file
View File

@@ -0,0 +1,23 @@
[core]
; https://www.php.net/manual/en/ini.core.php
post_max_size=10M
upload_max_filesize=10M
[opcache]
; https://www.php.net/manual/en/opcache.installation.php#opcache.installation.recommended
opcache.enable_cli=1
[jit]
; https://wiki.php.net/rfc/jit_config_defaults
opcache.jit=tracing
opcache.jit_buffer_size=64M
[extra]
; http://symfony.com/doc/current/performance.html
opcache.memory_consumption=256
opcache.max_accelerated_files=20000
opcache.preload=/var/www/html/preload.php
opcache.preload_user=www-data
opcache.validate_timestamps=0
realpath_cache_size = 4096K
realpath_cache_ttl = 600

67
debian/scripts/init.sh vendored Executable file
View File

@@ -0,0 +1,67 @@
#!/bin/sh -eu
# Set PDF generation browser path based on architecture
if [ "$(dpkg --print-architecture)" = "amd64" ]; then
export SNAPPDF_CHROMIUM_PATH=/usr/bin/google-chrome-stable
elif [ "$(dpkg --print-architecture)" = "arm64" ]; then
export SNAPPDF_CHROMIUM_PATH=/usr/bin/chromium
fi
if [ "$*" = 'supervisord -c /etc/supervisor/supervisord.conf' ]; then
# Check for required folders and create if needed
[ -d /var/www/html/storage/framework/sessions ] || mkdir -p /var/www/html/storage/framework/sessions
[ -d /var/www/html/storage/framework/views ] || mkdir -p /var/www/html/storage/framework/views
[ -d /var/www/html/storage/framework/cache ] || mkdir -p /var/www/html/storage/framework/cache
# Workaround for application updates
if [ "$(ls -A /tmp/public)" ]; then
echo "Updating public folder..."
rm -rf /var/www/html/public/.htaccess \
/var/www/html/public/.well-known \
/var/www/html/public/*
mv /tmp/public/* \
/tmp/public/.htaccess \
/tmp/public/.well-known \
/var/www/html/public/
fi
echo "Public Folder is up to date"
# Ensure owner, file and directory permissions are correct
chown -R www-data:www-data \
/var/www/html/public \
/var/www/html/storage
find /var/www/html/public \
/var/www/html/storage \
-type f -exec chmod 644 {} \;
find /var/www/html/public \
/var/www/html/storage \
-type d -exec chmod 755 {} \;
# Clear and cache config in production
if [ "$APP_ENV" = "production" ]; then
runuser -u www-data -- php artisan optimize
runuser -u www-data -- php artisan package:discover
runuser -u www-data -- php artisan migrate --force
# If first IN run, it needs to be initialized
if [ "$(php -d opcache.preload='' artisan tinker --execute='echo Schema::hasTable("accounts") && !App\Models\Account::all()->first();')" = "1" ]; then
echo "Running initialization..."
php artisan db:seed --force
if [ -n "${IN_USER_EMAIL}" ] && [ -n "${IN_PASSWORD}" ]; then
php artisan ninja:create-account --email "${IN_USER_EMAIL}" --password "${IN_PASSWORD}"
else
echo "Initialization failed - Set IN_USER_EMAIL and IN_PASSWORD in .env"
exit 1
fi
fi
echo "Production setup completed"
fi
echo "Starting supervisord..."
fi
exec "$@"

39
debian/supervisor/supervisord.conf vendored Normal file
View File

@@ -0,0 +1,39 @@
[supervisord]
nodaemon=true
user=root
logfile=/dev/null
logfile_maxbytes=0
pidfile=/var/run/supervisord.pid
[program:php-fpm]
command=/usr/local/sbin/php-fpm -F
autostart=true
autorestart=true
priority=5
stdout_logfile=/dev/fd/1
stdout_logfile_maxbytes=0
redirect_stderr=true
[program:queue-worker]
process_name=%(program_name)s_%(process_num)02d
command=php /var/www/html/artisan queue:work --sleep=3 --tries=3 --max-time=3600 --verbose
autostart=true
autorestart=true
stopasgroup=true
killasgroup=true
user=www-data
numprocs=2
environment=HOME="/var/www"
stdout_logfile=/dev/fd/1
stdout_logfile_maxbytes=0
redirect_stderr=true
stopwaitsecs=3600
[program:scheduler]
command=php /var/www/html/artisan schedule:work --verbose
autostart=true
autorestart=true
user=www-data
stdout_logfile=/dev/fd/1
stdout_logfile_maxbytes=0
redirect_stderr=true

View File

@@ -1,87 +0,0 @@
version: '3.7'
services:
server:
image: nginx
restart: always
env_file: env
volumes:
# Vhost configuration
#- ./config/caddy/Caddyfile:/etc/caddy/Caddyfiledocker-com
- ./config/nginx/in-vhost.conf:/etc/nginx/conf.d/in-vhost.conf:ro
- ./docker/app/public:/var/www/app/public:ro
depends_on:
- app
# Run webserver nginx on port 80
# Feel free to modify depending what port is already occupied
ports:
- "80:80"
#- "443:443"
networks:
- invoiceninja
extra_hosts:
- "in5.localhost:192.168.0.124 " #host and ip
app:
image: invoiceninja/invoiceninja:5
env_file: env
restart: always
volumes:
- ./config/hosts:/etc/hosts:ro
- ./docker/app/public:/var/www/app/public:rw,delegated
- ./docker/app/storage:/var/www/app/storage:rw,delegated
- ./config/php/php.ini:/usr/local/etc/php/php.ini
- ./config/php/php-cli.ini:/usr/local/etc/php/php-cli.ini
depends_on:
- db
networks:
- invoiceninja
extra_hosts:
- "in5.localhost:192.168.0.124 " #host and ip
db:
image: mysql:8
# When running on ARM64 use MariaDB instead of MySQL
# image: mariadb:10.4
# For auto DB backups comment out image and use the build block below
# build:
# context: ./config/mysql
restart: always
env_file: env
volumes:
- ./docker/mysql/data:/var/lib/mysql:rw,delegated
# remove comments for next 4 lines if you want auto sql backups
#- ./docker/mysql/bak:/backups:rw
#- ./config/mysql/backup-script:/etc/cron.daily/daily:ro
#- ./config/mysql/backup-script:/etc/cron.weekly/weekly:ro
#- ./config/mysql/backup-script:/etc/cron.monthly/monthly:ro
networks:
- invoiceninja
extra_hosts:
- "in5.localhost:192.168.0.124 " #host and ip
# THIS IS ONLY A VALID CONFIGURATION FOR IN 4. DO NOT USE FOR IN 5.
# cron:
# image: invoiceninja/invoiceninja:alpine-4
# volumes:
# - ./docker/app/public:/var/www/app/public:rw,delegated
# - ./docker/app/storage:/var/www/app/storage:rw,delegated
# - ./docker/app/public/logo:/var/www/app/public/logo:rw,delegated
# entrypoint: |
# /bin/sh -c 'sh -s <<EOF
# trap "break;exit" SIGHUP SIGINT SIGTERM
# sleep 300s
# while /bin/true; do
# ./artisan ninja:send-invoices
# ./artisan ninja:send-reminders
# sleep 1d
# done
# EOF'
# networks:
# - invoiceninja
#
networks:
invoiceninja:

View File

@@ -1,13 +0,0 @@
FROM invoiceninja/invoiceninja:5
USER root
RUN apk add --no-cache supervisor \
&& mkdir /var/log/supervisord /var/run/supervisord \
&& chown $INVOICENINJA_USER:www-data /var/log/supervisord /var/run/supervisord
COPY supervisord.conf /
USER $INVOICENINJA_USER
CMD ["/usr/bin/supervisord", "-c", "/supervisord.conf"]

View File

@@ -1,29 +0,0 @@
[supervisord]
nodaemon=true
user=invoiceninja
pidfile=/var/run/supervisord/supervisord.pid
logfile=/dev/null ; nodaemon will cause logs to go to stdout
logfile_maxbytes=0
loglevel=error
[program:php-fpm]
stdout_logfile=/dev/stdout
stdout_logfile_maxbytes=0
stderr_logfile=/dev/stderr
stderr_logfile_maxbytes=0
command=php-fpm
[program:scheduler]
stdout_logfile=/dev/stdout
stdout_logfile_maxbytes=0
stderr_logfile=/dev/stderr
stderr_logfile_maxbytes=0
command=php artisan schedule:work
[program:queue-worker]
stdout_logfile=/dev/stdout
stdout_logfile_maxbytes=0
stderr_logfile=/dev/stderr
stderr_logfile_maxbytes=0
numprocs=2
command=php artisan queue:work --sleep=3 --tries=1 --memory=1024 --timeout=3600 --daemon