SQL,一个 'multi-tenant' 问题:如何将公共数据与用户数据分开?
SQL, a 'multi-tenant' issue: how to separate common data from user's data?
我有一个 SQL
'architectural' 设计疑问,所以我在这里问一下...如果没有什么意义,请原谅,我对 SQL
很陌生... :-(
更新:正如我刚刚从评论中了解到的那样,这是一个"multi-tenant"问题...
我的应用程序是一种 "contacts manager"。
它会被一些 "user" 人使用,他们可以访问一些 "person" 人的数据。
用户和人员集是不相交的。
Person 的数据由服务器端的应用程序定期填充。
用户可以与人员数据进行交互,添加 - 例如 - 一些 "notes",或一些额外的 "phone" 号码。
用户添加的数据应该(RW
)只能由拥有它的用户访问,并且对其他用户不可见;相反,系统添加的数据应该(RO
)可供任何用户访问。
感兴趣的table是这样的:
--------------------------
user
--------------------------
id | username | password
--------------------------
------------------------------------------------------
person
-------------------------------------------------------
id | key | name | age | sex | address | phone | notes
-------------------------------------------------------
"id" 字段是 "integer autoincrement primary keys",而 "key" 字段是个人的唯一标识符。
到目前为止我想出的最好的解决方案是为每个添加的用户数据添加一条新记录,在该人的table布局中添加一个"id_user"字段,用于存储id的位置拥有该数据记录的用户。
所以这个人的table应该变成:
-----------------------------------------------------------------
person
-----------------------------------------------------------------
id | key | name | age | sex | address | phone | notes | id_user
-----------------------------------------------------------------
(当然"common"数据应该有一个"id_user"字段内容为null,或者一些特殊的保留值。)
我不太喜欢这个解决方案,因为它为每个人重复记录,所以提取查询会变得更加复杂,而且人 table 可能会变得非常大...
例如,我可以考虑为不同的用户使用不同的模式,但我不知道这是否是 reasonable/feasible...
问题是:您是否考虑接受此解决方案table,and/or您认为有更好的选择吗?
P.S.: 我目前正在使用 sqlite,但标准 SQL 答案应该更可取...
我认为,根据模式的复杂程度,有多种改进方法。在任何系统中,您都应该决定需要 select、编辑或删除哪些数据,这确实有助于选择正确的模型。
用户与人完全分离:
users (id, username, password, name, age, sex, address, phone, notes)
persons (id, key, name, age, sex, address, phone, notes)
如果您一次仅查询用户信息或仅查询人员信息,则没有必要将他们的信息合并为一个 table。
将配置文件数据存储在单独的 table:
users (id, username, password, profile_id)
persons (id, key, profile_id)
profiles (id, name, age, sex, address, phone, notes)
无需并集即可查询所有用户和人员的电话select
反向依赖:
users (id, username, password)
persons (id, key)
profiles (id, type, parentid, pname, age, sex, address, phone, notes)
其中 type
是 0 表示用户,1 表示人,parentid
是来自 users
或 persons
的 id
。某种 eav 模型,可以帮助需要多个配置文件的人。
如果正在使用多个配置文件(也许将来会使用),比 3 更好的方法是使用过渡 table:
users (id, username, password)
persons (id, key)
user_or_person_profiles (type, parentid, profile_id)
profiles (id, pname, age, sex, address, phone, notes)
它也可以帮助人,这也是用户(也许人和用户的脱节是暂时的)。
与之前相反,您可以将用户和人员合二为一table
people (id, groupid, username, password, key, name, age, sex, address, phone, notes)
其中 groupid
可以是预定义的常量(0 代表用户,1 代表个人),或来自 groups
table 的 id,可用于构建 "group-role-permission"用户权限系统有您需要或想象的那么复杂。
同样,只有您知道要操作哪些数据以及操作频率,才能决定哪种模式更好。
希望,它能以某种方式帮助...
我有一个 SQL
'architectural' 设计疑问,所以我在这里问一下...如果没有什么意义,请原谅,我对 SQL
很陌生... :-(
更新:正如我刚刚从评论中了解到的那样,这是一个"multi-tenant"问题...
我的应用程序是一种 "contacts manager"。
它会被一些 "user" 人使用,他们可以访问一些 "person" 人的数据。
用户和人员集是不相交的。
Person 的数据由服务器端的应用程序定期填充。
用户可以与人员数据进行交互,添加 - 例如 - 一些 "notes",或一些额外的 "phone" 号码。
用户添加的数据应该(RW
)只能由拥有它的用户访问,并且对其他用户不可见;相反,系统添加的数据应该(RO
)可供任何用户访问。
感兴趣的table是这样的:
--------------------------
user
--------------------------
id | username | password
--------------------------
------------------------------------------------------
person
-------------------------------------------------------
id | key | name | age | sex | address | phone | notes
-------------------------------------------------------
"id" 字段是 "integer autoincrement primary keys",而 "key" 字段是个人的唯一标识符。
到目前为止我想出的最好的解决方案是为每个添加的用户数据添加一条新记录,在该人的table布局中添加一个"id_user"字段,用于存储id的位置拥有该数据记录的用户。
所以这个人的table应该变成:
-----------------------------------------------------------------
person
-----------------------------------------------------------------
id | key | name | age | sex | address | phone | notes | id_user
-----------------------------------------------------------------
(当然"common"数据应该有一个"id_user"字段内容为null,或者一些特殊的保留值。)
我不太喜欢这个解决方案,因为它为每个人重复记录,所以提取查询会变得更加复杂,而且人 table 可能会变得非常大...
例如,我可以考虑为不同的用户使用不同的模式,但我不知道这是否是 reasonable/feasible...
问题是:您是否考虑接受此解决方案table,and/or您认为有更好的选择吗?
P.S.: 我目前正在使用 sqlite,但标准 SQL 答案应该更可取...
我认为,根据模式的复杂程度,有多种改进方法。在任何系统中,您都应该决定需要 select、编辑或删除哪些数据,这确实有助于选择正确的模型。
用户与人完全分离:
users (id, username, password, name, age, sex, address, phone, notes) persons (id, key, name, age, sex, address, phone, notes)
如果您一次仅查询用户信息或仅查询人员信息,则没有必要将他们的信息合并为一个 table。
将配置文件数据存储在单独的 table:
users (id, username, password, profile_id) persons (id, key, profile_id) profiles (id, name, age, sex, address, phone, notes)
无需并集即可查询所有用户和人员的电话select
反向依赖:
users (id, username, password) persons (id, key) profiles (id, type, parentid, pname, age, sex, address, phone, notes)
其中 type
是 0 表示用户,1 表示人,parentid
是来自 users
或 persons
的 id
。某种 eav 模型,可以帮助需要多个配置文件的人。
如果正在使用多个配置文件(也许将来会使用),比 3 更好的方法是使用过渡 table:
users (id, username, password) persons (id, key) user_or_person_profiles (type, parentid, profile_id) profiles (id, pname, age, sex, address, phone, notes)
它也可以帮助人,这也是用户(也许人和用户的脱节是暂时的)。
与之前相反,您可以将用户和人员合二为一table
people (id, groupid, username, password, key, name, age, sex, address, phone, notes)
其中
groupid
可以是预定义的常量(0 代表用户,1 代表个人),或来自groups
table 的 id,可用于构建 "group-role-permission"用户权限系统有您需要或想象的那么复杂。
同样,只有您知道要操作哪些数据以及操作频率,才能决定哪种模式更好。
希望,它能以某种方式帮助...