PHP code example of qkskima / model

1. Go to this page and download the library: Download qkskima/model library. Choose the download type require.

2. Extract the ZIP file and open the index.php.

3. Add this code to the index.php.
    
        
<?php
require_once('vendor/autoload.php');

/* Start to develop here. Best regards https://php-download.com/ */

    

qkskima / model example snippets


use QkSkima\Model\BaseModel;
use Symfony\Component\Validator\Constraints as Assert;

class Order extends BaseModel
{
    protected const TABLE = 'tx_sitepackage_orders';
    
    #[Assert\NotBlank]
    public ?string $orderNumber = null;
    
    #[Assert\Email]
    public ?string $customerEmail = null;
    
    #[Assert\Valid]
    public array $orderItems = [];
    
    protected function getRelations(): array
    {
        return [
            'orderItems' => [
                'class' => OrderItem::class,
                'type' => 'many'
            ]
        ];
    }
    
    protected function getBusinessRules(): array
    {
        return [
            new OrderDateBusinessRule(),
            new OrderTotalBusinessRule(),
        ];
    }
}

// Method 1: Create with validation and save
$order = Order::create($formData);

// Method 2: Create, validate, and save separately
$order = Order::fromArray($formData);
if ($order->validate()) {
    $order->save();
}

$order = Order::find(123);
$order->update([
    'status' => 'completed',
    'customerName' => 'Updated Name'
]);

$order = Order::find(123);
$order->destroy();

$order = Order::create($formData);

if ($order->hasErrors()) {
    $errors = $order->getErrors();
    
    // Structure:
    // [
    //     'customerEmail' => ['Invalid email address'],
    //     'orderItems.0.startDate' => ['Start date must be in the future'],
    //     'totalAmount' => ['Total amount does not match']
    // ]
}

$formData = [
    'orderNumber' => 'ORD-001',
    'customerEmail' => '[email protected]',
    'orderItems' => [
        [
            'productName' => 'Widget A',
            'quantity' => 2,
            'unitPrice' => 50.00
        ],
        [
            'productName' => 'Widget B',
            'quantity' => 1,
            'unitPrice' => 30.00
        ]
    ]
];

$order = Order::fromArray($formData);
// orderItems are automatically converted to OrderItem instances
// and validated recursively

class OrderDateBusinessRule implements BusinessRuleInterface
{
    public function getName(): string
    {
        return 'order_date_validation';
    }
    
    public function validate(BaseModel $model): BusinessRuleResult
    {
        $result = BusinessRuleResult::success();
        
        if (!$model instanceof Order) {
            return $result;
        }
        
        $orderDateTime = new \DateTime($model->orderDate);
        $now = new \DateTime();
        
        if ($orderDateTime > $now) {
            $result->addViolation(
                'orderDate',
                'Order date cannot be in the future'
            );
        }
        
        return $result;
    }
}

public function validate(BaseModel $model): BusinessRuleResult
{
    $result = BusinessRuleResult::success();
    
    // Validate nested order items
    foreach ($model->orderItems as $index => $item) {
        if ($item->startDate < new \DateTime()) {
            $result->addViolation(
                "orderItems.{$index}.startDate",
                'Start date must be in the future'
            );
        }
    }
    
    return $result;
}

public static function find(int $uid): ?self
{
    $queryBuilder = GeneralUtility::makeInstance(ConnectionPool::class)
        ->getQueryBuilderForTable(self::TABLE);
    
    $row = $queryBuilder
        ->select('*')
        ->from(self::TABLE)
        ->where(
            $queryBuilder->expr()->eq('uid', $uid)
        )
        ->executeQuery()
        ->fetchAssociative();
    
    return $row ? self::fromArray($row) : null;
}

[
    'customerEmail' => ['Invalid email address'],
    'totalAmount' => ['Must be positive', 'Does not match total'],
    'orderItems.0.quantity' => ['Must be positive'],
    'orderItems.1.startDate' => ['Start date must be in the future']
]

class UniqueOrderNumberRule implements BusinessRuleInterface
{
    public function validate(BaseModel $model): BusinessRuleResult
    {
        $result = BusinessRuleResult::success();
        
        if (!$model instanceof Order) {
            return $result;
        }
        
        $queryBuilder = GeneralUtility::makeInstance(ConnectionPool::class)
            ->getQueryBuilderForTable('tx_sitepackage_orders');
        
        $count = $queryBuilder
            ->count('uid')
            ->from('tx_sitepackage_orders')
            ->where(
                $queryBuilder->expr()->eq(
                    'order_number',
                    $queryBuilder->createNamedParameter($model->orderNumber)
                ),
                $queryBuilder->expr()->neq(
                    'uid',
                    $queryBuilder->createNamedParameter($model->uid ?? 0)
                )
            )
            ->executeQuery()
            ->fetchOne();
        
        if ($count > 0) {
            $result->addViolation(
                'orderNumber',
                'This order number already exists'
            );
        }
        
        return $result;
    }
}