通信记录和通信首选项的数据库设计

时间:2013-07-09 12:30:09

标签: database database-design

我需要设计一个数据库结构,以便在某些情况下保留客户通信信息和首选通信类型的记录。基本设计将包括

  • 通讯记录:每位客户可能会在数据库中记录一个或多个电话号码,地址,电子邮件地址等。或者他们可能没有针对某些案例的任何定义记录(例如他可能有电话号码但没有在系统中定义任何地址)
  • 记录子类型:电话号码可以是线路或GSM电话号码。地址可以是家庭或工作地址等。
  • 客户首选项:客户将在某些情况下设置首选的通信类型。情况包括:
    • 发送一次性登录密码(仅限手机)
    • 发送结算信息(可能是手机号码,电子邮件地址或普通地址。)

因此,某些偏好将接受某种通信类型(仅限电话号码)或子类型(仅限GSM电话号码),而有些可能接受多种类型(地址或电子邮件)

我正在尝试使DB设计处理这个问题,它必须是一个优化的结构。

我很难决定结构。为具有类型(电话)和子类型(GSM)的所有通信记录创建单个表将为每条记录创建许多不必要的字段(因为地址将包含数据库字段,如城市和国家,而电话记录不会,虽然它需要数字字段)为每个创建单独的表更好,但这次我将在定义首选项表时遇到问题,因为有些偏好只会接受一个子类型(如GSM手机),而有些人会接受多种类型(如地址或电子邮件)

满足此类需求的最佳数据库设计方法是什么? DBMS尚未确定,但它可能是Postgresql或Oracle。

2 个答案:

答案 0 :(得分:0)

地址需要在一个单独的表中,因为如你所说,地址有很多列。如有必要,您可以在地址表中放置一个标志,以区分工作地址和家庭地址。

Address
-------
Address ID
Street
City
...

地址ID是一个自动递增的整数或长整数。它是主要(群集)密钥。

其余的通讯记录可以放在Contact表中。该表如下所示:

Contact
-------
Contact ID
Contact Type (Land line phone, email, cell phone, etc.)
Contact Information

Contact ID是一个自动递增的整数或长整数。它是主要(群集)密钥。

联系信息是一个包含电子邮件地址或电话号码的varchar。

Preference表如下所示:

Preference
----------
Preference ID
Preference Order
Customer ID
Preference Type (address or contact)
Address ID
Contact ID

Preference ID是一个自动递增的整数或长整数。它是主要(群集)密钥。

偏好顺序定义首选项的顺序。首先是电子邮件,然后是电话,作为一个例子。

客户ID是返回Customer表的外键。

地址ID或联系人ID分别是返回地址表或联系人表的外键。

答案 1 :(得分:0)

选择一本好的数据模型模式书,例如Hay,Silverston或Fowler的“分析模式”。

您希望将电子邮件,电话,邮件地址和Web地址抽象为抽象地址类型,以便您可以将单个外键指向任何类型的地址。使用表继承。

GSM号码不是电话号码的子类型,因为您应该只对永不改变的事物使用继承,并且可以将某人的电话号码从一个小区移动到固定电话。

create table address (
  id serial primary key,
  type smallint not null references address_type(id) -- elided
);

create table address_phone_number (
  id int primary key references address(id),
  phone_number text
);

/*
add subtype tables for email, web, mailing...
*/

create table party (
  id serial primary key,
  type int not null references party_type(id), -- elided
  name text not null
);

create table party_address (
  party_id int not null references party(id),
  address_id int not null references address(id),
  role char(2) not null, -- examples: wf=work fax, ho = home
  primary key party_id, address_id, role)
);

你可以将part_address子类型说成party_address_phone_number来添加电话分机