Skip to main content

Request Session

Throughout the projects using the UpDevs SDK you're able to access some session data through the property RequestSession. It is available in several places. The available properties are:

PropertyDescription
IdSession identifier.
CustomDataCustom data. Maybe provided by the UpDevs SDK, but usually are user-defined properties.
LoggedUserObject containing the logged user's information.
HttpInfoHTTP request information.
TenantTenant.
IsLoggedInWhether the user is logged in.
FormChangedPropertiesNames of all properties that were changed in the object (if updating a record).

Availability

In this section you will find out how to access RequestSession.

App/Domain Services

Inside all application and domain services you have access to RequestSession through the globally available property:

public class MyDomainService : BaseListDomainService<MyEntity, MyResponse>,
IMyDomainService
{
public MyDomainService(IServiceProvider serviceProvider, IUnitOfWork unitOfWork)
: base(serviceProvider, unitOfWork) { }

public void MyMethod()
{
if (!RequestSession.IsLoggedIn || RequestSession.Tenant != "MyAllowedTenant")
{
return;
}

// Perform operations...
}
}

Events

Inside both before and after save event handlers you have access to RequestSession through the notification parameter:

public class UserBeforeSave : BeforeSaveEntityNotificationHandler<User>
{
public override async Task Handle(
BeforeSaveEntityNotification<User> notification,
CancellationToken cancellationToken
)
{
notification.Entity.UpdatedByUserId = notification.RequestSession.LoggedUser.UserId;

if (notification.EntityState == EntityState.Added)
{
var validationToken = new ValidationToken
{
CreationDate = DateTime.UtcNow,
ExpirationDate = DateTime.UtcNow.AddDays(1),
Token = $"{RandomProvider.GetThreadRandom().Next(100000, 1000000)}"
};
notification.Entity.ValidationToken =
await notification.UnitOfWork.GetRepository<ValidationToken>().AddAsync(
validationToken,
cancellationToken
);
}
}
}

Validators

Inside validators, you have access to RequestSession through the unitOfWork parameter:

public class UserValidator : BaseEntityValidator<User>
{
private readonly ValidationErrorContext _validationContext;

public UserValidator(ValidationErrorContext validationContext)
: base(validationContext)
{
_validationContext = validationContext;
}

public override async Task Validate(
IUnitOfWork unitOfWork,
User current,
User original,
EntityState state
)
{
switch (state)
{
case EntityState.Added:
// ...
break;
case EntityState.Modified:
if (unitOfWork.RequestSession.LoggedUser.UserId != original.Id)
{
_validationContext.AddError(
Constants.Validator.Hidden,
"You can only edit your own user data."
);
}
// ...
}
}
}

Specifications

Inside all specifications you have access to RequestSession through the globally available property:

public class DoctorsWhoMadeTransfersInPastMonthsSpecification 
: BaseSpecification<HistoryItem>
{
private readonly int _pastMonths;

public DoctorsWhoMadeTransfersInPastMonthsSpecification(int pastMonths = 3)
{
_pastMonths = pastMonths;
PageSize = 10;
Include = historyItem => historyItem.Include(hi => hi.Doctor);
OrderBy = historyItem => historyItem.OrderBy(hi => hi.CreationDate)
}

public override Expression<Func<CaseHistoryItem, bool>> IsSatisfiedBy()
{
var startDate = DateTime.UtcNow.AddMonths(-_pastMonths);
return historyItem => historyItem.IsTransferRelated
&& historyItem.DoctorId != null
&& historyItem.CreatedByUserId == RequestSession.LoggedUser.UserId
&& historyItem.CreationDate >= startDate;
}
}

DatabaseContext

Inside your database context you have access to RequestSession through the globally available property, inside the Setup method:

public class DatabaseContext : BaseContext
{
public DatabaseContext()
{
SourceAssemblies.Add(typeof(DatabaseContext).Assembly);
}

protected override void Setup(DbContextOptionsBuilder optionsBuilder)
{
if (optionsBuilder.IsConfigured)
{
return;
}

if (RequestSession.CustomData["MyKey"].ToString() == "MyValue")
{
// Do something.
}

optionsBuilder.UseSqlServer(GetConnectionString());
}
}

UnitOfWork

Wherever you have access to IUnitOfWork you can access the RequestSession property, like UnitOfWork.RequestSession.

Repositories

Inside all repositories you have access to RequestSession through the globally available property:

public class DoctorRepository : Repository<Doctor>
{
public DoctorRepository(
DbContext dbContext,
DataEfExceptionMessagesResource dataEfExceptionMessagesResource
) : base(dbContext, dataEfExceptionMessagesResource) { }

public async Task UpdateCustomData()
{
if (!RequestSession.IsLoggedIn || RequestSession.Tenant != "MyAllowedTenant")
{
return;
}

// Perform operations...
return;
}
}

Custom Data

If you'd like to share data throughout the services, validators, etc., you can add them inside RequestSession's CustomData property. This can be done in all the places you can access the RequestSession, for example:

Setting data:

RequestSession.CustomData.TryAdd("TestKey", "TestValue");

Reading data:

var testValue = RequestSession.CustomData["TestKey"];

Inside Controllers

Since you don't have access to the RequestSession property inside controllers, you need to invoke the GetRequestSession extension method:

public class MyController : BaseApiController
{
[HttpGet("my-action")]
public IActionResult MyAction()
{
HttpContext.GetRequestSession().CustomData.TryAdd("TestKey", "TestValue");
// ...
}
}