diff --git a/.github/actions/ci-prepare/action.yml b/.github/actions/ci-prepare/action.yml index bf3847bec2..b92618117a 100644 --- a/.github/actions/ci-prepare/action.yml +++ b/.github/actions/ci-prepare/action.yml @@ -12,16 +12,19 @@ runs: - name: Setup Services shell: bash run: | + docker network create imi-ci-service-network --subnet 172.10.12.0/24 + docker compose -f ./.github/service/redis-cluster/docker-compose.yml up -d docker compose -f ./.github/docker-compose.yml up -d ${{ inputs.env }} docker exec ${{ inputs.env }} php -v docker exec ${{ inputs.env }} php -m + docker exec ${{ inputs.env }} php --ri redis docker exec ${{ inputs.env }} php --ri swoole docker exec ${{ inputs.env }} php -r "echo 'opcache config: '; print_r(opcache_get_status(false));" docker exec ${{ inputs.env }} composer -V - name: Prepare shell: bash run: | - docker exec ${{ inputs.env }} apt install -y rsync + docker exec ${{ inputs.env }} apt install -y rsync netcat-openbsd docker exec ${{ inputs.env }} composer config --global cache-files-dir /tmp/base_cache/composer docker exec ${{ inputs.env }} composer config -g process-timeout 600 docker exec ${{ inputs.env }} composer update --no-interaction --prefer-dist --no-progress ${COMPOSER_ENV} diff --git a/.github/docker-compose.yml b/.github/docker-compose.yml index 3890391a9d..544e0531ea 100644 --- a/.github/docker-compose.yml +++ b/.github/docker-compose.yml @@ -1,12 +1,14 @@ -version: "3.4" -volumes: - shared-volume: +version: '3.5' + +name: ci services: shared-tmp: image: busybox - command: chmod -R 777 /tmp/docker + container_name: shared-tmp + command: /tmp/shared-env.sh volumes: - - shared-volume:/tmp/docker + - /run/shared:/run/shared + - ./shared-env.sh:/tmp/shared-env.sh mysql: image: mysql:${MYSQL_DOCKER_VERSION} @@ -38,17 +40,51 @@ services: volumes: - "${GITHUB_WORKSPACE}:/imi:rw" +# redis: +# image: redis:6-alpine +# container_name: redis +# depends_on: +# - shared-tmp +# command: redis-server /etc/redis.conf +# volumes: +# - ./redis.conf:/etc/redis.conf +# - /run/shared:/run/shared +# ports: +# - 6379:6379 + redis: - image: redis:6-alpine + image: bitnami/redis:7.2 container_name: redis depends_on: - shared-tmp - command: redis-server /etc/redis.conf volumes: - - ./redis.conf:/etc/redis.conf - - shared-volume:/tmp/docker + - "${GITHUB_WORKSPACE}/.github/service/redis-tls/certs:/opt/bitnami/redis/certs" + - "${GITHUB_WORKSPACE}/.github/service/redis-tls/redis-overrides.conf:/opt/bitnami/redis/redis-overrides.conf" + - /run/shared:/run/shared + environment: + REDIS_OVERRIDES_FILE: "/opt/bitnami/redis/redis-overrides.conf" + REDIS_PORT_NUMBER: 6379 + REDIS_PASSWORD: "l83aa26" + REDIS_TLS_ENABLED: "true" + REDIS_TLS_PORT_NUMBER: 6443 + REDIS_TLS_CERT_FILE: "/opt/bitnami/redis/certs/redis.crt" + REDIS_TLS_KEY_FILE: "/opt/bitnami/redis/certs/redis.key" + REDIS_TLS_DH_PARAMS_FILE: "/opt/bitnami/redis/certs/redis.dh" + REDIS_TLS_CA_FILE: "/opt/bitnami/redis/certs/ca.crt" + REDIS_TLS_AUTH_CLIENTS: "yes" + healthcheck: + test: ["CMD-SHELL", "redis-cli -h 127.0.0.1 -p $${REDIS_PORT_NUMBER:-6379} -a $${REDIS_PASSWORD} INFO | grep 'redis_version'"] + interval: 3s + timeout: 60s + retries: 30 ports: - - 6379:6379 + - "6379:6379" + - "6443:6443" + networks: + proxies: + aliases: + - redis + ipv4_address: 172.10.12.111 rabbitmq: container_name: rabbitmq @@ -100,15 +136,29 @@ services: - postgres environment: MYSQL_SERVER_HOST: mysql - REDIS_SERVER_HOST: ${REDIS_SERVER_HOST} + REDIS_SERVER_HOST: ${REDIS_SERVER_HOST:-redis} + REDIS_SERVER_PASSWORD: ${REDIS_SERVER_PASSWORD:-l83aa26} PGSQL_SERVER_HOST: postgres MYSQL_SERVER_PASSWORD: "" AMQP_SERVER_HOST: "rabbitmq" KAFKA_BOOTSTRAP_SERVERS: "kafka1:9092" GITHUB_TOKEN: ${GITHUB_TOKEN} + REDIS_SERVER_CLUSTER_PASSWORD: "l83aa26" + REDIS_SERVER_CLUSTER_SEEDS: "172.10.12.2:6379,172.10.12.3:6379,172.10.12.4:6379,172.10.12.5:6379,172.10.12.6:6379,172.10.12.7:6379" + REDIS_SERVER_TLS_CLUSTER_SEEDS: "172.10.12.2:6443,172.10.12.3:6443,172.10.12.4:6443,172.10.12.5:6443,172.10.12.6:6443,172.10.12.7:6443" + REDIS_SERVER_UNIX_SOCK: "/run/shared/redis.sock" + REDIS_SERVER_TLS_HOST: "redis" + REDIS_SERVER_TLS_PORT: "6443" + REDIS_SERVER_TLS_PASSWORD: "l83aa26" + REDIS_SERVER_TLS_CA_FILE: "/imi/.github/service/redis-tls/certs/ca.crt" + REDIS_SERVER_TLS_CERT_FILE: "/imi/.github/service/redis-tls/certs/client.crt" + REDIS_SERVER_TLS_KEY_FILE: "/imi/.github/service/redis-tls/certs/client.key" volumes: - "${GITHUB_WORKSPACE}:/imi:rw" - - shared-volume:/tmp/docker + - /run/shared:/run/shared + networks: + default: + proxies: working_dir: /imi command: tail -f /dev/null tty: true @@ -125,11 +175,22 @@ services: environment: MYSQL_SERVER_HOST: mysql REDIS_SERVER_HOST: ${REDIS_SERVER_HOST} + REDIS_SERVER_PASSWORD: ${REDIS_SERVER_PASSWORD:-l83aa26} PGSQL_SERVER_HOST: postgres MYSQL_SERVER_PASSWORD: "" AMQP_SERVER_HOST: "rabbitmq" KAFKA_BOOTSTRAP_SERVERS: "kafka1:9092" GITHUB_TOKEN: ${GITHUB_TOKEN} + REDIS_SERVER_CLUSTER_PASSWORD: "l83aa26" + REDIS_SERVER_CLUSTER_SEEDS: "172.10.12.2:6379,172.10.12.3:6379,172.10.12.4:6379,172.10.12.5:6379,172.10.12.6:6379,172.10.12.7:6379" + REDIS_SERVER_TLS_CLUSTER_SEEDS: "172.10.12.2:6443,172.10.12.3:6443,172.10.12.4:6443,172.10.12.5:6443,172.10.12.6:6443,172.10.12.7:6443" + REDIS_SERVER_UNIX_SOCK: "/run/shared/redis.sock" + REDIS_SERVER_TLS_HOST: "redis" + REDIS_SERVER_TLS_PORT: "6443" + REDIS_SERVER_TLS_PASSWORD: "l83aa26" + REDIS_SERVER_TLS_CA_FILE: "/imi/.github/service/redis-tls/certs/ca.crt" + REDIS_SERVER_TLS_CERT_FILE: "/imi/.github/service/redis-tls/certs/client.crt" + REDIS_SERVER_TLS_KEY_FILE: "/imi/.github/service/redis-tls/certs/client.key" build: context: . dockerfile: php.dockerfile @@ -141,7 +202,10 @@ services: volumes: - "${GITHUB_WORKSPACE}:/imi:rw" - "/tmp/base_cache:/tmp/base_cache:rw" - - shared-volume:/tmp/docker + - /run/shared:/run/shared + networks: + default: + proxies: working_dir: /imi command: tail -f /dev/null @@ -154,6 +218,16 @@ services: - "${GITHUB_WORKSPACE}:/imi:rw" - "/tmp/base_cache:/tmp/base_cache:rw" - "/tmp/base_cache/phpstan:/tmp/phpstan:rw" + networks: + default: + proxies: working_dir: /imi command: tail -f /dev/null - tty: true \ No newline at end of file + tty: true + +networks: + default: + driver: bridge + proxies: + name: "imi-ci-service-network" + external: true \ No newline at end of file diff --git a/.github/redis.conf b/.github/redis.conf index e693751bc8..573cc8805c 100644 --- a/.github/redis.conf +++ b/.github/redis.conf @@ -112,7 +112,7 @@ tcp-backlog 511 # incoming connections. There is no default, so Redis will not listen # on a unix socket when not specified. # -unixsocket /tmp/docker/redis.sock +unixsocket /run/shared/redis.sock unixsocketperm 777 # Close the connection after a client is idle for N seconds (0 to disable) diff --git a/.github/service/redis-cluster/docker-compose.yml b/.github/service/redis-cluster/docker-compose.yml new file mode 100644 index 0000000000..0a56be4fd7 --- /dev/null +++ b/.github/service/redis-cluster/docker-compose.yml @@ -0,0 +1,148 @@ +version: '3.5' + +name: redis-cluster +services: + node-0: + image: bitnami/redis-cluster:7.2 + volumes: + - "${GITHUB_WORKSPACE}/.github/service/redis-tls/certs:/opt/bitnami/redis/certs" + depends_on: + - node-1 + - node-2 + - node-3 + - node-4 + - node-5 + environment: + REDIS_PORT_NUMBER: 6379 + REDIS_PASSWORD: l83aa26 + REDISCLI_AUTH: l83aa26 + REDIS_CLUSTER_REPLICAS: 1 + REDIS_CLUSTER_CREATOR: yes + REDIS_NODES: node-0 node-1 node-2 node-3 node-4 node-5 + REDIS_TLS_ENABLED: "true" + REDIS_TLS_PORT_NUMBER: 6443 + REDIS_TLS_CERT_FILE: "/opt/bitnami/redis/certs/redis.crt" + REDIS_TLS_KEY_FILE: "/opt/bitnami/redis/certs/redis.key" + REDIS_TLS_CA_FILE: "/opt/bitnami/redis/certs/ca.crt" + REDIS_TLS_DH_PARAMS_FILE: "/opt/bitnami/redis/certs/redis.dh" + REDIS_TLS_AUTH_CLIENTS: "yes" + healthcheck: + test: ["CMD-SHELL", "redis-cli -h 127.0.0.1 -p $${REDIS_PORT_NUMBER:-6379} -a $${REDIS_PASSWORD} CLUSTER INFO | grep 'cluster_state:ok'"] + interval: 3s + timeout: 60s + retries: 30 + networks: + proxies: + aliases: + - redis-cluster-node-0 + ipv4_address: 172.10.12.2 + + node-1: + image: bitnami/redis-cluster:7.2 + volumes: + - "${GITHUB_WORKSPACE}/.github/service/redis-tls/certs:/opt/bitnami/redis/certs" + environment: + REDIS_PORT_NUMBER: 6379 + REDIS_PASSWORD: l83aa26 + REDIS_NODES: node-0 node-1 node-2 node-3 node-4 node-5 + REDIS_TLS_ENABLED: "true" + REDIS_TLS_PORT_NUMBER: 6443 + REDIS_TLS_CERT_FILE: "/opt/bitnami/redis/certs/redis.crt" + REDIS_TLS_KEY_FILE: "/opt/bitnami/redis/certs/redis.key" + REDIS_TLS_CA_FILE: "/opt/bitnami/redis/certs/ca.crt" + REDIS_TLS_DH_PARAMS_FILE: "/opt/bitnami/redis/certs/redis.dh" + REDIS_TLS_AUTH_CLIENTS: "yes" + networks: + proxies: + aliases: + - redis-cluster-node-1 + ipv4_address: 172.10.12.3 + + node-2: + image: bitnami/redis-cluster:7.2 + volumes: + - "${GITHUB_WORKSPACE}/.github/service/redis-tls/certs:/opt/bitnami/redis/certs" + environment: + REDIS_PORT_NUMBER: 6379 + REDIS_PASSWORD: l83aa26 + REDIS_NODES: node-0 node-1 node-2 node-3 node-4 node-5 + REDIS_TLS_ENABLED: "true" + REDIS_TLS_PORT_NUMBER: 6443 + REDIS_TLS_CERT_FILE: "/opt/bitnami/redis/certs/redis.crt" + REDIS_TLS_KEY_FILE: "/opt/bitnami/redis/certs/redis.key" + REDIS_TLS_CA_FILE: "/opt/bitnami/redis/certs/ca.crt" + REDIS_TLS_DH_PARAMS_FILE: "/opt/bitnami/redis/certs/redis.dh" + REDIS_TLS_AUTH_CLIENTS: "yes" + networks: + proxies: + aliases: + - redis-cluster-node-2 + ipv4_address: 172.10.12.4 + + node-3: + image: bitnami/redis-cluster:7.2 + volumes: + - "${GITHUB_WORKSPACE}/.github/service/redis-tls/certs:/opt/bitnami/redis/certs" + environment: + REDIS_PORT_NUMBER: 6379 + REDIS_PASSWORD: l83aa26 + REDIS_NODES: node-0 node-1 node-2 node-3 node-4 node-5 + REDIS_TLS_ENABLED: "true" + REDIS_TLS_PORT_NUMBER: 6443 + REDIS_TLS_CERT_FILE: "/opt/bitnami/redis/certs/redis.crt" + REDIS_TLS_KEY_FILE: "/opt/bitnami/redis/certs/redis.key" + REDIS_TLS_CA_FILE: "/opt/bitnami/redis/certs/ca.crt" + REDIS_TLS_DH_PARAMS_FILE: "/opt/bitnami/redis/certs/redis.dh" + REDIS_TLS_AUTH_CLIENTS: "yes" + networks: + proxies: + aliases: + - redis-cluster-node-3 + ipv4_address: 172.10.12.5 + + node-4: + image: bitnami/redis-cluster:7.2 + volumes: + - "${GITHUB_WORKSPACE}/.github/service/redis-tls/certs:/opt/bitnami/redis/certs" + environment: + REDIS_PORT_NUMBER: 6379 + REDIS_PASSWORD: l83aa26 + REDIS_NODES: node-0 node-1 node-2 node-3 node-4 node-5 + REDIS_TLS_ENABLED: "true" + REDIS_TLS_PORT_NUMBER: 6443 + REDIS_TLS_CERT_FILE: "/opt/bitnami/redis/certs/redis.crt" + REDIS_TLS_KEY_FILE: "/opt/bitnami/redis/certs/redis.key" + REDIS_TLS_CA_FILE: "/opt/bitnami/redis/certs/ca.crt" + REDIS_TLS_DH_PARAMS_FILE: "/opt/bitnami/redis/certs/redis.dh" + REDIS_TLS_AUTH_CLIENTS: "yes" + networks: + proxies: + aliases: + - redis-cluster-node-4 + ipv4_address: 172.10.12.6 + + node-5: + image: bitnami/redis-cluster:7.2 + volumes: + - "${GITHUB_WORKSPACE}/.github/service/redis-tls/certs:/opt/bitnami/redis/certs" + environment: + REDIS_PORT_NUMBER: 6379 + REDIS_PASSWORD: l83aa26 + REDIS_NODES: node-0 node-1 node-2 node-3 node-4 node-5 + REDIS_TLS_ENABLED: "true" + REDIS_TLS_PORT_NUMBER: 6443 + REDIS_TLS_CERT_FILE: "/opt/bitnami/redis/certs/redis.crt" + REDIS_TLS_KEY_FILE: "/opt/bitnami/redis/certs/redis.key" + REDIS_TLS_CA_FILE: "/opt/bitnami/redis/certs/ca.crt" + REDIS_TLS_DH_PARAMS_FILE: "/opt/bitnami/redis/certs/redis.dh" + REDIS_TLS_AUTH_CLIENTS: "yes" + networks: + proxies: + aliases: + - redis-cluster-node-5 + ipv4_address: 172.10.12.7 + +networks: + proxies: + name: "imi-ci-service-network" + external: true \ No newline at end of file diff --git a/.github/service/redis-tls/certs/ca.crt b/.github/service/redis-tls/certs/ca.crt new file mode 100644 index 0000000000..891425abcd --- /dev/null +++ b/.github/service/redis-tls/certs/ca.crt @@ -0,0 +1,31 @@ +-----BEGIN CERTIFICATE----- +MIIFSzCCAzOgAwIBAgIUJ9PoXzht9SGd1PP9unf2JK8Lp1gwDQYJKoZIhvcNAQEL +BQAwNTETMBEGA1UECgwKUmVkaXMgVGVzdDEeMBwGA1UEAwwVQ2VydGlmaWNhdGUg +QXV0aG9yaXR5MB4XDTI0MDMwODA4MTc0MloXDTM0MDMwNjA4MTc0MlowNTETMBEG +A1UECgwKUmVkaXMgVGVzdDEeMBwGA1UEAwwVQ2VydGlmaWNhdGUgQXV0aG9yaXR5 +MIICIjANBgkqhkiG9w0BAQEFAAOCAg8AMIICCgKCAgEA4a8sm6bsz1yz86wF8gDZ +C4pjXH5xwMZbV4/iXgtPRbPxhUM+9wk4wXJyflxtBmeVIa1tC56GLqjg/b5Td57Q +OeKtGZVCXkefTKPND87hIUafXHol8ss69FzJ/Y3K1sVeJXZyvDumuuOq4mFei4HJ +M8+e+Cy4PxRZVm/FlG7JqNKIYLpkx1HbwFChhtyH0kRPCKqm0OS2Ez0Ok6awoFM4 +LkiGDiDQUl71INn4zfwNF246V/CXUdOYRtjcZETkB4etAffg4NBFdxuklK4e1Yvu +OJTz4wotXWA3BWyEP4BazFxJDIPYhzeGR+s5/1Pv22t/rt8qjiW6OH3YKACQLddx +uBDKIxivbdwK322fLpESKoW6unGXH2G92AgjZcAzHT+u9y2A/RTUmJQ9Tvadp7r8 +hKZ6cLUYa722iT2Pwy/9InyR7gJKobtbTHeLgzaHv+yYEy+57DieVwmg9ae47Pi2 +Uv6FkuAP0WcsfCzNgUJ2+XtUBVo3XfgMMPKy9z17Ub+38pZJVN5hG/Jnj/7BCECe +/i9kleVsBp5CO6728jwDdX85zsgy7cPjbfjE0LaN9a/kq0mVB5+Aa4mHua5eTmgB +EZukUEHx6wPazuFVYAz0z4SSvIX0IWRvJK9E2mSr0akMzkXpFTMnNr5XLzympvKq +Dow5aZlrSTrqeM/SKOiEYrsCAwEAAaNTMFEwHQYDVR0OBBYEFNelk3Skwpg/I+Yr +B+rMwWPlkSlRMB8GA1UdIwQYMBaAFNelk3Skwpg/I+YrB+rMwWPlkSlRMA8GA1Ud +EwEB/wQFMAMBAf8wDQYJKoZIhvcNAQELBQADggIBAE1Vho2acHEZN8v+UMMSZRoO +JAJI9RytvEoSoO7F3sl6nHsDfCgplyO5pLfhRUuU1UC0O6Vi1azwy3Hy93s9+6GP +oXe1yoseZ0rr80JMQZQMAvhymTt5uOfN7T1wd8fZFsaZmXz8WEeMduYYToZKa3pl +5i2rr2+w/A63J2wgDBvC+T9gtXkufgCDIvZ41vews2TrqPO2fy3RG5iZ0aKkTUb5 +MDxIPYgwchK7BTjY7TEidk+VKC7Gk48EuX6CCeFqftJW6I4hBb0RA3soJ2tvbGeY +ENlP+udM1lwJEO/x+n9NiNgmGJmYDvfJ0dRDLk8ugcSF0uNsKI9VtU5tn674lLHH +YpxCyvC4iPgrXW02z8SP7Jvcy/rUtg836CXx6shRr5b7WWtDdRUjr8S6FoLermzF +JgqC4LpSGwAawGKsquq2c/sbrw3p2F5OBwD4Zhub5LNYgHe5fbJUE+2GJalhwrF5 +RPOCFi7EXn8YpD3AIkojy4YGRZEPdjpre9Km87+9MTpxpr5v1YH11HvTCbmPlud+ +cXPSGEhnSV4kv8lwTnZqNJcZrk1XOkBy3mz3sOTWxs3Lx5GDR0L1ZRncR2rSAjEN +suL90zQzyMDny3HUA43M/yb46qySsp9uduGnQn9Hdq/eXUZ09yuReJq690/Ux0dd +7tP7mhYKvuJwxuokBDBc +-----END CERTIFICATE----- diff --git a/.github/service/redis-tls/certs/ca.key b/.github/service/redis-tls/certs/ca.key new file mode 100644 index 0000000000..a3e77d2c6e --- /dev/null +++ b/.github/service/redis-tls/certs/ca.key @@ -0,0 +1,51 @@ +-----BEGIN RSA PRIVATE KEY----- +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 +-----END RSA PRIVATE KEY----- diff --git a/.github/service/redis-tls/certs/client.crt b/.github/service/redis-tls/certs/client.crt new file mode 100644 index 0000000000..4f8058daa7 --- /dev/null +++ b/.github/service/redis-tls/certs/client.crt @@ -0,0 +1,24 @@ +-----BEGIN CERTIFICATE----- +MIIEEDCCAfigAwIBAgIUbTTNMoBTdAfw6xBhAJKSkeTGHnYwDQYJKoZIhvcNAQEL +BQAwNTETMBEGA1UECgwKUmVkaXMgVGVzdDEeMBwGA1UEAwwVQ2VydGlmaWNhdGUg +QXV0aG9yaXR5MB4XDTI0MDMwODA4MTc0MloXDTI1MDMwODA4MTc0MlowKzETMBEG +A1UECgwKUmVkaXMgVGVzdDEUMBIGA1UEAwwLQ2xpZW50LW9ubHkwggEiMA0GCSqG +SIb3DQEBAQUAA4IBDwAwggEKAoIBAQDWZyd9ecP/LoGN7Jocc3ILTeP/MBBnr+Qa +U+Z0M6PbLeMiqCPlCbrNkMl5dF3tQfRmsHW2nosl43c+zfiO+MOwEB4q1leS/Hj4 +Kdo6jXBWv0xonjOuNEEmjaHgThR3Vf8y4HpagUr7d3KNBgkbFjIfcajB/XXRdkzF +hCIsevoJnI2baopnGlFG7rTTMBAF016+LS2Wva0LK/W3Wt5Q4x7ptF9RxxS1GFcc +EYdXeP/J2Py3XODeS6W4KS6/ge2BRsIQx8q85uaZa/ygczcIb31I3KA6Ax3AB5CJ +mVVZ8s6YRi0u21mlg9U5qH4QqKTPyyl7Bv6l5DDeRVMLWT3l1o/JAgMBAAGjIjAg +MAsGA1UdDwQEAwIFoDARBglghkgBhvhCAQEEBAMCB4AwDQYJKoZIhvcNAQELBQAD +ggIBADllO1pLS+kHWVXsPIhLpWv0H/Yr9gccZjwceXVCN1u2Eo1DHrh8vjZPwC4I +6sTqFACXQsHGPunJxCKanmd6oxTL/SpvHh4Z+V0vw5+bhBiaEJaTo6yQZQrB9i3J +IP+pnJg+/vW+D+D5kMq52pewukpBVuFVKPZDEMkJRSCw7mU+IjkxQN7NKUsWf19Q +ri9kCOPsj3wxCNoYNHbafaipW8IydjcMdAIrrpgsG+OmekMti33AtsMsdAE7FSbA +bs1fIDUq76zda0/OLJ1k6aVjmLn9oleYoUHmubTtiMBYYSKGGSnrDvIAp7MSkPu7 +/GGjR2v6tcPm+gOE/C2u2XoIKTyhXDnINIbrrfCHUKC3mVQRVHV9qQ1f+23rMSMX +yAo6b07YRJfqRmJq3+J/CSlHS/l+EdQZhpJlCVrb07w21OSqxolixKFHlxME/neR +s7OZdpPsJ2vpMM8YnbkBRQd4N1S5d7YaumIijsxfnBv2mJjGhMkACsHhMmNr8QkD +OD+yzP+HRzr5fseuog0l0xxw8zWEP/tXcOVvWjYdXdilhc0RZog1tDrkK/xAlImB +v3mHqo0LaoK+5zr2FTT+/kbp+uwy4tJH2buQC8xrwVoOXtQJz+rB2rdYxTmM6Krc +Edmh5/nvNKUt2xxAw2sJmlczL7Y1a20kJRs2nKhY1zmTwGyc +-----END CERTIFICATE----- diff --git a/.github/service/redis-tls/certs/client.key b/.github/service/redis-tls/certs/client.key new file mode 100644 index 0000000000..42f41d709e --- /dev/null +++ b/.github/service/redis-tls/certs/client.key @@ -0,0 +1,27 @@ +-----BEGIN RSA PRIVATE KEY----- +MIIEpgIBAAKCAQEA1mcnfXnD/y6BjeyaHHNyC03j/zAQZ6/kGlPmdDOj2y3jIqgj +5Qm6zZDJeXRd7UH0ZrB1tp6LJeN3Ps34jvjDsBAeKtZXkvx4+CnaOo1wVr9MaJ4z +rjRBJo2h4E4Ud1X/MuB6WoFK+3dyjQYJGxYyH3Gowf110XZMxYQiLHr6CZyNm2qK +ZxpRRu600zAQBdNevi0tlr2tCyv1t1reUOMe6bRfUccUtRhXHBGHV3j/ydj8t1zg +3kuluCkuv4HtgUbCEMfKvObmmWv8oHM3CG99SNygOgMdwAeQiZlVWfLOmEYtLttZ +pYPVOah+EKikz8spewb+peQw3kVTC1k95daPyQIDAQABAoIBAQCqubVuavmxR30O +YGtPYHZdngaBe+p0RlFizZBi04QU0fNd83mxtg+0BSkJt6nbdXuCEd2KL7Ep2Hlp +32Wfo2Nf3VXIUqmld7l0Ew+dNGdSDD5xyBfrDd0bMAjIriQJ6sat4qZLT00/9JuY +xEeX9BKxizYQUx3wTz1OwqrbtIlKAJQJvpi8eFfMhXZXQvWhTRAMedCDgbuOXyO2 +uHBTveNDS62BoqYZIq9LwBBpL46dpdGq6NSGQgOR8F8FYL0dFxQb+4NeTv/dIUra +YQ6cXFupnVj5D5wLJmqfCcZqX8E0pUaTcIqLIZWNBxQfpXLOTOUurwn8PKMwOSbj +u4Zx72EBAoGBAPYaZFNUyyCEn0I0X/I1hhWLcTetu8L8eXHt9jyctMeAo13aky8a +AkeUlQGmzV7ECT64/j9ysHs9jiwTVM6L1+Z1elSWYivF0TzQcTwPzFz7JRJ9BxSw +NM166vHkxBMYmlTvE1oYkn8ba1gY52b4H4nwVeSN/+jZ/6sok5zR6JpZAoGBAN8G +aY8/g27b2ib7vKgg9InL5TYT7f4cV1IQnuJ0uNbZrFSboWO/ZyMcKBPgLP0iAZ/8 +4r/Ct0QB7gRhg+g7xICkon9Gj0GXNjSiaoqyQfoZdVX/5KFvBItc1YwQo1G+Svvj +o907qtIqifGSu4J7XA7cMPJSpaj+qxY/APSwuxLxAoGBAOWtjdIDgaswep1D2gNn +FmMHBzuqZWA9Vm4QYk0BBupl0JFnyxMbV+NL9KBc9q+pjuM9rPKz66aotQXHaM92 +zaCkJO3Kh4ZIkNULx5IBQH3KWTfe/Xu+UxktzRTBpogX3vjDQrFD23zKryzB2TxM +9so6RT8PkzTSNvya2uBxOn7JAoGBAI9rzzxYiswiw+Jn5sV0E+39WhRxso3Eaf8T +Qym8CBXae3EZeCruLoQsmjVV53iNguAAv0y0CijI2OimUS5qKQ7VUM5qcLusYyZr +//nbcoREFOnOGpgaDaEVfRqKpIxvxEbB+GHP+iUXSAg65Sye6e+AeFWNAo1v4FP5 +BkNU16jxAoGBAMG2VavizJTm4Nm7XYdiNZQ4X1x655q60pwWCrWsEmDnw5LEz4ei +PUmG4nvftiEOwgAHckNnb6KHennvtSsjqFWzo/p3tHlK/O9No7r2WNYbODOxSq1i +9mIffYLxfgJSUrRWlpX1paEg231DpijLR7b2/h+Xm0t8r4Z3xAGgC9sy +-----END RSA PRIVATE KEY----- diff --git a/.github/service/redis-tls/certs/redis.crt b/.github/service/redis-tls/certs/redis.crt new file mode 100644 index 0000000000..81700aa396 --- /dev/null +++ b/.github/service/redis-tls/certs/redis.crt @@ -0,0 +1,23 @@ +-----BEGIN CERTIFICATE----- +MIID6DCCAdACFG00zTKAU3QH8OsQYQCSkpHkxh53MA0GCSqGSIb3DQEBCwUAMDUx +EzARBgNVBAoMClJlZGlzIFRlc3QxHjAcBgNVBAMMFUNlcnRpZmljYXRlIEF1dGhv +cml0eTAeFw0yNDAzMDgwODE3NDJaFw0yNTAzMDgwODE3NDJaMCwxEzARBgNVBAoM +ClJlZGlzIFRlc3QxFTATBgNVBAMMDEdlbmVyaWMtY2VydDCCASIwDQYJKoZIhvcN +AQEBBQADggEPADCCAQoCggEBAMnHIR6eACxE1Ft+0cFAP0x+ZAXw0RMgbOT8TU5j +cturdhywZq5C9KJ0SKPfBxDiEjkRCQnyetsWfRlkt8VaW4z7I8e6P3szmCVlUy5u +2ODhyDOGwue+sI4mmzxO7kpKjY0S+uH1WtfcQG1e/8nzFc+vig1SMBFh47SJnjJd +I32WOgUG/q6MN5r/NLixfUrXIAUUnOLBYdW9C1FEn8BitiZeKgJotduGggjrXV6V +mtBbFw9oOrv1YhQsYs0zV//VoLMkzHRKLBJOr86wGfl0MO++cHOpDbzLT7LlJvQt +GeR4Cn2M1U1zn9fqZZRa9lZFFS95ys8XsmjV2KEGWwBTlH0CAwEAATANBgkqhkiG +9w0BAQsFAAOCAgEATau8XAaGVzaU23PWIhRR1+R8jQa+hZTK58qBSDFBGNjy06YT +I6+AfJQV23gxC20bshLONGItcUdkKXi+O0pElWaJ/mjQUYCt2vCAtH5LLwPLug6m +lP6YvufTiWuu6KZ5cl4fstKdTAIefcN9qb6OQYI9V6qLEIqY4t8VCQBkUtuNaCck +wyrq2BTzFNgyIDT5AS2L5gpLnahHz3iyi4dGTgZznPe2qZ3qzvxpzc68r16NMe22 +WujYVzzjHJimHJgEPjpct0DPhmc0edNk25iTRzK33DGCiWLBQ9U7BqcTjr6oMQf1 +GlcmZtI1hVKBVa2B4jLWm2avkH1egqVm2ZZmXvZLwvqNA7chR1DJCWCQFsiGxf4K +E9XceBsMWyV/ccG0Pby9RGj/NzW2wujDQWXaffnwKhkfrnOJxu2Yye1KJMge0xJj +AAJQaMgRCDYCraWNuKdyFutkafMCuaOa91xriUtgJPJI81oWo2NGeLVA6Sxhzuwt +9pWvutG1fKfTA/qbqBH7kgdT5ozUthQUBgfd8NPuL/hlN5yeZWVWsVBXGbW9TeLI +JjYNmWT1bmdDHyaiAKs8R6y5d7w462kCirrxUWNB9s6AvruR+6Zz+ZJwqxhpiuW+ +u9tEVBw4oyndHdk1Yd87+kNb07VZ7RpOCL5fqWPE3Oj7840B+hE1we4bJtk= +-----END CERTIFICATE----- diff --git a/.github/service/redis-tls/certs/redis.dh b/.github/service/redis-tls/certs/redis.dh new file mode 100644 index 0000000000..5677df11d0 --- /dev/null +++ b/.github/service/redis-tls/certs/redis.dh @@ -0,0 +1,8 @@ +-----BEGIN DH PARAMETERS----- +MIIBCAKCAQEAuOlvuysLa1Aw3+Qybxi+a1CNN80Zp09U5AHFj7GcJn4Oy158rmdp +xrJOHP1KS+11Fj1XIiwNByRjNTaVmPeCpM823K7fzHnNfe/AxFDksomDc9CajCPe +xLOUojW5iFiGW1HZGhN5m5g1JOYa/4YRCOdrNmHwoKLjCIg+n7TXL1ICEktSxuPs +7HeZSNL69uJ/xoX/TlCoCU5ql9dLVnAvYVkaL9sA5n0hmlPgUAHOrsIGxpd0S9Ez +aYKVkNpaHzUUsq3yNLTlgeDQjq1v9ZCpDbLv3PuMoZFawNG/I+T34Ak+gYZ4ZcFi +3q/thwzQPw3LjrM36gByHx16jISuSF3QOwIBAg== +-----END DH PARAMETERS----- diff --git a/.github/service/redis-tls/certs/redis.key b/.github/service/redis-tls/certs/redis.key new file mode 100644 index 0000000000..eb7a695cc1 --- /dev/null +++ b/.github/service/redis-tls/certs/redis.key @@ -0,0 +1,27 @@ +-----BEGIN RSA PRIVATE KEY----- +MIIEowIBAAKCAQEAycchHp4ALETUW37RwUA/TH5kBfDREyBs5PxNTmNy26t2HLBm +rkL0onRIo98HEOISOREJCfJ62xZ9GWS3xVpbjPsjx7o/ezOYJWVTLm7Y4OHIM4bC +576wjiabPE7uSkqNjRL64fVa19xAbV7/yfMVz6+KDVIwEWHjtImeMl0jfZY6BQb+ +row3mv80uLF9StcgBRSc4sFh1b0LUUSfwGK2Jl4qAmi124aCCOtdXpWa0FsXD2g6 +u/ViFCxizTNX/9WgsyTMdEosEk6vzrAZ+XQw775wc6kNvMtPsuUm9C0Z5HgKfYzV +TXOf1+pllFr2VkUVL3nKzxeyaNXYoQZbAFOUfQIDAQABAoIBAAhINiHNlnA6uwSu +Zemqu25mWbCsu8gvMokLmhi3mEVP+l8fFnfco7HvV/Px+ZZF0T2qZ1aTL1vCxou+ +SJS/KrbUsBlImcZyzbHrQMjNH/XLDq6ev21HtHOBPinxi3JdMQYzWzzfF0V48uQK +XDFr2t9VczMsxnBQNkp4w5eJnyVObJA+jPsAxXA1+2nj1ZVYqACrPzzEwPrWi4ji +rqTxRqS94DIVEID6PGB1SFoKjS6BHUktYooNboUir+idl634CVwSREp1QjPge2pW +BW52+Z/VHI4cqOvXJgdRX9K4jkHFLp0qyENflchyZ2AG1mxeTIZjfffaQvwgP6T2 +JC32cfkCgYEA7413fOAKIJfM12TBokXzyAmL66TRXehlyoW0UOyyR2pikUR2f5EL +enUbh2U8Btrk8DrKTKlPNGl2SC+SefxmW+FnPY+VDwqhYp3+YnMODE+2/i4tjAIU +wL1WauzAc/78cjyihEWlH6rA+OSRJCsSwki8Qn3a9EUI4mYUidtror8CgYEA16G1 +dRjDJG7KekVaTXz3ZAmwq+k9UKu4eoVPQhw22SEw/dBJ5olpMxkUFsCLVEle82mV +xcaEoAECI2/+3Us3wUmv0dJ6bW72pc7qdW7CQathDpwozaAPRE29QgP2W3HQERUy +IHr5N0Z1Yo7XGgAcuyOlU3d4/8S0z6rhuGQJo8MCgYEAgeRjdgLFewbUu7aWiDcG +COGkTRIBtLne+AGn1HmD8dVtvPcyidlMMApv8uqhsdXfbaNzLj5gBDtrN5kUA7Eo +j4mZQXgpiw5ok+C3nwpkA6j1wL2pVNGMDzabNT9K25rXp9nZBX/+GT2thUfqq4Hv +mgl2i1dS8kC8oIZZfKbNpmECgYBhMlYd2zSTJpGEPeCvjwXghPGq++6Uf2MfbxnD +3f3nL6vqrMmy7fuKeeJxQwdKzevL4qsNRCeiC/JP0Prb+zy9lp53AN4Il/z7zmIm +3u8XNM4CDOfjkCNxkW0e5bRVkd7M5HX86BGQFeVxsJtK8AQDYtTx46eZ+qvZ89fd +CtLBiwKBgCUOvKt1WGuBlHBy3mfXsf2UgQdJATMY/HHzvpFRKakri/VEFphugKms +v1ascCbeboYn8+yfAa2uNLGJ/u346dOfXoszA/1v5UzMlRZK5HYYgGGkRAoeTMsL +6BzAUFxSe5mVIvxbIvmFUreP/ZovMC74idoMA+N8OUifAzcNF+4E +-----END RSA PRIVATE KEY----- diff --git a/.github/service/redis-tls/redis-overrides.conf b/.github/service/redis-tls/redis-overrides.conf new file mode 100644 index 0000000000..d3f0f7abee --- /dev/null +++ b/.github/service/redis-tls/redis-overrides.conf @@ -0,0 +1,2 @@ +unixsocket /run/shared/redis.sock +unixsocketperm 777 diff --git a/.github/shared-env.sh b/.github/shared-env.sh new file mode 100755 index 0000000000..1f7958ff34 --- /dev/null +++ b/.github/shared-env.sh @@ -0,0 +1,11 @@ +#!/bin/env sh + +set -ex + +echo "init shared" + +rm -rf /run/shared/* || true +chmod -R 777 /run/shared + + +tail -f /dev/null \ No newline at end of file diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 2792781342..49079081f6 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -34,7 +34,6 @@ jobs: REPOSITORY_OWNER: ${{ github.repository_owner }} IMAGE_VERSION: ${{ matrix.swoole.version }} MYSQL_DOCKER_VERSION: "8.0" - REDIS_SERVER_HOST: redis ROADRUNNER_DOCKER_VERSION: ${{ matrix.roadrunner }} GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} steps: @@ -56,6 +55,18 @@ jobs: uses: ./.github/actions/ci-prepare with: env: ${{ env.ENV_SERVICE }} + - name: Test Env + if: ${{ env.test_prepared && always() }} + run: | + docker ps + docker logs shared-tmp || true + docker logs redis || true + docker exec ${ENV_SERVICE} bash -c "ls -lha /run/shared" + echo ">>> redis-cluster-node-0" + docker exec ${ENV_SERVICE} bash -c "echo -e 'auth l83aa26\r\ninfo server' | nc redis-cluster-node-0-1 6379 -w 1" + docker exec ${ENV_SERVICE} bash -c "echo -e 'auth l83aa26\r\ncluster info\r\ncluster nodes' | nc redis-cluster-node-0-1 6379 -w 1" + echo ">>> redis" + docker exec ${ENV_SERVICE} bash -c "echo -e 'auth l83aa26\r\ninfo server' | nc redis 6379 -w 1" - name: Test if: ${{ env.test_prepared && always() }} run: docker exec ${ENV_SERVICE} composer test @@ -65,6 +76,10 @@ jobs: - name: Test database if: ${{ env.test_prepared && always() }} run: docker exec ${ENV_SERVICE} composer test-database + - name: Test redis + if: ${{ env.test_prepared && always() }} + run: | + docker exec ${ENV_SERVICE} composer test-redis - name: Test swoole if: ${{ env.test_prepared && always() }} run: docker exec ${ENV_SERVICE} composer test-swoole @@ -117,100 +132,6 @@ jobs: if: failure() run: docker exec ${ENV_SERVICE} php .github/print-logs.php - ci-unix: - name: Linux Swoole-${{ matrix.swoole.version }} RoadRunner-${{ matrix.roadrunner }} With Redis UnixSocket - runs-on: ubuntu-latest - strategy: - fail-fast: false - matrix: - swoole: - - version: php8.2-swoole-5.1 - roadrunner: [2.7.*] - env: - ENV_SERVICE: swoole - REPOSITORY_OWNER: ${{ github.repository_owner }} - IMAGE_VERSION: ${{ matrix.swoole.version }} - MYSQL_DOCKER_VERSION: "8.0" - REDIS_SERVER_HOST: /tmp/docker/redis.sock - ROADRUNNER_DOCKER_VERSION: ${{ matrix.roadrunner }} - GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} - steps: - - name: Checkout - uses: actions/checkout@v4 - - name: Prepare1 - run: | - echo "REPOSITORY_OWNER=${REPOSITORY_OWNER,,}" >>${GITHUB_ENV} - mkdir -p /tmp/base_cache/composer - - name: Cache dependencies - uses: actions/cache@v4 - with: - path: /tmp/base_cache/composer - key: ${{ runner.os }}-composer-${{ env.IMAGE_VERSION }}-${{ hashFiles('*/composer.json', 'src/Components/*/composer.json') }} - restore-keys: | - ${{ runner.os }}-composer-${{ env.IMAGE_VERSION }}- - ${{ runner.os }}-composer- - - name: Prepare2 - uses: ./.github/actions/ci-prepare - with: - env: ${{ env.ENV_SERVICE }} - - name: Test - if: ${{ env.test_prepared && always() }} - run: docker exec ${ENV_SERVICE} composer test - - name: Test connection-center - if: ${{ env.test_prepared && always() }} - run: docker exec ${ENV_SERVICE} composer test-connection-center - - name: Test database - if: ${{ env.test_prepared && always() }} - run: docker exec ${ENV_SERVICE} composer test-database - - name: Test swoole - if: ${{ env.test_prepared && always() }} - run: docker exec ${ENV_SERVICE} composer test-swoole - - name: Test workerman - if: ${{ env.test_prepared && always() }} - run: docker exec ${ENV_SERVICE} composer test-workerman - - name: Test workerman-gateway - if: ${{ env.test_prepared && always() }} - run: docker exec ${ENV_SERVICE} composer test-workerman-gateway - - name: Test roadrunner - if: ${{ env.test_prepared && always() }} - run: docker exec ${ENV_SERVICE} composer test-roadrunner - - name: Test fpm - if: ${{ env.test_prepared && always() }} - run: docker exec ${ENV_SERVICE} composer test-fpm - - name: Test jwt - if: ${{ env.test_prepared && always() }} - run: docker exec ${ENV_SERVICE} composer test-jwt - - name: Test queue - if: ${{ env.test_prepared && always() }} - run: docker exec ${ENV_SERVICE} composer test-queue - - name: Test amqp - if: ${{ env.test_prepared && always() }} - run: docker exec ${ENV_SERVICE} composer test-amqp - - name: Test kafka - if: ${{ env.test_prepared && always() }} - run: docker exec ${ENV_SERVICE} composer test-kafka - - name: Test grpc - if: ${{ env.test_prepared && always() }} - run: docker exec ${ENV_SERVICE} composer test-grpc - - name: Test snowflake - if: ${{ env.test_prepared && always() }} - run: docker exec ${ENV_SERVICE} composer test-snowflake - - name: Test mqtt - if: ${{ env.test_prepared && always() }} - run: docker exec ${ENV_SERVICE} composer test-mqtt - - name: Test smarty - if: ${{ env.test_prepared && always() }} - run: docker exec ${ENV_SERVICE} composer test-smarty - - name: Test pgsql - if: ${{ env.test_prepared && always() }} - run: docker exec ${ENV_SERVICE} composer test-pgsql - - name: Test model - if: ${{ env.test_prepared && always() }} - run: docker exec ${ENV_SERVICE} composer test-model - - name: Print logs - if: failure() - run: docker exec ${ENV_SERVICE} php .github/print-logs.php - ci-swoole-cli: name: Swoole-cli-${{ matrix.swoole-cli }} runs-on: ubuntu-latest @@ -221,13 +142,19 @@ jobs: env: MYSQL_DOCKER_VERSION: "8.0" GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} + REDIS_SERVER_HOST: "127.0.0.1" + REDIS_SERVER_PASSWORD: "l83aa26" + REDIS_SERVER_CLUSTER_PASSWORD: "l83aa26" + REDIS_SERVER_CLUSTER_SEEDS: "172.10.12.2:6379,172.10.12.3:6379,172.10.12.4:6379,172.10.12.5:6379,172.10.12.6:6379,172.10.12.7:6379" steps: - name: Checkout uses: actions/checkout@v4 - name: Setup Services shell: bash run: | - sudo apt update && sudo apt install -y rsync + sudo apt update && sudo apt install -y rsync netcat-openbsd tree + docker network create imi-ci-service-network --subnet 172.10.12.0/24 + docker compose -f ./.github/service/redis-cluster/docker-compose.yml up -d docker compose -f ./.github/docker-compose.yml up -d mysql postgres redis rabbitmq kafka1 echo "127.0.0.1 kafka1" | sudo tee -a /etc/hosts - name: Setup swoole-cli @@ -266,7 +193,22 @@ jobs: docker exec postgres psql -d db_imi_test -U root -f /imi/.github/pgsql.sql echo "::endgroup::" echo "test_prepared=1" >> $GITHUB_ENV - + - name: Test Env + if: ${{ env.test_prepared && always() }} + run: | + docker ps + docker logs shared-tmp + docker logs redis + find /run/shared -name *.sock + tree -alfugh /run/shared + echo ">>> redis" + echo -e 'auth l83aa26\r\ninfo server' | nc 127.0.0.1 6379 -w 1 + echo ">>> =====" + docker compose -f ./.github/service/redis-cluster/docker-compose.yml logs + echo ">>> redis-cluster" + echo -e 'auth l83aa26\r\ninfo server' | nc 172.10.12.2 6379 -w 1 + echo -e 'auth l83aa26\r\ncluster info\r\ncluster nodes' | nc 172.10.12.2 6379 -w 1 + docker compose -f ./.github/service/redis-cluster/docker-compose.yml exec node-0 cat /bitnami/redis/data/nodes.conf - name: Test if: ${{ env.test_prepared && always() }} run: composer test @@ -276,6 +218,18 @@ jobs: - name: Test database if: ${{ env.test_prepared && always() }} run: composer test-database + - name: Test redis + if: ${{ env.test_prepared && always() }} + env: + REDIS_SERVER_UNIX_SOCK: "/run/shared/redis.sock" + REDIS_SERVER_TLS_CLUSTER_SEEDS: "172.10.12.2:6443,172.10.12.3:6443,172.10.12.4:6443,172.10.12.5:6443,172.10.12.6:6443,172.10.12.7:6443" + REDIS_SERVER_TLS_HOST: "127.0.0.1" + REDIS_SERVER_TLS_PORT: "6443" + REDIS_SERVER_TLS_PASSWORD: "l83aa26" + REDIS_SERVER_TLS_CA_FILE: ${{ github.workspace }}/.github/service/redis-tls/certs/ca.crt + REDIS_SERVER_TLS_CERT_FILE: ${{ github.workspace }}/.github/service/redis-tls/certs/client.crt + REDIS_SERVER_TLS_KEY_FILE: ${{ github.workspace }}/.github/service/redis-tls/certs/client.key + run: composer test-redis - name: Test swoole if: ${{ env.test_prepared && always() }} run: composer test-swoole @@ -328,8 +282,8 @@ jobs: strategy: fail-fast: false matrix: - php: ["8.1", "8.2"] - swoole: [v5.1.0, v5.0.3] + php: ["8.2"] # ["8.1", "8.2"] + swoole: [v5.1.0] # [v5.1.0, v5.0.3] roadrunner: [2.7.*] env: MYSQL_SERVER_PASSWORD: "root" @@ -350,8 +304,11 @@ jobs: socket=/tmp/mysql.sock - name: Setup Redis uses: shogo82148/actions-setup-redis@v1 + id: setup-redis with: - redis-version: "6.x" + redis-version: "7.2" + redis-port: "6379" + redis-tls-port: "6443" # MacOS Arm64 下需要下面的修复,否则无法编译成功 - name: Fix include run: | @@ -365,7 +322,7 @@ jobs: php-version: ${{ matrix.php }} tools: pecl extensions: > - apcu, bcmath, curl, openssl, mbstring, intl, json, redis, mysqli, pdo, pdo_mysql, sockets, zip, :opcache, + apcu, bcmath, curl, openssl, mbstring, intl, json, redis, mysqli, pdo, pdo_mysql, sockets, zip, :opcache, swoole-swoole/swoole-src@${{ matrix.swoole }} env: SWOOLE_CONFIGURE_OPTS: > @@ -422,6 +379,16 @@ jobs: - name: Test database if: ${{ env.test_prepared && always() }} run: composer test-database + - name: Test redis + if: ${{ env.test_prepared && always() }} + env: + REDIS_SERVER_UNIX_SOCK: ${{ steps.setup-redis.outputs.redis-unix-socket }} + REDIS_SERVER_TLS_HOST: "127.0.0.1" + REDIS_SERVER_TLS_PORT: "6443" + REDIS_SERVER_TLS_CA_FILE: ${{ steps.setup-redis.outputs.redis-tls-dir }}/ca.crt + REDIS_SERVER_TLS_CERT_FILE: ${{ steps.setup-redis.outputs.redis-tls-dir }}/client.crt + REDIS_SERVER_TLS_KEY_FILE: ${{ steps.setup-redis.outputs.redis-tls-dir }}/client.key + run: composer test-redis - name: Test swoole if: ${{ env.test_prepared && always() }} run: composer test-swoole @@ -554,6 +521,9 @@ jobs: - name: Test database if: ${{ env.test_prepared && always() }} run: composer test-database + - name: Test redis + if: ${{ env.test_prepared && always() }} + run: composer test-redis - name: Test fpm if: ${{ env.test_prepared && always() }} run: composer test-fpm diff --git a/.github/workflows/codecov.yml b/.github/workflows/codecov.yml index c669235027..f4f1ad4e26 100644 --- a/.github/workflows/codecov.yml +++ b/.github/workflows/codecov.yml @@ -22,6 +22,7 @@ env: jobs: test: runs-on: ubuntu-latest + if: false strategy: matrix: testType: [core, swoole, components] diff --git a/.github/workflows/phpcs.yml b/.github/workflows/phpcs.yml index a13fada701..cc66675538 100644 --- a/.github/workflows/phpcs.yml +++ b/.github/workflows/phpcs.yml @@ -53,6 +53,7 @@ jobs: - name: Prepare2 run: | echo "::group::Env prepare" + docker network create imi-ci-service-network --subnet 172.10.12.0/24 docker compose -f ./.github/docker-compose.yml up -d ${ENV_SERVICE} echo "::endgroup::" echo "::group::Env info" diff --git a/.github/workflows/phpstan.yml b/.github/workflows/phpstan.yml index e018282367..825732d655 100644 --- a/.github/workflows/phpstan.yml +++ b/.github/workflows/phpstan.yml @@ -61,6 +61,7 @@ jobs: - name: Prepare2 run: | echo "::group::Env prepare" + docker network create imi-ci-service-network --subnet 172.10.12.0/24 docker compose -f ./.github/docker-compose.yml up -d ${ENV_SERVICE} echo "::endgroup::" echo "::group::Env info" @@ -196,6 +197,11 @@ jobs: run: | docker exec ${ENV_SERVICE} ./dev/phpstan.sh model + - name: Analyse redis + if: ${{ env.test_prepared && always() }} + run: | + docker exec ${ENV_SERVICE} ./dev/phpstan.sh redis + - name: Save All composer.lock And autoloader-suffix if: ${{ env.test_prepared && always() }} run: | diff --git a/.github/workflows/rector.yml b/.github/workflows/rector.yml index c6ea13c4d9..5096ae1d15 100644 --- a/.github/workflows/rector.yml +++ b/.github/workflows/rector.yml @@ -45,6 +45,7 @@ jobs: - name: Prepare2 run: | echo "::group::Env prepare" + docker network create imi-ci-service-network --subnet 172.10.12.0/24 docker compose -f ./.github/docker-compose.yml up -d ${ENV_SERVICE} echo "::endgroup::" echo "::group::Env info" @@ -182,3 +183,8 @@ jobs: if: ${{ env.test_prepared && always() }} run: | docker exec -w /imi/src/Components/model ${ENV_SERVICE} /imi/vendor/bin/rector process --dry-run + + - name: Analyse redis + if: ${{ env.test_prepared && always() }} + run: | + docker exec -w /imi/src/Components/redis ${ENV_SERVICE} /imi/vendor/bin/rector process --dry-run diff --git a/.gitignore b/.gitignore index 69774d9b2c..46577635ec 100644 --- a/.gitignore +++ b/.gitignore @@ -9,6 +9,7 @@ composer.lock /mddoc/vendor *.lock /src/Components/*/vendor +/src/Components/*/tests/.env /split-repository/vendor /.vscode *.pid diff --git a/composer.json b/composer.json index 04f2356c58..c853291e0d 100644 --- a/composer.json +++ b/composer.json @@ -53,14 +53,16 @@ "files": [ "dev/bootstrap.php", "tests/helper.php", - "src/Components/model/vendor/autoload.php" + "src/Components/model/vendor/autoload.php", + "src/Components/redis/vendor/autoload.php" ] }, "suggest": { "ext-inotify": "高性能热更新支持", "ext-pdo": "数据库操作支持", "symfony/polyfill-uuid": "模型 uuid 发号器依赖", - "ext-uuid": "模型 uuid 发号器依赖" + "ext-uuid": "模型 uuid 发号器依赖", + "ext-redis": "phpredis 客户端依赖" }, "minimum-stability": "dev", "prefer-stable": true, @@ -120,6 +122,7 @@ ], "test-database": "@php vendor/bin/phpunit -c src/Components/database/tests/phpunit.xml", "test-model": "@php vendor/bin/phpunit -c src/Components/model/tests/phpunit.xml", + "test-redis": "@php vendor/bin/phpunit -c src/Components/redis/tests/phpunit.xml", "test-components": [ "@composer test-swoole", "@composer test-workerman", diff --git a/dev/phpstan.sh b/dev/phpstan.sh index 0c5ad795dc..3ec6bc5889 100755 --- a/dev/phpstan.sh +++ b/dev/phpstan.sh @@ -28,11 +28,13 @@ components=( "connection-center" "database" "model" + "redis" ) analyze_component() { component="$1" gen_baseline="$2" + show_verbose="$3" echo "Analyzing: $component, Generate Baseline: $gen_baseline" analyse_configuration="" @@ -48,12 +50,17 @@ analyze_component() { args+=("--generate-baseline=./phpstan-baseline/baseline-$component.neon" "--allow-empty-baseline") fi + if [ "$show_verbose" == "true" ]; then + args+=("-v") + fi + echo ./vendor/bin/phpstan analyse "${args[@]}" PHPSTAN_ANALYSE_COMPONENT_NAME="$component" PHPSTAN_GENERATE_BASELINE="$gen_baseline" ./vendor/bin/phpstan analyse "${args[@]}" -vvv } use_baseline="false" +use_verbose="false" input_components=() while [[ $# -gt 0 ]]; do @@ -66,6 +73,10 @@ while [[ $# -gt 0 ]]; do use_baseline="true" shift ;; + -v) + use_verbose="true" + shift + ;; *) # 如果不是 --baseline 标志,将参数添加到 components 数组中 input_components+=("$1") @@ -77,13 +88,13 @@ done if [ ${#input_components[@]} -eq 0 ]; then # If no arguments are provided, analyze all components for component in "${components[@]}"; do - analyze_component "$component" "$use_baseline" + analyze_component "$component" "$use_baseline" "$use_verbose" done else # Analyze the specified components provided as arguments for component in "${input_components[@]}"; do if [[ " ${components[@]} " =~ " $component " || "core" == "$component" ]]; then - analyze_component "$component" "$use_baseline" + analyze_component "$component" "$use_baseline" "$use_verbose" else echo "Invalid component name: $component" fi diff --git a/dev/rector.sh b/dev/rector.sh index e1f9d88a02..1f83a71f6b 100644 --- a/dev/rector.sh +++ b/dev/rector.sh @@ -28,6 +28,7 @@ components=( "connection-center" "database" "model" + "redis" ) analyze_component() { diff --git a/doc/SUMMARY.md b/doc/SUMMARY.md index 2e883a2896..b0dded04a4 100644 --- a/doc/SUMMARY.md +++ b/doc/SUMMARY.md @@ -183,7 +183,9 @@ * [前置和后置事件](components/orm/relation/events.md) * [数据库迁移](components/orm/migration.md) * [Redis](components/redis/index.md) -* [Redis 模型](components/orm/RedisModel.md) + * [连接与配置](components/redis/index.md) + * [Redis 使用](components/redis/function.md) + * [Redis 模型](components/orm/RedisModel.md) * [内存表模型](components/orm/MemoryTableModel.md) * [缓存](components/cache/index.md) * [使用说明](components/cache/index.md) diff --git a/doc/base/version/2.1-3.0.md b/doc/base/version/2.1-3.0.md index 032f4be6d8..d959c290bb 100644 --- a/doc/base/version/2.1-3.0.md +++ b/doc/base/version/2.1-3.0.md @@ -65,31 +65,31 @@ return [ ### 框架核心 -* `psr/http-message` 版本升级,请求和响应相关类的类型声明有改动 +- `psr/http-message` 版本升级,请求和响应相关类的类型声明有改动 -* 重构注解类写法 +- 重构注解类写法 -* Bean 类默认不支持互相注入,需要使用注解声明 `#[Bean(recursion: true)]` +- Bean 类默认不支持互相注入,需要使用注解声明 `#[Bean(recursion: true)]` -* 定时任务 `Imi\Cron\Annotation\Cron` 注解的 `unique` 值类型更改为 `\Imi\Cron\Consts\UniqueLevel` 枚举,大小写有所变化 +- 定时任务 `Imi\Cron\Annotation\Cron` 注解的 `unique` 值类型更改为 `\Imi\Cron\Consts\UniqueLevel` 枚举,大小写有所变化 ### 事件 -* 使用注解监听事件,`public function handle(Imi\Event\EventParam $e): void` 改为 `public function handle(Imi\Event\Contract\IEvent $e): void` +- 使用注解监听事件,`public function handle(Imi\Event\EventParam $e): void` 改为 `public function handle(Imi\Event\Contract\IEvent $e): void` -* `Imi\Event::trigger()` 计划废弃,建议改为 `Imi\Event::dispatch()`,用法有所变动,请查阅文档 +- `Imi\Event::trigger()` 计划废弃,建议改为 `Imi\Event::dispatch()`,用法有所变动,请查阅文档 -* 事件名称规则统一改为全小写,为保持兼容请[参考文档](/v3.0/event/index.html#3.0%20兼容性) +- 事件名称规则统一改为全小写,为保持兼容请[参考文档](/v3.0/event/index.html#3.0%20兼容性) ### 模型 -* UUID 发号器的 `type` 类型改为枚举,大小写有所变化 +- UUID 发号器的 `type` 类型改为枚举,大小写有所变化 -* 模型类静态事件命名更改,连接符由`:`改为`.`,事件名称也有改变请[参考文档](/v3.0/components/orm/RDModel/event.html) +- 模型类静态事件命名更改,连接符由`:`改为`.`,事件名称也有改变请[参考文档](/v3.0/components/orm/RDModel/event.html) ### WebSocket -* 重构 `Imi\Server\WebSocket\Enum::NonControlFrameType` 为枚举 +- 重构 `Imi\Server\WebSocket\Enum::NonControlFrameType` 为枚举 ### imi-access-control @@ -97,15 +97,15 @@ return [ ### imi-amqp -* 连接配置项有所增改,参考 [连接配置项](https://doc.imiphp.com/v3.0/components/mq/amqp.html#%E8%BF%9E%E6%8E%A5%E9%85%8D%E7%BD%AE%E9%A1%B9) +- 连接配置项有所增改,参考 [连接配置项](https://doc.imiphp.com/v3.0/components/mq/amqp.html#%E8%BF%9E%E6%8E%A5%E9%85%8D%E7%BD%AE%E9%A1%B9) -* `Imi\AMQP\Annotation\Connection` 注解类的连接配置全部废弃,只保留 `poolName` +- `Imi\AMQP\Annotation\Connection` 注解类的连接配置全部废弃,只保留 `poolName` -* 废弃 `Imi\AMQP\Swoole\AMQPSwooleConnection` 客户端类 +- 废弃 `Imi\AMQP\Swoole\AMQPSwooleConnection` 客户端类 -* 消费者类 `Imi\AMQP\Base\BaseConsumer::consume()` 方法返回值类型应设置为 `\Imi\AMQP\Enum\ConsumerResult`,且必须返回枚举值 +- 消费者类 `Imi\AMQP\Base\BaseConsumer::consume()` 方法返回值类型应设置为 `\Imi\AMQP\Enum\ConsumerResult`,且必须返回枚举值 -* `Imi\Queue\Enum\QueueType` 改为原生注解,如需自定义请编写枚举并实现 `Imi\Queue\Enum\QueueType\IQueueType` 接口 +- `Imi\Queue\Enum\QueueType` 改为原生注解,如需自定义请编写枚举并实现 `Imi\Queue\Enum\QueueType\IQueueType` 接口 ### imi-macro @@ -115,25 +115,34 @@ return [ 由于 Hprose 官方弃坑,废弃并移出主仓库,代码仓库: +### imi-redis + +- 弃用为核心独立组件 +- 适配新连接中心 +- 支持多客户端支持(`phpredis`, `predis`) +- 支持`TLS`连接 +- 新的使用方法请[参考文档](/v3.0/components/redis/index.html) +- 废弃`\Imi\Redis\RedisHandler::class`,使用到的地方请迁移为`\Imi\Redis\Handler\IRedisHandler::class`或者具体实现类 + ### 废弃 -* 废弃命名空间声明在 `config.php` 的写法,统一写到 `composer.json` 的 `imi.namespace` +- 废弃命名空间声明在 `config.php` 的写法,统一写到 `composer.json` 的 `imi.namespace` -* 废弃支持模型 insert、update 传入 $data 参数 +- 废弃支持模型 insert、update 传入 $data 参数 -* 废弃模型基类中使用 `ConfigValue` 注解,改为在 `Meta` 类中读取配置 +- 废弃模型基类中使用 `ConfigValue` 注解,改为在 `Meta` 类中读取配置 -* 废弃按表指定模型生成配置 +- 废弃按表指定模型生成配置 -* 废弃 `Imi\Model\ModelManager` +- 废弃 `Imi\Model\ModelManager` -* 废弃 `Model::updateBatch()` 和 `Model::deleteBatch()` +- 废弃 `Model::updateBatch()` 和 `Model::deleteBatch()` -* 废弃模型查询时动态指定字段名的特殊处理 +- 废弃模型查询时动态指定字段名的特殊处理 -* 废弃注释注解,改为全部使用原生注解 +- 废弃注释注解,改为全部使用原生注解 -* 废弃命令行相关类:(右侧是新的类名) +- 废弃命令行相关类:(右侧是新的类名) `Imi\Cli\Annotation\Arg` => `Imi\Cli\Annotation\Option` @@ -149,9 +158,9 @@ return [ `Imi\Tool\ArgType` => `Imi\Cli\ArgType` -* 废弃 `Query::alias()` +- 废弃 `Query::alias()` -* 废弃 `Query::chunkEach()`,改为: +- 废弃 `Query::chunkEach()`,改为: ```php $query->chunkById($count, $column, $alias)->each(); @@ -159,18 +168,18 @@ $query->chunkById($count, $column, $alias)->each(); $query->chunkByOffset($limit)->each(); ``` -* 废弃 `Imi\Pool\ResourceConfigMode::TURN` 改为 `Imi\Pool\ResourceConfigMode::ROUND_ROBIN` +- 废弃 `Imi\Pool\ResourceConfigMode::TURN` 改为 `Imi\Pool\ResourceConfigMode::ROUND_ROBIN` -* 废弃连接池类的 `createResource()` 方法,改为 `createNewResource()`,影响自定义连接池 +- 废弃连接池类的 `createResource()` 方法,改为 `createNewResource()`,影响自定义连接池 -* 废弃 `Imi\Util\DateTime::getLastWeek()`,错误的命名,改为 `Imi\Util\DateTime::getPrevWeek()` +- 废弃 `Imi\Util\DateTime::getLastWeek()`,错误的命名,改为 `Imi\Util\DateTime::getPrevWeek()` -* 废弃 `ExtractData` 注解,建议使用 `RequestParam` +- 废弃 `ExtractData` 注解,建议使用 `RequestParam` -* 废弃 `ErrorLog::onException()`,建议使用 `Imi\Log\Log::error()` +- 废弃 `ErrorLog::onException()`,建议使用 `Imi\Log\Log::error()` -* 废弃 Swoole MySQL 客户端,建议使用 PDO 和 mysqli +- 废弃 Swoole MySQL 客户端,建议使用 PDO 和 mysqli -* 废弃 gRPC 旧的 Server 相关类 +- 废弃 gRPC 旧的 Server 相关类 -* 废弃 `imiGetEnv()`、建议使用 `Imi\env()` +- 废弃 `imiGetEnv()`、建议使用 `Imi\env()` diff --git a/doc/components/orm/RedisModel.md b/doc/components/orm/RedisModel.md index e98be390c5..9be8e44ec9 100644 --- a/doc/components/orm/RedisModel.md +++ b/doc/components/orm/RedisModel.md @@ -159,9 +159,9 @@ Redis模型中只有 `name`、`type` 和 `listSeparator` 生效。 `type` 支持: -* `json`,序列化为 JSON 字符串 -* `list`必须设置 `listSeparator`,以此来分割为数组 -* `set`,使用 `,` 分割为数组 +- `json`,序列化为 JSON 字符串 +- `list`必须设置 `listSeparator`,以此来分割为数组 +- `set`,使用 `,` 分割为数组 ## 模型操作 @@ -232,3 +232,34 @@ TestRedisModel::deleteBatch('kkk', [ 'name' => 'imi' ]); ``` + +### Fork 模型 + +Fork 模型特性,支持在运行阶段创建一个新的模型类,这个类从原模型继承。 + +并且支持指定新模型类使用的:数据库名、数据表名、连接池名。 + +方法定义: + +```php +/** + * Fork 模型. + * + * @return class-string + */ +public static function fork(?string $poolName = null, ?string $formatter = null, int $db = null) +``` + +例子: + +```php +// 重新指定模型要使用的连接池 +$newClassName = TestModel::fork('redis_pool_2'); + +// 重新指定模型要使用的序列化类 +$formatter = \Imi\Util\Format\PhpSerialize::class; +$newClassName = TestModel::fork('redis_pool_2', $formatter); + +// 重新指定模型使用指定 db (不推荐把redis分多个库的用法) +$newClassName = TestModel::fork('redis_pool_2', null, 3); +``` diff --git a/doc/components/redis/function.md b/doc/components/redis/function.md new file mode 100644 index 0000000000..154558a399 --- /dev/null +++ b/doc/components/redis/function.md @@ -0,0 +1,241 @@ +# Redis 使用 + +[toc] + +## 基础使用 + +> 注意,方法和传参在不同客户端中可能存在不一致性,具体参考各自客户端文档 + +### 获取连接对象 + +```php +use \Imi\Redis\RedisManager; + +/** @var \Imi\Redis\Handler\PhpRedisHandler $redis */ +$redis = RedisManager::getInstance(); + +// 获取到`$redis`返回值为实现`Imi\Redis\Handler\IRedisHandler`的具体驱动 +// 建议根据实际情况使用注解或强类型把`$redis`的类型限制为`Imi\Redis\Handler\IRedisHandler`具体实现驱动以活动更好的`IDE`提示支持 +// 具体驱动有: +// \Imi\Redis\Handler\PhpRedisHandler +// \Imi\Redis\Handler\PhpRedisClusterHandler +// \Imi\Redis\Handler\PredisHandler +// \Imi\Redis\Handler\PredisClusterHandler + +$redis->set('imi:redis:test', date('Y-m-d H:i:s')); +$datetime = $redis->get('imi:redis:test'); +``` + +### 获取新连接对象 + +每次调用都尝试从连接池中获取新的对象! + +```php +use \Imi\Redis\RedisManager; +$redis = RedisManager::getNewInstance(); +$redis->get('key-xxx') +``` + +### 获取默认连接池名称 + +```php +use \Imi\Redis\RedisManager; +echo RedisManager::getDefaultPoolName(); +``` + +### 便捷操作(不建议使用) + +> **不建议使用该模式,`ide`提示无法完善** + +`Redis::方法名()` + +```php +use \Imi\Redis\Redis; +Redis::set('imi:redis:test', date('Y-m-d H:i:s')); +$datetime = Redis::get('imi:redis:test'); +``` + +### 回调方式使用`Redis` + +```php +use \Imi\Redis\Redis; +$result = Redis::use(function(Imi\Redis\Handler\IRedisHandler $redis){ + $redis->set('a', 1); + return true; +}); // true +``` + +## 进阶使用 + +### evalEx + +imi 封装了一个基于 `evalSha` 和 `eval` 的便捷方法,优先使用 `evalSha` 尝试,失败则使用 `eval` 方法。 + +定义:`public function evalEx($script, $args = null, $num_keys = null)` + +```php +use \Imi\Redis\RedisManager; +/** @var \Imi\Redis\Handler\PhpRedisHandler $redis */ +$redis = RedisManager::getInstance(); +return false !== $redis->evalEx(<<