Files
Christoph Schwörer f045b99a25 Codebasis als Dateien ins Arbeitsrepo statt als Gitlink
QuellCode/CentronERP war nur als Gitlink (Submodul-Referenz auf 79c1142)
getrackt, ohne .gitmodules und ohne erreichbares Remote. Der
Untersuchungsgegenstand der Versuchsreihe war damit nicht reproduzierbar
gesichert: Ein Klon haette ein leeres Verzeichnis erhalten, und die Belege
der 3.287 Anforderungen waeren nicht ueberpruefbar gewesen.

Umstellung:
- Historie nach c:\DEV\CentronERP_git_snapshot_79c1142 ausgelagert
  (vollstaendig lesbar, enthaelt 79c1142 und Vorgaenger 89ccfd6)
- Gitlink aus dem Index entfernt
- Dateiinhalt aufgenommen: 24.557 Dateien, rund 333 MB

Die verschachtelte .gitignore der Codebasis gilt weiter, Build-Artefakte
bleiben ausgeschlossen. Details in Versuche/Versuch_01/_Codebasis-Nachweis.md
2026-08-26 07:43:51 +02:00

18 KiB

Receipts Backend Architecture

This document describes the generic architecture and components of the receipts system in the c-entron.NET backend, which provides a unified foundation for all receipt types including offers, orders, delivery lists, invoices, contracts, and credit vouchers.

Overview

The receipts system follows a layered architecture pattern with a shared base implementation that is extended by specific receipt types. All receipt types inherit from common base classes and share fundamental operations while providing specialized functionality through their own business logic classes.

Core Components

Entity Layer

ReceiptBase Abstract Class

Location: src/backend/Centron.Entities/Entities/Sales/Receipts/ReceiptBase.cs

The ReceiptBase abstract class serves as the foundation for all receipt entities in the system. It inherits from BaseEntity and implements the IReceiptBase interface.

Key Properties:

  • Receipt Header Information: Number, Date, Version, State, Editor
  • Branch Information: BranchI3D, BranchOrigin
  • Currency Information: CurrencyI3D, CurrencyFactor, CurrencyString, ExclusiveOfVAT
  • Contact Information: Receiver, Phone, Fax, Email
  • Address Information: AddressI3D, ContactPersonI3D, Street, PostOfficeBox, Zip, City, ContactName, CountryI3D
  • Audit Fields: CreatedByI3D, CreatedAt, ChangedByI3D, ChangedAt, Application Version tracking
  • System Fields: ConcurrencyControlGuid, CustomUpdateArticlePricesAndTexts

Abstract Methods:

  • ReceiptKind: Returns the specific receipt type (CentronObjectKindNumeric)
  • GetReceiptItems(): Returns all receipt items
  • SetReceiptItems(): Sets receipt items collection
  • AddItem(): Adds a new item to the receipt
  • RemoveItem(): Removes an item from the receipt

Receipt Types Hierarchy

All receipt types extend ReceiptBase and follow a consistent pattern of entity classes, database tables, and views:

Receipt Type Entity Class Database Table Database View Items Table Items View
Offers ReceiptOffer AngKopf Offers AngPos OfferItems
Orders ReceiptOrder AufKopf Orders AufPos OrderItems
Delivery Lists ReceiptDeliveryList LiefKopf DeliveryLists LiefPos DeliveryListItems
Invoices ReceiptInvoice RechKopf Invoices RechPos InvoiceItems
Contracts ReceiptContract VertragKopf Contracts VertragPos ContractItems
Credit Vouchers ReceiptCreditVoucher GutKopf CreditVouchers GutPos CreditVoucherItems
Pickup Lists ReceiptPickupList AbholKopf PickupLists AbholPos PickupListItems

Entity Locations:

  • src/backend/Centron.Entities/Entities/Sales/Receipts/Offers/ReceiptOffer.cs
  • src/backend/Centron.Entities/Entities/Sales/Receipts/Orders/ReceiptOrder.cs
  • src/backend/Centron.Entities/Entities/Sales/Receipts/DeliveryLists/ReceiptDeliveryList.cs
  • src/backend/Centron.Entities/Entities/Sales/Receipts/Invoices/ReceiptInvoice.cs
  • src/backend/Centron.Entities/Entities/Sales/Receipts/ContractLists/ReceiptContract.cs
  • src/backend/Centron.Entities/Entities/Sales/Receipts/CreditVouchers/ReceiptCreditVoucher.cs
  • src/backend/Centron.Entities/Entities/Sales/Receipts/PickupLists/ReceiptPickupList.cs

Database Schema

Dual Layer Architecture: Tables and Views

The receipts system uses a dual-layer database architecture consisting of legacy tables and modern views. This design maintains backward compatibility while providing cleaner interfaces for the C# application.

Legacy Tables (German Names)

The original database tables use German naming conventions and contain historical structure:

*Header Tables (Kopf):

  • AngKopf - Offer headers
  • AufKopf - Order headers
  • LiefKopf - Delivery list headers
  • RechKopf - Invoice headers
  • VertragKopf - Contract headers
  • GutKopf - Credit voucher headers
  • AbholKopf - Pickup list headers

*Position Tables (Pos):

  • AngPos - Offer items
  • AufPos - Order items
  • LiefPos - Delivery list items
  • RechPos - Invoice items
  • VertragPos - Contract items
  • GutPos - Credit voucher items
  • AbholPos - Pickup list items

*Version Tables (Versions): Each receipt type maintains version history through dedicated version tables:

  • AngKopfVersions / AngPosVersions - Offer version history
  • AufKopfVersions / AufPosVersions - Order version history
  • LiefKopfVersions / LiefPosVersions - Delivery list version history
  • RechKopfVersions / RechPosVersions - Invoice version history
  • VertragKopfVersions / VertragPosVersions - Contract version history
  • GutKopfVersions / GutPosVersions - Credit voucher version history
  • AbholKopfVersions / AbholPosVersions - Pickup list version history

Modern Views (English Names)

For C# application compatibility, cleaner views with English names are used:

Header Views:

  • Offers - Clean view of AngKopf
  • Orders - Clean view of AufKopf
  • DeliveryLists - Clean view of LiefKopf
  • Invoices - Clean view of RechKopf
  • Contracts - Clean view of VertragKopf
  • CreditVouchers - Clean view of GutKopf
  • PickupLists - Clean view of AbholKopf

Item Views:

  • OfferItems - Clean view of AngPos
  • OrderItems - Clean view of AufPos
  • DeliveryListItems - Clean view of LiefPos
  • InvoiceItems - Clean view of RechPos
  • ContractItems - Clean view of VertragPos
  • CreditVoucherItems - Clean view of GutPos
  • PickupListItems - Clean view of AbholPos

Version Views:

  • OfferVersions / OfferItemVersions - Offer version views
  • OrderVersions / OrderItemVersions - Order version views
  • DeliveryListVersions / DeliveryListItemVersions - Delivery list version views
  • InvoiceVersions / InvoiceItemVersions - Invoice version views
  • ContractVersions / ContractItemVersions - Contract version views
  • CreditVoucherVersions / CreditVoucherItemVersions - Credit voucher version views
  • PickupListVersions / PickupListItemVersions - Pickup list version views

Shared Logging Infrastructure

AnlageLog Table

Purpose: Centralized logging for all receipt types
Structure: Shared table with receipt type differentiation

Key Columns:

  • AnlageI3D - References the specific receipt's I3D
  • AnlageArt - Receipt type identifier (corresponds to ObjectKind)
  • Log entry details and timestamps

AnlageArt Values:

  • 1 = Offer
  • 2 = Order
  • 3 = Delivery List
  • 4 = Invoice
  • 5 = Pickup List
  • 6 = Credit Voucher
  • 22 = Contract

This pattern (ObjectI3D + ObjectKind / AnlageI3D + AnlageArt) is used throughout the system for shared references across different entity types.

Schema Maintenance

Version Tables: 1:1 Copies of Original Tables

Critical Requirement: Version tables (*KopfVersions, *PosVersions) are exact 1:1 copies of their corresponding original tables. This means every column that exists in the base table must also exist in the version table with identical structure and data types.

Version Table Structure:

  • Contains all columns from the original table
  • Excludes certain system columns (I3D, OriginalI3D)
  • Adds OriginalI3D column to reference the original record
  • Adds KopfVersionsI3D column (for *Pos version tables) to reference the header version

Versioning Implementation Example: The versioning mechanism (as seen in AssetHeadDAO.SaveAssetVersion) works by:

-- Copy header record to version table
INSERT INTO AngKopfVersions (all_columns_except_I3D, OriginalI3D)
SELECT all_columns_except_I3D, I3D AS OriginalI3D
FROM AngKopf
WHERE I3D = @receiptId

-- Copy all item records to version table
INSERT INTO AngPosVersions (all_columns_except_I3D, OriginalI3D, KopfVersionsI3D)
SELECT all_columns_except_I3D, I3D AS OriginalI3D, @headerVersionId AS KopfVersionsI3D
FROM AngPos
WHERE AngKopfI3D = @receiptId

Adding New Columns - Complete Checklist

When adding new columns to receipts, all of the following must be updated:

  1. Base Table: Add column to the legacy table (e.g., AngKopf)
  2. Version Table: Add the identical column to the version table (e.g., AngKopfVersions)
  3. Update Views: Modify both the main view (e.g., Offers) and version view (e.g., OfferVersions) to include the new column
  4. Entity Classes: Add the property to the C# entity class (e.g., ReceiptOffer) and version entity if applicable
  5. Mapping Classes: Update NHibernate mapping classes for ORM functionality
  6. Temporary Legacy Entities: Add the property to the matching *Kopf / *Pos temporary entity under src/backend/Centron.Entities/Entities/DbEntities/
  7. Temporary Entity Mappings: Add the mapping to the matching class under src/backend/Centron.DAO/Mappings/TemporaryEntities/
  8. SaveReceipt Repository: Copy the value in the receipt-type-specific SaveReceipt*Repository (SynchronizeReceiptData for header fields, SynchronizeReceiptItemData for item fields)
  9. DTOs and Interfaces: Add the property to webservice DTOs and relevant receipt interfaces when the value crosses BL/WebService/UI boundaries
  10. Version Views: Ensure version views (OfferVersions, OfferItemVersions) include the new column

⚠️ Critical Warning: Forgetting to add a column to the version table will cause runtime errors when the versioning system attempts to copy records. The DoGetFieldList() method dynamically generates field lists, so missing columns in version tables will break the INSERT statements.

Critical Save Warning: The normal NHibernate receipt entity mapping is not the only persistence path. Receipt saves go through legacy SaveReceipt*Repository classes, which synchronize the modern receipt entities into temporary legacy table entities (RechKopf, RechPos, LiefKopf, LiefPos, etc.) before writing to the database. If a new field is only added to the modern entity/view mapping but not to the temporary entity, temporary mapping, and SaveReceipt*Repository, the value may load correctly from the view but will not be persisted on save.

Version Table Maintenance Process

**For Header Tables (Kopf → KopfVersions):

  1. Add column to base table: ALTER TABLE AngKopf ADD NewColumn datatype
  2. Add identical column to version table: ALTER TABLE AngKopfVersions ADD NewColumn datatype
  3. Update corresponding views to include the new column

**For Item Tables (Pos → PosVersions):

  1. Add column to base table: ALTER TABLE AngPos ADD NewColumn datatype
  2. Add identical column to version table: ALTER TABLE AngPosVersions ADD NewColumn datatype
  3. Update corresponding views to include the new column

This strict 1:1 correspondence ensures that the automatic versioning system (AssetHeadDAO.SaveAssetVersion and similar methods) can create complete snapshots of receipt states for audit trails and change tracking.

Business Logic Layer

ReceiptBL - Core Business Logic

Location: src/backend/Centron.BL/Sales/Receipts/ReceiptBL.cs

The ReceiptBL class provides the central business logic for all receipt operations. It contains over 10,000 lines of code handling comprehensive receipt management functionality.

Key Responsibilities:

  • CRUD Operations: Generic methods for loading, searching, and saving receipts
  • Receipt Processing: State management, workflow processing, validation
  • Item Management: Adding, updating, removing receipt items
  • Price Calculations: Tax calculations, discounts, currency conversions
  • Document Generation: PDF generation, printing, email sending
  • Integration: Connection with accounting systems, warehousing, customer management
  • Workflow Management: Approval processes, state transitions
  • Reporting: Export functionality (Excel, PDF)

Core Methods:

  • GetReceiptByI3D<T>(int receiptI3D): Generic receipt retrieval
  • GetReceipts<T>(IReceiptFilter filter): Search receipts with filtering
  • SaveReceipt<T>(T receipt): Generic receipt saving
  • DeleteReceipt(int receiptI3D, CentronObjectKindNumeric receiptKind): Receipt deletion
  • ExportReceiptToExcel(): Excel export functionality

SpecificLogics Pattern

The ReceiptBL utilizes a SpecificLogics helper class that delegates specialized operations to receipt-type-specific business logic classes:

  • ContractSpecificLogic for contracts
  • InvoiceSpecificLogic for invoices
  • OrderSpecificLogic for orders
  • And similar classes for other receipt types

Data Access Layer

Repository Pattern

Each receipt type has its own repository for data persistence:

  • SaveReceiptContractRepository → VertragKopf & VertragPos tables
  • SaveReceiptInvoiceRepository → RechKopf & RechPos tables
  • SaveReceiptOfferRepository → AngKopf & AngPos tables
  • SaveReceiptOrderRepository → AufKopf & AufPos tables
  • SaveReceiptDeliveryListRepository → LiefKopf & LiefPos tables
  • SaveReceiptCreditVoucherRepository → GutKopf & GutPos tables
  • SaveReceiptPickupListRepository → AbholKopf & AbholPos tables
  • And similar repositories for supplier receipt types

These repositories are a legacy persistence layer between the normal NHibernate receipt entities and the database. They create or update temporary table entities and explicitly assign many properties. When adding a persisted receipt header or item field, update the repository method that synchronizes that level:

  • Header field: SynchronizeReceiptData(...)
  • Item field: SynchronizeReceiptItemData(...)

Do not rely on AutoMapper or the modern NHibernate entity mapping for this save path. End-to-end tests are the preferred safety net for new receipt fields because they execute the database script, save through ReceiptWebServiceBL.SaveReceipt(...), reload the receipt, and can assert the raw legacy table values.

Database Table Structure

All receipt types follow a consistent two-table pattern:

*Header Tables (Kopf):

  • Contains receipt-level information (customer, dates, totals, etc.)
  • Inherits from ReceiptTable base structure
  • Primary key: I3D (identity column)
  • Common audit fields: CreatedAt, ChangedAt, CreatedByI3D, ChangedByI3D

*Position Tables (Pos):

  • Contains individual line items/positions
  • Foreign key reference to header table (*KopfI3D)
  • Article information, quantities, prices, and item-specific data
  • Primary key: I3D (identity column)
  • Position number: Pos (for ordering)

Common Workflows

Receipt Creation Process

  1. Initialize Receipt Entity - Create new receipt instance with default values
  2. Set Header Information - Customer, addresses, dates, currency
  3. Add Receipt Items - Products/services with quantities and prices
  4. Calculate Totals - Tax calculations, discounts, final amounts
  5. Validate Business Rules - Check inventory, credit limits, etc.
  6. Save to Database - Persist header and position records
  7. Generate Document - Create PDF, send emails if required

Receipt State Management

Receipts progress through defined states:

  • Draft - Initial creation, can be freely modified
  • Released - Approved for processing, limited modifications
  • Processed - Finalized, minimal changes allowed
  • Cancelled - Marked as cancelled, read-only

Item Management

  • Dynamic Item Addition - Items can be added at any time during draft state
  • Price Calculation - Automatic recalculation of totals when items change
  • Inventory Integration - Real-time stock checking and updates
  • Article Linking - Connection to master article data

Integration Points

Customer Management

  • Customer data integration for addresses and contact information
  • Credit limit checking and payment term assignment
  • Customer-specific pricing and discount structures

Inventory System

  • Real-time stock level checking
  • Automatic inventory updates on receipt processing
  • Serial number and barcode tracking

Accounting System

  • Automatic journal entry generation
  • Tax calculation and reporting
  • Integration with financial reporting systems

Document Management

  • PDF generation for all receipt types
  • Email delivery capabilities
  • Document archiving and retrieval

Extensibility

Adding New Receipt Types

To add a new receipt type:

  1. Create Entity Classes - Header and position entities extending base classes
  2. Implement Business Logic - Specific BL class with type-specific operations
  3. Create Database Tables - Following the *Kopf/*Pos naming convention
  4. Add Repository Classes - For data persistence operations
  5. Register with SpecificLogics - Enable integration with core ReceiptBL

Customization Points

  • Custom Fields - Additional properties on receipt entities
  • Business Rules - Custom validation and processing logic
  • Workflow Extensions - Additional states and transitions
  • Integration Hooks - Custom external system connections

Performance Considerations

Database Optimization

  • Indexed Foreign Keys - All *KopfI3D references are indexed
  • Pagination Support - Large result sets handled via paging
  • Query Optimization - Efficient queries for common operations

Memory Management

  • Lazy Loading - Receipt items loaded on demand
  • Batch Operations - Bulk processing for multiple receipts
  • Caching Strategy - Frequently accessed data cached appropriately

Security

Access Control

  • User-based Permissions - Role-based access to receipt functions
  • Branch Isolation - Users can only access receipts from their branches
  • Audit Trail - Complete tracking of all receipt changes

Data Protection

  • Concurrency Control - GUID-based optimistic locking
  • Data Validation - Input validation and sanitization
  • Transaction Management - ACID compliance for all operations

Best Practices

Development Guidelines

  • Use Generic Methods - Leverage ReceiptBL generic operations where possible
  • Follow Inheritance Patterns - Extend base classes rather than duplicating code
  • Implement Proper Error Handling - Use try-catch blocks and meaningful error messages
  • Maintain Audit Trails - Always populate CreatedBy/ChangedBy fields

Testing Considerations

  • Unit Tests - Test business logic methods in isolation
  • Integration Tests - Test complete receipt workflows
  • Database Tests - Verify data persistence and retrieval
  • Performance Tests - Ensure acceptable response times under load