{"id":116,"date":"2006-06-04T22:47:50","date_gmt":"2006-06-05T03:47:50","guid":{"rendered":"http:\/\/www.juixe.com\/techknow\/index.php\/2006\/06\/04\/query-managed-auto-increment\/"},"modified":"2006-06-04T22:47:50","modified_gmt":"2006-06-05T03:47:50","slug":"query-managed-auto-increment","status":"publish","type":"post","link":"http:\/\/juixe.com\/techknow\/index.php\/2006\/06\/04\/query-managed-auto-increment\/","title":{"rendered":"Query Managed Auto Increment"},"content":{"rendered":"<p>Different database vendors allow you to auto increment an integer primary key in different ways.  I thought that I could manage to increment the primary key from within the same insert statement.  Given the following table:<\/p>\n<pre>\nCREATE TABLE temps (\n   id INT NOT NULL,\n   name VARCHAR(10) NOT NULL,\n   PRIMARY KEY (id)\n);\n<\/pre>\n<p>I thought could create a single insert statement that also managed to auto increment the id primary key.  I thought I could do something like:<\/p>\n<pre>\nINSERT INTO temps VALUES(\n   (SELECT max(t.id)+1 FROM\n      (SELECT id FROM temps UNION SELECT 0)\n   t),\n'juixe');\n<\/pre>\n<p>When I run the above insert statement using MySQL 4.1.15 I get an error that reads, &#8220;You can&#8217;t specify target table &#8216;temps&#8217; for update in FROM clause.&#8221;<\/p>\n<p>Using Microsoft SQL Server 2005 Express I get an error that reads, &#8220;Subqueries are not allowed in this context.  Only scalar expressions are allowed.&#8221;  This is most unfortunate because subqueries are really powerful.<\/p>\n<p>I had better luck on Oracle Database 10g Express Edition where I could run what I call Query Managed Auto Increment statement.  On Oracle 10g EX I was able to run the following Query Managed Auto Increment statement with a minor modification:<\/p>\n<pre>\nINSERT INTO temps VALUES(\n   (SELECT max(t.id)+1 FROM\n      (SELECT id FROM temps UNION SELECT 0 from user_tables)\n   t),\n'techknow');\n<\/pre>\n<p>What doesn&#8217;t work well in Oracle is that you can&#8217;t run a select statement without a table name.  On Oracle you can&#8217;t run the following statement: select 0.  Query Managed Auto Increment works in Oracle but you would need default to a table that has at least one record, such as the user_tables table.<\/p>\n<p>Just for completeness I tried PostgreSQL 8.1.4.  PostgreSQL supports static select statements, select statements without the from clause and return a constant value.  Because PostgreSQL supports static select statements I am guaranteed that the following will return at least one row of ids even if the table is empty:<\/p>\n<pre>\nSELECT id FROM temps UNION SELECT 0;\n<\/pre>\n<p>Adding one to the max id returns the next primary key id, which I use in the insert statement.  Once again here is the working SQL (in PostgreSQL) that manages the primary key and automatically increments the id to the next available integer value.<\/p>\n<pre>\nINSERT INTO temps VALUES(\n   (SELECT max(t.id)+1 FROM\n      (SELECT id FROM temps UNION SELECT 0)\n   t),\n'zenze');\n<\/pre>\n<p>So in conclusion, Query Managed Auto Increment doesn&#8217;t exactly work in MySQL because you can&#8217;t use a subquery that refers the same table as the insert.  SQL Server has the limitation that you can&#8217;t even execute a subquery in an insert.  And as we have seen Query Managed Auto Increment works on Oracle and PostgreSQL.<\/p>\n<p>Technorati Tags: <a href=\"http:\/\/technorati.com\/tag\/sql\" rel=\"tag\">sql<\/a>, <a href=\"http:\/\/technorati.com\/tag\/query\" rel=\"tag\"> query<\/a>, <a href=\"http:\/\/technorati.com\/tag\/subqueries\" rel=\"tag\"> subqueries<\/a>, <a href=\"http:\/\/technorati.com\/tag\/mysql\" rel=\"tag\"> mysql<\/a>, <a href=\"http:\/\/technorati.com\/tag\/sql+server\" rel=\"tag\"> sql server<\/a>, <a href=\"http:\/\/technorati.com\/tag\/oracle\" rel=\"tag\"> oracle<\/a>, <a href=\"http:\/\/technorati.com\/tag\/postgresql\" rel=\"tag\"> postgresql<\/a><\/p>\n","protected":false},"excerpt":{"rendered":"<p>Different database vendors allow you to auto increment an integer primary key in different ways. I thought that I could manage to increment the primary key from within the same insert statement. Given the following table: CREATE TABLE temps ( id INT NOT NULL, name VARCHAR(10) NOT NULL, PRIMARY KEY (id) ); I thought could [&hellip;]<\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"spay_email":"","footnotes":""},"categories":[23,3],"tags":[],"jetpack_featured_media_url":"","jetpack_shortlink":"https:\/\/wp.me\/p902K-1S","jetpack_sharing_enabled":true,"_links":{"self":[{"href":"http:\/\/juixe.com\/techknow\/index.php\/wp-json\/wp\/v2\/posts\/116"}],"collection":[{"href":"http:\/\/juixe.com\/techknow\/index.php\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"http:\/\/juixe.com\/techknow\/index.php\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"http:\/\/juixe.com\/techknow\/index.php\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"http:\/\/juixe.com\/techknow\/index.php\/wp-json\/wp\/v2\/comments?post=116"}],"version-history":[{"count":0,"href":"http:\/\/juixe.com\/techknow\/index.php\/wp-json\/wp\/v2\/posts\/116\/revisions"}],"wp:attachment":[{"href":"http:\/\/juixe.com\/techknow\/index.php\/wp-json\/wp\/v2\/media?parent=116"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"http:\/\/juixe.com\/techknow\/index.php\/wp-json\/wp\/v2\/categories?post=116"},{"taxonomy":"post_tag","embeddable":true,"href":"http:\/\/juixe.com\/techknow\/index.php\/wp-json\/wp\/v2\/tags?post=116"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}