Files
andy 9f22b522df v1.3.0 Restructure Saxonite workspace and upgrade to .NET 10 (#1)
Move Saxonite’s projects into a dedicated `Workspace` folder and align the solution with .NET 10 and the current Common workspace. Update encryption integration, test project structure and coverage, and repository guidance and upgrade notes.

- Relocate application and library projects while retaining Git rename history.
- Split tests into Admin, Online, and Shared projects; add representative behavioral and serialization tests.
- Update Common integration, application version, and repository documentation.

Application version: 1.3.0

Reviewed-on: #1
Co-authored-by: andy <andy@sarand.com>
2026-10-16 18:24:16 +01:00

234 lines
9.1 KiB
C#

using Sarand.Net.Standard.Base.App;
using Sarand.Net.Standard.Base.Bus;
using Sarand.Net.Standard.Base.Core;
using Sarand.Net.Standard.Base.Utils;
using Saxonite.Net.Standard.Base.App;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Net.Mail;
using System.Text;
using System.Xml.Linq;
namespace Saxonite.Net.Standard.Base.Bus
{
//=======================================================================
// Contact data - associated with Organisations, Users etc.
//=======================================================================
public class SaxSportContactsData
{
//-------------------------------------------------------------------
// Definitions.
private static readonly String ElementName_Contacts = "Contacts";
private static readonly String ElementName_Contact = "Contact";
private static readonly String AttributeName_Type = "Type";
private static readonly String ElementName_Type = "Type";
private static readonly String ElementName_UserAccountId = "UserAccountId";
private static readonly String ElementName_Title = "Title";
private static readonly String ElementName_FirstName = "FirstName";
private static readonly String ElementName_LastName = "LastName";
private static readonly String ElementName_Phone = "Phone";
private static readonly String ElementName_EmailAddress = "EmailAddress";
//-------------------------------------------------------------------
// Data members.
private class ContactData
{
public Sax.SportContactType ContactType { get; set; }
public SysId UserAccountId { get; set; }
public String Title { get; set; }
public String FirstName { get; set; }
public String LastName { get; set; }
public String EmailAddress { get; set; }
public String Phone { get; set; }
}
private Dictionary<Sax.SportContactType, ContactData> contacts { get; } = new Dictionary<Sax.SportContactType, ContactData>();
//-------------------------------------------------------------------
// Construction - from serialised data.
public SaxSportContactsData(String contactsData = "")
{
FromXml(contactsData);
}
//-------------------------------------------------------------------
// Properties.
public List<Sax.SportContactType> ContactTypes { get { return contacts.Keys.ToList(); } }
//-------------------------------------------------------------------
// Utilities.
/// <summary>Get the contact for the specified type.</summary>
private ContactData GetContactData(Sax.SportContactType contactType)
{
if ((int)contactType < 1) return null;
ContactData contact = contacts.GetValueOrDefault(contactType, null);
if (contact == null)
contacts.Add(contactType, contact = new ContactData() { ContactType = contactType });
return contact;
}
//-------------------------------------------------------------------
// Contacts.
//-------------------------------------------------------------------
/// <summary>Extract the title associated with the specified type.</summary>
public String GetContactTitle(Sax.SportContactType contactType)
{
return contacts.GetValueOrDefault(contactType, new ContactData()).Title;
}
/// <summary>Extract the first name associated with the specified type.</summary>
public String GetContactFirstName(Sax.SportContactType contactType)
{
return contacts.GetValueOrDefault(contactType, new ContactData()).FirstName;
}
/// <summary>Extract the last name associated with the specified type.</summary>
public String GetContactLastName(Sax.SportContactType contactType)
{
return contacts.GetValueOrDefault(contactType, new ContactData()).LastName;
}
/// <summary>Extract the email address associated with the specified type.</summary>
public String GetContactEmailAddress(Sax.SportContactType contactType)
{
return contacts.GetValueOrDefault(contactType, new ContactData()).EmailAddress;
}
/// <summary>Extract the phone associated with the specified type.</summary>
public String GetContactPhone(Sax.SportContactType contactType)
{
return contacts.GetValueOrDefault(contactType, new ContactData()).Phone;
}
/// <summary>Set the name associated with the specified contact.</summary>
public bool SetContactName(Sax.SportContactType contactType, String title, String firstName, String lastName)
{
if ((int)contactType < 1 || lastName.IsEmpty()) return false;
ContactData contact = GetContactData(contactType);
if (contact == null) return false;
contact.Title = title;
contact.FirstName = firstName;
contact.LastName = lastName;
return true;
}
/// <summary>Set the email address associated with the specified contact.</summary>
public bool SetContactEmailAddress(Sax.SportContactType contactType, String emailAddress)
{
if ((int)contactType < 1 || emailAddress.IsEmpty()) return false;
ContactData contact = GetContactData(contactType);
if (contact == null) return false;
contact.EmailAddress = emailAddress;
return true;
}
/// <summary>Set the phone associated with the specified contact.</summary>
public bool SetContactPhone(Sax.SportContactType contactType, String phone)
{
if ((int)contactType < 1 || phone.IsEmpty()) return false;
ContactData contact = GetContactData(contactType);
if (contact == null) return false;
contact.Phone = phone;
return true;
}
//-------------------------------------------------------------------
/// <summary>Clear the value associated with the specified method.</summary>
public bool ClearContact(Sax.SportContactType contactType)
{
return contacts.Remove(contactType);
}
/// <summary>Clear all contact methods.</summary>
public void ClearContacts()
{
contacts.Clear();
}
//-------------------------------------------------------------------
// Serialisation.
//-------------------------------------------------------------------
/// <summary>Serialise as XML.</summary>
public String ToXml()
{
try
{
XDocument doc = new XDocument();
XElement contactsElement = doc.AppendElement(ElementName_Contacts);
foreach (ContactData contactData in contacts.Values)
{
if ((int)contactData.ContactType < 1 || (!SysId.IsValid(contactData.UserAccountId) && StringUtil.IsBlank(contactData.LastName))) continue;
XElement contactElement = contactsElement.AppendElement(ElementName_Contact);
contactElement.SetAttribute(AttributeName_Type, ((int)contactData.ContactType).ToString());
contactElement.AppendElement(ElementName_Type, contactData.ContactType.ToString());
if (!StringUtil.IsBlank(contactData.Title))
contactElement.AppendElement(ElementName_Title, contactData.Title);
if (!StringUtil.IsBlank(contactData.FirstName))
contactElement.AppendElement(ElementName_FirstName, contactData.FirstName);
if (!StringUtil.IsBlank(contactData.LastName))
contactElement.AppendElement(ElementName_LastName, contactData.LastName);
if (!StringUtil.IsBlank(contactData.EmailAddress))
contactElement.AppendElement(ElementName_EmailAddress, contactData.EmailAddress);
if (!StringUtil.IsBlank(contactData.Phone))
contactElement.AppendElement(ElementName_Phone, contactData.Phone);
}
return doc.GetXml();
}
catch (Exception exc)
{
SaLogger.Warn($"{SysUtil.Fn} " + ExceptionUtil.GetLogMessage(exc));
}
return "";
}
//-------------------------------------------------------------------
/// <summary>Deserialise from XML data.</summary>
private void FromXml(String contactsData)
{
contacts.Clear();
if (StringUtil.IsEmpty(contactsData)) return;
try
{
// Load XML data.
XDocument doc = XDocument.Parse(contactsData);
XElement rootElement = doc.Root;
foreach (XElement rootChildElement in rootElement.GetChildElements())
{
String rootChildElementName = rootChildElement.GetLocalName();
if (rootChildElementName.EqualsCI(ElementName_Contact))
{
// Contact.
String contactTypeValue = rootChildElement.GetChildText(ElementName_Type);
Sax.SportContactType contactType = EnumUtil.ParseEnum(contactTypeValue, Sax.SportContactType.Unknown);
if (contactType != Sax.SportContactType.Unknown)
{
ContactData contactData = new ContactData()
{
ContactType = contactType,
UserAccountId = SysId.ToSysId(rootChildElement.GetChildText(ElementName_UserAccountId)),
Title = rootChildElement.GetChildText(ElementName_Title),
FirstName = rootChildElement.GetChildText(ElementName_FirstName),
LastName = rootChildElement.GetChildText(ElementName_LastName),
EmailAddress = rootChildElement.GetChildText(ElementName_EmailAddress),
Phone = rootChildElement.GetChildText(ElementName_Phone),
};
contacts.Add(contactType, contactData);
}
else SaLogger.Warn($"{SysUtil.Fn} Unrecognised contact type: " + contactType);
}
else SaLogger.Warn($"{SysUtil.Fn} Unexpected 'Root' child element: " + rootChildElementName);
}
}
catch (Exception exc)
{
SaLogger.Warn($"{SysUtil.Fn} " + ExceptionUtil.GetLogMessage(exc));
}
}
//-------------------------------------------------------------------
}
//=======================================================================
}