Add employee-to-order assignments with FR-EM-3 conflict validation
Docker-Images bauen und veröffentlichen / build (, omsorgCore/Dockerfile, omsorgcore) (push) Successful in 17s
Docker-Images bauen und veröffentlichen / build (, omsorgWeb/Dockerfile, omsorgweb) (push) Successful in 6s
Docker-Images bauen und veröffentlichen / build (, omsorgapp/Dockerfile, omsorgapp) (push) Successful in 17s

Adds the Assignment core object (Order x Employee, date range) with full
CRUD, soft-delete/trash integration, and generated API clients.

Layers FR-EM-3 conflict checks onto assignment creation: qualification,
absence/availability, working-hours approximation, cross-order overlap,
and active-contract coverage. Each check's severity (Warning vs. Error)
is configurable at runtime via a new AssignmentValidationSettings
singleton and admin settings panel, instead of being hardcoded - lets
the business tune strictness per check without a redeploy.

Adds a live GET /api/assignments/check endpoint so the create-assignment
dialog can preview conflicts as the user picks employee/dates, before
they hit save, rather than only finding out after submitting.

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
This commit is contained in:
Felix Kemmler
2026-08-11 00:44:14 +02:00
co-authored by Claude Sonnet 5
parent fcbf27db3c
commit dfeb37cf33
104 changed files with 15846 additions and 7 deletions
@@ -0,0 +1,97 @@
<?php
/**
* AssignmentValidationSettingsApiTest
* PHP version 8.1
*
* @category Class
* @package OmsorgCoreClient
* @author OpenAPI Generator team
* @link https://openapi-generator.tech
*/
/**
* OmsorgCore.Api
*
* No description provided (generated by Openapi Generator https://github.com/openapitools/openapi-generator)
*
* The version of the OpenAPI document: 1.0
* Generated by: https://openapi-generator.tech
* Generator version: 7.14.0
*/
/**
* NOTE: This class is auto generated by OpenAPI Generator (https://openapi-generator.tech).
* https://openapi-generator.tech
* Please update the test case below to test the endpoint.
*/
namespace OmsorgCoreClient\Test\Api;
use \OmsorgCoreClient\Configuration;
use \OmsorgCoreClient\ApiException;
use \OmsorgCoreClient\ObjectSerializer;
use PHPUnit\Framework\TestCase;
/**
* AssignmentValidationSettingsApiTest Class Doc Comment
*
* @category Class
* @package OmsorgCoreClient
* @author OpenAPI Generator team
* @link https://openapi-generator.tech
*/
class AssignmentValidationSettingsApiTest extends TestCase
{
/**
* Setup before running any test cases
*/
public static function setUpBeforeClass(): void
{
}
/**
* Setup before running each test case
*/
public function setUp(): void
{
}
/**
* Clean up after running each test case
*/
public function tearDown(): void
{
}
/**
* Clean up after running all test cases
*/
public static function tearDownAfterClass(): void
{
}
/**
* Test case for apiSettingsAssignmentValidationGet
*
* .
*
*/
public function testApiSettingsAssignmentValidationGet()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
/**
* Test case for apiSettingsAssignmentValidationPut
*
* .
*
*/
public function testApiSettingsAssignmentValidationPut()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
}
@@ -0,0 +1,133 @@
<?php
/**
* AssignmentsApiTest
* PHP version 8.1
*
* @category Class
* @package OmsorgCoreClient
* @author OpenAPI Generator team
* @link https://openapi-generator.tech
*/
/**
* OmsorgCore.Api
*
* No description provided (generated by Openapi Generator https://github.com/openapitools/openapi-generator)
*
* The version of the OpenAPI document: 1.0
* Generated by: https://openapi-generator.tech
* Generator version: 7.14.0
*/
/**
* NOTE: This class is auto generated by OpenAPI Generator (https://openapi-generator.tech).
* https://openapi-generator.tech
* Please update the test case below to test the endpoint.
*/
namespace OmsorgCoreClient\Test\Api;
use \OmsorgCoreClient\Configuration;
use \OmsorgCoreClient\ApiException;
use \OmsorgCoreClient\ObjectSerializer;
use PHPUnit\Framework\TestCase;
/**
* AssignmentsApiTest Class Doc Comment
*
* @category Class
* @package OmsorgCoreClient
* @author OpenAPI Generator team
* @link https://openapi-generator.tech
*/
class AssignmentsApiTest extends TestCase
{
/**
* Setup before running any test cases
*/
public static function setUpBeforeClass(): void
{
}
/**
* Setup before running each test case
*/
public function setUp(): void
{
}
/**
* Clean up after running each test case
*/
public function tearDown(): void
{
}
/**
* Clean up after running all test cases
*/
public static function tearDownAfterClass(): void
{
}
/**
* Test case for apiAssignmentsGet
*
* .
*
*/
public function testApiAssignmentsGet()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
/**
* Test case for apiAssignmentsIdDelete
*
* .
*
*/
public function testApiAssignmentsIdDelete()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
/**
* Test case for apiAssignmentsIdGet
*
* .
*
*/
public function testApiAssignmentsIdGet()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
/**
* Test case for apiAssignmentsIdPut
*
* .
*
*/
public function testApiAssignmentsIdPut()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
/**
* Test case for apiAssignmentsPost
*
* .
*
*/
public function testApiAssignmentsPost()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
}
@@ -0,0 +1,108 @@
<?php
/**
* AssignmentConflictResponseTest
*
* PHP version 8.1
*
* @category Class
* @package OmsorgCoreClient
* @author OpenAPI Generator team
* @link https://openapi-generator.tech
*/
/**
* OmsorgCore.Api
*
* No description provided (generated by Openapi Generator https://github.com/openapitools/openapi-generator)
*
* The version of the OpenAPI document: 1.0
* Generated by: https://openapi-generator.tech
* Generator version: 7.14.0
*/
/**
* NOTE: This class is auto generated by OpenAPI Generator (https://openapi-generator.tech).
* https://openapi-generator.tech
* Please update the test case below to test the model.
*/
namespace OmsorgCoreClient\Test\Model;
use PHPUnit\Framework\TestCase;
/**
* AssignmentConflictResponseTest Class Doc Comment
*
* @category Class
* @description AssignmentConflictResponse
* @package OmsorgCoreClient
* @author OpenAPI Generator team
* @link https://openapi-generator.tech
*/
class AssignmentConflictResponseTest extends TestCase
{
/**
* Setup before running any test case
*/
public static function setUpBeforeClass(): void
{
}
/**
* Setup before running each test case
*/
public function setUp(): void
{
}
/**
* Clean up after running each test case
*/
public function tearDown(): void
{
}
/**
* Clean up after running all test cases
*/
public static function tearDownAfterClass(): void
{
}
/**
* Test "AssignmentConflictResponse"
*/
public function testAssignmentConflictResponse()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
/**
* Test attribute "type"
*/
public function testPropertyType()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
/**
* Test attribute "severity"
*/
public function testPropertySeverity()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
/**
* Test attribute "message"
*/
public function testPropertyMessage()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
}
@@ -0,0 +1,117 @@
<?php
/**
* AssignmentResponsePagedResponseTest
*
* PHP version 8.1
*
* @category Class
* @package OmsorgCoreClient
* @author OpenAPI Generator team
* @link https://openapi-generator.tech
*/
/**
* OmsorgCore.Api
*
* No description provided (generated by Openapi Generator https://github.com/openapitools/openapi-generator)
*
* The version of the OpenAPI document: 1.0
* Generated by: https://openapi-generator.tech
* Generator version: 7.14.0
*/
/**
* NOTE: This class is auto generated by OpenAPI Generator (https://openapi-generator.tech).
* https://openapi-generator.tech
* Please update the test case below to test the model.
*/
namespace OmsorgCoreClient\Test\Model;
use PHPUnit\Framework\TestCase;
/**
* AssignmentResponsePagedResponseTest Class Doc Comment
*
* @category Class
* @description AssignmentResponsePagedResponse
* @package OmsorgCoreClient
* @author OpenAPI Generator team
* @link https://openapi-generator.tech
*/
class AssignmentResponsePagedResponseTest extends TestCase
{
/**
* Setup before running any test case
*/
public static function setUpBeforeClass(): void
{
}
/**
* Setup before running each test case
*/
public function setUp(): void
{
}
/**
* Clean up after running each test case
*/
public function tearDown(): void
{
}
/**
* Clean up after running all test cases
*/
public static function tearDownAfterClass(): void
{
}
/**
* Test "AssignmentResponsePagedResponse"
*/
public function testAssignmentResponsePagedResponse()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
/**
* Test attribute "items"
*/
public function testPropertyItems()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
/**
* Test attribute "total_count"
*/
public function testPropertyTotalCount()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
/**
* Test attribute "page"
*/
public function testPropertyPage()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
/**
* Test attribute "page_size"
*/
public function testPropertyPageSize()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
}
@@ -0,0 +1,153 @@
<?php
/**
* AssignmentResponseTest
*
* PHP version 8.1
*
* @category Class
* @package OmsorgCoreClient
* @author OpenAPI Generator team
* @link https://openapi-generator.tech
*/
/**
* OmsorgCore.Api
*
* No description provided (generated by Openapi Generator https://github.com/openapitools/openapi-generator)
*
* The version of the OpenAPI document: 1.0
* Generated by: https://openapi-generator.tech
* Generator version: 7.14.0
*/
/**
* NOTE: This class is auto generated by OpenAPI Generator (https://openapi-generator.tech).
* https://openapi-generator.tech
* Please update the test case below to test the model.
*/
namespace OmsorgCoreClient\Test\Model;
use PHPUnit\Framework\TestCase;
/**
* AssignmentResponseTest Class Doc Comment
*
* @category Class
* @description AssignmentResponse
* @package OmsorgCoreClient
* @author OpenAPI Generator team
* @link https://openapi-generator.tech
*/
class AssignmentResponseTest extends TestCase
{
/**
* Setup before running any test case
*/
public static function setUpBeforeClass(): void
{
}
/**
* Setup before running each test case
*/
public function setUp(): void
{
}
/**
* Clean up after running each test case
*/
public function tearDown(): void
{
}
/**
* Clean up after running all test cases
*/
public static function tearDownAfterClass(): void
{
}
/**
* Test "AssignmentResponse"
*/
public function testAssignmentResponse()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
/**
* Test attribute "id"
*/
public function testPropertyId()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
/**
* Test attribute "order_id"
*/
public function testPropertyOrderId()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
/**
* Test attribute "employee_id"
*/
public function testPropertyEmployeeId()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
/**
* Test attribute "employee_first_name"
*/
public function testPropertyEmployeeFirstName()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
/**
* Test attribute "employee_last_name"
*/
public function testPropertyEmployeeLastName()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
/**
* Test attribute "start_date"
*/
public function testPropertyStartDate()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
/**
* Test attribute "end_date"
*/
public function testPropertyEndDate()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
/**
* Test attribute "note"
*/
public function testPropertyNote()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
}
@@ -0,0 +1,126 @@
<?php
/**
* AssignmentValidationSettingsResponseTest
*
* PHP version 8.1
*
* @category Class
* @package OmsorgCoreClient
* @author OpenAPI Generator team
* @link https://openapi-generator.tech
*/
/**
* OmsorgCore.Api
*
* No description provided (generated by Openapi Generator https://github.com/openapitools/openapi-generator)
*
* The version of the OpenAPI document: 1.0
* Generated by: https://openapi-generator.tech
* Generator version: 7.14.0
*/
/**
* NOTE: This class is auto generated by OpenAPI Generator (https://openapi-generator.tech).
* https://openapi-generator.tech
* Please update the test case below to test the model.
*/
namespace OmsorgCoreClient\Test\Model;
use PHPUnit\Framework\TestCase;
/**
* AssignmentValidationSettingsResponseTest Class Doc Comment
*
* @category Class
* @description AssignmentValidationSettingsResponse
* @package OmsorgCoreClient
* @author OpenAPI Generator team
* @link https://openapi-generator.tech
*/
class AssignmentValidationSettingsResponseTest extends TestCase
{
/**
* Setup before running any test case
*/
public static function setUpBeforeClass(): void
{
}
/**
* Setup before running each test case
*/
public function setUp(): void
{
}
/**
* Clean up after running each test case
*/
public function tearDown(): void
{
}
/**
* Clean up after running all test cases
*/
public static function tearDownAfterClass(): void
{
}
/**
* Test "AssignmentValidationSettingsResponse"
*/
public function testAssignmentValidationSettingsResponse()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
/**
* Test attribute "qualification_mode"
*/
public function testPropertyQualificationMode()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
/**
* Test attribute "absence_mode"
*/
public function testPropertyAbsenceMode()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
/**
* Test attribute "working_hours_mode"
*/
public function testPropertyWorkingHoursMode()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
/**
* Test attribute "overlap_mode"
*/
public function testPropertyOverlapMode()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
/**
* Test attribute "contract_mode"
*/
public function testPropertyContractMode()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
}
@@ -0,0 +1,126 @@
<?php
/**
* CreateAssignmentRequestTest
*
* PHP version 8.1
*
* @category Class
* @package OmsorgCoreClient
* @author OpenAPI Generator team
* @link https://openapi-generator.tech
*/
/**
* OmsorgCore.Api
*
* No description provided (generated by Openapi Generator https://github.com/openapitools/openapi-generator)
*
* The version of the OpenAPI document: 1.0
* Generated by: https://openapi-generator.tech
* Generator version: 7.14.0
*/
/**
* NOTE: This class is auto generated by OpenAPI Generator (https://openapi-generator.tech).
* https://openapi-generator.tech
* Please update the test case below to test the model.
*/
namespace OmsorgCoreClient\Test\Model;
use PHPUnit\Framework\TestCase;
/**
* CreateAssignmentRequestTest Class Doc Comment
*
* @category Class
* @description CreateAssignmentRequest
* @package OmsorgCoreClient
* @author OpenAPI Generator team
* @link https://openapi-generator.tech
*/
class CreateAssignmentRequestTest extends TestCase
{
/**
* Setup before running any test case
*/
public static function setUpBeforeClass(): void
{
}
/**
* Setup before running each test case
*/
public function setUp(): void
{
}
/**
* Clean up after running each test case
*/
public function tearDown(): void
{
}
/**
* Clean up after running all test cases
*/
public static function tearDownAfterClass(): void
{
}
/**
* Test "CreateAssignmentRequest"
*/
public function testCreateAssignmentRequest()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
/**
* Test attribute "order_id"
*/
public function testPropertyOrderId()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
/**
* Test attribute "employee_id"
*/
public function testPropertyEmployeeId()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
/**
* Test attribute "start_date"
*/
public function testPropertyStartDate()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
/**
* Test attribute "end_date"
*/
public function testPropertyEndDate()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
/**
* Test attribute "note"
*/
public function testPropertyNote()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
}
@@ -0,0 +1,117 @@
<?php
/**
* TrashAssignmentResponseTest
*
* PHP version 8.1
*
* @category Class
* @package OmsorgCoreClient
* @author OpenAPI Generator team
* @link https://openapi-generator.tech
*/
/**
* OmsorgCore.Api
*
* No description provided (generated by Openapi Generator https://github.com/openapitools/openapi-generator)
*
* The version of the OpenAPI document: 1.0
* Generated by: https://openapi-generator.tech
* Generator version: 7.14.0
*/
/**
* NOTE: This class is auto generated by OpenAPI Generator (https://openapi-generator.tech).
* https://openapi-generator.tech
* Please update the test case below to test the model.
*/
namespace OmsorgCoreClient\Test\Model;
use PHPUnit\Framework\TestCase;
/**
* TrashAssignmentResponseTest Class Doc Comment
*
* @category Class
* @description TrashAssignmentResponse
* @package OmsorgCoreClient
* @author OpenAPI Generator team
* @link https://openapi-generator.tech
*/
class TrashAssignmentResponseTest extends TestCase
{
/**
* Setup before running any test case
*/
public static function setUpBeforeClass(): void
{
}
/**
* Setup before running each test case
*/
public function setUp(): void
{
}
/**
* Clean up after running each test case
*/
public function tearDown(): void
{
}
/**
* Clean up after running all test cases
*/
public static function tearDownAfterClass(): void
{
}
/**
* Test "TrashAssignmentResponse"
*/
public function testTrashAssignmentResponse()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
/**
* Test attribute "id"
*/
public function testPropertyId()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
/**
* Test attribute "employee_first_name"
*/
public function testPropertyEmployeeFirstName()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
/**
* Test attribute "employee_last_name"
*/
public function testPropertyEmployeeLastName()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
/**
* Test attribute "deleted_at"
*/
public function testPropertyDeletedAt()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
}
@@ -0,0 +1,90 @@
<?php
/**
* UpdateAssignmentRequestTest
*
* PHP version 8.1
*
* @category Class
* @package OmsorgCoreClient
* @author OpenAPI Generator team
* @link https://openapi-generator.tech
*/
/**
* OmsorgCore.Api
*
* No description provided (generated by Openapi Generator https://github.com/openapitools/openapi-generator)
*
* The version of the OpenAPI document: 1.0
* Generated by: https://openapi-generator.tech
* Generator version: 7.14.0
*/
/**
* NOTE: This class is auto generated by OpenAPI Generator (https://openapi-generator.tech).
* https://openapi-generator.tech
* Please update the test case below to test the model.
*/
namespace OmsorgCoreClient\Test\Model;
use PHPUnit\Framework\TestCase;
/**
* UpdateAssignmentRequestTest Class Doc Comment
*
* @category Class
* @description UpdateAssignmentRequest
* @package OmsorgCoreClient
* @author OpenAPI Generator team
* @link https://openapi-generator.tech
*/
class UpdateAssignmentRequestTest extends TestCase
{
/**
* Setup before running any test case
*/
public static function setUpBeforeClass(): void
{
}
/**
* Setup before running each test case
*/
public function setUp(): void
{
}
/**
* Clean up after running each test case
*/
public function tearDown(): void
{
}
/**
* Clean up after running all test cases
*/
public static function tearDownAfterClass(): void
{
}
/**
* Test "UpdateAssignmentRequest"
*/
public function testUpdateAssignmentRequest()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
/**
* Test attribute "note"
*/
public function testPropertyNote()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
}
@@ -0,0 +1,126 @@
<?php
/**
* UpdateAssignmentValidationSettingsRequestTest
*
* PHP version 8.1
*
* @category Class
* @package OmsorgCoreClient
* @author OpenAPI Generator team
* @link https://openapi-generator.tech
*/
/**
* OmsorgCore.Api
*
* No description provided (generated by Openapi Generator https://github.com/openapitools/openapi-generator)
*
* The version of the OpenAPI document: 1.0
* Generated by: https://openapi-generator.tech
* Generator version: 7.14.0
*/
/**
* NOTE: This class is auto generated by OpenAPI Generator (https://openapi-generator.tech).
* https://openapi-generator.tech
* Please update the test case below to test the model.
*/
namespace OmsorgCoreClient\Test\Model;
use PHPUnit\Framework\TestCase;
/**
* UpdateAssignmentValidationSettingsRequestTest Class Doc Comment
*
* @category Class
* @description UpdateAssignmentValidationSettingsRequest
* @package OmsorgCoreClient
* @author OpenAPI Generator team
* @link https://openapi-generator.tech
*/
class UpdateAssignmentValidationSettingsRequestTest extends TestCase
{
/**
* Setup before running any test case
*/
public static function setUpBeforeClass(): void
{
}
/**
* Setup before running each test case
*/
public function setUp(): void
{
}
/**
* Clean up after running each test case
*/
public function tearDown(): void
{
}
/**
* Clean up after running all test cases
*/
public static function tearDownAfterClass(): void
{
}
/**
* Test "UpdateAssignmentValidationSettingsRequest"
*/
public function testUpdateAssignmentValidationSettingsRequest()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
/**
* Test attribute "qualification_mode"
*/
public function testPropertyQualificationMode()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
/**
* Test attribute "absence_mode"
*/
public function testPropertyAbsenceMode()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
/**
* Test attribute "working_hours_mode"
*/
public function testPropertyWorkingHoursMode()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
/**
* Test attribute "overlap_mode"
*/
public function testPropertyOverlapMode()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
/**
* Test attribute "contract_mode"
*/
public function testPropertyContractMode()
{
// TODO: implement
self::markTestIncomplete('Not implemented');
}
}