added vatNumber validation order - necessary for Sweden
This commit is contained in:
parent
4591cf156a
commit
e170d00f0d
4 changed files with 82 additions and 51 deletions
|
@ -51,7 +51,7 @@ public class VatUtils
|
|||
/// </summary>
|
||||
/// <param name="vatNumber"></param>
|
||||
/// <returns></returns>
|
||||
private static string SanitizeVatNumber(string vatNumber)
|
||||
public static string SanitizeVatNumber(string vatNumber)
|
||||
{
|
||||
if (string.IsNullOrWhiteSpace(vatNumber))
|
||||
return "";
|
||||
|
|
|
@ -54,9 +54,9 @@ else
|
|||
<EditForm EditContext="ActivityContext">
|
||||
<DataAnnotationsValidator/>
|
||||
|
||||
<div class="row mb-1">
|
||||
<label for="activityType" class="col-md-2 col-form-label">Ordre Type</label>
|
||||
<div class="col-md-4">
|
||||
<div class="row mb-1 g-2">
|
||||
<label for="activityType" class="col-sm-2 col-form-label-sm">Ordre Type</label>
|
||||
<div class="col-sm-4">
|
||||
<InputSelect id="activityType" class="form-select bg-primary text-bg-primary" @bind-Value="@Activity.ActivityTypeEnum">
|
||||
<option value="">→ TAG MIG ←</option>
|
||||
<option value="onSite">Besøg</option>
|
||||
|
@ -65,8 +65,8 @@ else
|
|||
<ValidationMessage For="@(() => Activity.ActivityTypeEnum)"></ValidationMessage>
|
||||
</div>
|
||||
|
||||
<label for="statusType" class="col-md-2 col-form-label">Status</label>
|
||||
<div class="col-md-4">
|
||||
<label for="statusType" class="col-sm-2 col-form-label-sm">Status</label>
|
||||
<div class="col-sm-4">
|
||||
<InputSelect id="statusType" class="form-select bg-primary text-bg-primary" @bind-Value="@Activity.ActivityStatusEnum">
|
||||
<option value="noSale">Ingen salg</option>
|
||||
@if (!string.IsNullOrEmpty(Activity.VatNumber) && !string.IsNullOrWhiteSpace(Activity.Address1) && Company.HasFolded == 0)
|
||||
|
@ -99,64 +99,75 @@ else
|
|||
</div>
|
||||
}
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="row mb-1">
|
||||
<label for="demo" class="col-md-2 col-form-label">Demo</label>
|
||||
<div class="col-md-4">
|
||||
<label for="demo" class="col-sm-2 col-form-label-sm">Demo</label>
|
||||
<div class="col-sm-4">
|
||||
<InputText id="demo" class="form-control" @bind-Value="Activity.Demo"/>
|
||||
<ValidationMessage For="@(() => Activity.Demo)"></ValidationMessage>
|
||||
</div>
|
||||
|
||||
<label for="email" class="col-md-2 col-form-label">Epost</label>
|
||||
<div class="col-md-4">
|
||||
<label for="email" class="col-sm-2 col-form-label-sm">Epost</label>
|
||||
<div class="col-sm-4">
|
||||
<InputText id="email" class="form-control" @bind-Value="Activity.Email"/>
|
||||
<ValidationMessage For="@(() => Activity.Email)"></ValidationMessage>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="row mb-1">
|
||||
<label for="referenceNumber" class="col-md-2 col-form-label">Rekvisition</label>
|
||||
<div class="col-md-4">
|
||||
<label for="referenceNumber" class="col-sm-2 col-form-label-sm">Rekvisition</label>
|
||||
<div class="col-sm-4">
|
||||
<InputText id="referenceNumber" class="form-control" @bind-Value="Activity.ReferenceNumber"/>
|
||||
<ValidationMessage For="@(() => Activity.ReferenceNumber)"></ValidationMessage>
|
||||
</div>
|
||||
|
||||
<label for="yourRef" class="col-md-2 col-form-label">Indkøber</label>
|
||||
<div class="col-md-4">
|
||||
<label for="yourRef" class="col-sm-2 col-form-label-sm">Indkøber</label>
|
||||
<div class="col-sm-4">
|
||||
<InputText id="yourRef" class="form-control" @bind-Value="Activity.YourRef"/>
|
||||
<ValidationMessage For="@(() => Activity.YourRef)"></ValidationMessage>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="row mb-1">
|
||||
<label for="orderMessage" class="col-md-2 col-form-label">Note /Kontor</label>
|
||||
<div class="col-md-4">
|
||||
<label for="orderMessage" class="col-sm-2 col-form-label-sm">Note /Kontor</label>
|
||||
<div class="col-sm-4">
|
||||
<InputTextArea id="orderMessage" class="form-control" @bind-Value="Activity.OrderMessage"/>
|
||||
<ValidationMessage For="@(() => Activity.OrderMessage)"></ValidationMessage>
|
||||
</div>
|
||||
|
||||
<label for="crmNote" class="col-md-2 col-form-label">Note /Selv</label>
|
||||
<div class="col-md-4">
|
||||
<label for="crmNote" class="col-sm-2 col-form-label-sm">Note /Selv</label>
|
||||
<div class="col-sm-4">
|
||||
<InputTextArea id="crmNote" class="form-control" @bind-Value="Activity.CrmNote"/>
|
||||
<ValidationMessage For="@(() => Activity.CrmNote)"></ValidationMessage>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="row mb-2">
|
||||
<label for="attention" class="col-md-2 col-form-label">Att.</label>
|
||||
<div class="col-md-4">
|
||||
<label for="attention" class="col-sm-2 col-form-label-sm">Att.</label>
|
||||
<div class="col-sm-4">
|
||||
<InputText id="attention" class="form-control" @bind-Value="Activity.Attention"/>
|
||||
<ValidationMessage For="@(() => Activity.Attention)"></ValidationMessage>
|
||||
</div>
|
||||
|
||||
<label for="phone" class="col-md-2 col-form-label">Tlf.</label>
|
||||
<div class="col-md-4">
|
||||
<label for="phone" class="col-sm-2 col-form-label-sm">Tlf.</label>
|
||||
<div class="col-sm-4">
|
||||
<InputText id="phone" class="form-control" @bind-Value="Activity.Phone"/>
|
||||
<ValidationMessage For="@(() => Activity.Phone)"></ValidationMessage>
|
||||
</div>
|
||||
|
||||
<label for="vatNumber" class="col-sm-2 col-form-label-sm">Org.nr.</label>
|
||||
<div class="col-sm-4">
|
||||
<InputText hidden="vatNumber" class="form-control" @bind-Value="Activity.VatNumber" />
|
||||
<ValidationMessage For="@(() => Activity.VatNumber)" />
|
||||
</div>
|
||||
</div>
|
||||
|
||||
|
||||
<div class="row">
|
||||
<div class="col-sm-4">
|
||||
<button class="btn btn-danger">Faktura</button>
|
||||
</div>
|
||||
<div class="cols-sm-3">
|
||||
<button class="btn btn-warning">Tidl. besøg</button>
|
||||
</div>
|
||||
<div class="col-sm-4">
|
||||
<button class="btn btn-success">Produkter</button>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
|
||||
<div id="this-draft" style="@(Activity.ActivityStatusEnum is "order" or "quote" ? "display: block" : "display:none")">
|
||||
@* Draft lines in draft -----------------------------------------------------*@
|
||||
<div class="row">
|
||||
|
@ -280,31 +291,31 @@ else
|
|||
aria-labelledby="deliveryHeader" data-bs-parent="#crmActivity">
|
||||
<div class="accordion-body">
|
||||
<div class="row mb-1">
|
||||
<label for="dlvName" class="col-md-2 col-form-label">Lev. Navn</label>
|
||||
<label for="dlvName" class="col-sm-2 col-form-label-sm">Lev. Navn</label>
|
||||
<div class="col-md-10">
|
||||
<InputText id="dlvName" class="form-control" @bind-Value="Activity.DlvName"/>
|
||||
</div>
|
||||
</div>
|
||||
<div class="row mb-1">
|
||||
<label for="dlvAddress1" class="col-md-2 col-form-label">Lev. Adresse</label>
|
||||
<label for="dlvAddress1" class="col-sm-2 col-form-label-sm">Lev. Adresse</label>
|
||||
<div class="col-md-10">
|
||||
<InputText id="dlvAddress1" class="form-control" @bind-Value="Activity.DlvAddress1"/>
|
||||
</div>
|
||||
</div>
|
||||
<div class="row mb-1">
|
||||
<label for="dlvAddress2" class="col-md-2 col-form-label">Lev. Adresse</label>
|
||||
<label for="dlvAddress2" class="col-sm-2 col-form-label-sm">Lev. Adresse</label>
|
||||
<div class="col-md-10">
|
||||
<InputText id="dlvAddress2" class="form-control" @bind-Value="Activity.DlvAddress2"/>
|
||||
</div>
|
||||
</div>
|
||||
<div class="row mb-1">
|
||||
<label for="dlvZipCode" class="col-md-2 col-form-label">Lev. Postnr</label>
|
||||
<label for="dlvZipCode" class="col-sm-2 col-form-label-sm">Lev. Postnr</label>
|
||||
<div class="col-md-10">
|
||||
<InputText id="dlvZipCode" class="form-control" @bind-Value="Activity.DlvZipCode"/>
|
||||
</div>
|
||||
</div>
|
||||
<div class="row mb-1">
|
||||
<label for="dlvCity" class="col-md-2 col-form-label">Lev. Bynavn</label>
|
||||
<label for="dlvCity" class="col-sm-2 col-form-label-sm">Lev. Bynavn</label>
|
||||
<div class="col-md-10">
|
||||
<InputText id="dlvCity" class="form-control" @bind-Value="Activity.DlvCity"/>
|
||||
</div>
|
||||
|
|
|
@ -39,7 +39,7 @@ public partial class AdvisorActivityCreatePage : IDisposable
|
|||
[Inject] private ILogger<AdvisorActivityCreatePage> Logger { get; set; }
|
||||
[Inject] private HttpInterceptorService Interceptor { get; set; }
|
||||
[Inject] private UserProfileService Profiles { get; set; }
|
||||
[Inject] private IToastService Toast { get; set; }
|
||||
[Inject] private IToastService Toaster { get; set; }
|
||||
[Inject] private NavigationManager Navigator { get; set; }
|
||||
[Inject] private ILocalStorageService Storage { get; set; }
|
||||
[Inject] private ICountryCatalogRepository Catalog { get; set; }
|
||||
|
@ -153,6 +153,10 @@ public partial class AdvisorActivityCreatePage : IDisposable
|
|||
}
|
||||
Working = false;
|
||||
//StateHasChanged();
|
||||
if (Company.CountryCode.ToLower() == "se" && VatUtils.SanitizeVatNumber(Activity.VatNumber).Length < 10)
|
||||
{
|
||||
Toaster.ShowWarning("Organisationsnummer skal opdateres.");
|
||||
}
|
||||
}
|
||||
|
||||
private async Task CallConfirmProductCheckModel()
|
||||
|
@ -181,17 +185,17 @@ public partial class AdvisorActivityCreatePage : IDisposable
|
|||
{
|
||||
Working = true;
|
||||
// pop a message
|
||||
Toast.ShowError("Produkt gennemgang mangler. Vent mens produkt oversigt indlæses. Gå ikke væk fra siden!", "Produkt check ...");
|
||||
Toaster.ShowError("Produkt gennemgang mangler. Vent mens produkt oversigt indlæses. Gå ikke væk fra siden!", "Produkt check ...");
|
||||
// product inventory has not been updated
|
||||
// send rpc call to sync ERP to CRM
|
||||
Toast.ShowInfo("Vent mens data synkroniseres ...", "ERP til CRM ...");
|
||||
Toaster.ShowInfo("Vent mens data synkroniseres ...", "ERP til CRM ...");
|
||||
var ts = await CustomerHistory.InvoiceErpToCrmRpc(CompanyId, Company.HistorySync);
|
||||
while (string.IsNullOrWhiteSpace(ts))
|
||||
await Task.Delay(500);
|
||||
// save pDate
|
||||
await Storage.SetItemAsync($"{CompanyId}-pDate", ts);
|
||||
// request products from backend
|
||||
Toast.ShowInfo("Vent mens produkt oversigt hentes", "CRM produkt liste");
|
||||
Toaster.ShowInfo("Vent mens produkt oversigt hentes", "CRM produkt liste");
|
||||
|
||||
CheckList = await CustomerHistory.FetchInventory(CompanyId);
|
||||
if(CheckList.Any())
|
||||
|
@ -211,6 +215,7 @@ public partial class AdvisorActivityCreatePage : IDisposable
|
|||
// Show CheckList modal
|
||||
ConfirmProductCheckModal.Show();
|
||||
}
|
||||
|
||||
private async Task ConfirmProductCheckCallback()
|
||||
{
|
||||
ConfirmProductCheckModal.Hide();
|
||||
|
@ -297,26 +302,35 @@ public partial class AdvisorActivityCreatePage : IDisposable
|
|||
// avoid duplication
|
||||
if (Working)
|
||||
return;
|
||||
// validate customer address1 - this is a required input
|
||||
// validate customer address1
|
||||
// - this is a required input
|
||||
if (string.IsNullOrWhiteSpace(Activity.Address1))
|
||||
{
|
||||
Toast.ShowError("Kunde adresse er ufuldstændig.");
|
||||
Toaster.ShowError("Kunde adresse er ufuldstændig.");
|
||||
return;
|
||||
}
|
||||
//
|
||||
// validate org number
|
||||
// - this is a required input
|
||||
// - must validate according to country rules.
|
||||
if (!VatUtils.ValidateFormat(Company.CountryCode, Activity.VatNumber))
|
||||
{
|
||||
Toaster.ShowError("Firma registreringsnummer er ikke korrekt.");
|
||||
return;
|
||||
}
|
||||
// validate input according to status
|
||||
switch (Activity.ActivityStatusEnum)
|
||||
{
|
||||
// don't accept order with no lines
|
||||
case "order" when DraftProvider.Draft.Items.Count == 0:
|
||||
Toast.ShowError("Ved bestilling skal der være en eller flere linjer i kladden.");
|
||||
Toaster.ShowError("Ved bestilling skal der være en eller flere linjer i kladden.");
|
||||
return;
|
||||
// phone number is required if first time customer
|
||||
case "order" when Company.Account is "NY" or "" && string.IsNullOrWhiteSpace(Activity.Phone):
|
||||
Toast.ShowError("Ved bestilling til ny kunde skal telefon nummer angives.");
|
||||
Toaster.ShowError("Ved bestilling til ny kunde skal telefon nummer angives.");
|
||||
return;
|
||||
// verify email address is a valid address
|
||||
case "quote" when !Utils.IsValidEmail(Activity.Email):
|
||||
Toast.ShowError("Ved tilbud skal en gyldig email adresse angives.");
|
||||
Toaster.ShowError("Ved tilbud skal en gyldig email adresse angives.");
|
||||
return;
|
||||
}
|
||||
// raise working flag
|
||||
|
@ -371,7 +385,7 @@ public partial class AdvisorActivityCreatePage : IDisposable
|
|||
// show result message
|
||||
if (result.IsSuccess)
|
||||
{
|
||||
Toast.ShowSuccess($"{result.Message}",
|
||||
Toaster.ShowSuccess($"{result.Message}",
|
||||
DraftProvider.Draft.Items.Count == 0 ? "Besøg er oprettet" : "Bestilling/Tilbud er oprettet");
|
||||
await DeleteDraft();
|
||||
Navigator.NavigateTo($"/advisor/customers");
|
||||
|
@ -380,7 +394,7 @@ public partial class AdvisorActivityCreatePage : IDisposable
|
|||
// lower working flag
|
||||
Working = false;
|
||||
// show error message
|
||||
Toast.ShowError(result.Message, "ORDRE FEJL");
|
||||
Toaster.ShowError(result.Message, "ORDRE FEJL");
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
|
@ -481,7 +495,13 @@ public partial class AdvisorActivityCreatePage : IDisposable
|
|||
{
|
||||
if (string.IsNullOrEmpty(Activity.ActivityTypeEnum) && !ReportClosed)
|
||||
{
|
||||
Toast.ShowWarning("Aktivitet type kan ikke være tom");
|
||||
Toaster.ShowWarning("Aktivitet type kan ikke være tom");
|
||||
PoFormInvalid = true;
|
||||
return;
|
||||
}
|
||||
|
||||
if (Company.CountryCode.ToLower() == "se" && VatUtils.SanitizeVatNumber(Activity.VatNumber).Length < 10)
|
||||
{
|
||||
PoFormInvalid = true;
|
||||
return;
|
||||
}
|
||||
|
|
|
@ -1,13 +1,13 @@
|
|||
{
|
||||
"appInfo": {
|
||||
"name": "Wonky Online",
|
||||
"version": "0.103.xxx",
|
||||
"version": "0.103.1",
|
||||
"rc": true,
|
||||
"sandBox": false,
|
||||
"image": "grumpy-coder.png"
|
||||
},
|
||||
"apiConfig": {
|
||||
"baseUrl": "https://dev.innotec.dk",
|
||||
"baseUrl": "https://zeta.innotec.dk",
|
||||
"catalog": "api/v2/catalog/country",
|
||||
"crmCustomers": "api/v2/crm/companies",
|
||||
"crmInventoryExt": "history/inventory",
|
||||
|
|
Loading…
Reference in a new issue