sql server - Ensure that one and only one default is defined for a set -


i have customer table has 1 many relationship address table. want constrain database customer with addresses have 1 (and one) default address.

i can quite add constraint ensure there ever 1 default address each customer. struggling on how apply constraint ensures address marked default.

to summarize:

  • a customer not required have addresses.
  • if customer has addresses there must default address.
  • there must 1 default address per customer.

here example of problem , 'unit' tests. using link table join customers , addresses.

create table customer (     id int primary key,     name varchar(100) not null )  create table [address] (     id int primary key,     address varchar(500) not null )  create table custaddress (     customerid int,     addressid int,     [default] bit not null,     foreign key (customerid) references customer(id),     foreign key (addressid) references [address](id) )  insert customer values (1, 'mr greedy')  insert [address] values (1, 'roly-poly house, fatland') insert [address] values (2, 'giant cottage, cave')  -- should succeed insert custaddress values (1, 1, 1) insert custaddress values (1, 2, 0)  delete custaddress  -- should fail no default address set insert custaddress values (1, 1, 0)  delete custaddress  -- should fail end no defualt address set insert custaddress values (1, 1, 1) insert custaddress values (1, 2, 0) update custaddress set [default] = 0 customerid = 1 , addressid = 1  delete custaddress  -- should fail end no defualt address set insert custaddress values (1, 1, 1) insert custaddress values (1, 2, 0) delete custaddress customerid = 1 , addressid = 1 

how changing schema to

create table customer (     id int primary key,     name varchar(100) not null )  create table [address] (     id int primary key,     address varchar(500) not null )   create table custdefaultaddress (     customerid int primary key, /*ensures no more 1 default*/     addressid int,     foreign key (customerid) references customer(id),     foreign key (addressid) references [address](id) )   create table custsecondaryaddress (     customerid int references custdefaultaddress(customerid),                     /*no secondary address can added unless default 1 exists*/     addressid int references [address](id),     primary key(customerid, addressid) ) 

if there additional requirement address must not present both primary , secondary address can enforce helper table , indexed view.

create table dbo.tworows   (      x int primary key   );  insert dbo.tworows values      (1),             (2)  go  create view v schemabinding   select d.addressid,          d.customerid     dbo.custdefaultaddress d          join dbo.custsecondaryaddress s            on d.addressid = s.addressid               , d.customerid = s.customerid          cross join dbo.tworows  go  create unique clustered index ix   on v(addressid, customerid)  

Comments

Popular posts from this blog

php - Calling a template part from a post -

Firefox SVG shape not printing when it has stroke -

How to mention the localhost in android -