# AbpMudBlazor
**Repository Path**: abduwaris/abp-mud-blazor
## Basic Information
- **Project Name**: AbpMudBlazor
- **Description**: No description available
- **Primary Language**: Unknown
- **License**: MIT
- **Default Branch**: main
- **Homepage**: None
- **GVP Project**: No
## Statistics
- **Stars**: 0
- **Forks**: 1
- **Created**: 2023-11-25
- **Last Updated**: 2024-04-30
## Categories & Tags
**Categories**: Uncategorized
**Tags**: None
## README
# MudBlazor Theme in ABP Blazor WebAssembly FINAL
## Introduction
In this part, I will show you how to customize/override pre-built Blazor pages of the [Identity Module](https://docs.abp.io/en/abp/latest/Modules/Identity) using [MudBlazor](https://www.mudblazor.com/) components. I assume that Tenant and Setting management pages are rarely used by end-users, so these modules are not covered in this sample to keep it short. You can customize every page using the principles shown here. All you need to do is:
1. Deriving a class that inherits the class you want to override
2. And adding the following attributes to the derived class:
```razor
@* to the razor file *@
@attribute [ExposeServices(typeof(BASE-CLASS))]
@attribute [Dependency(ReplaceServices = true)]
```
```charp
// or to the C# file
[ExposeServices(typeof(BASE-CLASS))]
[Dependency(ReplaceServices = true)]
```
See [Blazor UI: Customization / Overriding Components](https://docs.abp.io/en/abp/latest/UI/Blazor/Customization-Overriding-Components) for more information.
## 16. Make Sure You Have Completed Previous Parts
You must complete the steps in [Part 1](https://github.com/yellow-dragon-cloud/AbpMudBlazor), [Part 2](https://github.com/yellow-dragon-cloud/AbpMudBlazor2), [Part 3](https://github.com/yellow-dragon-cloud/AbpMudBlazor3), and [Part 4](https://github.com/yellow-dragon-cloud/AbpMudBlazor4) to continue.
## 17. Create Required Files
Create `Identity` folder under `Acme.BookStore.Blazor/Pages/`.
Create the following files in this folder:
1. `MudPermissionManagementModal.razor`
2. `MudPermissionManagementModal.razor.cs`
3. `MudRoleManagement.razor`
4. `MudRoleManagement.razor.cs`
5. `MudUserManagement.razor`
6. `MudUserManagement.razor.cs`
## 18. Modify These Files' Content As Shown Below
1. `MudPermissionManagementModal.razor`
```razor
@using Microsoft.Extensions.Localization
@using Volo.Abp.PermissionManagement.Blazor.Components
@using Volo.Abp.PermissionManagement.Localization
@inherits PermissionManagementModal
@L["Permissions"] - @_entityDisplayName
@L["SelectAllInAllTabs"]
@if (_groups != null)
{
@* ?! *@
@foreach (var group in _groups)
{
@group.DisplayName
@L["SelectAllInThisTab"]
@foreach (var permission in group.Permissions)
{
@GetShownName(permission)
}
}
}
@L["Cancel"]
@L["Save"]
```
***
2. `MudPermissionManagementModal.razor.cs`
```csharp
using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
using Microsoft.AspNetCore.Components;
using MudBlazor;
using Volo.Abp.AspNetCore.Components.Web.Configuration;
using Volo.Abp.PermissionManagement;
using Volo.Abp.PermissionManagement.Localization;
namespace Acme.BookStore.Blazor.Pages.Identity;
public partial class MudPermissionManagementModal
{
[Inject] private IPermissionAppService PermissionAppService { get; set; }
[Inject] private ICurrentApplicationConfigurationCacheResetService CurrentApplicationConfigurationCacheResetService { get; set; }
private bool _isVisible;
protected virtual DialogOptions DialogOptions
{
get => new()
{
CloseButton = true,
CloseOnEscapeKey = true,
DisableBackdropClick = true,
MaxWidth = MaxWidth.Medium
};
}
private string _providerName;
private string _providerKey;
private string _entityDisplayName;
private List _groups;
private readonly List _disabledPermissions = new();
private int _grantedPermissionCount = 0;
private int _notGrantedPermissionCount = 0;
private bool GrantAll
{
get => _notGrantedPermissionCount == 0;
set
{
if (_groups == null) return;
_grantedPermissionCount = 0;
_notGrantedPermissionCount = 0;
foreach (var permission in _groups.SelectMany(x => x.Permissions))
{
if (IsDisabledPermission(permission)) continue;
permission.IsGranted = value;
if (value)
_grantedPermissionCount++;
else
_notGrantedPermissionCount++;
}
}
}
public MudPermissionManagementModal()
{
LocalizationResource = typeof(AbpPermissionManagementResource);
}
public async Task OpenDialogAsync(string providerName, string providerKey, string entityDisplayName = null)
{
try
{
_providerName = providerName;
_providerKey = providerKey;
var result = await PermissionAppService.GetAsync(_providerName, _providerKey);
_entityDisplayName = entityDisplayName ?? result.EntityDisplayName;
_groups = result.Groups;
_grantedPermissionCount = 0;
_notGrantedPermissionCount = 0;
foreach (var permission in _groups.SelectMany(x => x.Permissions))
{
if (permission.IsGranted && permission.GrantedProviders.All(x => x.ProviderName != _providerName))
{
_disabledPermissions.Add(permission);
continue;
}
if (permission.IsGranted)
_grantedPermissionCount++;
else
_notGrantedPermissionCount++;
}
_isVisible = true;
StateHasChanged();
}
catch (Exception e)
{
await HandleErrorAsync(e);
}
}
private async Task CloseModalAsync()
{
await InvokeAsync(() => { _isVisible = false; });
}
private async Task SaveAsync()
{
try
{
var updateDto = new UpdatePermissionsDto
{
Permissions = _groups
.SelectMany(g => g.Permissions)
.Select(p => new UpdatePermissionDto { IsGranted = p.IsGranted, Name = p.Name })
.ToArray()
};
await PermissionAppService.UpdateAsync(_providerName, _providerKey, updateDto);
await CurrentApplicationConfigurationCacheResetService.ResetAsync();
await CloseModalAsync();
}
catch (Exception e)
{
await HandleErrorAsync(e);
}
}
private void GroupGrantAllChanged(bool value, PermissionGroupDto permissionGroup)
{
foreach (var permission in permissionGroup.Permissions)
{
if (!IsDisabledPermission(permission))
SetPermissionGrant(permission, value);
}
}
private void PermissionChanged(bool value, PermissionGroupDto permissionGroup, PermissionGrantInfoDto permission)
{
SetPermissionGrant(permission, value);
if (value && permission.ParentName != null)
{
var parentPermission = GetParentPermission(permissionGroup, permission);
SetPermissionGrant(parentPermission, true);
}
else if (value == false)
{
var childPermissions = GetChildPermissions(permissionGroup, permission);
foreach (var childPermission in childPermissions)
{
SetPermissionGrant(childPermission, false);
}
}
}
private void SetPermissionGrant(PermissionGrantInfoDto permission, bool value)
{
if (permission.IsGranted == value) return;
if (value)
{
_grantedPermissionCount++;
_notGrantedPermissionCount--;
}
else
{
_grantedPermissionCount--;
_notGrantedPermissionCount++;
}
permission.IsGranted = value;
}
private static PermissionGrantInfoDto GetParentPermission(PermissionGroupDto permissionGroup, PermissionGrantInfoDto permission)
{
return permissionGroup.Permissions.First(x => x.Name == permission.ParentName);
}
private static List GetChildPermissions(PermissionGroupDto permissionGroup, PermissionGrantInfoDto permission)
{
return permissionGroup.Permissions.Where(x => x.Name.StartsWith(permission.Name)).ToList();
}
private bool IsDisabledPermission(PermissionGrantInfoDto permissionGrantInfo)
{
return _disabledPermissions.Any(x => x == permissionGrantInfo);
}
private string GetShownName(PermissionGrantInfoDto permissionGrantInfo)
{
if (!IsDisabledPermission(permissionGrantInfo))
return permissionGrantInfo.DisplayName;
return string.Format(
"{0} ({1})",
permissionGrantInfo.DisplayName,
permissionGrantInfo.GrantedProviders
.Where(p => p.ProviderName != _providerName)
.Select(p => p.ProviderName)
.JoinAsString(", ")
);
}
}
```
***
3. `MudRoleManagement.razor`
```razor
@using MudBlazor;
@using Blazorise
@using Blazorise.DataGrid
@using Volo.Abp.BlazoriseUI
@using Volo.Abp.BlazoriseUI.Components
@using Volo.Abp.Identity
@using Microsoft.AspNetCore.Authorization
@using Volo.Abp.PermissionManagement.Blazor.Components
@using Volo.Abp.Identity.Localization
@using Volo.Abp.AspNetCore.Components.Web
@using Volo.Abp.AspNetCore.Components.Web.Theming
@using Volo.Abp.BlazoriseUI.Components.ObjectExtending
@using Volo.Abp.AspNetCore.Components.Web.Theming.Layout
@using Volo.Abp.DependencyInjection
@using Volo.Abp.Identity.Blazor.Pages.Identity
@attribute [Authorize(IdentityPermissions.Roles.Default)]
@attribute [ExposeServices(typeof(RoleManagement))]
@attribute [Dependency(ReplaceServices = true)]
@inject AbpBlazorMessageLocalizerHelper LH
@inherits RoleManagement
@* ************************* DATA GRID ************************* *@
@L["Roles"]
@L["NewRole"]
@if (HasUpdatePermission)
{
}
@if (HasDeletePermission)
{
}
@if (context.Item.IsDefault)
{
@L["DisplayName:IsDefault"]
}
@if (context.Item.IsPublic)
{
@L["DisplayName:IsPublic"]
}
@* ************************* CREATE MODAL ************************* *@
@if (HasCreatePermission)
{
@L["NewRole"]
NewEntity.Name) />
@L["DisplayName:IsDefault"]
@L["DisplayName:IsPublic"]
@L["Cancel"]
@L["Save"]
}
@* ************************* EDIT MODAL ************************* *@
@if (HasUpdatePermission)
{
@L["Edit"]
EditingEntity.Name) />
@L["DisplayName:IsDefault"]
@L["DisplayName:IsPublic"]
@L["Cancel"]
@L["Save"]
}
@if (HasManagePermissionsPermission)
{
}
```
***
4. `MudRoleManagement.razor.cs`
```csharp
using System.Threading.Tasks;
using MudBlazor;
using Volo.Abp.Application.Dtos;
using Volo.Abp.Identity;
namespace Acme.BookStore.Blazor.Pages.Identity;
public partial class MudRoleManagement
{
private MudForm _createForm;
private MudForm _editForm;
private bool _createDialogVisible;
private bool _editDialogVisible;
private MudDataGrid _dataGrid;
private MudPermissionManagementModal _permissionManagementModal;
protected async Task> LoadServerData(GridState state)
{
if (GetListInput is PagedAndSortedResultRequestDto pageResultRequest)
{
pageResultRequest.MaxResultCount = state.PageSize;
pageResultRequest.SkipCount = state.Page * state.PageSize;
}
var result = await AppService.GetListAsync(GetListInput);
return new()
{
Items = result.Items,
TotalItems = (int)result.TotalCount
};
}
protected override Task OpenCreateModalAsync()
{
NewEntity = new();
_createDialogVisible = true;
return Task.CompletedTask;
}
protected override Task CloseCreateModalAsync()
{
_createDialogVisible = false;
return Task.CompletedTask;
}
protected override async Task CreateEntityAsync()
{
if (_createForm.IsValid)
{
var createDto = MapToCreateInput(NewEntity);
await AppService.CreateAsync(createDto);
await _dataGrid.ReloadServerData();
_createDialogVisible = false;
}
}
protected override Task OpenEditModalAsync(IdentityRoleDto entity)
{
EditingEntityId = entity.Id;
EditingEntity = MapToEditingEntity(entity);
_editDialogVisible = true;
return Task.CompletedTask;
}
protected override Task CloseEditModalAsync()
{
_editDialogVisible = false;
return Task.CompletedTask;
}
protected override async Task UpdateEntityAsync()
{
if (_editForm.IsValid)
{
await base.UpdateEntityAsync();
await _dataGrid.ReloadServerData();
_editDialogVisible = false;
}
}
protected override async Task DeleteEntityAsync(IdentityRoleDto entity)
{
if (await Message.Confirm(GetDeleteConfirmationMessage(entity)))
{
await base.DeleteEntityAsync(entity);
await _dataGrid.ReloadServerData();
}
}
protected override Task OnUpdatedEntityAsync()
{
return Task.CompletedTask;
}
protected virtual async Task OpenPermissionsModalAsync(IdentityRoleDto entity)
{
await _permissionManagementModal.OpenDialogAsync(PermissionProviderName, entity.Name);
}
protected virtual DialogOptions DialogOptions
{
get => new()
{
CloseButton = true,
CloseOnEscapeKey = true,
DisableBackdropClick = true
};
}
}
```
***
5. `MudUserManagement.razor`
```razor
@using Microsoft.AspNetCore.Authorization
@using Volo.Abp.DependencyInjection
@using Volo.Abp.PermissionManagement.Blazor.Components
@using Volo.Abp.Identity.Localization
@using Volo.Abp.AspNetCore.Components.Web.Theming.Layout
@using Volo.Abp.Identity
@using Volo.Abp.Identity.Blazor.Pages.Identity
@attribute [Authorize(IdentityPermissions.Users.Default)]
@attribute [ExposeServices(typeof(UserManagement))]
@attribute [Dependency(ReplaceServices = true)]
@inject AbpBlazorMessageLocalizerHelper LH
@inherits UserManagement
@* ************************* DATA GRID ************************* *@
@L["Users"]
@L["NewUser"]
@if (HasUpdatePermission)
{
}
@if (HasDeletePermission)
{
}
@* ************************* CREATE MODAL ************************* *@
@if (HasCreatePermission)
{
@L["NewUser"]
@L["DisplayName:IsActive"]
@L["DisplayName:LockoutEnabled"]
@if (NewUserRoles != null)
{
@foreach (var role in NewUserRoles)
{
@role.Name
}
}
else
{
N/A
}
@L["Cancel"]
@L["Save"]
}
@* ************************* EDIT MODAL ************************* *@
@if (HasUpdatePermission)
{
@L["Edit"]
@L["DisplayName:IsActive"]
@L["DisplayName:LockoutEnabled"]
@if (EditUserRoles != null)
{
@foreach (var role in EditUserRoles)
{
@role.Name
}
}
else
{
N/A
}
@L["Cancel"]
@L["Save"]
}
@if (HasManagePermissionsPermission)
{
}
```
***
6. `MudUserManagement.razor.cs`
```csharp
using System.Linq;
using System.Threading.Tasks;
using MudBlazor;
using Volo.Abp.Application.Dtos;
using Volo.Abp.Identity;
using Volo.Abp.Identity.Blazor.Pages.Identity;
namespace Acme.BookStore.Blazor.Pages.Identity;
public partial class MudUserManagement
{
private MudForm _createForm;
private MudForm _editForm;
private bool _createDialogVisible;
private bool _editDialogVisible;
private MudDataGrid _dataGrid;
private MudPermissionManagementModal _permissionManagementModal;
protected async Task> LoadServerData(GridState state)
{
if (GetListInput is PagedAndSortedResultRequestDto pageResultRequest)
{
pageResultRequest.MaxResultCount = state.PageSize;
pageResultRequest.SkipCount = state.Page * state.PageSize;
}
var result = await AppService.GetListAsync(GetListInput);
return new()
{
Items = result.Items,
TotalItems = (int)result.TotalCount
};
}
protected override Task OpenCreateModalAsync()
{
NewEntity = new() { IsActive = true };
NewUserRoles = Roles.Select(i => new AssignedRoleViewModel
{
Name = i.Name,
IsAssigned = i.IsDefault
}).ToArray();
_createDialogVisible = true;
return Task.CompletedTask;
}
protected override Task CloseCreateModalAsync()
{
_createDialogVisible = false;
return Task.CompletedTask;
}
protected override async Task CreateEntityAsync()
{
if (_createForm.IsValid)
{
var createDto = MapToCreateInput(NewEntity);
await AppService.CreateAsync(createDto);
await _dataGrid.ReloadServerData();
await CloseCreateModalAsync();
}
}
protected override async Task OpenEditModalAsync(IdentityUserDto entity)
{
var userRoleNames = (await AppService.GetRolesAsync(entity.Id)).Items.Select(r => r.Name).ToList();
EditUserRoles = Roles.Select(x => new AssignedRoleViewModel
{
Name = x.Name,
IsAssigned = userRoleNames.Contains(x.Name)
}).ToArray();
EditingEntityId = entity.Id;
EditingEntity = MapToEditingEntity(entity);
_editDialogVisible = true;
}
protected override Task CloseEditModalAsync()
{
_editDialogVisible = false;
return Task.CompletedTask;
}
protected override async Task UpdateEntityAsync()
{
if (_editForm.IsValid)
{
await AppService.UpdateAsync(EditingEntityId, EditingEntity);
await _dataGrid.ReloadServerData();
await CloseEditModalAsync();
}
}
protected override async Task DeleteEntityAsync(IdentityUserDto entity)
{
if (await Message.Confirm(GetDeleteConfirmationMessage(entity)))
{
await base.DeleteEntityAsync(entity);
await _dataGrid.ReloadServerData();
}
}
protected override Task OnUpdatedEntityAsync()
{
return Task.CompletedTask;
}
protected virtual async Task OpenPermissionsModalAsync(IdentityUserDto entity)
{
await _permissionManagementModal.OpenDialogAsync(
PermissionProviderName, entity.Id.ToString());
}
protected virtual DialogOptions DialogOptions
{
get => new()
{
CloseButton = true,
CloseOnEscapeKey = true,
DisableBackdropClick = true
};
}
}
```
***
## Screenshots


## Source Code
The source code of this project is [available on Github](https://github.com/yellow-dragon-cloud/AbpMudBlazorFinal)