1

I have a table with 3 columns (ID, username, full name), I want the ID to be AUTOINCREMENT. I want to insert into the table only if it does not already exist in the table.

This is my Code:

$fullName = $_POST['fullname'];
$username = $_POST['username'];
$dbhost = "localhost";
  $dbname = "databasename";
  $dbusername = "root";
  $dbpassword = "";

  $link = new PDO("mysql:host=$dbhost;dbname=$dbname","$dbusername","");

  $statement = $link->prepare('INSERT INTO accounts (username, fullname)
      VALUES (:username, :fname)');

  $statement->execute([
      'fname' => $fullName,
      'username' => $usernameget,
  ]);
  • 1
    **WARNING**: Writing your own access control layer is not easy and there are many opportunities to get it severely wrong. Please, do not write your own authentication system when any modern [development framework](http://codegeekz.com/best-php-frameworks-for-developers/) like [Laravel](http://laravel.com/) comes with a robust [authentication system](https://laravel.com/docs/master/authentication) built-in. At the absolute least follow [recommended security best practices](http://www.phptherightway.com/#security) and **never store passwords as plain-text** or a weak hash like **SHA1 or MD5**. – tadman Jul 15 '19 at 01:46
  • 1
    **WARNING**: When using `mysqli` you should be using [parameterized queries](http://php.net/manual/en/mysqli.quickstart.prepared-statements.php) and [`bind_param`](http://php.net/manual/en/mysqli-stmt.bind-param.php) to add any data to your query. **DO NOT** use string interpolation or concatenation to accomplish this because you have created a severe [SQL injection bug](http://bobby-tables.com/). **NEVER** put `$_POST`, `$_GET` or data *of any kind* directly into a query, it can be very harmful if someone seeks to exploit your mistake. – tadman Jul 15 '19 at 01:46
  • Note: If you're not populating a column, omit it from the `INSERT`. – tadman Jul 15 '19 at 01:46
  • Did you mean "a table with 3 columns?" – Trevor Reid Jul 15 '19 at 01:50
  • 2
    Omit the `id` column from the `INSERT` statement both in the list of columns used and the `VALUES()` component. Additionally, **DO NOT** use this code unless this is purely for academic purposes. If this is for learning purposes only, then I have a number of links there dealing with proper use of placeholder values, something that's really important to learn first before making a mess of things. – tadman Jul 15 '19 at 01:51
  • 1
  • @tadman but how can I check if the username or full name already exists on the table – Jalaleddine Askari Jul 15 '19 at 01:55
  • [Set a `UNIQUE` constraint](https://dev.mysql.com/doc/refman/8.0/en/create-index.html) (index) on those columns. Your `INSERT` will be rejected if those already exist. – tadman Jul 15 '19 at 02:08

6 Answers6

1

If your id is already autoncrement then you no need to mention in query.

You can simply write below query

insert into accounts (username,fullname) values( $username , $fullname )
Manish Patel
  • 117
  • 8
  • This still has a massive SQL injection bug. You can't gloss that over, and fixing it is trivial, either by substituting values for `?` to pass the buck, or by showing how this is done. – tadman Jul 15 '19 at 01:52
  • Then in this case. you need to check, if data already exist or not. you can do like this. Select statement and if statement execute it then data already exist if not then you can insert the data – Manish Patel Jul 15 '19 at 01:53
  • @ManishPatel How ?? – Jalaleddine Askari Jul 15 '19 at 01:57
  • you can refer this.. https://stackoverflow.com/questions/3164505/mysql-insert-record-if-not-exists-in-table – Manish Patel Jul 15 '19 at 02:00
  • Test and set is going to have a [race condition](https://en.wikipedia.org/wiki/Race_condition) where you may double-insert. – tadman Jul 15 '19 at 02:15
0

There's several things to fix here.

  • Don't specify column values if you don't need to, or don't care about the value. Only specify if necessary or relevant. In this case id should be omitted.
  • Always use placeholder values for your user data. Never put $_GET or $_POST data directly in a query.
  • To avoid duplication add a UNIQUE constraint on the table.

To fix that you do adjust your code:

// Enable exceptions, avoiding the need for manual error checking
mysqli_report(MYSQLI_REPORT_ERROR | MYSQLI_REPORT_STRICT);

// Try and keep the order of things like this consistent through your code
$username = $_POST['username'];
$fullname = $_POST['fullname'];

// Here using a short, common name for the database handle $db    
$db = new mysqli("localhost","root","","database");

// Prepare your insert first as a query with no data, only placeholders
$db->prepare("insert into accounts (username,fullname) values(?,?)");

// Bind the data to the placeholders, here two string ("s") values.
$db->bind_param('ss', $username, $fullname);

// Execute the query
$db->execute();

To add the UNIQUE constraints use CREATE INDEX:

CREATE INDEX idx_accounts_username (username);
CREATE INDEX idx_accounts_full_name (full_name);

That has to be run in your MySQL shell, not PHP.

When a UNIQUE constraint is in place MySQL will not allow duplicate data. Note that NULL values don't count, and can be "duplicated". Set NOT NULL on your columns to force them to be completely unique.

tadman
  • 194,930
  • 21
  • 217
  • 240
  • 1
    Please check , Code Updated – Jalaleddine Askari Jul 15 '19 at 02:28
  • PDO is actually a lot more pleasant to use than `mysqli`, so that's great to see. Not sure why you changed the name of the variables so dramatically, though. That won't work unless you pull in the data from `$_POST` correctly. In PDO you can `execute($_POST)` if you set the name of the placeholders the same as the arguments you're expecting. – tadman Jul 15 '19 at 02:30
  • the code now works, but i need just to check if the value already exists, how can i do it in PDO – Jalaleddine Askari Jul 15 '19 at 02:32
  • If you want it unique, my advice on adding a `UNIQUE` index still applies. Try not to make such radical changes in the nature of your question. We're trying to answer to the `mysqli` one and then you went and switched it to something completely different. – tadman Jul 15 '19 at 02:34
0

As your id is autoincrement primary key, so you can create or update it with:

insert into accounts (username,fullname) values( $username , $fullname ) on duplicate key update username = '$username',fullname = '$fullname'

LF00
  • 22,077
  • 20
  • 117
  • 225
0

you can do this with if else condition in PHP

$fullname = $_POST['fullname'];
$username = $_POST['username'];

$chk = mysqli_query("select * FROM `accounts` where fullname='$fullname' and username='$username'");
$rs = mysqli_fetch_array($chk);
if($rs == "")
{
    $ins = mysqli_query("INSERT INTO `accounts`(fullname,username) VALUES ('$fullname','$username'))";
} 
else{
    echo "Duplicate entry";
}   

or you can do this by SQL Query also.

INSERT INTO accounts(username,fullname)
SELECT * from (SELECT '$username', '$fullname') AS tmp
WHERE NOT EXISTS
(SELECT username FROM accounts WHERE username='$username')
Mohit Kumar
  • 902
  • 2
  • 6
  • 18
0

To get correct answers, a question must be asked with as much explanation as possible. you should atleast tell what have you done and then what are you getting.
As far as i have understood, to achieve your goal, the table structure must be changed and inserting query also.
Remember to accept the answer and click the upvote button if the answer satisfies you,
else give more information in the question, so that members here, can give right answers.

If you understand table creating queries go to bottom of this answer or else do as follows:
if you use gui to create table,
1. click on create new table.

enter image description here
2. in the right pane give table name and column names as shown. (dont give space in 'full name' instead give 'full_name' or 'fullname')

enter image description here 3. scroll the winow to the right till you see A_I column as shown.

enter image description here 4. tick the first line (which we have used as id), 'add index' box will appear.
just click here go (at the bottom).
you will be redirected to table list as shown.

enter image description here 6. open (click) your table again.

enter image description here 7. click on structure.
enter image description here now suppose you don't want duplicates in 'username' column, click this column and click on 'unique' as shown

enter image description here if you don't want duplicate when both the columns' value together, click both the columns and then click 'unique' as shown

enter image description here



if you understand create table commands:

here is the sql for above: CREATE TABLE accounts ( id int(11) NOT NULL AUTO_INCREMENT, username varchar(25) NOT NULL, fullname varchar(55) NOT NULL, PRIMARY KEY (id), UNIQUE KEY username (username) ) ENGINE=MyISAM DEFAULT CHARSET=latin1


with above table structure records will be autoincremented and duplicate names will not be added. (remember to handle duplicate entries error in you inserting querie with
INSERT IGNORE INTO

with this your query will be:

$statement = $link->prepare('INSERT IGNORE INTO accounts (username, fullname)
      VALUES (:username, :fname)');


or you can also use
ON DUPLICATE KEY)

sifr_dot_in
  • 1,395
  • 2
  • 18
  • 26
0

First set your primary key (eg. id) if not set as auto increment

Second use multiple insertion value

INSERT IGNORE INTO accounts (username,fullname) VALUES ("p","k"),("c","s");

IGNORE keyword is use to duplicate

IF you want to see with PDO

Pankaj Chauhan
  • 1,241
  • 11
  • 12