diff --git a/.gitignore b/.gitignore index 46d87d2d30d6167368a3384d68ac433c9645f833..17141eae59749c820256f9d4eb8b9178a21d8f4c 100644 --- a/.gitignore +++ b/.gitignore @@ -19,7 +19,6 @@ npm-debug.log /.buildpath /.project -composer.lock package-lock.json local.log diff --git a/.gitlab-ci.yml b/.gitlab-ci.yml index 211ed96f2792e2c69e4f8cd46b90a4d3e5e776e5..ab19db1667590581545297b9b9827b68de512674 100644 --- a/.gitlab-ci.yml +++ b/.gitlab-ci.yml @@ -64,21 +64,6 @@ prepare_node: - branches - tags -prepare_composer: - stage: prepare - image: registry.metager.de/open-source/composer/master - variables: - COMPOSER_HOME: "$CI_PROJECT_DIR/.composer" - script: - - composer install --no-dev - artifacts: - paths: - - vendor - cache: - key: "metager-${CI_JOB_NAME}" - paths: - - .composer - review: variables: HELM_UPGRADE_VALUES_FILE: .gitlab/review-apps-values.yaml @@ -143,16 +128,19 @@ stop_review: development: <<: *development_template - only: - refs: - - development - kubernetes: active - except: - variables: - - $STAGING_ENABLED - - $CANARY_ENABLED - - $INCREMENTAL_ROLLOUT_ENABLED - - $INCREMENTAL_ROLLOUT_MODE + rules: + - if: '$CI_KUBERNETES_ACTIVE == null || $CI_KUBERNETES_ACTIVE == ""' + when: never + - if: '$STAGING_ENABLED' + when: never + - if: '$CANARY_ENABLED' + when: never + - if: '$INCREMENTAL_ROLLOUT_ENABLED' + when: never + - if: '$INCREMENTAL_ROLLOUT_MODE' + when: never + - if: '$CI_COMMIT_BRANCH == $CI_DEFAULT_BRANCH' + production: @@ -162,6 +150,19 @@ production: ROLLOUT_RESOURCE_TYPE: deployment environment: url: https://metager.de + rules: + - if: '$CI_KUBERNETES_ACTIVE == null || $CI_KUBERNETES_ACTIVE == ""' + when: never + - if: '$STAGING_ENABLED' + when: never + - if: '$CANARY_ENABLED' + when: never + - if: '$INCREMENTAL_ROLLOUT_ENABLED' + when: never + - if: '$INCREMENTAL_ROLLOUT_MODE' + when: never + - if: '$CI_COMMIT_BRANCH == "master"' + integrationtest: stage: integrationtest diff --git a/.gitlab/development-values.yaml b/.gitlab/development-values.yaml index e99a88b3f56d21446adc1c31b980f24f966eb4dc..03dfbf02081018d6cba6baadecbaf21003ebe9b7 100644 --- a/.gitlab/development-values.yaml +++ b/.gitlab/development-values.yaml @@ -42,6 +42,7 @@ podAnnotations: deploymentApiVersion: apps/v1 ingress: annotations: + kubernetes.io/ingress.class: nginx-ingress cert-manager.io/cluster-issuer: letsencrypt-prod nginx.ingress.kubernetes.io/client-body-buffer-size: "30m" nginx.ingress.kubernetes.io/proxy-body-size: "30m" @@ -51,6 +52,7 @@ ingress: more_set_headers "X-Content-Type-Options: nosniff"; more_set_headers "ReferrerPolicy: origin"; more_set_headers "X-XSS-Protection: 1; mode=block"; + more_set_headers "Permissions-Policy: interest-cohort=()"; if ($arg_out = "results-with-style") { more_set_headers "X-Frame-Options: allow-from https://scripts.zdv.uni-mainz.de/"; } diff --git a/.gitlab/production-values.yaml b/.gitlab/production-values.yaml index 76a9603c240183714d8b980309db22ee665a963c..90e92bae792464ae231457b88d9ab93f3ac2a645 100644 --- a/.gitlab/production-values.yaml +++ b/.gitlab/production-values.yaml @@ -71,6 +71,7 @@ ingress: more_set_headers "X-Content-Type-Options: nosniff"; more_set_headers "ReferrerPolicy: origin"; more_set_headers "X-XSS-Protection: 1; mode=block"; + more_set_headers "Permissions-Policy: interest-cohort=()"; if ($arg_out = "results-with-style") { more_set_headers "X-Frame-Options: allow-from https://scripts.zdv.uni-mainz.de/"; } diff --git a/.gitlab/review-apps-values.yaml b/.gitlab/review-apps-values.yaml index cb1109f7e75b03e10071418d5abe9bdab391c7c1..b187cd9331fdbae73cb3d547afed19e9aabe70a7 100644 --- a/.gitlab/review-apps-values.yaml +++ b/.gitlab/review-apps-values.yaml @@ -17,6 +17,7 @@ ingress: more_set_headers "X-Content-Type-Options: nosniff"; more_set_headers "ReferrerPolicy: origin"; more_set_headers "X-XSS-Protection: 1; mode=block"; + more_set_headers "Permissions-Policy: interest-cohort=()"; if ($arg_out = "results-with-style") { more_set_headers "X-Frame-Options: allow-from https://scripts.zdv.uni-mainz.de/"; } diff --git a/.phpunit.result.cache b/.phpunit.result.cache new file mode 100644 index 0000000000000000000000000000000000000000..9aac3dea614af8035f3b97418fa1e8b1cfe50eb9 --- /dev/null +++ b/.phpunit.result.cache @@ -0,0 +1 @@ +C:37:"PHPUnit\Runner\DefaultTestResultCache":1522:{a:2:{s:7:"defects";a:13:{s:44:"Tests\Browser\StaticPagesTest::testStartpage";i:4;s:46:"Tests\Browser\StaticPagesTest::testDatenschutz";i:4;s:40:"Tests\Browser\StaticPagesTest::testHilfe";i:4;s:42:"Tests\Browser\StaticPagesTest::testSpenden";i:4;s:38:"Tests\Browser\StaticPagesTest::testApp";i:4;s:42:"Tests\Browser\StaticPagesTest::testKontakt";i:4;s:39:"Tests\Browser\StaticPagesTest::testTeam";i:4;s:40:"Tests\Browser\StaticPagesTest::testAbout";i:4;s:42:"Tests\Browser\StaticPagesTest::testImpress";i:4;s:41:"Tests\Browser\StaticPagesTest::testPlugin";i:4;s:41:"Tests\Browser\StaticPagesTest::testWidget";i:4;s:50:"Tests\Browser\StaticPagesTest::testWebsearchWidget";i:4;s:51:"Tests\Browser\StaticPagesTest::testSitesearchWidget";i:4;}s:5:"times";a:13:{s:44:"Tests\Browser\StaticPagesTest::testStartpage";d:1.179;s:46:"Tests\Browser\StaticPagesTest::testDatenschutz";d:3.296;s:40:"Tests\Browser\StaticPagesTest::testHilfe";d:1.095;s:42:"Tests\Browser\StaticPagesTest::testSpenden";d:1.585;s:38:"Tests\Browser\StaticPagesTest::testApp";d:1.036;s:42:"Tests\Browser\StaticPagesTest::testKontakt";d:1.468;s:39:"Tests\Browser\StaticPagesTest::testTeam";d:1.155;s:40:"Tests\Browser\StaticPagesTest::testAbout";d:1.016;s:42:"Tests\Browser\StaticPagesTest::testImpress";d:1.105;s:41:"Tests\Browser\StaticPagesTest::testPlugin";d:1.171;s:41:"Tests\Browser\StaticPagesTest::testWidget";d:1.071;s:50:"Tests\Browser\StaticPagesTest::testWebsearchWidget";d:1.025;s:51:"Tests\Browser\StaticPagesTest::testSitesearchWidget";d:1.099;}}} \ No newline at end of file diff --git a/.vscode/launch.json b/.vscode/launch.json index 7987693b275ab4e9e2834defffbf52c763a061ef..eddd6068e8fa0bb943b3ccf2336eba7bb1609510 100644 --- a/.vscode/launch.json +++ b/.vscode/launch.json @@ -8,7 +8,7 @@ "name": "PHP - Listen for XDebug", "type": "php", "request": "launch", - "port": 9000, + "port": 9003, "pathMappings": { "/html": "${workspaceRoot}" } @@ -17,7 +17,7 @@ "name": "PHP - Launch currently open script", "type": "php", "request": "launch", - "port": 9000, + "port": 9003, "program": "${file}", "cwd": "${fileDirname}", "pathMappings": { diff --git a/Dockerfile b/Dockerfile index 28944a0b1e0faee9899b27329b9ce8fbd7ff346e..65b62ce5ab5a8f2d0f00b8a4a9c8869985250747 100644 --- a/Dockerfile +++ b/Dockerfile @@ -1,73 +1,76 @@ -FROM alpine:3.11.3 +FROM debian:10 -RUN apk add --update \ +# Install System Components +RUN apt update \ + && apt install -y \ nginx \ tzdata \ - ca-certificates \ - dcron \ - zip \ - redis \ - libpng \ - php7 \ - php7-fpm \ - php7-common \ - php7-curl \ - php7-mbstring \ - php7-sqlite3 \ - php7-pdo_mysql \ - php7-pdo_sqlite \ - php7-dom \ - php7-simplexml \ - php7-tokenizer \ - php7-zip \ - php7-redis \ - php7-gd \ - php7-json \ - php7-pcntl \ - php7-opcache \ - php7-fileinfo \ - && rm -rf /var/cache/apk/* + cron \ + lsb-release \ + apt-transport-https \ + curl \ + zip + +RUN curl -o /etc/apt/trusted.gpg.d/php.gpg https://packages.sury.org/php/apt.gpg \ + && echo "deb https://packages.sury.org/php/ $(lsb_release -sc) main" | tee /etc/apt/sources.list.d/php.list + +# Install PHP Components +RUN apt update \ + && apt install -y \ + php7.4 \ + php7.4-xml \ + php7.4-fpm \ + php7.4-common \ + php7.4-curl \ + php7.4-mbstring \ + php7.4-sqlite3 \ + php7.4-mysql \ + php7.4-sqlite \ + php7.4-zip \ + php7.4-redis \ + php7.4-gd \ + php7.4-json \ + php7.4-opcache WORKDIR /html -RUN sed -i 's/;error_log = log\/php7\/error.log/error_log = \/dev\/stderr/g' /etc/php7/php-fpm.conf && \ - sed -i 's/;daemonize = yes/daemonize = no/g' /etc/php7/php-fpm.conf && \ - sed -i 's/listen = 127.0.0.1:9000/listen = 9000/g' /etc/php7/php-fpm.d/www.conf && \ - sed -i 's/;request_terminate_timeout = 0/request_terminate_timeout = 30/g' /etc/php7/php-fpm.d/www.conf && \ - sed -i 's/;request_terminate_timeout_track_finished = no/request_terminate_timeout_track_finished = yes/g' /etc/php7/php-fpm.d/www.conf && \ - sed -i 's/;decorate_workers_output = no/decorate_workers_output = no/g' /etc/php7/php-fpm.d/www.conf && \ - sed -i 's/;catch_workers_output = yes/catch_workers_output = yes/g' /etc/php7/php-fpm.d/www.conf && \ - sed -i 's/user = nobody/user = nginx/g' /etc/php7/php-fpm.d/www.conf && \ - sed -i 's/group = nobody/group = nginx/g' /etc/php7/php-fpm.d/www.conf && \ - sed -i 's/pm.max_children = 5/pm.max_children = 1024/g' /etc/php7/php-fpm.d/www.conf && \ - sed -i 's/pm.start_servers = 2/pm.start_servers = 50/g' /etc/php7/php-fpm.d/www.conf && \ - sed -i 's/pm.min_spare_servers = 1/pm.min_spare_servers = 5/g' /etc/php7/php-fpm.d/www.conf && \ - sed -i 's/pm.max_spare_servers = 3/pm.max_spare_servers = 50/g' /etc/php7/php-fpm.d/www.conf && \ - sed -i 's/user = www-data/user = nginx/g' /etc/php7/php-fpm.d/www.conf && \ - sed -i 's/group = www-data/group = nginx/g' /etc/php7/php-fpm.d/www.conf && \ - sed -i 's/;cgi.fix_pathinfo=1/cgi.fix_pathinfo=0/g' /etc/php7/php.ini && \ - sed -i 's/expose_php = On/expose_php = Off/g' /etc/php7/php.ini && \ +RUN mkdir -p /run/php && \ + sed -i 's/error_log = \/var\/log\/php7.4-fpm.log/error_log = \/dev\/stderr/g' /etc/php/7.4/fpm/php-fpm.conf && \ + sed -i 's/;daemonize = yes/daemonize = no/g' /etc/php/7.4/fpm/php-fpm.conf && \ + sed -i 's/listen = \/run\/php\/php7.4-fpm.sock/listen = 9000/g' /etc/php/7.4/fpm/pool.d/www.conf && \ + sed -i 's/;request_terminate_timeout = 0/request_terminate_timeout = 30/g' /etc/php/7.4/fpm/pool.d/www.conf && \ + sed -i 's/;request_terminate_timeout_track_finished = no/request_terminate_timeout_track_finished = yes/g' /etc/php/7.4/fpm/pool.d/www.conf && \ + sed -i 's/;decorate_workers_output = no/decorate_workers_output = no/g' /etc/php/7.4/fpm/pool.d/www.conf && \ + sed -i 's/;catch_workers_output = yes/catch_workers_output = yes/g' /etc/php/7.4/fpm/pool.d/www.conf && \ + sed -i 's/pm.max_children = 5/pm.max_children = 1024/g' /etc/php/7.4/fpm/pool.d/www.conf && \ + sed -i 's/pm.start_servers = 2/pm.start_servers = 50/g' /etc/php/7.4/fpm/pool.d/www.conf && \ + sed -i 's/pm.min_spare_servers = 1/pm.min_spare_servers = 5/g' /etc/php/7.4/fpm/pool.d/www.conf && \ + sed -i 's/pm.max_spare_servers = 3/pm.max_spare_servers = 50/g' /etc/php/7.4/fpm/pool.d/www.conf && \ + sed -i 's/;cgi.fix_pathinfo=1/cgi.fix_pathinfo=0/g' /etc/php/7.4/fpm/php.ini && \ # Opcache configuration - sed -i 's/;opcache.enable=1/opcache.enable=1/g' /etc/php7/php.ini && \ - sed -i 's/;opcache.memory_consumption=128/opcache.memory_consumption=128/g' /etc/php7/php.ini && \ - sed -i 's/;opcache.interned_strings_buffer=8/opcache.interned_strings_buffer=8/g' /etc/php7/php.ini && \ - sed -i 's/;opcache.max_accelerated_files=10000/opcache.max_accelerated_files=10000/g' /etc/php7/php.ini && \ - sed -i 's/;opcache.max_wasted_percentage=5/opcache.max_wasted_percentage=5/g' /etc/php7/php.ini && \ - sed -i 's/;opcache.validate_timestamps=1/opcache.validate_timestamps=1/g' /etc/php7/php.ini && \ - sed -i 's/;opcache.revalidate_freq=2/opcache.revalidate_freq=300/g' /etc/php7/php.ini && \ - sed -i 's/upload_max_filesize = 2M/upload_max_filesize = 30M/g' /etc/php7/php.ini && \ - sed -i 's/post_max_size = 8M/post_max_size = 30M/g' /etc/php7/php.ini && \ - echo "daemonize yes" >> /etc/redis.conf && \ - ln -s /dev/null /var/log/nginx/access.log && \ - ln -s /dev/stdout /var/log/nginx/error.log && \ + sed -i 's/;opcache.enable=1/opcache.enable=1/g' /etc/php/7.4/fpm/php.ini && \ + sed -i 's/;opcache.memory_consumption=128/opcache.memory_consumption=128/g' /etc/php/7.4/fpm/php.ini && \ + sed -i 's/;opcache.interned_strings_buffer=8/opcache.interned_strings_buffer=8/g' /etc/php/7.4/fpm/php.ini && \ + sed -i 's/;opcache.max_accelerated_files=10000/opcache.max_accelerated_files=10000/g' /etc/php/7.4/fpm/php.ini && \ + sed -i 's/;opcache.max_wasted_percentage=5/opcache.max_wasted_percentage=5/g' /etc/php/7.4/fpm/php.ini && \ + sed -i 's/;opcache.validate_timestamps=1/opcache.validate_timestamps=1/g' /etc/php/7.4/fpm/php.ini && \ + sed -i 's/;opcache.revalidate_freq=2/opcache.revalidate_freq=300/g' /etc/php/7.4/fpm/php.ini && \ + sed -i 's/upload_max_filesize = 2M/upload_max_filesize = 30M/g' /etc/php/7.4/fpm/php.ini && \ + sed -i 's/post_max_size = 8M/post_max_size = 30M/g' /etc/php/7.4/fpm/php.ini && \ cp /usr/share/zoneinfo/Europe/Berlin /etc/localtime && \ echo "Europe/Berlin" > /etc/timezone && \ (crontab -l ; echo "* * * * * php /html/artisan schedule:run >> /dev/null 2>&1") | crontab - COPY config/nginx.conf /etc/nginx/nginx.conf -COPY config/nginx-default.conf /etc/nginx/conf.d/default.conf -RUN sed -i 's/fastcgi_pass phpfpm:9000;/fastcgi_pass localhost:9000;/g' /etc/nginx/conf.d/default.conf -COPY --chown=root:nginx . /html +COPY config/nginx-default.conf /etc/nginx/sites-available/default +RUN sed -i 's/fastcgi_pass phpfpm:9000;/fastcgi_pass localhost:9000;/g' /etc/nginx/sites-available/default +COPY --chown=root:www-data . /html + +COPY ./helpers/installComposer.sh /usr/bin/installComposer +RUN chmod +x /usr/bin/installComposer && \ + /usr/bin/installComposer && \ + rm /usr/bin/installComposer && \ + composer install --no-dev WORKDIR /html EXPOSE 80 @@ -76,8 +79,8 @@ CMD cp /root/.env .env && \ sed -i 's/^REDIS_PASSWORD=.*/REDIS_PASSWORD=null/g' .env && \ if [ "$GITLAB_ENVIRONMENT_NAME" = "production" ]; then sed -i 's/^APP_ENV=.*/APP_ENV=production/g' .env; else sed -i 's/^APP_ENV=.*/APP_ENV=development/g' .env; fi && \ cp database/useragents.sqlite.example database/useragents.sqlite && \ - chown -R root:nginx storage/logs/metager bootstrap/cache && \ + chown -R root:www-data storage/logs/metager bootstrap/cache && \ chmod -R g+w storage/logs/metager bootstrap/cache && \ - crond -L /dev/stdout && \ + cron -L /dev/stdout && \ php artisan spam:load && \ - php-fpm7 + php-fpm7.4 diff --git a/DockerfileDev b/DockerfileDev index a2d762ee3988b5c151323cbccae8ad8bf40fe3cd..fec1a15f334b648c9f5f4a560a6f64d3fddb528c 100644 --- a/DockerfileDev +++ b/DockerfileDev @@ -1,61 +1,58 @@ -FROM alpine:3.11.3 +FROM debian:10 -RUN apk add --update \ +# Install System Components +RUN apt update \ + && apt install -y \ nginx \ tzdata \ - ca-certificates \ - dcron \ - zip \ - redis \ - php7 \ - php7-fpm \ - php7-common \ - php7-curl \ - php7-mbstring \ - php7-sqlite3 \ - php7-pdo_mysql \ - php7-pdo_sqlite \ - php7-dom \ - php7-simplexml \ - php7-tokenizer \ - php7-zip \ - php7-redis \ - php7-gd \ - php7-json \ - php7-pcntl \ - php7-fileinfo \ - php7-xdebug \ - && rm -rf /var/cache/apk/* + cron \ + lsb-release \ + apt-transport-https \ + curl \ + zip + +RUN curl -o /etc/apt/trusted.gpg.d/php.gpg https://packages.sury.org/php/apt.gpg \ + && echo "deb https://packages.sury.org/php/ $(lsb_release -sc) main" | tee /etc/apt/sources.list.d/php.list + +# Install PHP Components +RUN apt update \ + && apt install -y \ + php7.4 \ + php7.4-xml \ + php7.4-fpm \ + php7.4-common \ + php7.4-curl \ + php7.4-mbstring \ + php7.4-sqlite3 \ + php7.4-mysql \ + php7.4-sqlite \ + php7.4-zip \ + php7.4-redis \ + php7.4-gd \ + php7.4-json \ + php7.4-xdebug WORKDIR /html -RUN sed -i 's/;error_log = log\/php7\/error.log/error_log = \/dev\/stderr/g' /etc/php7/php-fpm.conf && \ - sed -i 's/;daemonize = yes/daemonize = no/g' /etc/php7/php-fpm.conf && \ - sed -i 's/listen = 127.0.0.1:9000/listen = 9000/g' /etc/php7/php-fpm.d/www.conf && \ - sed -i 's/;request_terminate_timeout = 0/request_terminate_timeout = 900/g' /etc/php7/php-fpm.d/www.conf && \ - sed -i 's/;request_terminate_timeout_track_finished = no/request_terminate_timeout_track_finished = yes/g' /etc/php7/php-fpm.d/www.conf && \ - sed -i 's/;decorate_workers_output = no/decorate_workers_output = no/g' /etc/php7/php-fpm.d/www.conf && \ - sed -i 's/;catch_workers_output = yes/catch_workers_output = yes/g' /etc/php7/php-fpm.d/www.conf && \ - sed -i 's/user = nobody/user = nginx/g' /etc/php7/php-fpm.d/www.conf && \ - sed -i 's/group = nobody/group = nginx/g' /etc/php7/php-fpm.d/www.conf && \ - sed -i 's/pm.max_children = 5/pm.max_children = 100/g' /etc/php7/php-fpm.d/www.conf && \ - sed -i 's/pm.start_servers = 2/pm.start_servers = 5/g' /etc/php7/php-fpm.d/www.conf && \ - sed -i 's/pm.min_spare_servers = 1/pm.min_spare_servers = 5/g' /etc/php7/php-fpm.d/www.conf && \ - sed -i 's/pm.max_spare_servers = 3/pm.max_spare_servers = 25/g' /etc/php7/php-fpm.d/www.conf && \ - sed -i 's/user = www-data/user = nginx/g' /etc/php7/php-fpm.d/www.conf && \ - sed -i 's/group = www-data/group = nginx/g' /etc/php7/php-fpm.d/www.conf && \ - sed -i 's/;cgi.fix_pathinfo=1/cgi.fix_pathinfo=0/g' /etc/php7/php.ini && \ - sed -i 's/expose_php = On/expose_php = Off/g' /etc/php7/php.ini && \ - sed -i 's/upload_max_filesize = 2M/upload_max_filesize = 30M/g' /etc/php7/php.ini && \ - sed -i 's/post_max_size = 8M/post_max_size = 30M/g' /etc/php7/php.ini && \ - sed -i 's/;zend_extension=xdebug.so/zend_extension=xdebug.so/g' /etc/php7/conf.d/xdebug.ini && \ - echo "xdebug.remote_enable = 1" >> /etc/php7/conf.d/xdebug.ini && \ - echo "xdebug.remote_autostart = 1" >> /etc/php7/conf.d/xdebug.ini && \ - echo "xdebug.remote_connect_back = 1" >> /etc/php7/conf.d/xdebug.ini && \ - echo "xdebug.idekey=VSCODE" >> /etc/php7/conf.d/xdebug.ini && \ - echo "daemonize yes" >> /etc/redis.conf && \ - ln -s /dev/null /var/log/nginx/access.log && \ - ln -s /dev/stdout /var/log/nginx/error.log && \ +RUN mkdir -p /run/php && \ + sed -i 's/error_log = \/var\/log\/php7.4-fpm.log/error_log = \/dev\/stderr/g' /etc/php/7.4/fpm/php-fpm.conf && \ + sed -i 's/;daemonize = yes/daemonize = no/g' /etc/php/7.4/fpm/php-fpm.conf && \ + sed -i 's/listen = \/run\/php\/php7.4-fpm.sock/listen = 9000/g' /etc/php/7.4/fpm/pool.d/www.conf && \ + sed -i 's/;request_terminate_timeout = 0/request_terminate_timeout = 30/g' /etc/php/7.4/fpm/pool.d/www.conf && \ + sed -i 's/;request_terminate_timeout_track_finished = no/request_terminate_timeout_track_finished = yes/g' /etc/php/7.4/fpm/pool.d/www.conf && \ + sed -i 's/;decorate_workers_output = no/decorate_workers_output = no/g' /etc/php/7.4/fpm/pool.d/www.conf && \ + sed -i 's/;catch_workers_output = yes/catch_workers_output = yes/g' /etc/php/7.4/fpm/pool.d/www.conf && \ + sed -i 's/pm.max_children = 5/pm.max_children = 1024/g' /etc/php/7.4/fpm/pool.d/www.conf && \ + sed -i 's/pm.start_servers = 2/pm.start_servers = 50/g' /etc/php/7.4/fpm/pool.d/www.conf && \ + sed -i 's/pm.min_spare_servers = 1/pm.min_spare_servers = 5/g' /etc/php/7.4/fpm/pool.d/www.conf && \ + sed -i 's/pm.max_spare_servers = 3/pm.max_spare_servers = 50/g' /etc/php/7.4/fpm/pool.d/www.conf && \ + sed -i 's/;cgi.fix_pathinfo=1/cgi.fix_pathinfo=0/g' /etc/php/7.4/fpm/php.ini && \ + sed -i 's/upload_max_filesize = 2M/upload_max_filesize = 30M/g' /etc/php/7.4/fpm/php.ini && \ + sed -i 's/post_max_size = 8M/post_max_size = 30M/g' /etc/php/7.4/fpm/php.ini && \ + echo "xdebug.mode = debug" >> /etc/php/7.4/fpm/conf.d/20-xdebug.ini && \ + echo "xdebug.start_with_request = yes" >> /etc/php/7.4/fpm/conf.d/20-xdebug.ini && \ + echo "xdebug.discover_client_host = true" >> /etc/php/7.4/fpm/conf.d/20-xdebug.ini && \ + echo "xdebug.idekey=VSCODE" >> /etc/php/7.4/fpm/conf.d/20-xdebug.ini && \ cp /usr/share/zoneinfo/Europe/Berlin /etc/localtime && \ echo "Europe/Berlin" > /etc/timezone && \ (crontab -l ; echo "* * * * * php /html/artisan schedule:run >> /dev/null 2>&1") | crontab - @@ -63,7 +60,14 @@ RUN sed -i 's/;error_log = log\/php7\/error.log/error_log = \/dev\/stderr/g' /et WORKDIR /html EXPOSE 80 -CMD chown -R root:nginx storage/logs/metager bootstrap/cache && \ +COPY ./helpers/installComposer.sh /usr/bin/installComposer + +RUN chmod +x /usr/bin/installComposer && \ + /usr/bin/installComposer && \ + rm /usr/bin/installComposer + +CMD chown -R root:www-data storage/logs/metager bootstrap/cache && \ chmod -R g+w storage/logs/metager bootstrap/cache && \ - crond -L /dev/stdout && \ - php-fpm7 + cron -L /dev/stdout && \ + composer install && \ + php-fpm7.4 diff --git a/DockerfileDev.ignore b/DockerfileDev.ignore index d6b954efbf510e511a85c7b357dddbcd530b9801..f0af6630a69016151e561981767bbe24cd44c0d9 100644 --- a/DockerfileDev.ignore +++ b/DockerfileDev.ignore @@ -2,4 +2,5 @@ README.md CHANGELOG.md vendor/* node_modules/* -storage/logs/* \ No newline at end of file +storage/logs/* +helpers/* \ No newline at end of file diff --git a/app/Console/Commands/SaveUseragents.php b/app/Console/Commands/SaveUseragents.php index a6e82947efeff870ffeeaefa812732491d87fb4d..7bf6a04363552a2b25722e76f554d61478477839 100644 --- a/app/Console/Commands/SaveUseragents.php +++ b/app/Console/Commands/SaveUseragents.php @@ -43,14 +43,16 @@ class SaveUseragents extends Command $agent = null; $now = Carbon::now('utc')->toDateTimeString(); - while (($agent = Redis::lpop("useragents")) !== null) { + while (!empty(($agent = Redis::lpop("useragents")))) { $newEntry = json_decode($agent, true); $newEntry["created_at"] = $now; $newEntry["updated_at"] = $now; $agents[] = $newEntry; } - - \App\UserAgent::insert($agents); + + if (!empty($agents)) { + \App\UserAgent::insert($agents); + } // Delete old entries (older than 24h) $expiration = Carbon::now('utc')->subDays(1); diff --git a/app/Exceptions/Handler.php b/app/Exceptions/Handler.php index ddf8c24cb904c239ca3ae53450ef4767d8f0e0b6..45c8cc7ff8b93e83af18cae264e31ea33f3b7893 100644 --- a/app/Exceptions/Handler.php +++ b/app/Exceptions/Handler.php @@ -2,7 +2,7 @@ namespace App\Exceptions; -use Exception; +use Throwable; use Illuminate\Auth\AuthenticationException; use Illuminate\Foundation\Exceptions\Handler as ExceptionHandler; @@ -27,10 +27,10 @@ class Handler extends ExceptionHandler * * This is a great spot to send exceptions to Sentry, Bugsnag, etc. * - * @param \Exception $exception + * @param \Throwable $exception * @return void */ - public function report(Exception $exception) + public function report(Throwable $exception) { parent::report($exception); } @@ -39,10 +39,10 @@ class Handler extends ExceptionHandler * Render an exception into an HTTP response. * * @param \Illuminate\Http\Request $request - * @param \Exception $exception + * @param \Throwable $exception * @return \Illuminate\Http\Response */ - public function render($request, Exception $exception) + public function render($request, Throwable $exception) { if ($request->is('*/meta/meta.ger3*')) { $registry = \Prometheus\CollectorRegistry::getDefault(); diff --git a/app/Http/Controllers/Assoziator.php b/app/Http/Controllers/Assoziator.php index b4a7d686dbaaf71e194d27d4f17d958b7fda643c..e60a0d3a804fef53c647752890709cb28eb94943 100644 --- a/app/Http/Controllers/Assoziator.php +++ b/app/Http/Controllers/Assoziator.php @@ -14,13 +14,25 @@ class Assoziator extends Controller return redirect(LaravelLocalization::getLocalizedURL(LaravelLocalization::getCurrentLocale(), '/asso')); } - $url = "https://metager.de/meta/meta.ger3?eingabe=" . urlencode($eingabe) . "&out=atom10&key=test"; + $params = [ + "eingabe" => $eingabe, + "out" => "atom10", + "key" => env("ASSO_KEY", "test"), + ]; + + + $url = route("resultpage", $params); + + # Special Case for local development as the port forwarding does not work within docker + if(env("APP_ENV", "") === "local" && stripos($url, "http://localhost:8080") === 0){ + $url = str_replace("http://localhost:8080", "http://nginx", $url); + } $ch = curl_init(); curl_setopt_array($ch, array( CURLOPT_RETURNTRANSFER => 1, - CURLOPT_USERAGENT => $_SERVER["AGENT"], + CURLOPT_USERAGENT => $_SERVER["HTTP_USER_AGENT"], CURLOPT_FOLLOWLOCATION => true, CURLOPT_CONNECTTIMEOUT => 10, CURLOPT_MAXCONNECTS => 500, @@ -34,6 +46,11 @@ class Assoziator extends Controller )); $response = curl_exec($ch); + + if(curl_errno($ch)){ + abort(500, curl_error($ch)); + } + $responseCode = curl_getinfo($ch, CURLINFO_HTTP_CODE); curl_close($ch); @@ -115,8 +132,9 @@ class Assoziator extends Controller ->with('navbarFocus', 'dienste') ->with('words', $words) ->with('keywords', $eingabe) - ->with('wordCount', $wordCount); + ->with('wordCount', $wordCount) + ->with('css', [mix('css/asso/style.css')]) + ->with('darkcss', [mix('css/asso/dark.css')]);; - die(var_dump($words)); } } diff --git a/app/Http/Controllers/HumanVerification.php b/app/Http/Controllers/HumanVerification.php index c9a352320fd26a72f7d70be3ef54f00d4580c786..6b3fcea0e846db9683691134a74cd57a2e26e643 100644 --- a/app/Http/Controllers/HumanVerification.php +++ b/app/Http/Controllers/HumanVerification.php @@ -47,10 +47,11 @@ class HumanVerification extends Controller if ($request->getMethod() == 'POST') { \App\PrometheusExporter::CaptchaAnswered(); $lockedKey = $user["lockedKey"]; - $key = $request->input('captcha'); - $key = strtolower($key); - if (!$hasher->check($key, $lockedKey)) { + $rules = ['captcha' => 'required|captcha_api:' . $lockedKey . ',math']; + $validator = validator()->make(request()->all(), $rules); + + if($validator->fails()) { $captcha = Captcha::create("default", true); $user["lockedKey"] = $captcha["key"]; HumanVerification::saveUser($user); diff --git a/app/Http/Controllers/KeyController.php b/app/Http/Controllers/KeyController.php index 88bb7e246d942cff18cb6d179b5eff6b9b736006..dcc9135513100fdd48bedfaaa223964eed426370 100644 --- a/app/Http/Controllers/KeyController.php +++ b/app/Http/Controllers/KeyController.php @@ -6,37 +6,38 @@ use Cookie; use Illuminate\Http\Request; use LaravelLocalization; use \App\Models\Key; +use \Carbon\Carbon; +use Validator; class KeyController extends Controller { - public function index(Request $request) - { - $redirUrl = $request->input('redirUrl', ""); - $cookie = Cookie::get('key'); - $key = $request->input('keyToSet', ''); - - if (empty($key) && empty($cookie)) { - $key = 'enter_key_here'; - } elseif (empty($key) && !empty($cookie)) { - $key = $cookie; - } elseif (!empty($key)) { - $key = $request->input('key'); - } + // How many Ad Free searches should a user get max when he creates a new key + const KEYCHANGE_ADFREE_SEARCHES = 150; + public function index(\App\Models\Key $key, Request $request) + { $cookieLink = LaravelLocalization::getLocalizedURL(LaravelLocalization::getCurrentLocale(), route('loadSettings', Cookie::get())); + $key->canChange(); + $changedAt = null; + if (!empty($key) && !empty($key->keyinfo) && !empty($key->keyinfo->KeyChangedAt)) { + $changedAt = $key->keyinfo->KeyChangedAt; + $changedAt = Carbon::createFromFormat('Y-m-d\TH:i:s.u\Z', $changedAt, "Europe/London"); + } return view('key') ->with('title', trans('titles.key')) - ->with('cookie', $key) + ->with('keystatus', $key->getStatus()) + ->with('cookie', $key->key) + ->with('changedAt', $changedAt) ->with('cookieLink', $cookieLink); } public function setKey(Request $request) { - $redirUrl = $request->input('redirUrl', ""); $keyToSet = $request->input('keyToSet'); $key = new Key($request->input('keyToSet', '')); - if ($key->getStatus()) { + $status = $key->getStatus(); + if ($status !== null) { # Valid Key $host = $request->header("X_Forwarded_Host", ""); if (empty($host)) { @@ -46,10 +47,7 @@ class KeyController extends Controller $settings = Cookie::get(); $settings['key'] = $keyToSet; $cookieLink = LaravelLocalization::getLocalizedURL(LaravelLocalization::getCurrentLocale(), route('loadSettings', $settings)); - return view('key') - ->with('title', trans('titles.key')) - ->with('cookie', $keyToSet) - ->with('cookieLink', $cookieLink); + return redirect(LaravelLocalization::getLocalizedURL(LaravelLocalization::getCurrentLocale(), route('keyindex'))); } else { $cookieLink = LaravelLocalization::getLocalizedURL(LaravelLocalization::getCurrentLocale(), route('loadSettings', Cookie::get())); return view('key') @@ -74,4 +72,152 @@ class KeyController extends Controller return redirect($url); } } + + public function changeKeyIndex(\App\Models\Key $key, Request $request){ + if(!$key->canChange()){ + return redirect(LaravelLocalization::getLocalizedURL(LaravelLocalization::getCurrentLocale(), route('keyindex'))); + } + return view('keychange', [ + "title" => trans('titles.keychange'), + "key" => $key->key, + "css" => [mix('css/keychange/index.css')] + ]); + } + + public function removeCurrent(\App\Models\Key $key, Request $request){ + if(!$key->canChange()){ + return redirect(LaravelLocalization::getLocalizedURL(LaravelLocalization::getCurrentLocale(), route('keyindex'))); + } + // Reduce Current Key + $res = $key->reduce(self::KEYCHANGE_ADFREE_SEARCHES); + if(empty($res) || empty($res->status) || $res->status !== "success"){ + return redirect(LaravelLocalization::getLocalizedURL(LaravelLocalization::getCurrentLocale(), route('keyindex'))); + } + // Redirect to Cookie Remove URL with redirect to step two + $validUntil = Carbon::now("Europe/London")->addDays(2); + $format = "Y-m-d H:i:s"; + $data = [ + "validUntil" => $validUntil->format($format), + "password" => hash_hmac("sha256", $validUntil->format($format), env("APP_KEY", "WEAK_KEY")), + ]; + $targetUrl = LaravelLocalization::getLocalizedURL(LaravelLocalization::getCurrentLocale(), route('changeKeyTwo', $data)); + $redirUrl = LaravelLocalization::getLocalizedURL(LaravelLocalization::getCurrentLocale(), route('removeCookie', [ + "ir" => $targetUrl + ])); + return redirect($redirUrl); + } + + public function generateNew(\App\Models\Key $key, Request $request){ + // Validate Request Data + $validUntil = $request->input('validUntil', ''); + $password = $request->input('password', ''); + $format = "Y-m-d H:i:s"; + + // Check if Validuntil + $valid = true; + if(empty($validUntil)){ + $valid = false; + }else{ + $validUntil = Carbon::createFromFormat($format, $validUntil, "Europe/London"); + if(!$validUntil){ + $valid = false; + } + } + + if($valid && Carbon::now()->diffInSeconds($validUntil) <= 0){ + $valid = false; + } + if($valid){ + // Check if hash matches + $expectedHash = hash_hmac("sha256", $validUntil->format($format), env("APP_KEY", "WEAK_KEY")); + if(!hash_equals($expectedHash, $password)){ + $valid = false; + } + } + if(!$valid){ + return redirect(LaravelLocalization::getLocalizedURL(LaravelLocalization::getCurrentLocale(), route('keyindex'))); + } + + // Check if the key already was generated + if (!$key->checkForChange("", $password)) { + return redirect(LaravelLocalization::getLocalizedURL(LaravelLocalization::getCurrentLocale(), route('keyindex'))); + } + + + return view('keychangetwo', [ + "title" => trans('titles.keychange'), + "validUntil" => $validUntil, + "css" => [mix('css/keychange/index.css')] + ]); + + } + + public function generateNewPost(\App\Models\Key $key, Request $request){ + // Validate Request Data + $validUntil = $request->input('validUntil', ''); + $password = $request->input('password', ''); + $format = "Y-m-d H:i:s"; + + // Check if Validuntil + $valid = true; + if(empty($validUntil)){ + $valid = false; + }else{ + $validUntil = Carbon::createFromFormat($format, $validUntil, "Europe/London"); + if(!$validUntil){ + $valid = false; + } + } + + if($valid && Carbon::now()->diffInSeconds($validUntil) <= 0){ + $valid = false; + } + if($valid){ + // Check if hash matches + $expectedHash = hash_hmac("sha256", $validUntil->format($format), env("APP_KEY", "WEAK_KEY")); + if(!hash_equals($expectedHash, $password)){ + $valid = false; + } + } + if(!$valid){ + return redirect(LaravelLocalization::getLocalizedURL(LaravelLocalization::getCurrentLocale(), route('keyindex'))); + } + + $validator = Validator::make($request->all(), [ + 'newkey' => 'required|min:4|max:20', + ]); + if($validator->fails()) { + $data = [ + "validUntil" => $validUntil->format($format), + "password" => hash_hmac("sha256", $validUntil->format($format), env("APP_KEY", "WEAK_KEY")), + "newkey" => $request->input('newkey', ''), + ]; + $targetUrl = LaravelLocalization::getLocalizedURL(LaravelLocalization::getCurrentLocale(), route('changeKeyTwo', $data)); + return redirect($targetUrl); + } + + $newkey = $request->input('newkey', ''); + + $characters = '0123456789abcdefghijklmnopqrstuvwxyz'; + $randomSuffix = ""; + $suffixCount = 3; + for($i = 0; $i < $suffixCount; $i++){ + $randomSuffix .= $characters[rand(0, strlen($characters)-1)]; + } + $newkey = $newkey . $randomSuffix; + + if($key->checkForChange($newkey, $password)){ + $result = $key->generateKey(null, self::KEYCHANGE_ADFREE_SEARCHES, $newkey, "Schlüssel gewechselt. Hash $password"); + if(!empty($result)){ + Cookie::queue('key', $result, 525600, '/', null, false, false); + return redirect(LaravelLocalization::getLocalizedURL(LaravelLocalization::getCurrentLocale(), route('changeKeyThree', ["newkey" => $result]))); + } + } + $data = [ + "validUntil" => $validUntil->format($format), + "password" => hash_hmac("sha256", $validUntil->format($format), env("APP_KEY", "WEAK_KEY")), + ]; + $targetUrl = LaravelLocalization::getLocalizedURL(LaravelLocalization::getCurrentLocale(), route('changeKeyTwo', $data)); + return redirect($targetUrl); + } } diff --git a/app/Http/Controllers/LanguageController.php b/app/Http/Controllers/LanguageController.php index 653a40b222983863ebded8ace5f404d34bd62270..ee6ee3557bbdc2c90fb7e7dd96c669e1476ddd2b 100644 --- a/app/Http/Controllers/LanguageController.php +++ b/app/Http/Controllers/LanguageController.php @@ -119,7 +119,7 @@ class LanguageController extends Controller foreach ($languages as $lang => $value) { if ($lang !== $to) { - $langs = array_add($langs, $lang, $lang); + $langs[$lang] = $lang; } } if (!isset($languages[$to])) { diff --git a/app/Http/Controllers/MailController.php b/app/Http/Controllers/MailController.php index 4c4ebcb90dd4a29e80830d1bd51f38bee9721cd0..a75018b9f3195240799b75ca0b44c0b13e463ab2 100644 --- a/app/Http/Controllers/MailController.php +++ b/app/Http/Controllers/MailController.php @@ -10,8 +10,8 @@ use LaravelLocalization; use Mail; use Log; use Validator; -use \IBAN; -use \IBANCountry; +use \PHP_IBAN\IBAN; +use \PHP_IBAN\IBANCountry; class MailController extends Controller { @@ -197,7 +197,7 @@ class MailController extends Controller # Validate Email if (!filter_var($email, FILTER_VALIDATE_EMAIL)) { - $email = "anonymous@suma-ev.de"; + $email = ""; } if(($private && (empty($firstname) || empty($lastname))) || (!$private && empty($company))){ $messageToUser = trans('spende.error.name'); @@ -220,7 +220,7 @@ class MailController extends Controller $betrag = round($betrag, 2, PHP_ROUND_HALF_DOWN); # Generating personalised key for donor - $key = app('App\Models\Key')->generateKey($betrag); + $key = app('App\Models\Key')->generateKey($betrag, null, null, 'Für ' . $betrag . '€ aufgeladen am '. date("d.m.Y")); try { $postdata = [ diff --git a/app/Http/Controllers/MetaGerSearch.php b/app/Http/Controllers/MetaGerSearch.php index d1d1f592684015da37811d1e7e0a83d48bdaa1ed..aa4b076a8b8c0e7fd566d56a8a73b96c1a553627 100644 --- a/app/Http/Controllers/MetaGerSearch.php +++ b/app/Http/Controllers/MetaGerSearch.php @@ -93,6 +93,21 @@ class MetaGerSearch extends Controller # Ergebnisse der Suchmaschinen kombinieren: $metager->prepareResults($timings); + $admitad = []; + $adgoal = []; + if(!$metager->isApiAuthorized() && !$metager->isDummy()){ + $newAdmitad = new \App\Models\Admitad($metager); + if(!empty($newAdmitad->hash)){ + $admitad[] = $newAdmitad; + } + $newAdgoal = new \App\Models\Adgoal($metager); + if(!empty($newAdgoal->hash)){ + $adgoal[] = $newAdgoal; + } + } + + $metager->parseAffiliates($admitad); + $metager->parseAffiliates($adgoal); $finished = true; foreach ($metager->getEngines() as $engine) { @@ -106,10 +121,8 @@ class MetaGerSearch extends Controller "metager" => [ "apiAuthorized" => $metager->isApiAuthorized(), ], - "adgoal" => [ - "loaded" => $metager->isAdgoalLoaded(), - "adgoalHash" => $metager->getAdgoalHash(), - ], + "admitad" => $admitad, + "adgoal" => $adgoal, "engines" => $metager->getEngines(), ], 60 * 60); } catch (\Exception $e) { @@ -190,14 +203,14 @@ class MetaGerSearch extends Controller $engines = $cached["engines"]; $adgoal = $cached["adgoal"]; + $admitad = $cached["admitad"]; $mg = $cached["metager"]; $metager = new MetaGer(substr($hash, strpos($hash, "loader_") + 7)); $metager->setApiAuthorized($mg["apiAuthorized"]); - $metager->setAdgoalLoaded($adgoal["loaded"]); - $metager->setAdgoalHash($adgoal["adgoalHash"]); $metager->parseFormData($request, false); + $metager->setJsEnabled(true); # Nach Spezialsuchen überprüfen: $metager->checkSpecialSearches($request); $metager->restoreEngines($engines); @@ -210,6 +223,20 @@ class MetaGerSearch extends Controller $metager->rankAll(); $metager->prepareResults(); + if(!$metager->isApiAuthorized() && !$metager->isDummy()){ + $newAdmitad = new \App\Models\Admitad($metager); + if(!empty($newAdmitad->hash)){ + $admitad[] = $newAdmitad; + } + $newAdgoal = new \App\Models\Adgoal($metager); + if(!empty($newAdgoal->hash)){ + $adgoal[] = $newAdgoal; + } + } + + $admitadFinished = $metager->parseAffiliates($admitad); + $adgoalFinished = $metager->parseAffiliates($adgoal); + $result = [ 'finished' => true, 'newResults' => [], @@ -256,7 +283,7 @@ class MetaGerSearch extends Controller } } - if (!$metager->isAdgoalLoaded()) { + if (!$adgoalFinished || !$admitadFinished) { $finished = false; } @@ -273,10 +300,8 @@ class MetaGerSearch extends Controller "metager" => [ "apiAuthorized" => $metager->isApiAuthorized(), ], - "adgoal" => [ - "loaded" => $metager->isAdgoalLoaded(), - "adgoalHash" => $metager->getAdgoalHash(), - ], + "admitad" => $admitad, + "adgoal" => $adgoal, "engines" => $metager->getEngines(), ], 1 * 60); diff --git a/app/Http/Controllers/SettingsController.php b/app/Http/Controllers/SettingsController.php index 8a637a2a1e42d465a825e4a190828c8064f77c52..374209010d2e36156db9d915a870923c1a7f7744 100644 --- a/app/Http/Controllers/SettingsController.php +++ b/app/Http/Controllers/SettingsController.php @@ -56,7 +56,7 @@ class SettingsController extends Controller $cookies = Cookie::get(); $settingActive = false; foreach ($cookies as $key => $value) { - if (\starts_with($key, [$fokus . "_engine_", $fokus . "_setting_"]) || strpos($key, $fokus . '_blpage') === 0 || $key === 'dark_mode' || $key === 'new_tab' || $key === 'key' || $key === 'zitate') { + if (stripos($key, $fokus . "_engine_") === 0 || stripos($key, $fokus . "_setting_") === 0 || strpos($key, $fokus . '_blpage') === 0 || $key === 'dark_mode' || $key === 'new_tab' || $key === 'key' || $key === 'zitate') { $settingActive = true; } } @@ -250,7 +250,7 @@ class SettingsController extends Controller $cookies = Cookie::get(); foreach ($cookies as $key => $value) { - if (\starts_with($key, [$fokus . "_engine_", $fokus . "_setting_"])) { + if (stripos($key, $fokus . "_engine_") === 0 || stripos($key, $fokus . "_setting_") === 0) { $path = \Request::path(); $cookiePath = "/" . substr($path, 0, strpos($path, "meta/") + 5); Cookie::queue($key, "", 0, $cookiePath, null, false, false); diff --git a/app/Http/Controllers/StartpageController.php b/app/Http/Controllers/StartpageController.php index 6369c87ad882aa7f61020387c8d9bbb880e55407..edae97096f9be10c8f6aeb10b73e9a49c6c1a18b 100644 --- a/app/Http/Controllers/StartpageController.php +++ b/app/Http/Controllers/StartpageController.php @@ -73,12 +73,6 @@ class StartpageController extends Controller return view($subpage, ['title' => 'Datenschutz Richtlinien']); } - public function loadLocalPage($locale = "de", $subpage = "datenschutz") - { - \App::setLocale($locale); - return loadPage($subpage); - } - public function loadPlugin(Request $request, $locale = "de") { $link = action('MetaGerSearch@search', []); diff --git a/app/Http/Controllers/Stresstest.php b/app/Http/Controllers/Stresstest.php index a4114a8c6c4c9f7766c78c55a406ead2d65aa7f0..402c4abba5836ebb7354e077700c2e29459766c8 100644 --- a/app/Http/Controllers/Stresstest.php +++ b/app/Http/Controllers/Stresstest.php @@ -24,7 +24,6 @@ class Stresstest extends MetaGerSearch # deactivates adgoal $metager->setDummy(true); - $metager->setAdgoalHash(true); parent::search($request, $metager, $timing); } diff --git a/app/Http/Middleware/BrowserVerification.php b/app/Http/Middleware/BrowserVerification.php index ecd9b76a2df4b270e3a4734ff49b9845641b6326..8069d2684aaa533cc3bfc2d4a80ea77b88fe18ae 100644 --- a/app/Http/Middleware/BrowserVerification.php +++ b/app/Http/Middleware/BrowserVerification.php @@ -17,7 +17,7 @@ class BrowserVerification * @param \Closure $next * @return mixed */ - public function handle($request, Closure $next) + public function handle($request, Closure $next, $route = "resultpage") { $bvEnabled = config("metager.metager.browserverification_enabled"); @@ -42,6 +42,7 @@ class BrowserVerification } header('X-Accel-Buffering: no'); + //use parameter for middleware to skip this when using associator if (($request->filled("loadMore") && Cache::has($request->input("loadMore"))) || app('App\Models\Key')->getStatus()) { return $next($request); } @@ -83,7 +84,7 @@ class BrowserVerification $params = $request->all(); $params["mgv"] = $key; - $url = route("resultpage", $params); + $url = route($route, $params); echo(view('layouts.resultpage.unverifiedResultPage') ->with('url', $url) diff --git a/app/Http/Middleware/HumanVerification.php b/app/Http/Middleware/HumanVerification.php index d38133150635a5487926aee6df36642c5ef9c9b6..202e52face64f290bf18e1caf66ae46de9ccbfaf 100644 --- a/app/Http/Middleware/HumanVerification.php +++ b/app/Http/Middleware/HumanVerification.php @@ -46,6 +46,8 @@ class HumanVerification * If someone that uses a bot finds this out we * might have to change it at some point. */ + + //use parameter for middleware to skip this when using associator if (!env('BOT_PROTECTION', false) || app('App\Models\Key')->getStatus()) { $update = false; return $next($request); diff --git a/app/Http/Middleware/RemoveKey.php b/app/Http/Middleware/RemoveKey.php index 5b1c0be94cb16640e1d7021cf61c743995df7590..a65dbf1daa5326666ace41380aa7260ef7f5e530 100644 --- a/app/Http/Middleware/RemoveKey.php +++ b/app/Http/Middleware/RemoveKey.php @@ -17,7 +17,7 @@ class RemoveKey public function handle($request, Closure $next) { // Check if a wrong Key Cookie is set and if so remove it - if(Cookie::has("key") && !app('App\Models\Key')->getStatus()){ + if(Cookie::has("key") && app('App\Models\Key')->getStatus() === null){ return redirect(route("removeCookie", ["ir" => url()->full()])); } return $next($request); diff --git a/app/MetaGer.php b/app/MetaGer.php index 1dc4284128df25827ca6090957874baa7b899820..76a8a40d556d5725aeee8dbfb187fef09e7ac4ad 100644 --- a/app/MetaGer.php +++ b/app/MetaGer.php @@ -48,6 +48,7 @@ class MetaGer protected $availableFoki = []; protected $startCount = 0; protected $canCache = false; + protected $javascript = false; # Daten über die Abfrage$ protected $ip; protected $useragent; @@ -148,7 +149,7 @@ class MetaGer $focusPages = []; foreach ($this->request->all() as $key => $value) { - if (starts_with($key, 'engine_') && $value === 'on') { + if (stripos($key, 'engine_') === 0 && $value === 'on') { $focusPages[] = $key; } } @@ -213,7 +214,15 @@ class MetaGer ->with('browser', (new Agent())->browser()) ->with('fokus', $this->fokus); break; - + case 'rss20': + return view('resultpages.metager3resultsrss20') + ->with('results', $viewResults) + ->with('eingabe', $this->eingabe) + ->with('apiAuthorized', $this->apiAuthorized) + ->with('metager', $this) + ->with('resultcount', sizeof($viewResults)) + ->with('fokus', $this->fokus); + break; case 'api': return view('resultpages.metager3resultsatom10', ['eingabe' => $this->eingabe, 'resultcount' => sizeof($viewResults), 'key' => $this->apiKey, 'metager' => $this]); break; @@ -307,33 +316,12 @@ class MetaGer if (empty($this->adgoalLoaded)) { $this->adgoalLoaded = false; } - if (!$this->apiAuthorized && !$this->adgoalLoaded && !$this->dummy) { - if (empty($this->adgoalHash)) { - if (!empty($this->jskey)) { - $js = Redis::connection('cache')->lpop("js" . $this->jskey); - if ($js !== null && boolval($js)) { - $this->javascript = true; - } - } - $this->adgoalHash = \App\Models\Adgoal::startAdgoal($this->results); - if (!empty($timings)) { - $timings["prepareResults"]["started adgoal"] = microtime(true) - $timings["starttime"]; - } - } - - if (!$this->javascript) { - $this->adgoalLoaded = \App\Models\Adgoal::parseAdgoal($this->results, $this->adgoalHash, true); - if (!empty($timings)) { - $timings["prepareResults"]["parsed adgoal"] = microtime(true) - $timings["starttime"]; - } - } else { - $this->adgoalLoaded = \App\Models\Adgoal::parseAdgoal($this->results, $this->adgoalHash, false); - if (!empty($timings)) { - $timings["prepareResults"]["parsed adgoal"] = microtime(true) - $timings["starttime"]; - } + + if (!empty($this->jskey)) { + $js = Redis::connection('cache')->lpop("js" . $this->jskey); + if ($js !== null && boolval($js)) { + $this->javascript = true; } - } else { - $this->adgoalLoaded = true; } # Human Verification @@ -435,7 +423,26 @@ class MetaGer } } - + /** + * @param \App\Models\Admitad[] $admitads + * @param Boolean $wait Wait for Results? + * @return Boolean whether or not all Admitad Objects are finished + */ + public function parseAffiliates(&$affiliates){ + $wait = false; + $finished = true; + if(!$this->javascript){ + $wait = true; + } + foreach ($affiliates as $affiliate) { + $affiliate->fetchAffiliates($wait); + $affiliate->parseAffiliates($this->results); + if(!$affiliate->finished){ + $finished = false; + } + } + return $finished; + } public function humanVerification(&$results) { @@ -1108,7 +1115,7 @@ class MetaGer $this->out = $request->input('out', "html"); # Standard output format html - if ($this->out !== "html" && $this->out !== "json" && $this->out !== "results" && $this->out !== "results-with-style" && $this->out !== "result-count" && $this->out !== "atom10" && $this->out !== "api") { + if ($this->out !== "html" && $this->out !== "json" && $this->out !== "results" && $this->out !== "results-with-style" && $this->out !== "result-count" && $this->out !== "atom10" && $this->out !== "api" && $this->out !== "rss20") { $this->out = "html"; } # Wir schalten den Cache aus, wenn die Ergebniszahl überprüft werden soll @@ -1503,7 +1510,6 @@ class MetaGer $logEntry .= " time=" . round((microtime(true) - $this->starttime), 2) . " serv=" . $this->fokus; $logEntry .= " interface=" . LaravelLocalization::getCurrentLocale(); $logEntry .= " sprachfilter=" . $this->lang; - $logEntry .= " key=" . $this->apiKey; $logEntry .= " eingabe=" . $this->eingabe; $logEntry = preg_replace("/\n+/", " ", $logEntry); @@ -1678,7 +1684,7 @@ class MetaGer $foki = array_keys($sumaFile['foki']); foreach ($cookies as $key => $value) { - if (starts_with($key, [$this->getFokus() . "_setting_", $this->getFokus() . "_engine_", $this->getFokus() . "_blpage"])) { + if (in_array($key, [$this->getFokus() . "_setting_", $this->getFokus() . "_engine_", $this->getFokus() . "_blpage"])) { $count++; continue; } @@ -1718,6 +1724,9 @@ class MetaGer $this->results = $results; } + /** + * @return \App\Models\Result[] + */ public function getResults() { return $this->results; @@ -1891,26 +1900,6 @@ class MetaGer return $this->engines; } - public function setAdgoalHash($hash) - { - $this->adgoalHash = $hash; - } - - public function getAdgoalHash() - { - return $this->adgoalHash; - } - - public function isAdgoalLoaded() - { - return $this->adgoalLoaded; - } - - public function setAdgoalLoaded($adgoalLoaded) - { - $this->adgoalLoaded = $adgoalLoaded; - } - public function isApiAuthorized() { return $this->apiAuthorized; @@ -1931,6 +1920,17 @@ class MetaGer return $this->headerPrinted; } + public function isDummy(){ + return $this->dummy; + } + + public function jsEnabled() { + return $this->javascript; + } + + public function setJsEnabled(bool $bool){ + $this->javascript = $bool; + } /** * Used by JS result loader to restore MetaGer Object of previous request */ diff --git a/app/Models/Adgoal.php b/app/Models/Adgoal.php index 38ecc00bd3bffcdfa1014e4d9e784b7bcfdccd30..714b8cb84bfee0cd9ff06804635835bc766489a6 100644 --- a/app/Models/Adgoal.php +++ b/app/Models/Adgoal.php @@ -22,29 +22,47 @@ class Adgoal "lk","sh","kn","lc","pm","vc","sd","sr","za","kr","sz","sy","tj","tw","tz","th","tg","to","tt","td","cz","tn", "tm","tc","tv","tr","us","ug","ua","xx","hu","uy","uz","vu","va","ve","ae","vn","wf","cx","by","eh","ww","zr","cf","cy",]; - public static function startAdgoal(&$results) + + public $hash; + public $finished = false; // Is true when the Request was sent to and read from Admitad App + private $affiliates = null; + private $startTime; + + /** + * Creates a new Adgoal object which will start a request for affiliate links + * based on a result List from MetaGer. + * It will parse the Links of the results and query any affiliate shops. + * + * @param \App\MetaGer $metager + */ + public function __construct(&$metager) { + $this->startTime = microtime(true); $publicKey = getenv('adgoal_public'); $privateKey = getenv('adgoal_private'); if ($publicKey === false) { return true; } + $results = $metager->getResults(); $linkList = ""; foreach ($results as $result) { if (!$result->new) { continue; } - $link = $result->link; + $link = $result->originalLink; if (strpos($link, "http") !== 0) { $link = "http://" . $link; } $linkList .= $link . ","; } + if(empty($linkList)){ + return; + } $linkList = rtrim($linkList, ","); # Hashwert - $hash = md5($linkList . $privateKey); + $this->hash = md5($linkList . $privateKey); $link = "https://xf.gdprvalidate.de/v4/check"; @@ -73,14 +91,14 @@ class Adgoal "key" => $publicKey, "panel" => "ZMkW9eSKJS", "member" => "338b9Bnm", - "signature" => $hash, + "signature" => $this->hash, "links" => $linkList, "country" => $country, ]; // Submit fetch job to worker $mission = [ - "resulthash" => $hash, + "resulthash" => $this->hash, "url" => $link, "useragent" => "Mozilla/5.0 (X11; Ubuntu; Linux x86_64; rv:81.0) Gecko/20100101 Firefox/81.0", "username" => null, @@ -97,76 +115,92 @@ class Adgoal ]; $mission = json_encode($mission); Redis::rpush(\App\MetaGer::FETCHQUEUE_KEY, $mission); - - return $hash; } - - public static function parseAdgoal(&$results, $hash, $waitForResult) - { - # Wait for result - $startTime = microtime(true); - $answer = null; - - # Hash is true if Adgoal request wasn't started in the first place - if ($hash === true) { - return true; + + public function fetchAffiliates($wait = false){ + if($this->affiliates !== null){ + return; } - - if ($waitForResult) { + + $answer = null; + $startTime = microtime(true); + if($wait){ while (microtime(true) - $startTime < 5) { - $answer = Cache::get($hash); + $answer = Cache::get($this->hash); if ($answer === null) { usleep(50 * 1000); } else { break; } } - } else { - $answer = Cache::get($hash); + }else{ + $answer = Cache::get($this->hash); } - if ($answer === null) { - return false; + $answer = json_decode($answer, true); + + // If the fetcher had an Error + if($answer === "no-result"){ + $this->affiliates = []; + return; } - - try { - $answer = json_decode($answer, true); - foreach ($answer as $partnershop) { - $targetUrl = $partnershop["url"]; - - $tld = $partnershop["tld"]; - $targetHost = parse_url($targetUrl, PHP_URL_HOST); - - /* - Adgoal sometimes returns affiliate Links for every URL - That's why we check if the corresponding TLD matches the orginial URL - */ - if($targetHost !== false && stripos($targetHost, $tld) === false){ - continue; - } + if(empty($answer) && !is_array($answer)){ + return; + } - foreach ($results as $result) { - if ($result->link === $targetUrl && !$result->partnershop) { - # Ein Advertiser gefunden - if ($result->image !== "") { - $result->logo = $partnershop["logo"]; - } else { - $result->image = $partnershop["logo"]; - } + $this->affiliates = $answer; + } - # Den Link hinzufügen: - $result->link = $partnershop["click_url"]; - $result->partnershop = true; - $result->changed = true; + /** + * Converts all Affiliate Links. + * + * @param \App\Models\Result[] $results + */ + public function parseAffiliates(&$results) + { + if($this->finished || $this->affiliates === null){ + return; + } + + foreach ($this->affiliates as $partnershop) { + $targetUrl = $partnershop["url"]; + + $tld = $partnershop["tld"]; + + // Sometimes TLD is null + if(empty($tld)){ + continue; + } + + $targetHost = parse_url($targetUrl, PHP_URL_HOST); + + /* + Adgoal sometimes returns affiliate Links for every URL + That's why we check if the corresponding TLD matches the orginial URL + */ + if($targetHost !== false && stripos($targetHost, $tld) === false){ + continue; + } + $preference = config("metager.metager.affiliate_preference", "adgoal"); + foreach ($results as $result) { + if ($result->originalLink === $targetUrl && (config("metager.metager.affiliate_preference", "adgoal") === "adgoal" || !$result->partnershop)) { + # Ein Advertiser gefunden + if ($result->image !== "" && !$result->partnershop) { + $result->logo = $partnershop["logo"]; + } else { + $result->image = $partnershop["logo"]; } + + # Den Link hinzufügen: + $result->link = $partnershop["click_url"]; + $result->partnershop = true; + $result->changed = true; } } - } catch (\ErrorException $e) { - Log::error($e->getMessage()); - } finally { - $requestTime = microtime(true) - $startTime; - \App\PrometheusExporter::Duration($requestTime, "adgoal"); } - return true; + + $requestTime = microtime(true) - $this->startTime; + \App\PrometheusExporter::Duration($requestTime, "adgoal"); + $this->finished = true; } } diff --git a/app/Models/Admitad.php b/app/Models/Admitad.php new file mode 100644 index 0000000000000000000000000000000000000000..67546117eec329577a481ba147354671fc3d8b96 --- /dev/null +++ b/app/Models/Admitad.php @@ -0,0 +1,154 @@ +<?php + +namespace App\Models; + +use Cache; +use Log; +use LaravelLocalization; +use Illuminate\Support\Facades\Redis; + +class Admitad +{ + const VALID_LANGS = [ + "de", + "en" + ]; + + public $hash; + public $finished = false; // Is true when the Request was sent to and read from Admitad App + private $affiliates = null; + + /** + * Creates a new Admitad object which will start a request for affiliate links + * based on a result List from MetaGer. + * It will parse the Links of the results and query any affiliate shops. + * + * @param \App\MetaGer $metager + */ + public function __construct(&$metager) + { + $results = $metager->getResults(); + // Generate a list of URLs + $resultLinks = []; + foreach($results as $result){ + if ($result->new) { + $resultLinks[] = $result->originalLink; + } + } + + if(empty($resultLinks)){ + return; + } + + $lang = LaravelLocalization::getCurrentLocale(); + if(!in_array($lang, self::VALID_LANGS)){ + $lang = "de"; + } + + $requestData = [ + "lang" => $lang, + "urls" => $resultLinks, + ]; + $requestData = json_encode($requestData); + $this->hash = md5($requestData); + + $url = "https://direct.metager.de/check"; + $token = env("ADMITAD_TOKEN", ""); + + // Submit fetch job to worker + $mission = [ + "resulthash" => $this->hash, + "url" => $url, + "useragent" => "Mozilla/5.0 (X11; Ubuntu; Linux x86_64; rv:81.0) Gecko/20100101 Firefox/81.0", + "username" => null, + "password" => null, + "headers" => [ + "Authorization" => "Bearer $token" + ], + "cacheDuration" => 60, + "name" => "Admitad", + "curlopts" => [ + CURLOPT_POST => true, + CURLOPT_POSTFIELDS => $requestData + ] + ]; + $mission = json_encode($mission); + Redis::rpush(\App\MetaGer::FETCHQUEUE_KEY, $mission); + } + + /** + * Fetches the Admitad Response from Redis + * @param Boolean $wait Whether or not to wait for a response + */ + public function fetchAffiliates($wait = false) { + if($this->affiliates !== null){ + return; + } + + $answer = null; + $startTime = microtime(true); + if($wait){ + while (microtime(true) - $startTime < 5) { + $answer = Cache::get($this->hash); + if ($answer === null) { + usleep(50 * 1000); + } else { + break; + } + } + }else{ + $answer = Cache::get($this->hash); + } + $answer = json_decode($answer, true); + + // If the fetcher had an Error + if($answer === "no-result"){ + $this->affiliates = []; + return; + } + + if(empty($answer) || !isset($answer["error"]) || $answer["error"] || !is_array($answer["result"])){ + return; + } + + $this->affiliates = $answer["result"]; + } + + /** + * Converts all Affiliate Links. + * + * @param \App\Models\Result[] $results + */ + public function parseAffiliates(&$results){ + if($this->finished || $this->affiliates === null){ + return; + } + foreach($this->affiliates as $linkResult){ + $originalUrl = $linkResult["originalUrl"]; + $redirUrl = $linkResult["redirUrl"]; + $image = $linkResult["image"]; + + if(empty($redirUrl)){ + // No Partnershop + continue; + } + + foreach ($results as $result) { + if ($result->originalLink === $originalUrl && (config("metager.metager.affiliate_preference", "adgoal") === "admitad" || !$result->partnershop)) { + # Ein Advertiser gefunden + if ($result->image !== "" && !$result->partnershop) { + $result->logo = $image; + } else { + $result->image = $image; + } + + # Den Link hinzufügen: + $result->link = $redirUrl; + $result->partnershop = true; + $result->changed = true; + } + } + } + $this->finished = true; + } +} diff --git a/app/Models/Key.php b/app/Models/Key.php index caef0430f53badc80ab164a30c463a049db8567d..e1fb7f3d27ce3efe0c8563e229f974f0f128e369 100644 --- a/app/Models/Key.php +++ b/app/Models/Key.php @@ -4,12 +4,15 @@ namespace App\Models; use Illuminate\Support\Facades\Redis; use Request; +use \Carbon\Carbon; class Key { public $key; - public $status; # valid key = true, invalid key = false, unidentified key = null + public $status; # Null If Key invalid | false if valid but has no adFreeSearches | true if valid and has adFreeSearches private $keyserver = "https://key.metager.de/"; + public $keyinfo; + const CHANGE_EVERY = 1 * 24 * 60 * 60; public function __construct($key, $status = null) { @@ -25,35 +28,29 @@ class Key { if ($this->key !== '' && $this->status === null) { $this->updateStatus(); - if(empty($this->status)){ + if($this->status === null){ // The user provided an invalid key which we will log to fail2ban $fail2banEnabled = config("metager.metager.fail2ban_enabled"); - if(empty($fail2banEnabled) || !$fail2banEnabled || !env("fail2banurl", false) || !env("fail2banuser") || !env("fail2banpassword")){ - return false; + if (!empty($fail2banEnabled) && $fail2banEnabled && !empty(env("fail2banurl", false)) && !empty(env("fail2banuser")) && !empty(env("fail2banpassword"))) { + // Submit fetch job to worker + $mission = [ + "resulthash" => "captcha", + "url" => env("fail2banurl") . "/mgkeytry/", + "useragent" => "Mozilla/5.0 (X11; Ubuntu; Linux x86_64; rv:81.0) Gecko/20100101 Firefox/81.0", + "username" => env("fail2banuser"), + "password" => env("fail2banpassword"), + "headers" => [ + "ip" => Request::ip() + ], + "cacheDuration" => 0, + "name" => "Captcha", + ]; + $mission = json_encode($mission); + Redis::rpush(\App\MetaGer::FETCHQUEUE_KEY, $mission); } - - // Submit fetch job to worker - $mission = [ - "resulthash" => "captcha", - "url" => env("fail2banurl") . "/mgkeytry/", - "useragent" => "Mozilla/5.0 (X11; Ubuntu; Linux x86_64; rv:81.0) Gecko/20100101 Firefox/81.0", - "username" => env("fail2banuser"), - "password" => env("fail2banpassword"), - "headers" => [ - "ip" => Request::ip() - ], - "cacheDuration" => 0, - "name" => "Captcha", - ]; - $mission = json_encode($mission); - Redis::rpush(\App\MetaGer::FETCHQUEUE_KEY, $mission); } } - if ($this->status === null || $this->status === false) { - return false; - } else { - return true; - } + return $this->status; } public function updateStatus() @@ -71,14 +68,15 @@ class Key try { $link = $this->keyserver . "v2/key/". urlencode($this->key); $result = json_decode(file_get_contents($link, false, $context)); - if ($result->{'apiAccess'} == 'unlimited') { - $this->status = true; - return true; - } else if ($result->{'apiAccess'} == 'normal' && $result->{'adFreeSearches'} > 0){ - $this->status = true; + if(!empty($result)){ + $this->keyinfo = $result; + if($this->keyinfo->adFreeSearches > 0 || $this->keyinfo->apiAccess === "unlimited"){ + $this->status = true; + }else{ + $this->status = false; + } return true; - } else { - $this->status = false; + }else{ return false; } } catch (\ErrorException $e) { @@ -118,15 +116,26 @@ class Key return false; } } - public function generateKey($payment) + public function generateKey($payment = null, $adFreeSearches = null, $key = null, $notes = "") { $authKey = base64_encode(env("KEY_USER", "test") . ':' . env("KEY_PASSWORD", "test")); - $postdata = http_build_query(array( - 'payment' => $payment, + $postdata = array( 'apiAccess' => 'normal', - 'notes' => 'Fuer ' . $payment . '€ aufgeladen am '. date("d.m.Y"), - 'expiresAfterDays' => 365 - )); + 'expiresAfterDays' => 365, + 'notes' => $notes + ); + if(!empty($key)){ + $postdata["key"] = $key; + } + + if(!empty($payment)){ + $postdata["payment"] = $payment; + }else if(!empty($adFreeSearches)){ + $postdata["adFreeSearches"] = $adFreeSearches; + }else{ + return false; + } + $postdata = http_build_query($postdata, "", "&", PHP_QUERY_RFC3986); $opts = array( 'http' => array( 'method' => 'POST', @@ -149,4 +158,89 @@ class Key return false; } } + + public function reduce($count){ + $authKey = base64_encode(env("KEY_USER", "test") . ':' . env("KEY_PASSWORD", "test")); + $postdata = http_build_query(array( + 'adFreeSearches' => $count, + )); + $opts = array( + 'http' => array( + 'method' => 'POST', + 'header' => [ + 'Content-type: application/x-www-form-urlencoded', + 'Authorization: Basic ' . $authKey + ], + 'content' => $postdata, + 'timeout' => 5 + ), + ); + + $context = stream_context_create($opts); + + try { + $link = $this->keyserver . "v2/key/" . $this->key . "/reduce-searches"; + $result = json_decode(file_get_contents($link, false, $context)); + return $result; + } catch (\ErrorException $e) { + return false; + } + } + + /** + * Tells if this key is liable to change to a custom key + * Currently only members are allowed to do so and only every 2 days + * Also only the original member key is allowed to be changed + * + * @return boolean + */ + public function canChange(){ + if(empty($this->status) || !preg_match("/^Mitgliederschlüssel\./", $this->keyinfo->notes) || $this->keyinfo->adFreeSearches < \App\Http\Controllers\KeyController::KEYCHANGE_ADFREE_SEARCHES){ + return false; + } + if(!empty($this->keyinfo->KeyChangedAt)){ + // "2021-03-09T09:19:44.000Z" + $keyChangedAt = Carbon::createFromTimeString($this->keyinfo->KeyChangedAt, 'Europe/London'); + if($keyChangedAt->diffInSeconds(Carbon::now()) > self::CHANGE_EVERY){ + return true; + }else{ + return false; + } + } + return true; + } + + public function checkForChange($newkey = "", $hash){ + $authKey = base64_encode(env("KEY_USER", "test") . ':' . env("KEY_PASSWORD", "test")); + $postdata = http_build_query(array( + 'hash' => $hash, + 'key' => $newkey, + )); + $opts = array( + 'http' => array( + 'method' => 'POST', + 'header' => [ + 'Content-type: application/x-www-form-urlencoded', + 'Authorization: Basic ' . $authKey + ], + 'content' => $postdata, + 'timeout' => 5 + ), + ); + + $context = stream_context_create($opts); + + try { + $link = $this->keyserver . "v2/key/can-change"; + $result = json_decode(file_get_contents($link, false, $context)); + + if(!empty($result) && $result->status === "success" && empty($result->results)){ + return true; + }else{ + return false; + } + } catch (\ErrorException $e) { + return false; + } + } } diff --git a/app/Models/Result.php b/app/Models/Result.php index c4a3ef48cea7e8b430adb54c512acfd752cf318d..8123420703ae88a31df326d75330b4d101db3a11 100644 --- a/app/Models/Result.php +++ b/app/Models/Result.php @@ -2,6 +2,7 @@ namespace App\Models; + /* Die Klasse Result sammelt alle Informationen über ein einzelnes Suchergebnis. * Die Results werden von den Suchmaschinenspezifischen Parser-Skripten erstellt. */ @@ -9,6 +10,7 @@ class Result { public $provider; # Die Engine von der das Suchergebnis kommt public $titel; # Der Groß Angezeigte Name für das Suchergebnis + public $originalLink; public $link; # Der Link auf die Ergebnisseite public $anzeigeLink; # Der tatsächlich angezeigte Link (rein optisch) public $descr; # Die eventuell gekürzte Beschreibung des Suchergebnisses @@ -41,6 +43,7 @@ class Result $this->provider = $provider; $this->titel = $this->sanitizeText(strip_tags(trim($titel))); $this->link = trim($link); + $this->originalLink = trim($link); $this->anzeigeLink = trim($anzeigeLink); $this->anzeigeLink = preg_replace("/(http[s]{0,1}:\/\/){0,1}(www\.){0,1}/si", "", $this->anzeigeLink); $this->descr = $this->sanitizeText(strip_tags(trim($descr), '<p>')); @@ -422,7 +425,7 @@ class Result */ public function getUrlElements($url) { - if (!starts_with($url, "http")) { + if (stripos($url, "http") !== 0) { $url = "http://" . $url; } diff --git a/chart/templates/deployment.yaml b/chart/templates/deployment.yaml index 79769c933515481006af018d6c48a49752c48876..7d7940cc9d40c0ef7e276939bb2e33ad4ed5129d 100644 --- a/chart/templates/deployment.yaml +++ b/chart/templates/deployment.yaml @@ -179,7 +179,7 @@ spec: {{ toYaml .Values.resourcesNginx | indent 12 }} # Redis Container - name: {{ .Chart.Name }}-redis - image: "redis:5.0.3-alpine" + image: "redis:6" imagePullPolicy: {{ .Values.image.pullPolicy }} command: ["redis-server", "/usr/local/etc/redis/redis.conf"] volumeMounts: @@ -206,7 +206,7 @@ spec: - name: {{ .Chart.Name }}-fetcher image: "{{ .Values.image.repository }}:{{ .Values.image.tag }}" command: ["su"] - args: ["-s", "/bin/sh", "-c", "php artisan requests:fetcher", "nginx"] + args: ["-s", "/bin/sh", "-c", "php artisan requests:fetcher", "www-data"] volumeMounts: - name: secrets mountPath: /html/.env diff --git a/chart/templates/ingress.yaml b/chart/templates/ingress.yaml index 044c6fad45a0bf6ce53a10fbb805abd6de44f0ef..e9306121bdfe9797a392cf3baf2d5fda16034029 100644 --- a/chart/templates/ingress.yaml +++ b/chart/templates/ingress.yaml @@ -57,6 +57,10 @@ spec: backend: serviceName: {{ template "fullname" . }} servicePort: {{ .Values.service.externalPort }} + - path: /wsb + backend: + serviceName: wsb + servicePort: 80 {{- if .Values.service.commonName }} - host: {{ template "hostname" .Values.service.commonName }} http: diff --git a/composer.json b/composer.json index 1255c1b3e02d7dd9dd1159753a3419414ba9adb6..5ae40325f41f0289b2f5fc86dc10373809e46bea 100644 --- a/composer.json +++ b/composer.json @@ -8,54 +8,42 @@ ], "license": "MIT", "require": { - "php": "^7.1.3", - "endclothing/prometheus_client_php": "^1.0", - "fideloper/proxy": "^4.0", - "globalcitizen/php-iban": "^2.6", + "php": "^7.3|^8.0", + "fideloper/proxy": "^4.4", + "fruitcake/laravel-cors": "^2.0", + "globalcitizen/php-iban": "^4.0.0", + "guzzlehttp/guzzle": "^7.0.1", "jenssegers/agent": "^2.6", - "laravel/framework": "5.8.*", - "laravel/tinker": "^1.0", + "laravel/framework": "^8.40", + "laravel/tinker": "^2.5", "mcamara/laravel-localization": "1.6.*", - "mews/captcha": "^2.2", - "symfony/dom-crawler": "^4.1" + "mews/captcha": "^3.2.6", + "promphp/prometheus_client_php": "^2.2", + "symfony/dom-crawler": "^5.2" }, "require-dev": { - "beyondcode/laravel-dump-server": "^1.0", + "facade/ignition": "^2.5", + "fakerphp/faker": "^1.9.1", + "laravel/sail": "^1.0.1", + "mockery/mockery": "^1.4.2", + "nunomaduro/collision": "^5.0", + "phpunit/phpunit": "^9.3.3", "browserstack/browserstack-local": "^1.1", - "filp/whoops": "^2.0", - "fzaninotto/faker": "^1.4", - "laravel/dusk": "^5.0", - "mockery/mockery": "^1.0", - "nunomaduro/collision": "^3.0", - "php-webdriver/webdriver": "^1.6", - "phpunit/phpunit": "^7.5" - }, - "config": { - "optimize-autoloader": true, - "preferred-install": "dist", - "sort-packages": true - }, - "extra": { - "laravel": { - "dont-discover": [] - } + "laravel/dusk": "^6.15", + "php-webdriver/webdriver": "^1.6" }, "autoload": { "psr-4": { - "App\\": "app/" - }, - "classmap": [ - "database/seeds", - "database/factories" - ] + "App\\": "app/", + "Database\\Factories\\": "database/factories/", + "Database\\Seeders\\": "database/seeders/" + } }, "autoload-dev": { "psr-4": { "Tests\\": "tests/" } }, - "minimum-stability": "dev", - "prefer-stable": true, "scripts": { "post-autoload-dump": [ "Illuminate\\Foundation\\ComposerScripts::postAutoloadDump", @@ -67,5 +55,17 @@ "post-create-project-cmd": [ "@php artisan key:generate --ansi" ] - } -} \ No newline at end of file + }, + "extra": { + "laravel": { + "dont-discover": [] + } + }, + "config": { + "optimize-autoloader": true, + "preferred-install": "dist", + "sort-packages": true + }, + "minimum-stability": "dev", + "prefer-stable": true +} diff --git a/composer.lock b/composer.lock new file mode 100644 index 0000000000000000000000000000000000000000..16b5ad52c3898007a10254853f6776eb9541104f --- /dev/null +++ b/composer.lock @@ -0,0 +1,8197 @@ +{ + "_readme": [ + "This file locks the dependencies of your project to a known state", + "Read more about it at https://getcomposer.org/doc/01-basic-usage.md#installing-dependencies", + "This file is @generated automatically" + ], + "content-hash": "aae0bd416c56bf2e37fdbcbb87c0bb10", + "packages": [ + { + "name": "asm89/stack-cors", + "version": "v2.0.3", + "source": { + "type": "git", + "url": "https://github.com/asm89/stack-cors.git", + "reference": "9cb795bf30988e8c96dd3c40623c48a877bc6714" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/asm89/stack-cors/zipball/9cb795bf30988e8c96dd3c40623c48a877bc6714", + "reference": "9cb795bf30988e8c96dd3c40623c48a877bc6714", + "shasum": "" + }, + "require": { + "php": "^7.0|^8.0", + "symfony/http-foundation": "~2.7|~3.0|~4.0|~5.0", + "symfony/http-kernel": "~2.7|~3.0|~4.0|~5.0" + }, + "require-dev": { + "phpunit/phpunit": "^6|^7|^8|^9", + "squizlabs/php_codesniffer": "^3.5" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "2.0-dev" + } + }, + "autoload": { + "psr-4": { + "Asm89\\Stack\\": "src/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Alexander", + "email": "iam.asm89@gmail.com" + } + ], + "description": "Cross-origin resource sharing library and stack middleware", + "homepage": "https://github.com/asm89/stack-cors", + "keywords": [ + "cors", + "stack" + ], + "support": { + "issues": "https://github.com/asm89/stack-cors/issues", + "source": "https://github.com/asm89/stack-cors/tree/v2.0.3" + }, + "time": "2021-03-11T06:42:03+00:00" + }, + { + "name": "brick/math", + "version": "0.9.2", + "source": { + "type": "git", + "url": "https://github.com/brick/math.git", + "reference": "dff976c2f3487d42c1db75a3b180e2b9f0e72ce0" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/brick/math/zipball/dff976c2f3487d42c1db75a3b180e2b9f0e72ce0", + "reference": "dff976c2f3487d42c1db75a3b180e2b9f0e72ce0", + "shasum": "" + }, + "require": { + "ext-json": "*", + "php": "^7.1 || ^8.0" + }, + "require-dev": { + "php-coveralls/php-coveralls": "^2.2", + "phpunit/phpunit": "^7.5.15 || ^8.5 || ^9.0", + "vimeo/psalm": "4.3.2" + }, + "type": "library", + "autoload": { + "psr-4": { + "Brick\\Math\\": "src/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "description": "Arbitrary-precision arithmetic library", + "keywords": [ + "Arbitrary-precision", + "BigInteger", + "BigRational", + "arithmetic", + "bigdecimal", + "bignum", + "brick", + "math" + ], + "support": { + "issues": "https://github.com/brick/math/issues", + "source": "https://github.com/brick/math/tree/0.9.2" + }, + "funding": [ + { + "url": "https://tidelift.com/funding/github/packagist/brick/math", + "type": "tidelift" + } + ], + "time": "2021-01-20T22:51:39+00:00" + }, + { + "name": "doctrine/inflector", + "version": "2.0.3", + "source": { + "type": "git", + "url": "https://github.com/doctrine/inflector.git", + "reference": "9cf661f4eb38f7c881cac67c75ea9b00bf97b210" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/doctrine/inflector/zipball/9cf661f4eb38f7c881cac67c75ea9b00bf97b210", + "reference": "9cf661f4eb38f7c881cac67c75ea9b00bf97b210", + "shasum": "" + }, + "require": { + "php": "^7.2 || ^8.0" + }, + "require-dev": { + "doctrine/coding-standard": "^7.0", + "phpstan/phpstan": "^0.11", + "phpstan/phpstan-phpunit": "^0.11", + "phpstan/phpstan-strict-rules": "^0.11", + "phpunit/phpunit": "^7.0 || ^8.0 || ^9.0" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "2.0.x-dev" + } + }, + "autoload": { + "psr-4": { + "Doctrine\\Inflector\\": "lib/Doctrine/Inflector" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Guilherme Blanco", + "email": "guilhermeblanco@gmail.com" + }, + { + "name": "Roman Borschel", + "email": "roman@code-factory.org" + }, + { + "name": "Benjamin Eberlei", + "email": "kontakt@beberlei.de" + }, + { + "name": "Jonathan Wage", + "email": "jonwage@gmail.com" + }, + { + "name": "Johannes Schmitt", + "email": "schmittjoh@gmail.com" + } + ], + "description": "PHP Doctrine Inflector is a small library that can perform string manipulations with regard to upper/lowercase and singular/plural forms of words.", + "homepage": "https://www.doctrine-project.org/projects/inflector.html", + "keywords": [ + "inflection", + "inflector", + "lowercase", + "manipulation", + "php", + "plural", + "singular", + "strings", + "uppercase", + "words" + ], + "support": { + "issues": "https://github.com/doctrine/inflector/issues", + "source": "https://github.com/doctrine/inflector/tree/2.0.x" + }, + "funding": [ + { + "url": "https://www.doctrine-project.org/sponsorship.html", + "type": "custom" + }, + { + "url": "https://www.patreon.com/phpdoctrine", + "type": "patreon" + }, + { + "url": "https://tidelift.com/funding/github/packagist/doctrine%2Finflector", + "type": "tidelift" + } + ], + "time": "2020-05-29T15:13:26+00:00" + }, + { + "name": "doctrine/lexer", + "version": "1.2.1", + "source": { + "type": "git", + "url": "https://github.com/doctrine/lexer.git", + "reference": "e864bbf5904cb8f5bb334f99209b48018522f042" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/doctrine/lexer/zipball/e864bbf5904cb8f5bb334f99209b48018522f042", + "reference": "e864bbf5904cb8f5bb334f99209b48018522f042", + "shasum": "" + }, + "require": { + "php": "^7.2 || ^8.0" + }, + "require-dev": { + "doctrine/coding-standard": "^6.0", + "phpstan/phpstan": "^0.11.8", + "phpunit/phpunit": "^8.2" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.2.x-dev" + } + }, + "autoload": { + "psr-4": { + "Doctrine\\Common\\Lexer\\": "lib/Doctrine/Common/Lexer" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Guilherme Blanco", + "email": "guilhermeblanco@gmail.com" + }, + { + "name": "Roman Borschel", + "email": "roman@code-factory.org" + }, + { + "name": "Johannes Schmitt", + "email": "schmittjoh@gmail.com" + } + ], + "description": "PHP Doctrine Lexer parser library that can be used in Top-Down, Recursive Descent Parsers.", + "homepage": "https://www.doctrine-project.org/projects/lexer.html", + "keywords": [ + "annotations", + "docblock", + "lexer", + "parser", + "php" + ], + "support": { + "issues": "https://github.com/doctrine/lexer/issues", + "source": "https://github.com/doctrine/lexer/tree/1.2.1" + }, + "funding": [ + { + "url": "https://www.doctrine-project.org/sponsorship.html", + "type": "custom" + }, + { + "url": "https://www.patreon.com/phpdoctrine", + "type": "patreon" + }, + { + "url": "https://tidelift.com/funding/github/packagist/doctrine%2Flexer", + "type": "tidelift" + } + ], + "time": "2020-05-25T17:44:05+00:00" + }, + { + "name": "dragonmantank/cron-expression", + "version": "v3.1.0", + "source": { + "type": "git", + "url": "https://github.com/dragonmantank/cron-expression.git", + "reference": "7a8c6e56ab3ffcc538d05e8155bb42269abf1a0c" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/dragonmantank/cron-expression/zipball/7a8c6e56ab3ffcc538d05e8155bb42269abf1a0c", + "reference": "7a8c6e56ab3ffcc538d05e8155bb42269abf1a0c", + "shasum": "" + }, + "require": { + "php": "^7.2|^8.0", + "webmozart/assert": "^1.7.0" + }, + "replace": { + "mtdowling/cron-expression": "^1.0" + }, + "require-dev": { + "phpstan/extension-installer": "^1.0", + "phpstan/phpstan": "^0.12", + "phpstan/phpstan-webmozart-assert": "^0.12.7", + "phpunit/phpunit": "^7.0|^8.0|^9.0" + }, + "type": "library", + "autoload": { + "psr-4": { + "Cron\\": "src/Cron/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Chris Tankersley", + "email": "chris@ctankersley.com", + "homepage": "https://github.com/dragonmantank" + } + ], + "description": "CRON for PHP: Calculate the next or previous run date and determine if a CRON expression is due", + "keywords": [ + "cron", + "schedule" + ], + "support": { + "issues": "https://github.com/dragonmantank/cron-expression/issues", + "source": "https://github.com/dragonmantank/cron-expression/tree/v3.1.0" + }, + "funding": [ + { + "url": "https://github.com/dragonmantank", + "type": "github" + } + ], + "time": "2020-11-24T19:55:57+00:00" + }, + { + "name": "egulias/email-validator", + "version": "2.1.25", + "source": { + "type": "git", + "url": "https://github.com/egulias/EmailValidator.git", + "reference": "0dbf5d78455d4d6a41d186da50adc1122ec066f4" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/egulias/EmailValidator/zipball/0dbf5d78455d4d6a41d186da50adc1122ec066f4", + "reference": "0dbf5d78455d4d6a41d186da50adc1122ec066f4", + "shasum": "" + }, + "require": { + "doctrine/lexer": "^1.0.1", + "php": ">=5.5", + "symfony/polyfill-intl-idn": "^1.10" + }, + "require-dev": { + "dominicsayers/isemail": "^3.0.7", + "phpunit/phpunit": "^4.8.36|^7.5.15", + "satooshi/php-coveralls": "^1.0.1" + }, + "suggest": { + "ext-intl": "PHP Internationalization Libraries are required to use the SpoofChecking validation" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "2.1.x-dev" + } + }, + "autoload": { + "psr-4": { + "Egulias\\EmailValidator\\": "src" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Eduardo Gulias Davis" + } + ], + "description": "A library for validating emails against several RFCs", + "homepage": "https://github.com/egulias/EmailValidator", + "keywords": [ + "email", + "emailvalidation", + "emailvalidator", + "validation", + "validator" + ], + "support": { + "issues": "https://github.com/egulias/EmailValidator/issues", + "source": "https://github.com/egulias/EmailValidator/tree/2.1.25" + }, + "funding": [ + { + "url": "https://github.com/egulias", + "type": "github" + } + ], + "time": "2020-12-29T14:50:06+00:00" + }, + { + "name": "fideloper/proxy", + "version": "4.4.1", + "source": { + "type": "git", + "url": "https://github.com/fideloper/TrustedProxy.git", + "reference": "c073b2bd04d1c90e04dc1b787662b558dd65ade0" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/fideloper/TrustedProxy/zipball/c073b2bd04d1c90e04dc1b787662b558dd65ade0", + "reference": "c073b2bd04d1c90e04dc1b787662b558dd65ade0", + "shasum": "" + }, + "require": { + "illuminate/contracts": "^5.0|^6.0|^7.0|^8.0|^9.0", + "php": ">=5.4.0" + }, + "require-dev": { + "illuminate/http": "^5.0|^6.0|^7.0|^8.0|^9.0", + "mockery/mockery": "^1.0", + "phpunit/phpunit": "^6.0" + }, + "type": "library", + "extra": { + "laravel": { + "providers": [ + "Fideloper\\Proxy\\TrustedProxyServiceProvider" + ] + } + }, + "autoload": { + "psr-4": { + "Fideloper\\Proxy\\": "src/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Chris Fidao", + "email": "fideloper@gmail.com" + } + ], + "description": "Set trusted proxies for Laravel", + "keywords": [ + "load balancing", + "proxy", + "trusted proxy" + ], + "support": { + "issues": "https://github.com/fideloper/TrustedProxy/issues", + "source": "https://github.com/fideloper/TrustedProxy/tree/4.4.1" + }, + "time": "2020-10-22T13:48:01+00:00" + }, + { + "name": "fruitcake/laravel-cors", + "version": "v2.0.4", + "source": { + "type": "git", + "url": "https://github.com/fruitcake/laravel-cors.git", + "reference": "a8ccedc7ca95189ead0e407c43b530dc17791d6a" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/fruitcake/laravel-cors/zipball/a8ccedc7ca95189ead0e407c43b530dc17791d6a", + "reference": "a8ccedc7ca95189ead0e407c43b530dc17791d6a", + "shasum": "" + }, + "require": { + "asm89/stack-cors": "^2.0.1", + "illuminate/contracts": "^6|^7|^8|^9", + "illuminate/support": "^6|^7|^8|^9", + "php": ">=7.2", + "symfony/http-foundation": "^4|^5", + "symfony/http-kernel": "^4.3.4|^5" + }, + "require-dev": { + "laravel/framework": "^6|^7|^8", + "orchestra/testbench-dusk": "^4|^5|^6|^7", + "phpunit/phpunit": "^6|^7|^8|^9", + "squizlabs/php_codesniffer": "^3.5" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "2.0-dev" + }, + "laravel": { + "providers": [ + "Fruitcake\\Cors\\CorsServiceProvider" + ] + } + }, + "autoload": { + "psr-4": { + "Fruitcake\\Cors\\": "src/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Fruitcake", + "homepage": "https://fruitcake.nl" + }, + { + "name": "Barry vd. Heuvel", + "email": "barryvdh@gmail.com" + } + ], + "description": "Adds CORS (Cross-Origin Resource Sharing) headers support in your Laravel application", + "keywords": [ + "api", + "cors", + "crossdomain", + "laravel" + ], + "support": { + "issues": "https://github.com/fruitcake/laravel-cors/issues", + "source": "https://github.com/fruitcake/laravel-cors/tree/v2.0.4" + }, + "funding": [ + { + "url": "https://github.com/barryvdh", + "type": "github" + } + ], + "time": "2021-04-26T11:24:25+00:00" + }, + { + "name": "globalcitizen/php-iban", + "version": "v4.0.0", + "source": { + "type": "git", + "url": "https://github.com/globalcitizen/php-iban.git", + "reference": "a8b0a1bbf42f25d977a28270787212542ba7e71d" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/globalcitizen/php-iban/zipball/a8b0a1bbf42f25d977a28270787212542ba7e71d", + "reference": "a8b0a1bbf42f25d977a28270787212542ba7e71d", + "shasum": "" + }, + "type": "library", + "autoload": { + "files": [ + "oophp-iban.php", + "php-iban.php" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "LGPL-3.0-only" + ], + "description": "php-iban is a library for parsing and validating IBAN (and IIBAN) bank account information.", + "support": { + "issues": "https://github.com/globalcitizen/php-iban/issues", + "source": "https://github.com/globalcitizen/php-iban/tree/v4.0.0" + }, + "time": "2020-08-24T08:27:30+00:00" + }, + { + "name": "graham-campbell/result-type", + "version": "v1.0.1", + "source": { + "type": "git", + "url": "https://github.com/GrahamCampbell/Result-Type.git", + "reference": "7e279d2cd5d7fbb156ce46daada972355cea27bb" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/GrahamCampbell/Result-Type/zipball/7e279d2cd5d7fbb156ce46daada972355cea27bb", + "reference": "7e279d2cd5d7fbb156ce46daada972355cea27bb", + "shasum": "" + }, + "require": { + "php": "^7.0|^8.0", + "phpoption/phpoption": "^1.7.3" + }, + "require-dev": { + "phpunit/phpunit": "^6.5|^7.5|^8.5|^9.0" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.0-dev" + } + }, + "autoload": { + "psr-4": { + "GrahamCampbell\\ResultType\\": "src/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Graham Campbell", + "email": "graham@alt-three.com" + } + ], + "description": "An Implementation Of The Result Type", + "keywords": [ + "Graham Campbell", + "GrahamCampbell", + "Result Type", + "Result-Type", + "result" + ], + "support": { + "issues": "https://github.com/GrahamCampbell/Result-Type/issues", + "source": "https://github.com/GrahamCampbell/Result-Type/tree/v1.0.1" + }, + "funding": [ + { + "url": "https://github.com/GrahamCampbell", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/graham-campbell/result-type", + "type": "tidelift" + } + ], + "time": "2020-04-13T13:17:36+00:00" + }, + { + "name": "guzzlehttp/guzzle", + "version": "7.3.0", + "source": { + "type": "git", + "url": "https://github.com/guzzle/guzzle.git", + "reference": "7008573787b430c1c1f650e3722d9bba59967628" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/guzzle/guzzle/zipball/7008573787b430c1c1f650e3722d9bba59967628", + "reference": "7008573787b430c1c1f650e3722d9bba59967628", + "shasum": "" + }, + "require": { + "ext-json": "*", + "guzzlehttp/promises": "^1.4", + "guzzlehttp/psr7": "^1.7 || ^2.0", + "php": "^7.2.5 || ^8.0", + "psr/http-client": "^1.0" + }, + "provide": { + "psr/http-client-implementation": "1.0" + }, + "require-dev": { + "bamarni/composer-bin-plugin": "^1.4.1", + "ext-curl": "*", + "php-http/client-integration-tests": "^3.0", + "phpunit/phpunit": "^8.5.5 || ^9.3.5", + "psr/log": "^1.1" + }, + "suggest": { + "ext-curl": "Required for CURL handler support", + "ext-intl": "Required for Internationalized Domain Name (IDN) support", + "psr/log": "Required for using the Log middleware" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "7.3-dev" + } + }, + "autoload": { + "psr-4": { + "GuzzleHttp\\": "src/" + }, + "files": [ + "src/functions_include.php" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Michael Dowling", + "email": "mtdowling@gmail.com", + "homepage": "https://github.com/mtdowling" + }, + { + "name": "Márk Sági-Kazár", + "email": "mark.sagikazar@gmail.com", + "homepage": "https://sagikazarmark.hu" + } + ], + "description": "Guzzle is a PHP HTTP client library", + "homepage": "http://guzzlephp.org/", + "keywords": [ + "client", + "curl", + "framework", + "http", + "http client", + "psr-18", + "psr-7", + "rest", + "web service" + ], + "support": { + "issues": "https://github.com/guzzle/guzzle/issues", + "source": "https://github.com/guzzle/guzzle/tree/7.3.0" + }, + "funding": [ + { + "url": "https://github.com/GrahamCampbell", + "type": "github" + }, + { + "url": "https://github.com/Nyholm", + "type": "github" + }, + { + "url": "https://github.com/alexeyshockov", + "type": "github" + }, + { + "url": "https://github.com/gmponos", + "type": "github" + } + ], + "time": "2021-03-23T11:33:13+00:00" + }, + { + "name": "guzzlehttp/promises", + "version": "1.4.1", + "source": { + "type": "git", + "url": "https://github.com/guzzle/promises.git", + "reference": "8e7d04f1f6450fef59366c399cfad4b9383aa30d" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/guzzle/promises/zipball/8e7d04f1f6450fef59366c399cfad4b9383aa30d", + "reference": "8e7d04f1f6450fef59366c399cfad4b9383aa30d", + "shasum": "" + }, + "require": { + "php": ">=5.5" + }, + "require-dev": { + "symfony/phpunit-bridge": "^4.4 || ^5.1" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.4-dev" + } + }, + "autoload": { + "psr-4": { + "GuzzleHttp\\Promise\\": "src/" + }, + "files": [ + "src/functions_include.php" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Michael Dowling", + "email": "mtdowling@gmail.com", + "homepage": "https://github.com/mtdowling" + } + ], + "description": "Guzzle promises library", + "keywords": [ + "promise" + ], + "support": { + "issues": "https://github.com/guzzle/promises/issues", + "source": "https://github.com/guzzle/promises/tree/1.4.1" + }, + "time": "2021-03-07T09:25:29+00:00" + }, + { + "name": "guzzlehttp/psr7", + "version": "1.8.2", + "source": { + "type": "git", + "url": "https://github.com/guzzle/psr7.git", + "reference": "dc960a912984efb74d0a90222870c72c87f10c91" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/guzzle/psr7/zipball/dc960a912984efb74d0a90222870c72c87f10c91", + "reference": "dc960a912984efb74d0a90222870c72c87f10c91", + "shasum": "" + }, + "require": { + "php": ">=5.4.0", + "psr/http-message": "~1.0", + "ralouphie/getallheaders": "^2.0.5 || ^3.0.0" + }, + "provide": { + "psr/http-message-implementation": "1.0" + }, + "require-dev": { + "ext-zlib": "*", + "phpunit/phpunit": "~4.8.36 || ^5.7.27 || ^6.5.14 || ^7.5.20 || ^8.5.8 || ^9.3.10" + }, + "suggest": { + "laminas/laminas-httphandlerrunner": "Emit PSR-7 responses" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.7-dev" + } + }, + "autoload": { + "psr-4": { + "GuzzleHttp\\Psr7\\": "src/" + }, + "files": [ + "src/functions_include.php" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Michael Dowling", + "email": "mtdowling@gmail.com", + "homepage": "https://github.com/mtdowling" + }, + { + "name": "Tobias Schultze", + "homepage": "https://github.com/Tobion" + } + ], + "description": "PSR-7 message implementation that also provides common utility methods", + "keywords": [ + "http", + "message", + "psr-7", + "request", + "response", + "stream", + "uri", + "url" + ], + "support": { + "issues": "https://github.com/guzzle/psr7/issues", + "source": "https://github.com/guzzle/psr7/tree/1.8.2" + }, + "time": "2021-04-26T09:17:50+00:00" + }, + { + "name": "intervention/image", + "version": "2.5.1", + "source": { + "type": "git", + "url": "https://github.com/Intervention/image.git", + "reference": "abbf18d5ab8367f96b3205ca3c89fb2fa598c69e" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/Intervention/image/zipball/abbf18d5ab8367f96b3205ca3c89fb2fa598c69e", + "reference": "abbf18d5ab8367f96b3205ca3c89fb2fa598c69e", + "shasum": "" + }, + "require": { + "ext-fileinfo": "*", + "guzzlehttp/psr7": "~1.1", + "php": ">=5.4.0" + }, + "require-dev": { + "mockery/mockery": "~0.9.2", + "phpunit/phpunit": "^4.8 || ^5.7" + }, + "suggest": { + "ext-gd": "to use GD library based image processing.", + "ext-imagick": "to use Imagick based image processing.", + "intervention/imagecache": "Caching extension for the Intervention Image library" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "2.4-dev" + }, + "laravel": { + "providers": [ + "Intervention\\Image\\ImageServiceProvider" + ], + "aliases": { + "Image": "Intervention\\Image\\Facades\\Image" + } + } + }, + "autoload": { + "psr-4": { + "Intervention\\Image\\": "src/Intervention/Image" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Oliver Vogel", + "email": "oliver@olivervogel.com", + "homepage": "http://olivervogel.com/" + } + ], + "description": "Image handling and manipulation library with support for Laravel integration", + "homepage": "http://image.intervention.io/", + "keywords": [ + "gd", + "image", + "imagick", + "laravel", + "thumbnail", + "watermark" + ], + "support": { + "issues": "https://github.com/Intervention/image/issues", + "source": "https://github.com/Intervention/image/tree/master" + }, + "time": "2019-11-02T09:15:47+00:00" + }, + { + "name": "jaybizzle/crawler-detect", + "version": "v1.2.106", + "source": { + "type": "git", + "url": "https://github.com/JayBizzle/Crawler-Detect.git", + "reference": "78bf6792cbf9c569dc0bf2465481978fd2ed0de9" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/JayBizzle/Crawler-Detect/zipball/78bf6792cbf9c569dc0bf2465481978fd2ed0de9", + "reference": "78bf6792cbf9c569dc0bf2465481978fd2ed0de9", + "shasum": "" + }, + "require": { + "php": ">=5.3.0" + }, + "require-dev": { + "phpunit/phpunit": "^4.8|^5.5|^6.5|^9.4" + }, + "type": "library", + "autoload": { + "psr-4": { + "Jaybizzle\\CrawlerDetect\\": "src/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Mark Beech", + "email": "m@rkbee.ch", + "role": "Developer" + } + ], + "description": "CrawlerDetect is a PHP class for detecting bots/crawlers/spiders via the user agent", + "homepage": "https://github.com/JayBizzle/Crawler-Detect/", + "keywords": [ + "crawler", + "crawler detect", + "crawler detector", + "crawlerdetect", + "php crawler detect" + ], + "support": { + "issues": "https://github.com/JayBizzle/Crawler-Detect/issues", + "source": "https://github.com/JayBizzle/Crawler-Detect/tree/v1.2.106" + }, + "time": "2021-05-24T20:30:32+00:00" + }, + { + "name": "jenssegers/agent", + "version": "v2.6.4", + "source": { + "type": "git", + "url": "https://github.com/jenssegers/agent.git", + "reference": "daa11c43729510b3700bc34d414664966b03bffe" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/jenssegers/agent/zipball/daa11c43729510b3700bc34d414664966b03bffe", + "reference": "daa11c43729510b3700bc34d414664966b03bffe", + "shasum": "" + }, + "require": { + "jaybizzle/crawler-detect": "^1.2", + "mobiledetect/mobiledetectlib": "^2.7.6", + "php": ">=5.6" + }, + "require-dev": { + "php-coveralls/php-coveralls": "^2.1", + "phpunit/phpunit": "^5.0|^6.0|^7.0" + }, + "suggest": { + "illuminate/support": "Required for laravel service providers" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "3.0-dev" + }, + "laravel": { + "providers": [ + "Jenssegers\\Agent\\AgentServiceProvider" + ], + "aliases": { + "Agent": "Jenssegers\\Agent\\Facades\\Agent" + } + } + }, + "autoload": { + "psr-4": { + "Jenssegers\\Agent\\": "src/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Jens Segers", + "homepage": "https://jenssegers.com" + } + ], + "description": "Desktop/mobile user agent parser with support for Laravel, based on Mobiledetect", + "homepage": "https://github.com/jenssegers/agent", + "keywords": [ + "Agent", + "browser", + "desktop", + "laravel", + "mobile", + "platform", + "user agent", + "useragent" + ], + "support": { + "issues": "https://github.com/jenssegers/agent/issues", + "source": "https://github.com/jenssegers/agent/tree/v2.6.4" + }, + "funding": [ + { + "url": "https://github.com/jenssegers", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/jenssegers/agent", + "type": "tidelift" + } + ], + "time": "2020-06-13T08:05:20+00:00" + }, + { + "name": "laravel/framework", + "version": "v8.44.0", + "source": { + "type": "git", + "url": "https://github.com/laravel/framework.git", + "reference": "7b3b27dc8911ab02a69731af2ba97b5130b2ddb8" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/laravel/framework/zipball/7b3b27dc8911ab02a69731af2ba97b5130b2ddb8", + "reference": "7b3b27dc8911ab02a69731af2ba97b5130b2ddb8", + "shasum": "" + }, + "require": { + "doctrine/inflector": "^1.4|^2.0", + "dragonmantank/cron-expression": "^3.0.2", + "egulias/email-validator": "^2.1.10", + "ext-json": "*", + "ext-mbstring": "*", + "ext-openssl": "*", + "league/commonmark": "^1.3", + "league/flysystem": "^1.1", + "monolog/monolog": "^2.0", + "nesbot/carbon": "^2.31", + "opis/closure": "^3.6", + "php": "^7.3|^8.0", + "psr/container": "^1.0", + "psr/simple-cache": "^1.0", + "ramsey/uuid": "^4.0", + "swiftmailer/swiftmailer": "^6.0", + "symfony/console": "^5.1.4", + "symfony/error-handler": "^5.1.4", + "symfony/finder": "^5.1.4", + "symfony/http-foundation": "^5.1.4", + "symfony/http-kernel": "^5.1.4", + "symfony/mime": "^5.1.4", + "symfony/process": "^5.1.4", + "symfony/routing": "^5.1.4", + "symfony/var-dumper": "^5.1.4", + "tijsverkoyen/css-to-inline-styles": "^2.2.2", + "vlucas/phpdotenv": "^5.2", + "voku/portable-ascii": "^1.4.8" + }, + "conflict": { + "tightenco/collect": "<5.5.33" + }, + "provide": { + "psr/container-implementation": "1.0" + }, + "replace": { + "illuminate/auth": "self.version", + "illuminate/broadcasting": "self.version", + "illuminate/bus": "self.version", + "illuminate/cache": "self.version", + "illuminate/collections": "self.version", + "illuminate/config": "self.version", + "illuminate/console": "self.version", + "illuminate/container": "self.version", + "illuminate/contracts": "self.version", + "illuminate/cookie": "self.version", + "illuminate/database": "self.version", + "illuminate/encryption": "self.version", + "illuminate/events": "self.version", + "illuminate/filesystem": "self.version", + "illuminate/hashing": "self.version", + "illuminate/http": "self.version", + "illuminate/log": "self.version", + "illuminate/macroable": "self.version", + "illuminate/mail": "self.version", + "illuminate/notifications": "self.version", + "illuminate/pagination": "self.version", + "illuminate/pipeline": "self.version", + "illuminate/queue": "self.version", + "illuminate/redis": "self.version", + "illuminate/routing": "self.version", + "illuminate/session": "self.version", + "illuminate/support": "self.version", + "illuminate/testing": "self.version", + "illuminate/translation": "self.version", + "illuminate/validation": "self.version", + "illuminate/view": "self.version" + }, + "require-dev": { + "aws/aws-sdk-php": "^3.155", + "doctrine/dbal": "^2.6|^3.0", + "filp/whoops": "^2.8", + "guzzlehttp/guzzle": "^6.5.5|^7.0.1", + "league/flysystem-cached-adapter": "^1.0", + "mockery/mockery": "^1.4.2", + "orchestra/testbench-core": "^6.8", + "pda/pheanstalk": "^4.0", + "phpunit/phpunit": "^8.5.8|^9.3.3", + "predis/predis": "^1.1.1", + "symfony/cache": "^5.1.4" + }, + "suggest": { + "aws/aws-sdk-php": "Required to use the SQS queue driver, DynamoDb failed job storage and SES mail driver (^3.155).", + "brianium/paratest": "Required to run tests in parallel (^6.0).", + "doctrine/dbal": "Required to rename columns and drop SQLite columns (^2.6|^3.0).", + "ext-ftp": "Required to use the Flysystem FTP driver.", + "ext-gd": "Required to use Illuminate\\Http\\Testing\\FileFactory::image().", + "ext-memcached": "Required to use the memcache cache driver.", + "ext-pcntl": "Required to use all features of the queue worker.", + "ext-posix": "Required to use all features of the queue worker.", + "ext-redis": "Required to use the Redis cache and queue drivers (^4.0|^5.0).", + "fakerphp/faker": "Required to use the eloquent factory builder (^1.9.1).", + "filp/whoops": "Required for friendly error pages in development (^2.8).", + "guzzlehttp/guzzle": "Required to use the HTTP Client, Mailgun mail driver and the ping methods on schedules (^6.5.5|^7.0.1).", + "laravel/tinker": "Required to use the tinker console command (^2.0).", + "league/flysystem-aws-s3-v3": "Required to use the Flysystem S3 driver (^1.0).", + "league/flysystem-cached-adapter": "Required to use the Flysystem cache (^1.0).", + "league/flysystem-sftp": "Required to use the Flysystem SFTP driver (^1.0).", + "mockery/mockery": "Required to use mocking (^1.4.2).", + "nyholm/psr7": "Required to use PSR-7 bridging features (^1.2).", + "pda/pheanstalk": "Required to use the beanstalk queue driver (^4.0).", + "phpunit/phpunit": "Required to use assertions and run tests (^8.5.8|^9.3.3).", + "predis/predis": "Required to use the predis connector (^1.1.2).", + "psr/http-message": "Required to allow Storage::put to accept a StreamInterface (^1.0).", + "pusher/pusher-php-server": "Required to use the Pusher broadcast driver (^4.0|^5.0|^6.0).", + "symfony/cache": "Required to PSR-6 cache bridge (^5.1.4).", + "symfony/filesystem": "Required to enable support for relative symbolic links (^5.1.4).", + "symfony/psr-http-message-bridge": "Required to use PSR-7 bridging features (^2.0).", + "wildbit/swiftmailer-postmark": "Required to use Postmark mail driver (^3.0)." + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "8.x-dev" + } + }, + "autoload": { + "files": [ + "src/Illuminate/Collections/helpers.php", + "src/Illuminate/Events/functions.php", + "src/Illuminate/Foundation/helpers.php", + "src/Illuminate/Support/helpers.php" + ], + "psr-4": { + "Illuminate\\": "src/Illuminate/", + "Illuminate\\Support\\": [ + "src/Illuminate/Macroable/", + "src/Illuminate/Collections/" + ] + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Taylor Otwell", + "email": "taylor@laravel.com" + } + ], + "description": "The Laravel Framework.", + "homepage": "https://laravel.com", + "keywords": [ + "framework", + "laravel" + ], + "support": { + "issues": "https://github.com/laravel/framework/issues", + "source": "https://github.com/laravel/framework" + }, + "time": "2021-05-27T16:46:06+00:00" + }, + { + "name": "laravel/tinker", + "version": "v2.6.1", + "source": { + "type": "git", + "url": "https://github.com/laravel/tinker.git", + "reference": "04ad32c1a3328081097a181875733fa51f402083" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/laravel/tinker/zipball/04ad32c1a3328081097a181875733fa51f402083", + "reference": "04ad32c1a3328081097a181875733fa51f402083", + "shasum": "" + }, + "require": { + "illuminate/console": "^6.0|^7.0|^8.0", + "illuminate/contracts": "^6.0|^7.0|^8.0", + "illuminate/support": "^6.0|^7.0|^8.0", + "php": "^7.2.5|^8.0", + "psy/psysh": "^0.10.4", + "symfony/var-dumper": "^4.3.4|^5.0" + }, + "require-dev": { + "mockery/mockery": "~1.3.3|^1.4.2", + "phpunit/phpunit": "^8.5.8|^9.3.3" + }, + "suggest": { + "illuminate/database": "The Illuminate Database package (^6.0|^7.0|^8.0)." + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "2.x-dev" + }, + "laravel": { + "providers": [ + "Laravel\\Tinker\\TinkerServiceProvider" + ] + } + }, + "autoload": { + "psr-4": { + "Laravel\\Tinker\\": "src/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Taylor Otwell", + "email": "taylor@laravel.com" + } + ], + "description": "Powerful REPL for the Laravel framework.", + "keywords": [ + "REPL", + "Tinker", + "laravel", + "psysh" + ], + "support": { + "issues": "https://github.com/laravel/tinker/issues", + "source": "https://github.com/laravel/tinker/tree/v2.6.1" + }, + "time": "2021-03-02T16:53:12+00:00" + }, + { + "name": "league/commonmark", + "version": "1.6.2", + "source": { + "type": "git", + "url": "https://github.com/thephpleague/commonmark.git", + "reference": "7d70d2f19c84bcc16275ea47edabee24747352eb" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/thephpleague/commonmark/zipball/7d70d2f19c84bcc16275ea47edabee24747352eb", + "reference": "7d70d2f19c84bcc16275ea47edabee24747352eb", + "shasum": "" + }, + "require": { + "ext-mbstring": "*", + "php": "^7.1 || ^8.0" + }, + "conflict": { + "scrutinizer/ocular": "1.7.*" + }, + "require-dev": { + "cebe/markdown": "~1.0", + "commonmark/commonmark.js": "0.29.2", + "erusev/parsedown": "~1.0", + "ext-json": "*", + "github/gfm": "0.29.0", + "michelf/php-markdown": "~1.4", + "mikehaertl/php-shellcommand": "^1.4", + "phpstan/phpstan": "^0.12", + "phpunit/phpunit": "^7.5 || ^8.5 || ^9.2", + "scrutinizer/ocular": "^1.5", + "symfony/finder": "^4.2" + }, + "bin": [ + "bin/commonmark" + ], + "type": "library", + "autoload": { + "psr-4": { + "League\\CommonMark\\": "src" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Colin O'Dell", + "email": "colinodell@gmail.com", + "homepage": "https://www.colinodell.com", + "role": "Lead Developer" + } + ], + "description": "Highly-extensible PHP Markdown parser which fully supports the CommonMark spec and Github-Flavored Markdown (GFM)", + "homepage": "https://commonmark.thephpleague.com", + "keywords": [ + "commonmark", + "flavored", + "gfm", + "github", + "github-flavored", + "markdown", + "md", + "parser" + ], + "support": { + "docs": "https://commonmark.thephpleague.com/", + "issues": "https://github.com/thephpleague/commonmark/issues", + "rss": "https://github.com/thephpleague/commonmark/releases.atom", + "source": "https://github.com/thephpleague/commonmark" + }, + "funding": [ + { + "url": "https://enjoy.gitstore.app/repositories/thephpleague/commonmark", + "type": "custom" + }, + { + "url": "https://www.colinodell.com/sponsor", + "type": "custom" + }, + { + "url": "https://www.paypal.me/colinpodell/10.00", + "type": "custom" + }, + { + "url": "https://github.com/colinodell", + "type": "github" + }, + { + "url": "https://www.patreon.com/colinodell", + "type": "patreon" + }, + { + "url": "https://tidelift.com/funding/github/packagist/league/commonmark", + "type": "tidelift" + } + ], + "time": "2021-05-12T11:39:41+00:00" + }, + { + "name": "league/flysystem", + "version": "1.1.3", + "source": { + "type": "git", + "url": "https://github.com/thephpleague/flysystem.git", + "reference": "9be3b16c877d477357c015cec057548cf9b2a14a" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/thephpleague/flysystem/zipball/9be3b16c877d477357c015cec057548cf9b2a14a", + "reference": "9be3b16c877d477357c015cec057548cf9b2a14a", + "shasum": "" + }, + "require": { + "ext-fileinfo": "*", + "league/mime-type-detection": "^1.3", + "php": "^7.2.5 || ^8.0" + }, + "conflict": { + "league/flysystem-sftp": "<1.0.6" + }, + "require-dev": { + "phpspec/prophecy": "^1.11.1", + "phpunit/phpunit": "^8.5.8" + }, + "suggest": { + "ext-fileinfo": "Required for MimeType", + "ext-ftp": "Allows you to use FTP server storage", + "ext-openssl": "Allows you to use FTPS server storage", + "league/flysystem-aws-s3-v2": "Allows you to use S3 storage with AWS SDK v2", + "league/flysystem-aws-s3-v3": "Allows you to use S3 storage with AWS SDK v3", + "league/flysystem-azure": "Allows you to use Windows Azure Blob storage", + "league/flysystem-cached-adapter": "Flysystem adapter decorator for metadata caching", + "league/flysystem-eventable-filesystem": "Allows you to use EventableFilesystem", + "league/flysystem-rackspace": "Allows you to use Rackspace Cloud Files", + "league/flysystem-sftp": "Allows you to use SFTP server storage via phpseclib", + "league/flysystem-webdav": "Allows you to use WebDAV storage", + "league/flysystem-ziparchive": "Allows you to use ZipArchive adapter", + "spatie/flysystem-dropbox": "Allows you to use Dropbox storage", + "srmklive/flysystem-dropbox-v2": "Allows you to use Dropbox storage for PHP 5 applications" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.1-dev" + } + }, + "autoload": { + "psr-4": { + "League\\Flysystem\\": "src/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Frank de Jonge", + "email": "info@frenky.net" + } + ], + "description": "Filesystem abstraction: Many filesystems, one API.", + "keywords": [ + "Cloud Files", + "WebDAV", + "abstraction", + "aws", + "cloud", + "copy.com", + "dropbox", + "file systems", + "files", + "filesystem", + "filesystems", + "ftp", + "rackspace", + "remote", + "s3", + "sftp", + "storage" + ], + "support": { + "issues": "https://github.com/thephpleague/flysystem/issues", + "source": "https://github.com/thephpleague/flysystem/tree/1.x" + }, + "funding": [ + { + "url": "https://offset.earth/frankdejonge", + "type": "other" + } + ], + "time": "2020-08-23T07:39:11+00:00" + }, + { + "name": "league/mime-type-detection", + "version": "1.7.0", + "source": { + "type": "git", + "url": "https://github.com/thephpleague/mime-type-detection.git", + "reference": "3b9dff8aaf7323590c1d2e443db701eb1f9aa0d3" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/thephpleague/mime-type-detection/zipball/3b9dff8aaf7323590c1d2e443db701eb1f9aa0d3", + "reference": "3b9dff8aaf7323590c1d2e443db701eb1f9aa0d3", + "shasum": "" + }, + "require": { + "ext-fileinfo": "*", + "php": "^7.2 || ^8.0" + }, + "require-dev": { + "friendsofphp/php-cs-fixer": "^2.18", + "phpstan/phpstan": "^0.12.68", + "phpunit/phpunit": "^8.5.8 || ^9.3" + }, + "type": "library", + "autoload": { + "psr-4": { + "League\\MimeTypeDetection\\": "src" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Frank de Jonge", + "email": "info@frankdejonge.nl" + } + ], + "description": "Mime-type detection for Flysystem", + "support": { + "issues": "https://github.com/thephpleague/mime-type-detection/issues", + "source": "https://github.com/thephpleague/mime-type-detection/tree/1.7.0" + }, + "funding": [ + { + "url": "https://github.com/frankdejonge", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/league/flysystem", + "type": "tidelift" + } + ], + "time": "2021-01-18T20:58:21+00:00" + }, + { + "name": "mcamara/laravel-localization", + "version": "1.6.1", + "source": { + "type": "git", + "url": "https://github.com/mcamara/laravel-localization.git", + "reference": "4f0bfd89e5ee8100cb8cff8ca2cc3b985ed46694" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/mcamara/laravel-localization/zipball/4f0bfd89e5ee8100cb8cff8ca2cc3b985ed46694", + "reference": "4f0bfd89e5ee8100cb8cff8ca2cc3b985ed46694", + "shasum": "" + }, + "require": { + "laravel/framework": "~5.2.0||~5.3.0||~5.4.0||~5.5.0||~5.6.0||~5.7.0||~5.8.0||^6.0||^7.0||^8.0", + "php": ">=7.1.0" + }, + "require-dev": { + "orchestra/testbench-browser-kit": "~3.4|~3.8|~4.0", + "phpunit/phpunit": "6.0.*|^8.0" + }, + "suggest": { + "ext-intl": "*" + }, + "type": "library", + "extra": { + "laravel": { + "providers": [ + "Mcamara\\LaravelLocalization\\LaravelLocalizationServiceProvider" + ], + "aliases": { + "LaravelLocalization": "Mcamara\\LaravelLocalization\\Facades\\LaravelLocalization" + } + } + }, + "autoload": { + "classmap": [], + "psr-0": { + "Mcamara\\LaravelLocalization": "src/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Marc Cámara", + "email": "mcamara88@gmail.com", + "role": "Developer" + } + ], + "description": "Easy localization for Laravel", + "homepage": "https://github.com/mcamara/laravel-localization", + "keywords": [ + "laravel", + "localization", + "php" + ], + "support": { + "issues": "https://github.com/mcamara/laravel-localization/issues", + "source": "https://github.com/mcamara/laravel-localization/tree/1.6.1" + }, + "funding": [ + { + "url": "https://github.com/iwasherefirst2", + "type": "github" + }, + { + "url": "https://github.com/mcamara", + "type": "github" + } + ], + "time": "2020-10-01T07:45:06+00:00" + }, + { + "name": "mews/captcha", + "version": "3.2.6", + "source": { + "type": "git", + "url": "https://github.com/mewebstudio/captcha.git", + "reference": "42c1b320e4cad1f6ec9a395da36d7eda5b67d122" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/mewebstudio/captcha/zipball/42c1b320e4cad1f6ec9a395da36d7eda5b67d122", + "reference": "42c1b320e4cad1f6ec9a395da36d7eda5b67d122", + "shasum": "" + }, + "require": { + "ext-gd": "*", + "illuminate/config": "~5|^6|^7|^8", + "illuminate/filesystem": "~5|^6|^7|^8", + "illuminate/hashing": "~5|^6|^7|^8", + "illuminate/session": "~5|^6|^7|^8", + "illuminate/support": "~5|^6|^7|^8", + "intervention/image": "~2.5", + "php": "^7.2|^8.0" + }, + "require-dev": { + "mockery/mockery": "^1.0", + "phpunit/phpunit": "^8.5" + }, + "type": "package", + "extra": { + "laravel": { + "providers": [ + "Mews\\Captcha\\CaptchaServiceProvider" + ], + "aliases": { + "Captcha": "Mews\\Captcha\\Facades\\Captcha" + } + } + }, + "autoload": { + "psr-4": { + "Mews\\Captcha\\": "src/" + }, + "files": [ + "src/helpers.php" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Muharrem ERÄ°N", + "email": "me@mewebstudio.com", + "homepage": "https://github.com/mewebstudio", + "role": "Developer" + } + ], + "description": "Laravel 5 & 6 Captcha Package", + "homepage": "https://github.com/mewebstudio/captcha", + "keywords": [ + "captcha", + "laravel5 Security", + "laravel6 Captcha", + "laravel6 Security" + ], + "support": { + "issues": "https://github.com/mewebstudio/captcha/issues", + "source": "https://github.com/mewebstudio/captcha/tree/3.2.6" + }, + "time": "2021-04-22T18:42:48+00:00" + }, + { + "name": "mobiledetect/mobiledetectlib", + "version": "2.8.37", + "source": { + "type": "git", + "url": "https://github.com/serbanghita/Mobile-Detect.git", + "reference": "9841e3c46f5bd0739b53aed8ac677fa712943df7" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/serbanghita/Mobile-Detect/zipball/9841e3c46f5bd0739b53aed8ac677fa712943df7", + "reference": "9841e3c46f5bd0739b53aed8ac677fa712943df7", + "shasum": "" + }, + "require": { + "php": ">=5.0.0" + }, + "require-dev": { + "phpunit/phpunit": "~4.8.35||~5.7" + }, + "type": "library", + "autoload": { + "classmap": [ + "Mobile_Detect.php" + ], + "psr-0": { + "Detection": "namespaced/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Serban Ghita", + "email": "serbanghita@gmail.com", + "homepage": "http://mobiledetect.net", + "role": "Developer" + } + ], + "description": "Mobile_Detect is a lightweight PHP class for detecting mobile devices. It uses the User-Agent string combined with specific HTTP headers to detect the mobile environment.", + "homepage": "https://github.com/serbanghita/Mobile-Detect", + "keywords": [ + "detect mobile devices", + "mobile", + "mobile detect", + "mobile detector", + "php mobile detect" + ], + "support": { + "issues": "https://github.com/serbanghita/Mobile-Detect/issues", + "source": "https://github.com/serbanghita/Mobile-Detect/tree/2.8.37" + }, + "funding": [ + { + "url": "https://github.com/serbanghita", + "type": "github" + } + ], + "time": "2021-02-19T21:22:57+00:00" + }, + { + "name": "monolog/monolog", + "version": "2.2.0", + "source": { + "type": "git", + "url": "https://github.com/Seldaek/monolog.git", + "reference": "1cb1cde8e8dd0f70cc0fe51354a59acad9302084" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/Seldaek/monolog/zipball/1cb1cde8e8dd0f70cc0fe51354a59acad9302084", + "reference": "1cb1cde8e8dd0f70cc0fe51354a59acad9302084", + "shasum": "" + }, + "require": { + "php": ">=7.2", + "psr/log": "^1.0.1" + }, + "provide": { + "psr/log-implementation": "1.0.0" + }, + "require-dev": { + "aws/aws-sdk-php": "^2.4.9 || ^3.0", + "doctrine/couchdb": "~1.0@dev", + "elasticsearch/elasticsearch": "^7", + "graylog2/gelf-php": "^1.4.2", + "mongodb/mongodb": "^1.8", + "php-amqplib/php-amqplib": "~2.4", + "php-console/php-console": "^3.1.3", + "phpspec/prophecy": "^1.6.1", + "phpstan/phpstan": "^0.12.59", + "phpunit/phpunit": "^8.5", + "predis/predis": "^1.1", + "rollbar/rollbar": "^1.3", + "ruflin/elastica": ">=0.90 <7.0.1", + "swiftmailer/swiftmailer": "^5.3|^6.0" + }, + "suggest": { + "aws/aws-sdk-php": "Allow sending log messages to AWS services like DynamoDB", + "doctrine/couchdb": "Allow sending log messages to a CouchDB server", + "elasticsearch/elasticsearch": "Allow sending log messages to an Elasticsearch server via official client", + "ext-amqp": "Allow sending log messages to an AMQP server (1.0+ required)", + "ext-mbstring": "Allow to work properly with unicode symbols", + "ext-mongodb": "Allow sending log messages to a MongoDB server (via driver)", + "graylog2/gelf-php": "Allow sending log messages to a GrayLog2 server", + "mongodb/mongodb": "Allow sending log messages to a MongoDB server (via library)", + "php-amqplib/php-amqplib": "Allow sending log messages to an AMQP server using php-amqplib", + "php-console/php-console": "Allow sending log messages to Google Chrome", + "rollbar/rollbar": "Allow sending log messages to Rollbar", + "ruflin/elastica": "Allow sending log messages to an Elastic Search server" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-main": "2.x-dev" + } + }, + "autoload": { + "psr-4": { + "Monolog\\": "src/Monolog" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Jordi Boggiano", + "email": "j.boggiano@seld.be", + "homepage": "https://seld.be" + } + ], + "description": "Sends your logs to files, sockets, inboxes, databases and various web services", + "homepage": "https://github.com/Seldaek/monolog", + "keywords": [ + "log", + "logging", + "psr-3" + ], + "support": { + "issues": "https://github.com/Seldaek/monolog/issues", + "source": "https://github.com/Seldaek/monolog/tree/2.2.0" + }, + "funding": [ + { + "url": "https://github.com/Seldaek", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/monolog/monolog", + "type": "tidelift" + } + ], + "time": "2020-12-14T13:15:25+00:00" + }, + { + "name": "nesbot/carbon", + "version": "2.48.1", + "source": { + "type": "git", + "url": "https://github.com/briannesbitt/Carbon.git", + "reference": "8d1f50f1436fb4b05e7127360483dd9c6e73da16" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/briannesbitt/Carbon/zipball/8d1f50f1436fb4b05e7127360483dd9c6e73da16", + "reference": "8d1f50f1436fb4b05e7127360483dd9c6e73da16", + "shasum": "" + }, + "require": { + "ext-json": "*", + "php": "^7.1.8 || ^8.0", + "symfony/polyfill-mbstring": "^1.0", + "symfony/translation": "^3.4 || ^4.0 || ^5.0" + }, + "require-dev": { + "doctrine/orm": "^2.7", + "friendsofphp/php-cs-fixer": "^2.14 || ^3.0", + "kylekatarnls/multi-tester": "^2.0", + "phpmd/phpmd": "^2.9", + "phpstan/extension-installer": "^1.0", + "phpstan/phpstan": "^0.12.54", + "phpunit/phpunit": "^7.5.20 || ^8.5.14", + "squizlabs/php_codesniffer": "^3.4" + }, + "bin": [ + "bin/carbon" + ], + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "2.x-dev", + "dev-3.x": "3.x-dev" + }, + "laravel": { + "providers": [ + "Carbon\\Laravel\\ServiceProvider" + ] + }, + "phpstan": { + "includes": [ + "extension.neon" + ] + } + }, + "autoload": { + "psr-4": { + "Carbon\\": "src/Carbon/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Brian Nesbitt", + "email": "brian@nesbot.com", + "homepage": "http://nesbot.com" + }, + { + "name": "kylekatarnls", + "homepage": "http://github.com/kylekatarnls" + } + ], + "description": "An API extension for DateTime that supports 281 different languages.", + "homepage": "http://carbon.nesbot.com", + "keywords": [ + "date", + "datetime", + "time" + ], + "support": { + "issues": "https://github.com/briannesbitt/Carbon/issues", + "source": "https://github.com/briannesbitt/Carbon" + }, + "funding": [ + { + "url": "https://opencollective.com/Carbon", + "type": "open_collective" + }, + { + "url": "https://tidelift.com/funding/github/packagist/nesbot/carbon", + "type": "tidelift" + } + ], + "time": "2021-05-26T22:08:38+00:00" + }, + { + "name": "nikic/php-parser", + "version": "v4.10.5", + "source": { + "type": "git", + "url": "https://github.com/nikic/PHP-Parser.git", + "reference": "4432ba399e47c66624bc73c8c0f811e5c109576f" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/nikic/PHP-Parser/zipball/4432ba399e47c66624bc73c8c0f811e5c109576f", + "reference": "4432ba399e47c66624bc73c8c0f811e5c109576f", + "shasum": "" + }, + "require": { + "ext-tokenizer": "*", + "php": ">=7.0" + }, + "require-dev": { + "ircmaxell/php-yacc": "^0.0.7", + "phpunit/phpunit": "^6.5 || ^7.0 || ^8.0 || ^9.0" + }, + "bin": [ + "bin/php-parse" + ], + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "4.9-dev" + } + }, + "autoload": { + "psr-4": { + "PhpParser\\": "lib/PhpParser" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Nikita Popov" + } + ], + "description": "A PHP parser written in PHP", + "keywords": [ + "parser", + "php" + ], + "support": { + "issues": "https://github.com/nikic/PHP-Parser/issues", + "source": "https://github.com/nikic/PHP-Parser/tree/v4.10.5" + }, + "time": "2021-05-03T19:11:20+00:00" + }, + { + "name": "opis/closure", + "version": "3.6.2", + "source": { + "type": "git", + "url": "https://github.com/opis/closure.git", + "reference": "06e2ebd25f2869e54a306dda991f7db58066f7f6" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/opis/closure/zipball/06e2ebd25f2869e54a306dda991f7db58066f7f6", + "reference": "06e2ebd25f2869e54a306dda991f7db58066f7f6", + "shasum": "" + }, + "require": { + "php": "^5.4 || ^7.0 || ^8.0" + }, + "require-dev": { + "jeremeamia/superclosure": "^2.0", + "phpunit/phpunit": "^4.0 || ^5.0 || ^6.0 || ^7.0 || ^8.0 || ^9.0" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "3.6.x-dev" + } + }, + "autoload": { + "psr-4": { + "Opis\\Closure\\": "src/" + }, + "files": [ + "functions.php" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Marius Sarca", + "email": "marius.sarca@gmail.com" + }, + { + "name": "Sorin Sarca", + "email": "sarca_sorin@hotmail.com" + } + ], + "description": "A library that can be used to serialize closures (anonymous functions) and arbitrary objects.", + "homepage": "https://opis.io/closure", + "keywords": [ + "anonymous functions", + "closure", + "function", + "serializable", + "serialization", + "serialize" + ], + "support": { + "issues": "https://github.com/opis/closure/issues", + "source": "https://github.com/opis/closure/tree/3.6.2" + }, + "time": "2021-04-09T13:42:10+00:00" + }, + { + "name": "phpoption/phpoption", + "version": "1.7.5", + "source": { + "type": "git", + "url": "https://github.com/schmittjoh/php-option.git", + "reference": "994ecccd8f3283ecf5ac33254543eb0ac946d525" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/schmittjoh/php-option/zipball/994ecccd8f3283ecf5ac33254543eb0ac946d525", + "reference": "994ecccd8f3283ecf5ac33254543eb0ac946d525", + "shasum": "" + }, + "require": { + "php": "^5.5.9 || ^7.0 || ^8.0" + }, + "require-dev": { + "bamarni/composer-bin-plugin": "^1.4.1", + "phpunit/phpunit": "^4.8.35 || ^5.7.27 || ^6.5.6 || ^7.0 || ^8.0 || ^9.0" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.7-dev" + } + }, + "autoload": { + "psr-4": { + "PhpOption\\": "src/PhpOption/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "Apache-2.0" + ], + "authors": [ + { + "name": "Johannes M. Schmitt", + "email": "schmittjoh@gmail.com" + }, + { + "name": "Graham Campbell", + "email": "graham@alt-three.com" + } + ], + "description": "Option Type for PHP", + "keywords": [ + "language", + "option", + "php", + "type" + ], + "support": { + "issues": "https://github.com/schmittjoh/php-option/issues", + "source": "https://github.com/schmittjoh/php-option/tree/1.7.5" + }, + "funding": [ + { + "url": "https://github.com/GrahamCampbell", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/phpoption/phpoption", + "type": "tidelift" + } + ], + "time": "2020-07-20T17:29:33+00:00" + }, + { + "name": "promphp/prometheus_client_php", + "version": "v2.2.2", + "source": { + "type": "git", + "url": "https://github.com/PromPHP/prometheus_client_php.git", + "reference": "5d27b6d84900d9b3208b5b6bf88d10ed0dc7a154" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/PromPHP/prometheus_client_php/zipball/5d27b6d84900d9b3208b5b6bf88d10ed0dc7a154", + "reference": "5d27b6d84900d9b3208b5b6bf88d10ed0dc7a154", + "shasum": "" + }, + "require": { + "ext-json": "*", + "php": "^7.2|^8.0", + "symfony/polyfill-apcu": "^1.6" + }, + "replace": { + "endclothing/prometheus_client_php": "*", + "jimdo/prometheus_client_php": "*", + "lkaemmerling/prometheus_client_php": "*" + }, + "require-dev": { + "guzzlehttp/guzzle": "^6.3|^7.0", + "phpstan/extension-installer": "^1.0", + "phpstan/phpstan": "^0.12.50", + "phpstan/phpstan-phpunit": "^0.12.16", + "phpstan/phpstan-strict-rules": "^0.12.5", + "phpunit/phpunit": "^8.4|^9.4", + "squizlabs/php_codesniffer": "^3.5" + }, + "suggest": { + "ext-apc": "Required if using APCu.", + "ext-redis": "Required if using Redis.", + "promphp/prometheus_push_gateway_php": "An easy client for using Prometheus PushGateway." + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.0-dev" + } + }, + "autoload": { + "psr-4": { + "Prometheus\\": "src/Prometheus/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "Apache-2.0" + ], + "authors": [ + { + "name": "Lukas Kämmerling", + "email": "kontakt@lukas-kaemmerling.de" + } + ], + "description": "Prometheus instrumentation library for PHP applications.", + "support": { + "issues": "https://github.com/PromPHP/prometheus_client_php/issues", + "source": "https://github.com/PromPHP/prometheus_client_php/tree/v2.2.2" + }, + "time": "2021-03-05T08:54:14+00:00" + }, + { + "name": "psr/container", + "version": "1.1.1", + "source": { + "type": "git", + "url": "https://github.com/php-fig/container.git", + "reference": "8622567409010282b7aeebe4bb841fe98b58dcaf" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/php-fig/container/zipball/8622567409010282b7aeebe4bb841fe98b58dcaf", + "reference": "8622567409010282b7aeebe4bb841fe98b58dcaf", + "shasum": "" + }, + "require": { + "php": ">=7.2.0" + }, + "type": "library", + "autoload": { + "psr-4": { + "Psr\\Container\\": "src/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "PHP-FIG", + "homepage": "https://www.php-fig.org/" + } + ], + "description": "Common Container Interface (PHP FIG PSR-11)", + "homepage": "https://github.com/php-fig/container", + "keywords": [ + "PSR-11", + "container", + "container-interface", + "container-interop", + "psr" + ], + "support": { + "issues": "https://github.com/php-fig/container/issues", + "source": "https://github.com/php-fig/container/tree/1.1.1" + }, + "time": "2021-03-05T17:36:06+00:00" + }, + { + "name": "psr/event-dispatcher", + "version": "1.0.0", + "source": { + "type": "git", + "url": "https://github.com/php-fig/event-dispatcher.git", + "reference": "dbefd12671e8a14ec7f180cab83036ed26714bb0" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/php-fig/event-dispatcher/zipball/dbefd12671e8a14ec7f180cab83036ed26714bb0", + "reference": "dbefd12671e8a14ec7f180cab83036ed26714bb0", + "shasum": "" + }, + "require": { + "php": ">=7.2.0" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.0.x-dev" + } + }, + "autoload": { + "psr-4": { + "Psr\\EventDispatcher\\": "src/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "PHP-FIG", + "homepage": "http://www.php-fig.org/" + } + ], + "description": "Standard interfaces for event handling.", + "keywords": [ + "events", + "psr", + "psr-14" + ], + "support": { + "issues": "https://github.com/php-fig/event-dispatcher/issues", + "source": "https://github.com/php-fig/event-dispatcher/tree/1.0.0" + }, + "time": "2019-01-08T18:20:26+00:00" + }, + { + "name": "psr/http-client", + "version": "1.0.1", + "source": { + "type": "git", + "url": "https://github.com/php-fig/http-client.git", + "reference": "2dfb5f6c5eff0e91e20e913f8c5452ed95b86621" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/php-fig/http-client/zipball/2dfb5f6c5eff0e91e20e913f8c5452ed95b86621", + "reference": "2dfb5f6c5eff0e91e20e913f8c5452ed95b86621", + "shasum": "" + }, + "require": { + "php": "^7.0 || ^8.0", + "psr/http-message": "^1.0" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.0.x-dev" + } + }, + "autoload": { + "psr-4": { + "Psr\\Http\\Client\\": "src/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "PHP-FIG", + "homepage": "http://www.php-fig.org/" + } + ], + "description": "Common interface for HTTP clients", + "homepage": "https://github.com/php-fig/http-client", + "keywords": [ + "http", + "http-client", + "psr", + "psr-18" + ], + "support": { + "source": "https://github.com/php-fig/http-client/tree/master" + }, + "time": "2020-06-29T06:28:15+00:00" + }, + { + "name": "psr/http-message", + "version": "1.0.1", + "source": { + "type": "git", + "url": "https://github.com/php-fig/http-message.git", + "reference": "f6561bf28d520154e4b0ec72be95418abe6d9363" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/php-fig/http-message/zipball/f6561bf28d520154e4b0ec72be95418abe6d9363", + "reference": "f6561bf28d520154e4b0ec72be95418abe6d9363", + "shasum": "" + }, + "require": { + "php": ">=5.3.0" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.0.x-dev" + } + }, + "autoload": { + "psr-4": { + "Psr\\Http\\Message\\": "src/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "PHP-FIG", + "homepage": "http://www.php-fig.org/" + } + ], + "description": "Common interface for HTTP messages", + "homepage": "https://github.com/php-fig/http-message", + "keywords": [ + "http", + "http-message", + "psr", + "psr-7", + "request", + "response" + ], + "support": { + "source": "https://github.com/php-fig/http-message/tree/master" + }, + "time": "2016-08-06T14:39:51+00:00" + }, + { + "name": "psr/log", + "version": "1.1.4", + "source": { + "type": "git", + "url": "https://github.com/php-fig/log.git", + "reference": "d49695b909c3b7628b6289db5479a1c204601f11" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/php-fig/log/zipball/d49695b909c3b7628b6289db5479a1c204601f11", + "reference": "d49695b909c3b7628b6289db5479a1c204601f11", + "shasum": "" + }, + "require": { + "php": ">=5.3.0" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.1.x-dev" + } + }, + "autoload": { + "psr-4": { + "Psr\\Log\\": "Psr/Log/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "PHP-FIG", + "homepage": "https://www.php-fig.org/" + } + ], + "description": "Common interface for logging libraries", + "homepage": "https://github.com/php-fig/log", + "keywords": [ + "log", + "psr", + "psr-3" + ], + "support": { + "source": "https://github.com/php-fig/log/tree/1.1.4" + }, + "time": "2021-05-03T11:20:27+00:00" + }, + { + "name": "psr/simple-cache", + "version": "1.0.1", + "source": { + "type": "git", + "url": "https://github.com/php-fig/simple-cache.git", + "reference": "408d5eafb83c57f6365a3ca330ff23aa4a5fa39b" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/php-fig/simple-cache/zipball/408d5eafb83c57f6365a3ca330ff23aa4a5fa39b", + "reference": "408d5eafb83c57f6365a3ca330ff23aa4a5fa39b", + "shasum": "" + }, + "require": { + "php": ">=5.3.0" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.0.x-dev" + } + }, + "autoload": { + "psr-4": { + "Psr\\SimpleCache\\": "src/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "PHP-FIG", + "homepage": "http://www.php-fig.org/" + } + ], + "description": "Common interfaces for simple caching", + "keywords": [ + "cache", + "caching", + "psr", + "psr-16", + "simple-cache" + ], + "support": { + "source": "https://github.com/php-fig/simple-cache/tree/master" + }, + "time": "2017-10-23T01:57:42+00:00" + }, + { + "name": "psy/psysh", + "version": "v0.10.8", + "source": { + "type": "git", + "url": "https://github.com/bobthecow/psysh.git", + "reference": "e4573f47750dd6c92dca5aee543fa77513cbd8d3" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/bobthecow/psysh/zipball/e4573f47750dd6c92dca5aee543fa77513cbd8d3", + "reference": "e4573f47750dd6c92dca5aee543fa77513cbd8d3", + "shasum": "" + }, + "require": { + "ext-json": "*", + "ext-tokenizer": "*", + "nikic/php-parser": "~4.0|~3.0|~2.0|~1.3", + "php": "^8.0 || ^7.0 || ^5.5.9", + "symfony/console": "~5.0|~4.0|~3.0|^2.4.2|~2.3.10", + "symfony/var-dumper": "~5.0|~4.0|~3.0|~2.7" + }, + "require-dev": { + "bamarni/composer-bin-plugin": "^1.2", + "hoa/console": "3.17.*" + }, + "suggest": { + "ext-pcntl": "Enabling the PCNTL extension makes PsySH a lot happier :)", + "ext-pdo-sqlite": "The doc command requires SQLite to work.", + "ext-posix": "If you have PCNTL, you'll want the POSIX extension as well.", + "ext-readline": "Enables support for arrow-key history navigation, and showing and manipulating command history.", + "hoa/console": "A pure PHP readline implementation. You'll want this if your PHP install doesn't already support readline or libedit." + }, + "bin": [ + "bin/psysh" + ], + "type": "library", + "extra": { + "branch-alias": { + "dev-main": "0.10.x-dev" + } + }, + "autoload": { + "files": [ + "src/functions.php" + ], + "psr-4": { + "Psy\\": "src/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Justin Hileman", + "email": "justin@justinhileman.info", + "homepage": "http://justinhileman.com" + } + ], + "description": "An interactive shell for modern PHP.", + "homepage": "http://psysh.org", + "keywords": [ + "REPL", + "console", + "interactive", + "shell" + ], + "support": { + "issues": "https://github.com/bobthecow/psysh/issues", + "source": "https://github.com/bobthecow/psysh/tree/v0.10.8" + }, + "time": "2021-04-10T16:23:39+00:00" + }, + { + "name": "ralouphie/getallheaders", + "version": "3.0.3", + "source": { + "type": "git", + "url": "https://github.com/ralouphie/getallheaders.git", + "reference": "120b605dfeb996808c31b6477290a714d356e822" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/ralouphie/getallheaders/zipball/120b605dfeb996808c31b6477290a714d356e822", + "reference": "120b605dfeb996808c31b6477290a714d356e822", + "shasum": "" + }, + "require": { + "php": ">=5.6" + }, + "require-dev": { + "php-coveralls/php-coveralls": "^2.1", + "phpunit/phpunit": "^5 || ^6.5" + }, + "type": "library", + "autoload": { + "files": [ + "src/getallheaders.php" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Ralph Khattar", + "email": "ralph.khattar@gmail.com" + } + ], + "description": "A polyfill for getallheaders.", + "support": { + "issues": "https://github.com/ralouphie/getallheaders/issues", + "source": "https://github.com/ralouphie/getallheaders/tree/develop" + }, + "time": "2019-03-08T08:55:37+00:00" + }, + { + "name": "ramsey/collection", + "version": "1.1.3", + "source": { + "type": "git", + "url": "https://github.com/ramsey/collection.git", + "reference": "28a5c4ab2f5111db6a60b2b4ec84057e0f43b9c1" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/ramsey/collection/zipball/28a5c4ab2f5111db6a60b2b4ec84057e0f43b9c1", + "reference": "28a5c4ab2f5111db6a60b2b4ec84057e0f43b9c1", + "shasum": "" + }, + "require": { + "php": "^7.2 || ^8" + }, + "require-dev": { + "captainhook/captainhook": "^5.3", + "dealerdirect/phpcodesniffer-composer-installer": "^0.7.0", + "ergebnis/composer-normalize": "^2.6", + "fakerphp/faker": "^1.5", + "hamcrest/hamcrest-php": "^2", + "jangregor/phpstan-prophecy": "^0.8", + "mockery/mockery": "^1.3", + "phpstan/extension-installer": "^1", + "phpstan/phpstan": "^0.12.32", + "phpstan/phpstan-mockery": "^0.12.5", + "phpstan/phpstan-phpunit": "^0.12.11", + "phpunit/phpunit": "^8.5 || ^9", + "psy/psysh": "^0.10.4", + "slevomat/coding-standard": "^6.3", + "squizlabs/php_codesniffer": "^3.5", + "vimeo/psalm": "^4.4" + }, + "type": "library", + "autoload": { + "psr-4": { + "Ramsey\\Collection\\": "src/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Ben Ramsey", + "email": "ben@benramsey.com", + "homepage": "https://benramsey.com" + } + ], + "description": "A PHP 7.2+ library for representing and manipulating collections.", + "keywords": [ + "array", + "collection", + "hash", + "map", + "queue", + "set" + ], + "support": { + "issues": "https://github.com/ramsey/collection/issues", + "source": "https://github.com/ramsey/collection/tree/1.1.3" + }, + "funding": [ + { + "url": "https://github.com/ramsey", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/ramsey/collection", + "type": "tidelift" + } + ], + "time": "2021-01-21T17:40:04+00:00" + }, + { + "name": "ramsey/uuid", + "version": "4.1.1", + "source": { + "type": "git", + "url": "https://github.com/ramsey/uuid.git", + "reference": "cd4032040a750077205918c86049aa0f43d22947" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/ramsey/uuid/zipball/cd4032040a750077205918c86049aa0f43d22947", + "reference": "cd4032040a750077205918c86049aa0f43d22947", + "shasum": "" + }, + "require": { + "brick/math": "^0.8 || ^0.9", + "ext-json": "*", + "php": "^7.2 || ^8", + "ramsey/collection": "^1.0", + "symfony/polyfill-ctype": "^1.8" + }, + "replace": { + "rhumsaa/uuid": "self.version" + }, + "require-dev": { + "codeception/aspect-mock": "^3", + "dealerdirect/phpcodesniffer-composer-installer": "^0.6.2 || ^0.7.0", + "doctrine/annotations": "^1.8", + "goaop/framework": "^2", + "mockery/mockery": "^1.3", + "moontoast/math": "^1.1", + "paragonie/random-lib": "^2", + "php-mock/php-mock-mockery": "^1.3", + "php-mock/php-mock-phpunit": "^2.5", + "php-parallel-lint/php-parallel-lint": "^1.1", + "phpbench/phpbench": "^0.17.1", + "phpstan/extension-installer": "^1.0", + "phpstan/phpstan": "^0.12", + "phpstan/phpstan-mockery": "^0.12", + "phpstan/phpstan-phpunit": "^0.12", + "phpunit/phpunit": "^8.5", + "psy/psysh": "^0.10.0", + "slevomat/coding-standard": "^6.0", + "squizlabs/php_codesniffer": "^3.5", + "vimeo/psalm": "3.9.4" + }, + "suggest": { + "ext-bcmath": "Enables faster math with arbitrary-precision integers using BCMath.", + "ext-ctype": "Enables faster processing of character classification using ctype functions.", + "ext-gmp": "Enables faster math with arbitrary-precision integers using GMP.", + "ext-uuid": "Enables the use of PeclUuidTimeGenerator and PeclUuidRandomGenerator.", + "paragonie/random-lib": "Provides RandomLib for use with the RandomLibAdapter", + "ramsey/uuid-doctrine": "Allows the use of Ramsey\\Uuid\\Uuid as Doctrine field type." + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "4.x-dev" + } + }, + "autoload": { + "psr-4": { + "Ramsey\\Uuid\\": "src/" + }, + "files": [ + "src/functions.php" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "description": "A PHP library for generating and working with universally unique identifiers (UUIDs).", + "homepage": "https://github.com/ramsey/uuid", + "keywords": [ + "guid", + "identifier", + "uuid" + ], + "support": { + "issues": "https://github.com/ramsey/uuid/issues", + "rss": "https://github.com/ramsey/uuid/releases.atom", + "source": "https://github.com/ramsey/uuid" + }, + "funding": [ + { + "url": "https://github.com/ramsey", + "type": "github" + } + ], + "time": "2020-08-18T17:17:46+00:00" + }, + { + "name": "swiftmailer/swiftmailer", + "version": "v6.2.7", + "source": { + "type": "git", + "url": "https://github.com/swiftmailer/swiftmailer.git", + "reference": "15f7faf8508e04471f666633addacf54c0ab5933" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/swiftmailer/swiftmailer/zipball/15f7faf8508e04471f666633addacf54c0ab5933", + "reference": "15f7faf8508e04471f666633addacf54c0ab5933", + "shasum": "" + }, + "require": { + "egulias/email-validator": "^2.0|^3.1", + "php": ">=7.0.0", + "symfony/polyfill-iconv": "^1.0", + "symfony/polyfill-intl-idn": "^1.10", + "symfony/polyfill-mbstring": "^1.0" + }, + "require-dev": { + "mockery/mockery": "^1.0", + "symfony/phpunit-bridge": "^4.4|^5.0" + }, + "suggest": { + "ext-intl": "Needed to support internationalized email addresses" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "6.2-dev" + } + }, + "autoload": { + "files": [ + "lib/swift_required.php" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Chris Corbyn" + }, + { + "name": "Fabien Potencier", + "email": "fabien@symfony.com" + } + ], + "description": "Swiftmailer, free feature-rich PHP mailer", + "homepage": "https://swiftmailer.symfony.com", + "keywords": [ + "email", + "mail", + "mailer" + ], + "support": { + "issues": "https://github.com/swiftmailer/swiftmailer/issues", + "source": "https://github.com/swiftmailer/swiftmailer/tree/v6.2.7" + }, + "funding": [ + { + "url": "https://github.com/fabpot", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/swiftmailer/swiftmailer", + "type": "tidelift" + } + ], + "time": "2021-03-09T12:30:35+00:00" + }, + { + "name": "symfony/console", + "version": "v5.2.8", + "source": { + "type": "git", + "url": "https://github.com/symfony/console.git", + "reference": "864568fdc0208b3eba3638b6000b69d2386e6768" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/console/zipball/864568fdc0208b3eba3638b6000b69d2386e6768", + "reference": "864568fdc0208b3eba3638b6000b69d2386e6768", + "shasum": "" + }, + "require": { + "php": ">=7.2.5", + "symfony/polyfill-mbstring": "~1.0", + "symfony/polyfill-php73": "^1.8", + "symfony/polyfill-php80": "^1.15", + "symfony/service-contracts": "^1.1|^2", + "symfony/string": "^5.1" + }, + "conflict": { + "symfony/dependency-injection": "<4.4", + "symfony/dotenv": "<5.1", + "symfony/event-dispatcher": "<4.4", + "symfony/lock": "<4.4", + "symfony/process": "<4.4" + }, + "provide": { + "psr/log-implementation": "1.0" + }, + "require-dev": { + "psr/log": "~1.0", + "symfony/config": "^4.4|^5.0", + "symfony/dependency-injection": "^4.4|^5.0", + "symfony/event-dispatcher": "^4.4|^5.0", + "symfony/lock": "^4.4|^5.0", + "symfony/process": "^4.4|^5.0", + "symfony/var-dumper": "^4.4|^5.0" + }, + "suggest": { + "psr/log": "For using the console logger", + "symfony/event-dispatcher": "", + "symfony/lock": "", + "symfony/process": "" + }, + "type": "library", + "autoload": { + "psr-4": { + "Symfony\\Component\\Console\\": "" + }, + "exclude-from-classmap": [ + "/Tests/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Fabien Potencier", + "email": "fabien@symfony.com" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Eases the creation of beautiful and testable command line interfaces", + "homepage": "https://symfony.com", + "keywords": [ + "cli", + "command line", + "console", + "terminal" + ], + "support": { + "source": "https://github.com/symfony/console/tree/v5.2.8" + }, + "funding": [ + { + "url": "https://symfony.com/sponsor", + "type": "custom" + }, + { + "url": "https://github.com/fabpot", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/symfony/symfony", + "type": "tidelift" + } + ], + "time": "2021-05-11T15:45:21+00:00" + }, + { + "name": "symfony/css-selector", + "version": "v5.2.9", + "source": { + "type": "git", + "url": "https://github.com/symfony/css-selector.git", + "reference": "5d5f97809015102116208b976eb2edb44b689560" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/css-selector/zipball/5d5f97809015102116208b976eb2edb44b689560", + "reference": "5d5f97809015102116208b976eb2edb44b689560", + "shasum": "" + }, + "require": { + "php": ">=7.2.5" + }, + "type": "library", + "autoload": { + "psr-4": { + "Symfony\\Component\\CssSelector\\": "" + }, + "exclude-from-classmap": [ + "/Tests/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Fabien Potencier", + "email": "fabien@symfony.com" + }, + { + "name": "Jean-François Simon", + "email": "jeanfrancois.simon@sensiolabs.com" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Converts CSS selectors to XPath expressions", + "homepage": "https://symfony.com", + "support": { + "source": "https://github.com/symfony/css-selector/tree/v5.2.9" + }, + "funding": [ + { + "url": "https://symfony.com/sponsor", + "type": "custom" + }, + { + "url": "https://github.com/fabpot", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/symfony/symfony", + "type": "tidelift" + } + ], + "time": "2021-05-16T13:07:46+00:00" + }, + { + "name": "symfony/deprecation-contracts", + "version": "v2.4.0", + "source": { + "type": "git", + "url": "https://github.com/symfony/deprecation-contracts.git", + "reference": "5f38c8804a9e97d23e0c8d63341088cd8a22d627" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/deprecation-contracts/zipball/5f38c8804a9e97d23e0c8d63341088cd8a22d627", + "reference": "5f38c8804a9e97d23e0c8d63341088cd8a22d627", + "shasum": "" + }, + "require": { + "php": ">=7.1" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-main": "2.4-dev" + }, + "thanks": { + "name": "symfony/contracts", + "url": "https://github.com/symfony/contracts" + } + }, + "autoload": { + "files": [ + "function.php" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Nicolas Grekas", + "email": "p@tchwork.com" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "A generic function and convention to trigger deprecation notices", + "homepage": "https://symfony.com", + "support": { + "source": "https://github.com/symfony/deprecation-contracts/tree/v2.4.0" + }, + "funding": [ + { + "url": "https://symfony.com/sponsor", + "type": "custom" + }, + { + "url": "https://github.com/fabpot", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/symfony/symfony", + "type": "tidelift" + } + ], + "time": "2021-03-23T23:28:01+00:00" + }, + { + "name": "symfony/dom-crawler", + "version": "v5.2.9", + "source": { + "type": "git", + "url": "https://github.com/symfony/dom-crawler.git", + "reference": "8d5201206ded6f37de475b041a11bfaf3ac73d5e" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/dom-crawler/zipball/8d5201206ded6f37de475b041a11bfaf3ac73d5e", + "reference": "8d5201206ded6f37de475b041a11bfaf3ac73d5e", + "shasum": "" + }, + "require": { + "php": ">=7.2.5", + "symfony/polyfill-ctype": "~1.8", + "symfony/polyfill-mbstring": "~1.0", + "symfony/polyfill-php80": "^1.15" + }, + "conflict": { + "masterminds/html5": "<2.6" + }, + "require-dev": { + "masterminds/html5": "^2.6", + "symfony/css-selector": "^4.4|^5.0" + }, + "suggest": { + "symfony/css-selector": "" + }, + "type": "library", + "autoload": { + "psr-4": { + "Symfony\\Component\\DomCrawler\\": "" + }, + "exclude-from-classmap": [ + "/Tests/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Fabien Potencier", + "email": "fabien@symfony.com" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Eases DOM navigation for HTML and XML documents", + "homepage": "https://symfony.com", + "support": { + "source": "https://github.com/symfony/dom-crawler/tree/v5.2.9" + }, + "funding": [ + { + "url": "https://symfony.com/sponsor", + "type": "custom" + }, + { + "url": "https://github.com/fabpot", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/symfony/symfony", + "type": "tidelift" + } + ], + "time": "2021-05-16T13:07:46+00:00" + }, + { + "name": "symfony/error-handler", + "version": "v5.2.8", + "source": { + "type": "git", + "url": "https://github.com/symfony/error-handler.git", + "reference": "1416bc16317a8188aabde251afef7618bf4687ac" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/error-handler/zipball/1416bc16317a8188aabde251afef7618bf4687ac", + "reference": "1416bc16317a8188aabde251afef7618bf4687ac", + "shasum": "" + }, + "require": { + "php": ">=7.2.5", + "psr/log": "^1.0", + "symfony/polyfill-php80": "^1.15", + "symfony/var-dumper": "^4.4|^5.0" + }, + "require-dev": { + "symfony/deprecation-contracts": "^2.1", + "symfony/http-kernel": "^4.4|^5.0", + "symfony/serializer": "^4.4|^5.0" + }, + "type": "library", + "autoload": { + "psr-4": { + "Symfony\\Component\\ErrorHandler\\": "" + }, + "exclude-from-classmap": [ + "/Tests/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Fabien Potencier", + "email": "fabien@symfony.com" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Provides tools to manage errors and ease debugging PHP code", + "homepage": "https://symfony.com", + "support": { + "source": "https://github.com/symfony/error-handler/tree/v5.2.8" + }, + "funding": [ + { + "url": "https://symfony.com/sponsor", + "type": "custom" + }, + { + "url": "https://github.com/fabpot", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/symfony/symfony", + "type": "tidelift" + } + ], + "time": "2021-05-07T13:42:21+00:00" + }, + { + "name": "symfony/event-dispatcher", + "version": "v5.2.4", + "source": { + "type": "git", + "url": "https://github.com/symfony/event-dispatcher.git", + "reference": "d08d6ec121a425897951900ab692b612a61d6240" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/event-dispatcher/zipball/d08d6ec121a425897951900ab692b612a61d6240", + "reference": "d08d6ec121a425897951900ab692b612a61d6240", + "shasum": "" + }, + "require": { + "php": ">=7.2.5", + "symfony/deprecation-contracts": "^2.1", + "symfony/event-dispatcher-contracts": "^2", + "symfony/polyfill-php80": "^1.15" + }, + "conflict": { + "symfony/dependency-injection": "<4.4" + }, + "provide": { + "psr/event-dispatcher-implementation": "1.0", + "symfony/event-dispatcher-implementation": "2.0" + }, + "require-dev": { + "psr/log": "~1.0", + "symfony/config": "^4.4|^5.0", + "symfony/dependency-injection": "^4.4|^5.0", + "symfony/error-handler": "^4.4|^5.0", + "symfony/expression-language": "^4.4|^5.0", + "symfony/http-foundation": "^4.4|^5.0", + "symfony/service-contracts": "^1.1|^2", + "symfony/stopwatch": "^4.4|^5.0" + }, + "suggest": { + "symfony/dependency-injection": "", + "symfony/http-kernel": "" + }, + "type": "library", + "autoload": { + "psr-4": { + "Symfony\\Component\\EventDispatcher\\": "" + }, + "exclude-from-classmap": [ + "/Tests/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Fabien Potencier", + "email": "fabien@symfony.com" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Provides tools that allow your application components to communicate with each other by dispatching events and listening to them", + "homepage": "https://symfony.com", + "support": { + "source": "https://github.com/symfony/event-dispatcher/tree/v5.2.4" + }, + "funding": [ + { + "url": "https://symfony.com/sponsor", + "type": "custom" + }, + { + "url": "https://github.com/fabpot", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/symfony/symfony", + "type": "tidelift" + } + ], + "time": "2021-02-18T17:12:37+00:00" + }, + { + "name": "symfony/event-dispatcher-contracts", + "version": "v2.4.0", + "source": { + "type": "git", + "url": "https://github.com/symfony/event-dispatcher-contracts.git", + "reference": "69fee1ad2332a7cbab3aca13591953da9cdb7a11" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/event-dispatcher-contracts/zipball/69fee1ad2332a7cbab3aca13591953da9cdb7a11", + "reference": "69fee1ad2332a7cbab3aca13591953da9cdb7a11", + "shasum": "" + }, + "require": { + "php": ">=7.2.5", + "psr/event-dispatcher": "^1" + }, + "suggest": { + "symfony/event-dispatcher-implementation": "" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-main": "2.4-dev" + }, + "thanks": { + "name": "symfony/contracts", + "url": "https://github.com/symfony/contracts" + } + }, + "autoload": { + "psr-4": { + "Symfony\\Contracts\\EventDispatcher\\": "" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Nicolas Grekas", + "email": "p@tchwork.com" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Generic abstractions related to dispatching event", + "homepage": "https://symfony.com", + "keywords": [ + "abstractions", + "contracts", + "decoupling", + "interfaces", + "interoperability", + "standards" + ], + "support": { + "source": "https://github.com/symfony/event-dispatcher-contracts/tree/v2.4.0" + }, + "funding": [ + { + "url": "https://symfony.com/sponsor", + "type": "custom" + }, + { + "url": "https://github.com/fabpot", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/symfony/symfony", + "type": "tidelift" + } + ], + "time": "2021-03-23T23:28:01+00:00" + }, + { + "name": "symfony/finder", + "version": "v5.2.9", + "source": { + "type": "git", + "url": "https://github.com/symfony/finder.git", + "reference": "ccccb9d48ca42757dd12f2ca4bf857a4e217d90d" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/finder/zipball/ccccb9d48ca42757dd12f2ca4bf857a4e217d90d", + "reference": "ccccb9d48ca42757dd12f2ca4bf857a4e217d90d", + "shasum": "" + }, + "require": { + "php": ">=7.2.5" + }, + "type": "library", + "autoload": { + "psr-4": { + "Symfony\\Component\\Finder\\": "" + }, + "exclude-from-classmap": [ + "/Tests/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Fabien Potencier", + "email": "fabien@symfony.com" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Finds files and directories via an intuitive fluent interface", + "homepage": "https://symfony.com", + "support": { + "source": "https://github.com/symfony/finder/tree/v5.2.9" + }, + "funding": [ + { + "url": "https://symfony.com/sponsor", + "type": "custom" + }, + { + "url": "https://github.com/fabpot", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/symfony/symfony", + "type": "tidelift" + } + ], + "time": "2021-05-16T13:07:46+00:00" + }, + { + "name": "symfony/http-client-contracts", + "version": "v2.4.0", + "source": { + "type": "git", + "url": "https://github.com/symfony/http-client-contracts.git", + "reference": "7e82f6084d7cae521a75ef2cb5c9457bbda785f4" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/http-client-contracts/zipball/7e82f6084d7cae521a75ef2cb5c9457bbda785f4", + "reference": "7e82f6084d7cae521a75ef2cb5c9457bbda785f4", + "shasum": "" + }, + "require": { + "php": ">=7.2.5" + }, + "suggest": { + "symfony/http-client-implementation": "" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-main": "2.4-dev" + }, + "thanks": { + "name": "symfony/contracts", + "url": "https://github.com/symfony/contracts" + } + }, + "autoload": { + "psr-4": { + "Symfony\\Contracts\\HttpClient\\": "" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Nicolas Grekas", + "email": "p@tchwork.com" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Generic abstractions related to HTTP clients", + "homepage": "https://symfony.com", + "keywords": [ + "abstractions", + "contracts", + "decoupling", + "interfaces", + "interoperability", + "standards" + ], + "support": { + "source": "https://github.com/symfony/http-client-contracts/tree/v2.4.0" + }, + "funding": [ + { + "url": "https://symfony.com/sponsor", + "type": "custom" + }, + { + "url": "https://github.com/fabpot", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/symfony/symfony", + "type": "tidelift" + } + ], + "time": "2021-04-11T23:07:08+00:00" + }, + { + "name": "symfony/http-foundation", + "version": "v5.2.8", + "source": { + "type": "git", + "url": "https://github.com/symfony/http-foundation.git", + "reference": "e8fbbab7c4a71592985019477532629cb2e142dc" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/http-foundation/zipball/e8fbbab7c4a71592985019477532629cb2e142dc", + "reference": "e8fbbab7c4a71592985019477532629cb2e142dc", + "shasum": "" + }, + "require": { + "php": ">=7.2.5", + "symfony/deprecation-contracts": "^2.1", + "symfony/polyfill-mbstring": "~1.1", + "symfony/polyfill-php80": "^1.15" + }, + "require-dev": { + "predis/predis": "~1.0", + "symfony/cache": "^4.4|^5.0", + "symfony/expression-language": "^4.4|^5.0", + "symfony/mime": "^4.4|^5.0" + }, + "suggest": { + "symfony/mime": "To use the file extension guesser" + }, + "type": "library", + "autoload": { + "psr-4": { + "Symfony\\Component\\HttpFoundation\\": "" + }, + "exclude-from-classmap": [ + "/Tests/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Fabien Potencier", + "email": "fabien@symfony.com" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Defines an object-oriented layer for the HTTP specification", + "homepage": "https://symfony.com", + "support": { + "source": "https://github.com/symfony/http-foundation/tree/v5.2.8" + }, + "funding": [ + { + "url": "https://symfony.com/sponsor", + "type": "custom" + }, + { + "url": "https://github.com/fabpot", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/symfony/symfony", + "type": "tidelift" + } + ], + "time": "2021-05-07T13:41:16+00:00" + }, + { + "name": "symfony/http-kernel", + "version": "v5.2.9", + "source": { + "type": "git", + "url": "https://github.com/symfony/http-kernel.git", + "reference": "eb540ef6870dbf33c92e372cfb869ebf9649e6cb" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/http-kernel/zipball/eb540ef6870dbf33c92e372cfb869ebf9649e6cb", + "reference": "eb540ef6870dbf33c92e372cfb869ebf9649e6cb", + "shasum": "" + }, + "require": { + "php": ">=7.2.5", + "psr/log": "~1.0", + "symfony/deprecation-contracts": "^2.1", + "symfony/error-handler": "^4.4|^5.0", + "symfony/event-dispatcher": "^5.0", + "symfony/http-client-contracts": "^1.1|^2", + "symfony/http-foundation": "^4.4|^5.0", + "symfony/polyfill-ctype": "^1.8", + "symfony/polyfill-php73": "^1.9", + "symfony/polyfill-php80": "^1.15" + }, + "conflict": { + "symfony/browser-kit": "<4.4", + "symfony/cache": "<5.0", + "symfony/config": "<5.0", + "symfony/console": "<4.4", + "symfony/dependency-injection": "<5.1.8", + "symfony/doctrine-bridge": "<5.0", + "symfony/form": "<5.0", + "symfony/http-client": "<5.0", + "symfony/mailer": "<5.0", + "symfony/messenger": "<5.0", + "symfony/translation": "<5.0", + "symfony/twig-bridge": "<5.0", + "symfony/validator": "<5.0", + "twig/twig": "<2.13" + }, + "provide": { + "psr/log-implementation": "1.0" + }, + "require-dev": { + "psr/cache": "^1.0|^2.0|^3.0", + "symfony/browser-kit": "^4.4|^5.0", + "symfony/config": "^5.0", + "symfony/console": "^4.4|^5.0", + "symfony/css-selector": "^4.4|^5.0", + "symfony/dependency-injection": "^5.1.8", + "symfony/dom-crawler": "^4.4|^5.0", + "symfony/expression-language": "^4.4|^5.0", + "symfony/finder": "^4.4|^5.0", + "symfony/process": "^4.4|^5.0", + "symfony/routing": "^4.4|^5.0", + "symfony/stopwatch": "^4.4|^5.0", + "symfony/translation": "^4.4|^5.0", + "symfony/translation-contracts": "^1.1|^2", + "twig/twig": "^2.13|^3.0.4" + }, + "suggest": { + "symfony/browser-kit": "", + "symfony/config": "", + "symfony/console": "", + "symfony/dependency-injection": "" + }, + "type": "library", + "autoload": { + "psr-4": { + "Symfony\\Component\\HttpKernel\\": "" + }, + "exclude-from-classmap": [ + "/Tests/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Fabien Potencier", + "email": "fabien@symfony.com" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Provides a structured process for converting a Request into a Response", + "homepage": "https://symfony.com", + "support": { + "source": "https://github.com/symfony/http-kernel/tree/v5.2.9" + }, + "funding": [ + { + "url": "https://symfony.com/sponsor", + "type": "custom" + }, + { + "url": "https://github.com/fabpot", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/symfony/symfony", + "type": "tidelift" + } + ], + "time": "2021-05-19T12:23:45+00:00" + }, + { + "name": "symfony/mime", + "version": "v5.2.9", + "source": { + "type": "git", + "url": "https://github.com/symfony/mime.git", + "reference": "64258e870f8cc75c3dae986201ea2df58c210b52" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/mime/zipball/64258e870f8cc75c3dae986201ea2df58c210b52", + "reference": "64258e870f8cc75c3dae986201ea2df58c210b52", + "shasum": "" + }, + "require": { + "php": ">=7.2.5", + "symfony/deprecation-contracts": "^2.1", + "symfony/polyfill-intl-idn": "^1.10", + "symfony/polyfill-mbstring": "^1.0", + "symfony/polyfill-php80": "^1.15" + }, + "conflict": { + "egulias/email-validator": "~3.0.0", + "phpdocumentor/reflection-docblock": "<3.2.2", + "phpdocumentor/type-resolver": "<1.4.0", + "symfony/mailer": "<4.4" + }, + "require-dev": { + "egulias/email-validator": "^2.1.10|^3.1", + "phpdocumentor/reflection-docblock": "^3.0|^4.0|^5.0", + "symfony/dependency-injection": "^4.4|^5.0", + "symfony/property-access": "^4.4|^5.1", + "symfony/property-info": "^4.4|^5.1", + "symfony/serializer": "^5.2" + }, + "type": "library", + "autoload": { + "psr-4": { + "Symfony\\Component\\Mime\\": "" + }, + "exclude-from-classmap": [ + "/Tests/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Fabien Potencier", + "email": "fabien@symfony.com" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Allows manipulating MIME messages", + "homepage": "https://symfony.com", + "keywords": [ + "mime", + "mime-type" + ], + "support": { + "source": "https://github.com/symfony/mime/tree/v5.2.9" + }, + "funding": [ + { + "url": "https://symfony.com/sponsor", + "type": "custom" + }, + { + "url": "https://github.com/fabpot", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/symfony/symfony", + "type": "tidelift" + } + ], + "time": "2021-05-16T13:07:46+00:00" + }, + { + "name": "symfony/polyfill-apcu", + "version": "v1.23.0", + "source": { + "type": "git", + "url": "https://github.com/symfony/polyfill-apcu.git", + "reference": "80f7fb64c5b64ebcba76f40215e63808a2062a18" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/polyfill-apcu/zipball/80f7fb64c5b64ebcba76f40215e63808a2062a18", + "reference": "80f7fb64c5b64ebcba76f40215e63808a2062a18", + "shasum": "" + }, + "require": { + "php": ">=7.1" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-main": "1.23-dev" + }, + "thanks": { + "name": "symfony/polyfill", + "url": "https://github.com/symfony/polyfill" + } + }, + "autoload": { + "psr-4": { + "Symfony\\Polyfill\\Apcu\\": "" + }, + "files": [ + "bootstrap.php" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Nicolas Grekas", + "email": "p@tchwork.com" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Symfony polyfill backporting apcu_* functions to lower PHP versions", + "homepage": "https://symfony.com", + "keywords": [ + "apcu", + "compatibility", + "polyfill", + "portable", + "shim" + ], + "support": { + "source": "https://github.com/symfony/polyfill-apcu/tree/v1.23.0" + }, + "funding": [ + { + "url": "https://symfony.com/sponsor", + "type": "custom" + }, + { + "url": "https://github.com/fabpot", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/symfony/symfony", + "type": "tidelift" + } + ], + "time": "2021-02-19T12:13:01+00:00" + }, + { + "name": "symfony/polyfill-ctype", + "version": "v1.23.0", + "source": { + "type": "git", + "url": "https://github.com/symfony/polyfill-ctype.git", + "reference": "46cd95797e9df938fdd2b03693b5fca5e64b01ce" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/polyfill-ctype/zipball/46cd95797e9df938fdd2b03693b5fca5e64b01ce", + "reference": "46cd95797e9df938fdd2b03693b5fca5e64b01ce", + "shasum": "" + }, + "require": { + "php": ">=7.1" + }, + "suggest": { + "ext-ctype": "For best performance" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-main": "1.23-dev" + }, + "thanks": { + "name": "symfony/polyfill", + "url": "https://github.com/symfony/polyfill" + } + }, + "autoload": { + "psr-4": { + "Symfony\\Polyfill\\Ctype\\": "" + }, + "files": [ + "bootstrap.php" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Gert de Pagter", + "email": "BackEndTea@gmail.com" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Symfony polyfill for ctype functions", + "homepage": "https://symfony.com", + "keywords": [ + "compatibility", + "ctype", + "polyfill", + "portable" + ], + "support": { + "source": "https://github.com/symfony/polyfill-ctype/tree/v1.23.0" + }, + "funding": [ + { + "url": "https://symfony.com/sponsor", + "type": "custom" + }, + { + "url": "https://github.com/fabpot", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/symfony/symfony", + "type": "tidelift" + } + ], + "time": "2021-02-19T12:13:01+00:00" + }, + { + "name": "symfony/polyfill-iconv", + "version": "v1.23.0", + "source": { + "type": "git", + "url": "https://github.com/symfony/polyfill-iconv.git", + "reference": "63b5bb7db83e5673936d6e3b8b3e022ff6474933" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/polyfill-iconv/zipball/63b5bb7db83e5673936d6e3b8b3e022ff6474933", + "reference": "63b5bb7db83e5673936d6e3b8b3e022ff6474933", + "shasum": "" + }, + "require": { + "php": ">=7.1" + }, + "suggest": { + "ext-iconv": "For best performance" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-main": "1.23-dev" + }, + "thanks": { + "name": "symfony/polyfill", + "url": "https://github.com/symfony/polyfill" + } + }, + "autoload": { + "psr-4": { + "Symfony\\Polyfill\\Iconv\\": "" + }, + "files": [ + "bootstrap.php" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Nicolas Grekas", + "email": "p@tchwork.com" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Symfony polyfill for the Iconv extension", + "homepage": "https://symfony.com", + "keywords": [ + "compatibility", + "iconv", + "polyfill", + "portable", + "shim" + ], + "support": { + "source": "https://github.com/symfony/polyfill-iconv/tree/v1.23.0" + }, + "funding": [ + { + "url": "https://symfony.com/sponsor", + "type": "custom" + }, + { + "url": "https://github.com/fabpot", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/symfony/symfony", + "type": "tidelift" + } + ], + "time": "2021-05-27T09:27:20+00:00" + }, + { + "name": "symfony/polyfill-intl-grapheme", + "version": "v1.23.0", + "source": { + "type": "git", + "url": "https://github.com/symfony/polyfill-intl-grapheme.git", + "reference": "24b72c6baa32c746a4d0840147c9715e42bb68ab" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/polyfill-intl-grapheme/zipball/24b72c6baa32c746a4d0840147c9715e42bb68ab", + "reference": "24b72c6baa32c746a4d0840147c9715e42bb68ab", + "shasum": "" + }, + "require": { + "php": ">=7.1" + }, + "suggest": { + "ext-intl": "For best performance" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-main": "1.23-dev" + }, + "thanks": { + "name": "symfony/polyfill", + "url": "https://github.com/symfony/polyfill" + } + }, + "autoload": { + "psr-4": { + "Symfony\\Polyfill\\Intl\\Grapheme\\": "" + }, + "files": [ + "bootstrap.php" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Nicolas Grekas", + "email": "p@tchwork.com" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Symfony polyfill for intl's grapheme_* functions", + "homepage": "https://symfony.com", + "keywords": [ + "compatibility", + "grapheme", + "intl", + "polyfill", + "portable", + "shim" + ], + "support": { + "source": "https://github.com/symfony/polyfill-intl-grapheme/tree/v1.23.0" + }, + "funding": [ + { + "url": "https://symfony.com/sponsor", + "type": "custom" + }, + { + "url": "https://github.com/fabpot", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/symfony/symfony", + "type": "tidelift" + } + ], + "time": "2021-05-27T09:17:38+00:00" + }, + { + "name": "symfony/polyfill-intl-idn", + "version": "v1.23.0", + "source": { + "type": "git", + "url": "https://github.com/symfony/polyfill-intl-idn.git", + "reference": "65bd267525e82759e7d8c4e8ceea44f398838e65" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/polyfill-intl-idn/zipball/65bd267525e82759e7d8c4e8ceea44f398838e65", + "reference": "65bd267525e82759e7d8c4e8ceea44f398838e65", + "shasum": "" + }, + "require": { + "php": ">=7.1", + "symfony/polyfill-intl-normalizer": "^1.10", + "symfony/polyfill-php72": "^1.10" + }, + "suggest": { + "ext-intl": "For best performance" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-main": "1.23-dev" + }, + "thanks": { + "name": "symfony/polyfill", + "url": "https://github.com/symfony/polyfill" + } + }, + "autoload": { + "psr-4": { + "Symfony\\Polyfill\\Intl\\Idn\\": "" + }, + "files": [ + "bootstrap.php" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Laurent Bassin", + "email": "laurent@bassin.info" + }, + { + "name": "Trevor Rowbotham", + "email": "trevor.rowbotham@pm.me" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Symfony polyfill for intl's idn_to_ascii and idn_to_utf8 functions", + "homepage": "https://symfony.com", + "keywords": [ + "compatibility", + "idn", + "intl", + "polyfill", + "portable", + "shim" + ], + "support": { + "source": "https://github.com/symfony/polyfill-intl-idn/tree/v1.23.0" + }, + "funding": [ + { + "url": "https://symfony.com/sponsor", + "type": "custom" + }, + { + "url": "https://github.com/fabpot", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/symfony/symfony", + "type": "tidelift" + } + ], + "time": "2021-05-27T09:27:20+00:00" + }, + { + "name": "symfony/polyfill-intl-normalizer", + "version": "v1.23.0", + "source": { + "type": "git", + "url": "https://github.com/symfony/polyfill-intl-normalizer.git", + "reference": "8590a5f561694770bdcd3f9b5c69dde6945028e8" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/polyfill-intl-normalizer/zipball/8590a5f561694770bdcd3f9b5c69dde6945028e8", + "reference": "8590a5f561694770bdcd3f9b5c69dde6945028e8", + "shasum": "" + }, + "require": { + "php": ">=7.1" + }, + "suggest": { + "ext-intl": "For best performance" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-main": "1.23-dev" + }, + "thanks": { + "name": "symfony/polyfill", + "url": "https://github.com/symfony/polyfill" + } + }, + "autoload": { + "psr-4": { + "Symfony\\Polyfill\\Intl\\Normalizer\\": "" + }, + "files": [ + "bootstrap.php" + ], + "classmap": [ + "Resources/stubs" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Nicolas Grekas", + "email": "p@tchwork.com" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Symfony polyfill for intl's Normalizer class and related functions", + "homepage": "https://symfony.com", + "keywords": [ + "compatibility", + "intl", + "normalizer", + "polyfill", + "portable", + "shim" + ], + "support": { + "source": "https://github.com/symfony/polyfill-intl-normalizer/tree/v1.23.0" + }, + "funding": [ + { + "url": "https://symfony.com/sponsor", + "type": "custom" + }, + { + "url": "https://github.com/fabpot", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/symfony/symfony", + "type": "tidelift" + } + ], + "time": "2021-02-19T12:13:01+00:00" + }, + { + "name": "symfony/polyfill-mbstring", + "version": "v1.23.0", + "source": { + "type": "git", + "url": "https://github.com/symfony/polyfill-mbstring.git", + "reference": "2df51500adbaebdc4c38dea4c89a2e131c45c8a1" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/polyfill-mbstring/zipball/2df51500adbaebdc4c38dea4c89a2e131c45c8a1", + "reference": "2df51500adbaebdc4c38dea4c89a2e131c45c8a1", + "shasum": "" + }, + "require": { + "php": ">=7.1" + }, + "suggest": { + "ext-mbstring": "For best performance" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-main": "1.23-dev" + }, + "thanks": { + "name": "symfony/polyfill", + "url": "https://github.com/symfony/polyfill" + } + }, + "autoload": { + "psr-4": { + "Symfony\\Polyfill\\Mbstring\\": "" + }, + "files": [ + "bootstrap.php" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Nicolas Grekas", + "email": "p@tchwork.com" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Symfony polyfill for the Mbstring extension", + "homepage": "https://symfony.com", + "keywords": [ + "compatibility", + "mbstring", + "polyfill", + "portable", + "shim" + ], + "support": { + "source": "https://github.com/symfony/polyfill-mbstring/tree/v1.23.0" + }, + "funding": [ + { + "url": "https://symfony.com/sponsor", + "type": "custom" + }, + { + "url": "https://github.com/fabpot", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/symfony/symfony", + "type": "tidelift" + } + ], + "time": "2021-05-27T09:27:20+00:00" + }, + { + "name": "symfony/polyfill-php72", + "version": "v1.23.0", + "source": { + "type": "git", + "url": "https://github.com/symfony/polyfill-php72.git", + "reference": "9a142215a36a3888e30d0a9eeea9766764e96976" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/polyfill-php72/zipball/9a142215a36a3888e30d0a9eeea9766764e96976", + "reference": "9a142215a36a3888e30d0a9eeea9766764e96976", + "shasum": "" + }, + "require": { + "php": ">=7.1" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-main": "1.23-dev" + }, + "thanks": { + "name": "symfony/polyfill", + "url": "https://github.com/symfony/polyfill" + } + }, + "autoload": { + "psr-4": { + "Symfony\\Polyfill\\Php72\\": "" + }, + "files": [ + "bootstrap.php" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Nicolas Grekas", + "email": "p@tchwork.com" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Symfony polyfill backporting some PHP 7.2+ features to lower PHP versions", + "homepage": "https://symfony.com", + "keywords": [ + "compatibility", + "polyfill", + "portable", + "shim" + ], + "support": { + "source": "https://github.com/symfony/polyfill-php72/tree/v1.23.0" + }, + "funding": [ + { + "url": "https://symfony.com/sponsor", + "type": "custom" + }, + { + "url": "https://github.com/fabpot", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/symfony/symfony", + "type": "tidelift" + } + ], + "time": "2021-05-27T09:17:38+00:00" + }, + { + "name": "symfony/polyfill-php73", + "version": "v1.23.0", + "source": { + "type": "git", + "url": "https://github.com/symfony/polyfill-php73.git", + "reference": "fba8933c384d6476ab14fb7b8526e5287ca7e010" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/polyfill-php73/zipball/fba8933c384d6476ab14fb7b8526e5287ca7e010", + "reference": "fba8933c384d6476ab14fb7b8526e5287ca7e010", + "shasum": "" + }, + "require": { + "php": ">=7.1" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-main": "1.23-dev" + }, + "thanks": { + "name": "symfony/polyfill", + "url": "https://github.com/symfony/polyfill" + } + }, + "autoload": { + "psr-4": { + "Symfony\\Polyfill\\Php73\\": "" + }, + "files": [ + "bootstrap.php" + ], + "classmap": [ + "Resources/stubs" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Nicolas Grekas", + "email": "p@tchwork.com" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Symfony polyfill backporting some PHP 7.3+ features to lower PHP versions", + "homepage": "https://symfony.com", + "keywords": [ + "compatibility", + "polyfill", + "portable", + "shim" + ], + "support": { + "source": "https://github.com/symfony/polyfill-php73/tree/v1.23.0" + }, + "funding": [ + { + "url": "https://symfony.com/sponsor", + "type": "custom" + }, + { + "url": "https://github.com/fabpot", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/symfony/symfony", + "type": "tidelift" + } + ], + "time": "2021-02-19T12:13:01+00:00" + }, + { + "name": "symfony/polyfill-php80", + "version": "v1.23.0", + "source": { + "type": "git", + "url": "https://github.com/symfony/polyfill-php80.git", + "reference": "eca0bf41ed421bed1b57c4958bab16aa86b757d0" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/polyfill-php80/zipball/eca0bf41ed421bed1b57c4958bab16aa86b757d0", + "reference": "eca0bf41ed421bed1b57c4958bab16aa86b757d0", + "shasum": "" + }, + "require": { + "php": ">=7.1" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-main": "1.23-dev" + }, + "thanks": { + "name": "symfony/polyfill", + "url": "https://github.com/symfony/polyfill" + } + }, + "autoload": { + "psr-4": { + "Symfony\\Polyfill\\Php80\\": "" + }, + "files": [ + "bootstrap.php" + ], + "classmap": [ + "Resources/stubs" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Ion Bazan", + "email": "ion.bazan@gmail.com" + }, + { + "name": "Nicolas Grekas", + "email": "p@tchwork.com" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Symfony polyfill backporting some PHP 8.0+ features to lower PHP versions", + "homepage": "https://symfony.com", + "keywords": [ + "compatibility", + "polyfill", + "portable", + "shim" + ], + "support": { + "source": "https://github.com/symfony/polyfill-php80/tree/v1.23.0" + }, + "funding": [ + { + "url": "https://symfony.com/sponsor", + "type": "custom" + }, + { + "url": "https://github.com/fabpot", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/symfony/symfony", + "type": "tidelift" + } + ], + "time": "2021-02-19T12:13:01+00:00" + }, + { + "name": "symfony/process", + "version": "v5.2.7", + "source": { + "type": "git", + "url": "https://github.com/symfony/process.git", + "reference": "98cb8eeb72e55d4196dd1e36f1f16e7b3a9a088e" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/process/zipball/98cb8eeb72e55d4196dd1e36f1f16e7b3a9a088e", + "reference": "98cb8eeb72e55d4196dd1e36f1f16e7b3a9a088e", + "shasum": "" + }, + "require": { + "php": ">=7.2.5", + "symfony/polyfill-php80": "^1.15" + }, + "type": "library", + "autoload": { + "psr-4": { + "Symfony\\Component\\Process\\": "" + }, + "exclude-from-classmap": [ + "/Tests/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Fabien Potencier", + "email": "fabien@symfony.com" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Executes commands in sub-processes", + "homepage": "https://symfony.com", + "support": { + "source": "https://github.com/symfony/process/tree/v5.3.0-BETA1" + }, + "funding": [ + { + "url": "https://symfony.com/sponsor", + "type": "custom" + }, + { + "url": "https://github.com/fabpot", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/symfony/symfony", + "type": "tidelift" + } + ], + "time": "2021-04-08T10:27:02+00:00" + }, + { + "name": "symfony/routing", + "version": "v5.2.9", + "source": { + "type": "git", + "url": "https://github.com/symfony/routing.git", + "reference": "4a7b2bf5e1221be1902b6853743a9bb317f6925e" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/routing/zipball/4a7b2bf5e1221be1902b6853743a9bb317f6925e", + "reference": "4a7b2bf5e1221be1902b6853743a9bb317f6925e", + "shasum": "" + }, + "require": { + "php": ">=7.2.5", + "symfony/deprecation-contracts": "^2.1", + "symfony/polyfill-php80": "^1.15" + }, + "conflict": { + "symfony/config": "<5.0", + "symfony/dependency-injection": "<4.4", + "symfony/yaml": "<4.4" + }, + "require-dev": { + "doctrine/annotations": "^1.10.4", + "psr/log": "~1.0", + "symfony/config": "^5.0", + "symfony/dependency-injection": "^4.4|^5.0", + "symfony/expression-language": "^4.4|^5.0", + "symfony/http-foundation": "^4.4|^5.0", + "symfony/yaml": "^4.4|^5.0" + }, + "suggest": { + "symfony/config": "For using the all-in-one router or any loader", + "symfony/expression-language": "For using expression matching", + "symfony/http-foundation": "For using a Symfony Request object", + "symfony/yaml": "For using the YAML loader" + }, + "type": "library", + "autoload": { + "psr-4": { + "Symfony\\Component\\Routing\\": "" + }, + "exclude-from-classmap": [ + "/Tests/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Fabien Potencier", + "email": "fabien@symfony.com" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Maps an HTTP request to a set of configuration variables", + "homepage": "https://symfony.com", + "keywords": [ + "router", + "routing", + "uri", + "url" + ], + "support": { + "source": "https://github.com/symfony/routing/tree/v5.2.9" + }, + "funding": [ + { + "url": "https://symfony.com/sponsor", + "type": "custom" + }, + { + "url": "https://github.com/fabpot", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/symfony/symfony", + "type": "tidelift" + } + ], + "time": "2021-05-16T13:07:46+00:00" + }, + { + "name": "symfony/service-contracts", + "version": "v2.4.0", + "source": { + "type": "git", + "url": "https://github.com/symfony/service-contracts.git", + "reference": "f040a30e04b57fbcc9c6cbcf4dbaa96bd318b9bb" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/service-contracts/zipball/f040a30e04b57fbcc9c6cbcf4dbaa96bd318b9bb", + "reference": "f040a30e04b57fbcc9c6cbcf4dbaa96bd318b9bb", + "shasum": "" + }, + "require": { + "php": ">=7.2.5", + "psr/container": "^1.1" + }, + "suggest": { + "symfony/service-implementation": "" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-main": "2.4-dev" + }, + "thanks": { + "name": "symfony/contracts", + "url": "https://github.com/symfony/contracts" + } + }, + "autoload": { + "psr-4": { + "Symfony\\Contracts\\Service\\": "" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Nicolas Grekas", + "email": "p@tchwork.com" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Generic abstractions related to writing services", + "homepage": "https://symfony.com", + "keywords": [ + "abstractions", + "contracts", + "decoupling", + "interfaces", + "interoperability", + "standards" + ], + "support": { + "source": "https://github.com/symfony/service-contracts/tree/v2.4.0" + }, + "funding": [ + { + "url": "https://symfony.com/sponsor", + "type": "custom" + }, + { + "url": "https://github.com/fabpot", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/symfony/symfony", + "type": "tidelift" + } + ], + "time": "2021-04-01T10:43:52+00:00" + }, + { + "name": "symfony/string", + "version": "v5.2.8", + "source": { + "type": "git", + "url": "https://github.com/symfony/string.git", + "reference": "01b35eb64cac8467c3f94cd0ce2d0d376bb7d1db" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/string/zipball/01b35eb64cac8467c3f94cd0ce2d0d376bb7d1db", + "reference": "01b35eb64cac8467c3f94cd0ce2d0d376bb7d1db", + "shasum": "" + }, + "require": { + "php": ">=7.2.5", + "symfony/polyfill-ctype": "~1.8", + "symfony/polyfill-intl-grapheme": "~1.0", + "symfony/polyfill-intl-normalizer": "~1.0", + "symfony/polyfill-mbstring": "~1.0", + "symfony/polyfill-php80": "~1.15" + }, + "require-dev": { + "symfony/error-handler": "^4.4|^5.0", + "symfony/http-client": "^4.4|^5.0", + "symfony/translation-contracts": "^1.1|^2", + "symfony/var-exporter": "^4.4|^5.0" + }, + "type": "library", + "autoload": { + "psr-4": { + "Symfony\\Component\\String\\": "" + }, + "files": [ + "Resources/functions.php" + ], + "exclude-from-classmap": [ + "/Tests/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Nicolas Grekas", + "email": "p@tchwork.com" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Provides an object-oriented API to strings and deals with bytes, UTF-8 code points and grapheme clusters in a unified way", + "homepage": "https://symfony.com", + "keywords": [ + "grapheme", + "i18n", + "string", + "unicode", + "utf-8", + "utf8" + ], + "support": { + "source": "https://github.com/symfony/string/tree/v5.2.8" + }, + "funding": [ + { + "url": "https://symfony.com/sponsor", + "type": "custom" + }, + { + "url": "https://github.com/fabpot", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/symfony/symfony", + "type": "tidelift" + } + ], + "time": "2021-05-10T14:56:10+00:00" + }, + { + "name": "symfony/translation", + "version": "v5.2.9", + "source": { + "type": "git", + "url": "https://github.com/symfony/translation.git", + "reference": "61af68dba333e2d376a325a29c2a3f2a605b4876" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/translation/zipball/61af68dba333e2d376a325a29c2a3f2a605b4876", + "reference": "61af68dba333e2d376a325a29c2a3f2a605b4876", + "shasum": "" + }, + "require": { + "php": ">=7.2.5", + "symfony/polyfill-mbstring": "~1.0", + "symfony/polyfill-php80": "^1.15", + "symfony/translation-contracts": "^2.3" + }, + "conflict": { + "symfony/config": "<4.4", + "symfony/dependency-injection": "<5.0", + "symfony/http-kernel": "<5.0", + "symfony/twig-bundle": "<5.0", + "symfony/yaml": "<4.4" + }, + "provide": { + "symfony/translation-implementation": "2.3" + }, + "require-dev": { + "psr/log": "~1.0", + "symfony/config": "^4.4|^5.0", + "symfony/console": "^4.4|^5.0", + "symfony/dependency-injection": "^5.0", + "symfony/finder": "^4.4|^5.0", + "symfony/http-kernel": "^5.0", + "symfony/intl": "^4.4|^5.0", + "symfony/service-contracts": "^1.1.2|^2", + "symfony/yaml": "^4.4|^5.0" + }, + "suggest": { + "psr/log-implementation": "To use logging capability in translator", + "symfony/config": "", + "symfony/yaml": "" + }, + "type": "library", + "autoload": { + "files": [ + "Resources/functions.php" + ], + "psr-4": { + "Symfony\\Component\\Translation\\": "" + }, + "exclude-from-classmap": [ + "/Tests/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Fabien Potencier", + "email": "fabien@symfony.com" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Provides tools to internationalize your application", + "homepage": "https://symfony.com", + "support": { + "source": "https://github.com/symfony/translation/tree/v5.2.9" + }, + "funding": [ + { + "url": "https://symfony.com/sponsor", + "type": "custom" + }, + { + "url": "https://github.com/fabpot", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/symfony/symfony", + "type": "tidelift" + } + ], + "time": "2021-05-16T13:07:46+00:00" + }, + { + "name": "symfony/translation-contracts", + "version": "v2.4.0", + "source": { + "type": "git", + "url": "https://github.com/symfony/translation-contracts.git", + "reference": "95c812666f3e91db75385749fe219c5e494c7f95" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/translation-contracts/zipball/95c812666f3e91db75385749fe219c5e494c7f95", + "reference": "95c812666f3e91db75385749fe219c5e494c7f95", + "shasum": "" + }, + "require": { + "php": ">=7.2.5" + }, + "suggest": { + "symfony/translation-implementation": "" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-main": "2.4-dev" + }, + "thanks": { + "name": "symfony/contracts", + "url": "https://github.com/symfony/contracts" + } + }, + "autoload": { + "psr-4": { + "Symfony\\Contracts\\Translation\\": "" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Nicolas Grekas", + "email": "p@tchwork.com" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Generic abstractions related to translation", + "homepage": "https://symfony.com", + "keywords": [ + "abstractions", + "contracts", + "decoupling", + "interfaces", + "interoperability", + "standards" + ], + "support": { + "source": "https://github.com/symfony/translation-contracts/tree/v2.4.0" + }, + "funding": [ + { + "url": "https://symfony.com/sponsor", + "type": "custom" + }, + { + "url": "https://github.com/fabpot", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/symfony/symfony", + "type": "tidelift" + } + ], + "time": "2021-03-23T23:28:01+00:00" + }, + { + "name": "symfony/var-dumper", + "version": "v5.2.8", + "source": { + "type": "git", + "url": "https://github.com/symfony/var-dumper.git", + "reference": "d693200a73fae179d27f8f1b16b4faf3e8569eba" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/var-dumper/zipball/d693200a73fae179d27f8f1b16b4faf3e8569eba", + "reference": "d693200a73fae179d27f8f1b16b4faf3e8569eba", + "shasum": "" + }, + "require": { + "php": ">=7.2.5", + "symfony/polyfill-mbstring": "~1.0", + "symfony/polyfill-php80": "^1.15" + }, + "conflict": { + "phpunit/phpunit": "<5.4.3", + "symfony/console": "<4.4" + }, + "require-dev": { + "ext-iconv": "*", + "symfony/console": "^4.4|^5.0", + "symfony/process": "^4.4|^5.0", + "twig/twig": "^2.13|^3.0.4" + }, + "suggest": { + "ext-iconv": "To convert non-UTF-8 strings to UTF-8 (or symfony/polyfill-iconv in case ext-iconv cannot be used).", + "ext-intl": "To show region name in time zone dump", + "symfony/console": "To use the ServerDumpCommand and/or the bin/var-dump-server script" + }, + "bin": [ + "Resources/bin/var-dump-server" + ], + "type": "library", + "autoload": { + "files": [ + "Resources/functions/dump.php" + ], + "psr-4": { + "Symfony\\Component\\VarDumper\\": "" + }, + "exclude-from-classmap": [ + "/Tests/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Nicolas Grekas", + "email": "p@tchwork.com" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Provides mechanisms for walking through any arbitrary PHP variable", + "homepage": "https://symfony.com", + "keywords": [ + "debug", + "dump" + ], + "support": { + "source": "https://github.com/symfony/var-dumper/tree/v5.2.8" + }, + "funding": [ + { + "url": "https://symfony.com/sponsor", + "type": "custom" + }, + { + "url": "https://github.com/fabpot", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/symfony/symfony", + "type": "tidelift" + } + ], + "time": "2021-05-07T13:42:21+00:00" + }, + { + "name": "tijsverkoyen/css-to-inline-styles", + "version": "2.2.3", + "source": { + "type": "git", + "url": "https://github.com/tijsverkoyen/CssToInlineStyles.git", + "reference": "b43b05cf43c1b6d849478965062b6ef73e223bb5" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/tijsverkoyen/CssToInlineStyles/zipball/b43b05cf43c1b6d849478965062b6ef73e223bb5", + "reference": "b43b05cf43c1b6d849478965062b6ef73e223bb5", + "shasum": "" + }, + "require": { + "ext-dom": "*", + "ext-libxml": "*", + "php": "^5.5 || ^7.0 || ^8.0", + "symfony/css-selector": "^2.7 || ^3.0 || ^4.0 || ^5.0" + }, + "require-dev": { + "phpunit/phpunit": "^4.8.35 || ^5.7 || ^6.0 || ^7.5" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "2.2.x-dev" + } + }, + "autoload": { + "psr-4": { + "TijsVerkoyen\\CssToInlineStyles\\": "src" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Tijs Verkoyen", + "email": "css_to_inline_styles@verkoyen.eu", + "role": "Developer" + } + ], + "description": "CssToInlineStyles is a class that enables you to convert HTML-pages/files into HTML-pages/files with inline styles. This is very useful when you're sending emails.", + "homepage": "https://github.com/tijsverkoyen/CssToInlineStyles", + "support": { + "issues": "https://github.com/tijsverkoyen/CssToInlineStyles/issues", + "source": "https://github.com/tijsverkoyen/CssToInlineStyles/tree/2.2.3" + }, + "time": "2020-07-13T06:12:54+00:00" + }, + { + "name": "vlucas/phpdotenv", + "version": "v5.3.0", + "source": { + "type": "git", + "url": "https://github.com/vlucas/phpdotenv.git", + "reference": "b3eac5c7ac896e52deab4a99068e3f4ab12d9e56" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/vlucas/phpdotenv/zipball/b3eac5c7ac896e52deab4a99068e3f4ab12d9e56", + "reference": "b3eac5c7ac896e52deab4a99068e3f4ab12d9e56", + "shasum": "" + }, + "require": { + "ext-pcre": "*", + "graham-campbell/result-type": "^1.0.1", + "php": "^7.1.3 || ^8.0", + "phpoption/phpoption": "^1.7.4", + "symfony/polyfill-ctype": "^1.17", + "symfony/polyfill-mbstring": "^1.17", + "symfony/polyfill-php80": "^1.17" + }, + "require-dev": { + "bamarni/composer-bin-plugin": "^1.4.1", + "ext-filter": "*", + "phpunit/phpunit": "^7.5.20 || ^8.5.14 || ^9.5.1" + }, + "suggest": { + "ext-filter": "Required to use the boolean validator." + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "5.3-dev" + } + }, + "autoload": { + "psr-4": { + "Dotenv\\": "src/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Graham Campbell", + "email": "graham@alt-three.com", + "homepage": "https://gjcampbell.co.uk/" + }, + { + "name": "Vance Lucas", + "email": "vance@vancelucas.com", + "homepage": "https://vancelucas.com/" + } + ], + "description": "Loads environment variables from `.env` to `getenv()`, `$_ENV` and `$_SERVER` automagically.", + "keywords": [ + "dotenv", + "env", + "environment" + ], + "support": { + "issues": "https://github.com/vlucas/phpdotenv/issues", + "source": "https://github.com/vlucas/phpdotenv/tree/v5.3.0" + }, + "funding": [ + { + "url": "https://github.com/GrahamCampbell", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/vlucas/phpdotenv", + "type": "tidelift" + } + ], + "time": "2021-01-20T15:23:13+00:00" + }, + { + "name": "voku/portable-ascii", + "version": "1.5.6", + "source": { + "type": "git", + "url": "https://github.com/voku/portable-ascii.git", + "reference": "80953678b19901e5165c56752d087fc11526017c" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/voku/portable-ascii/zipball/80953678b19901e5165c56752d087fc11526017c", + "reference": "80953678b19901e5165c56752d087fc11526017c", + "shasum": "" + }, + "require": { + "php": ">=7.0.0" + }, + "require-dev": { + "phpunit/phpunit": "~6.0 || ~7.0 || ~9.0" + }, + "suggest": { + "ext-intl": "Use Intl for transliterator_transliterate() support" + }, + "type": "library", + "autoload": { + "psr-4": { + "voku\\": "src/voku/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Lars Moelleken", + "homepage": "http://www.moelleken.org/" + } + ], + "description": "Portable ASCII library - performance optimized (ascii) string functions for php.", + "homepage": "https://github.com/voku/portable-ascii", + "keywords": [ + "ascii", + "clean", + "php" + ], + "support": { + "issues": "https://github.com/voku/portable-ascii/issues", + "source": "https://github.com/voku/portable-ascii/tree/1.5.6" + }, + "funding": [ + { + "url": "https://www.paypal.me/moelleken", + "type": "custom" + }, + { + "url": "https://github.com/voku", + "type": "github" + }, + { + "url": "https://opencollective.com/portable-ascii", + "type": "open_collective" + }, + { + "url": "https://www.patreon.com/voku", + "type": "patreon" + }, + { + "url": "https://tidelift.com/funding/github/packagist/voku/portable-ascii", + "type": "tidelift" + } + ], + "time": "2020-11-12T00:07:28+00:00" + }, + { + "name": "webmozart/assert", + "version": "1.10.0", + "source": { + "type": "git", + "url": "https://github.com/webmozarts/assert.git", + "reference": "6964c76c7804814a842473e0c8fd15bab0f18e25" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/webmozarts/assert/zipball/6964c76c7804814a842473e0c8fd15bab0f18e25", + "reference": "6964c76c7804814a842473e0c8fd15bab0f18e25", + "shasum": "" + }, + "require": { + "php": "^7.2 || ^8.0", + "symfony/polyfill-ctype": "^1.8" + }, + "conflict": { + "phpstan/phpstan": "<0.12.20", + "vimeo/psalm": "<4.6.1 || 4.6.2" + }, + "require-dev": { + "phpunit/phpunit": "^8.5.13" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.10-dev" + } + }, + "autoload": { + "psr-4": { + "Webmozart\\Assert\\": "src/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Bernhard Schussek", + "email": "bschussek@gmail.com" + } + ], + "description": "Assertions to validate method input/output with nice error messages.", + "keywords": [ + "assert", + "check", + "validate" + ], + "support": { + "issues": "https://github.com/webmozarts/assert/issues", + "source": "https://github.com/webmozarts/assert/tree/1.10.0" + }, + "time": "2021-03-09T10:59:23+00:00" + } + ], + "packages-dev": [ + { + "name": "browserstack/browserstack-local", + "version": "v1.1.0", + "source": { + "type": "git", + "url": "https://github.com/browserstack/browserstack-local-php.git", + "reference": "491c6e31960ce8111d2cb70cb84d03e73f270dbb" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/browserstack/browserstack-local-php/zipball/491c6e31960ce8111d2cb70cb84d03e73f270dbb", + "reference": "491c6e31960ce8111d2cb70cb84d03e73f270dbb", + "shasum": "" + }, + "require": { + "php": ">=5.3.19" + }, + "require-dev": { + "phpunit/phpunit": "4.6.*" + }, + "suggest": { + "phpdocumentor/phpdocumentor": "2.*" + }, + "type": "library", + "autoload": { + "psr-4": { + "BrowserStack\\": "lib/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "description": "PHP bindings for BrowserStack Local", + "homepage": "https://github.com/browserstack/browserstack-local-php", + "keywords": [ + "BrowserStack", + "browserstacklocal", + "local", + "php", + "selenium" + ], + "support": { + "issues": "https://github.com/browserstack/browserstack-local-php/issues", + "source": "https://github.com/browserstack/browserstack-local-php" + }, + "time": "2016-09-19T13:39:06+00:00" + }, + { + "name": "doctrine/instantiator", + "version": "1.4.0", + "source": { + "type": "git", + "url": "https://github.com/doctrine/instantiator.git", + "reference": "d56bf6102915de5702778fe20f2de3b2fe570b5b" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/doctrine/instantiator/zipball/d56bf6102915de5702778fe20f2de3b2fe570b5b", + "reference": "d56bf6102915de5702778fe20f2de3b2fe570b5b", + "shasum": "" + }, + "require": { + "php": "^7.1 || ^8.0" + }, + "require-dev": { + "doctrine/coding-standard": "^8.0", + "ext-pdo": "*", + "ext-phar": "*", + "phpbench/phpbench": "^0.13 || 1.0.0-alpha2", + "phpstan/phpstan": "^0.12", + "phpstan/phpstan-phpunit": "^0.12", + "phpunit/phpunit": "^7.0 || ^8.0 || ^9.0" + }, + "type": "library", + "autoload": { + "psr-4": { + "Doctrine\\Instantiator\\": "src/Doctrine/Instantiator/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Marco Pivetta", + "email": "ocramius@gmail.com", + "homepage": "https://ocramius.github.io/" + } + ], + "description": "A small, lightweight utility to instantiate objects in PHP without invoking their constructors", + "homepage": "https://www.doctrine-project.org/projects/instantiator.html", + "keywords": [ + "constructor", + "instantiate" + ], + "support": { + "issues": "https://github.com/doctrine/instantiator/issues", + "source": "https://github.com/doctrine/instantiator/tree/1.4.0" + }, + "funding": [ + { + "url": "https://www.doctrine-project.org/sponsorship.html", + "type": "custom" + }, + { + "url": "https://www.patreon.com/phpdoctrine", + "type": "patreon" + }, + { + "url": "https://tidelift.com/funding/github/packagist/doctrine%2Finstantiator", + "type": "tidelift" + } + ], + "time": "2020-11-10T18:47:58+00:00" + }, + { + "name": "facade/flare-client-php", + "version": "1.8.0", + "source": { + "type": "git", + "url": "https://github.com/facade/flare-client-php.git", + "reference": "69742118c037f34ee1ef86dc605be4a105d9e984" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/facade/flare-client-php/zipball/69742118c037f34ee1ef86dc605be4a105d9e984", + "reference": "69742118c037f34ee1ef86dc605be4a105d9e984", + "shasum": "" + }, + "require": { + "facade/ignition-contracts": "~1.0", + "illuminate/pipeline": "^5.5|^6.0|^7.0|^8.0", + "php": "^7.1|^8.0", + "symfony/http-foundation": "^3.3|^4.1|^5.0", + "symfony/mime": "^3.4|^4.0|^5.1", + "symfony/var-dumper": "^3.4|^4.0|^5.0" + }, + "require-dev": { + "friendsofphp/php-cs-fixer": "^2.14", + "phpunit/phpunit": "^7.5.16", + "spatie/phpunit-snapshot-assertions": "^2.0" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.0-dev" + } + }, + "autoload": { + "psr-4": { + "Facade\\FlareClient\\": "src" + }, + "files": [ + "src/helpers.php" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "description": "Send PHP errors to Flare", + "homepage": "https://github.com/facade/flare-client-php", + "keywords": [ + "exception", + "facade", + "flare", + "reporting" + ], + "support": { + "issues": "https://github.com/facade/flare-client-php/issues", + "source": "https://github.com/facade/flare-client-php/tree/1.8.0" + }, + "funding": [ + { + "url": "https://github.com/spatie", + "type": "github" + } + ], + "time": "2021-04-30T11:11:50+00:00" + }, + { + "name": "facade/ignition", + "version": "2.9.0", + "source": { + "type": "git", + "url": "https://github.com/facade/ignition.git", + "reference": "e7db3b601ce742568b92648818ef903904d20164" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/facade/ignition/zipball/e7db3b601ce742568b92648818ef903904d20164", + "reference": "e7db3b601ce742568b92648818ef903904d20164", + "shasum": "" + }, + "require": { + "ext-json": "*", + "ext-mbstring": "*", + "facade/flare-client-php": "^1.6", + "facade/ignition-contracts": "^1.0.2", + "filp/whoops": "^2.4", + "illuminate/support": "^7.0|^8.0", + "monolog/monolog": "^2.0", + "php": "^7.2.5|^8.0", + "symfony/console": "^5.0", + "symfony/var-dumper": "^5.0" + }, + "require-dev": { + "friendsofphp/php-cs-fixer": "^2.14", + "mockery/mockery": "^1.3", + "orchestra/testbench": "^5.0|^6.0", + "psalm/plugin-laravel": "^1.2" + }, + "suggest": { + "laravel/telescope": "^3.1" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "2.x-dev" + }, + "laravel": { + "providers": [ + "Facade\\Ignition\\IgnitionServiceProvider" + ], + "aliases": { + "Flare": "Facade\\Ignition\\Facades\\Flare" + } + } + }, + "autoload": { + "psr-4": { + "Facade\\Ignition\\": "src" + }, + "files": [ + "src/helpers.php" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "description": "A beautiful error page for Laravel applications.", + "homepage": "https://github.com/facade/ignition", + "keywords": [ + "error", + "flare", + "laravel", + "page" + ], + "support": { + "docs": "https://flareapp.io/docs/ignition-for-laravel/introduction", + "forum": "https://twitter.com/flareappio", + "issues": "https://github.com/facade/ignition/issues", + "source": "https://github.com/facade/ignition" + }, + "time": "2021-05-05T06:45:12+00:00" + }, + { + "name": "facade/ignition-contracts", + "version": "1.0.2", + "source": { + "type": "git", + "url": "https://github.com/facade/ignition-contracts.git", + "reference": "3c921a1cdba35b68a7f0ccffc6dffc1995b18267" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/facade/ignition-contracts/zipball/3c921a1cdba35b68a7f0ccffc6dffc1995b18267", + "reference": "3c921a1cdba35b68a7f0ccffc6dffc1995b18267", + "shasum": "" + }, + "require": { + "php": "^7.3|^8.0" + }, + "require-dev": { + "friendsofphp/php-cs-fixer": "^v2.15.8", + "phpunit/phpunit": "^9.3.11", + "vimeo/psalm": "^3.17.1" + }, + "type": "library", + "autoload": { + "psr-4": { + "Facade\\IgnitionContracts\\": "src" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Freek Van der Herten", + "email": "freek@spatie.be", + "homepage": "https://flareapp.io", + "role": "Developer" + } + ], + "description": "Solution contracts for Ignition", + "homepage": "https://github.com/facade/ignition-contracts", + "keywords": [ + "contracts", + "flare", + "ignition" + ], + "support": { + "issues": "https://github.com/facade/ignition-contracts/issues", + "source": "https://github.com/facade/ignition-contracts/tree/1.0.2" + }, + "time": "2020-10-16T08:27:54+00:00" + }, + { + "name": "fakerphp/faker", + "version": "v1.14.1", + "source": { + "type": "git", + "url": "https://github.com/FakerPHP/Faker.git", + "reference": "ed22aee8d17c7b396f74a58b1e7fefa4f90d5ef1" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/FakerPHP/Faker/zipball/ed22aee8d17c7b396f74a58b1e7fefa4f90d5ef1", + "reference": "ed22aee8d17c7b396f74a58b1e7fefa4f90d5ef1", + "shasum": "" + }, + "require": { + "php": "^7.1 || ^8.0", + "psr/container": "^1.0", + "symfony/deprecation-contracts": "^2.2" + }, + "conflict": { + "fzaninotto/faker": "*" + }, + "require-dev": { + "bamarni/composer-bin-plugin": "^1.4.1", + "ext-intl": "*", + "symfony/phpunit-bridge": "^4.4 || ^5.2" + }, + "suggest": { + "ext-curl": "Required by Faker\\Provider\\Image to download images.", + "ext-dom": "Required by Faker\\Provider\\HtmlLorem for generating random HTML.", + "ext-iconv": "Required by Faker\\Provider\\ru_RU\\Text::realText() for generating real Russian text.", + "ext-mbstring": "Required for multibyte Unicode string functionality." + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-main": "v1.15-dev" + } + }, + "autoload": { + "psr-4": { + "Faker\\": "src/Faker/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "François Zaninotto" + } + ], + "description": "Faker is a PHP library that generates fake data for you.", + "keywords": [ + "data", + "faker", + "fixtures" + ], + "support": { + "issues": "https://github.com/FakerPHP/Faker/issues", + "source": "https://github.com/FakerPHP/Faker/tree/v.1.14.1" + }, + "time": "2021-03-30T06:27:33+00:00" + }, + { + "name": "filp/whoops", + "version": "2.12.1", + "source": { + "type": "git", + "url": "https://github.com/filp/whoops.git", + "reference": "c13c0be93cff50f88bbd70827d993026821914dd" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/filp/whoops/zipball/c13c0be93cff50f88bbd70827d993026821914dd", + "reference": "c13c0be93cff50f88bbd70827d993026821914dd", + "shasum": "" + }, + "require": { + "php": "^5.5.9 || ^7.0 || ^8.0", + "psr/log": "^1.0.1" + }, + "require-dev": { + "mockery/mockery": "^0.9 || ^1.0", + "phpunit/phpunit": "^4.8.36 || ^5.7.27 || ^6.5.14 || ^7.5.20 || ^8.5.8 || ^9.3.3", + "symfony/var-dumper": "^2.6 || ^3.0 || ^4.0 || ^5.0" + }, + "suggest": { + "symfony/var-dumper": "Pretty print complex values better with var-dumper available", + "whoops/soap": "Formats errors as SOAP responses" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "2.7-dev" + } + }, + "autoload": { + "psr-4": { + "Whoops\\": "src/Whoops/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Filipe Dobreira", + "homepage": "https://github.com/filp", + "role": "Developer" + } + ], + "description": "php error handling for cool kids", + "homepage": "https://filp.github.io/whoops/", + "keywords": [ + "error", + "exception", + "handling", + "library", + "throwable", + "whoops" + ], + "support": { + "issues": "https://github.com/filp/whoops/issues", + "source": "https://github.com/filp/whoops/tree/2.12.1" + }, + "funding": [ + { + "url": "https://github.com/denis-sokolov", + "type": "github" + } + ], + "time": "2021-04-25T12:00:00+00:00" + }, + { + "name": "hamcrest/hamcrest-php", + "version": "v2.0.1", + "source": { + "type": "git", + "url": "https://github.com/hamcrest/hamcrest-php.git", + "reference": "8c3d0a3f6af734494ad8f6fbbee0ba92422859f3" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/hamcrest/hamcrest-php/zipball/8c3d0a3f6af734494ad8f6fbbee0ba92422859f3", + "reference": "8c3d0a3f6af734494ad8f6fbbee0ba92422859f3", + "shasum": "" + }, + "require": { + "php": "^5.3|^7.0|^8.0" + }, + "replace": { + "cordoval/hamcrest-php": "*", + "davedevelopment/hamcrest-php": "*", + "kodova/hamcrest-php": "*" + }, + "require-dev": { + "phpunit/php-file-iterator": "^1.4 || ^2.0", + "phpunit/phpunit": "^4.8.36 || ^5.7 || ^6.5 || ^7.0" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "2.1-dev" + } + }, + "autoload": { + "classmap": [ + "hamcrest" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "description": "This is the PHP port of Hamcrest Matchers", + "keywords": [ + "test" + ], + "support": { + "issues": "https://github.com/hamcrest/hamcrest-php/issues", + "source": "https://github.com/hamcrest/hamcrest-php/tree/v2.0.1" + }, + "time": "2020-07-09T08:09:16+00:00" + }, + { + "name": "laravel/dusk", + "version": "v6.15.0", + "source": { + "type": "git", + "url": "https://github.com/laravel/dusk.git", + "reference": "45b55fa20321086c4f8cc4e712cbe54db644e21c" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/laravel/dusk/zipball/45b55fa20321086c4f8cc4e712cbe54db644e21c", + "reference": "45b55fa20321086c4f8cc4e712cbe54db644e21c", + "shasum": "" + }, + "require": { + "ext-json": "*", + "ext-zip": "*", + "illuminate/console": "^6.0|^7.0|^8.0", + "illuminate/support": "^6.0|^7.0|^8.0", + "nesbot/carbon": "^2.0", + "php": "^7.2|^8.0", + "php-webdriver/webdriver": "^1.9.0", + "symfony/console": "^4.3|^5.0", + "symfony/finder": "^4.3|^5.0", + "symfony/process": "^4.3|^5.0", + "vlucas/phpdotenv": "^3.0|^4.0|^5.0" + }, + "require-dev": { + "mockery/mockery": "^1.0", + "orchestra/testbench": "^4.16|^5.17.1|^6.12.1", + "phpunit/phpunit": "^7.5.15|^8.4|^9.0" + }, + "suggest": { + "ext-pcntl": "Used to gracefully terminate Dusk when tests are running." + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "6.x-dev" + }, + "laravel": { + "providers": [ + "Laravel\\Dusk\\DuskServiceProvider" + ] + } + }, + "autoload": { + "psr-4": { + "Laravel\\Dusk\\": "src/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Taylor Otwell", + "email": "taylor@laravel.com" + } + ], + "description": "Laravel Dusk provides simple end-to-end testing and browser automation.", + "keywords": [ + "laravel", + "testing", + "webdriver" + ], + "support": { + "issues": "https://github.com/laravel/dusk/issues", + "source": "https://github.com/laravel/dusk/tree/v6.15.0" + }, + "time": "2021-04-06T14:14:57+00:00" + }, + { + "name": "laravel/sail", + "version": "v1.7.0", + "source": { + "type": "git", + "url": "https://github.com/laravel/sail.git", + "reference": "d1f703d73f782af5427697cdc5023395cd341963" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/laravel/sail/zipball/d1f703d73f782af5427697cdc5023395cd341963", + "reference": "d1f703d73f782af5427697cdc5023395cd341963", + "shasum": "" + }, + "require": { + "illuminate/console": "^8.0|^9.0", + "illuminate/contracts": "^8.0|^9.0", + "illuminate/support": "^8.0|^9.0", + "php": "^7.3|^8.0" + }, + "bin": [ + "bin/sail" + ], + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.x-dev" + }, + "laravel": { + "providers": [ + "Laravel\\Sail\\SailServiceProvider" + ] + } + }, + "autoload": { + "psr-4": { + "Laravel\\Sail\\": "src/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Taylor Otwell", + "email": "taylor@laravel.com" + } + ], + "description": "Docker files for running a basic Laravel application.", + "keywords": [ + "docker", + "laravel" + ], + "support": { + "issues": "https://github.com/laravel/sail/issues", + "source": "https://github.com/laravel/sail" + }, + "time": "2021-05-25T16:41:13+00:00" + }, + { + "name": "mockery/mockery", + "version": "1.4.3", + "source": { + "type": "git", + "url": "https://github.com/mockery/mockery.git", + "reference": "d1339f64479af1bee0e82a0413813fe5345a54ea" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/mockery/mockery/zipball/d1339f64479af1bee0e82a0413813fe5345a54ea", + "reference": "d1339f64479af1bee0e82a0413813fe5345a54ea", + "shasum": "" + }, + "require": { + "hamcrest/hamcrest-php": "^2.0.1", + "lib-pcre": ">=7.0", + "php": "^7.3 || ^8.0" + }, + "conflict": { + "phpunit/phpunit": "<8.0" + }, + "require-dev": { + "phpunit/phpunit": "^8.5 || ^9.3" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.4.x-dev" + } + }, + "autoload": { + "psr-0": { + "Mockery": "library/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Pádraic Brady", + "email": "padraic.brady@gmail.com", + "homepage": "http://blog.astrumfutura.com" + }, + { + "name": "Dave Marshall", + "email": "dave.marshall@atstsolutions.co.uk", + "homepage": "http://davedevelopment.co.uk" + } + ], + "description": "Mockery is a simple yet flexible PHP mock object framework", + "homepage": "https://github.com/mockery/mockery", + "keywords": [ + "BDD", + "TDD", + "library", + "mock", + "mock objects", + "mockery", + "stub", + "test", + "test double", + "testing" + ], + "support": { + "issues": "https://github.com/mockery/mockery/issues", + "source": "https://github.com/mockery/mockery/tree/1.4.3" + }, + "time": "2021-02-24T09:51:49+00:00" + }, + { + "name": "myclabs/deep-copy", + "version": "1.10.2", + "source": { + "type": "git", + "url": "https://github.com/myclabs/DeepCopy.git", + "reference": "776f831124e9c62e1a2c601ecc52e776d8bb7220" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/myclabs/DeepCopy/zipball/776f831124e9c62e1a2c601ecc52e776d8bb7220", + "reference": "776f831124e9c62e1a2c601ecc52e776d8bb7220", + "shasum": "" + }, + "require": { + "php": "^7.1 || ^8.0" + }, + "replace": { + "myclabs/deep-copy": "self.version" + }, + "require-dev": { + "doctrine/collections": "^1.0", + "doctrine/common": "^2.6", + "phpunit/phpunit": "^7.1" + }, + "type": "library", + "autoload": { + "psr-4": { + "DeepCopy\\": "src/DeepCopy/" + }, + "files": [ + "src/DeepCopy/deep_copy.php" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "description": "Create deep copies (clones) of your objects", + "keywords": [ + "clone", + "copy", + "duplicate", + "object", + "object graph" + ], + "support": { + "issues": "https://github.com/myclabs/DeepCopy/issues", + "source": "https://github.com/myclabs/DeepCopy/tree/1.10.2" + }, + "funding": [ + { + "url": "https://tidelift.com/funding/github/packagist/myclabs/deep-copy", + "type": "tidelift" + } + ], + "time": "2020-11-13T09:40:50+00:00" + }, + { + "name": "nunomaduro/collision", + "version": "v5.4.0", + "source": { + "type": "git", + "url": "https://github.com/nunomaduro/collision.git", + "reference": "41b7e9999133d5082700d31a1d0977161df8322a" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/nunomaduro/collision/zipball/41b7e9999133d5082700d31a1d0977161df8322a", + "reference": "41b7e9999133d5082700d31a1d0977161df8322a", + "shasum": "" + }, + "require": { + "facade/ignition-contracts": "^1.0", + "filp/whoops": "^2.7.2", + "php": "^7.3 || ^8.0", + "symfony/console": "^5.0" + }, + "require-dev": { + "brianium/paratest": "^6.1", + "fideloper/proxy": "^4.4.1", + "friendsofphp/php-cs-fixer": "^2.17.3", + "fruitcake/laravel-cors": "^2.0.3", + "laravel/framework": "^9.0", + "nunomaduro/larastan": "^0.6.2", + "nunomaduro/mock-final-classes": "^1.0", + "orchestra/testbench": "^7.0", + "phpstan/phpstan": "^0.12.64", + "phpunit/phpunit": "^9.5.0" + }, + "type": "library", + "extra": { + "laravel": { + "providers": [ + "NunoMaduro\\Collision\\Adapters\\Laravel\\CollisionServiceProvider" + ] + } + }, + "autoload": { + "psr-4": { + "NunoMaduro\\Collision\\": "src/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Nuno Maduro", + "email": "enunomaduro@gmail.com" + } + ], + "description": "Cli error handling for console/command-line PHP applications.", + "keywords": [ + "artisan", + "cli", + "command-line", + "console", + "error", + "handling", + "laravel", + "laravel-zero", + "php", + "symfony" + ], + "support": { + "issues": "https://github.com/nunomaduro/collision/issues", + "source": "https://github.com/nunomaduro/collision" + }, + "funding": [ + { + "url": "https://www.paypal.com/cgi-bin/webscr?cmd=_s-xclick&hosted_button_id=66BYDWAT92N6L", + "type": "custom" + }, + { + "url": "https://github.com/nunomaduro", + "type": "github" + }, + { + "url": "https://www.patreon.com/nunomaduro", + "type": "patreon" + } + ], + "time": "2021-04-09T13:38:32+00:00" + }, + { + "name": "phar-io/manifest", + "version": "2.0.1", + "source": { + "type": "git", + "url": "https://github.com/phar-io/manifest.git", + "reference": "85265efd3af7ba3ca4b2a2c34dbfc5788dd29133" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/phar-io/manifest/zipball/85265efd3af7ba3ca4b2a2c34dbfc5788dd29133", + "reference": "85265efd3af7ba3ca4b2a2c34dbfc5788dd29133", + "shasum": "" + }, + "require": { + "ext-dom": "*", + "ext-phar": "*", + "ext-xmlwriter": "*", + "phar-io/version": "^3.0.1", + "php": "^7.2 || ^8.0" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "2.0.x-dev" + } + }, + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Arne Blankerts", + "email": "arne@blankerts.de", + "role": "Developer" + }, + { + "name": "Sebastian Heuer", + "email": "sebastian@phpeople.de", + "role": "Developer" + }, + { + "name": "Sebastian Bergmann", + "email": "sebastian@phpunit.de", + "role": "Developer" + } + ], + "description": "Component for reading phar.io manifest information from a PHP Archive (PHAR)", + "support": { + "issues": "https://github.com/phar-io/manifest/issues", + "source": "https://github.com/phar-io/manifest/tree/master" + }, + "time": "2020-06-27T14:33:11+00:00" + }, + { + "name": "phar-io/version", + "version": "3.1.0", + "source": { + "type": "git", + "url": "https://github.com/phar-io/version.git", + "reference": "bae7c545bef187884426f042434e561ab1ddb182" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/phar-io/version/zipball/bae7c545bef187884426f042434e561ab1ddb182", + "reference": "bae7c545bef187884426f042434e561ab1ddb182", + "shasum": "" + }, + "require": { + "php": "^7.2 || ^8.0" + }, + "type": "library", + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Arne Blankerts", + "email": "arne@blankerts.de", + "role": "Developer" + }, + { + "name": "Sebastian Heuer", + "email": "sebastian@phpeople.de", + "role": "Developer" + }, + { + "name": "Sebastian Bergmann", + "email": "sebastian@phpunit.de", + "role": "Developer" + } + ], + "description": "Library for handling version information and constraints", + "support": { + "issues": "https://github.com/phar-io/version/issues", + "source": "https://github.com/phar-io/version/tree/3.1.0" + }, + "time": "2021-02-23T14:00:09+00:00" + }, + { + "name": "php-webdriver/webdriver", + "version": "1.11.1", + "source": { + "type": "git", + "url": "https://github.com/php-webdriver/php-webdriver.git", + "reference": "da16e39968f8dd5cfb7d07eef91dc2b731c69880" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/php-webdriver/php-webdriver/zipball/da16e39968f8dd5cfb7d07eef91dc2b731c69880", + "reference": "da16e39968f8dd5cfb7d07eef91dc2b731c69880", + "shasum": "" + }, + "require": { + "ext-curl": "*", + "ext-json": "*", + "ext-zip": "*", + "php": "^5.6 || ~7.0 || ^8.0", + "symfony/polyfill-mbstring": "^1.12", + "symfony/process": "^2.8 || ^3.1 || ^4.0 || ^5.0" + }, + "replace": { + "facebook/webdriver": "*" + }, + "require-dev": { + "friendsofphp/php-cs-fixer": "^2.0", + "ondram/ci-detector": "^2.1 || ^3.5 || ^4.0", + "php-coveralls/php-coveralls": "^2.4", + "php-mock/php-mock-phpunit": "^1.1 || ^2.0", + "php-parallel-lint/php-parallel-lint": "^1.2", + "phpunit/phpunit": "^5.7 || ^7 || ^8 || ^9", + "squizlabs/php_codesniffer": "^3.5", + "symfony/var-dumper": "^3.3 || ^4.0 || ^5.0" + }, + "suggest": { + "ext-SimpleXML": "For Firefox profile creation" + }, + "type": "library", + "autoload": { + "psr-4": { + "Facebook\\WebDriver\\": "lib/" + }, + "files": [ + "lib/Exception/TimeoutException.php" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "description": "A PHP client for Selenium WebDriver. Previously facebook/webdriver.", + "homepage": "https://github.com/php-webdriver/php-webdriver", + "keywords": [ + "Chromedriver", + "geckodriver", + "php", + "selenium", + "webdriver" + ], + "support": { + "issues": "https://github.com/php-webdriver/php-webdriver/issues", + "source": "https://github.com/php-webdriver/php-webdriver/tree/1.11.1" + }, + "time": "2021-05-21T15:12:49+00:00" + }, + { + "name": "phpdocumentor/reflection-common", + "version": "2.2.0", + "source": { + "type": "git", + "url": "https://github.com/phpDocumentor/ReflectionCommon.git", + "reference": "1d01c49d4ed62f25aa84a747ad35d5a16924662b" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/phpDocumentor/ReflectionCommon/zipball/1d01c49d4ed62f25aa84a747ad35d5a16924662b", + "reference": "1d01c49d4ed62f25aa84a747ad35d5a16924662b", + "shasum": "" + }, + "require": { + "php": "^7.2 || ^8.0" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-2.x": "2.x-dev" + } + }, + "autoload": { + "psr-4": { + "phpDocumentor\\Reflection\\": "src/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Jaap van Otterdijk", + "email": "opensource@ijaap.nl" + } + ], + "description": "Common reflection classes used by phpdocumentor to reflect the code structure", + "homepage": "http://www.phpdoc.org", + "keywords": [ + "FQSEN", + "phpDocumentor", + "phpdoc", + "reflection", + "static analysis" + ], + "support": { + "issues": "https://github.com/phpDocumentor/ReflectionCommon/issues", + "source": "https://github.com/phpDocumentor/ReflectionCommon/tree/2.x" + }, + "time": "2020-06-27T09:03:43+00:00" + }, + { + "name": "phpdocumentor/reflection-docblock", + "version": "5.2.2", + "source": { + "type": "git", + "url": "https://github.com/phpDocumentor/ReflectionDocBlock.git", + "reference": "069a785b2141f5bcf49f3e353548dc1cce6df556" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/phpDocumentor/ReflectionDocBlock/zipball/069a785b2141f5bcf49f3e353548dc1cce6df556", + "reference": "069a785b2141f5bcf49f3e353548dc1cce6df556", + "shasum": "" + }, + "require": { + "ext-filter": "*", + "php": "^7.2 || ^8.0", + "phpdocumentor/reflection-common": "^2.2", + "phpdocumentor/type-resolver": "^1.3", + "webmozart/assert": "^1.9.1" + }, + "require-dev": { + "mockery/mockery": "~1.3.2" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "5.x-dev" + } + }, + "autoload": { + "psr-4": { + "phpDocumentor\\Reflection\\": "src" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Mike van Riel", + "email": "me@mikevanriel.com" + }, + { + "name": "Jaap van Otterdijk", + "email": "account@ijaap.nl" + } + ], + "description": "With this component, a library can provide support for annotations via DocBlocks or otherwise retrieve information that is embedded in a DocBlock.", + "support": { + "issues": "https://github.com/phpDocumentor/ReflectionDocBlock/issues", + "source": "https://github.com/phpDocumentor/ReflectionDocBlock/tree/master" + }, + "time": "2020-09-03T19:13:55+00:00" + }, + { + "name": "phpdocumentor/type-resolver", + "version": "1.4.0", + "source": { + "type": "git", + "url": "https://github.com/phpDocumentor/TypeResolver.git", + "reference": "6a467b8989322d92aa1c8bf2bebcc6e5c2ba55c0" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/phpDocumentor/TypeResolver/zipball/6a467b8989322d92aa1c8bf2bebcc6e5c2ba55c0", + "reference": "6a467b8989322d92aa1c8bf2bebcc6e5c2ba55c0", + "shasum": "" + }, + "require": { + "php": "^7.2 || ^8.0", + "phpdocumentor/reflection-common": "^2.0" + }, + "require-dev": { + "ext-tokenizer": "*" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-1.x": "1.x-dev" + } + }, + "autoload": { + "psr-4": { + "phpDocumentor\\Reflection\\": "src" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Mike van Riel", + "email": "me@mikevanriel.com" + } + ], + "description": "A PSR-5 based resolver of Class names, Types and Structural Element Names", + "support": { + "issues": "https://github.com/phpDocumentor/TypeResolver/issues", + "source": "https://github.com/phpDocumentor/TypeResolver/tree/1.4.0" + }, + "time": "2020-09-17T18:55:26+00:00" + }, + { + "name": "phpspec/prophecy", + "version": "1.13.0", + "source": { + "type": "git", + "url": "https://github.com/phpspec/prophecy.git", + "reference": "be1996ed8adc35c3fd795488a653f4b518be70ea" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/phpspec/prophecy/zipball/be1996ed8adc35c3fd795488a653f4b518be70ea", + "reference": "be1996ed8adc35c3fd795488a653f4b518be70ea", + "shasum": "" + }, + "require": { + "doctrine/instantiator": "^1.2", + "php": "^7.2 || ~8.0, <8.1", + "phpdocumentor/reflection-docblock": "^5.2", + "sebastian/comparator": "^3.0 || ^4.0", + "sebastian/recursion-context": "^3.0 || ^4.0" + }, + "require-dev": { + "phpspec/phpspec": "^6.0", + "phpunit/phpunit": "^8.0 || ^9.0" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.11.x-dev" + } + }, + "autoload": { + "psr-4": { + "Prophecy\\": "src/Prophecy" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Konstantin Kudryashov", + "email": "ever.zet@gmail.com", + "homepage": "http://everzet.com" + }, + { + "name": "Marcello Duarte", + "email": "marcello.duarte@gmail.com" + } + ], + "description": "Highly opinionated mocking framework for PHP 5.3+", + "homepage": "https://github.com/phpspec/prophecy", + "keywords": [ + "Double", + "Dummy", + "fake", + "mock", + "spy", + "stub" + ], + "support": { + "issues": "https://github.com/phpspec/prophecy/issues", + "source": "https://github.com/phpspec/prophecy/tree/1.13.0" + }, + "time": "2021-03-17T13:42:18+00:00" + }, + { + "name": "phpunit/php-code-coverage", + "version": "9.2.6", + "source": { + "type": "git", + "url": "https://github.com/sebastianbergmann/php-code-coverage.git", + "reference": "f6293e1b30a2354e8428e004689671b83871edde" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/sebastianbergmann/php-code-coverage/zipball/f6293e1b30a2354e8428e004689671b83871edde", + "reference": "f6293e1b30a2354e8428e004689671b83871edde", + "shasum": "" + }, + "require": { + "ext-dom": "*", + "ext-libxml": "*", + "ext-xmlwriter": "*", + "nikic/php-parser": "^4.10.2", + "php": ">=7.3", + "phpunit/php-file-iterator": "^3.0.3", + "phpunit/php-text-template": "^2.0.2", + "sebastian/code-unit-reverse-lookup": "^2.0.2", + "sebastian/complexity": "^2.0", + "sebastian/environment": "^5.1.2", + "sebastian/lines-of-code": "^1.0.3", + "sebastian/version": "^3.0.1", + "theseer/tokenizer": "^1.2.0" + }, + "require-dev": { + "phpunit/phpunit": "^9.3" + }, + "suggest": { + "ext-pcov": "*", + "ext-xdebug": "*" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "9.2-dev" + } + }, + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Sebastian Bergmann", + "email": "sebastian@phpunit.de", + "role": "lead" + } + ], + "description": "Library that provides collection, processing, and rendering functionality for PHP code coverage information.", + "homepage": "https://github.com/sebastianbergmann/php-code-coverage", + "keywords": [ + "coverage", + "testing", + "xunit" + ], + "support": { + "issues": "https://github.com/sebastianbergmann/php-code-coverage/issues", + "source": "https://github.com/sebastianbergmann/php-code-coverage/tree/9.2.6" + }, + "funding": [ + { + "url": "https://github.com/sebastianbergmann", + "type": "github" + } + ], + "time": "2021-03-28T07:26:59+00:00" + }, + { + "name": "phpunit/php-file-iterator", + "version": "3.0.5", + "source": { + "type": "git", + "url": "https://github.com/sebastianbergmann/php-file-iterator.git", + "reference": "aa4be8575f26070b100fccb67faabb28f21f66f8" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/sebastianbergmann/php-file-iterator/zipball/aa4be8575f26070b100fccb67faabb28f21f66f8", + "reference": "aa4be8575f26070b100fccb67faabb28f21f66f8", + "shasum": "" + }, + "require": { + "php": ">=7.3" + }, + "require-dev": { + "phpunit/phpunit": "^9.3" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "3.0-dev" + } + }, + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Sebastian Bergmann", + "email": "sebastian@phpunit.de", + "role": "lead" + } + ], + "description": "FilterIterator implementation that filters files based on a list of suffixes.", + "homepage": "https://github.com/sebastianbergmann/php-file-iterator/", + "keywords": [ + "filesystem", + "iterator" + ], + "support": { + "issues": "https://github.com/sebastianbergmann/php-file-iterator/issues", + "source": "https://github.com/sebastianbergmann/php-file-iterator/tree/3.0.5" + }, + "funding": [ + { + "url": "https://github.com/sebastianbergmann", + "type": "github" + } + ], + "time": "2020-09-28T05:57:25+00:00" + }, + { + "name": "phpunit/php-invoker", + "version": "3.1.1", + "source": { + "type": "git", + "url": "https://github.com/sebastianbergmann/php-invoker.git", + "reference": "5a10147d0aaf65b58940a0b72f71c9ac0423cc67" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/sebastianbergmann/php-invoker/zipball/5a10147d0aaf65b58940a0b72f71c9ac0423cc67", + "reference": "5a10147d0aaf65b58940a0b72f71c9ac0423cc67", + "shasum": "" + }, + "require": { + "php": ">=7.3" + }, + "require-dev": { + "ext-pcntl": "*", + "phpunit/phpunit": "^9.3" + }, + "suggest": { + "ext-pcntl": "*" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "3.1-dev" + } + }, + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Sebastian Bergmann", + "email": "sebastian@phpunit.de", + "role": "lead" + } + ], + "description": "Invoke callables with a timeout", + "homepage": "https://github.com/sebastianbergmann/php-invoker/", + "keywords": [ + "process" + ], + "support": { + "issues": "https://github.com/sebastianbergmann/php-invoker/issues", + "source": "https://github.com/sebastianbergmann/php-invoker/tree/3.1.1" + }, + "funding": [ + { + "url": "https://github.com/sebastianbergmann", + "type": "github" + } + ], + "time": "2020-09-28T05:58:55+00:00" + }, + { + "name": "phpunit/php-text-template", + "version": "2.0.4", + "source": { + "type": "git", + "url": "https://github.com/sebastianbergmann/php-text-template.git", + "reference": "5da5f67fc95621df9ff4c4e5a84d6a8a2acf7c28" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/sebastianbergmann/php-text-template/zipball/5da5f67fc95621df9ff4c4e5a84d6a8a2acf7c28", + "reference": "5da5f67fc95621df9ff4c4e5a84d6a8a2acf7c28", + "shasum": "" + }, + "require": { + "php": ">=7.3" + }, + "require-dev": { + "phpunit/phpunit": "^9.3" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "2.0-dev" + } + }, + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Sebastian Bergmann", + "email": "sebastian@phpunit.de", + "role": "lead" + } + ], + "description": "Simple template engine.", + "homepage": "https://github.com/sebastianbergmann/php-text-template/", + "keywords": [ + "template" + ], + "support": { + "issues": "https://github.com/sebastianbergmann/php-text-template/issues", + "source": "https://github.com/sebastianbergmann/php-text-template/tree/2.0.4" + }, + "funding": [ + { + "url": "https://github.com/sebastianbergmann", + "type": "github" + } + ], + "time": "2020-10-26T05:33:50+00:00" + }, + { + "name": "phpunit/php-timer", + "version": "5.0.3", + "source": { + "type": "git", + "url": "https://github.com/sebastianbergmann/php-timer.git", + "reference": "5a63ce20ed1b5bf577850e2c4e87f4aa902afbd2" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/sebastianbergmann/php-timer/zipball/5a63ce20ed1b5bf577850e2c4e87f4aa902afbd2", + "reference": "5a63ce20ed1b5bf577850e2c4e87f4aa902afbd2", + "shasum": "" + }, + "require": { + "php": ">=7.3" + }, + "require-dev": { + "phpunit/phpunit": "^9.3" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "5.0-dev" + } + }, + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Sebastian Bergmann", + "email": "sebastian@phpunit.de", + "role": "lead" + } + ], + "description": "Utility class for timing", + "homepage": "https://github.com/sebastianbergmann/php-timer/", + "keywords": [ + "timer" + ], + "support": { + "issues": "https://github.com/sebastianbergmann/php-timer/issues", + "source": "https://github.com/sebastianbergmann/php-timer/tree/5.0.3" + }, + "funding": [ + { + "url": "https://github.com/sebastianbergmann", + "type": "github" + } + ], + "time": "2020-10-26T13:16:10+00:00" + }, + { + "name": "phpunit/phpunit", + "version": "9.5.4", + "source": { + "type": "git", + "url": "https://github.com/sebastianbergmann/phpunit.git", + "reference": "c73c6737305e779771147af66c96ca6a7ed8a741" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/sebastianbergmann/phpunit/zipball/c73c6737305e779771147af66c96ca6a7ed8a741", + "reference": "c73c6737305e779771147af66c96ca6a7ed8a741", + "shasum": "" + }, + "require": { + "doctrine/instantiator": "^1.3.1", + "ext-dom": "*", + "ext-json": "*", + "ext-libxml": "*", + "ext-mbstring": "*", + "ext-xml": "*", + "ext-xmlwriter": "*", + "myclabs/deep-copy": "^1.10.1", + "phar-io/manifest": "^2.0.1", + "phar-io/version": "^3.0.2", + "php": ">=7.3", + "phpspec/prophecy": "^1.12.1", + "phpunit/php-code-coverage": "^9.2.3", + "phpunit/php-file-iterator": "^3.0.5", + "phpunit/php-invoker": "^3.1.1", + "phpunit/php-text-template": "^2.0.3", + "phpunit/php-timer": "^5.0.2", + "sebastian/cli-parser": "^1.0.1", + "sebastian/code-unit": "^1.0.6", + "sebastian/comparator": "^4.0.5", + "sebastian/diff": "^4.0.3", + "sebastian/environment": "^5.1.3", + "sebastian/exporter": "^4.0.3", + "sebastian/global-state": "^5.0.1", + "sebastian/object-enumerator": "^4.0.3", + "sebastian/resource-operations": "^3.0.3", + "sebastian/type": "^2.3", + "sebastian/version": "^3.0.2" + }, + "require-dev": { + "ext-pdo": "*", + "phpspec/prophecy-phpunit": "^2.0.1" + }, + "suggest": { + "ext-soap": "*", + "ext-xdebug": "*" + }, + "bin": [ + "phpunit" + ], + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "9.5-dev" + } + }, + "autoload": { + "classmap": [ + "src/" + ], + "files": [ + "src/Framework/Assert/Functions.php" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Sebastian Bergmann", + "email": "sebastian@phpunit.de", + "role": "lead" + } + ], + "description": "The PHP Unit Testing framework.", + "homepage": "https://phpunit.de/", + "keywords": [ + "phpunit", + "testing", + "xunit" + ], + "support": { + "issues": "https://github.com/sebastianbergmann/phpunit/issues", + "source": "https://github.com/sebastianbergmann/phpunit/tree/9.5.4" + }, + "funding": [ + { + "url": "https://phpunit.de/donate.html", + "type": "custom" + }, + { + "url": "https://github.com/sebastianbergmann", + "type": "github" + } + ], + "time": "2021-03-23T07:16:29+00:00" + }, + { + "name": "sebastian/cli-parser", + "version": "1.0.1", + "source": { + "type": "git", + "url": "https://github.com/sebastianbergmann/cli-parser.git", + "reference": "442e7c7e687e42adc03470c7b668bc4b2402c0b2" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/sebastianbergmann/cli-parser/zipball/442e7c7e687e42adc03470c7b668bc4b2402c0b2", + "reference": "442e7c7e687e42adc03470c7b668bc4b2402c0b2", + "shasum": "" + }, + "require": { + "php": ">=7.3" + }, + "require-dev": { + "phpunit/phpunit": "^9.3" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.0-dev" + } + }, + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Sebastian Bergmann", + "email": "sebastian@phpunit.de", + "role": "lead" + } + ], + "description": "Library for parsing CLI options", + "homepage": "https://github.com/sebastianbergmann/cli-parser", + "support": { + "issues": "https://github.com/sebastianbergmann/cli-parser/issues", + "source": "https://github.com/sebastianbergmann/cli-parser/tree/1.0.1" + }, + "funding": [ + { + "url": "https://github.com/sebastianbergmann", + "type": "github" + } + ], + "time": "2020-09-28T06:08:49+00:00" + }, + { + "name": "sebastian/code-unit", + "version": "1.0.8", + "source": { + "type": "git", + "url": "https://github.com/sebastianbergmann/code-unit.git", + "reference": "1fc9f64c0927627ef78ba436c9b17d967e68e120" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/sebastianbergmann/code-unit/zipball/1fc9f64c0927627ef78ba436c9b17d967e68e120", + "reference": "1fc9f64c0927627ef78ba436c9b17d967e68e120", + "shasum": "" + }, + "require": { + "php": ">=7.3" + }, + "require-dev": { + "phpunit/phpunit": "^9.3" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.0-dev" + } + }, + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Sebastian Bergmann", + "email": "sebastian@phpunit.de", + "role": "lead" + } + ], + "description": "Collection of value objects that represent the PHP code units", + "homepage": "https://github.com/sebastianbergmann/code-unit", + "support": { + "issues": "https://github.com/sebastianbergmann/code-unit/issues", + "source": "https://github.com/sebastianbergmann/code-unit/tree/1.0.8" + }, + "funding": [ + { + "url": "https://github.com/sebastianbergmann", + "type": "github" + } + ], + "time": "2020-10-26T13:08:54+00:00" + }, + { + "name": "sebastian/code-unit-reverse-lookup", + "version": "2.0.3", + "source": { + "type": "git", + "url": "https://github.com/sebastianbergmann/code-unit-reverse-lookup.git", + "reference": "ac91f01ccec49fb77bdc6fd1e548bc70f7faa3e5" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/sebastianbergmann/code-unit-reverse-lookup/zipball/ac91f01ccec49fb77bdc6fd1e548bc70f7faa3e5", + "reference": "ac91f01ccec49fb77bdc6fd1e548bc70f7faa3e5", + "shasum": "" + }, + "require": { + "php": ">=7.3" + }, + "require-dev": { + "phpunit/phpunit": "^9.3" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "2.0-dev" + } + }, + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Sebastian Bergmann", + "email": "sebastian@phpunit.de" + } + ], + "description": "Looks up which function or method a line of code belongs to", + "homepage": "https://github.com/sebastianbergmann/code-unit-reverse-lookup/", + "support": { + "issues": "https://github.com/sebastianbergmann/code-unit-reverse-lookup/issues", + "source": "https://github.com/sebastianbergmann/code-unit-reverse-lookup/tree/2.0.3" + }, + "funding": [ + { + "url": "https://github.com/sebastianbergmann", + "type": "github" + } + ], + "time": "2020-09-28T05:30:19+00:00" + }, + { + "name": "sebastian/comparator", + "version": "4.0.6", + "source": { + "type": "git", + "url": "https://github.com/sebastianbergmann/comparator.git", + "reference": "55f4261989e546dc112258c7a75935a81a7ce382" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/sebastianbergmann/comparator/zipball/55f4261989e546dc112258c7a75935a81a7ce382", + "reference": "55f4261989e546dc112258c7a75935a81a7ce382", + "shasum": "" + }, + "require": { + "php": ">=7.3", + "sebastian/diff": "^4.0", + "sebastian/exporter": "^4.0" + }, + "require-dev": { + "phpunit/phpunit": "^9.3" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "4.0-dev" + } + }, + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Sebastian Bergmann", + "email": "sebastian@phpunit.de" + }, + { + "name": "Jeff Welch", + "email": "whatthejeff@gmail.com" + }, + { + "name": "Volker Dusch", + "email": "github@wallbash.com" + }, + { + "name": "Bernhard Schussek", + "email": "bschussek@2bepublished.at" + } + ], + "description": "Provides the functionality to compare PHP values for equality", + "homepage": "https://github.com/sebastianbergmann/comparator", + "keywords": [ + "comparator", + "compare", + "equality" + ], + "support": { + "issues": "https://github.com/sebastianbergmann/comparator/issues", + "source": "https://github.com/sebastianbergmann/comparator/tree/4.0.6" + }, + "funding": [ + { + "url": "https://github.com/sebastianbergmann", + "type": "github" + } + ], + "time": "2020-10-26T15:49:45+00:00" + }, + { + "name": "sebastian/complexity", + "version": "2.0.2", + "source": { + "type": "git", + "url": "https://github.com/sebastianbergmann/complexity.git", + "reference": "739b35e53379900cc9ac327b2147867b8b6efd88" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/sebastianbergmann/complexity/zipball/739b35e53379900cc9ac327b2147867b8b6efd88", + "reference": "739b35e53379900cc9ac327b2147867b8b6efd88", + "shasum": "" + }, + "require": { + "nikic/php-parser": "^4.7", + "php": ">=7.3" + }, + "require-dev": { + "phpunit/phpunit": "^9.3" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "2.0-dev" + } + }, + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Sebastian Bergmann", + "email": "sebastian@phpunit.de", + "role": "lead" + } + ], + "description": "Library for calculating the complexity of PHP code units", + "homepage": "https://github.com/sebastianbergmann/complexity", + "support": { + "issues": "https://github.com/sebastianbergmann/complexity/issues", + "source": "https://github.com/sebastianbergmann/complexity/tree/2.0.2" + }, + "funding": [ + { + "url": "https://github.com/sebastianbergmann", + "type": "github" + } + ], + "time": "2020-10-26T15:52:27+00:00" + }, + { + "name": "sebastian/diff", + "version": "4.0.4", + "source": { + "type": "git", + "url": "https://github.com/sebastianbergmann/diff.git", + "reference": "3461e3fccc7cfdfc2720be910d3bd73c69be590d" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/sebastianbergmann/diff/zipball/3461e3fccc7cfdfc2720be910d3bd73c69be590d", + "reference": "3461e3fccc7cfdfc2720be910d3bd73c69be590d", + "shasum": "" + }, + "require": { + "php": ">=7.3" + }, + "require-dev": { + "phpunit/phpunit": "^9.3", + "symfony/process": "^4.2 || ^5" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "4.0-dev" + } + }, + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Sebastian Bergmann", + "email": "sebastian@phpunit.de" + }, + { + "name": "Kore Nordmann", + "email": "mail@kore-nordmann.de" + } + ], + "description": "Diff implementation", + "homepage": "https://github.com/sebastianbergmann/diff", + "keywords": [ + "diff", + "udiff", + "unidiff", + "unified diff" + ], + "support": { + "issues": "https://github.com/sebastianbergmann/diff/issues", + "source": "https://github.com/sebastianbergmann/diff/tree/4.0.4" + }, + "funding": [ + { + "url": "https://github.com/sebastianbergmann", + "type": "github" + } + ], + "time": "2020-10-26T13:10:38+00:00" + }, + { + "name": "sebastian/environment", + "version": "5.1.3", + "source": { + "type": "git", + "url": "https://github.com/sebastianbergmann/environment.git", + "reference": "388b6ced16caa751030f6a69e588299fa09200ac" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/sebastianbergmann/environment/zipball/388b6ced16caa751030f6a69e588299fa09200ac", + "reference": "388b6ced16caa751030f6a69e588299fa09200ac", + "shasum": "" + }, + "require": { + "php": ">=7.3" + }, + "require-dev": { + "phpunit/phpunit": "^9.3" + }, + "suggest": { + "ext-posix": "*" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "5.1-dev" + } + }, + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Sebastian Bergmann", + "email": "sebastian@phpunit.de" + } + ], + "description": "Provides functionality to handle HHVM/PHP environments", + "homepage": "http://www.github.com/sebastianbergmann/environment", + "keywords": [ + "Xdebug", + "environment", + "hhvm" + ], + "support": { + "issues": "https://github.com/sebastianbergmann/environment/issues", + "source": "https://github.com/sebastianbergmann/environment/tree/5.1.3" + }, + "funding": [ + { + "url": "https://github.com/sebastianbergmann", + "type": "github" + } + ], + "time": "2020-09-28T05:52:38+00:00" + }, + { + "name": "sebastian/exporter", + "version": "4.0.3", + "source": { + "type": "git", + "url": "https://github.com/sebastianbergmann/exporter.git", + "reference": "d89cc98761b8cb5a1a235a6b703ae50d34080e65" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/sebastianbergmann/exporter/zipball/d89cc98761b8cb5a1a235a6b703ae50d34080e65", + "reference": "d89cc98761b8cb5a1a235a6b703ae50d34080e65", + "shasum": "" + }, + "require": { + "php": ">=7.3", + "sebastian/recursion-context": "^4.0" + }, + "require-dev": { + "ext-mbstring": "*", + "phpunit/phpunit": "^9.3" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "4.0-dev" + } + }, + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Sebastian Bergmann", + "email": "sebastian@phpunit.de" + }, + { + "name": "Jeff Welch", + "email": "whatthejeff@gmail.com" + }, + { + "name": "Volker Dusch", + "email": "github@wallbash.com" + }, + { + "name": "Adam Harvey", + "email": "aharvey@php.net" + }, + { + "name": "Bernhard Schussek", + "email": "bschussek@gmail.com" + } + ], + "description": "Provides the functionality to export PHP variables for visualization", + "homepage": "http://www.github.com/sebastianbergmann/exporter", + "keywords": [ + "export", + "exporter" + ], + "support": { + "issues": "https://github.com/sebastianbergmann/exporter/issues", + "source": "https://github.com/sebastianbergmann/exporter/tree/4.0.3" + }, + "funding": [ + { + "url": "https://github.com/sebastianbergmann", + "type": "github" + } + ], + "time": "2020-09-28T05:24:23+00:00" + }, + { + "name": "sebastian/global-state", + "version": "5.0.2", + "source": { + "type": "git", + "url": "https://github.com/sebastianbergmann/global-state.git", + "reference": "a90ccbddffa067b51f574dea6eb25d5680839455" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/sebastianbergmann/global-state/zipball/a90ccbddffa067b51f574dea6eb25d5680839455", + "reference": "a90ccbddffa067b51f574dea6eb25d5680839455", + "shasum": "" + }, + "require": { + "php": ">=7.3", + "sebastian/object-reflector": "^2.0", + "sebastian/recursion-context": "^4.0" + }, + "require-dev": { + "ext-dom": "*", + "phpunit/phpunit": "^9.3" + }, + "suggest": { + "ext-uopz": "*" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "5.0-dev" + } + }, + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Sebastian Bergmann", + "email": "sebastian@phpunit.de" + } + ], + "description": "Snapshotting of global state", + "homepage": "http://www.github.com/sebastianbergmann/global-state", + "keywords": [ + "global state" + ], + "support": { + "issues": "https://github.com/sebastianbergmann/global-state/issues", + "source": "https://github.com/sebastianbergmann/global-state/tree/5.0.2" + }, + "funding": [ + { + "url": "https://github.com/sebastianbergmann", + "type": "github" + } + ], + "time": "2020-10-26T15:55:19+00:00" + }, + { + "name": "sebastian/lines-of-code", + "version": "1.0.3", + "source": { + "type": "git", + "url": "https://github.com/sebastianbergmann/lines-of-code.git", + "reference": "c1c2e997aa3146983ed888ad08b15470a2e22ecc" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/sebastianbergmann/lines-of-code/zipball/c1c2e997aa3146983ed888ad08b15470a2e22ecc", + "reference": "c1c2e997aa3146983ed888ad08b15470a2e22ecc", + "shasum": "" + }, + "require": { + "nikic/php-parser": "^4.6", + "php": ">=7.3" + }, + "require-dev": { + "phpunit/phpunit": "^9.3" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.0-dev" + } + }, + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Sebastian Bergmann", + "email": "sebastian@phpunit.de", + "role": "lead" + } + ], + "description": "Library for counting the lines of code in PHP source code", + "homepage": "https://github.com/sebastianbergmann/lines-of-code", + "support": { + "issues": "https://github.com/sebastianbergmann/lines-of-code/issues", + "source": "https://github.com/sebastianbergmann/lines-of-code/tree/1.0.3" + }, + "funding": [ + { + "url": "https://github.com/sebastianbergmann", + "type": "github" + } + ], + "time": "2020-11-28T06:42:11+00:00" + }, + { + "name": "sebastian/object-enumerator", + "version": "4.0.4", + "source": { + "type": "git", + "url": "https://github.com/sebastianbergmann/object-enumerator.git", + "reference": "5c9eeac41b290a3712d88851518825ad78f45c71" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/sebastianbergmann/object-enumerator/zipball/5c9eeac41b290a3712d88851518825ad78f45c71", + "reference": "5c9eeac41b290a3712d88851518825ad78f45c71", + "shasum": "" + }, + "require": { + "php": ">=7.3", + "sebastian/object-reflector": "^2.0", + "sebastian/recursion-context": "^4.0" + }, + "require-dev": { + "phpunit/phpunit": "^9.3" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "4.0-dev" + } + }, + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Sebastian Bergmann", + "email": "sebastian@phpunit.de" + } + ], + "description": "Traverses array structures and object graphs to enumerate all referenced objects", + "homepage": "https://github.com/sebastianbergmann/object-enumerator/", + "support": { + "issues": "https://github.com/sebastianbergmann/object-enumerator/issues", + "source": "https://github.com/sebastianbergmann/object-enumerator/tree/4.0.4" + }, + "funding": [ + { + "url": "https://github.com/sebastianbergmann", + "type": "github" + } + ], + "time": "2020-10-26T13:12:34+00:00" + }, + { + "name": "sebastian/object-reflector", + "version": "2.0.4", + "source": { + "type": "git", + "url": "https://github.com/sebastianbergmann/object-reflector.git", + "reference": "b4f479ebdbf63ac605d183ece17d8d7fe49c15c7" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/sebastianbergmann/object-reflector/zipball/b4f479ebdbf63ac605d183ece17d8d7fe49c15c7", + "reference": "b4f479ebdbf63ac605d183ece17d8d7fe49c15c7", + "shasum": "" + }, + "require": { + "php": ">=7.3" + }, + "require-dev": { + "phpunit/phpunit": "^9.3" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "2.0-dev" + } + }, + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Sebastian Bergmann", + "email": "sebastian@phpunit.de" + } + ], + "description": "Allows reflection of object attributes, including inherited and non-public ones", + "homepage": "https://github.com/sebastianbergmann/object-reflector/", + "support": { + "issues": "https://github.com/sebastianbergmann/object-reflector/issues", + "source": "https://github.com/sebastianbergmann/object-reflector/tree/2.0.4" + }, + "funding": [ + { + "url": "https://github.com/sebastianbergmann", + "type": "github" + } + ], + "time": "2020-10-26T13:14:26+00:00" + }, + { + "name": "sebastian/recursion-context", + "version": "4.0.4", + "source": { + "type": "git", + "url": "https://github.com/sebastianbergmann/recursion-context.git", + "reference": "cd9d8cf3c5804de4341c283ed787f099f5506172" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/sebastianbergmann/recursion-context/zipball/cd9d8cf3c5804de4341c283ed787f099f5506172", + "reference": "cd9d8cf3c5804de4341c283ed787f099f5506172", + "shasum": "" + }, + "require": { + "php": ">=7.3" + }, + "require-dev": { + "phpunit/phpunit": "^9.3" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "4.0-dev" + } + }, + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Sebastian Bergmann", + "email": "sebastian@phpunit.de" + }, + { + "name": "Jeff Welch", + "email": "whatthejeff@gmail.com" + }, + { + "name": "Adam Harvey", + "email": "aharvey@php.net" + } + ], + "description": "Provides functionality to recursively process PHP variables", + "homepage": "http://www.github.com/sebastianbergmann/recursion-context", + "support": { + "issues": "https://github.com/sebastianbergmann/recursion-context/issues", + "source": "https://github.com/sebastianbergmann/recursion-context/tree/4.0.4" + }, + "funding": [ + { + "url": "https://github.com/sebastianbergmann", + "type": "github" + } + ], + "time": "2020-10-26T13:17:30+00:00" + }, + { + "name": "sebastian/resource-operations", + "version": "3.0.3", + "source": { + "type": "git", + "url": "https://github.com/sebastianbergmann/resource-operations.git", + "reference": "0f4443cb3a1d92ce809899753bc0d5d5a8dd19a8" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/sebastianbergmann/resource-operations/zipball/0f4443cb3a1d92ce809899753bc0d5d5a8dd19a8", + "reference": "0f4443cb3a1d92ce809899753bc0d5d5a8dd19a8", + "shasum": "" + }, + "require": { + "php": ">=7.3" + }, + "require-dev": { + "phpunit/phpunit": "^9.0" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "3.0-dev" + } + }, + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Sebastian Bergmann", + "email": "sebastian@phpunit.de" + } + ], + "description": "Provides a list of PHP built-in functions that operate on resources", + "homepage": "https://www.github.com/sebastianbergmann/resource-operations", + "support": { + "issues": "https://github.com/sebastianbergmann/resource-operations/issues", + "source": "https://github.com/sebastianbergmann/resource-operations/tree/3.0.3" + }, + "funding": [ + { + "url": "https://github.com/sebastianbergmann", + "type": "github" + } + ], + "time": "2020-09-28T06:45:17+00:00" + }, + { + "name": "sebastian/type", + "version": "2.3.1", + "source": { + "type": "git", + "url": "https://github.com/sebastianbergmann/type.git", + "reference": "81cd61ab7bbf2de744aba0ea61fae32f721df3d2" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/sebastianbergmann/type/zipball/81cd61ab7bbf2de744aba0ea61fae32f721df3d2", + "reference": "81cd61ab7bbf2de744aba0ea61fae32f721df3d2", + "shasum": "" + }, + "require": { + "php": ">=7.3" + }, + "require-dev": { + "phpunit/phpunit": "^9.3" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "2.3-dev" + } + }, + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Sebastian Bergmann", + "email": "sebastian@phpunit.de", + "role": "lead" + } + ], + "description": "Collection of value objects that represent the types of the PHP type system", + "homepage": "https://github.com/sebastianbergmann/type", + "support": { + "issues": "https://github.com/sebastianbergmann/type/issues", + "source": "https://github.com/sebastianbergmann/type/tree/2.3.1" + }, + "funding": [ + { + "url": "https://github.com/sebastianbergmann", + "type": "github" + } + ], + "time": "2020-10-26T13:18:59+00:00" + }, + { + "name": "sebastian/version", + "version": "3.0.2", + "source": { + "type": "git", + "url": "https://github.com/sebastianbergmann/version.git", + "reference": "c6c1022351a901512170118436c764e473f6de8c" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/sebastianbergmann/version/zipball/c6c1022351a901512170118436c764e473f6de8c", + "reference": "c6c1022351a901512170118436c764e473f6de8c", + "shasum": "" + }, + "require": { + "php": ">=7.3" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "3.0-dev" + } + }, + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Sebastian Bergmann", + "email": "sebastian@phpunit.de", + "role": "lead" + } + ], + "description": "Library that helps with managing the version number of Git-hosted PHP projects", + "homepage": "https://github.com/sebastianbergmann/version", + "support": { + "issues": "https://github.com/sebastianbergmann/version/issues", + "source": "https://github.com/sebastianbergmann/version/tree/3.0.2" + }, + "funding": [ + { + "url": "https://github.com/sebastianbergmann", + "type": "github" + } + ], + "time": "2020-09-28T06:39:44+00:00" + }, + { + "name": "theseer/tokenizer", + "version": "1.2.0", + "source": { + "type": "git", + "url": "https://github.com/theseer/tokenizer.git", + "reference": "75a63c33a8577608444246075ea0af0d052e452a" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/theseer/tokenizer/zipball/75a63c33a8577608444246075ea0af0d052e452a", + "reference": "75a63c33a8577608444246075ea0af0d052e452a", + "shasum": "" + }, + "require": { + "ext-dom": "*", + "ext-tokenizer": "*", + "ext-xmlwriter": "*", + "php": "^7.2 || ^8.0" + }, + "type": "library", + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Arne Blankerts", + "email": "arne@blankerts.de", + "role": "Developer" + } + ], + "description": "A small library for converting tokenized PHP source code into XML and potentially other formats", + "support": { + "issues": "https://github.com/theseer/tokenizer/issues", + "source": "https://github.com/theseer/tokenizer/tree/master" + }, + "funding": [ + { + "url": "https://github.com/theseer", + "type": "github" + } + ], + "time": "2020-07-12T23:59:07+00:00" + } + ], + "aliases": [], + "minimum-stability": "dev", + "stability-flags": [], + "prefer-stable": true, + "prefer-lowest": false, + "platform": { + "php": "^7.3|^8.0" + }, + "platform-dev": [], + "plugin-api-version": "2.0.0" +} diff --git a/config/app.php b/config/app.php index 67d46683195056c5ead15a83f219c69c5b5f740f..7e7cd109bd96c89405b0bf6ea2c27d01e84f39bb 100644 --- a/config/app.php +++ b/config/app.php @@ -213,6 +213,7 @@ return [ 'File' => Illuminate\Support\Facades\File::class, 'Gate' => Illuminate\Support\Facades\Gate::class, 'Hash' => Illuminate\Support\Facades\Hash::class, + 'Http' => Illuminate\Support\Facades\Http::class, 'Lang' => Illuminate\Support\Facades\Lang::class, 'Log' => Illuminate\Support\Facades\Log::class, 'Mail' => Illuminate\Support\Facades\Mail::class, diff --git a/config/mail.php b/config/mail.php index 880f8753758863982c100546681a6e58c61bd801..ed5948d4a9a74dabcaf54fca8a11161e2ce366a5 100644 --- a/config/mail.php +++ b/config/mail.php @@ -4,112 +4,107 @@ return [ /* |-------------------------------------------------------------------------- - | Mail Driver + | Default Mailer |-------------------------------------------------------------------------- | - | Laravel supports both SMTP and PHP's "mail" function as drivers for the - | sending of e-mail. You may specify which one you're using throughout - | your application here. By default, Laravel is setup for SMTP mail. + | This option controls the default mailer that is used to send any email + | messages sent by your application. Alternative mailers may be setup + | and used as needed; however, this mailer will be used by default. | - | Supported: "smtp", "mail", "sendmail", "mailgun", "mandrill", - | "ses", "sparkpost", "log" - | - */ + */ - 'driver' => env('MAIL_DRIVER', 'smtp'), + 'default' => env('MAIL_MAILER', 'smtp'), /* |-------------------------------------------------------------------------- - | SMTP Host Address + | Mailer Configurations |-------------------------------------------------------------------------- | - | Here you may provide the host address of the SMTP server used by your - | applications. A default option is provided that is compatible with - | the Mailgun mail service which will provide reliable deliveries. + | Here you may configure all of the mailers used by your application plus + | their respective settings. Several examples have been configured for + | you and you are free to add your own as your application requires. | - */ - - 'host' => env('MAIL_HOST', 'smtp.mailgun.org'), - - /* - |-------------------------------------------------------------------------- - | SMTP Host Port - |-------------------------------------------------------------------------- + | Laravel supports a variety of mail "transport" drivers to be used while + | sending an e-mail. You will specify which one you are using for your + | mailers below. You are free to add additional mailers as required. | - | This is the SMTP port used by your application to deliver e-mails to - | users of the application. Like the host we have set this value to - | stay compatible with the Mailgun e-mail application by default. + | Supported: "smtp", "sendmail", "mailgun", "ses", + | "postmark", "log", "array" | - */ + */ - 'port' => env('MAIL_PORT', 587), + 'mailers' => [ + 'smtp' => [ + 'transport' => 'smtp', + 'host' => env('MAIL_HOST', 'smtp.mailgun.org'), + 'port' => env('MAIL_PORT', 587), + 'encryption' => env('MAIL_ENCRYPTION', 'tls'), + 'username' => env('MAIL_USERNAME'), + 'password' => env('MAIL_PASSWORD'), + 'timeout' => null, + 'auth_mode' => null, + ], - /* - |-------------------------------------------------------------------------- - | Global "From" Address - |-------------------------------------------------------------------------- - | - | You may wish for all e-mails sent by your application to be sent from - | the same address. Here, you may specify a name and address that is - | used globally for all e-mails that are sent by your application. - | - */ + 'ses' => [ + 'transport' => 'ses', + ], - 'from' => [ - 'address' => null, - 'name' => null, - ], + 'mailgun' => [ + 'transport' => 'mailgun', + ], - /* - |-------------------------------------------------------------------------- - | E-Mail Encryption Protocol - |-------------------------------------------------------------------------- - | - | Here you may specify the encryption protocol that should be used when - | the application send e-mail messages. A sensible default using the - | transport layer security protocol should provide great security. - | - */ + 'postmark' => [ + 'transport' => 'postmark', + ], - 'encryption' => env('MAIL_ENCRYPTION', 'tls'), + 'sendmail' => [ + 'transport' => 'sendmail', + 'path' => '/usr/sbin/sendmail -bs', + ], - /* - |-------------------------------------------------------------------------- - | SMTP Server Username - |-------------------------------------------------------------------------- - | - | If your SMTP server requires a username for authentication, you should - | set it here. This will get used to authenticate with your server on - | connection. You may also set the "password" value below this one. - | - */ + 'log' => [ + 'transport' => 'log', + 'channel' => env('MAIL_LOG_CHANNEL'), + ], - 'username' => env('MAIL_USERNAME'), + 'array' => [ + 'transport' => 'array', + ], + ], /* |-------------------------------------------------------------------------- - | SMTP Server Password + | Global "From" Address |-------------------------------------------------------------------------- | - | Here you may set the password required by your SMTP server to send out - | messages from your application. This will be given to the server on - | connection so that the application will be able to send messages. + | You may wish for all e-mails sent by your application to be sent from + | the same address. Here, you may specify a name and address that is + | used globally for all e-mails that are sent by your application. | - */ + */ - 'password' => env('MAIL_PASSWORD'), + 'from' => [ + 'address' => env('MAIL_FROM_ADDRESS', 'hello@example.com'), + 'name' => env('MAIL_FROM_NAME', 'Example'), + ], /* |-------------------------------------------------------------------------- - | Sendmail System Path + | Markdown Mail Settings |-------------------------------------------------------------------------- | - | When using the "sendmail" driver to send e-mails, we will need to know - | the path to where Sendmail lives on this server. A default path has - | been provided here, which will work well on most of your systems. + | If you are using Markdown based email rendering, you may configure your + | theme and component paths here, allowing you to customize the design + | of the emails. Or, you may simply stick with the Laravel defaults! | - */ + */ - 'sendmail' => '/usr/sbin/sendmail -bs', + 'markdown' => [ + 'theme' => 'default', + + 'paths' => [ + resource_path('views/vendor/mail'), + ], + ], -]; +]; \ No newline at end of file diff --git a/config/metager/metager.php b/config/metager/metager.php index fda3d2ee5f774fc260638f5e408a3245d26a6feb..583e6a9a7cbea3d1a451b6d77c934a05c2e650b9 100644 --- a/config/metager/metager.php +++ b/config/metager/metager.php @@ -6,4 +6,5 @@ return [ "w3m\/", ], "fail2ban_enabled" => true, + "affiliate_preference" => "adgoal", ]; diff --git a/config/nginx-default-dev.conf b/config/nginx-default-dev.conf index 9541a5b8f2e24698dc5d948394c77942567ed994..3874ffc7e36e070210c6ab05a94b72161e285716 100644 --- a/config/nginx-default-dev.conf +++ b/config/nginx-default-dev.conf @@ -6,9 +6,6 @@ server { client_max_body_size 30M; - #charset koi8-r; - #access_log /var/log/nginx/host.access.log main; - location / { try_files $uri $uri/ /index.php?$query_string; } @@ -31,27 +28,4 @@ server { location = /50x.html { root /usr/share/nginx/html; } - - # proxy the PHP scripts to Apache listening on 127.0.0.1:80 - # - #location ~ \.php$ { - # proxy_pass http://127.0.0.1; - #} - - # pass the PHP scripts to FastCGI server listening on 127.0.0.1:9000 - # - #location ~ \.php$ { - # root html; - # fastcgi_pass 127.0.0.1:9000; - # fastcgi_index index.php; - # fastcgi_param SCRIPT_FILENAME /scripts$fastcgi_script_name; - # include fastcgi_params; - #} - - # deny access to .htaccess files, if Apache's document root - # concurs with nginx's one - # - #location ~ /\.ht { - # deny all; - #} } \ No newline at end of file diff --git a/config/nginx-default.conf b/config/nginx-default.conf index 904949a9388f71b18b3af23930b856872ec72136..98ff270fe6f34222b35a5694d8766e7ddc24deed 100644 --- a/config/nginx-default.conf +++ b/config/nginx-default.conf @@ -6,9 +6,6 @@ server { client_max_body_size 30M; - #charset koi8-r; - #access_log /var/log/nginx/host.access.log main; - location / { try_files $uri $uri/ /index.php?$query_string; } @@ -22,35 +19,10 @@ server { include fastcgi_params; } - #error_page 404 /404.html; - # redirect server error pages to the static page /50x.html # error_page 500 502 503 504 /50x.html; location = /50x.html { root /usr/share/nginx/html; } - - # proxy the PHP scripts to Apache listening on 127.0.0.1:80 - # - #location ~ \.php$ { - # proxy_pass http://127.0.0.1; - #} - - # pass the PHP scripts to FastCGI server listening on 127.0.0.1:9000 - # - #location ~ \.php$ { - # root html; - # fastcgi_pass 127.0.0.1:9000; - # fastcgi_index index.php; - # fastcgi_param SCRIPT_FILENAME /scripts$fastcgi_script_name; - # include fastcgi_params; - #} - - # deny access to .htaccess files, if Apache's document root - # concurs with nginx's one - # - #location ~ /\.ht { - # deny all; - #} } \ No newline at end of file diff --git a/config/nginx.conf b/config/nginx.conf index a9dec6136bca901482e4f685b36be9a3b69a1646..bda36994ef5576c97157eaa3d96c4de560a748d0 100644 --- a/config/nginx.conf +++ b/config/nginx.conf @@ -1,9 +1,8 @@ +user www-data; +worker_processes auto; -user nginx; -worker_processes 100; - -error_log /var/log/nginx/error.log warn; -pid /var/run/nginx.pid; +error_log /dev/stdout warn; +pid /run/nginx.pid; daemon off; @@ -20,15 +19,18 @@ http { '$status $body_bytes_sent "$http_referer" ' '"$http_user_agent" "$http_x_forwarded_for"'; - access_log /var/log/nginx/access.log main; + access_log /dev/null main; sendfile on; #tcp_nopush on; - keepalive_timeout 65; client_max_body_size 30M; + keepalive_timeout 65; + keepalive_requests 50; + gzip on; include /etc/nginx/conf.d/*.conf; -} \ No newline at end of file + include /etc/nginx/sites-enabled/*; +} diff --git a/config/session.php b/config/session.php index 1db9bc0769c20dc7137d7496682363666723d724..797030ac5cef27780781f05cccfa4865c68bd3f4 100644 --- a/config/session.php +++ b/config/session.php @@ -161,7 +161,7 @@ return [ | */ - 'secure' => env('SESSION_SECURE_COOKIE', false), + 'secure' => env('SESSION_SECURE_COOKIE'), /* |-------------------------------------------------------------------------- diff --git a/database/seeds/.gitkeep b/database/seeders/.gitkeep similarity index 100% rename from database/seeds/.gitkeep rename to database/seeders/.gitkeep diff --git a/database/seeds/DatabaseSeeder.php b/database/seeders/DatabaseSeeder.php similarity index 88% rename from database/seeds/DatabaseSeeder.php rename to database/seeders/DatabaseSeeder.php index 379c31513d6f0877a70614fe9d504f5fd559642f..ebc5e0e5257f1e08795b57ee282852cb7ca97c75 100644 --- a/database/seeds/DatabaseSeeder.php +++ b/database/seeders/DatabaseSeeder.php @@ -1,5 +1,7 @@ <?php +namespace Database\Seeders; + use Illuminate\Database\Seeder; class DatabaseSeeder extends Seeder diff --git a/database/seeds/UsersSeeder.php b/database/seeders/UsersSeeder.php similarity index 90% rename from database/seeds/UsersSeeder.php rename to database/seeders/UsersSeeder.php index 284507e63abac3bb131f15e9d36df95714f4beef..ae1064478b06193c1a55a3ef2aea2d2111abcb43 100644 --- a/database/seeds/UsersSeeder.php +++ b/database/seeders/UsersSeeder.php @@ -1,6 +1,10 @@ <?php +namespace Database\Seeders; + use Illuminate\Database\Seeder; +use DB; +use Hash; class UsersSeeder extends Seeder { diff --git a/docker-compose.yml b/docker-compose.yml index 1b05b4f8884f4735a4cd1110436c4b5504b4dac3..e76638715285935aec718dbebda3326abb0c2157 100644 --- a/docker-compose.yml +++ b/docker-compose.yml @@ -1,10 +1,5 @@ version: '3.7' services: - phpdeps: - image: prooph/composer:7.3 - volumes: - - .:/app - command: install assets: image: node:10 volumes: @@ -14,11 +9,11 @@ services: dependencies: depends_on: - "mgdb" - image: php:7.3-cli-alpine + image: php:7.3-cli volumes: - .:/data working_dir: /data - command: /bin/sh -c "apk add --update dos2unix && dos2unix ./init.sh && ./init.sh && ./init.sh" + command: /bin/sh -c "/data/init.sh" mgdb: restart: on-failure image: mariadb:latest @@ -30,12 +25,11 @@ services: - MYSQL_DATABASE=metager redis: restart: on-failure - image: redis:6.0-rc1-alpine + image: redis:6 phpfpm: depends_on: - "mgdb" - "dependencies" - - "phpdeps" - "assets" - "redis" restart: on-failure @@ -56,7 +50,7 @@ services: volumes: - .:/html - ./config/nginx.conf:/etc/nginx/nginx.conf - - ./config/nginx-default-dev.conf:/etc/nginx/conf.d/default.conf + - ./config/nginx-default-dev.conf:/etc/nginx/sites-available/default ports: - "8080:80" worker: @@ -67,7 +61,7 @@ services: working_dir: /html volumes: - .:/html - command: "su -s /bin/sh -c 'php artisan requests:fetcher' nginx" + command: "su -s /bin/sh -c 'php artisan requests:fetcher' www-data" test: depends_on: - "phpfpm" diff --git a/helpers/installComposer.sh b/helpers/installComposer.sh new file mode 100644 index 0000000000000000000000000000000000000000..30b33e631e52f9981ccd340862e063111ae00d63 --- /dev/null +++ b/helpers/installComposer.sh @@ -0,0 +1,17 @@ +#!/bin/sh + +EXPECTED_CHECKSUM="$(php -r 'copy("https://composer.github.io/installer.sig", "php://stdout");')" +php -r "copy('https://getcomposer.org/installer', 'composer-setup.php');" +ACTUAL_CHECKSUM="$(php -r "echo hash_file('sha384', 'composer-setup.php');")" + +if [ "$EXPECTED_CHECKSUM" != "$ACTUAL_CHECKSUM" ] +then + >&2 echo 'ERROR: Invalid installer checksum' + rm composer-setup.php + exit 1 +fi + +php composer-setup.php --install-dir=/usr/bin --filename=composer --quiet +RESULT=$? +rm composer-setup.php +exit $RESULT \ No newline at end of file diff --git a/public/index.php b/public/index.php index 872ae19f6058aab6d046162d0c37f2328a6b2c96..102e81a558084877dc7a5e9cbadfdd4c2bf89d9e 100644 --- a/public/index.php +++ b/public/index.php @@ -1,11 +1,24 @@ <?php -/** - * Laravel - A PHP Framework For Web Artisans - * - * @package Laravel - * @author Taylor Otwell <taylor@laravel.com> - */ +use Illuminate\Contracts\Http\Kernel; +use Illuminate\Http\Request; + +define('LARAVEL_START', microtime(true)); + +/* +|-------------------------------------------------------------------------- +| Check If The Application Is Under Maintenance +|-------------------------------------------------------------------------- +| +| If the application is in maintenance / demo mode via the "down" command +| we will load this file so that any pre-rendered content can be shown +| instead of starting the framework, which could cause an exception. +| +*/ + +if (file_exists(__DIR__.'/../storage/framework/maintenance.php')) { + require __DIR__.'/../storage/framework/maintenance.php'; +} # Manchmal passiert es, dass ein Proxy sowohl den HEADER HTTP_FORWARDED, als auch den HEADER "HTTP_X_FORWARDED_FOR" setzt # Wir löschen den einen und verwenden Ihn nicht: @@ -24,46 +37,30 @@ if (!empty($_SERVER["HTTP_USER_AGENT"])) { |-------------------------------------------------------------------------- | | Composer provides a convenient, automatically generated class loader for -| our application. We just need to utilize it! We'll simply require it -| into the script here so that we don't have to worry about manual -| loading any of our classes later on. It feels nice to relax. -| - */ - -require __DIR__ . '/../bootstrap/autoload.php'; - -/* -|-------------------------------------------------------------------------- -| Turn On The Lights -|-------------------------------------------------------------------------- -| -| We need to illuminate PHP development, so let us turn on the lights. -| This bootstraps the framework and gets it ready for use, then it -| will load up this application so that we can run it and send -| the responses back to the browser and delight our users. +| this application. We just need to utilize it! We'll simply require it +| into the script here so we don't need to manually load our classes. | - */ +*/ -$app = require_once __DIR__ . '/../bootstrap/app.php'; +require __DIR__.'/../vendor/autoload.php'; /* |-------------------------------------------------------------------------- | Run The Application |-------------------------------------------------------------------------- | -| Once we have the application, we can handle the incoming request -| through the kernel, and send the associated response back to -| the client's browser allowing them to enjoy the creative -| and wonderful application we have prepared for them. +| Once we have the application, we can handle the incoming request using +| the application's HTTP kernel. Then, we will send the response back +| to this client's browser, allowing them to enjoy our application. | - */ +*/ -$kernel = $app->make(Illuminate\Contracts\Http\Kernel::class); +$app = require_once __DIR__.'/../bootstrap/app.php'; -$response = $kernel->handle( - $request = Illuminate\Http\Request::capture() -); +$kernel = $app->make(Kernel::class); -$response->send(); +$response = tap($kernel->handle( + $request = Request::capture() +))->send(); -$kernel->terminate($request, $response); +$kernel->terminate($request, $response); \ No newline at end of file diff --git a/resources/js/donation.js b/resources/js/donation.js index 9c649d0b1913578c145a6627ba5f7dd1e2e824eb..404befffbcc7975d96237bd00d581c9c9dfd4e5f 100644 --- a/resources/js/donation.js +++ b/resources/js/donation.js @@ -6,4 +6,35 @@ document.addEventListener("DOMContentLoaded", (event) => { }, 100); } }); -}); \ No newline at end of file + updateRequiredForName(); + document.querySelector("#donate-button").removeAttribute("disabled"); + document.querySelectorAll("input[name=person]").forEach(element => { + element.onclick = (e) => { + updateRequiredForName(); + } + element.onchange = (e) => { + updateRequiredForName(); + } + }); +}); + +function updateRequiredForName() { + let privateCheckbox = document.querySelector("#private"); + let companyCheckbox = document.querySelector("#company"); + let firstname = document.querySelector("#firstname"); + let lastname = document.querySelector("#lastname"); + let companyname = document.querySelector("#companyname"); + if(!privateCheckbox || !companyCheckbox || !firstname || !lastname || !companyname){ + return; + } + if(privateCheckbox.checked){ + firstname.required = "required"; + lastname.required = "required"; + companyname.removeAttribute("required"); + } + if(companyCheckbox.checked){ + companyname.required = "required"; + firstname.removeAttribute("required"); + lastname.removeAttribute("required"); + } +} \ No newline at end of file diff --git a/resources/lang/de/key.php b/resources/lang/de/key.php index f29f434b0c955872eb77b9fe56ae78593892bc20..494d46a8f98431c0b4cbeb765d31c2540662d693 100644 --- a/resources/lang/de/key.php +++ b/resources/lang/de/key.php @@ -4,7 +4,7 @@ return [ 'h1' => "Schlüssel für Ihre werbefreie Suche", 'p1' => 'MetaGer bietet <a href=":url1">SUMA-EV Mitgliedern</a> und großzügigen <a href=":url2">Spendern</a> einen Schlüssel an, mit dem sie Zugriff auf ein Kontingent an werbefreien Suchen haben.', 'p2' => 'Auf dieser Seite können Sie Ihren Schlüssel (sofern bekannt) eingeben. Wir speichern diesen mit Hilfe eines Cookies auf Ihrem PC. Auf diese Weise sendet Ihr Browser den Schlüssel automatisch bei jeder durchgeführten Suche an uns, sodass wir die Werbung für Sie entfernen können.', - 'p3' => 'Wenn Sie sich den Cookie anschauen steht dort drin "key=xxxx". Wir verwenden diesen dementsprechend nicht für Tracking-Zwecke. Er wird auch zu keinem Zeitpunkt in irgendeiner Form von uns gespeichert oder geloggt.', + 'p3' => 'Wenn Sie sich den Cookie anschauen steht dort drin "key=xxxx". Er wird zu keinem Zeitpunkt in irgendeiner Form von uns gespeichert oder geloggt. Wir verwenden diesen insbesondere auch nicht für Tracking-Zwecke', 'p4' => 'Wichtig: Um diese Funktion nutzen zu können, müssen Sie Cookies in Ihrem Browser zugelassen haben. Die Einstellung bleibt dann solange gespeichert, wie Ihr Browser Cookies speichert.', 'p5' => 'Um den Schlüssel darüber hinausgehend speichern zu können haben Sie folgende Möglichkeiten:', 'li1' => 'Richten Sie sich folgenden Link als Startseite/Lesezeichen ein:', @@ -12,5 +12,10 @@ return [ 'placeholder1' => 'Schlüssel eingeben...', 'removeKey' => 'aktuellen Schlüssel entfernen', 'invalidKey' => 'Der eingegebene Schlüssel ist ungültig', + 'empty' => 'Ihr Schlüssel ist zwar gültig, enthält aber keine werbefreien Suchen mehr.', 'backLink' => 'Zurück zur letzten Seite', + 'custom.h3' => 'Wunsch-Schlüssel', + 'custom.p1' => 'Mitglieder des SUMA-EV haben die Möglichkeit, sich einen eigenen Schlüssel auszusuchen.', + 'custom.p2' => 'Der nächste Wechsel Ihres Schlüssels ist in :nextchange möglich.', + 'custom.a1' => 'Wunsch Schlüssel einrichten' ]; diff --git a/resources/lang/de/keychange.php b/resources/lang/de/keychange.php new file mode 100644 index 0000000000000000000000000000000000000000..8c44147c6acd9cb47606368f93965a2920cc265e --- /dev/null +++ b/resources/lang/de/keychange.php @@ -0,0 +1,23 @@ +<?php + +return [ + 'h1' => 'Wunsch Schlüssel', + 'p1' => 'Mit diesem Tool haben Sie die Möglichkeit Ihren aktuellen Mitgliederschlüssel ":key" zu wechseln. Mitgliederschlüssel sind an Ihre Mitgliedschaft im SUMA-EV gekoppelt. So kann dieser automatisch erneuert werden. Auch wenn wir das nicht tun, hätten wir dadurch natürlich theoretisch die Möglichkeit eine Verknüpfung zwischen Mitgliederschlüssel und durchgeführten Suchen zu schaffen. Mit dem Wechsel auf einen Wunsch Schlüssel wird eine solche Verknüpfung theoretisch und praktisch für uns unmöglich.', + 'p2' => 'Außerdem können Sie mit diesem Tool einen Schlüssel erstellen, der leichter zu merken ist. Bitte heben Sie sich den ursprünglichen Schlüssel dennoch auf. Dadurch, dass der neue Schlüssel nicht mehr automatisch erneuert werden kann, wird dieser irgendwann ungültig. In dem Fall müssen Sie diesen Prozess wiederholen, indem Sie Ihren ursprünglichen Mitgliederschlüssel (:key) bei MetaGer eingeben und dieses Tool erneut aufrufen.', + 'p3' => 'Heben Sie sich deshalb beide Schlüssel gut auf und beachten Sie insbesondere, dass wir nicht in der Lage sind Ihnen den neuen, durch diesen Wechsel entstandenen, Schlüssel bei Verlust mitzuteilen oder wiederherzustellen.', + 'p4' => 'Dieses Tool führt Sie durch folgende Schritte um einen neuen anonymen Wunsch Schlüssel zu erstellen:', + 'ol1.li1' => 'Entfernen aller Informationen über den aktuellen Mitgliederschlüssel aus Ihrem Browser', + 'ol1.li2' => 'Erzeugen einer URL mit der ein neuer Schlüssel erstellt werden kann. Diese URL enthält keine Informationen mehr über den Mitgliederschlüssel.', + 'ol1.li3' => 'Erzeugen eines neuen Wunsch Schlüssels', + 'ol1.li4' => 'Speichern des neuen Wunsch Schlüssels im Browser', + 'a1' => 'Gelesen - Wunsch Schlüssel erstellen', + + 'p5' => 'Ihr bisheriger Mitgliederschlüssel wurde nun aus dem Browser gelöscht. Außerdem haben wir eine URL erzeugt, mit der Sie sich Ihren Wunschschlüssel erstellen können. Dies ist innerhalb von :validUntil jederzeit und von jedem Gerät aus möglich indem Sie folgende URL im Browser aufrufen, oder direkt das Formular auf dieser Seite verwenden.', + 'p6' => 'In das nachfolgende Textfeld können, Sie nun Ihren gewünschten Schlüssel eintragen. Um Ãœberschneidungen zu vermeiden fügen wir noch ein paar Zeichen an den Schlüssel an. Mit dem Klick auf generieren wird Ihr neuer Schlüssel dann erzeugt und auf der folgenden Seite angezeigt, damit Sie Ihn sich abspeichern können.', + 'input1label' => 'Wunsch Schlüssel eintragen (Mindestens 4 und maximal 20 Zeichen)', + 'input1' => 'Wunsch Schlüssel eintragen', + 'button1' => 'Wunsch Schlüssel generieren', + + 'p7' => ' Ihr neuer Wunsch Schlüssel wurde erfolgreich eingerichtet. Bitte merken Sie ihn sich gut. Er kann bei Verlust nämlich nicht wiederhergestellt werden. Er wird außerdem irgendwann ungültig werden. Wenn der Fall eintritt, tragen Sie bei MetaGer bitte Ihren regulären Mitgliederschlüssel ein und wiederholen Sie diesen Vorgang.', + 'p8' => 'Ihr neuer Schlüssel lautet:', +]; \ No newline at end of file diff --git a/resources/lang/de/partnershops.php b/resources/lang/de/partnershops.php index c3c8427de6b8ef909be3777d9f6b4bb7fc6e55cf..ae57c49ad510969ac68478439281855bd6240103 100644 --- a/resources/lang/de/partnershops.php +++ b/resources/lang/de/partnershops.php @@ -3,6 +3,6 @@ return [ 'heading' => 'MetaGer-Partnershop', 'paragraph.1' => 'Wenn in der MetaGer-Ergebnisliste Links erscheinen, bei denen das Wort "Partnershop" steht, dann sind das zunächst normale Ergebnisse einer MetaGer-Suche. Sie werden im Ranking nicht bevorzugt oder höher eingestuft, sondern wie alle anderen Suchergebnisse auch behandelt.', - 'paragraph.2' => 'Hinter diesem Link steht dann eine Firma, von der wir dann, wenn der Link angeklickt wird, einen geringen Betrag zur Finanzierung von MetaGer erhalten. Beim Ergebnis wird das zugehörige Firmenlogo angezeigt. Auch daran erkennen Sie immer unsere Partnershops. Beim Anklicken (und nur dann) eines solchen Ergebnisses werden auch Nutzerdaten an die Klickadresse weitergegeben. Zu diesen Nutzerdaten gehören auch die Suchbegriffe, die Sie auf MetaGer eingegeben haben, in Verbindung mit Ihrer IP-Adresse. Wenn Sie dies vermeiden wollen, dann können Sie bei MetaGer aber auf "anonym Ã¶ffnen" klicken. Sie müssen also auch dabei Ihre Daten nicht weitergeben. Allerdings erhalten wir dann auch keinen Beitrag zur Finanzierung von MetaGer. Wir bitten Sie dann um eine Spende, damit wir MetaGer als unabhängige Alternative in einem gemeinnützigen Verein weiter entwickeln und betreiben können: <a href="/spende">www.metager.de/spende</a>', + 'paragraph.2' => 'Wenn der Link angeklickt wird, erhalten wir einen geringen Betrag zur Finanzierung von MetaGer. Beim Ergebnis wird das zugehörige Firmenlogo angezeigt. Auch daran erkennen Sie immer unsere Partnershops. Beim Anklicken eines solchen Ergebnisses, werden Sie auf einen unserer Dienste "direct.metager.de" geleitet. Dieser kommuniziert anschließend mit unserem Werbenetzwerk, um einen Affiliate Link zu generieren. Dabei werden keine Nutzerdaten weitergegeben. Anschließend leiten wir Sie direkt zur Zielwebseite weiter. Wenn Sie dies vermeiden wollen, dann können Sie bei MetaGer auf "anonym öffnen" klicken. Allerdings erhalten wir dann auch keinen Beitrag zur Finanzierung von MetaGer. Wir bitten Sie dann um eine <a href=":link">Spende</a>, damit wir MetaGer als unabhängige Alternative in einem gemeinnützigen Verein weiter entwickeln und betreiben können.', 'paragraph.3' => 'Mitglieder des SUMA_EV können unsere werbefreie Suche nutzen. <a href="/beitritt">Werden Sie Mitglied!</a>', ]; diff --git a/resources/lang/de/settings.php b/resources/lang/de/settings.php index 3925e423a48bbcd475e9dbed2b284c7481e2d183..407d2c6a0f814bf7165463298ba097867e460d83 100644 --- a/resources/lang/de/settings.php +++ b/resources/lang/de/settings.php @@ -36,6 +36,8 @@ return [ 'off' => 'Aus', 'on' => 'An', + 'more' => 'Weitere Einstellungen', + // Translations from the settings overview 'noSettings' => 'Aktuell sind keine Einstellungen gesetzt!', 'allSettings.header' => 'Auf :root gesetzte Einstellungen', diff --git a/resources/lang/de/spende.php b/resources/lang/de/spende.php index 36f20392b863d548b5af95d124856ba552970668..193e73d537f4c1a8389f627af9fe800f9ecba224 100644 --- a/resources/lang/de/spende.php +++ b/resources/lang/de/spende.php @@ -32,6 +32,8 @@ return [ 'bankinfo.2.4' => '(Konto-Nr.: 4075 0332 01, BLZ: 43060967)', 'bankinfo.3' => 'Falls Sie eine Spendenbescheinigung wünschen, teilen Sie uns bitte Ihre vollständige Adresse mit. Bei Spenden bis 300,-€ genügt der Kontoauszug für die Absetzbarkeit beim Finanzamt.', + 'lastschrift.info' => 'Wenn Sie per Lastschrift spenden möchten, tragen Sie in das nachfolgende Formular bitte die Informationen zur Spendenhöhe und Ihre Kontoinformationen ein. Wir buchen dann bequem innerhalb der nächsten 2 Wochen vom angegebenen Konto ab.', + 'lastschrift.info2' => 'Sofern unter Regelmäßigkeit nicht anders von Ihnen angegeben, findet eine Abbuchung stets nur einmalig statt.', 'lastschrift.1' => 'Spenden mittels elektronischem Lastschriftverfahren:', 'lastschrift.2' => 'Tragen Sie hier Ihre Kontodaten ein. Wir buchen dann entsprechend von Ihrem Konto ab. Notwendige Felder sind mit einem "*" gekennzeichnet.', 'lastschrift.3f' => 'Bitte geben Sie den Vornamen des Kontoinhabers ein:', @@ -39,7 +41,7 @@ return [ 'lastschrift.3l' => 'Bitte geben Sie den Nachnamen des Kontoinhabers ein:', 'lastschrift.3l.placeholder' => 'Nachname', 'lastschrift.3c' => 'Bitte geben Sie den Firmenkontonamen ein:', - 'lastschrift.3c.placeholder' => 'Firma', + 'lastschrift.3c.placeholder' => 'Firmenname', 'lastschrift.4' => 'Ihre E-Mail Adresse:', 'lastschrift.5' => 'Ihre Telefonnummer, um Ihre Spende ggf. durch einen Rückruf zu verifizieren:', 'lastschrift.6' => 'Ihre IBAN:', @@ -47,14 +49,14 @@ return [ 'lastschrift.8.message' => 'Hier können Sie uns ggf. noch eine Mitteilung dazu senden:', 'lastschrift.8.message.placeholder' => 'Weitere Angaben', 'lastschrift.10' => 'Ihre Daten werden über eine verschlüsselte Verbindung zu uns übertragen und können von Dritten nicht mitgelesen werden. SUMA-EV verwendet Ihre Daten ausschließlich für die Spendenabrechnung; Ihre Daten werden nicht weitergegeben. Spenden an den SUMA-EV sind steuerlich absetzbar, da der Verein vom Finanzamt Hannover Nord als gemeinnützig anerkannt ist, eingetragen in das Vereinsregister beim Amtsgericht Hannover unter VR200033.', - 'lastschrift.private' => '*Privatperson:', - 'lastschrift.company' => '*Firma:', + 'lastschrift.private' => 'Privatperson:', + 'lastschrift.company' => 'Firma:', 'paypal.1' => 'Mit einem Klick auf Spenden werden Sie zu Paypal weitergeleitet.', - 'submit' => 'Spenden', + 'submit' => 'Abschicken', 'member.1' => 'Oder doch lieber Mitglied werden?', 'member.2' => 'Es kostet nicht mehr und bietet viele Vorteile:', diff --git a/resources/lang/de/titles.php b/resources/lang/de/titles.php index d216ce29334bdfcf6b6d979ed2abdb6a032cdbd7..15a4e4144082c629b771cbae8e1e7e7b778fb009 100644 --- a/resources/lang/de/titles.php +++ b/resources/lang/de/titles.php @@ -24,6 +24,7 @@ return [ 'asso' => 'Assoziator - MetaGer', 'plugin' => 'Plugin - MetaGer', 'key' => 'Mitgliederschlüssel - MetaGer', + 'keychange' => 'Mitgliederschlüssel wechseln', 'settings' => 'Sucheinstellungen (:fokus)', 'allSettings' => 'Alle Sucheinstellungen - MetaGer', 'transparency' => 'Transparenzerklärung - MetaGer', diff --git a/resources/lang/en/key.php b/resources/lang/en/key.php index a78cb1fe3b7d01ec60431d39d5972a814409158d..299c18da27b91e3b1621875185f94f36dfa26ecf 100644 --- a/resources/lang/en/key.php +++ b/resources/lang/en/key.php @@ -1,16 +1,21 @@ <?php return [ - 'h1' => "Key for your ad-free search", - 'p1' => 'MetaGer offers <a href=":url1">SUMA-EV members</a> and generous <a href=":url2">donors</a> a key that gives them access to a volume of ad-free searches.', - 'p2' => 'On this page you can enter your key (if known). We save it with the help of a cookie on your PC. This way, your browser automatically sends the key to us every time you search, so we can remove the ad for you.', - 'p3' => 'If you look at the cookie there is "key = xxxx" in there. We do not use it for tracking purposes. It is also never stored or logged by us in any way.', - 'p4' => 'Important: In order to use this function, you must have allowed cookies in your browser. The setting will remain saved as long as your browser saves cookies.', - 'p5' => 'In order to be able to save the key beyond that, you have the following options:', - 'li1' => 'Set the following URL as start page/bookmark in your browser:', - 'li2' => 'If you are using MetaGer as the default search engine, you can delete the entry after entering the key and add it again. If you have to enter a "search string" in your browser, you can use <code>:url</code>.', - 'placeholder1' => 'Enter key ...', - 'removeKey' => 'Remove current key', - 'invalidKey' => 'The entered key is invalid', - 'backLink' => 'Back to the last page', + "h1" => "Key for your ad-free search", + "p1" => "MetaGer offers <a href=\":url1\">SUMA-EV members</a> and generous <a href=\":url2\">donors</a> a key that gives them access to a volume of ad-free searches.", + "p2" => "On this page you can enter your key (if known). We save it with the help of a cookie on your PC. This way, your browser automatically sends the key to us every time you search, so we can remove the ad for you.", + "p3" => "If you look at the cookie there is \"key = xxxx\" in there. We do not use it for tracking purposes. It is also never stored or logged by us in any way.", + "p4" => "Important: In order to use this function, you must have allowed cookies in your browser. The setting will remain saved as long as your browser saves cookies.", + "p5" => "In order to be able to save the key beyond that, you have the following options:", + "li1" => "Set the following URL as start page/bookmark in your browser:", + "li2" => "If you are using MetaGer as the default search engine, you can delete the entry after entering the key and add it again. If you have to enter a \"search string\" in your browser, you can use <code>:url</code>.", + "placeholder1" => "Enter key ...", + "removeKey" => "Remove current key", + "invalidKey" => "The entered key is invalid", + "empty" => "Your key is valid but no longer contains ad-free searches.", + "backLink" => "Back to the last page", + "custom.h3" => "Favorite Key", + "custom.p1" => "Members of the SUMA-EV have the opportunity to choose their own key.", + 'custom.p2' => 'The next change of your key is possible in :nextchange.', + "custom.a1" => "Set up the favorite key" ]; diff --git a/resources/lang/en/keychange.php b/resources/lang/en/keychange.php new file mode 100644 index 0000000000000000000000000000000000000000..210c70d3f534a1e0b5384cd9c0444fed91d2f37f --- /dev/null +++ b/resources/lang/en/keychange.php @@ -0,0 +1,23 @@ +<?php + +return [ + 'h1' => 'Favorite Key', + 'p1' => 'With this tool you have the possibility to change your current membership key ":key". Membership keys are linked to your membership in SUMA-EV. So it can be renewed automatically. Even if we don\'t do that, we would of course theoretically have the possibility of creating a link between the membership key and the searches carried out. With the change to a desired key, such a link is theoretically and practically impossible for us.', + 'p2' => 'Also, you can use this tool to create a key that is easier to remember. Please keep the original key anyway. Because the new key can no longer be renewed automatically, it will eventually become invalid. In that case you will have to repeat this process by entering your original membership key (:key) into MetaGer and calling up this tool again.', + 'p3' => 'You should therefore keep both keys in a safe place and pay particular attention to the fact that we are not able to restore the new one if it is lost.', + 'p4' => 'This tool guides you through the following steps to create a new anonymous favorite key:', + 'ol1.li1' => 'Remove all information about the current member key from your browser', + 'ol1.li2' => 'Generating a URL with which a new key can be created. This URL no longer contains information about the member key.', + 'ol1.li3' => 'Generate a new favorite key', + 'ol1.li4' => 'Save the new favorite key in the browser', + 'a1' => 'Read - create a favorite key', + + 'p5' => 'Your previous membership key has now been deleted from the browser. We have also created a URL that you can use to create your desired key. This is possible within :validUntil at any time and from any device by calling up the following URL in the browser, or directly using the form on this page.', + 'p6' => 'You can now enter your desired key in the following text field. To avoid overlapping, we add a few more characters to the key. By clicking on generate, your new key will be generated and displayed on the following page so that you can save it.', + 'input1label' => 'Enter the desired key (at least 4 and a maximum of 20 characters)', + 'input1' => 'Enter the desired key', + 'button1' => 'Generate favorite key', + + 'p7' => 'Your new desired key has been successfully set up. Please make a note of it. It cannot be restored if it is lost. It will also expire at some point. If this occurs, please enter your regular membership key at MetaGer and repeat this process.', + 'p8' => 'Your new key is:', +]; \ No newline at end of file diff --git a/resources/lang/en/partnershops.php b/resources/lang/en/partnershops.php index 597456c52f123ac38a0c937110abc37972c2ce16..2f6d8371b66a438137bee590d8723003e7abacf4 100644 --- a/resources/lang/en/partnershops.php +++ b/resources/lang/en/partnershops.php @@ -3,6 +3,6 @@ return [ 'heading' => "MetaGer-Partnershop", 'paragraph.1' => "Whenever you see results with a label that says 'Partnershop', this is just a regular result. It is not ranked differently or prefered.", - 'paragraph.2' => "The result link is associated with a company that pays us a small amount for every time the link is clicked, so that MetaGer can be financed. The result also shows the company's logo. Your data is only transmitted to te websites of these companies when you click the result. The transmitted data includes your MetaGer search phrase and your IP address. In order to avoid the transmission of such data, you may use the 'OPEN ANONYMOUSLY' button, but if you do so, we do not get paid for the click. In that case we would really encourage you to donate, so that MetaGer can we maintained and developed further on.", - 'paragraph.3' => 'SUMA-EV members may use our ad-free search. <a href="/beitritt>Become a Member</a>', + 'paragraph.2' => 'If the link is clicked, we will receive a small amount to finance MetaGer. The corresponding company logo is displayed with the result. You can always recognize our partner shops by this. If you click on such a result, you will be directed to one of our services "direct.metager.de". This then communicates with our advertising network in order to generate an affiliate link. No user data will be passed on. We will then redirect you directly to the target website. If you want to avoid this, you can click on "Open anonymously" at MetaGer. However, we will then not receive any contribution to the financing of MetaGer. We then ask for a <a href=":link"> donation </a> so that we can continue to develop and operate MetaGer as an independent alternative in a non-profit organization.', + 'paragraph.3' => 'SUMA-EV members may use our ad-free search. <a href=":link">Become a Member</a>', ]; diff --git a/resources/lang/en/settings.php b/resources/lang/en/settings.php index d45aec158ba791736576d44560aca2baf292453c..6956f43ee213b86f36cf3f5c2008950cb8d909b2 100644 --- a/resources/lang/en/settings.php +++ b/resources/lang/en/settings.php @@ -36,6 +36,8 @@ return [ 'off' => 'off', 'on' => 'on', + 'more' => 'More Settings', + // Translations from the settings overview 'noSettings' => "Currently no settings are set!", 'allSettings.header' => "Settings on :root", diff --git a/resources/lang/en/spende.php b/resources/lang/en/spende.php index 77168c8bf588e88324832e36888ce8eaac3df56d..753087209afcdc972fc4bb36cc14beab6d3cced7 100644 --- a/resources/lang/en/spende.php +++ b/resources/lang/en/spende.php @@ -32,20 +32,22 @@ return [ 'bankinfo.2.4' => '(AN: 4075 0332 01, BC: 43060967)', "bankinfo.3" => "If you wish to receive a donation receipt,\r\nplease specify your full adress and (if available)\r\nyour E-Mail adress on the money transfer form.", - + "lastschrift.info" => "If you would like to donate by direct debit, please enter the information about the amount of the donation and your account information in the form below. We will then conveniently debit the specified account within the next 2 weeks.", + "lastschrift.info2" => "Unless otherwise specified by you under Regularity, a charge will only be made once.", "lastschrift.1" => "Donate by Sepa direct debit", "lastschrift.2" => "Enter your account data. We will debit your bank account accordingly. This method is only available for SEPA area. Required fields are marked with \"*\"", + "lastschrift.3c" => "Please enter the company account name:", + "lastschrift.3f" => "Please enter the first name of the account holder:", "lastschrift.3f.placeholder" => "First Name", + "lastschrift.3l" => "Please enter the last name of the account holder:", "lastschrift.3l.placeholder" => "Last Name", "lastschrift.3c.placeholder" => "Business Name", "lastschrift.4" => "Your E-Mail Adress:", "lastschrift.5" => "Your phone number to verify your donation by callback:", "lastschrift.6" => "Your IBAN:", "lastschrift.7" => "Your BIC:", - "lastschrift.8.value" => "Here you can tell us, what amount you want to donate:", "lastschrift.8.message" => "Here you can informally add a message to your donation:", "lastschrift.8.message.placeholder" => "Message", - "lastschrift.9" => "Donate", "lastschrift.10" => "Your information is transmitted encrypted and is not read by a third party. SUMA-EV only uses your information for accounting; Your information is not passed on. Donations to the SUMA-EV are tax-deductible, because the association is recognized as charitable by the Finanzamt Hannover Nord (revenue board), listed in the register of associations, Amtsgericht Hannover under VR200033. A certificate for single donations above 300,-EUR is sent automatically (post address is required!). For donations below 300,-EUR an account current is enough for tax-deduction.", "lastschrift.private" => "*As a Person:", "lastschrift.company" => "*As a Business:", @@ -74,9 +76,11 @@ return [ "bic" => "BIC", 'betrag' => 'Amount', "danke.message" => "Your message", + "danke.schluessel" => "As a small thank you, we offer our donors a key for advertising-free searches. <br> This can be entered by clicking on the key symbol next to the search bar. <br> Your key is:", 'error.iban' => 'The IBAN entered does not seem to be correct. Message was not sent.', 'error.bic' => 'The IBAN entered does not belong to a country in the SEPA area. For a direct debit we need a BIC from you.', 'error.amount' => 'The donation amount entered is invalid. Please correct your entry and try again.', + "error.name" => "It seems like they didn't give a name. Please try again.", 'error.frequency' => 'The frequency you entered for your donation is invalid.', ]; diff --git a/resources/lang/en/titles.php b/resources/lang/en/titles.php index a4b5d0ff4c5777703ab467272cd8b975a6a164fe..8de337c0b27804f23570014ced90fadbf92a7f86 100644 --- a/resources/lang/en/titles.php +++ b/resources/lang/en/titles.php @@ -1,30 +1,30 @@ <?php return [ - "index" => "MetaGer: Privacy Protected Search & Find", - "impressum" => "Site Notice - MetaGer", - "about" => "About Us - MetaGer", - "team" => "Team - MetaGer", - "kontakt" => "Contact - MetaGer", - "spende" => "Donation - MetaGer", - "datenschutz" => "Privacy - MetaGer", - "hilfe" => "Help - MetaGer", - "widget" => "MetaGer Widget", - "settings" => "Settings", - "websearch" => "Websearch-Widget - MetaGer", - "sitesearch" => "Sitesearch-Widget - MetaGer", - "faq" => "FAQ - MetaGer", - "partnershops" => "Partnershops - MetaGer", - "languages" => "translation tool - MetaGer", - "languages.edit" => "Edit language files - MetaGer", - "app" => "Apps - MetaGer", - "faktencheck" => "Fact-checks versus fake news", - 'jugendschutz' => 'Youth protection', - 'ad-info' => 'MetaGer Advertisements', - 'asso' => 'Associator - MetaGer', - 'plugin' => 'Plugin - MetaGer', - 'key' => 'Ad-Free-Key - MetaGer', - 'allSettings' => 'All Settings - MetaGer', - 'transparency' => 'Transparency statement - MetaGer', - + "index" => "MetaGer: Privacy Protected Search & Find", + "impressum" => "Site Notice - MetaGer", + "about" => "About Us - MetaGer", + "team" => "Team - MetaGer", + "kontakt" => "Contact - MetaGer", + "spende" => "Donation - MetaGer", + "datenschutz" => "Privacy - MetaGer", + "hilfe" => "Help - MetaGer", + "widget" => "MetaGer Widget", + "settings" => "Settings", + "websearch" => "Websearch-Widget - MetaGer", + "sitesearch" => "Sitesearch-Widget - MetaGer", + "faq" => "FAQ - MetaGer", + "partnershops" => "Partnershops - MetaGer", + "languages" => "translation tool - MetaGer", + "languages.edit" => "Edit language files - MetaGer", + "app" => "Apps - MetaGer", + "faktencheck" => "Fact-checks versus fake news", + "jugendschutz" => "Youth protection", + "ad-info" => "MetaGer Advertisements", + "asso" => "Associator - MetaGer", + "plugin" => "Plugin - MetaGer", + "key" => "Ad-Free-Key - MetaGer", + "keychange" => "Change membership key", + "allSettings" => "All Settings - MetaGer", + "transparency" => "Transparency statement - MetaGer" ]; diff --git a/resources/lang/en/widget.php b/resources/lang/en/widget.php index a24e1053f6b7d150b125ccc5b6cf077fa68df771..a5892df3432035483200c26f991a023399bb7249 100644 --- a/resources/lang/en/widget.php +++ b/resources/lang/en/widget.php @@ -7,5 +7,5 @@ return [ Please choose the scope of your widget:', 'body.2' => 'Search the Web', 'body.3' => 'Search one Domain', - 'body.4' => 'Please note: You must not use this widget, if your implementation suggests that MetaGer is your service or that your site is the real MetaGer homepage (all this has alreday happend). Therefore it is especially forbidden to remove our logo.', + 'body.4' => 'Please note: You must not use this widget, if your implementation suggests that MetaGer is your service or that your site is the real MetaGer homepage (all this has already happened). Therefore it is especially forbidden to remove our logo.', ]; diff --git a/resources/lang/es/spende.php b/resources/lang/es/spende.php index 5b0450f5332e2ff30b5b3d41bf901f677b1d0b7b..9e8659eb2b7f1e963d728b35e5041c8af7746bc0 100644 --- a/resources/lang/es/spende.php +++ b/resources/lang/es/spende.php @@ -24,11 +24,8 @@ return [ "bankinfo.2.2" => "BIC: GENODEM1GLS", "bankinfo.2.3" => "Banco: GLS Gemeinschaftsbank, Bochum", "bankinfo.2.4" => "(NDC: 4075 0332 01, Código: 43060967)", - "bankinfo.3" => "En caso que desea recibir un recibo de donación, indÃquenos su dirección completa. Para donaciones de hasta 200,00 €, es suficiente el extracto de cuenta donde figura la donación para solicitar la deducción de impuestos.", "lastschrift.1" => "Donaciones mediante domiciliación bancaria electrónica:", "lastschrift.2" => "Ingrese los detalles de su cuenta aquÃ. Luego, debitaremos su cuenta según sus indicaciones. Los campos que están marcados con \"*\" son obligatorios.", - "lastschrift.3" => "Por favor introduzca el nombre del titular de la cuenta:", - "lastschrift.3.placeholder" => "Nombre", "lastschrift.4" => "Su correo electrónico:", "lastschrift.5" => "Su número de teléfono, para que podamos verificar su donación con una llamada telefónica si es necesario:", "lastschrift.6" => "Su IBAN:", @@ -58,7 +55,4 @@ return [ "error.bic" => "El IBAN introducido no pertenece a ningún paÃs del área SEPA. Necesitamos su BIC para una domiciliación bancaria.", "error.amount" => "El monto de la donación ingresado no es válido. Corrija su entrada y vuelva a intentarlo.", "error.frequency" => "La frecuencia ingresada para su donación no es válida.", - "lastschrift.8.value" => "Aquà puede entrar su donación:", - "lastschrift.8.value.placeholder" => "Monto de donación", - "lastschrift.9" => "Donación" ]; diff --git a/resources/less/metager/pages/asso/style-dark.less b/resources/less/metager/pages/asso/style-dark.less new file mode 100644 index 0000000000000000000000000000000000000000..8a60b0a30d8f350052ae548c9454e1fa5d9aec4e --- /dev/null +++ b/resources/less/metager/pages/asso/style-dark.less @@ -0,0 +1,7 @@ +.reasso { + color: #fd8307; +} + +tr:nth-child(odd){ + background-color: #333030; +} \ No newline at end of file diff --git a/resources/less/metager/pages/asso/style.less b/resources/less/metager/pages/asso/style.less new file mode 100644 index 0000000000000000000000000000000000000000..a3234f46bfa44f143f5e51ad92b79b1078783adc --- /dev/null +++ b/resources/less/metager/pages/asso/style.less @@ -0,0 +1,33 @@ +table { + width: 100%; +} +table > tbody > tr { + text-align: center; + +} + +tr:nth-child(odd){ + background-color: #dbd8d8; +} +form div.input-group-addon button { + padding: 9px; +} + +.reasso { + color: #06C; + font-size: 1.3rem; + cursor: pointer; +} +.reasso:hover { + color: red; +} + +td.association { + display: flex; + align-items: center; + margin-left: 8px; + padding: 8px; +} +.asso-search-link { + margin-right: 10px; +} \ No newline at end of file diff --git a/resources/less/metager/pages/donation.less b/resources/less/metager/pages/donation.less index ef10a95f6e95c6cdca0467afc10c04d82b05b1c8..b7d819a568060c0ee977e6d25f51254720da91c3 100644 --- a/resources/less/metager/pages/donation.less +++ b/resources/less/metager/pages/donation.less @@ -71,6 +71,11 @@ font-weight: bold; } } + + #lastschrift-info { + margin-top: 16px; + } + #payment-methods { display: flex; flex-wrap: wrap; diff --git a/resources/less/metager/pages/key-dark.less b/resources/less/metager/pages/key-dark.less index 7a84e3ad7e7d3ecd9f7edacc9297b3d380bbde70..ecfdd63f4d77bdc99228f7798ac4dbbded9986f9 100644 --- a/resources/less/metager/pages/key-dark.less +++ b/resources/less/metager/pages/key-dark.less @@ -8,7 +8,7 @@ .card-medium; margin: 8px 0; .error { - color: red; + color: #fd5757; text-align: center; font-weight: bold; } diff --git a/resources/less/metager/pages/key.less b/resources/less/metager/pages/key.less index c1367a3f85fcd2c64db80a0c7090b136d85e0030..53f581e492ff486ed028d2172b8e374859dbfcc6 100644 --- a/resources/less/metager/pages/key.less +++ b/resources/less/metager/pages/key.less @@ -24,4 +24,14 @@ text-align: center; margin-top: 16px; } + + #remove-key { + margin-top: 8px; + } + + #enter-key-form { + display: flex; + justify-content: center; + gap: 4px; + } } \ No newline at end of file diff --git a/resources/less/metager/pages/keychange/index.less b/resources/less/metager/pages/keychange/index.less new file mode 100644 index 0000000000000000000000000000000000000000..1fa3e44f6be161d32508cc08faabe9a162378aa0 --- /dev/null +++ b/resources/less/metager/pages/keychange/index.less @@ -0,0 +1,16 @@ +#steps { + display: flex; + justify-content: space-between; + padding: 16px; + counter-reset: steps; + > div { + counter-increment: steps; + padding: 8px; + &::before { + content: counter(steps)". "; + } + &.active { + background-color: #2879025c; + } + } +} \ No newline at end of file diff --git a/resources/less/metager/pages/resultpage/result.less b/resources/less/metager/pages/resultpage/result.less index f1181a78d0e74ead2fc2be2afb3ad4f4d5b5aa35..c68a83545058d9102840d1c1d932b66a04ae5d10 100644 --- a/resources/less/metager/pages/resultpage/result.less +++ b/resources/less/metager/pages/resultpage/result.less @@ -51,10 +51,29 @@ } } .result-hoster { + cursor: pointer; font-size: .9em; margin-left: 20px; color: #808080; white-space: nowrap; + >ul { + list-style-type: none; + padding-left: 20px; + position: absolute; + width: fit-content; + padding: 8px; + display: none; + a { + color: @link-color; + &:hover { + color: @a-hover-color; + } + margin-left: 4px; + } + } + &:focus > ul { + display: block; + } } } .result-subheadline { diff --git a/resources/views/assoziator/asso.blade.php b/resources/views/assoziator/asso.blade.php index d55f1a879c9f14153801c870f82b89c7b3b7c77b..89d2e4e6f4b7ad54a919c2ab25eb1757f41d6883 100644 --- a/resources/views/assoziator/asso.blade.php +++ b/resources/views/assoziator/asso.blade.php @@ -1,65 +1,54 @@ @extends('layouts.subPages') -@section('title', $title ) +@section('title', $title) @section('content') - <style> - form div.input-group-addon button { - padding: 9px; - } + <h1 class="page-title">{{ trans('asso.head.1') }}</h1> + <div class="card-heavy"> + <p>{{ trans('asso.1.1') }} <a + href="{{ LaravelLocalization::getLocalizedURL(LaravelLocalization::getCurrentLocale(), '/datenschutz') }}" + target="_blank">{{ trans('asso.1.2') }}</a>{{ trans('asso.1.3') }}.</p> - .reasso { - color: rgb(0, 102, 204); - } - .reasso:hover { - color: red; - } - td.association { - display: flex; - } - .asso-search-link { - margin-right: 10px; - } - </style> - <h1 class="page-title">{{ trans('asso.head.1') }}</h1> - <div class="card-heavy"> - <p>{{ trans('asso.1.1') }} <a href="{{ LaravelLocalization::getLocalizedURL(LaravelLocalization::getCurrentLocale(), '/datenschutz') }}" target="_blank">{{ trans('asso.1.2') }}</a>{{ trans('asso.1.3') }}.</p> - - <form method="post" class="form-inline"> - <input type="text" class="form-control search-input-mini" placeholder="{{ trans('asso.search.placeholder') }}" @if(isset($keywords)) value="{{$keywords}}" @endif name="q" required autofocus/><button type="submit" class="search-btn-mini"><img id="asso-search-icon" class= "mg-icon" src="/img/icon-lupe.svg" alt="{{ trans('icon-lupe.alt') }}"></button> - </form> - </div> - @if(isset($words)) - <div class="card-heavy"> - <div class="table-responsive"> - <table class="table"> - <caption>Assoziationen für "{{ $keywords }}"</caption> - <thead> - <tr> - <th>#</th> - <th>Assoziation</th> - <th>Relevanz</th> - </tr> - </thead> - <tbody> - @php $i = 1; @endphp - @foreach($words as $key => $value) - <tr> - <td>{{ $i }}</td> - <td class="association"> - <a class="asso-search-link" href="{{ action('MetaGerSearch@search', ['eingabe' => $key]) }}" title="{{ trans('asso.searchasso.title') }}"><img class= "mg-icon" src="/img/icon-lupe.svg" alt="{{ trans('icon-lupe.alt') }}"></a> - <form method="POST"> - <button name="q" value="{{ $key }}" class="reasso" type="submit" title="{{ trans('asso.reasso.title') }}">{{ $key }}</button> - </form> - </td> - <td>{{ round(($value / $wordCount) * 100, 2) }}%</td> - @php $i++; @endphp - </tr> - @endforeach - </tbody> - </table> - </div> - </div> - @endif -@endsection + <form method="get" class="form-inline" + action="{{ LaravelLocalization::getLocalizedURL(LaravelLocalization::getCurrentLocale(), route('assoresults')) }}"> + <input type="text" class="form-control search-input-mini" placeholder="{{ trans('asso.search.placeholder') }}" + @if (isset($keywords)) value="{{ $keywords }}" @endif name="q" required autofocus /><button type="submit" class="search-btn-mini"><img id="asso-search-icon" class= "mg-icon" src="/img/icon-lupe.svg" alt="{{ trans('icon-lupe.alt') }}"></button> + </form> + </div> + @if (isset($words)) + <div class="card-heavy"> + <div class="table-responsive"> + <table class="table"> + <caption>Assoziationen für "{{ $keywords }}"</caption> + <thead> + <tr> + <th>#</th> + <th>Assoziation</th> + <th>Relevanz</th> + </tr> + </thead> + <tbody> + @php $i = 1; @endphp + @foreach ($words as $key => $value) + <tr> + <td>{{ $i }}</td> + <td class="association"> + <a class="asso-search-link" + href="{{ action('MetaGerSearch@search', ['eingabe' => $key]) }}" + title="{{ trans('asso.searchasso.title') }}"><i class="fa fa-search" + aria-hidden="true"></i></a> + <a name="q" value="{{ $key }}" class="reasso" + href="{{ route('assoresults', ['q' => $key]) }}" + title="{{ trans('asso.reasso.title') }}">{{ $key }}</a> + </td> + <td>{{ round(($value / $wordCount) * 100, 2) }}%</td> + @php $i++; @endphp + </tr> + @endforeach + </tbody> + </table> + </div> + </div> + @endif +@endsection \ No newline at end of file diff --git a/resources/views/key.blade.php b/resources/views/key.blade.php index eec467c0a73225d9dbf3054474f0059f1f8ec135..efd6d4a685be290ac0eebe57c3836018101e2331 100644 --- a/resources/views/key.blade.php +++ b/resources/views/key.blade.php @@ -19,12 +19,13 @@ <p>{{ trans('key.p2') }}</p> <p>{{ trans('key.p3') }}</p> <p>{{ trans('key.p4') }}</p> + @if(isset($keystatus) && $keystatus !== null) <p>{{ trans('key.p5') }}</p> <ol> <li> @lang ('key.li1') <div class="copyLink"> - <input id="loadSettings" class="loadSettings" type="text" value="{{$cookieLink}}"> + <input id="loadSettings" class="loadSettings" type="text" value="{{$cookieLink}}" readonly> <button class="js-only btn btn-default" onclick="var copyText = document.getElementById('loadSettings');copyText.select();copyText.setSelectionRange(0, 99999);document.execCommand('copy');">@lang('settings.copy')</button> </div> </li> @@ -32,30 +33,47 @@ <li> @lang('key.li2') <div class="copyLink"> - <input id="searchString" class="loadSettings" type="text" value="{{route("resultpage", ["key" => $cookie]) . "&eingabe=%s"}}"> + <input id="searchString" class="loadSettings" type="text" value="{{route("resultpage", ["key" => $cookie]) . "&eingabe=%s"}}" readonly> <button class="js-only btn btn-default" onclick="var copyText = document.getElementById('searchString');copyText.select();copyText.setSelectionRange(0, 99999);document.execCommand('copy');">@lang('settings.copy')</button> </div> </li> </ol> + @endif + </div> + + <div class="section"> + <h3>@lang('key.custom.h3')</h3> + <p>@lang('key.custom.p1')</p> + @if(app('App\Models\Key')->canChange()) + <a class="btn btn-default" href="{{ LaravelLocalization::getLocalizedURL(LaravelLocalization::getCurrentLocale(), route('changeKeyOne')) }}">@lang('key.custom.a1')</a> + @elseif(!empty($changedAt) && app('App\Models\Key')->keyinfo->adFreeSearches >= \App\Http\Controllers\KeyController::KEYCHANGE_ADFREE_SEARCHES) + <p>@lang('key.custom.p2', [ + 'nextchange' => trim(str_replace(" später", "", $changedAt->addSeconds(\App\Models\Key::CHANGE_EVERY)->longRelativeDiffForHumans(Carbon::now("Europe/London"), 2))) + ])</p> + @endif </div> + <div class="section"> + @if(isset($keystatus) && $keystatus === false) + <p class="error">@lang('key.empty')</p> + @endif + @if(isset($keyValid) && $keyValid === false) + <p class="error">@lang('key.invalidKey')</p> + @endif <div id="form-wrapper"> - <form method="post"> + <form id="enter-key-form" method="post"> <input type="hidden" name="redirUrl" value="{{ Request::input('redirUrl', '') }}" /> - <input type="text" name="keyToSet" value="{{$cookie === 'enter_key_here' ? '' : $cookie}}" placeholder="@lang('key.placeholder1')" autofocus> - <button type="submit" class="btn btn-success">OK</button> + <input type="text" name="keyToSet" value="{{$cookie === '' ? '' : $cookie}}" placeholder="@lang('key.placeholder1')" autofocus> + <button type="submit" class="btn btn-default">OK</button> </form> - @if($cookie !== 'enter_key_here') - <form method="post" action="{{ LaravelLocalization::getLocalizedURL(LaravelLocalization::getCurrentLocale(), action('KeyController@removeKey', ['redirUrl' => url()->full()])) }}"> + @if(isset($keystatus) && $keystatus !== null) + <form id="remove-key" method="post" action="{{ LaravelLocalization::getLocalizedURL(LaravelLocalization::getCurrentLocale(), action('KeyController@removeKey', ['redirUrl' => url()->full()])) }}"> <input type="hidden" name="redirUrl" value="{{ Request::input('redirUrl', '') }}" /> <button type="submit" class="btn btn-default">@lang('key.removeKey')</button> </form> @endif - </div> - @if(isset($keyValid) && $keyValid === false) - <p class="error">@lang('key.invalidKey')</p> - @endif - @if(Request::input('redirUrl', '') !== '') + </div> + @if(Request::input('redirUrl', '') !== '' && parse_url(Request::input('redirUrl', ''), PHP_URL_HOST) === parse_url(url()->full(), PHP_URL_HOST)) <div id="back-link"><a href="{{Request::input('redirUrl')}}">@lang('key.backLink')</a></div> @endif </div> diff --git a/resources/views/keychange.blade.php b/resources/views/keychange.blade.php new file mode 100644 index 0000000000000000000000000000000000000000..f1b5329b3417887fd68ab69c457fdc16a549f497 --- /dev/null +++ b/resources/views/keychange.blade.php @@ -0,0 +1,27 @@ +@extends('layouts.subPages', ['page' => 'key']) + +@section('title', $title ) + +@section('content') +<div class="card-heavy" id="steps"> + <div class="step-one active">Entfernen des aktuellen Schlüssels</div> + <div class="step-two">Generieren des neuen Schlüssels</div> + <div class="step-three">Speichern des neuen Schlüssels</div> +</div> +<div class="card-heavy"> +<h1>@lang('keychange.h1')</h1> +<p>@lang('keychange.p1', ["key" => $key])</p> +<p>@lang('keychange.p2', ["key" => $key])</p> +<p>@lang('keychange.p3')</p> +<p>@lang('keychange.p4')</p> +<ol> + <li>@lang('keychange.ol1.li1')</li> + <li>@lang('keychange.ol1.li2')</li> + <li>@lang('keychange.ol1.li3')</li> + <li>@lang('keychange.ol1.li4')</li> +</ol> +<form action="" method="post"> + <button class="btn btn-default">@lang('keychange.a1')</button> +</form> +</div> +@endsection diff --git a/resources/views/keychangethree.blade.php b/resources/views/keychangethree.blade.php new file mode 100644 index 0000000000000000000000000000000000000000..518852f51f13729a0f3b1a59d76d34ec7e9bf7a3 --- /dev/null +++ b/resources/views/keychangethree.blade.php @@ -0,0 +1,20 @@ +@extends('layouts.subPages', ['page' => 'key']) + +@section('title', $title ) + +@section('content') +<div class="card-heavy" id="steps"> + <div class="step-one">Entfernen des aktuellen Schlüssels</div> + <div class="step-two">Generieren des neuen Schlüssels</div> + <div class="step-three active">Speichern des neuen Schlüssels</div> +</div> +<div class="card-heavy"> + <h1>@lang('keychange.h1')</h1> + <p>@lang('keychange.p7')</p> + <p>@lang('keychange.p8')</p> + <div class="copyLink"> + <input id="searchString" class="loadSettings" type="text" value="{{ Request::input('newkey', '') }}" readonly> + <button class="js-only btn btn-default" onclick="var copyText = document.getElementById('searchString');copyText.select();copyText.setSelectionRange(0, 99999);document.execCommand('copy');">@lang('settings.copy')</button> + </div> +</div> +@endsection diff --git a/resources/views/keychangetwo.blade.php b/resources/views/keychangetwo.blade.php new file mode 100644 index 0000000000000000000000000000000000000000..0d224dd8833fb531bc41deef87a170a5ed95cca6 --- /dev/null +++ b/resources/views/keychangetwo.blade.php @@ -0,0 +1,35 @@ +@extends('layouts.subPages', ['page' => 'key']) + +@section('title', $title ) + +@section('content') +<div class="card-heavy" id="steps"> + <div class="step-one">Entfernen des aktuellen Schlüssels</div> + <div class="step-two active">Generieren des neuen Schlüssels</div> + <div class="step-three">Speichern des neuen Schlüssels</div> +</div> +<div class="card-heavy"> + <h1>@lang('keychange.h1')</h1> + <p>@lang('keychange.p5', [ + 'validUntil' => trim(str_replace(" später", "", $validUntil->longRelativeDiffForHumans(Carbon::now("Europe/London"), 1))) + ])</p> + <div class="copyLink"> + <input id="searchString" class="loadSettings" type="text" value="{{ url()->full() }}" readonly> + <button class="js-only btn btn-default" onclick="var copyText = document.getElementById('searchString');copyText.select();copyText.setSelectionRange(0, 99999);document.execCommand('copy');">@lang('settings.copy')</button> + </div> + <br> + <p>@lang('keychange.p6')</p> + + <form action="{{ LaravelLocalization::getLocalizedURL(LaravelLocalization::getCurrentLocale(), route('changeKeyTwo')) }}" method="post"> + <input type="hidden" name="validUntil" value="{{ Request::input('validUntil', '') }}"> + <input type="hidden" name="password" value="{{ Request::input('password', '') }}"> + @if(Request::filled('newkey')) + <p style="color: red">@lang('keychange.input1label')</p> + @else + <p><label for="mewkey">@lang('keychange.input1label')</label></p> + @endif + <input type="text" name="newkey" id="newkey" required placeholder="@lang('keychange.input1')" value="{{ Request::input('newkey', '') }}"> + <button type="submit" class="btn btn-default">@lang('keychange.button1')</button> + </form> +</div> +@endsection diff --git a/resources/views/layouts/result.blade.php b/resources/views/layouts/result.blade.php index c1522f1e6597720adcc4f180db948118f1b6a195..1f4a94018fc4a2480cc3802e0038c7d2d2116710 100644 --- a/resources/views/layouts/result.blade.php +++ b/resources/views/layouts/result.blade.php @@ -12,7 +12,15 @@ @if(sizeof($result->gefVon)===1) <a class="result-hoster" href="{{ $result->gefVonLink[0] }}" target="{{ $metager->getNewtab() }}" rel="noopener" tabindex="-1">{{ trans('result.gefVon') . " " . $result->gefVon[0] }} </a> @else - <span title="{{ (implode(', ', $result->gefVon)) }}" class="result-hoster"> {{ trans('result.gefVon') . " " . sizeof($result->gefVon) . " " . trans('result.providers') }} </span> + <span title="{{ (implode(', ', $result->gefVon)) }}" class="result-hoster" tabindex="0"> + {{ trans('result.gefVon') . " " . sizeof($result->gefVon) . " " . trans('result.providers') }} + <ul class="card-heavy"> + @foreach($result->gefVon as $index => $gefVon) + <li><a class="result-hoster" href="{{ $result->gefVonLink[$index] }}" target="{{ $metager->getNewtab() }}" rel="noopener" tabindex="-1">{{ trans('result.gefVon') . " " . $result->gefVon[$index] }} </a></li> + @endforeach + </ul> + </span> + @endif </div> <div class="result-subheadline"> diff --git a/resources/views/resultpages/metager3resultsrss20.blade.php b/resources/views/resultpages/metager3resultsrss20.blade.php new file mode 100644 index 0000000000000000000000000000000000000000..28e2e0149b83cf2605e3f9598fa363f025f6e08c --- /dev/null +++ b/resources/views/resultpages/metager3resultsrss20.blade.php @@ -0,0 +1,24 @@ +<?xmlversion = "1.0"encoding = "UTF-8"?> + <rss version="2.0" + xmlns:opensearch="http://a9.com/-/spec/opensearch/1.1/" + xmlns:mg="http://metager.de/opensearch/" + xmlns:atom="http://www.w3.org/2005/Atom"> + <channel> + <title>{!! htmlspecialchars($eingabe, ENT_XML1, 'UTF-8'); !!} - MetaGer</title> + <opensearch:totalResults>{{ $resultcount }}</opensearch:totalResults> + <opensearch:Query role="request" searchTerms="{{ htmlspecialchars($eingabe, ENT_QUOTES) }}"/> + <mg:nextSearchResults url="{{htmlspecialchars($metager->nextSearchLink() ,ENT_QUOTES)}}" /> + @if($apiAuthorized) + @foreach($metager->getResults() as $result) + <item> + <title>{!! htmlspecialchars($result->titel, ENT_XML1, 'UTF-8'); !!}</title> + <link>{!! htmlspecialchars($result->link, ENT_XML1, 'UTF-8'); !!}</link> + <mg:anzeigeLink>{!! htmlspecialchars($result->anzeigeLink, ENT_XML1, 'UTF-8'); !!}</mg:anzeigeLink> + <description> + {!! htmlspecialchars($result->longDescr, ENT_XML1, 'UTF-8'); !!} + </description> + </item> + @endforeach + @endif + </channel> + </rss> diff --git a/resources/views/settings/index.blade.php b/resources/views/settings/index.blade.php index 0245b5d1e93977a4c1a4778d522fcbc5a6e4b4eb..33d8c98916358897cad8c437261d2d2d1014ccbc 100644 --- a/resources/views/settings/index.blade.php +++ b/resources/views/settings/index.blade.php @@ -124,7 +124,7 @@ <div class="card-light"> - <h2>Weitere Einstellungen</h2> + <h2>@lang('settings.more')</h2> <p>@lang('settings.hint')</p> <form id="setting-form" action="{{ LaravelLocalization::getLocalizedURL(LaravelLocalization::getCurrentLocale(), route('enableSetting')) }}" method="post" class="form"> <input type="hidden" name="fokus" value="{{ $fokus }}"> diff --git a/resources/views/spende/partnershops.blade.php b/resources/views/spende/partnershops.blade.php index 4d4342df44d90fcce59ee721b7bd781af06b87b8..96e9391d3b0f9b692f324517df4e7809da2c64c4 100644 --- a/resources/views/spende/partnershops.blade.php +++ b/resources/views/spende/partnershops.blade.php @@ -5,8 +5,10 @@ @section('navbarFocus.datenschutz', 'class="active"') @section('content') - <h1>{{ trans('partnershops.heading') }}</h1> - <p>{{ trans('partnershops.paragraph.1') }}</p> - <p>{!! trans('partnershops.paragraph.2') !!}</p> - <p>{!! trans('partnershops.paragraph.3') !!}</p> + <div class="card-heavy"> + <h1>{{ trans('partnershops.heading') }}</h1> + <p>{{ trans('partnershops.paragraph.1') }}</p> + <p>{!! trans('partnershops.paragraph.2', ["link" => LaravelLocalization::getLocalizedURL(LaravelLocalization::getCurrentLocale(), route("spende"))]) !!}</p> + <p>{!! trans('partnershops.paragraph.3', ["link" => LaravelLocalization::getLocalizedURL(LaravelLocalization::getCurrentLocale(), route("beitritt"))]) !!}</p> + </div> @endsection diff --git a/resources/views/spende/spende.blade.php b/resources/views/spende/spende.blade.php index 45d95c0698c2f7bd86c1812043ad980415da9f4b..7263c1ebf68a11e956ce331b981b088fea482763 100644 --- a/resources/views/spende/spende.blade.php +++ b/resources/views/spende/spende.blade.php @@ -68,6 +68,8 @@ <a class="payment-label" href="?method=bank-transfer"><nobr>{!! trans('spende.ueberweisung') !!}</nobr></a> <a class="payment-label" href="?method=paypal"><nobr>{!! trans('spende.paypal') !!}</nobr></a> </div> + <p id="lastschrift-info">@lang('spende.lastschrift.info')</p> + <p>@lang('spende.lastschrift.info2')</p> <h3>{!! trans('spende.headline.3') !!}</h3> <div class="amount-row"> <input type="radio" value="5" class="amount-radio" name="amount" id="amount-5euro" required="required" @if(empty($data) || $data["betrag"] === "5")checked="checked"@endif> <label for="amount-5euro" class="amount-label">5€</label> @@ -96,6 +98,8 @@ <p>{!! trans('spende.lastschrift.2') !!}</p> <input type="hidden" name="dt" value="{{ md5(date('Y') . date('m') . date('d')) }}"> <div id="input-picker" class="form-group donation-form-group"> + <label>*Kontoinhaber</label> + <br> <input type="radio" required="required" id="private" name="person" value="private" @if(empty($data) || $data["person"] === "private")checked="checked"@endif><label for="private">{{trans('spende.lastschrift.private')}}</label> <div id="input-private" class="show-on-input-checked form-inline"> <input type="text" class="form-control" id="firstname" name="firstname" placeholder="{!! trans('spende.lastschrift.3f.placeholder') !!}" @if(isset($data['firstname'])) value="{{$data['firstname']}}" @endif /> diff --git a/resources/views/team/team.blade.php b/resources/views/team/team.blade.php index f02ad135c3338f4fe0a1ebc15ef4b5ba7a86ac25..a32f9a43b930b56d10ff3b3014847e314357412c 100644 --- a/resources/views/team/team.blade.php +++ b/resources/views/team/team.blade.php @@ -22,9 +22,6 @@ <li> <p>Höfer, Kim - {!! trans('team.role.6') !!} </li> - <li> - <p>Aprea, Davide - {!! trans('team.role.9') !!} - </li> <li> <p><a href="https://de.wikipedia.org/wiki/Wolfgang_Sander-Beuermann" target="_blank" rel="noopener">Sander-Beuermann, Wolfgang</a>, Dr.-Ing - {!! trans('team.role.8') !!} </li> diff --git a/routes/cookie.php b/routes/cookie.php index 3a6bc2cfca3407e15e9d1d561a8b8c2f7f44706d..afdcc09f807147b5d88598e89f32fc6d21d0f958 100644 --- a/routes/cookie.php +++ b/routes/cookie.php @@ -6,10 +6,27 @@ Route::group( 'middleware' => [ 'localeSessionRedirect', 'localizationRedirect' ]*/ ], function () { - Route::get('meta/key', "KeyController@index")->middleware('removekey'); + Route::get('meta/key', "KeyController@index")->middleware('removekey')->name('keyindex'); Route::post('meta/key', 'KeyController@setKey'); Route::any('meta/key/remove', 'KeyController@removeKey')->name("removeCookie"); + Route::group([ + 'prefix' => 'meta/key/change' + ], function() { + // Routes to change the key for members + Route::get('remove-current', 'KeyController@changeKeyIndex')->middleware('removekey')->name('changeKeyOne'); + Route::post('remove-current', 'KeyController@removeCurrent')->middleware('removekey'); + + Route::get('generate-new', 'KeyController@generateNew')->name('changeKeyTwo'); + Route::post('generate-new', 'KeyController@generateNewPost'); + + Route::get('save-new', function(){ + return view('keychangethree', ["title" => trans('titles.keychange'), "css" => [mix('css/keychange/index.css')]]); + })->name('changeKeyThree'); + }); + + + Route::group([ 'prefix' => 'meta/settings', ], diff --git a/routes/web.php b/routes/web.php index a02f40bd6a67967e6013ae98d1933fa67fb99912..1c5d12de2df921c69b40dac29e83379cb559713a 100644 --- a/routes/web.php +++ b/routes/web.php @@ -3,6 +3,7 @@ use Illuminate\Support\Facades\Redis; use Jenssegers\Agent\Agent; use Prometheus\RenderTextFormat; +use Illuminate\Http\Request; /* |-------------------------------------------------------------------------- @@ -38,9 +39,11 @@ Route::group( Route::get('asso', function () { return view('assoziator.asso') ->with('title', trans('titles.asso')) - ->with('navbarFocus', 'dienste'); + ->with('navbarFocus', 'dienste') + ->with('css', [mix('css/asso/style.css')]) + ->with('darkcss', [mix('css/asso/dark.css')]); }); - Route::post('asso', 'Assoziator@asso'); + Route::get('asso/meta.ger3', 'Assoziator@asso')->middleware('browserverification:assoresults', 'humanverification')->name("assoresults"); Route::get('impressum', function () { return view('impressum') @@ -86,7 +89,7 @@ Route::group( ->with('title', trans('titles.spende')) ->with('js', [mix('/js/donation.js')]) ->with('navbarFocus', 'foerdern'); - }); + })->name("spende"); Route::get('spende/danke/{data}', ['as' => 'danke', function ($data) { return view('spende.danke') ->with('title', trans('titles.spende')) @@ -106,7 +109,7 @@ Route::group( } else { return response()->download(storage_path('app/public/aufnahmeantrag-en.pdf'), "SUMA-EV_Membershipform_" . (new \DateTime())->format("Y_m_d") . ".pdf", ["Content-Type" => "application/pdf"]); } - }); + })->name("beitritt"); Route::get('bform1.htm', function () { return redirect('beitritt'); @@ -198,8 +201,8 @@ Route::group( Route::get('engine/stats.json', 'AdminInterface@engineStats'); Route::get('check', 'AdminInterface@check'); Route::get('engines', 'AdminInterface@engines'); - Route::get('ip', function () { - dd(Request::ip(), $_SERVER["AGENT"]); + Route::get('ip', function (Request $request) { + dd($request->ip(), $_SERVER["AGENT"]); }); Route::get('bot', 'HumanVerification@botOverview'); Route::post('bot', 'HumanVerification@botOverviewChange'); @@ -230,8 +233,8 @@ Route::group( Route::get('r/metager/{mm}/{pw}/{url}', ['as' => 'humanverification', 'uses' => 'HumanVerification@removeGet']); Route::post('img/dog.jpg', 'HumanVerification@whitelist'); Route::get('index.css', 'HumanVerification@browserVerification'); - Route::get('index.js', function () { - $key = Request::input("id", ""); + Route::get('index.js', function (Request $request) { + $key = $request->input("id", ""); // Verify that key is a md5 checksum if (!preg_match("/^[a-f0-9]{32}$/", $key)) { @@ -318,7 +321,27 @@ Route::group( }); }); - Route::get('metrics', function () { + Route::get('metrics', function (Request $request) { + // Only allow access to metrics from within our network + $ip = $request->ip(); + $allowedNetworks = [ + "10.", + "172.", + "192.", + "127.0.0.1", + ]; + + $allowed = false; + foreach($allowedNetworks as $part){ + if(stripos($ip, $part) === 0){ + $allowed = true; + } + } + + if(!$allowed){ + abort(401); + } + $registry = \Prometheus\CollectorRegistry::getDefault(); $renderer = new RenderTextFormat(); diff --git a/webpack.mix.js b/webpack.mix.js index 61811640cc8a95b85eab992cea2af0a39fadf191..33fa0435bdfc5008b4c631104b8452e86dd2aaef 100644 --- a/webpack.mix.js +++ b/webpack.mix.js @@ -45,9 +45,18 @@ mix .less("resources/less/metager/pages/count/style.less", "public/css/count/style.css", { strictMath: true }) + .less("resources/less/metager/pages/asso/style-dark.less", "public/css/asso/dark.css", { + strictMath: true + }) + .less("resources/less/metager/pages/asso/style.less", "public/css/asso/style.css", { + strictMath: true + }) .less("resources/less/metager/pages/spende/danke.less", "public/css/spende/danke.css", { strictMath: true }) + .less("resources/less/metager/pages/keychange/index.less", "public/css/keychange/index.css", { + strictMath: true + }) // js .babel( [