Files
Masterarbeit/QuellCode/CentronERP/tests/Centron.Tests.EndToEnd/Tests/ReceiptProvisions/ReceiptProvisionTests.cs
T
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

997 lines
45 KiB
C#

using System;
using System.Collections.Generic;
using System.Linq;
using Centron.BusinessLogic;
using Centron.BusinessLogic.Administration.Rights;
using Centron.BusinessLogic.EmployeeArea;
using Centron.BusinessLogic.Sales.Receipts;
using Centron.BusinessLogic.Sales.Receipts.DataAndResults;
using Centron.BusinessLogic.Sales.Receipts.Internal;
using Centron.BusinessLogic.WebServices.Accounts;
using Centron.BusinessLogic.WebServices.Administration.Rights;
using Centron.BusinessLogic.WebServices.Sales.Receipts;
using Centron.DAO;
using Centron.Data.Entities.Administration.Logins;
using Centron.Data.Entities.Sales.Receipts;
using Centron.Data.WebServices.Sales.Receipts.Invoices;
using Centron.Data.WebServices.Sales.Receipts.Offers;
using Centron.Interfaces;
using Centron.Interfaces.Accounts;
using Centron.Interfaces.Administration.Environment;
using Centron.Interfaces.BL;
using Centron.Interfaces.Sales.Receipts;
using Centron.Interfaces.Sales.Receipts.InsertReceipts;
using Centron.Tests.EndToEnd.Infrastructure;
using CentronSoftware.Centron.WebServices.Entities.Sales.Receipts;
using CentronSoftware.Centron.WebServices.Entities.Sales.Receipts.ContractLists;
using CentronSoftware.Centron.WebServices.EntitiesWrongPlace.Sales.Receipts.DataAndResults;
using CentronSoftware.Centron.WebServices.Extensions;
using Xunit;
using Xunit.Abstractions;
namespace Centron.Tests.EndToEnd.Tests.ReceiptProvisions
{
public class ReceiptProvisionTests : EndToEndTest
{
public ReceiptProvisionTests(ITestOutputHelper testOutputHelper)
: base(testOutputHelper)
{
}
private const int CustomerNumber = 10020;
private const int Offer1I3D = 6750;
private const int Offer2I3D = 6748;
private const int Offer3I3D = 6732;
private const int Offer4I3D = 6728;
private const int Offer5I3D = 6723;
private const int Offer6I3D = 6716;
public override void Execute()
{
this.CanNotCreateProvisionSchemaWithInvalidData(step:1);
this.CreateNewSchema(step:2);
this.LoadProvisionSchema(step:3);
this.CanUseSchemaAsGlobal(step:4);
this.CanAssignSchemaToCustomer(step:5);
this.LoadProvisionSchemaCustomerAssignments(step:6);
this.DeleteProvisionSchema(step:7);
this.CanSaveReadAndDeleteReceiptProvisionItems(step: 8);
this.CanSaveReceiptWithProvisionItems(step: 9);
this.ProvisionIsCopiedWhenForwarding(step: 10);
this.ApplySchemaToExistingOpenReceipts(step: 11);
this.GetProvisionEvaluation(step: 12);
this.ProvisionRightsExist(step: 13);
this.CanNotSaveOrDeleteSchemaWithoutRights(step: 14);
this.UpdateSchemaCustomerAssignments(step: 15);
this.UpdateSchemaCustomerAssignmentWithoutRights(step: 16);
this.FilterEmployeeI3DWorks(step: 17);
this.GetReceiptsWithoutProvision(step: 18);
this.ProvisionUpdatesWhenPurchasePriceChanges(step: 19);
}
private void CanNotCreateProvisionSchemaWithInvalidData(int step)
{
void ShouldThrowFor<T>(ReceiptProvisionSchemaDTO schema, LoggedInUser currentUser)
where T : Exception
{
using var session = new BLSession();
Assert.Throws<T>(() => session.GetBL<ReceiptProvisionSchemaWebServiceBL>().SaveProvisionSchema(schema, currentUser));
}
ShouldThrowFor<ArgumentNullException>(new ReceiptProvisionSchemaDTO
{
Name = null, //Error
}, this.GetLoggedInUser());
ShouldThrowFor<ArgumentNullException>(new ReceiptProvisionSchemaDTO
{
Name = string.Empty, //Error
}, this.GetLoggedInUser());
ShouldThrowFor<ArgumentNullException>(new ReceiptProvisionSchemaDTO
{
Name = " ", //Error
}, this.GetLoggedInUser());
ShouldThrowFor<ArgumentException>(new ReceiptProvisionSchemaDTO
{
I3D = -1, //Error
Name = "Something"
}, this.GetLoggedInUser());
ShouldThrowFor<ArgumentNullException>(new ReceiptProvisionSchemaDTO
{
I3D = 0,
Name = "Something",
Items = null //Error
}, this.GetLoggedInUser());
ShouldThrowFor<ArgumentNullException>(new ReceiptProvisionSchemaDTO
{
I3D = 0,
Name = "Something",
Items =
{
null //Error
}
}, this.GetLoggedInUser());
ShouldThrowFor<ArgumentException>(new ReceiptProvisionSchemaDTO
{
I3D = 0,
Name = "Something",
Items =
{
new ReceiptProvisionSchemaItemDTO
{
Receiver = ReceiptProvisionReceiver.ReceiptAdviser1,
ProvisionPercentage = -10 //Error
}
}
}, this.GetLoggedInUser());
ShouldThrowFor<ArgumentException>(new ReceiptProvisionSchemaDTO
{
I3D = 0,
Name = "Something",
Items =
{
new ReceiptProvisionSchemaItemDTO
{
Receiver = ReceiptProvisionReceiver.ReceiptAdviser1,
SharePercentage = -10 //Error
}
}
}, this.GetLoggedInUser());
ShouldThrowFor<ArgumentException>(new ReceiptProvisionSchemaDTO
{
I3D = 0,
Name = "Something",
Items =
{
new ReceiptProvisionSchemaItemDTO
{
Receiver = ReceiptProvisionReceiver.ReceiptAdviser1,
Source = (ReceiptProvisionSource)123456, //Error
}
}
}, this.GetLoggedInUser());
ShouldThrowFor<ArgumentException>(new ReceiptProvisionSchemaDTO
{
I3D = 0,
Name = "Something",
Items =
{
new ReceiptProvisionSchemaItemDTO
{
Receiver = (ReceiptProvisionReceiver)123456, //Error
}
}
}, this.GetLoggedInUser());
ShouldThrowFor<ArgumentNullException>(new ReceiptProvisionSchemaDTO
{
I3D = 0,
Name = "Something",
Items =
{
new ReceiptProvisionSchemaItemDTO
{
Receiver = ReceiptProvisionReceiver.FixedEmployee,
EmployeeI3D = null, //Error
}
}
}, this.GetLoggedInUser());
ShouldThrowFor<ArgumentNullException>(new ReceiptProvisionSchemaDTO
{
I3D = 0,
Name = "Something",
Items =
{
new ReceiptProvisionSchemaItemDTO
{
Receiver = ReceiptProvisionReceiver.FixedEmployee,
EmployeeI3D = 1,
}
}
}, null); //Error (LoggedInUser currentUser is NULL)
ShouldThrowFor<ArgumentException>(new ReceiptProvisionSchemaDTO
{
I3D = 0,
Name = "Something",
Items =
{
new ReceiptProvisionSchemaItemDTO
{
Receiver = ReceiptProvisionReceiver.FixedEmployee,
EmployeeI3D = 1,
Value = (ReceiptProvisionValue)123456, //Error
}
}
}, this.GetLoggedInUser());
ShouldThrowFor<ArgumentNullException>(new ReceiptProvisionSchemaDTO
{
I3D = 0,
Name = "Something",
Items =
{
new ReceiptProvisionSchemaItemDTO
{
Receiver = ReceiptProvisionReceiver.FixedEmployee,
EmployeeI3D = 1,
Source = ReceiptProvisionSource.MaterialGroups,
SourceMaterialGroups = null //Error
}
}
}, this.GetLoggedInUser());
ShouldThrowFor<ArgumentException>(new ReceiptProvisionSchemaDTO
{
I3D = 0,
Name = "Something",
Items =
{
new ReceiptProvisionSchemaItemDTO
{
Receiver = ReceiptProvisionReceiver.FixedEmployee,
EmployeeI3D = 1,
Source = ReceiptProvisionSource.MaterialGroups,
SourceMaterialGroups = new() //Error (empty list)
}
}
}, this.GetLoggedInUser());
}
private void CreateNewSchema(int step)
{
var schema = new ReceiptProvisionSchemaDTO
{
Name = "Globale Provision",
Items =
{
new ReceiptProvisionSchemaItemDTO
{
Receiver = ReceiptProvisionReceiver.FixedEmployee,
EmployeeI3D = 23,
SharePercentage = 100,
ProvisionPercentage = 10,
Source = ReceiptProvisionSource.ServiceOnly,
Value = ReceiptProvisionValue.Auto
},
new ReceiptProvisionSchemaItemDTO
{
Receiver = ReceiptProvisionReceiver.CustomerAdviser1,
EmployeeI3D = null,
SharePercentage = 80,
ProvisionPercentage = 5,
Source = ReceiptProvisionSource.ServiceOnly,
Value = ReceiptProvisionValue.Auto,
Description = "Test-Test"
},
new ReceiptProvisionSchemaItemDTO
{
Receiver = ReceiptProvisionReceiver.CustomerAdviser5,
EmployeeI3D = null,
SharePercentage = 20,
ProvisionPercentage = 5,
Source = ReceiptProvisionSource.ServiceOnly,
Value = ReceiptProvisionValue.Auto,
Description = "CustomerAdviser5"
},
new ReceiptProvisionSchemaItemDTO
{
Receiver = ReceiptProvisionReceiver.ReceiptAdviser1,
EmployeeI3D = null,
SharePercentage = 100,
ProvisionPercentage = 3,
Source = ReceiptProvisionSource.MaterialGroups,
SourceMaterialGroups = new List<ReceiptProvisionSourceMaterialGroup>
{
new() { MaterialGroupI3D = 1, SubMaterialGroupI3D = null },
new() { MaterialGroupI3D = 2, SubMaterialGroupI3D = 10 },
},
Value = ReceiptProvisionValue.Auto,
FilterEmployeeI3D = 10,
}
}
};
using var session = new BLSession();
var saveResult1 = session.GetBL<ReceiptProvisionSchemaWebServiceBL>().SaveProvisionSchema(schema, this.GetLoggedInUser());
this.Verifier.Verify($"{step}_CreateNewSchema_1", saveResult1);
var saveResult2 = session.GetBL<ReceiptProvisionSchemaWebServiceBL>().SaveProvisionSchema(schema, this.GetLoggedInUser());
this.Verifier.Verify($"{step}_CreateNewSchema_2", saveResult2);
}
private void LoadProvisionSchema(int step)
{
using var session = new BLSession();
var allSchemas = session.GetBL<ReceiptProvisionSchemaWebServiceBL>().GetAllProvisionSchemas();
this.Verifier.Verify($"{step}_AllSchemas", allSchemas);
}
private void CanUseSchemaAsGlobal(int step)
{
using var session = new BLSession();
var schema = session.GetBL<ReceiptProvisionSchemaWebServiceBL>().GetAllProvisionSchemas().First();
// Set up AutomHelpdesk test data using BL layer
var settings = session.GetBL<ReceiptWebServiceBL>().GetReceiptSettings(this.GetLoggedInUser().User);
settings.GlobalReceiptProvisionSchemaI3D = schema.I3D;
settings.AutomHelpdeskAdditionalText1 = "Additional Text 1 for Test";
settings.AutomHelpdeskAdditionalText2 = "Additional Text 2 for Test";
settings.AutomHelpdeskOnlyInternal = true;
settings.AutomHelpdeskPriority = 2;
settings.AutomHelpdeskStatus = 1;
settings.AutomHelpdeskSubCategory1 = 3;
settings.AutomHelpdeskSubCategory2 = 5;
settings.AutomHelpdeskProcessorI3Ds = "10";
settings.AutomHelpdeskResponsiblePersonI3D = 15;
settings.AutomHelpdeskSendEmailToProcessor = true;
settings.AutomHelpdeskCategoryI3D = 20;
settings.AutomHelpdeskCreateSeparateTicketsMode = 1;
settings.AutomHelpdeskOpenAfterwards = true;
settings.AutomHelpdeskCreateTicketForAll = true;
settings.AutomHelpdeskSelectedTemplateI3D = 25;
session.GetBL<ReceiptWebServiceBL>().UpdateReceiptSettings(settings, this.GetLoggedInUser().User);
this.Verifier.Verify($"{step}_ReceiptSettingsWithGlobalProvisionSchema", settings);
// Ensure we get the global schema as a "current provision-schema for this customer"
var schemaForCustomer = session.GetBL<ReceiptProvisionSchemaBL>().GetCurrentProvisionSchemaForCustomer(CustomerNumber, null);
Assert.Equal(schema.I3D, schemaForCustomer.I3D);
// Ensure we get the correct provision-schema when creating a new receipt
var receiptResult = session.GetBL<ReceiptWebServiceBL>().CreateNewReceipt(
CentronObjectKindNumeric.OfferClass,
this.GetLoggedInUser(),
CustomerNumber,
new CreateReceiptData { IgnoreCallbacks = true },
addressI3D: null,
contactPersonI3D: null,
insertSalutationAndAgreement: false,
ignoreDefaultContract: true,
insertCustomerDiscount: false).ThrowIfError();
var offer = (ReceiptOfferDTO)receiptResult.Receipt;
this.Verifier.Verify($"{step}_ProvisionInNewReceipt", offer.Provision);
}
private void CanAssignSchemaToCustomer(int step)
{
using var session = new BLSession();
// The first one is the global one already, we wanna assign a different one to the customer, so we use .Last()
var schema = session.GetBL<ReceiptProvisionSchemaWebServiceBL>().GetAllProvisionSchemas().Last();
var accountFilter = new AccountFilter
{
OldReference = new AccountFilterOldReference
{
Kind = AccountTypeKind.Customer,
I3D = CustomerNumber
}
};
var account = session.GetBL<AccountWebServiceBL>().GetAccount(this.GetLoggedInUser(), accountFilter, false).ThrowIfError();
if (account.TryGetCustomerData(out var customerData))
{
customerData.ProvisionSchemaI3D = schema.I3D;
}
session.GetBL<AccountWebServiceBL>().SaveAccount(this.GetLoggedInUser(), account, mixMode: false, isDataImport: false).ThrowIfError();
this.Verifier.VerifyTable($"{step}_AccountCustomerWithProvisionSchema", "AccountCustomers", $"Number = {CustomerNumber}");
// Ensure we get the customer-schema as a "current provision-schema for this customer"
var schemaForCustomer = session.GetBL<ReceiptProvisionSchemaBL>().GetCurrentProvisionSchemaForCustomer(CustomerNumber, null);
Assert.Equal(schema.I3D, schemaForCustomer.I3D);
// Ensure we get the correct provision-schema when creating a new receipt
var receiptResult = session.GetBL<ReceiptWebServiceBL>().CreateNewReceipt(
CentronObjectKindNumeric.OfferClass,
this.GetLoggedInUser(),
CustomerNumber,
new CreateReceiptData { IgnoreCallbacks = true },
addressI3D: null,
contactPersonI3D: null,
insertSalutationAndAgreement: false,
ignoreDefaultContract: true,
insertCustomerDiscount: false).ThrowIfError();
var offer = (ReceiptOfferDTO)receiptResult.Receipt;
this.Verifier.Verify($"{step}_ProvisionInNewReceipt", offer.Provision);
}
private void LoadProvisionSchemaCustomerAssignments(int step)
{
using var session = new BLSession();
var assignments = session.GetBL<ReceiptProvisionSchemaWebServiceBL>().GetAllProvisionSchemaDetails();
this.Verifier.Verify($"{step}_CustomerAssignments", assignments);
}
private void DeleteProvisionSchema(int step)
{
using var session = new BLSession();
session.GetBL<ReceiptProvisionSchemaWebServiceBL>().DeleteProvisionSchema(1, this.GetLoggedInUser());
session.GetBL<ReceiptProvisionSchemaWebServiceBL>().DeleteProvisionSchema(2, this.GetLoggedInUser());
this.Verifier.VerifyTable($"{step}_AccountCustomer_NoSchema", "AccountCustomers", $"Number = {CustomerNumber}");
this.Verifier.VerifyTable($"{step}_Schemas", "ReceiptProvisionSchemas");
this.Verifier.VerifyTable($"{step}_SchemaItems", "ReceiptProvisionSchemaItems");
// Ensure we get NULL as a "current provision-schema for this customer"
var schemaForCustomer = session.GetBL<ReceiptProvisionSchemaBL>().GetCurrentProvisionSchemaForCustomer(CustomerNumber, null);
Assert.Null(schemaForCustomer);
}
private void CanSaveReadAndDeleteReceiptProvisionItems(int step)
{
using var session = new DAOSession();
var existingProvisionItems = session.GetGenericDAO<ReceiptProvisionItemEntity>().Query().ToList();
Assert.Empty(existingProvisionItems);
var item = new ReceiptProvisionItemEntity
{
ReceiptI3D = 1,
ReceiptKind = CentronObjectKindNumeric.OfferClass,
Receiver = ReceiptProvisionReceiver.FixedEmployee,
EmployeeI3D = 23,
FilterEmployeeI3D = 11,
SharePercentage = 60,
ProvisionPercentage = 10,
Source = ReceiptProvisionSource.All,
Value = ReceiptProvisionValue.Auto,
Description = "Another test description",
ActualProvision = 100.50m,
ActualPrice = 123.45m,
ActualEmployeeI3D = 23
};
session.GetGenericDAO<ReceiptProvisionItemEntity>().SaveOrUpdate(item);
Assert.NotEqual(0, item.I3D);
this.Verifier.VerifyTable($"{step}_ReceiptProvisionItems_AfterInsert", "ReceiptProvisionItems");
session.GetGenericDAO<ReceiptProvisionItemEntity>().Delete(item);
var provisionItemsAfterDelete = session.GetGenericDAO<ReceiptProvisionItemEntity>().Query().ToList();
this.Verifier.VerifyTable($"{step}_ReceiptProvisionItems_AfterDelete", "ReceiptProvisionItems");
}
private void CanSaveReceiptWithProvisionItems(int step)
{
// We have to insert a provision-schema, to use the new structure
// If there is none (as right now), then we will automatically fall back to the old provision structure
using (var session = new BLSession())
{
session.GetBL<ReceiptProvisionSchemaWebServiceBL>().SaveProvisionSchema(new ReceiptProvisionSchemaDTO
{
Name = "Test"
}, this.GetLoggedInUser());
}
var offerI3Ds = new List<int>
{
Offer1I3D,
Offer2I3D,
Offer3I3D,
Offer4I3D,
Offer5I3D,
Offer6I3D,
};
foreach (var offerI3D in offerI3Ds)
{
ReceiptOfferDTO offer;
// Create new version
using (var session = new BLSession())
{
var newVersion = session.GetBL<ReceiptWebServiceBL>().CreateNewVersion(
CentronObjectKindNumeric.OfferClass,
offerI3D,
version: null,
newContactPersonI3D: null,
this.GetLoggedInUser().User,
new CreateNewVersionData
{
IgnoreCallbacks = true,
}).ThrowIfError();
offer = (ReceiptOfferDTO)newVersion.Receipt;
}
// Set provision
offer.Provision = new List<ReceiptProvision>
{
new()
{
Receiver = ReceiptProvisionReceiver.CustomerAdviser1,
EmployeeI3D = null,
SharePercentage = 100,
ProvisionPercentage = 20.0m,
Source = ReceiptProvisionSource.ProductsOnly,
Value = ReceiptProvisionValue.Earnings,
FilterEmployeeI3D = 34,
},
new()
{
Receiver = ReceiptProvisionReceiver.FixedEmployee,
EmployeeI3D = 10,
SharePercentage = 80,
ProvisionPercentage = 30.0m,
Source = ReceiptProvisionSource.ServiceOnly,
Value = ReceiptProvisionValue.Sales,
Description = "Some description"
},
new()
{
Receiver = ReceiptProvisionReceiver.FixedEmployee,
EmployeeI3D = 12,
SharePercentage = 100,
ProvisionPercentage = 100,
Value = ReceiptProvisionValue.Sales,
Source = ReceiptProvisionSource.MaterialGroups,
SourceMaterialGroups = new List<ReceiptProvisionSourceMaterialGroup>
{
new () { MaterialGroupI3D = 1, SubMaterialGroupI3D = null, }, // Hardware
new () { MaterialGroupI3D = 1, SubMaterialGroupI3D = 10, }, // Hardware -> Monitore
}
}
};
// Save receipt
using (var session = new BLSession())
{
var saveResult = session.GetBL<ReceiptWebServiceBL>().SaveReceipt(
offer,
this.GetLoggedInUser().User,
new SaveReceiptData
{
IgnoreCallbacks = true
},
autoLockIfNewReceipt: false,
CreatedThroughApplication.WebServices,
receiptTemplateFolderI3D: 0).ThrowIfError();
}
// Verify provision
this.Verifier.VerifyTable($"{step}_Offer_{offerI3D}_WithProvision", "ReceiptProvisionItems", $"ReceiptI3D = {offerI3D} AND ReceiptKind = 1");
}
}
private void ProvisionIsCopiedWhenForwarding(int step)
{
using var session = new BLSession();
var forwardResult = session.GetBL<ReceiptWebServiceBL>().ForwardReceipt(
CentronObjectKindNumeric.InvoiceClass,
this.GetLoggedInUser().User,
new ForwardReceiptData
{
IgnoreCallbacks = true,
CreateReceiptData = new CreateReceiptData
{
IgnoreCallbacks = true,
},
CreateReceiptItemsFromExistingItemsData = new List<CreateReceiptItemsFromExistingItemsData>
{
new()
{
IgnoreCallbacks = true,
},
},
},
new List<ReceiptToForward>
{
new()
{
ReceiptKind = CentronObjectKindNumeric.OfferClass,
ReceiptI3D = Offer1I3D,
}
},
receiptProjectLayoutItemI3DsToForward: null,
InsertReceiptTakeoverOptions.Reference,
onlyTakeoverAvailableQuantity: true,
ignoreDefaultContract: true).ThrowIfError();
var invoice = (ReceiptInvoiceDTO)forwardResult.Receipt;
this.Verifier.Verify($"{step}_ProvisionAfterForwarding", invoice.Provision);
}
private void ApplySchemaToExistingOpenReceipts(int step)
{
using (var session = new BLSession())
{
// Create new schema
var schema = session.GetBL<ReceiptProvisionSchemaWebServiceBL>().SaveProvisionSchema(new ReceiptProvisionSchemaDTO
{
Name = "Globales-Schema",
Items = new List<ReceiptProvisionSchemaItemDTO>
{
new ReceiptProvisionSchemaItemDTO
{
Receiver = ReceiptProvisionReceiver.CustomerAdviser2,
SharePercentage = 90,
ProvisionPercentage = 10,
Source = ReceiptProvisionSource.All,
Description = "Hibbety Hoppety - DESCRIPTION!",
Value = ReceiptProvisionValue.Auto
}
}
}, this.GetLoggedInUser());
// Set it as global
var settings = session.GetBL<ReceiptWebServiceBL>().GetReceiptSettings(this.GetLoggedInUser().User);
settings.GlobalReceiptProvisionSchemaI3D = schema.I3D;
session.GetBL<ReceiptWebServiceBL>().UpdateReceiptSettings(settings, this.GetLoggedInUser().User);
}
Test("Offers_Invoices_Open",
new List<CentronObjectKindNumeric> { CentronObjectKindNumeric.OfferClass, CentronObjectKindNumeric.InvoiceClass },
includeClosedReceipts:false,
forceOverwriteProvision:false,
from: null,
to: null,
branchI3Ds: null);
Test("Offers_Invoices_Open_Again",
new List<CentronObjectKindNumeric> { CentronObjectKindNumeric.OfferClass, CentronObjectKindNumeric.InvoiceClass },
includeClosedReceipts:false,
forceOverwriteProvision:false,
from: null,
to: null,
branchI3Ds: null);
Test("Offers_Invoices_Open_Overwrite",
new List<CentronObjectKindNumeric> { CentronObjectKindNumeric.OfferClass, CentronObjectKindNumeric.InvoiceClass },
includeClosedReceipts:false,
forceOverwriteProvision:true,
from: null,
to: null,
branchI3Ds: null);
Test("Offers_Invoices_Open_DateTo",
new List<CentronObjectKindNumeric> { CentronObjectKindNumeric.OfferClass, CentronObjectKindNumeric.InvoiceClass },
includeClosedReceipts:false,
forceOverwriteProvision:true,
from: null,
to: new DateTime(2017, 6, 30),
branchI3Ds: null);
this.Verifier.VerifyTable($"{step}_ReceiptProvisionItems", "ReceiptProvisionItems");
void Test(string name, List<CentronObjectKindNumeric> receiptKinds, bool includeClosedReceipts, bool forceOverwriteProvision, DateTime? from, DateTime? to, List<int> branchI3Ds)
{
List<ReceiptProvisionUpdate> alreadyUpdatedReceipts = null;
while (true)
{
using (var session = new BLSession())
{
int? previousCount = alreadyUpdatedReceipts?.Count;
alreadyUpdatedReceipts = session.GetBL<ReceiptProvisionSchemaBL>().ApplyCurrentSchemaToOpenReceiptsWithoutProvision(
receiptKinds,
null,
includeClosedReceipts,
forceOverwriteProvision,
from,
to,
branchI3Ds,
alreadyUpdatedReceipts,
this.GetLoggedInUser(),
receiptsToUpdateCount:10); //Use a smaller count so we can test the "call the method again" workflow
// We didn't get any new receipts, that means we are done
if (previousCount == alreadyUpdatedReceipts.Count)
break;
}
}
this.Verifier.Verify($"{step}_ApplyCurrentSchemaToReceipts_{name}", alreadyUpdatedReceipts);
}
}
private void GetProvisionEvaluation(int step)
{
// One invoice should have a receipt-user-state, so we can check the filtering for it
this.Sql("UPDATE dbo.RechKopf SET ReceiptUserStateI3D = 1 WHERE I3D = 1330");
// And one should be closed
this.Sql("UPDATE dbo.RechKopf SET Status = 2 WHERE I3D = 1347");
// And we need some receipt with 0 provision
this.Sql("UPDATE dbo.ReceiptProvisionItems SET ActualProvision = 0, ActualProvisionSales = NULL, ActualProvisionEarnings = NULL WHERE ReceiptI3D = 6420 AND ReceiptKind = 4");
RunTest("All", new ReceiptProvisionEvaluationFilter(), this.GetLoggedInUser());
RunTest("DateStart", new ReceiptProvisionEvaluationFilter { DateStart = new DateTime(2017, 3, 1)}, this.GetLoggedInUser());
RunTest("DateEnd", new ReceiptProvisionEvaluationFilter { DateEnd = new DateTime(2017, 4, 1)}, this.GetLoggedInUser());
RunTest("ReceiptUserState", new ReceiptProvisionEvaluationFilter { ReceiptUserStateI3D = 1 }, this.GetLoggedInUser());
RunTest("OnlyClosedReceipts", new ReceiptProvisionEvaluationFilter { OnlyClosedReceipts = true }, this.GetLoggedInUser());
RunTest("OnlyOwn", new ReceiptProvisionEvaluationFilter { OnlyOwn = true }, this.GetLoggedInUser(userI3D: 16)); //AppUser 16 is Employee 27
RunTest("IncludeZeroProvision_Before", new ReceiptProvisionEvaluationFilter { DateStart = new DateTime(2017, 6, 26), DateEnd = new DateTime(2017, 6, 26), IncludeZeroProvisions = false}, this.GetLoggedInUser());
RunTest("IncludeZeroProvision_After", new ReceiptProvisionEvaluationFilter { DateStart = new DateTime(2017, 6, 26), DateEnd = new DateTime(2017, 6, 26), IncludeZeroProvisions = true}, this.GetLoggedInUser());
RunRightsTests();
void RunTest(string name, ReceiptProvisionEvaluationFilter filter, LoggedInUser currentUser)
{
using var session = new BLSession();
var evaluations = session.GetBL<ReceiptProvisionSchemaWebServiceBL>().GetProvisionEvaluation(filter, currentUser);
this.Verifier.Verify($"{step}_{name}", evaluations);
// Ensure that all the price and provision fields add up
Assert.All(evaluations, f =>
{
Assert.Equal(f.Price, f.PriceSales.GetValueOrDefault() + f.PriceEarnings.GetValueOrDefault());
Assert.Equal(f.Provision, f.ProvisionSales.GetValueOrDefault() + f.ProvisionEarnings.GetValueOrDefault());
});
}
void RunRightsTests()
{
const int UserI3DWithoutRight = 26;
// First, remove the User 26 from the administrator right-group
this.Sql($"DELETE FROM dbo.Sichmemb WHERE Gruppe = 6 AND Benutzer = {UserI3DWithoutRight}");
// Throws if you don't have the right
var exception = Assert.Throws<ResultException>(() =>
{
RunTest("Rights_NoRight", new ReceiptProvisionEvaluationFilter(), this.GetLoggedInUser(UserI3DWithoutRight));
});
this.Verifier.Verify($"{step}_Rights_NoRight_Exception", new { exception.Message, exception.MessageCode });
// Now add the right to a group
this.Sql($"INSERT INTO dbo.Sichtrus (Gruppe, Recht) VALUES (15, {UserRightsConst.Sales.Provision.PROVISION_EVALUATION_MODULE})");
// You should get all now
RunTest("Rights_All", new ReceiptProvisionEvaluationFilter(), this.GetLoggedInUser(UserI3DWithoutRight));
// And add the "only-own" right
this.Sql($"INSERT INTO dbo.Sichtrus (Gruppe, Recht) VALUES (15, {UserRightsConst.Sales.Provision.PROVISION_EVALUATION_ONLY_OWN})");
// You should get only your own now
RunTest("Rights_OnlyOwn", new ReceiptProvisionEvaluationFilter(), this.GetLoggedInUser(UserI3DWithoutRight));
}
}
private void ProvisionRightsExist(int step)
{
var provisionRights = new[]
{
UserRightsConst.Sales.Provision.ID,
UserRightsConst.Sales.Provision.PROVISION_EVALUATION_MODULE,
UserRightsConst.Sales.Provision.PROVISION_EVALUATION_ONLY_OWN,
UserRightsConst.Sales.Provision.PROVISION_SCHEMA_MANAGEMENT,
UserRightsConst.Sales.Provision.PROVISION_SCHEMA_CUSTOMER_ASSIGNMENT,
};
using var session = new BLSession();
var allRights = session.GetBL<AppRightsWebserviceBL>().GetAllRights().ThrowIfError();
var foundRights = allRights.Where(f => provisionRights.Contains(f.I3D)).ToList();
this.Verifier.Verify($"{step}_Provision_Rights", foundRights);
}
private void CanNotSaveOrDeleteSchemaWithoutRights(int step)
{
using var session = new BLSession();
// Load current user
var currentUser = new LoggedInUser(session.GetBL<AppUserBL>().GetAppUser(f => f.I3D == 20));
var currentUserHasRight = session.GetBL<AppRightsBL>().HasUserRight(currentUser.UserI3D.Value, UserRightsConst.Sales.Provision.PROVISION_SCHEMA_MANAGEMENT);
Assert.False(currentUserHasRight); // And make sure he doesn't have the needed right
// Save new Schema / Update schema
var exception = Assert.Throws<ResultException>(() =>
{
using var testSession = new BLSession();
testSession.GetBL<ReceiptProvisionSchemaWebServiceBL>().SaveProvisionSchema(new ReceiptProvisionSchemaDTO
{
Name = "Test-Schema that can't be saved anyways",
Items = new List<ReceiptProvisionSchemaItemDTO>
{
new ReceiptProvisionSchemaItemDTO
{
Receiver = ReceiptProvisionReceiver.FixedEmployee,
EmployeeI3D = 1
}
}
}, currentUser);
});
this.Verifier.Verify($"{step}_SaveProvisionSchema_RightMissingException", new { exception.Message, exception.MessageCode });
// Delete existing schema
var existingSchemaI3D = session.GetBL<ReceiptProvisionSchemaWebServiceBL>().GetAllProvisionSchemas().First().I3D;
exception = Assert.Throws<ResultException>(() =>
{
using var testSession = new BLSession();
testSession.GetBL<ReceiptProvisionSchemaWebServiceBL>().DeleteProvisionSchema(existingSchemaI3D, currentUser);
});
this.Verifier.Verify($"{step}_DeleteProvisionSchema_RightMissingException", new { exception.Message, exception.MessageCode });
}
private void UpdateSchemaCustomerAssignments(int step)
{
using (var session = new BLSession())
{
var detailsBefore = session.GetBL<ReceiptProvisionSchemaWebServiceBL>().GetAllProvisionSchemaDetails();
this.Verifier.Verify($"{step}_ProvisionSchemaDetails_Before", detailsBefore);
}
using (var session = new BLSession())
{
// Assign schema 3 to customer 10011, and NULL to all other customers
var assignments = new List<ReceiptProvisionSchemaDetailsDTO>
{
new ReceiptProvisionSchemaDetailsDTO
{
SchemaI3D = 3,
CustomerAssignments = new List<ReceiptProvisionSchemaCustomerAssignmentDTO>
{
new ReceiptProvisionSchemaCustomerAssignmentDTO
{
CustomerNumber = 10011
},
new ReceiptProvisionSchemaCustomerAssignmentDTO
{
CustomerNumber = 10011,
BranchI3D = 0
},
new ReceiptProvisionSchemaCustomerAssignmentDTO
{
CustomerNumber = 10012,
BranchI3D = 1
}
}
}
};
session.GetBL<ReceiptProvisionSchemaWebServiceBL>().UpdateProvisionSchemaCustomerAssignments(assignments, this.GetLoggedInUser());
}
using (var session = new BLSession())
{
var detailsAfter = session.GetBL<ReceiptProvisionSchemaWebServiceBL>().GetAllProvisionSchemaDetails();
this.Verifier.Verify($"{step}_ProvisionSchemaDetails_After", detailsAfter);
this.Verifier.VerifySql($"{step}_AccountCustomersTable", "SELECT AC.Number, AC.ProvisionSchemaI3D FROM dbo.AccountCustomers AC");
this.Verifier.VerifyTable($"{step}_ReceiptProvisionSchemaCustomerAssignments", "ReceiptProvisionSchemaCustomerAssignments");
}
}
private void UpdateSchemaCustomerAssignmentWithoutRights(int step)
{
using var session = new BLSession();
// Load current user
var currentUser = new LoggedInUser(session.GetBL<AppUserBL>().GetAppUser(f => f.I3D == 20));
var currentUserHasRight = session.GetBL<AppRightsBL>().HasUserRight(currentUser.UserI3D.Value, UserRightsConst.Sales.Provision.PROVISION_SCHEMA_CUSTOMER_ASSIGNMENT);
Assert.False(currentUserHasRight); // And make sure he doesn't have the needed right
// Save new Schema / Update schema
var exception = Assert.Throws<ResultException>(() =>
{
using var testSession = new BLSession();
testSession.GetBL<ReceiptProvisionSchemaWebServiceBL>().UpdateProvisionSchemaCustomerAssignments(new List<ReceiptProvisionSchemaDetailsDTO>(), currentUser);
});
this.Verifier.Verify($"{step}_UpdateProvisionSchemaCustomerAssignments_RightMissingException", new { exception.Message, exception.MessageCode });
}
private void FilterEmployeeI3DWorks(int step)
{
Test("BothProvisions", Offer1I3D, null, null);
Test("OnlyFirstProvision", Offer1I3D, 34, 60);
Test("OnlyFirstProvision_SecondSkipped", Offer1I3D, 34, null);
Test("OnlySecondProvision", Offer1I3D, 35, null);
void Test(string name, int offerI3D, int? filterEmployeeI3D, int? secondFilterEmployeeI3D)
{
ReceiptOfferDTO offer;
// Create new version
using (var session = new BLSession())
{
var newVersion = session.GetBL<ReceiptWebServiceBL>().CreateNewVersion(
CentronObjectKindNumeric.OfferClass,
offerI3D,
version: null,
newContactPersonI3D: null,
this.GetLoggedInUser().User,
new CreateNewVersionData
{
IgnoreCallbacks = true,
}).ThrowIfError();
offer = (ReceiptOfferDTO)newVersion.Receipt;
}
// Set provision
offer.Provision = new List<ReceiptProvision>
{
new()
{
Receiver = ReceiptProvisionReceiver.CustomerAdviser1,
EmployeeI3D = null,
SharePercentage = 100,
ProvisionPercentage = 100.0m,
Source = ReceiptProvisionSource.ProductsOnly,
Value = ReceiptProvisionValue.Earnings,
FilterEmployeeI3D = filterEmployeeI3D,
},
new()
{
Receiver = ReceiptProvisionReceiver.CustomerAdviser1,
EmployeeI3D = null,
SharePercentage = 100,
ProvisionPercentage = 100.0m,
Source = ReceiptProvisionSource.ProductsOnly,
Value = ReceiptProvisionValue.Earnings,
FilterEmployeeI3D = secondFilterEmployeeI3D,
}
};
// Save receipt
using (var session = new BLSession())
{
var saveResult = session.GetBL<ReceiptWebServiceBL>().SaveReceipt(
offer,
this.GetLoggedInUser().User,
new SaveReceiptData
{
IgnoreCallbacks = true
},
autoLockIfNewReceipt: false,
CreatedThroughApplication.WebServices,
receiptTemplateFolderI3D: 0).ThrowIfError();
}
// Verify provision
this.Verifier.VerifyTable($"{step}_Offer_{offerI3D}_{name}", "ReceiptProvisionItems", $"ReceiptI3D = {offerI3D} AND ReceiptKind = 1");
}
}
private void GetReceiptsWithoutProvision(int step)
{
using var session = new BLSession();
var filter = new ReceiptWithoutProvisionFilter
{
DateStart = null,
DateEnd = null
};
var receiptsWithoutProvision = session.GetBL<ReceiptProvisionSchemaWebServiceBL>().GetReceiptsWithoutProvision(filter, this.GetLoggedInUser());
this.Verifier.Verify($"{step}_ReceiptsWithoutProvision", receiptsWithoutProvision);
}
private void ProvisionUpdatesWhenPurchasePriceChanges(int step)
{
using var session = new BLSession();
var itemI3D = 21318;
var newPurchasePrice = 10;
// Update the purchase-price of this item
// That should force a recalculation of the provision
session.GetBL<ReceiptBL>().UpdateReceiptItemPurchasePrice(
this.GetLoggedInUser().User,
CentronObjectKindNumeric.OfferClass,
Offer1I3D,
itemI3D,
null,
newPurchasePrice).ThrowIfError();
// Verify provision
this.Verifier.VerifyTable($"{step}_Offer", "ReceiptProvisionItems", $"ReceiptI3D = {Offer1I3D} AND ReceiptKind = 1");
}
}
}