Same form that submits to two different tables - sql

I am quite new to Microsoft Access but i have been working with databases for quite a while now, so I understand "the back end" (so to speak) as to how I will set up this database, but I'm not sure how to tell Access what to do and how to do it.
The aim of my database is to load up a customer's account with their information; eg, phone number address, email, etc. All this information has been migrated to a table within my new database project.
from here I would like to create a separate table which has notes which can be assigned to each user's account number. the aim of this is to be able to read up on recent activity of these customers and be able to search and filter that information on an easy to use front end interface.
So so far I have two tables, one with the customer's information in it and another which is where I would like to save the notes for each customer.
the primary key which I will be using is the customer's account numbers. This, of course, being unique to each customer and would be perfect for the primary key in both of these tables.
I have set up a relationship between both of the tables as they will both contain the user's account numbers.
I'm just not sure how to go about it and would really appreciate the help. I am currently using Microsoft Access 2007.

for your second table you need to use a new primary key like "customerInformationID". Reference the customer table by a foreign key.
Then you can join these tables like this:
SELECT c.Name, c.Number, ci.notes
FROM customer AS c
INNER JOIN customerInformation AS ci ON c.customerID = ci.customerID
Why do you need two tables anyways? If you don't need them for a technical purpose like "every user shall be able to store his own notes to a customer" then you can also store them in your main table as all of these information are only dependent from the primary key.
Best Regards
Bruellhusten

Related

Best way to mimic inheritance in postgresql?

For an application I am writing, there are two types of "users", those who have made accounts and those who have not, virtual_users. These two types are nearly identical, except account_users have a password, and email is required and must be unique amongst all account_users, although it can be the same as any number for virtual_users. A large number of tables have a column that references users, which should include both, and 90% of app functionality treats them as interchangeable. What is the best way of handling this? Some options I have considered:
-Put both types of users in the same table and have a complicated constraints regarding uniqueness, basically, if password is not NULL, email must be unique among all users where password is not NULL. I have no idea how I would write this constraint. On the few occasions I only want account_users query for only users who have a password. This seems like the best solution if I can figure out how to write the constraint.
-Have Account_users inherit from Virtual_usersand Virtual_users has an additional column password and unique constraints on email. From here there are two potential options:
---Have a Users table which includes two columns account_user_id and virtual_user_id one of which is NULL and one of which corresponds to the appropriate user. When other tables need to reference a user, they reference this table. Have all my queries server side for users query both tables and combine.
---When other tables need to reference they reference either table. I don't think this is possible. Have all my queries server side for users query both tables and combine.
Any advice would be appreciated.
I assume the scenario is you have a system which some parts require the user to be signed into a registered account, and others do not, but you'd still like to track users.
Postgres has table inheritance. You could use that, but I'd be concerned about the caveats.
You could put them all into one table and use some sort of flag, like Single Table Inheritance, but then you run into constraint issues. You would then enforce constraints in the model. This should be fine if you have a strong model.
You could have separate accounts and users. Rather than one being a special case of the other, they key is thinking of them as two conceptually different things. In OO terms, an account has a user.
-- Visitors to the site who haven't signed up.
create table users (
id serial,
-- The unverified email they might have given you.
email text,
-- Any other common information like a tracking token
token text
);
-- Users who have registered.
create table accounts (
id serial,
user_id int references users(id),
-- Their verified email.
email text not null,
-- Hashed, of course.
password text not null
-- any additional information only for accounts
);
I like this because there are no flags involved, users and accounts can have separate constraints, and the accounts table doesn't get bloated with users that showed up once and never came back.
You'd access complete account information with a simple join.
select accounts.*, users.token
from accounts
join users on accounts.user_id = users.id
where accounts.id = ?
If you want to delete an account you can do so without losing the underlying user information.
delete from accounts where accounts.id = ?
Systems which require an account use accounts. Systems which don't use users. Systems which behave differently for users and accounts can check if a user has an account easily.
select accounts.id
from accounts
where accounts.user_id = ?
User tracking is associated with the users table, so you have a consistent record of a user's behavior before and after they register.

Adding record with new foreign key

I have few tables to store company information in my database, but I want to focus on two of them. One table, Company, contains CompanyID, which is autoincremented, and some other columns that are irrelevant for now. The problem is that companies use different versions of names (e.g. IBM vs. International Business Machines) and I want/need to store them all for futher use, so I can't keep names in Company table. Therefore I have another table, CompanyName that uses CompanyID as a foreign key (it's one-to-many relation).
Now, I need to import some new companies, and I have names only. Therefore I want to add them to CompanyName table, but create new records in Company table immediately, so I can put right CompanyID in CompanyName table.
Is it possible with one query? How to approach this problem properly? Do I need to go as far as writing VBA procedure to add records one by one?
I searched Stack and other websites, but I didn't find any solution for my problem, and I can't figure it out myself. I guess it could be done with form and subform, but ultimately I want to put all my queries in macro, so data import would be done automatically.
I'm not database expert, so maybe I just designed it badly, but I didn't figure out another way to cleanly store multiple names of the same entity.
The table structure you setup appears to be a good way to do this. But there's not a way to insert records into both tables at the same time. One option is to write two queries to insert records into Company and then CompanyName. After inserting records into Company you will need to create a query that joins from the source table to the Company table joining it on a field that uniquely defines the record beside the autoincrement key. That will allow you to get the key field from Company for use when you insert into CompanyName.
The other option, is to write some VBA code to loop through the source data inserting records into both. The would be preferable since it should be more reliable.

access database relationships

I am using access 2007. I made a database called holiday which has 3 tables namely:
client - this has all the client information
flight - this stores flight information
cruise - this stores cruiser information
what I'm thinking of doing, is to make a relationship between these three tables. I just thought myself "relationships" from google and from what I understand is that I should use a one-to-many relationship.
I did that each table has a column called customerID where the client table has it as a primary key and the others as foreign-key. What I want to know is how do I link up the tables so that when I enter information onto the client table both flight and cruise should open as subselection because currently only one is opening and I don't know how to enter the other?
There's 2 ways to create a relationship between tables.
One is permanently with the Relationships Window (under Database Tools in Access 2010). Drag from a field in one table to a field in an other table. Then double click on the line (join) to edit the join type.
The other is to do this temporarily in A Query Builder window. Then you create the join the same way as above. This join is only set in this query only, or anything else based on this query.
OK, now that you them joined, what are your plans. One way is to create a form for editing the customer info, along with two sub-forms for editing the flight & cruise info.
Good luck

Current primary key is ineffective at preventing duplicates. Does this sound like a good way to rearchitect my tables?

Every so often, I update our research recruitment database with those who responded to our Craigslist ad. Each respondent is given a unique respondentID, which is the primary key.
Sometimes, people respond to these Craigslist ads multiple times. I think we may have duplicate people in our database, which is bad.
I would like to change the primary key of all my recruitment tables from respondentID to Email, which will prevent duplicates and make it easier to look up information. There are probably duplicate email records in my database already, and I need to clean this up if so.
Here's the current architecture for my three recruitment tables:
demographic - contains columns like RespondentID (PK), Email (I want this to be PK), Phone, etc
genre - contains columns like RespondentID (PK), Horror, etc
platform - contains columns like RespondentID (PK), TV, etc.
I want to join all three tables together at some point so we can get a better understanding of someone.
Here are my questions:
How can I eliminate duplicate respondents already in my database? (I can tell if they are duplicates because they will have the same Email value.)
Given my current architecture, how can I transition my database to have Email as the primary key without messing up my data?
After transitioning to a new architecture, what is the process I can use to delete duplicates in my Craigslist ad spreadsheet before I append them to Demo, Genre, and Platform tables?
Here are my ideas about solutions:
Create backup tables. Join the three tables and export the big table to Excel. In Excel, use Data Filtering and Conditional Formatting to find the duplicate entries, and delete them by hand. Unfortunately, I have 20,000 records which will crash Excel. :( The chief issue is that I don't know how to remove duplicate entries within a table using SQL. (Also, if I have two entries by bobdole#republican.com, one entry should remain.) Can you come up with a smarter solution involving SQL and Access?
After each Email record is unique, I will create new tables with each using Email as the primary key.
When I want to remove duplicates within the data I'd like to import, I should be able to easily do it within Excel. Next, I will use this SQL command to deduplicate between the current database and the incoming data:
DELETE * from newParticipantsList
WHERE Email in (SelectEmail from Demo)
I'm going to try to duplicate my current architecture in a small test table in Access and see if I can figure it out. Overall, I don't have much experience with joining tables and removing data in SQL, so it's a little scary.
Maybe I'm just being thick, but why don't you just create a new Identity column in the existing table? You can always remove those records you deem duplicates, but the Identity column is guaranteed to be unique under all circumstances.
It will be up to you to make sure that any new records inserted into the table are not duplicates, by checking the Email column.
To remove duplicates from demographic table you could do something like:
WITH RecordsToKeep AS (
SELECT MIN(RespondentID) as RespondentID
FROM demographic
GROUP BY Email
) DELETE demographic
FROM demographic
LEFT JOIN RecordsToKeep on RecordsToKeep.RespondentID = demographic.RespondentID
where RecordsToKeep.RespondentID IS NULL
This will keep the first record for each email address and delete the rest. You will need to remap the genre and platform tables before you delete the source.
In terms of what to do in the future, you could get SQL to do all the de-duplicating for you by importing the data into a staging table and then only import distinct records to the final when the address isn't already in the demographic table.
There is no reason to change the Email Address to be the primary key. String's aren't great primary keys for a number of reasons. The problem you have isn't with duplicate keys, the problem is how you are inserting the data.

Simple database table design

I'm trying to design a database structure using best practice but I can't get my head around something which I'm sure is fundamental. The DB is for the users(100+) to subscribe to which magazines(100+) they read.
I have a table for the usernames, user info and magazine titles, but I'm unsure where to list the magazines that each user follows. Do I add a column in the user table and link it to the magazine table or would each user be setup with their own "follow" table that lists the magazine there? I'm getting myself confused I think so any help would be great.
Regards
Ryan
What you're struggling with is called a many-to-many relationship.
To solve this problem, you need a third table--perhaps called user_magazines. This third table should two key fields, one from the user table and the other from the magazine table. For example, user_id column and a magazine_id column. This is called a compound key. With both of these columns, you are now able to discern which books have been read by a whichever user.
This is best understood visually:
In the picture above you can see that the third table (the middle table, stock_category) enables us to know what stock item belongs to which categories.
First of all, you must understand a many-to-many relationship, like take your example of users and magazines. First understand the scenario : A single user can follow many magazines, and a single magazine can be followed by many users, so there exists a many-to-many relationship between users and magazines.
Whenever there exists many-to-many relationship between two entities, we have to introduce a third entity between them which is called an associative entity!
so you have to introduce a third entity named as per your choice and it will be containing information about which user is following which magazine
you can go to http://sqlrelationship.com/many-to-many-relationship/ for better understanding using diagrams
You should have a users table, with an auto-incrementing primary key, username, and anything else you want to store about that user.
Next, a magazines table which contains another auto-incrementing primary key, the name of the mag and anything else you need to store about that magazine.
Finally, a subscriptions table. this should have an auto-incrementing primary key (actually that's not really necessary on this table but personally I would add it), a user_ID column and a magazine_ID column.
To add a subscription, just add a new record to the subscription table containing the ID of the user and the ID of the relevant magazine. This allows for users to subscribe to multiple magazines.
If you want to get fancy you can add referential integrity constraints to the subscriptions table - this tells the database management system that a particular column is a reference to another table, and can specify what to do upon modifying it (for example you could have the DBMS automatically delete subscriptions owned by a particular user if that user is deleted)
You definitely do NOT want to add a column to the user table and have it refer to the magazine table. Users would only be able to follow or subscribe to one magazine which doesn't reflect the real world.
You'll want to have a join table that has a userId and a magazineId. For each magazine that a user subscribes to there will be one entry in the join table.
I'm inferring a little bit about your table structure but if you had:
User (id, login)
Magazine (id, name)
User_Magazine (userId, magazineId)
Perhaps this last table should be called subscription because there may be other information like the subscription end date which you'd want to track and that is really what it is representing in the real world.
You'd be able to put an entry into the User_Magazine table for every subscription.
And if you wanted to see all the magazines a user with the login jdoe had you'd do:
SELECT name
FROM User, Magazine, User_Magazine
WHERE login = 'jdoe'
AND User.id = User_Magazine.userId
AND Magazine.id = User_Magazine.magazineId
You should create a separate table called UserMagazineSubs. Make the UserID + MagazineTile ID as a composite key.
This table will capture all User and Magazine relationship details.
A User_To_Magazine table, that has two columns - UserId and MagazineId, and the key is composite containing both columns