0

I'm pretty new to php and mysql so bear with me while I try to explain what I'm going for.

I have an online form that is taking information and placing it into a MYSQL database. That function works perfectly, but now I'm to the point where I want to cut down on duplicate entries as much as possible.

Our employees will be entering Customer Name, billing address, and shipping address to the db. Some customers have multiple billing addresses and shipping addresses though. What I'd like to do is make it so that if any one of those 3 is a new entry then the record is saved but if all 3 are duplicates it does not get inserted into the database. I was hoping something like this would do the trick:

$cn = $_POST[CustomerName];
$ba = $_POST[BillingAddress];
$sa = $_POST[ShippingAddress];
$custname = mysqli_query("SELECT DISTINCT customerName FROM customer WHERE customerName LIKE '$cn'");
$billaddress = mysqli_query("SELECT DISTINCT billingaddress FROM customer WHERE billingaddress LIKE '$ba'");
$shipaddress = mysqli_query("SELECT DISTINCT shippingaddress FROM customer WHERE shippingaddress LIKE '$sa'");



if ($custname != $_POST[CustomerName] OR $billaddress != $_POST[BillingAddress] OR $shipaddress != $_POST[ShippingAddress])
    {
    mysqli_query($con,"INSERT INTO customer(customerName, billingaddress, shippingaddress)
VALUES
('$_POST[CustomerName]','$_POST[BillingAddress]','$_POST[ShippingAddress]')");
    }

Unfortunately, this still adds the record when all three parameters are duplicates. Anythoughts on why that would be happening, or any suggestions on how to get my desired results a little easier?

I've tried making the customer name field unique, but when that's the case it drops the entire record. If I'm understanding correctly, the primary key / unique method won't be able to be used for my issue. That is likely my inexperience talking though, so if anyone could help I'd appreciate it greatly.

EDIT: I thought I'd also mention I've tried using mysql_real_escape_string methods and the array return method to no avail.

The table dafinition is this:

**customer**
idcustomer (primary key, auto-increment)
customerName
billingaddress
shippingaddress
Matt Mills
  • 8,692
  • 6
  • 40
  • 64
  • 1
    Suggestive read => http://stackoverflow.com/q/60174/ (*highly*) – Funk Forty Niner Mar 31 '14 at 19:47
  • 3
    When using `mysqli` you should be using parameterized queries and [`bind_param`](http://php.net/manual/en/mysqli-stmt.bind-param.php) to add user data to your query. **DO NOT** use string interpolation to accomplish this because you will probably create severe [SQL injection bugs](http://bobby-tables.com/). **NEVER** put `$_POST` data directly in your query. What you're doing here is extremely reckless. – tadman Mar 31 '14 at 19:51
  • 1
    Like I said, I'm very new to all this. This is actually my very first project with sql and php, so thanks for the tips. I'll look into fixing all that. I'm still a very long way from going live with it so I'm just trying to get the syntax down and the functionality to do what I want it to. – user3311933 Mar 31 '14 at 19:59

1 Answers1

0

I suggest using a trigger to control the logic of you transactions with a BEFORE action.

DELIMITER $$
CREATE TRIGGER tbl_noduplicate
BEFORE INSERT ON tbl
FOR EACH ROW
BEGIN
  IF (EXISTS(SELECT * FROM tbl WHERE col1 = NEW.col1)) THEN
    INSERT INTO tbl (col1,col2,col3)   
    VALUES (NEW.col1, NEW.col2, NEW.col3);
  END IF;
END$$
DELIMITER ;

Ok - here is what i think :
1- here a new data model i think you should implement :
This when one customer has one or more shipping or billing addresses enter image description here

Here is the code to do this :

CREATE TABLE IF NOT EXISTS customer (
  idcustomer int(11) NOT NULL DEFAULT 0,
  customerName varchar(30) DEFAULT NULL,
  customer_email varchar(30) DEFAULT NULL,
  PRIMARY KEY (idcustomer)
);


CREATE TABLE IF NOT EXISTS ref_address_type (
  address_type_code int(11) DEFAULT NULL,
  address_type_desc varchar(30) DEFAULT NULL,
  UNIQUE INDEX UK_ref_address_type_address_ty (address_type_code)
);

CREATE TABLE IF NOT EXISTS customer_address (
  idaddress int(11) NOT NULL DEFAULT 0,
  fk_idcustomer int(11) DEFAULT NULL,
  street varchar(100) DEFAULT NULL,
  street_number int(11) DEFAULT NULL,
  house_app_number int(11) DEFAULT NULL,
  city varchar(50) DEFAULT NULL,
  country varchar(50) DEFAULT NULL,
  zipcode int(11) DEFAULT NULL,
  fk_address_type_code int(11) DEFAULT NULL,
  PRIMARY KEY (idaddress),
  CONSTRAINT FK_customer_address_customer_idcustomer FOREIGN KEY (fk_idcustomer)
  REFERENCES customer (idcustomer) ,
  CONSTRAINT FK_customer_address_ref_address_type_address_type_code FOREIGN KEY (fk_address_type_code)
  REFERENCES ref_address_type (address_type_code) 
);
Up_One
  • 5,213
  • 3
  • 33
  • 65
  • Would I use that trigger in place of my current IF statement, or is that just defining the trigger so that I can use it later in the code? – user3311933 Mar 31 '14 at 20:02
  • Just create the trigger on the table where you don't want duplicates and fix the loginc inside the trigger sql block. – Up_One Mar 31 '14 at 20:11
  • another thing you can do is creating a composite key on your table ! – Up_One Mar 31 '14 at 20:13
  • Ok, I figured out how to use the trigger hehe. . .Thing is, that's preventing it from adding a new entry if the col1 name already exists. I feel like this might be a good solution if we can make it so that it only drops the entry if col1,col2, and col3 are already entered. Maybe I put something in incorrectly? I'd appreciate your thoughts on it while I continue to fiddle with it. – user3311933 Mar 31 '14 at 20:28
  • i will help you! nop but i wanna understand better your need ! (i don't want and duplicate values for customerName, billingaddress, shippingaddress on the same row? correct! ) – Up_One Mar 31 '14 at 20:33
  • Yes that's correct. Customers have multiple billing and shipping addresses though so I need to be able to add entries for customers with the same name, but different billing and shipping addresses. Turns out I'd left my code in from before which was stopping your trigger from working. Now i'm getting an error saying: Error: Can't update table 'customer' in stored function/trigger because it is already used by statement which invoked this stored function/trigger. Thoughts? – user3311933 Mar 31 '14 at 20:43
  • can you place you table/tables definition in your question so i can see how you database design is ? only tables that are involved in this process – Up_One Mar 31 '14 at 20:44
  • I'm not quite sure what you mean but It's a very simple table that we're working with. I'll post it up in a rudimentary fashion. – user3311933 Mar 31 '14 at 20:58
  • Alright, Table definition is posted, and cleaned up and fixed by arootbeer(Thanks a ton!). – user3311933 Mar 31 '14 at 21:21
  • how many addresss the customer can have ? (one billing and one shipping) ? – Up_One Mar 31 '14 at 21:37
  • How many addresses they can have will vary, but there are only going to be two types of address (billing and shipping). I'm not too certain how many of each they'll need. I'd hope no more than 15 or 20 at MOST, but I could be wrong. – user3311933 Mar 31 '14 at 21:41
  • Hey Up_One, were you able to come up with anything? I have been tinkering with the trigger but can't seem to get it to work. I was thinking that changing the trigger to check both billingaddress AND shippingaddress would do the trick but I can't seem to figure out the syntax for that. – user3311933 Apr 02 '14 at 13:52
  • sorry for my delay , i will give you solution letter today (it's a promise ) – Up_One Apr 02 '14 at 13:53