This question already has an answer here:
Mysql - Add auto_increment to primary key
(1 answer)
Closed 9 years ago.
I have a form that sends the data it captures in to a database, i have a primary key attached to my table (form_id) which i want to autoincrement everytime a new form is submitted and consequently added into my database table. Currently it is just adding a 0 for the first form submitted then anymore forms i submit after do not show as it gives me a message saying you can not have two rows with the same id as zero, which is correct so i would like to change this?
Below is my php code that submits the data into the database:
public function action_claimincentive() {
$this->template->content = View::factory('crm/uk/claim_incentive_form');
$this->template->content->thanks = false;
$this->template->content->val = '';
$this->template->content->post = '';
if ($this->request->post('form')) {
$post = $this->request->post('form');
$stmt = DB::query(Database::INSERT, 'INSERT INTO `claim_incentive_form_data` (`Claimant Name`, `Claimant Postcode`, `Purchase Order No.`, `Claimant Email Address`, `Storename`, `Storetown`, `Date of Sale`, `Date of Delivery`, `Tempur Acknowledgement No.`, `Tempur Product`)
VALUES (:claimantname, :claimantpostcode, :orderno, :email, :storename, :storetown, :dateofsale, :dateofdelivery, :acknowledgementno, :tempurproduct)');
$stmt->param(':claimantname', $post['claimantname']);
$stmt->param(':claimantpostcode', $post['claimantpostcode']);
$stmt->param(':orderno', $post['orderno']);
$stmt->param(':email', $post['email']);
$stmt->param(':storename', $post['storename']);
$stmt->param(':storetown', $post['storetown']);
$stmt->param(':dateofsale', $post['dateofsale']);
$stmt->param(':dateofdelivery', $post['dateofdelivery']);
$stmt->param(':acknowledgementno', $post['acknowledgementno']);
$stmt->param(':tempurproduct', $post['tempurproduct']);
try {
$stmt->execute();
$this->template->content->post = $post;
$this->template->content->thanks = true;
} catch (Exception $e) {
FB::error($e);
}
}
}
This sounds more like a MySQL issue rather than anything else. Make sure you have your Primary Key setup to auto increment. Try altering the table to add the auto increment feature:
ALTER TABLE [table name] MODIFY COLUMN [column name] [column type] PRIMARY KEY AUTO_INCREMENT;
In the above example. Replace the keys in brackets with their appropriate names. Replace [table name] with the name of your table, [column name] with the name of the column and [column type] with the type of the column (SMALLINT, INT, etc).
For more information, see this answer posted by roman.
For more information on the AUTO_INCREMENT feature, check out the MySQL Development Documentation here.
You need to add AUTO_INCREMENT to the primary key column on the table check this http://dev.mysql.com/doc/refman/5.0/en/example-auto-increment.html
you should be able to alter the table with something like this
ALTER TABLE claim_incentive_form_data CHANGE id id INT(10)AUTO_INCREMENT PRIMARY KEY;
Just make sure you change the id column and the datatype if yours are diffrent from that.
You have to set the auto_increment setting in the table within mysql.
ALTER TABLE `claim_incentive_form_data` MODIFY COLUMN `your_primary_column` int(4) PRIMARY KEY AUTO_INCREMENT
Refs:
http://dev.mysql.com/doc/refman/5.0/en/example-auto-increment.html
http://dev.mysql.com/doc/refman/5.0/en/alter-table.html
you have to set form_id as primary key, auto increment and not null.
Related
I searched on stack and try to apply many solutions i found, but not a single is working with this one.
I have a problem with this query because ON DUPLICATE KEY UPDATE is INSERT new results instead of updating existing ones.
INSERT INTO signal_providers_relations (
id,
client_id,
provider_id,
active_sp,
subscription_sp,
created_by,
cr_datetime,
ea_settings_active_sp,
ea_settings_sp,
up_datetime,
sp_risk_allocation,
sp_max_trades )
VALUES (
'',
'".$user_id."',
'".$r['provider_id']."',
'".$r['active_sp']."',
'".$r['subscription_sp']."',
'".$r['created_by']."',
'".$r['cr_datetime']."',
'".$r['ea_settings_active_sp']."',
'".$r['ea_settings_sp']."',
'".$r['up_datetime']."',
'".$r['sp_risk_allocation']."',
'".$r['sp_max_trades']."'
)
ON DUPLICATE KEY
UPDATE
id = '".$r['id']."'
client_id = '".$user_id."',
provider_id = '".$r['provider_id']."',
active_sp = '".$r['active_sp']."',
subscription_sp = '".$r['subscription_sp']."',
created_by = '".$r['created_by']."',
cr_datetime = '".$r['cr_datetime']."',
ea_settings_active_sp = '".$r['ea_settings_active_sp']."',
ea_settings_sp = '".$r['ea_settings_sp']."',
up_datetime = '".$r['up_datetime']."',
sp_risk_allocation = '".$r['sp_risk_allocation']."',
sp_max_trades = '".$r['sp_max_trades']."'
Here is a image with table structure
Assuming this table holds data specific to a single client/provider relationship then your UNIQUE identifier is really a combination of the client_id and provider_id - so you could drop your current client_id and provider_id INDEXES and replace them with a UNIQUE compound index.
ALTER TABLE `signal_providers_relations` DROP INDEX `client_id`;
ALTER TABLE `signal_providers_relations` DROP INDEX `provider_id`;
ALTER TABLE `test`.`signal_providers_relations`
ADD UNIQUE `unique_client_provider` (`client_id`, `provider_id`);
This will give you a specific, unique key which would trigger ON DUPLICATE KEY UPDATE when you attempt to insert data for a specific client/provider combination that already exists, which is what I think you're trying to achieve.
It's quite likely you could, at this point, drop the meaningless id column and change that unique_client_provider key just created to being the PRIMARY instead - but that may have repercussions on other parts of your code.
to avoid this use REPLACE INTO instead of INSERT INTO in your query
After looking around on stackoverflow, I'm still having a little trouble understanding the one-to-many relationship in mysql. I have a request coming in from the user (form submission) which will be stored in one table. This is a dynamic form that lets the user add extra fields therefore those will be stored in a separate table. So in short, in my db design, there will be one table for the users with PRIMARY KEY AUTO INCREMENT and there will be another table for the hostnames PER user (multiple fields -array) and using a foreign key that references to the primary key in the user table. Sorry if this is long but trying to make this a good question.
Example:
User Table: (ONE)
1. John Doe, blah, 11-12-15
2. Sally Po, blah, 11-14-15
3. John Doe, blah, 11-15-15
(these are three separate requests)
(numbers are primary key auto incr.)
Host Name Table: (MANY)
1. www.johndoe.com
1. www.johndoe2.com
1. www.johndoe3.com
2. www.sallypo.com
2. www.sallypo2.com
(these numbers (foreign key) should match the primary key for each request)
Code (Leaving out the actual queries + pretty sure I shouln't be using last_id):
$sql = "CREATE TABLE IF NOT EXISTS userTable (
id int AUTO_INCREMENT,
firstName VARCHAR(30) NOT NULL,
date DATE NOT NULL,
PRIMARY KEY (id)
)";
//query
$sql = "CREATE TABLE IF NOT EXISTS hostNamesTable (
id int NOT NULL,
hostName VARCHAR(90) NOT NULL,
FOREIGN KEY (id) REFERENCES userTable(id)
)";
//query
$sql = "INSERT INTO userTable (firstName, date)
VALUES ('$firstName', '$date')";
//query
$last_id = mysqli_insert_id();
for($i = 0; $i < sizeof($hostName); $i++){
$sql = "INSERT INTO hostNamesTable (id, hostName)
VALUES ('$last_id', '$hostName[$i]')";
//query
}
What am I doing wrong? (is this the right way to go about it?)
note: I was trying to get the last_id of the user Table so that I can use it in the hostName table as the foreign key
EDIT: I'm using MySQLi with php
EDIT 2:
After the changes, this is the error I am getting now: Cannot add or update a child row: a foreign key constraint fails (d9832482827984hb28397429.hostNamesTable, CONSTRAINT hostNamesTable_ibfk_1 FOREIGN KEY (id) REFERENCES userTable (id))Error: INSERT INTO hostNamesTable (id, hostName, ) VALUES ('', 'secondhost.net')
--Looks like the $last_id isn't even being recorded?
EDIT 3: Started working. Not sure what it was but I think it was because of some type.
why dont you just add an extra column in the hostNames table which is called "ref_user" and contains the ID of the user you are reffering to? So you can use unique IDs in both tables.
Make a query like:
SELECT * FROM hostNames WHERE ref_user = (SELECT id FROM userTable WHERE <uniqueColumn> = <uniqueIdentifierOfUser>);
But the included request must return only one line from users.
try adding mysqli $link as a parameter in your mysqli_insert_id
$last_id = mysqli_insert_id($link);
i presume you have this somewhere in your code
$link = mysqli_connect("localhost", "mysql_user", "mysql_password", "mysql_db");
if this doesn't work, try using mysql LAST_INSERT_ID() function
$last_id = $mysqli->query("SELECT LAST_INSERT_ID() AS last_id")->fetch_object()->last_id;
I am trying to do an INSERT only if the combination of two columns (a and b) does not exist already. Otherwise, I want to do an UPDATE. The issue of the following code is that it always INSERTs a new row instead of updating when I want to. The reason I think, is because I don't manage do have a kind of two-unique-column in the settings of my table.
Does any one have a solution? Google doesn't seem to be my friend today..
The table:
id : int, primary, AI
a b c and d : int
The code:
$req = $connexion -> prepare("
INSERT INTO position (a,b,c,d)
VALUES (:a,:b,:c,:d)
ON DUPLICATE KEY UPDATE
c=:c;");
$position->bindParam(':a', $a);
$position->bindParam(':b', $b);
$position->bindParam(':c', $c);
$position->bindParam(':d', $d);
$a = $val_a;
$b = $val_b;
$c = $val_c;
$d = $val_d;
$req -> execute();
ON DUPLICATE KEY requires a UNIQUE KEY if you are not matching to the PRIMARY KEY. You can add a UNIQUE KEY by using an ALTER TABLE query
ALTER TABLE position ADD UNIQUE KEY (a,b)
Have you already tried to alter the table to reflect what you need? try this before executing your code.
ALTER TABLE `position` ADD UNIQUE `unique_index`(`a`, `b`);
I have a table named users
fields:
ID INT
First_name VARCHAR
Second_name VARCHAR
National_ID INT
The ID field is an AUTO_INCREMENT.
I need to AUTO_INCREMENT the first 2000 users with just the ID and the other fields remain blank,so that the new users will start at 2001.
Kindly assist.
It's called auto increment, your ID column must be set to auto increment.
ALTER TABLE users AUTO_INCREMENT=2001;
Update
If you wish to actually create those rows (not just set the auto increment value) you can use PHP for this:
for($i=1; $i<=2000; $i++)
{
$query = 'INSERT INTO users (id) VALUES ('.$i.')';
//execute this query using your desired PDO or sql extension
}
I have a form to edit a record (specimen). On the form is a multiple select list which contains records from a table (topic). This select list shows topics as selected that exist for the specimen (as identified in the specimen_topic lookup table) as well as those that can be added to the specimen (from the topic table).
I want to be able to add topics not selected in the list to the lookup table where the topic_fk does not already exist for the specimen_fk:
CREATE TABLE IF NOT EXISTS `specimen_topic_lookup` (
`specimen_topic_lookup_pk` int(6) NOT NULL AUTO_INCREMENT,
`specimen_fk` int(6) NOT NULL,
`topic_fk` int(3) NOT NULL,
PRIMARY KEY (`specimen_topic_lookup_pk`)
) ENGINE=MyISAM DEFAULT CHARSET=utf8 COLLATE=utf8_swedish_ci AUTO_INCREMENT=8 ;
Any ideas how I can do this?
UPDATE
I have made the fields specimen_fk and topic_fk UNIQUE. Using the code below, only one record is created in specimen_table lookup, when two records should have been created (before making the fields UNIQUE, two records were created OK...). I assume this is because $specimen_pk is the same value for each insert.
foreach($topics as $topic){
$query_topics = "INSERT IGNORE INTO specimen_topic_lookup(specimen_fk, topic_fk)
VALUES ('$specimen_pk', '$topic')";
$result_topics = mysql_query($query_topics, $connection) or die(mysql_error());
}
Looks like having UNIQUE is stopping having a record made with the same value (which is at least what I expected...)
THIS WORKS
Without having to make specimen_fk OR topic_fk UNIQUE...
foreach($topics as $topic){
$query_topics = "INSERT INTO specimen_topic_lookup(specimen_fk, topic_fk)
SELECT '$specimen_pk', '$topic'
FROM DUAL
WHERE NOT EXISTS (SELECT 1
FROM specimen_topic_lookup
WHERE specimen_fk = '$specimen_pk' AND topic_fk = '$topic')";
$result_topics = mysql_query($query_topics, $connection) or die(mysql_error());
Create a unique index on the table and use insert ignore or on duplicate key update:
create unique index specimen_topic_lookup(specimen_fk, topic_fk);
insert ignore into specimen_topic_lookup(specimen_fk, topic_fk)
select $speciment_fk, $topic_fk;
Or, alternatively, you can just do the following without the unique index:
insert into specimen_topic_lookup(specifmen_fk, topic_fk)
select $speciment_fk, $topic_fk
from dual
where not exists (select 1
from specimen_topic_lookup
where specimen_fk = $specimen_fk and topic_fk = $topic_fk
);
Use an INSERT IGNORE statement. This will insert any rows that do not violate the unique key, and ignore the ones that do.