diff --git a/.docker/images/php/application/Dockerfile b/.docker/images/php/application/Dockerfile index 1c2f0eb3c..818e2bf92 100644 --- a/.docker/images/php/application/Dockerfile +++ b/.docker/images/php/application/Dockerfile @@ -1,28 +1,28 @@ -ARG BASE_IMAGE -FROM ${BASE_IMAGE} as base - -RUN apt update && apt install -y \ - sqlite3 - -FROM base as prod - -USER $APP_USER_NAME - -FROM base as ci - -USER $APP_USER_NAME - -FROM base as local - -#ARG APP_SSH_PASSWORD -#RUN echo "$APP_USER_NAME:$APP_SSH_PASSWORD" | chpasswd 2>&1 -# -## Required to start sshd, otherwise the container will error out on startup with the message -## "sshd: no hostkeys available -- exiting." -## @see https://stackoverflow.com/a/65348102/413531 -#RUN ssh-keygen -A -# -## we use SSH deployment configuration in PhpStorm for local development -#EXPOSE 22 -# -#CMD ["/usr/sbin/sshd", "-D"] +ARG BASE_IMAGE +FROM ${BASE_IMAGE} as base + +RUN apt update && apt install -y \ + sqlite3 + +FROM base as prod + +USER $APP_USER_NAME + +FROM base as ci + +USER $APP_USER_NAME + +FROM base as local + +#ARG APP_SSH_PASSWORD +#RUN echo "$APP_USER_NAME:$APP_SSH_PASSWORD" | chpasswd 2>&1 +# +## Required to start sshd, otherwise the container will error out on startup with the message +## "sshd: no hostkeys available -- exiting." +## @see https://stackoverflow.com/a/65348102/413531 +#RUN ssh-keygen -A +# +## we use SSH deployment configuration in PhpStorm for local development +#EXPOSE 22 +# +#CMD ["/usr/sbin/sshd", "-D"] diff --git a/.docker/images/php/base/Dockerfile b/.docker/images/php/base/Dockerfile index 0b41e93b4..99a8b01ae 100644 --- a/.docker/images/php/base/Dockerfile +++ b/.docker/images/php/base/Dockerfile @@ -1,165 +1,166 @@ -ARG COMPOSER_VERSION -ARG TARGET_PHP_VERSION -FROM composer:${COMPOSER_VERSION} as composer -FROM php:${TARGET_PHP_VERSION}-fpm as base - -# make build args available as ENV variables to downstream images -# so that we don't have to pass the same build args again -ARG APP_USER_ID -ARG APP_GROUP_ID -ARG APP_USER_NAME -ARG APP_GROUP_NAME -ARG APP_CODE_PATH - -ARG ENV -ENV APP_USER_ID=${APP_USER_ID} -ENV APP_GROUP_ID=${APP_GROUP_ID} -ENV APP_USER_NAME=${APP_USER_NAME} -ENV APP_GROUP_NAME=${APP_GROUP_NAME} -ENV APP_CODE_PATH=${APP_CODE_PATH} -ENV TARGET_PHP_VERSION=${TARGET_PHP_VERSION} - -ENV ENV=${ENV} - -RUN addgroup -gid $APP_GROUP_ID $APP_GROUP_NAME && \ - adduser --disabled-password --uid $APP_USER_ID --shell /bin/bash --ingroup $APP_GROUP_NAME $APP_USER_NAME && \ - mkdir -p $APP_CODE_PATH && \ - chown $APP_USER_NAME: $APP_CODE_PATH - -ADD https://gitsecret.jfrog.io/artifactory/api/security/keypair/public/repositories/git-secret-apk /etc/apk/keys/git-secret-apk.rsa.pub - -RUN apt update && \ - apt install -y \ - bash \ - git \ - git-secret \ - gawk \ - gnupg \ - make \ - strace \ - sudo \ - vim - - -# Install intl -RUN apt-get update && apt-get install -y \ - libicu-dev \ - libssl-dev \ - libcurl4-openssl-dev \ - libfreetype6-dev \ - libjpeg62-turbo-dev \ - libpng-dev \ - libxml2-dev \ - libmagickwand-dev \ - git \ - zlib1g-dev \ - unzip \ - libzip-dev \ - mupdf-tools \ - imagemagick \ - libmcrypt-dev - -# Install fileinfo -RUN docker-php-ext-install -j$(nproc) fileinfo -# Install intl -RUN docker-php-ext-install -j$(nproc) intl -# Install mongodb -RUN pecl install mongodb \ - && docker-php-ext-enable mongodb -# Install mcrypt -RUN pecl install mcrypt \ - && docker-php-ext-enable mcrypt -# Install curl -RUN docker-php-ext-install -j$(nproc) curl -# Install Zip -RUN docker-php-ext-install zip -# Install gd -RUN docker-php-ext-configure gd --with-freetype --with-jpeg \ - && docker-php-ext-install -j$(nproc) gd -# Install soap -RUN docker-php-ext-install -j$(nproc) soap -# Install imagick -RUN pecl install imagick \ - && docker-php-ext-enable imagick -# Install mysql -RUN docker-php-ext-install -j$(nproc) pdo_mysql -# Install opcache -RUN docker-php-ext-install -j$(nproc) opcache -RUN apt-get update && apt-get install -y \ - libc-client-dev libkrb5-dev libldap2-dev && \ - rm -r /var/lib/apt/lists/* - -# Install ldap -RUN docker-php-ext-install -j$(nproc) ldap - -RUN docker-php-ext-configure imap --with-kerberos --with-imap-ssl && \ - docker-php-ext-install -j$(nproc) imap - -COPY ./.docker/images/php/base/pdf/php_pdflib.so /pdflib.so - -# make bash default shell -RUN sed -e 's;/bin/ash$;/bin/bash;g' -i /etc/passwd - -COPY ./.docker/images/php/base/conf.d/zz-app.ini $PHP_INI_DIR/conf.d/zz-app.ini -COPY ./.docker/images/php/base/conf.d/zz-app-${ENV}.ini $PHP_INI_DIR/conf.d/zz-ppp-${ENV}.ini - -COPY ./.docker/images/php/base/.bashrc /home/${APP_USER_NAME}/.bashrc -COPY ./.docker/images/php/base/.bashrc /root/.bashrc - -COPY --from=composer /usr/bin/composer /usr/local/bin/composer - -RUN git config --system --add safe.directory "$APP_CODE_PATH" - -WORKDIR $APP_CODE_PATH - -FROM base as codebase - -# By only copying the composer files required to run composer install -# the layer will be cached and only invalidated when the composer dependencies are changed -COPY ./src/new/composer.json /dependencies/new/ -COPY ./src/new/composer.lock /dependencies/new/ - -# use a cache mount to cache the composer dependencies -# this is essentially a cache that lives in Docker BuildKit (i.e. has nothing to do with the host system) -RUN --mount=type=cache,target=/tmp/.composer \ - cd /dependencies/new && \ - if [ "$ENV" == "prod" ] ; \ - then \ - # on production, we don't want test dependencies - COMPOSER_HOME=/tmp/.composer composer install --no-scripts --no-plugins --no-progress -o --no-dev; \ - else \ - COMPOSER_HOME=/tmp/.composer composer install --no-scripts --no-plugins --no-progress -o; \ - fi - -# copy the full codebase -COPY ./src/ /codebase - -# move the dependencies -RUN mv /dependencies/new/vendor /codebase/new/vendor - -# remove files we don't require in the image to keep the image size small -RUN cd /codebase && \ - rm -rf .docker/ .build/ .infrastructure/ && \ - if [ "$ENV" == "prod" ] ; \ - then \ - # on production, we don't want tests - rm -rf tests/; \ - fi - -FROM base as prod - -COPY --from=codebase --chown=$APP_USER_NAME:$APP_GROUP_NAME /codebase $APP_CODE_PATH - -FROM base as ci - -COPY --from=codebase --chown=$APP_USER_NAME:$APP_GROUP_NAME /codebase $APP_CODE_PATH - -FROM base as local - -# add app user to sudoers -# see https://ostechnix.com/add-delete-and-grant-sudo-privileges-to-users-in-alpine-linux/ for adding sudo -# see https://askubuntu.com/a/340669 for not requiring a sudo pw -RUN echo "root ALL=(ALL) NOPASSWD: ALL " | tee -a "/etc/sudoers.d/users" && \ - echo "${APP_USER_NAME} ALL=(ALL) NOPASSWD: ALL " | tee -a "/etc/sudoers.d/users" - -RUN pecl install xdebug +ARG COMPOSER_VERSION +ARG TARGET_PHP_VERSION +FROM composer:${COMPOSER_VERSION} as composer +FROM php:${TARGET_PHP_VERSION}-fpm as base + +# make build args available as ENV variables to downstream images +# so that we don't have to pass the same build args again +ARG APP_USER_ID +ARG APP_GROUP_ID +ARG APP_USER_NAME +ARG APP_GROUP_NAME +ARG APP_CODE_PATH + +ARG ENV +ENV APP_USER_ID=${APP_USER_ID} +ENV APP_GROUP_ID=${APP_GROUP_ID} +ENV APP_USER_NAME=${APP_USER_NAME} +ENV APP_GROUP_NAME=${APP_GROUP_NAME} +ENV APP_CODE_PATH=${APP_CODE_PATH} +ENV TARGET_PHP_VERSION=${TARGET_PHP_VERSION} + +ENV ENV=${ENV} + +RUN addgroup -gid $APP_GROUP_ID $APP_GROUP_NAME && \ + adduser --disabled-password --uid $APP_USER_ID --shell /bin/bash --ingroup $APP_GROUP_NAME $APP_USER_NAME && \ + mkdir -p $APP_CODE_PATH && \ + chown $APP_USER_NAME: $APP_CODE_PATH + +ADD https://gitsecret.jfrog.io/artifactory/api/security/keypair/public/repositories/git-secret-apk /etc/apk/keys/git-secret-apk.rsa.pub + +RUN apt update && \ + apt install -y \ + bash \ + git \ + git-secret \ + gawk \ + gnupg \ + make \ + strace \ + sudo \ + vim \ + nano + + +# Install intl +RUN apt-get update && apt-get install -y \ + libicu-dev \ + libssl-dev \ + libcurl4-openssl-dev \ + libfreetype6-dev \ + libjpeg62-turbo-dev \ + libpng-dev \ + libxml2-dev \ + libmagickwand-dev \ + git \ + zlib1g-dev \ + unzip \ + libzip-dev \ + mupdf-tools \ + imagemagick \ + libmcrypt-dev + +# Install fileinfo +RUN docker-php-ext-install -j$(nproc) fileinfo +# Install intl +RUN docker-php-ext-install -j$(nproc) intl +# Install mongodb +RUN pecl install mongodb \ + && docker-php-ext-enable mongodb +# Install mcrypt +RUN pecl install mcrypt \ + && docker-php-ext-enable mcrypt +# Install curl +RUN docker-php-ext-install -j$(nproc) curl +# Install Zip +RUN docker-php-ext-install zip +# Install gd +RUN docker-php-ext-configure gd --with-freetype --with-jpeg \ + && docker-php-ext-install -j$(nproc) gd +# Install soap +RUN docker-php-ext-install -j$(nproc) soap +# Install imagick +RUN pecl install imagick \ + && docker-php-ext-enable imagick +# Install mysql +RUN docker-php-ext-install -j$(nproc) pdo_mysql +# Install opcache +RUN docker-php-ext-install -j$(nproc) opcache +RUN apt-get update && apt-get install -y \ + libc-client-dev libkrb5-dev libldap2-dev && \ + rm -r /var/lib/apt/lists/* + +# Install ldap +RUN docker-php-ext-install -j$(nproc) ldap + +RUN docker-php-ext-configure imap --with-kerberos --with-imap-ssl && \ + docker-php-ext-install -j$(nproc) imap + +COPY ./.docker/images/php/base/pdf/php_pdflib.so /pdflib.so + +# make bash default shell +RUN sed -e 's;/bin/ash$;/bin/bash;g' -i /etc/passwd + +COPY ./.docker/images/php/base/conf.d/zz-app.ini $PHP_INI_DIR/conf.d/zz-app.ini +COPY ./.docker/images/php/base/conf.d/zz-app-${ENV}.ini $PHP_INI_DIR/conf.d/zz-ppp-${ENV}.ini + +COPY ./.docker/images/php/base/.bashrc /home/${APP_USER_NAME}/.bashrc +COPY ./.docker/images/php/base/.bashrc /root/.bashrc + +COPY --from=composer /usr/bin/composer /usr/local/bin/composer + +RUN git config --system --add safe.directory "$APP_CODE_PATH" + +WORKDIR $APP_CODE_PATH + +FROM base as codebase + +# By only copying the composer files required to run composer install +# the layer will be cached and only invalidated when the composer dependencies are changed +COPY ./src/new/composer.json /dependencies/new/ +COPY ./src/new/composer.lock /dependencies/new/ + +# use a cache mount to cache the composer dependencies +# this is essentially a cache that lives in Docker BuildKit (i.e. has nothing to do with the host system) +RUN --mount=type=cache,target=/tmp/.composer \ + cd /dependencies/new && \ + if [ "$ENV" == "prod" ] ; \ + then \ + # on production, we don't want test dependencies + COMPOSER_HOME=/tmp/.composer composer install --no-scripts --no-plugins --no-progress -o --no-dev; \ + else \ + COMPOSER_HOME=/tmp/.composer composer install --no-scripts --no-plugins --no-progress -o; \ + fi + +# copy the full codebase +COPY ./src/ /codebase + +# move the dependencies +RUN mv /dependencies/new/vendor /codebase/new/vendor + +# remove files we don't require in the image to keep the image size small +RUN cd /codebase && \ + rm -rf .docker/ .build/ .infrastructure/ && \ + if [ "$ENV" == "prod" ] ; \ + then \ + # on production, we don't want tests + rm -rf tests/; \ + fi + +FROM base as prod + +COPY --from=codebase --chown=$APP_USER_NAME:$APP_GROUP_NAME /codebase $APP_CODE_PATH + +FROM base as ci + +COPY --from=codebase --chown=$APP_USER_NAME:$APP_GROUP_NAME /codebase $APP_CODE_PATH + +FROM base as local + +# add app user to sudoers +# see https://ostechnix.com/add-delete-and-grant-sudo-privileges-to-users-in-alpine-linux/ for adding sudo +# see https://askubuntu.com/a/340669 for not requiring a sudo pw +RUN echo "root ALL=(ALL) NOPASSWD: ALL " | tee -a "/etc/sudoers.d/users" && \ + echo "${APP_USER_NAME} ALL=(ALL) NOPASSWD: ALL " | tee -a "/etc/sudoers.d/users" + +RUN pecl install xdebug diff --git a/.docker/images/php/cron/bin/start-cron.sh b/.docker/images/php/cron/bin/start-cron.sh index acceae769..7002a4f1e 100644 --- a/.docker/images/php/cron/bin/start-cron.sh +++ b/.docker/images/php/cron/bin/start-cron.sh @@ -3,7 +3,9 @@ rsyslogd cron touch /var/log/cron.log +touch /var/log/syslog.log chmod -R 0777 /var/log/cron.log +chmod -R 0777 /var/log/syslog.log rm /data/www/new/var/cache/* rm /data/www/new/var/log/* chmod -R 0777 /data/www/new/var/cache diff --git a/.make/03-application-qa.mk b/.make/03-application-qa.mk index 5fe21677d..b9f87d8a6 100644 --- a/.make/03-application-qa.mk +++ b/.make/03-application-qa.mk @@ -1,109 +1,114 @@ -##@ [Application: QA] - -# variables -CORES?=$(shell (nproc || sysctl -n hw.ncpu) 2> /dev/null) - -# constants -## files -ALL_FILES=./ -APP_FILES=src/ -TEST_FILES=tests/ - -## bash colors -RED:=\033[0;31m -GREEN:=\033[0;32m -YELLOW:=\033[0;33m -NO_COLOR:=\033[0m - -# Tool CLI config -PHPUNIT_CMD=php vendor/bin/phpunit -PHPUNIT_ARGS= -PHPUNIT_FILES= -PHPSTAN_CMD=php -d xdebug.mode=off -d memory_limit=-1 vendor/bin/phpstan analyse -PHPSTAN_ARGS=--level=9 -PHPSTAN_FILES=$(APP_FILES) $(TEST_FILES) -PHPCS_CMD=php -d xdebug.mode=off -d memory_limit=-1 vendor/bin/phpcs -PHPCS_ARGS=--parallel=$(CORES) --standard=psr12 -PHPCS_FILES=$(APP_FILES) -PHPCBF_CMD=php -d xdebug.mode=off -d memory_limit=-1 vendor/bin/phpcbf -PHPCBF_ARGS=$(PHPCS_ARGS) -PHPCBF_FILES=$(PHPCS_FILES) -PARALLEL_LINT_CMD=php -d xdebug.mode=off -d memory_limit=-1 vendor/bin/parallel-lint -PARALLEL_LINT_ARGS=-j 4 --exclude vendor/ --exclude .docker --exclude .git -PARALLEL_LINT_FILES=$(ALL_FILES) -COMPOSER_REQUIRE_CHECKER_CMD=php -d xdebug.mode=off -d memory_limit=-1 vendor/bin/composer-require-checker -COMPOSER_REQUIRE_CHECKER_ARGS=--ignore-parse-errors - -# call with NO_PROGRESS=true to hide tool progress (makes sense when invoking multiple tools together) -NO_PROGRESS?=false -ifeq ($(NO_PROGRESS),true) - PHPSTAN_ARGS+= --no-progress - PARALLEL_LINT_ARGS+= --no-progress -else - PHPCS_ARGS+= -p - PHPCBF_ARGS+= -p -endif - -# Use NO_PROGRESS=false when running individual tools. -# On NO_PROGRESS=true the corresponding tool has no output on success -# apart from its runtime but it will still print -# any errors that occured. -define execute - if [ "$(NO_PROGRESS)" = "false" ]; then \ - eval "$(EXECUTE_IN_APPLICATION_CONTAINER) $(1) $(2) $(3) $(4)"; \ - else \ - START=$$(date +%s); \ - printf "%-35s" "$@"; \ - if OUTPUT=$$(eval "$(EXECUTE_IN_APPLICATION_CONTAINER) $(1) $(2) $(3) $(4)" 2>&1); then \ - printf " $(GREEN)%-6s$(NO_COLOR)" "done"; \ - END=$$(date +%s); \ - RUNTIME=$$((END-START)) ;\ - printf " took $(YELLOW)$${RUNTIME}s$(NO_COLOR)\n"; \ - else \ - printf " $(RED)%-6s$(NO_COLOR)" "fail"; \ - END=$$(date +%s); \ - RUNTIME=$$((END-START)) ;\ - printf " took $(YELLOW)$${RUNTIME}s$(NO_COLOR)\n"; \ - echo "$$OUTPUT"; \ - printf "\n"; \ - exit 1; \ - fi; \ - fi -endef - -.PHONY: test -test: ## Run all tests - @$(EXECUTE_IN_APPLICATION_CONTAINER) $(PHPUNIT_CMD) $(PHPUNIT_ARGS) $(ARGS) - -.PHONY: phplint -phplint: ## Run phplint on all files - @$(call execute,$(PARALLEL_LINT_CMD),$(PARALLEL_LINT_ARGS),$(PARALLEL_LINT_FILES), $(ARGS)) - -.PHONY: phpcs -phpcs: ## Run style check on all application files - @$(call execute,$(PHPCS_CMD),$(PHPCS_ARGS),$(PHPCS_FILES), $(ARGS)) - -.PHONY: phpcbf -phpcbf: ## Run style fixer on all application files - @$(call execute,$(PHPCBF_CMD),$(PHPCBF_ARGS),$(PHPCBF_FILES), $(ARGS)) - -.PHONY: phpstan -phpstan: ## Run static analyzer on all application and test files - @$(call execute,$(PHPSTAN_CMD),$(PHPSTAN_ARGS),$(PHPSTAN_FILES), $(ARGS)) - -.PHONY: composer-require-checker -composer-require-checker: ## Run dependency checker - @$(call execute,$(COMPOSER_REQUIRE_CHECKER_CMD),$(COMPOSER_REQUIRE_CHECKER_ARGS),"", $(ARGS)) - -.PHONY: qa -qa: ## Run code quality tools on all files - @"$(MAKE)" -j $(CORES) -k --no-print-directory --output-sync=target qa-exec NO_PROGRESS=true - -.PHONY: qa-exec -qa-exec: phpstan \ - phplint \ - phpcs - - - #composer-require-checker \ - +##@ [Application: QA] + +# variables +CORES?=$(shell (nproc || sysctl -n hw.ncpu) 2> /dev/null) + +# constants +## files +ALL_FILES=./ +APP_FILES=src/ +TEST_FILES=tests/ + +## bash colors +RED:=\033[0;31m +GREEN:=\033[0;32m +YELLOW:=\033[0;33m +NO_COLOR:=\033[0m + +# Tool CLI config +PHPUNIT_CMD=php -dxdebug.mode=off vendor/bin/phpunit +PHPUNIT_CMD_XDEBUG=php vendor/bin/phpunit +PHPUNIT_ARGS= +PHPUNIT_FILES= +PHPSTAN_CMD=php -d xdebug.mode=off -d memory_limit=-1 vendor/bin/phpstan analyse +PHPSTAN_ARGS=--level=9 +PHPSTAN_FILES=$(APP_FILES) $(TEST_FILES) +PHPCS_CMD=php -d xdebug.mode=off -d memory_limit=-1 vendor/bin/phpcs +PHPCS_ARGS=--parallel=$(CORES) --standard=psr12 +PHPCS_FILES=$(APP_FILES) +PHPCBF_CMD=php -d xdebug.mode=off -d memory_limit=-1 vendor/bin/phpcbf +PHPCBF_ARGS=$(PHPCS_ARGS) +PHPCBF_FILES=$(PHPCS_FILES) +PARALLEL_LINT_CMD=php -d xdebug.mode=off -d memory_limit=-1 vendor/bin/parallel-lint +PARALLEL_LINT_ARGS=-j 4 --exclude vendor/ --exclude .docker --exclude .git +PARALLEL_LINT_FILES=$(ALL_FILES) +COMPOSER_REQUIRE_CHECKER_CMD=php -d xdebug.mode=off -d memory_limit=-1 vendor/bin/composer-require-checker +COMPOSER_REQUIRE_CHECKER_ARGS=--ignore-parse-errors + +# call with NO_PROGRESS=true to hide tool progress (makes sense when invoking multiple tools together) +NO_PROGRESS?=false +ifeq ($(NO_PROGRESS),true) + PHPSTAN_ARGS+= --no-progress + PARALLEL_LINT_ARGS+= --no-progress +else + PHPCS_ARGS+= -p + PHPCBF_ARGS+= -p +endif + +# Use NO_PROGRESS=false when running individual tools. +# On NO_PROGRESS=true the corresponding tool has no output on success +# apart from its runtime but it will still print +# any errors that occured. +define execute + if [ "$(NO_PROGRESS)" = "false" ]; then \ + eval "$(EXECUTE_IN_APPLICATION_CONTAINER) $(1) $(2) $(3) $(4)"; \ + else \ + START=$$(date +%s); \ + printf "%-35s" "$@"; \ + if OUTPUT=$$(eval "$(EXECUTE_IN_APPLICATION_CONTAINER) $(1) $(2) $(3) $(4)" 2>&1); then \ + printf " $(GREEN)%-6s$(NO_COLOR)" "done"; \ + END=$$(date +%s); \ + RUNTIME=$$((END-START)) ;\ + printf " took $(YELLOW)$${RUNTIME}s$(NO_COLOR)\n"; \ + else \ + printf " $(RED)%-6s$(NO_COLOR)" "fail"; \ + END=$$(date +%s); \ + RUNTIME=$$((END-START)) ;\ + printf " took $(YELLOW)$${RUNTIME}s$(NO_COLOR)\n"; \ + echo "$$OUTPUT"; \ + printf "\n"; \ + exit 1; \ + fi; \ + fi +endef + +.PHONY: test +test: ## Run all tests + @$(EXECUTE_IN_APPLICATION_CONTAINER) $(PHPUNIT_CMD) $(PHPUNIT_ARGS) $(ARGS) + +.PHONY: test-xdebug +test-xdebug: ## Run all tests + @$(EXECUTE_IN_APPLICATION_CONTAINER) $(PHPUNIT_CMD_XDEBUG) $(PHPUNIT_ARGS) $(ARGS) + +.PHONY: phplint +phplint: ## Run phplint on all files + @$(call execute,$(PARALLEL_LINT_CMD),$(PARALLEL_LINT_ARGS),$(PARALLEL_LINT_FILES), $(ARGS)) + +.PHONY: phpcs +phpcs: ## Run style check on all application files + @$(call execute,$(PHPCS_CMD),$(PHPCS_ARGS),$(PHPCS_FILES), $(ARGS)) + +.PHONY: phpcbf +phpcbf: ## Run style fixer on all application files + @$(call execute,$(PHPCBF_CMD),$(PHPCBF_ARGS),$(PHPCBF_FILES), $(ARGS)) + +.PHONY: phpstan +phpstan: ## Run static analyzer on all application and test files + @$(call execute,$(PHPSTAN_CMD),$(PHPSTAN_ARGS),$(PHPSTAN_FILES), $(ARGS)) + +.PHONY: composer-require-checker +composer-require-checker: ## Run dependency checker + @$(call execute,$(COMPOSER_REQUIRE_CHECKER_CMD),$(COMPOSER_REQUIRE_CHECKER_ARGS),"", $(ARGS)) + +.PHONY: qa +qa: ## Run code quality tools on all files + @"$(MAKE)" -j $(CORES) -k --no-print-directory --output-sync=target qa-exec NO_PROGRESS=true + +.PHONY: qa-exec +qa-exec: phpstan \ + phplint \ + phpcs + + + #composer-require-checker \ +