Phymnary.SugarPot.AspNetCore.Domain
1.2.2
dotnet add package Phymnary.SugarPot.AspNetCore.Domain --version 1.2.2
NuGet\Install-Package Phymnary.SugarPot.AspNetCore.Domain -Version 1.2.2
<PackageReference Include="Phymnary.SugarPot.AspNetCore.Domain" Version="1.2.2" />
<PackageVersion Include="Phymnary.SugarPot.AspNetCore.Domain" Version="1.2.2" />
<PackageReference Include="Phymnary.SugarPot.AspNetCore.Domain" />
paket add Phymnary.SugarPot.AspNetCore.Domain --version 1.2.2
#r "nuget: Phymnary.SugarPot.AspNetCore.Domain, 1.2.2"
#:package Phymnary.SugarPot.AspNetCore.Domain@1.2.2
#addin nuget:?package=Phymnary.SugarPot.AspNetCore.Domain&version=1.2.2
#tool nuget:?package=Phymnary.SugarPot.AspNetCore.Domain&version=1.2.2
Phymnary.SugarPot.AspNetCore.Domain
Shared domain contracts and primitives for SugarPot ASP.NET Core stacks.
This project contains contracts only (interfaces, attributes, DTO-like primitives, and exception types). It does not provide persistence, transport, or host-specific runtime implementations.
Package scope
The root namespace is:
Phymnary.SugarPot.AspNetCore
Main groups:
- Domain/runtime context contracts
- Entity and validation primitives
- Repository and advanced query contracts
- Auditing contracts and metadata helpers
- Multi-tenancy and security context contracts
- Domain/business exception abstractions
Contracts by area
Runtime and scope contracts
IAbortedTokenCancellationToken Get(CancellationToken cancellationToken)
IRunAtDateTimeOffset Value { get; }
IScopeBuilderAsyncServiceScope Initialize(ScopeContext context)
ScopeContextCurrentUserId,CurrentTenantId,RequestAborted
IDbFunctionProviderBeginTransactionAsync(...)UseResilientStrategyAsync(...)UseResilientStrategyWithTransactionAsync(...)
Entity contracts
IEntity- exposes
EntityDomainStatus DomainStatus
- exposes
Entity<TKey>- base class with
[Key] TKey Id { get; protected init; }
- base class with
EntityDomainStatusIsAdded,IsSoftDeleted,OnAttached(),SoftDelete()
ISoftDeleteDeletedById,DeletedAt, and defaultDelete()implementation that flags domain status
Validation contracts
IEntityValidator<TEntity>ValueTask<EntityValidationResult> ValidateAsync(...)
EntityValidationResultIsValid,Errors, plus staticValid
EntityValidationFailureDetailProperty,Message, optionalCode
Repository contracts
IRepository<TEntity>- write methods:
InsertAsync,UpsertAsync,UpdateAsync,Delete - read methods:
FindAsync,QueryAsync,AnyAsync,CountAsync - advanced query entry point:
AdvanceQuery(...)
- write methods:
IRepository<TEntity, TKey>- adds
GetAsync(TKey id, ...)
- adds
IQueryTransaction- transaction lifecycle and savepoint-related API
Advanced query contracts
IAdvanceOrderBuilding<T>IAdvancePageBuilding<T>IAdvanceSelectableBuilding<T>IAdvanceQueryBuilder<T>PaginateResult<TEntity>
The flow is designed as a staged builder:
- Order (
OrderBy/OrderByDescending) - Page (
Pick) - Optional projection (
Select) - Execute (
PaginateAsyncorBuild)
Auditing contracts
IAuditable- audit identity (
GetAuditKey) and created/updated fields
- audit identity (
IPropertyChangeAudit- immutable shape for property change records
AuditingAttribute- class-level include list of auditable properties
DisabledAuditingAttribute- class/property-level opt-out
EntityPropertyAuditingMetadata- computes if a property can be audited via
CanAudit(...)
- computes if a property can be audited via
AuditingEntityMapper<TConcrete, TImplement>- mapping hook via
Func<TConcrete, TImplement>
- mapping hook via
TrackByDomainorDatabase
Multi-tenancy and security contracts
IMultiTenantGuid TenantId { get; set; }
ICurrentTenantGuid? Id { get; }
ICurrentUserGuid? Id { get; }
Exception contracts and types
IBusinessExceptionHttpStatusCode StatusCode, optionalErrorCode
IDomainException : IBusinessException
Provided domain exception classes:
DomainNotImplementedException(422 UnprocessableContent)EntityNotFoundException(404 NotFound)EntityValidationException(400 BadRequest, includesFailures)EntityPersistenceException(409 Conflict)TenantMissingInContextException(403 Forbidden)
Error code defaults are configurable globally through DomainErrorCodeRegistry.
Extension helpers
EntityExtensions.Attach(...)- Adds an entity to an
ICollection<T>and marksDomainStatus.IsAdded
- Adds an entity to an
ServiceProviderExtensions.InheritAsyncServiceScope(...)- Builds
ScopeContextfrom current user/tenant/aborted token services and initializes a new async scope
- Builds
Note: ServiceProviderExtensions is declared in namespace Phymnary.SugarPot.AspNetCore.Api.Extensions.
Installation
NuGet:
dotnet add package Phymnary.SugarPot.AspNetCore.Domain
Usage examples
Define an entity
using Phymnary.SugarPot.AspNetCore.Entities;
public sealed class User : Entity<Guid>, ISoftDelete
{
public User(Guid id) : base(id) { }
public string Name { get; set; } = string.Empty;
public Guid? DeletedById { get; set; }
public DateTimeOffset? DeletedAt { get; set; }
}
Attach child entity and mark as added
using Phymnary.SugarPot.AspNetCore.Entities;
using Phymnary.SugarPot.AspNetCore.Extensions;
var addresses = new List<Address>();
var address = addresses.Attach(new Address(Guid.NewGuid()));
// address.DomainStatus.IsAdded == true
Implement entity validation
using Phymnary.SugarPot.AspNetCore.Entities;
public sealed class UserValidator : IEntityValidator<User>
{
public ValueTask<EntityValidationResult> ValidateAsync(
User entity,
CancellationToken cancellationToken = default)
{
if (string.IsNullOrWhiteSpace(entity.Name))
{
return ValueTask.FromResult(new EntityValidationResult
{
IsValid = false,
Errors =
[
new EntityValidationFailureDetail
{
Property = nameof(User.Name),
Message = "Name is required",
Code = "USR_NAME_REQUIRED"
}
]
});
}
return ValueTask.FromResult(EntityValidationResult.Valid);
}
}
Throw standardized domain exceptions
using Phymnary.SugarPot.AspNetCore.Exceptions;
throw new EntityNotFoundException("User not found")
.WithErrorCode("USR_NOT_FOUND");
Design intent
- Keep this package implementation-agnostic.
- Place EF Core, database, messaging, and host-specific logic in other packages.
- Use these contracts to keep domain and application layers stable and testable.
Build metadata
Version is provided via $(AspPackedVersion) from the parent build configuration.
License
See the repository root for license details.
| Product | Versions Compatible and additional computed target framework versions. |
|---|---|
| .NET | net8.0 is compatible. net8.0-android was computed. net8.0-browser was computed. net8.0-ios was computed. net8.0-maccatalyst was computed. net8.0-macos was computed. net8.0-tvos was computed. net8.0-windows was computed. net9.0 is compatible. net9.0-android was computed. net9.0-browser was computed. net9.0-ios was computed. net9.0-maccatalyst was computed. net9.0-macos was computed. net9.0-tvos was computed. net9.0-windows was computed. net10.0 is compatible. net10.0-android was computed. net10.0-browser was computed. net10.0-ios was computed. net10.0-maccatalyst was computed. net10.0-macos was computed. net10.0-tvos was computed. net10.0-windows was computed. |
-
net10.0
- Phymnary.SugarPot.Module (>= 1.0.2)
-
net8.0
- Phymnary.SugarPot.Module (>= 1.0.2)
-
net9.0
- Phymnary.SugarPot.Module (>= 1.0.2)
NuGet packages (2)
Showing the top 2 NuGet packages that depend on Phymnary.SugarPot.AspNetCore.Domain:
| Package | Downloads |
|---|---|
|
Phymnary.SugarPot.AspNetCore.Application
Package Description |
|
|
Phymnary.SugarPot.AspNetCore.EntityFrameworkCore
Package Description |
GitHub repositories
This package is not used by any popular GitHub repositories.