Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
97 changes: 97 additions & 0 deletions .github/workflows/ci-linux.yml
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,9 @@ concurrency:
group: "${{ github.workflow }}-${{ github.ref }}"
cancel-in-progress: true

permissions:
contents: read

jobs:
setup-phpunit-matrix:
runs-on: ubuntu-latest
Expand Down Expand Up @@ -203,3 +206,97 @@ jobs:
run: |
cd galette-core/galette/plugins/plugin-auto
../../vendor/bin/phpunit --test-suffix=.php --bootstrap tests/TestsBootstrap.php --no-coverage --process-isolation tests/GaletteAuto/

upgrade:
runs-on: ubuntu-latest

strategy:
matrix:
db-image: ['mysql:8.4', 'mariadb:11', 'postgres:17']
fail-fast: false

env:
DB: ${{ matrix.db-image }}

services:
# Label used to access the service container
db:
# Docker Hub image
image: ${{ matrix.db-image }}
# Provide env variables for both mysql and pgsql
env:
POSTGRES_USER: galette_tests
POSTGRES_PASSWORD: g@l3tte
POSTGRES_DB: galette_tests
MYSQL_USER: galette_tests
MYSQL_PASSWORD: g@l3tte
MYSQL_ROOT_PASSWORD: g@l3tte
MYSQL_DATABASE: galette_tests
# Open network ports for both mysql and pgsql
ports:
- 3306:3306
- 5432:5432
# Set health checks to wait until postgres has started
options: >-
--health-cmd="bash -c 'if [[ -n $(command -v pg_isready) ]]; then pg_isready; else if [[ -n $(command -v mysqladmin) ]]; then mysqladmin ping; else mariadb-admin ping; fi fi'"
--health-interval=10s
--health-timeout=5s
--health-retries=10

name: Upgrade from previous release on ${{ matrix.db-image }}

steps:
- name: PHP
uses: shivammathur/setup-php@v2
with:
php-version: '8.4'
tools: composer, pecl
coverage: none
extensions: apcu
ini-values: apc.enable_cli=1

- name: Build Galette
uses: galette/.github/actions/build-galette@main
with:
php-version: '8.4'

- name: Checkout plugin
uses: actions/checkout@v7
with:
path: galette-core/galette/plugins/plugin-auto
fetch-depth: 0

- name: Find previous release
run: |
cd galette-core/galette/plugins/plugin-auto
echo "PREVIOUS_RELEASE=$(git tag --list '[0-9]*' --sort=-v:refname --no-contains HEAD | head -n1)" >> $GITHUB_ENV

- name: Install previous release for PostgreSQL
env:
PGPASSWORD: g@l3tte
run: |
cd galette-core
bin/console galette:install -v --dbtype=pgsql --dbhost=localhost --dbname=galette_tests --dbuser=galette_tests --dbpass=g@l3tte --admin=admin --password=admin --no-interaction -w
git -C galette/plugins/plugin-auto show "$PREVIOUS_RELEASE:scripts/pgsql.sql" \
| psql -v ON_ERROR_STOP=1 -h localhost -U galette_tests galette_tests
if: startsWith(matrix.db-image, 'postgres')

- name: Install previous release for MariaDB
run: |
cd galette-core
mysql -e 'create database IF NOT EXISTS galette_tests;' -u galette_tests --password=g@l3tte -h 127.0.0.1 -P 3306
bin/console galette:install -v --dbtype=mysql --dbhost=127.0.0.1 --dbname=galette_tests --dbuser=galette_tests --dbpass=g@l3tte --admin=admin --password=admin --no-interaction -w
git -C galette/plugins/plugin-auto show "$PREVIOUS_RELEASE:scripts/mysql.sql" \
| mysql -u galette_tests --password=g@l3tte -h 127.0.0.1 -P 3306 galette_tests
if: startsWith(matrix.db-image, 'mysql') || startsWith(matrix.db-image, 'mariadb')

- name: Upgrade
run: |
cd galette-core
bin/console galette:plugins:install-db --no-interaction plugin-auto | tee upgrade.log
grep -q 'Database for plugin "plugin-auto" upgraded' upgrade.log

- name: Unit tests
run: |
cd galette-core/galette/plugins/plugin-auto
../../vendor/bin/phpunit --test-suffix=.php --bootstrap tests/TestsBootstrap.php --no-coverage --process-isolation tests/GaletteAuto/
Comment thread
github-advanced-security[bot] marked this conversation as resolved.
Fixed
2 changes: 1 addition & 1 deletion _define.php
Original file line number Diff line number Diff line change
Expand Up @@ -61,5 +61,5 @@
'autoPreferences' => 'admin',
'storeAutoPreferences' => 'admin'
],
dbver: 1.00
dbver: 1.1
);
55 changes: 55 additions & 0 deletions lib/GaletteAuto/PluginEventProvider.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,55 @@
<?php

/**
* This file is part of Galette Auto plugin (https://galette.eu).
* SPDX-FileCopyrightText: Copyright © 2009-2026 The Galette Team
* SPDX-License-Identifier: GPL-3.0-or-later
*/

declare(strict_types=1);

namespace GaletteAuto;

use Galette\Entity\Adherent;
use Galette\Events\GaletteEvent;
use GaletteAuto\Repository\Vehicles;
use League\Event\ListenerRegistry;
use League\Event\ListenerSubscriber;
use Psr\Container\ContainerInterface;

/**
* Auto listeners on core events
*
* @author Johan Cwiklinski <johan@x-tnd.be>
*/
class PluginEventProvider implements ListenerSubscriber
{
/**
* Constructor
*
* Built while plugins are loaded: the vehicles repository is resolved
* only when an event is emitted.
*
* @param ContainerInterface $container Container
*/
public function __construct(private readonly ContainerInterface $container)
{
}

/**
* Set up listeners
*
* @param ListenerRegistry $acceptor Listener
*/
public function subscribeListeners(ListenerRegistry $acceptor): void
{
$acceptor->subscribeTo(
'member.before_remove',
function (GaletteEvent $event): void {
/** @var \ArrayObject<string, mixed> $member */
$member = $event->getObject();
$this->container->get(Vehicles::class)->removeForMember((int)$member[Adherent::PK]);
}
);
}
}
19 changes: 19 additions & 0 deletions lib/GaletteAuto/PluginGaletteAuto.php
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,8 @@
use Galette\Core\Plugins\PublicPagesProviderInterface;
use Galette\Entity\Adherent;
use Galette\Core\GalettePlugin;
use Laminas\Db\Metadata\Object\ConstraintObject;
use Laminas\Db\Metadata\Source\Factory;

/**
* Galette Auto plugin main class
Expand Down Expand Up @@ -270,4 +272,21 @@ public function isInstalled(): bool
&& $this->zdb->tableExists(AUTO_PREFIX . Transmission::TABLE)
;
}

/**
* Version of tables installed before plugins versions were recorded
*
* Vehicles of a removed member are removed along since 1.1.
*/
public function getLegacyDbVersion(): ?float
{
$metadata = Factory::createSourceFromAdapter($this->zdb->db);
/** @var ConstraintObject $constraint */
foreach ($metadata->getConstraints(PREFIX_DB . AUTO_PREFIX . Auto::TABLE) as $constraint) {
if ($constraint->isForeignKey() && $constraint->getColumns() === [Adherent::PK]) {
return $constraint->getDeleteRule() === 'CASCADE' ? null : 1.0;
}
}
return null;
}
}
49 changes: 49 additions & 0 deletions lib/GaletteAuto/Repository/Vehicles.php
Original file line number Diff line number Diff line change
Expand Up @@ -294,6 +294,55 @@ public function remove(array $ids): void
}
}

/**
* Remove a member's vehicles, with their history and photos
*
* Member is also dropped from the history of vehicles they formerly
* owned: they are part of its primary key.
*
* @param int $id_adh Member ID
*
* @throws \Throwable
*/
public function removeForMember(int $id_adh): void
{
$transaction = !$this->zdb->inTransaction();

try {
if ($transaction) {
$this->zdb->beginTransaction();
}

$select = $this->zdb->select(AUTO_PREFIX . Auto::TABLE);
$select->columns([Auto::PK])->where([Adherent::PK => $id_adh]);
$ids = array_map(
fn($row) => (int)$row[Auto::PK],
$this->zdb->execute($select)->toArray()
);

if (count($ids) > 0) {
$this->remove($ids);
}

$delete = $this->zdb->delete(AUTO_PREFIX . History::TABLE);
$delete->where([Adherent::PK => $id_adh]);
$this->zdb->execute($delete);

if ($transaction) {
$this->zdb->commit();
}
} catch (\Throwable $e) {
if ($transaction) {
$this->zdb->rollback();
}
Analog::log(
'[' . static::class . '] Cannot remove vehicles of member #' . $id_adh . ' | ' . $e->getMessage(),
Analog::ERROR
);
throw $e;
}
}

/**
* Build vehicles select, joining their properties
*/
Expand Down
Loading
Loading