Open Closed

How to Add extended property of tenant and view it in another tab in create tenant Modal #7925


User avatar
0
nabass created

How to get extended property from tenant

Check the docs before asking a question: https://abp.io/docs/latest Check the samples to see the basic tasks: https://abp.io/docs/latest/samples The exact solution to your question may have been answered before, and please first use the search on the homepage. Provide us with the following info: 🧐 Hint: If you are using the ABP Studio, you can see all the information about your solution from the configuration window, which opens when you right-click on the solution and click on the Solution Configuration button.

  • ABP Framework version: vX.X.X
  • UI Type: Angular / MVC / Blazor WASM / Blazor Server
  • Database System: EF Core (SQL Server, Oracle, MySQL, PostgreSQL, etc..) / MongoDB
  • Tiered (for MVC) or Auth Server Separated (for Angular): yes/no
  • Exception message and full stack trace:
  • Steps to reproduce the issue:

11 Answer(s)
  • User Avatar
    0
    liangshiwei created
    Support Team Fullstack Developer

    Hi see https://abp.io/docs/latest/framework/architecture/modularity/extending/module-entity-extensions

    view it in another tab in create tenant Modal

    you need to override the CreateModalModel

    move these code to a new tab

    you can download saas module to get CreateModalModel page code

    Here is the document about how to override page. https://abp.io/docs/latest/framework/ui/mvc-razor-pages/customization-user-interface

  • User Avatar
    0
    nabass created

    hi i followed the document but nothing changes 1- source code of tenant page doesn't have tabs despite the view has 2 tabs ( Basic info && Database Connection String)

    2- section (Completely Overriding a Razor Page) into document i found there is no need to inherit just use AbpPageModel if i create all logic in cs file here is my final code:=>

    public class MyCreateModalModel : AbpPageModel
    {
        protected ITenantAppService TenantAppService { get; }
        public MyCreateModalModel(ITenantAppService tenantAppService) //: base(tenantAppService)
        {
            TenantAppService = tenantAppService;
        }
    
        [BindProperty]
        public TenantInfoModel Tenant { get; set; }
    
        public virtual Task<IActionResult> OnGetAsync()
        {
            Tenant = new TenantInfoModel();
            return Task.FromResult<IActionResult>(Page());
        }
    
        public virtual async Task<IActionResult> OnPostAsync()
        {
            ValidateModel();
    
            var input = ObjectMapper.Map<TenantInfoModel, TenantCreateDto>(Tenant);
            await TenantAppService.CreateAsync(input);
    
            return NoContent();
        }
    
        public class TenantInfoModel : ExtensibleObject
        {
            [Required]
            [DynamicStringLength(typeof(TenantConsts), nameof(TenantConsts.MaxNameLength))]
            [Display(Name = "DisplayName:TenantName")]
            public string Name { get; set; }
    
            [Required]
            [EmailAddress]
            [DynamicStringLength(typeof(TenantConsts), nameof(TenantConsts.MaxAdminEmailAddressLength))]
            public string AdminEmailAddress { get; set; }
    
            [Required]
            [DataType(DataType.Password)]
            [DynamicStringLength(typeof(TenantConsts), nameof(TenantConsts.MaxPasswordLength))]
            public string AdminPassword { get; set; }
        }
    }
    

    and this is my html code: =>

    @using Microsoft.Extensions.Localization
    @using Volo.Abp.AspNetCore.Mvc.UI.Bootstrap.TagHelpers.Modal
    @using Volo.Abp.Localization
    @using Volo.Abp.ObjectExtending
    @using Volo.Abp.TenantManagement.Localization
    @model Horizon.HorizonERP.Web.Pages.TenantManagement.Tenants.MyCreateModalModel
    @using Volo.Abp.Data
    @using Volo.Abp.TenantManagement;
    @inject IHtmlLocalizer<AbpTenantManagementResource> L
    @inject IStringLocalizerFactory StringLocalizerFactory
    @{
        Layout = null;
    }
    <form method="post" asp-page="/TenantManagement/Tenants/MyCreateModal">
        <abp-modal>
            <abp-modal-header title="@L["NewTenant"].Value"></abp-modal-header>
            <abp-modal-body>
                <abp-tabs>
                    <abp-tab title="Main Info">
                        <abp-input asp-for="Tenant.Name" />
                        <abp-input asp-for="Tenant.AdminEmailAddress" />
                        <div class="mb-3">
                            <label class="form-label">@L["DisplayName:AdminPassword"].Value</label>
                            <span> * </span>
                            <div class="input-group">
                                <input type="password" class="form-control" maxlength="@TenantConsts.MaxPasswordLength" asp-for="Tenant.AdminPassword" />
                                <button class="btn btn-secondary" type="button" id="PasswordVisibilityButton">
                                    <i class="fa fa-eye-slash" aria-hidden="true"></i>
                                </button>
                            </div>
                            <span asp-validation-for="Tenant.AdminPassword"></span>
                        </div>
                    </abp-tab>
                    <abp-tab title="Extra">
                        @foreach (var propertyInfo in ObjectExtensionManager.Instance.GetProperties<MyCreateModalModel.TenantInfoModel>())
                        {
                            if (!propertyInfo.Name.EndsWith("_Text"))
                            {
                                if (propertyInfo.Type.IsEnum || !propertyInfo.Lookup.Url.IsNullOrEmpty())
                                {
                                    if (propertyInfo.Type.IsEnum)
                                    {
                                        Model.Tenant.ExtraProperties.ToEnum(propertyInfo.Name, propertyInfo.Type);
                                    }
                                    <abp-select asp-for="Tenant.ExtraProperties[propertyInfo.Name]"
                                                label="@propertyInfo.GetLocalizedDisplayName(StringLocalizerFactory)"
                                                autocomplete-api-url="@propertyInfo.Lookup.Url"
                                                autocomplete-selected-item-name="@Model.Tenant.GetProperty(propertyInfo.Name+"_Text")"
                                                autocomplete-selected-item-value="@Model.Tenant.GetProperty(propertyInfo.Name)"
                                                autocomplete-filter-param-name="@propertyInfo.Lookup.FilterParamName"
                                                autocomplete-items-property-name="@propertyInfo.Lookup.ResultListPropertyName"
                                                autocomplete-display-property-name="@propertyInfo.Lookup.DisplayPropertyName"
                                                autocomplete-value-property-name="@propertyInfo.Lookup.ValuePropertyName"></abp-select>
                                }
                                else
                                {
                                    <abp-input type="@propertyInfo.GetInputType()"
                                               asp-for="Tenant.ExtraProperties[propertyInfo.Name]"
                                               label="@propertyInfo.GetLocalizedDisplayName(StringLocalizerFactory)"
                                               asp-format="@propertyInfo.GetInputFormatOrNull()"
                                               value="@propertyInfo.GetInputValueOrNull(Model.Tenant.GetProperty(propertyInfo.Name))" />
                                }
                            }
                        }
                    </abp-tab>
                </abp-tabs>
            </abp-modal-body>
            <abp-modal-footer buttons="@(AbpModalButtons.Cancel|AbpModalButtons.Save)"></abp-modal-footer>
        </abp-modal>
    </form>
    
    

    but final result is the same nothing changed so did i miss logic or registration or code line i must put anything ??

  • User Avatar
    0
    liangshiwei created
    Support Team Fullstack Developer

    it works for me

    @page
    @using Microsoft.Extensions.Localization
    @using Volo.Abp.AspNetCore.Mvc.UI.Bootstrap.TagHelpers.Modal
    @using Volo.Abp.Data
    @using Volo.Abp.Localization
    @using Volo.Abp.ObjectExtending
    @using Volo.Saas
    @using Volo.Saas.Host.Pages.Saas.Host.Tenants
    @using Volo.Saas.Localization
    @model CreateModalModel
    @inject IStringLocalizer<SaasResource> L
    @inject IStringLocalizerFactory StringLocalizerFactory
    @{
    Layout = null;
    }
    <form method="post" asp-page="/Saas/Host/Tenants/CreateModal">
        <abp-modal>
            <abp-modal-header title="@L["NewTenant"].Value"></abp-modal-header>
            <abp-modal-body>
                <abp-tabs>
                    <abp-tab title="Main Info">
                        <abp-input asp-for="Tenant.Name" />
                        <abp-input asp-for="Tenant.AdminEmailAddress" />
                        <div class="mb-3">
                            <label class="form-label">@L["DisplayName:AdminPassword"].Value</label>
                            <span> * </span>
                            <div class="input-group">
                                <input type="password" class="form-control" maxlength="@TenantConsts.MaxPasswordLength" asp-for="Tenant.AdminPassword" />
                                <button class="btn btn-secondary" type="button" id="PasswordVisibilityButton">
                                    <i class="fa fa-eye-slash" aria-hidden="true"></i>
                                </button>
                            </div>
                            <span asp-validation-for="Tenant.AdminPassword"></span>
                        </div>
                    </abp-tab>
                    <abp-tab title="Extra">
                        @foreach (var propertyInfo in ObjectExtensionManager.Instance.GetProperties<CreateModalModel.TenantInfoModel>())
                        {
                        if (!propertyInfo.Name.EndsWith("_Text"))
                        {
                        if (propertyInfo.Type.IsEnum || !propertyInfo.Lookup.Url.IsNullOrEmpty())
                        {
                        if (propertyInfo.Type.IsEnum)
                        {
                        Model.Tenant.ExtraProperties.ToEnum(propertyInfo.Name, propertyInfo.Type);
                        }
                        <abp-select asp-for="Tenant.ExtraProperties[propertyInfo.Name]"
                                    label="@propertyInfo.GetLocalizedDisplayName(StringLocalizerFactory)"
                                    autocomplete-api-url="@propertyInfo.Lookup.Url"
                                    autocomplete-selected-item-name="@Model.Tenant.GetProperty(propertyInfo.Name+"_Text")"
                                    autocomplete-selected-item-value="@Model.Tenant.GetProperty(propertyInfo.Name)"
                                    autocomplete-filter-param-name="@propertyInfo.Lookup.FilterParamName"
                                    autocomplete-items-property-name="@propertyInfo.Lookup.ResultListPropertyName"
                                    autocomplete-display-property-name="@propertyInfo.Lookup.DisplayPropertyName"
                                    autocomplete-value-property-name="@propertyInfo.Lookup.ValuePropertyName"></abp-select>
                        }
                        else
                        {
                        <abp-input type="@propertyInfo.GetInputType()"
                                   asp-for="Tenant.ExtraProperties[propertyInfo.Name]"
                                   label="@propertyInfo.GetLocalizedDisplayName(StringLocalizerFactory)"
                                   asp-format="@propertyInfo.GetInputFormatOrNull()"
                                   value="@propertyInfo.GetInputValueOrNull(Model.Tenant.GetProperty(propertyInfo.Name))" />
                        }
                        }
                        }
                    </abp-tab>
                </abp-tabs>
            </abp-modal-body>
            <abp-modal-footer buttons="@(AbpModalButtons.Cancel|AbpModalButtons.Save)"></abp-modal-footer>
        </abp-modal>
    </form>
    
    

  • User Avatar
    0
    nabass created

    hi i moved page into same path as you

    and final result is

    steps what i did is: 1- get the application contract tenant source to use it's Dto within cs file

    2- copy html code that you used 3- change namespace of cs file to (namespace Horizon.HorizonERP.Web.Pages.Sass.Host.Tenants)

    so what i miss ?

  • User Avatar
    0
    liangshiwei created
    Support Team Fullstack Developer

    You should use the same cshtml file name

  • User Avatar
    0
    nabass created

    wow it works thank you lian :)

  • User Avatar
    0
    nabass created

    sorry i noticed that where is Database Connection strings tab ??

  • User Avatar
    0
    liangshiwei created
    Support Team Fullstack Developer

    HI,

    i just copy the code you provided

    https://abp.io/support/questions/7925/How-to-Add-extended-property-of-tenant-and-view-it-in-another-tab-in-create-tenant-Modal#answer-3a15170e-c56b-d5fd-eed1-ed4cefe85aed

  • User Avatar
    0
    nabass created

    Please Still Has the same Issue that The Database Connection String Tab not exist on the custom tenant screen, although i already have licenses but i cant get the source of this Page "/Saas/Host/Tenants/CreateModal" from github Please could you provide me the original source code of this Page.

    appreciate your Quick response.

  • User Avatar
    0
    liangshiwei created
    Support Team Fullstack Developer

    Hi,

    sure, please email me. i will share it with you.

    shiwei.liang@volosoft.com

    BTW, you can download it via ABP CLI abp get-source Volo.Saas

  • User Avatar
    0
    nabass created

    thanks for efforts it works well thank you again

Made with ❤️ on ABP v9.1.0-preview. Updated on November 11, 2024, 11:11