【问题标题】:Is it possible to have different properties for the same model in multi-tenant applications scenario?在多租户应用场景中,同一个模型可以有不同的属性吗?
【发布时间】:2019-08-14 18:28:42
【问题描述】:

我必须设计一个多租户应用程序,我需要为同一模型中的每个租户提供自定义字段。

客户 1 需要使用一些自定义字段,客户 2 需要管理同一张表中的其他字段等等..

这是一个例子: 同一张表(票)有一个共同的(基本)字段列表,那么每个租户应该在模型中有他的附加列:

我想先实现一个 EF Code 的 .Net Core Web 应用程序。

namespace Models.Base
{
    public class TicketBase
    {
        public int Id { get; set; }
        public string Description { get; set; }
        public Datetime CreationDate { get; set; } 
    }
}

租户 1

namespace Models.Tenant1
{
    public class Ticket : TicketBase
    {

        public string CustomerName { get; set; }
        public Datetime DateCustomerCall { get; set; } 
    }
}

租户 2

namespace Models.Tenant2
{
    public class Ticket : TicketBase
    {

        public string AnotherDescription { get; set; }
        public Datetime AnotherDate { get; set; } 
    }
}

以这种方式设计模型是否正确,或者对于这个非常常见的问题有不同的方法?

【问题讨论】:

  • 没有一种万能的解决方案。这在很大程度上取决于您的模型有何不同、需求变化的频率等。
  • 嗨,我想使用这种方法 stackify.com/writing-multitenant-asp-net-core-applicationsbenfoster.io/blog/… 但似乎它们共享相同的模型
  • 如果 TicketBase 类代表简单的票证属性并且您永远不会将 Ticketbase 类实例化为对象,那么您可以考虑将这些属性作为 ITicket 接口的一部分而不是 TicketBase 类。并让多个租户实现 ITicket + 他们的附加属性。这也将帮助您利用多租户 DI 注入,您可以在其中注册租户特定的票证对象并在您的代码中根据租户通过 ITicket 接口解析它们……这只是您设计的另一种思考方式。
  • 谢谢 Asif,您将如何在 .net core EF 中实现它?

标签: c# entity-framework-core multi-tenant


【解决方案1】:

恕我直言,在 SaaS 中,拥有单一代码库和灵活的多租户配置/扩展是成功的关键。

要为每个租户启用自定义字段,业务模型必须具有固定的基本字段集。自定义字段必须按 entityid 和 tenantid 存储在单独的表中。

您的表格可能如下所示。首选此模型,因为使用通用扩展表会导致可扩展性降低,并且随着使用量的增加很快就会被数据量填充。

门票

TicketExtn(包含按租户和实体的自定义字段的扩展表)

TicketExtn 表将包含如下字段

TicketId TenantId FieldId FieldValue FieldDataType 等等 当我们尝试获取Ticket 实体的数据时,我们还将从TicketExtn 表中获取数据并设置模型中的字段。

BaseModel 如下所示

public class ExtendedField
{
    public Guid Id { get; set; }
    public string FieldName { get; set; }
    public Guid DataTypeId { get; set; }
    /// <summary>
    /// Can also be a typed class, this is just for reference
    /// </summary>
    /// <value>The field value.</value>
    public string FieldValue { get; set; }
    /// <summary>
    /// Incase of using string for fieldvalue, the string to format the value as per the required datatype 
    /// will be provided here.
    /// </summary>
    /// <value>The field value format string.</value>
    public string FieldValueFormatString { get; set; }
}

public class BaseModel
{
    Dictionary<string, ExtendedField> ExtendedRows { get; set; }
}

public class Ticket : BaseModel
{
    public int Id { get; set; }
    public string Description { get; set; }
    public DateTime CreationDate { get; set; }
}

在您的服务层中,将有填充这些扩展行的逻辑。最好让用于填充扩展行的逻辑具有通用性,这样对于任意数量的实体,该逻辑都可以重复使用。

HTH

【讨论】:

  • 谢谢 Saravanan,这是应用程序的实际实现。 (比如github.com/dubeaud/bugnet),我想知道是否有一种方法可以在 mvc 场景中以最简单的方式处理实体、视图模型和视图。我想要 Ticket.MyPropertyTenant1 = "value" 之类的东西,没有字典、数据类型等的句柄。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2021-12-26
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2020-01-22
  • 2023-03-03
相关资源
最近更新 更多