Hi,
I have a hangfire job which calls a class in the Core project. This class calls the settings manager to get a setting value.
string dealerNo = await _settingManager.GetSettingValueAsync(MyConstants.DealerNo);
This returns a empty string as the dealer no. Is there any configuration that needs to be done to get Settings manager to work with hangfire?
22 Answer(s)
-
0
Is
MyConstants.DealerNo
setting related to tenants and users? -
0
Its related to Tenant
-
0
You can inject the session and see. I guess there is no tenant id currently, so you got the wrong return value.
-
0
I injected the AbpSession but the tenant id returned is null.
i enclosed the code block in the using statement. as below,
`using (_unitOfWorkManager.Current.SetTenantId(_abpSession.TenantId)) {
}`
-
0
Yes, the background job has no session information. You can pass TenantId to the background job and then set the TenantId of the current session (also for userid)
see: https://aspnetboilerplate.com/Pages/Documents/Abp-Session#overriding-current-session-values
-
0
Tha job is a recurring job and i have registerd it in the WebCoreModule. How can i then pass in the tenant id?
-
0
Please share your code (including AppSettingProvider)
-
0
Below is the App setting code,
public static class PasstimeManagement { public const string PasstimeAddress = "PasstimeAddress"; public const string Password = "App.Passtime.Password"; public const string UserName = "App.Passtime.UserName"; public const string DealerNo = "App.Passtime.DealerNo"; }
Below is the App settings provider code,
private IEnumerable<SettingDefinition> GetPasstimeSettings() { return new[] { new SettingDefinition(AppSettings.PasstimeManagement.PasstimeAddress, GetFromAppSettings(AppSettings.PasstimeManagement.PasstimeAddress)), new SettingDefinition(AppSettings.PasstimeManagement.Password, GetFromAppSettings(AppSettings.PasstimeManagement.Password, ""), scopes: SettingScopes.Tenant), new SettingDefinition(AppSettings.PasstimeManagement.UserName, GetFromAppSettings(AppSettings.PasstimeManagement.UserName, ""), scopes: SettingScopes.Tenant), new SettingDefinition(AppSettings.PasstimeManagement.DealerNo, GetFromAppSettings(AppSettings.PasstimeManagement.DealerNo, ""), scopes: SettingScopes.Tenant) }; }
Below is the code in the job,
[UnitOfWork] public virtual async Task SendDeviceUnlockNotification() { using (_unitOfWorkManager.Current.SetTenantId(_abpSession.TenantId)) { string dealerNo = await _settingManager.GetSettingValueAsync(PasstimeManagement.DealerNo); ///more lines below } }
-
0
What is the function of the
SendDeviceUnlockNotification
method? Is it a notification to all tenants? -
0
This function should run periodically and check the database for device unlock requests. When a record is found, the job should pick it up and call a external service to unlock the device. The parameters for the request is stored tenant wise. (e.g. the dealer no is chaning from tenant to tenant).
If the device is unlocked, then a push notification is sent via App center to the mobile.
-
0
The problem now is that this requires the correct tenant ID (because you need to get the settings for this tenant), can you get the tenant ID via device unlock requests?
Then call
using (_unitOfWorkManager.Current.SetTenantId(YourTenantId))
-
0
No. The external service does not have the tenant id.
-
0
I don't know your specific business. As I said above, if you want to get the tenant's settings you need to find a way to get TenantId.
-
0
I hardcoded the tenant id for testing as below,
_unitOfWorkManager.Current.SetTenantId(2)
but still the setting value is empty.
-
0
You can see if there is a setting information for the tenant with id 2 in the AbpSettings table of the database.
-
0
Yes there is a setting. still the setting is not returned
-
0
Do you have a Telegram or skype?
-
0
Show screenshot of records in database.
-
0
Hi,
I got the code to work partially. i was able to set the tenant using the _abpSession.Use(2, null) hardcoding 2 as the tenant id for debugging. and it worked.
I can get the Tenant id from the User table. The Payment entity has a loan mapped to it. The Loan has the User. So now when i want to get the user using usermanager, since it is outside the unit of work manager (i guess), I am getting a error stating that the user id is not found. But user id is available in the table.
//get the tenant id for the payment User user = await _userManager.GetUserByIdAsync(payment.Loan.UserId);
Is there a way i can include the User as well when i am getting the payment detiails. There is a navigation property to User table from the loan object.
Payment -> Loan -> User
Any help is highly appriciated.
[UnitOfWork] public virtual async Task SendDeviceUnlockNotification() { try { //get the device unlock requests from the db IList<Payment> payments = _paymentRepository.GetAllIncluding(p => p.Loan).Where(p => p.DeviceUnlockStatus == "Requested").ToList(); //loop through the payments and check the device unlock status foreach (Payment payment in payments) { //get the tenant id for the payment User user = await _userManager.GetUserByIdAsync(payment.Loan.UserId);
using (_abpSession.Use(user.TenantId, null)) { using (_unitOfWorkManager.Current.SetTenantId(_abpSession.TenantId)) { string status = await _passtimeDomainService.GetDeviceStatus(payment.Loan.VIN); if (status.ToLower() == "enabled") { //update the device unlock status payment.DeviceUnlockStatus = "Unlocked"; await _paymentRepository.UpdateAsync(payment); //send push notification NotificationData notificationData = new NotificationData { UserName = user.UserName, Name = "Vehicle Unlocked Notification", Title = "Vehicle Unlocked", Body = "Your vehicle has been unlocked" }; await _appCentre.NotifyAsync(notificationData); } } } } _unitOfWorkManager.Current.SaveChanges(); } catch (Exception ex) { //log any exception } }
-
0
I managed to get this to work. I disabled the filters in the unit of work manager. Then it returned the user.
_unitOfWorkManager.Current.DisableFilter("MayHaveTenant", "MustHaveTenant"); //get the tenant id for the payment User user = await _userManager.Users.Where(u=>u.Id == payment.Loan.UserId).FirstOrDefaultAsync();
Please let me know any issues in the above solution.
-
0
It is fine, but will not work if you use multiple (tenant-specific) databases.
-
0
I am using single database. so i think i will not run into a problem.
Thanks All for the support.