DevLearningTools

LEARN · SQL

SQL CREATE TABLE

CREATE TABLE defines a new table's columns, types, and keys. Build Beacon Robotics' actual departments, employees, projects, and project_assignments tables here.

The joins-overview lesson back in Module 4 introduced departments, employees' department_id and manager_id, projects, and project_assignments, and promised the real CREATE TABLE syntax would come in this module. This is that lesson, the statements that actually build every table this course has been querying ever since.

Learning Objectives

  • Write a CREATE TABLE statement with columns, types, and a primary key.
  • Use a FOREIGN KEY to link a table to another, like employees.department_id to departments.id.
  • Know how auto-incrementing primary keys differ across every database in this course.

Creating departments

id is the primary key, uniquely identifying each row, AUTO_INCREMENT means the database assigns the next whole number automatically on every insert, no need to specify it manually. VARCHAR(50) is a variable-length text column capped at 50 characters, covered in full in the data types lesson later in this course.

MySQL / MariaDB
CREATE TABLE departments (
  id INT AUTO_INCREMENT PRIMARY KEY,
  name VARCHAR(50) NOT NULL
);

Creating employees, With a Foreign Key

FOREIGN KEY (department_id) REFERENCES departments(id) is what formally makes department_id a real foreign key, the database now enforces that any value stored there must match an actual id in departments (or be NULL). manager_id's foreign key points back at employees(id) itself, the formal, enforced version of the self-join relationship from Module 4, a table can absolutely reference itself this way.

MySQL / MariaDB
CREATE TABLE employees (
  id INT AUTO_INCREMENT PRIMARY KEY,
  first_name VARCHAR(50) NOT NULL,
  last_name VARCHAR(50) NOT NULL,
  department_id INT,
  salary DECIMAL(10,2),
  hire_date DATE,
  manager_id INT,
  FOREIGN KEY (department_id) REFERENCES departments(id),
  FOREIGN KEY (manager_id) REFERENCES employees(id)
);

Creating projects and project_assignments

project_assignments is the many-to-many linking table from Module 4, its two foreign keys are what actually enforce that every row connects a real employee to a real project, nothing more needed for the basic shape, a composite PRIMARY KEY spanning both columns is covered in Module 8's Constraints.

MySQL / MariaDB
CREATE TABLE projects (
  id INT AUTO_INCREMENT PRIMARY KEY,
  name VARCHAR(100) NOT NULL
);

CREATE TABLE project_assignments (
  employee_id INT,
  project_id INT,
  FOREIGN KEY (employee_id) REFERENCES employees(id),
  FOREIGN KEY (project_id) REFERENCES projects(id)
);

The Finished Schema

All four CREATE TABLE statements above build exactly this: employees pointing at departments through department_id, and project_assignments linking employees to projects. Every join and subquery since Module 4 has been querying this same shape.

1234
  1. 1departments: id and name. Engineering, Research, Marketing, Sales, and Legal, which has zero employees.
  2. 2employees: Points at departments via department_id (the arrow), and at itself via manager_id for the self-join, not drawn here to keep the diagram readable.
  3. 3projects: id and name. Warehouse Bot v2, Night Vision Sensors, Fleet Dashboard.
  4. 4project_assignments: The many-to-many link table: one row per employee-project pairing, pointing at both employees and projects (dashed arrows).

Auto-Incrementing IDs by Database

DatabaseAuto-Incrementing Primary Key Syntax
MySQL / MariaDBid INT AUTO_INCREMENT PRIMARY KEY
PostgreSQLid SERIAL PRIMARY KEY (or GENERATED ALWAYS AS IDENTITY, modern style)
SQL Serverid INT IDENTITY(1,1) PRIMARY KEY
SQLiteid INTEGER PRIMARY KEY (auto-increments by default)
Oracle (12c+)id NUMBER GENERATED ALWAYS AS IDENTITY PRIMARY KEY
NOTE

This is one of the most genuinely fragmented syntax areas in all of SQL, five different databases, five different ways to say "auto-number this primary key." Everything else about CREATE TABLE, column definitions, NOT NULL, FOREIGN KEY, stays essentially the same across all six.

Try It Yourself

Write a CREATE TABLE statement for a new reviews table: id (auto-incrementing primary key), employee_id (foreign key to employees), rating (an integer), on MySQL.

Answer
CREATE TABLE reviews (
  id INT AUTO_INCREMENT PRIMARY KEY,
  employee_id INT,
  rating INT,
  FOREIGN KEY (employee_id) REFERENCES employees(id)
);

Frequently Asked Questions

Does the referenced table (departments) need to exist before creating employees?

Yes, a FOREIGN KEY referencing departments(id) requires departments to already exist, otherwise the CREATE TABLE statement for employees fails. Table creation order matters whenever foreign keys are involved.

What happens if an INSERT tries to use a department_id that doesn't exist in departments?

The foreign key constraint rejects it, the INSERT fails rather than silently storing an invalid reference. This enforcement is the entire point of declaring it as a FOREIGN KEY instead of a plain INT.

Common Beginner Mistakes

Creating employees before departments exists

The FOREIGN KEY (department_id) REFERENCES departments(id) clause fails immediately, departments(id) doesn't exist yet to reference. Create tables in dependency order: the table being referenced first, the table with the foreign key second.

Using AUTO_INCREMENT syntax on PostgreSQL, or SERIAL on MySQL

Neither works on the other database, this is exactly the fragmented area the table above exists to flag. Check which of the five patterns applies before writing a CREATE TABLE statement.

Best Practices

  • Create tables in dependency order, referenced tables before the tables with foreign keys pointing at them.
  • Use consistent, descriptive column names across related tables, department_id on employees clearly points at departments, not some abbreviated or inconsistent name.
  • Look up the correct auto-increment syntax for the target database rather than assuming one pattern works everywhere.

Interview Questions

Why must departments be created before employees in Beacon Robotics' schema?

employees has FOREIGN KEY (department_id) REFERENCES departments(id), which requires departments(id) to already exist at the moment employees is created. Creating tables out of dependency order causes the FOREIGN KEY clause to fail.

Write the CREATE TABLE statement for projects, with an auto-incrementing id and a required name column, on PostgreSQL.

CREATE TABLE projects (id SERIAL PRIMARY KEY, name VARCHAR(100) NOT NULL); — SERIAL is PostgreSQL's auto-incrementing integer type, equivalent to MySQL's AUTO_INCREMENT but a different keyword entirely.

Summary

CREATE TABLE defines a table's columns, types, and keys, FOREIGN KEY formally links one table to another, enforced by the database itself. Auto-incrementing primary key syntax is one of the most fragmented areas across this course's six databases, five genuinely different patterns for the same idea.

What's Next?

DROP TABLE next, removing a table entirely, and what happens when other tables still hold foreign keys pointing at it.

</>

Ready to Practice SQL?

Write and run real SQL queries online, right in your browser, no install or signup required. Pick a playground based on which database you want to practice on.

SQLite / PostgreSQL

Fast, no server, no ads.

Open DB Fiddle ↗

MySQL / SQL Server

Switch databases with one dropdown.

Open SQL Fiddle ↗

Both open a third-party SQL playground in a new tab. External site terms and privacy policy apply.