Database CheatSheet
SQLGo to video for this category
italics, [optional]
italic variables, < generic item type>, [optional item], alt1 | alt2, ... more, underline defaults, Keyboard shortcuts
Throughout this CheatSheet we will use the below symbols and conventions to document commands:
lowercase-italics Words in italics indicate the item is a user provided variable. You must substitute the appropriate names or values.
Example:
Provide an example with italics.
Provide same example with actual data.
< > Angle brackets contain a generic item type. You must substitute it with the appropriate values. The angle brackets themselves are not typed.
Example:
Provide an example with angle brackets.
Provide same example with actual data.
[ ] Square brackets contain optional items. The square brackets themselves are not typed.
Example:
Provide an example with square brackets.
Provide same example with actual data.
| Items separated by a single vertical bar are alternative items. You can select only one of the group of items separated by single vertical bars. The vertical bar itself is not typed.
Example:
Provide an example with vertical bar.
Provide same example with actual data.
Other Symbols and conventions:
Keyboard Shortcuts:
lowercase-italics Words in italics indicate the item is a user provided variable. You must substitute the appropriate names or values.
Example:
Provide an example with italics.
Provide same example with actual data.
< > Angle brackets contain a generic item type. You must substitute it with the appropriate values. The angle brackets themselves are not typed.
Example:
Provide an example with angle brackets.
Provide same example with actual data.
[ ] Square brackets contain optional items. The square brackets themselves are not typed.
Example:
Provide an example with square brackets.
Provide same example with actual data.
| Items separated by a single vertical bar are alternative items. You can select only one of the group of items separated by single vertical bars. The vertical bar itself is not typed.
Example:
Provide an example with vertical bar.
Provide same example with actual data.
Other Symbols and conventions:
- ... An ellipsis indicates that multiple entries of the type immediately preceding the ellipsis are allowed.
- Underlined items indicate default options.
Keyboard Shortcuts:
- Mac keyboard shortcuts generally use the Command key.
- Windows keyboard shortcuts generally use the Control key.
- By convention, keyboard commands are written like Command+C. This means to press the Command key and the lower case "c" key simultaneously.
- Mac and Windows usually, but not always, use the same key combinations for the shortcuts, so they could be expressed as commandOrControl+C.
Terms
- Database (aka data store): organized collection of data stored electronically and accessed by a database management system.
- Relational Database: database where data is organized into one or more data tables which may be related to each other.
- Relational Database Management System (RDBMS): Provides a user interface for the database and applications using the database, as well as administrative functions for managing data storage, access, and performance.
- SQL (Structured Query Language): the standard language to create, modify, and extract data from a relational database.
- SQL statement: A unit of SQL code that defines the action to be carried out.
- Query: request to access data from a database to manipulate it or retrieve it.
- Schema: the "blueprint" of the database defining how the data is organized. It includes logical constraints such as table names, fields, data types, and the relationships between them.
- Table (aka relation): a set of related data, structured in rows and columns. Columns are named and have a data type. Data items are stored in the rows.
- SQL Keywords: reserved words that have special meaning in the SQL language. By convention these are in upper case in your SQL statements.
- Identifiers: names you supply for variables such as table names, column names, etc. They must be unique and cannot be keywords. These are not in upper case.
SQL Syntax
- Semicolons: End each statement with a semicolon.
- Quotes:
- Use single quotes for string literals: 'Hello World'.
- Double quotes for identifiers with capital letters: "CreatedAt"
- Use two single quotes to escape a single quote in a string:
''
- Comments:
- Single line comments:
-- This is a comment
- Multi-line comments:
/* multi-line comment here */
- Capitalization: SQL is case insensitive. Convention: uppercase keywords (shell commands excepted), lower case identifiers (table names, column names, etc.)
SELECT title, author, publisher FROM books;
- There is no consensus on capitalization of data types (e.g., varchar vs VARCHAR). Either can be used.
- Naming Conventions: Common practice to use snake_case:
- Table names: No consensus on pluralization:
library_book
,library_books
- Column names: Singular snake_case is common:
title
,postal_code
SQL Comparison Operators
Equal to:
=
Not equal to: <>
Greater than, greater than or equal to:
>
, >=
Less than, less than or equal to:
<
, <=SQL Logical Operators
Commonly used in WHERE clauses.
AND True if all the conditions separated by AND are true.
OR True if any of the conditions separated by OR are true.
NOT Where the condition is NOT true.
Examples
SELECT * FROM books WHERE available = 1 AND price > 9.99;
SELECT * FROM books WHERE price = 0 OR price > 9.99;
SELECT * FROM books WHERE NOT price = 0;
Alternatively use the not equal comparison operator:
SELECT * FROM books WHERE price <> 0;
Postgres DatabaseGo to video for this category
Syntax:
- Only allows single quotes around strings.
- Does not distinguish capitalization on identifiers (e.g., table or column names) unless they are in double quotes.
PSQL Shell
Ref: postgresql.org/docs/current/app-psql.htmlDefine shell, CLI, terminal
Language shell: A language shell such as PSQL, is a simple, interactive computer programming environment that takes single user inputs (i.e. single expressions), evaluates them, and returns the result to the user. Each input is executed piecewise.
Besides the PSQL shell, common examples of a language shell include Unix shells such as Bash, and Z Shell (zsh). The Node.js shell executes JavaScript scripts.
Language shell is also called a Read–Eval–Print Loop (REPL).
Command-line interface (CLI): is a computer program that processes commands in the form of lines of text. The user typically interacts with the shell via a CLI.
Terminal is an application that wraps the command line interface. By default it launches a Unix shell. From there you can launch the PSQL shell or other shell programs you have installed.
Besides the PSQL shell, common examples of a language shell include Unix shells such as Bash, and Z Shell (zsh). The Node.js shell executes JavaScript scripts.
Language shell is also called a Read–Eval–Print Loop (REPL).
Command-line interface (CLI): is a computer program that processes commands in the form of lines of text. The user typically interacts with the shell via a CLI.
Terminal is an application that wraps the command line interface. By default it launches a Unix shell. From there you can launch the PSQL shell or other shell programs you have installed.
Shell Commands
Unix commands:
which psql returns path to psql executable filepsql --version returns psql version
man psql Official psql docs.
Open the PSQL Shell:
psql -U postgres Open the postgres DB as the postgres username
psql database_name Open the specified DB under the current user's system username
psql -d database_name -U username Open the specified DB under the specified username
PSQL Commands:
\conninfo Connection info includes: database name, username, socket, port number.
\l List all databases
\du List all users and their assigned roles.
\d or \dt List all relations (tables)
\d tablename Show information for the specified table.
\c database_name Connect to another database.
\h Help | \? command Help on the specified command
\q | quit | exit |
Ctrl+D
Quit PSQLshow data_directory Returns the path to where your database data is stored.
PG Admin
Open SQL Query Tool:
|

View Table column properties:
Refresh:
Rt-click any heading > Query Tool
| Toolbar:
Tools menu > Query Tool
- Execute query:
Execute/Refresh toolbar ▶
- Toggle comments:
Cmd+Shift+/
- Create Database:
Rt-click Databases > Create: Database
- Drop Database:
Rt-click database_name > Delete/Drop
- Create Table:
Rt-click Tables > Create: Table
- Drop Table:
Rt-click tablename > Delete/Drop
- Add column to table:
tablename > Rt-click Columns > Create: Column
Rt-click tablename > View/Edit Data: All Rows
| Toolbar:
View Table column properties:
Rt-click tablename > properties > Columns tab
Refresh:
Rt-click any category on left panel > refresh
| Object menu > Refresh
Data Types (Most common)
- Ref (full list): postgresql.org/docs/current/datatype
- Capitalization: No consensus. Docs show data types in lower case.
- When creating a table each column must include the name and datatype:
CREATE TABLE tablename (fieldname datatype, fieldname datatype);
Character string data types
Ref: postgresql.org/docs/current/datatype-character- CHARACTER VARYING(n) | alias: VARCHAR(n) variable-length with limit (can specify any limit).
- CHARACTER(n) | alias: CHAR(n) fixed-length. Values less than n length are padded with spaces.
- TEXT variable unlimited length.
- VARCHAR and TEXT can store up to 1GB of data.
- Per Postgres docs, there is no performance difference between VARCHAR(n), VARCHAR, and TEXT.
Numeric data types
Ref: postgresql.org/docs/current/datatype-numeric- INTEGER | alias: INT Integers (no decimal points) range +/-2.1 billion.
- SMALLINT (range +/-32k).
- BIGINT (range +/- 9x10^18).
- NUMERIC | alias: DECIMAL Allows decimal points.
- NUMERIC(percision,scale) Specify precision (total digits), and scale (number of digits after the decimal point).
- Floating point numbers (aka floats): the decimal point can "float" to the appropriate position.
- REAL single precision floating-point number.
- DOUBLE PRECISION double precision floating-point number.
Boolean data type (true or false)
Ref: postgresql.org/docs/current/datatype-boolean- BOOLEAN True values: true, yes, on, 1; False values: false, no, off, 0.
Date/Time data types
Ref: postgresql.org/docs/current/datatype-datetime- DATE 'YYYY-MM-DD'
- TIME 'hh:mm:ss'
- TIMESTAMP 'YYYY-MM-DD hh:mm:ss[.fraction] [time zone]'
- Timestamp values are converted from the current time zone to UTC for storage, and back to current time zone on retrieval.
- Current time zone defaults to the server's time.
Binary data type (e.g., binary image file)
Ref: postgresql.org/docs/current/datatype-binary- BYTEA Variable-length binary string.
Example
Create a table named books with columns:
- id - Auto-incrementing integer row id column.
- title - Length is variable up to 255 characters.
- author - Length is variable up to 100 characters.
- cover - cover image - binary image file.
- isbn - 13 number characters uniquely identifying a book.
- description - no specified character limit.
- quantity - integer value.
- price - in format xxx.xx so 5 total numbers including two after the decimal point
- on_sale - boolean
- published_date - date without time.
CREATE TABLE books (
id SERIAL PRIMARY KEY, title VARCHAR(255), author VARCHAR(100),
isbn CHAR(13), description TEXT, quantity INTEGER, price NUMERIC(5,2),
on_sale BOOLEAN,
published_date DATE
);
Auto-incrementing Row ID
- Data type can be SMALLINT, INT, or BIGINT. Can be PRIMARY KEY.
- id INT GENERATED ALWAYS AS IDENTITY does not allow you to set id.
- id INT GENERATED BY DEFAULT AS IDENTITY allows you to set id.
Examples. Specify a start number.
- Id automatically generated. Does not allow id to be set.
CREATE TABLE authors (
id INT GENERATED ALWAYS AS IDENTITY PRIMARY KEY,
name VARCHAR(255)
);
First statement works, second statement throws an error:
INSERT INTO authors(name) VALUES('Joey R.');
INSERT INTO authors(id, name) VALUES(45, 'Sheena R.');
- Allow id to be set:
CREATE TABLE authors (
id INT GENERATED BY DEFAULT AS IDENTITY PRIMARY KEY,
name VARCHAR(255)
);
Both statements work:
INSERT INTO authors(name) VALUES('Joey R.');
INSERT INTO authors(id, name) VALUES(45, 'Sheena R.');
- Start with specified number.
CREATE TABLE authors (
id INT GENERATED ALWAYS AS IDENTITY PRIMARY KEY (START WITH 10000),
name VARCHAR(255)
);
Current Date function
Get current date:CURRENT_DATE
Get current timestamp (date and time):
CURRENT_TIMESTAMP
Date format and insert row example
Uses ISO8601 format:
Date: YYYY-MM-DD
Timestamp: YYYY-MM-DD HH:MM:SS.SSSS
Example:
Date: YYYY-MM-DD
Timestamp: YYYY-MM-DD HH:MM:SS.SSSS
Example:
INSERT INTO articles(title, author, content, published, created_at, updated_at) VALUES('Learn Postgres', 'Joey R.', 'Blah blah.', true, CURRENT_TIMESTAMP, CURRENT_TIMESTAMP);
Postgres Identifiers (table names, column names, etc.)
- Ref: Postgresql:Identifiers
- Keywords and identifiers not in double quotes are case insensitive. Internally, unquoted uppercase letters are down-cased. From a convenience perspective it makes sense to just use lower case letters for identifiers.
MySQL
Manual: dev.mysql.com/doc/refman/en
MySQL is a free, open-source relational database management system.More details
- Pronounced "My S-Q-L"
- A relational database management system (RMDB) is a software program that defined, manipulates, retrieves, and manages data in a database.
- Uses the SQL query language.
- Programmed in C and C++.
- Cross-platform support: Can be installed on Linux, MacOS, Windows.
- MySQL is owned by Oracle since 2010.
- There are two MySQL editions:
- The free open source MySQL Community Server.
- A proprietary subscription based Enterprise Server.
- MySQL was also forked into a separate open source project in 2009 called MariaDB. It is not owned by Oracle but is compatible with MySQL.
Install/Upgrade
Check if installed (version, location):
mysql --version Returns version number.
which mysql Returns the executable file path.
Download the Database: dev.mysql.com/downloads/mysql
Optionally download MySQL's official GUI: dev.mysql.com/downloads/workbench
Start/Stop MySQL Server (Mac)
Start: Apple menu > System Preferences > MySQL > Start MySQL Server
Stop: Apple menu > System Preferences > MySQL > Stop MySQL Server
Always Running: Apple menu > System Preferences > MySQL > Check: Start MySQL when your computer starts up.
mysql Command-Line Client
The MySQL database installation comes with a simple SQL Shell called mysql.
Official tutorial: dev.mysql.com: Tutorial
help; Returns list of shell commands.
Syntax:
- Statements are case insensitive. By convention SQL statements are shown in caps.
- Statements must end in a semicolon. Exceptions: QUIT, USE, SOURCE
- Strings can be in single or double quotes.
Open/Close Shell:
mysql -u root -p Connect to the mysql shell.
Ctrl+C | \c Exit a multi-line statement.-u flag is for username (change value to your username if not root).-p flag prompts for your password.dbname Optionally append a database name to the statement to open the shell to it.
Ctrl+D | QUIT | \q Disconnect from the mysql shell.
Databases:
SHOW DATABASES; List all databases
CREATE DATABASE dbname; Create a database.
USE dbname Access a specific database.
SELECT DATABASE(); Shows what database you are currently in.
SOURCE /path/to/dbfilename.sql Import an existing MySQL database.
On Mac your dbs are stored in: /usr/local/mysql-version/data/
Tables:
SHOW TABLES; List all tables in the database.
CREATE TABLE articles (title VARCHAR(100), createdAt DATE); Create a table.
ALTER TABLE articles (title VARCHAR(200)); Alter a table.
DESCRIBE articles; Show a table's schema.
SHOW CREATE TABLE articles; Show the create table statement for the specified table.
SHOW INDEX FROM articles; Show any indexes on a table.
Rows: Use standard SQL statements:
INSERT INTO articles VALUES ('Learn SQL', '2020-02-20');
Populate a database table with a text file.
The text file: someData.txt
- One line per database row.
- Separate columns using tabs. Put columns in the order they appear in the database.
LOAD DATA LOCAL INFILE '/path/someData.txt' INTO TABLE tablename;
MySQL Workbench (GUI Interface)
Manual: dev.mysql.com/doc/workbench/en
Launch app: On mac launch it from Launchpad or pin it to your Dock.
View existing or create new DB connections: Database menu > Manage Connections
Connect to a database: Database menu > Connect to Database > Select the connection.
Create/Edit a connection
Field with defaults (if any) are:
Connection Name: Give it a name such as the db name for a db-specific connection.
Hostname: 127.0.0.1 This is the same as localhost
Port: 3306
Username: root
Password: You can store it in your keychain on MacOS or enter it each time you connect.
Default Schema: To automatically open a specific database, enter the db name here.
The SQL Editor
Use the SQL Editor tab to enter SQL statements, create new databases, new tables, etc.
Data Types (Most common)
- Ref (full list): dev.mysql.com/doc/refman/en/data-types
- When creating a table each column must include the name and datatype:
CREATE TABLE tablename (fieldname datatype, fieldname datatype);
Character string data types
Ref: Docs:string-types- CHAR(n) Fixed length (max: 255). Values less than n length are padded with spaces.
- VARCHAR(n) Variable length up to n.
- TEXT Strings above 255 characters. Also: tinytext, mediumtext, longtext.
- BLOB Stores binary data (e.g., an image file). Also: tinyblob, mediumblog, longblog.
Number data types
Ref: Docs:numeric-types- INT | INTEGER Integers (no decimal points). Also: smallint, mediumint, bigint.
- INT(5) Specify percision (number of digits). Allowed range: -99999 to 99999.
- DECIMAL | NUMERIC Allows decimal points.
- DECIMAL(5,2) Specify percision (5 total digits), and scale (2 digits after the decimal point). Allowed range: -999.99 to 999.99.
- BOOLEAN Stores 0 for false, 1 for true.
Date/time data types
Ref: Docs:date-and-time-types- YEAR YYYY
- DATE 'YYYY-MM-DD'
- TIME 'hh:mm:ss'
- DATETIME 'YYYY-MM-DD hh:mm:ss[.fraction]'. Fractions of a second are optional.
- TIMESTAMP 'YYYY-MM-DD hh:mm:ss[.fraction]'
- Unlike Datetime, Timestamp values are converted from the current time zone to UTC for storage, and back to current time zone on retrieval.
- Current time zone defaults to the server's time.
Auto-incrementing Row ID
id INT NOT NULL AUTO_INCREMENT PRIMARY KEY
Current Date function
Get current date:CURRENT_DATE()
Get current timestamp (date and time):
CURRENT_TIMESTAMP()
Date format and insert row example
Uses ISO8601 format:
Date: "YYYY-MM-DD" (string) or YYYYMMDD (numeric).
Timestamp: "YYYY-MM-DD HH-MM-SS" (string) or YYYYMMDDHHMMSS.uuuuuu (numeric).
Example:
Date: "YYYY-MM-DD" (string) or YYYYMMDD (numeric).
Timestamp: "YYYY-MM-DD HH-MM-SS" (string) or YYYYMMDDHHMMSS.uuuuuu (numeric).
Example:
INSERT INTO articles(title, author, content, published, created_at, updated_at) VALUES('Learn Postgres', 'Joey R.', 'Blah blah.', true, CURRENT_DATE(), CURRENT_DATE());
Sqlite
Install/Upgrade
Check if installed (version, location):
sqlite3 --version Returns version number.
which sqlite3 Returns the executable file path.
Download Program: Sqlite.org/index.html
Sqlite Shell
Ref: Sqlite:cli
.help List all shell commands.
Open/close shell:
sqlite3 Open sqlite shell from any directory. Opens to an empty in-memory database.
Ctrl+D | .quit | .exit Exit the shell.
Create new database:
.save db-name Save the in-memory database to the current directory.
Open Existing Database:
.open db-filename Opens existing database file. Use path if not in same directory.
Get DB info:
.tables Returns list of tables.
pragma table_info('tablename'); Returns one row per column with:
column_name | Data type | Can be null? (0/1) | Default value | Is primary key? (0/1)
Execute SQL Statements: Enter SQL statements.
SELECT rowid, * FROM tablename; Query table for rowid and all columns.
GUI Interface
DB Browser for Sqlite: sqlitebrowser.org
Download: sqlitebrowser.org/dl
Modify Tables
Database Structure tab > Tables: Select table > Modify tableRemove or reorder fields
You can add a field in SQLite using SQL but you can't remove or reorder fields.
The GUI does a complex transaction behind the scenes to accomplish this.Database Structure tab > Tables: Select table > Modify table button > Select Field > Remove/MoveUp/MoveDown
Data Types
- Sqlite uses dynamic typing. Columns are assigned data type affinities but will accept values of any data type. Values themselves have a data class.
Static vs dynamic typing
- Dynamic Typing: Sqlite uses dynamic typing meaning a value's data type is determined by its syntax.
- The value "7" is a text type because it's in quotes and 7.0 is a real type because it has a decimal, even if they are saved to a column with data type of INTEGER.
- Static Typing: Other SQL database engines use static typing, meaning the data type of a value is determined by the column's data type. If the value doesn't match the column's data type it will be converted.
- Any value saved to a column defined with data type INTEGER will be converted to an integer (if possible). So "7" and 7.0 would both be converted to integer 7.
- Any value saved to a column defined with data type
A storage class is more general than a datatype. The INTEGER storage class, for example, includes 6 different integer datatypes of different lengths. This makes a difference on disk. But as soon as INTEGER values are read off of disk and into memory for processing, they are converted to the most general datatype (8-byte signed integer). And so for the most part, "storage class" is indistinguishable from "datatype" and the two terms can be used interchangeably.
The type affinity of a column is the recommended type for data stored in that column. The important idea here is that the type is recommended, not required. Any column can still store any type of data. It is just that some columns, given the choice, will prefer to use one storage class over another. The preferred storage class for a column is called its "affinity".
Storage Class (5 storage classes)
Datatype ≈ Storage Class. Values are assigned one of the following storage classes:- NULL: For a NULL value.
- INTEGER: Whole numbers (positive or negative). No decimals. Ex: -3, 0, 200.
- REAL: Number with decimal points (floating points). Ex: -3.1, 0.00001, 200.0.
- TEXT: Value with quotes: 'Hello', '7', 'true'.
- BLOB: Blob of data, stored exactly as input. Used with binary data like images.
Datatype vs Storage Class
Storage class is a superset of datatypes. For instance, the INTEGER storage class includes 6 datatypes for integers of different lengths. These different datatypes are stored differently on disk to maximize efficiency, but when read they are converted to the INTEGER datatype of the storage class. So in Sqlite, datatype and storage class can be though of as the same thing (and the terms used interchangeably).
Type Affinity (5 type affinities)
Type affinity is the recommended datatype assigned to a column when creating a table.
Based on the column's type affinity Sqlite will save a value as is or convert its storage class.
- TEXT: Stores values as null, text, or blob storage classes.
- Numeric values are converted to text: 7 -> '7', 7.1 -> '7.1'
- NUMERIC: Stores values in all 5 storage classes, but will convert quoted numbers.
- '7' -> 7, '7.1' -> 7.1.
- INTEGER: Essentially same as NUMERIC. Difference relates to CAST expressions.
- REAL: Like NUMERIC but converts integer values to floating point. Ex: 7 -> 7.0.
- BLOB: Stores values in all 5 storage classes. Doesn't convert storage classes.
For compatibility, Sqlite will map any datatype name to type affinities using these rules:
- BLOB: accepts BLOB and unspecified.
- TEXT: accepts any name that contains TEXT, CHAR, or CLOB.
- Ex: VARCHAR(255). The 255 character limit is ignored.
- INTEGER: accepts any name that contains INT.
- REAL: accepts any name that contains REAL, FLOA, or DOUB.
- NUMERIC: accepts any name not covered above.
Data type substitutions:
Booleans: Store as INTEGER. Keyword TRUE is stored as 1, FALSE as 0.
Dates formatted as:
Dates formatted as:
- ISO8601 Date Strings ("YYYY-MM-DD HH:MM:SS.SSS") store as TEXT.
- Unix timestamps (number of seconds since 1970-01-01) store as INTEGER.
- Set current timestamp as column default value:
created_at TEXT DEFAULT CURRENT_TIMESTAMP
Example create books table
Create a table named books with columns:
- id - Auto-incrementing integer row id column.
- title - Length is variable up to 255 characters.
- author - Length is variable up to 100 characters.
- cover - cover image - binary image file.
- isbn - 13 number characters uniquely identifying a book.
- description - no specified character limit.
- quantity - integer value.
- price - in format xxx.xx so 5 total numbers including two after the decimal point
- on_sale - boolean.
- published_date - date without time.
CREATE TABLE books (
id INTEGER PRIMARY KEY, title TEXT, author TEXT, cover BLOB,
isbn TEXT, description TEXT, quantity INTEGER, price REAL,
on_sale INTEGER,
published_date TEXT
);
Auto-incrementing Row ID
Rowid: Sqlite automatically creates an auto-incrementing column called rowid.
To use a different name such as "id", add column
To use a different name such as "id", add column
- Rowid: Sqlite autogenerates a special rowid column when you create a table. A sequential rowid INTEGER (1, 2, 3, etc.) is autogenerated for every row.
- Alias Rowid: Adding your own column name such as "id" of type INTEGER and PRIMARY KEY will automatically make it an alias for rowid.
id INTEGER PRIMARY KEY
- To create a table w/o a rowid:
CREATE TABLE books (...) WITHOUT ROWID;
Examples and reasons you should alias rowid
Examples:
Why create an alias rowid? Sqlite recommends creating an alias rowid column. The rowid number can change if you use the vacuum command for optimizing the database, but the alias id will not change. Also you cannot create foreign keys and joins on rowid. Use the alias rowid column instead.
- Primary Key Column Constraint: Isbn number (Int'l Standard Book Number):
CREATE TABLE books (id INTEGER PRIMARY KEY, title TEXT, summary TEXT, isbn TEXT UNIQUE, cover BLOB, price REAL, available BOOLEAN, published_on DATETIME);
- Table without a rowid:
CREATE TABLE states (name TEXT, abbreviation TEXT PRIMARY KEY) WITHOUT ROWID;
Why create an alias rowid? Sqlite recommends creating an alias rowid column. The rowid number can change if you use the vacuum command for optimizing the database, but the alias id will not change. Also you cannot create foreign keys and joins on rowid. Use the alias rowid column instead.
Current Date function
Get current date: longhanddate('now')
| shorthand date()
Get current date and time: longhand
datetime('now')
| shorthand: datetime()
Format and insert row example
Uses ISO8601 format:
Date: YYYY-MM-DD
Date and time: YYYY-MM-DD HH:MM:SS
Date: YYYY-MM-DD
Date and time: YYYY-MM-DD HH:MM:SS
INSERT INTO articles(title, author, content, published, created_at, updated_at)
VALUES('Learn Sqlite', 'Joey R.', 'Blah blah.', true, datetime(), datetime());
TablesGo to video for this category
Create Table
CREATE TABLE [IF NOT EXISTS] [schema_name.]table_name ( column_name1 DATA_TYPE [DEFAULT value] [column_constraints], column_name2 DATA_TYPE [DEFAULT value] [column_constraints], table_constraints ) [WITHOUT ROWID];
schema_name: Optionally add the database name, or TEMP to put table in a temporary db.
IF NOT EXISTS: Only create the table if it doesn't already exist.
Column definitions: name, data type, [default value, constraints].
IF NOT EXISTS: Only create the table if it doesn't already exist.
Column definitions: name, data type, [default value, constraints].
Examples
- Create books table:
CREATE TABLE books (title TEXT, description TEXT, isbn INTEGER, cover BLOB, price NUMERIC, available BOOLEAN, published_date DATETIME);
- Optionally include the db name before the table name:
CREATE TABLE mydb.books (title TEXT, description TEXT, isbn INTEGER, cover BLOB, price NUMERIC, available BOOLEAN, published_date DATETIME);
- Create table only if it doesn't already exist:
CREATE TABLE books IF NOT EXISTS (title TEXT, description TEXT, isbn INTEGER, cover BLOB, price NUMERIC, available BOOLEAN, published_date DATETIME);
Optional Default Values:
column_name DATA_TYPE DEFAULT value
Optional Constraints:
Constraints: PRIMARY KEY, UNIQUE, NOT NULL, CHECK, FOREIGN KEY.- NOT NULL: Field must contain a value.
column_name DATA_TYPE NOT NULL
- UNIQUE: Cannot be another row with the same value for the field.
column_name DATA_TYPE UNIQUE
- CHECK(expression): Add a custom constraint
column_name DATA_TYPE CHECK(expression)
- Ex:
CHECK(length(title) <= 200)
CHECK(price >= 0)
Example
Add the following default values and column constraints to the books table:
- Title must be present and not more than 200 characters long.
- Isbn number must be unique.
- Price must be greater than or equal to 0.
- Set default value for the available field to TRUE.
- Set default for created_at to the CURRENT_TIMESTAMP
CREATE TABLE books (title TEXT NOT NULL CHECK(length(title) <= 200), description TEXT, isbn INTEGER UNIQUE, cover BLOB, price NUMERIC CHECK(price >= 0), available BOOLEAN DEFAULT TRUE, published_date DATETIME, created_at DATETIME DEFAULT CURRENT_TIMESTAMP);
Primary Key
Primary key definition
Primary Key: a column, or combination of columns, in a table designated to uniquely identify the table record. The value must be unique and must not be null. There can only be one PK.
The primary key may be a field already present in the data model (e.g., ISBN number for books), or a field can be created to be the primary key (e.g., an id field).Column Constraint (single column primary key)
column_name TYPE PRIMARY KEY
- Auto-incrementing: Commonly the primary key will be an auto-incrementing "id" field.
Single column auto-incrementing primary key example
- Primary key column constraint auto-incrementing: ID as primary key:
CREATE TABLE books (id INT GENERATED ALWAYS AS IDENTITY PRIMARY KEY, isbn CHAR(13), title VARCHAR(255), description TEXT);
MySQL:
Insert row:
CREATE TABLE books (id INT NOT NULL AUTO_INCREMENT PRIMARY KEY, isbn CHAR(13), title VARCHAR(255), description TEXT);Sqlite:
Sqlite: CREATE TABLE books (id INTEGER PRIMARY KEY, isbn TEXT, title TEXT, description TEXT);
Insert row:
INSERT INTO books(isbn, title, description)
VALUES('1234567891011', 'Learn SQL', 'Blah blah.');
- Not auto-incrementing: some other unique field value. Can be a number or text data type.
Single column primary key example (not auto-incrementing)
- Primary key column constraint not auto-incrementing: Isbn number (Int'l Standard Book Number) as primary key.
CREATE TABLE books (isbn CHAR(13) NOT NULL UNIQUE PRIMARY KEY, title VARCHAR(255), description TEXT);
Sqlite:
CREATE TABLE books (isbn TEXT NOT NULL UNIQUE PRIMARY KEY, title TEXT, description TEXT);
Insert row:
INSERT INTO books(isbn, title, description)
VALUES('1234567891011', 'Learn SQL', 'Blah blah.');
Table Constraint (multicolumn primary key)
CREATE TABLE table_name (..., PRIMARY KEY(column_name, column_name));
Multi-column primary key (table constraint) example
- Primary Key Table Constraint: Multicolumn (aka composite) primary key:
CREATE TABLE states (state_name VARCHAR(100), state_abbreviation VARCHAR(5), country_name VARCHAR(100), country_code CHAR(3), PRIMARY KEY(state_abbreviation, country_code));
Sqlite:CREATE TABLE states (state_name TEXT, state_abbreviation TEXT, country_name TEXT, country_code TEXT, PRIMARY KEY(state_abbreviation, country_code));
Insert row:
INSERT INTO states(state_name, state_abbreviation, country_name, country_code)
VALUES('California', 'CA', 'United States of America', 'USA');
Index
An index is an additional data structure that speeds up queries at the cost of additional writes and storage space. The UNIQUE keyword enforces uniqueness. There is no consensus on naming convention.
Multicolumn index:
CREATE [UNIQUE] INDEX index_name
ON table_name(column_name);
Multicolumn index:
CREATE INDEX index_name
ON table_name(column1, column2);
Remove Index:
DROP INDEX [IF EXISTS] index_name;
Examples
- Create an index on the ISBN number:
CREATE INDEX books_index_isbn
ON books(isbn);
- Enforce uniqueness:
CREATE UNIQUE INDEX books_index_isbn
ON books(isbn);
- Multicolumn index:
CREATE INDEX addresses_index_country_postal
ON addresses(country_code, postal_code);
- Remove Index:
DROP INDEX books_index_isbn;
Foreign Key
One-to-many association: Use foreign key to enforce the relationship.
- Parent table: A row can be associated with zero, one, or multiple rows in child table. Child rows can only reference a named column (not Sqlite's rowid).
CREATE TABLE parent_tablename (id INTEGER PRIMARY KEY, column_name TYPE, ...);
- Child table: Contains column with foreign key constraint referencing one id row of parent table.
CREATE TABLE child_tablename (
column_name TYPE,
parent_tablename_id INTEGER NOT NULL,
FOREIGN KEY (parent_tablename_id) REFERENCES parent_tablename (id)
);
Example and benefit of using foreign keys
Example:
Insert rows:
Why use Foreign Keys:
- Parent Table:
Postgres: CREATE TABLE authors (id INT GENERATED ALWAYS AS IDENTITY PRIMARY KEY, name TEXT); MySQL: CREATE TABLE authors (id INT NOT NULL AUTO_INCREMENT PRIMARY KEY, name TEXT); Sqlite: CREATE TABLE authors (id INTEGER PRIMARY KEY, name TEXT);
- Child Table:
CREATE TABLE books (
title TEXT,
author_id INTEGER NOT NULL,
FOREIGN KEY (author_id) REFERENCES authors (id)
);
Insert rows:
INSERT INTO authors(name) VALUES('Joey R.'); INSERT INTO books(title, author_id) VALUES('Learn SQL', 1);
Why use Foreign Keys:
- Prevents adding rows in child table that don't correspond with row in parent table.
- To prevent orphaned rows in child table if a row in the parent table is deleted.
Foreign Key Constraints: On Delete
To prevent leaving orphaned rows in the child table when a parent row is deleted, add an ON DELETE foreign key constraint.
CREATE TABLE child_tablename (
column_name TYPE,
parent_tablename_id INTEGER NOT NULL,
FOREIGN KEY (parent_tablename_id)
REFERENCES parent_tablename (id)
ON DELETE action
);
ON DELETE Actions:
- NO ACTION Default. Prevents parent row from being deleted if there are associated child rows because foreign keys require a valid associated row or be NULL.
- RESTRICT prevents parent row from being deleted if there are associated child rows. Same result as NO ACTION.
- CASCADE when a parent row is deleted, all associated rows in the child table will automatically be deleted.
- SET NULL when parent row is deleted, the child table's foreign key column of associated rows is set to NULL.
- SET DEFAULT when parent row is deleted, the child table's foreign key column of associated rows is set to the DEFAULT value specified in the column definition.
Example
- Parent Table:
Postgres: CREATE TABLE authors (id INT GENERATED ALWAYS AS IDENTITY PRIMARY KEY, name VARCHAR(100); MySQL: CREATE TABLE authors (id INT NOT NULL AUTO_INCREMENT PRIMARY KEY, name VARCHAR(100)); Sqlite: CREATE TABLE authors (id INTEGER PRIMARY KEY, name TEXT);
- Child Table: Delete child rows when associated parent row is deleted:
CREATE TABLE books ( title TEXT, author_id INTEGER NOT NULL, FOREIGN KEY (author_id) REFERENCES authors (id) ON DELETE CASCADE );
Alter Table
Rename table:
ALTER TABLE table_name RENAME TO new_name;
Add column:
ALTER TABLE table_name ADD column_name TEXT;Drop column:
ALTER TABLE table_name DROP COLUMN column_name;Rename column:
ALTER TABLE table_name RENAME COLUMN old_name TO new_name;Modify column data type:
ALTER TABLE table_name MODIFY COLUMN column_name datatype;Modify column, add NOT NULL (same process for adding UNIQUE, DEFAULT, CHECK)
ALTER TABLE table_name MODIFY column_name datatype NOT NULL;Sqlite: can't drop or alter columns directly. Either create a new table with the removed or modified column and transfer the data, or use a GUI sqlite database program to do it for you (See Sqlite GUI interface section).
Examples
Rename table:
Add column: ALTER TABLE books RENAME TO articles;
ALTER TABLE books ADD author TEXT;
Drop column:
ALTER TABLE books DROP COLUMN author;
Rename column:
ALTER TABLE books RENAME COLUMN published_on TO published_date;
Modify column datatype:
ALTER TABLE books MODIFY COLUMN published_date timestamp;
Modify column, add NOT NULL:
ALTER TABLE books MODIFY COLUMN published_date timestamp NOT NULL;
Drop Table
DROP TABLE [IF EXISTS] tablename; Deletes table and all its data.
Query DataGo to video for this category
Query all or specific columns
Select all columns and rows from a table:SELECT * FROM table_name;
Select specific columns:
SELECT column1, column2, column3 FROM table_name;
Alias a column name:
SELECT column1, column2 AS other_name FROM table_name;
Eliminate duplicates with DISTINCT:
SELECT DISTINCT column_name FROM table_name;
Examples
- Select all rows from a table:
SELECT * FROM books;
- Select specific columns:
SELECT isbn, title, published_on FROM books;
- Alias a column name:
SELECT isbn, title, published_on AS published FROM books;
- Eliminate duplicates with DISTINCT:
SELECT DISTINCT author FROM books;
Add Conditions with the WHERE clause
Select specific row id:
SELECT * FROM table_name WHERE id = x;
Select rows that meet a WHERE clause condition:
SELECT * FROM table_name
WHERE condition;
Select rows that meet multiple WHERE clause conditions:
SELECT * FROM table_name
WHERE condition1 AND condition2;
Examples
- Select specific rowid:
SELECT * FROM books WHERE id = 3;
- Select rows that meet a WHERE clause condition:
SELECT * FROM books
WHERE available = TRUE;
- Select rows that meet multiple WHERE clause conditions:
SELECT * FROM books
WHERE available = TRUE AND price > 9.99;
ORDER BY
SELECT * FROM table_nameOrder by multiple columns: order by first column, then second.
ORDER BY column_name [ASC | DESC];
SELECT * FROM table_name
ORDER BY column_name [ASC | DESC], column_name [ASC | DESC];
Example
- Order by price, in ascending order (lowest to highest):
SELECT * FROM books
ORDER BY price;
- Since ASC is the default, you can leave it out.
- Order by price, in descending order (highest to lowest):
SELECT * FROM books
ORDER BY price DESC;
- Order by available (on top) and price (lowest to highest):
SELECT * FROM books
ORDER BY available DESC, price ASC;
LIMIT
Use LIMIT with ORDER BY otherwise the returned rows will be random.
SELECT * FROM table_name
ORDER BY column_name
LIMIT x;
With Offset (e.g., to get rows 11-20, offset 10):
SELECT * FROM table_name ORDER BY column_name LIMIT x OFFSET y;
Examples
SELECT * FROM books
ORDER BY price
LIMIT 10;
- With Offset (e.g., to get rows 11-20, offset 10):
SELECT * FROM books ORDER BY price LIMIT 10 OFFSET 10;
Aggregation (Count, Avg, Min/Max, Sum)
COUNT:
SELECT COUNT(*) FROM table_name;
Count rows with non NULL values in a column:
SELECT COUNT(column_name) FROM table_name;
With condition:
SELECT COUNT(*) FROM table_name
WHERE condition;
Examples
- Count all rows in table:
SELECT COUNT(*) FROM books;
- Count only rows with an ISBN value:
SELECT COUNT(isbn) FROM books;
- With condition:
SELECT COUNT(*) FROM books
WHERE available = TRUE;
SELECT AVG(column_name) FROM table_name;
MIN - Smallest:
SELECT MIN(column_name) FROM table_name;
MAX - Largest:
SELECT MAX(column_name) FROM table_name;
SUM Column values:
SELECT SUM(column_name) FROM table_name;
Examples
- Average price:
SELECT AVG(price) FROM books;
- Lowest price:
SELECT MIN(price) FROM books;
- Highest price:
SELECT MAX(price) FROM books;
- Sum column values:
SELECT SUM(quantity) FROM books;
IN
The IN operator compares a value to a list of specified values.
Returns true if the value is in the list, false otherwise.
Returns true if the value is in the list, false otherwise.
SELECT * FROM table_name
WHERE column_name IN (val1, val2, val3, ...);
Example
Get books where the author is either: Joey R., Linda R., or Johnny R.
SELECT * FROM books
WHERE author IN ('Joey R.', 'Linda R.', 'Johnny R.');
LIKE
The LIKE operator in the WHERE clause allows you to match a pattern.
% before a pattern: any characters can come before it.
% after a pattern: any characters can come after it.
% before a pattern: any characters can come before it.
% after a pattern: any characters can come after it.
SELECT * FROM table_nameSearching case insensitive depends on the database:
WHERE column_name LIKE '[%]pattern[%]';
- Postgres:
ILIKE
- MySQL: downcase the column first
LOWER(column_name) LIKE '[%]pattern[%]'
- Sqlite:
LIKE
is case insensitive by default.
Examples
Case sensitive (Postgres and MySQL)
Case insensitive:
Postgres:
MySQL:
Sqlite:
SELECT * FROM books
WHERE title LIKE '%database%';
Case insensitive:
Postgres:
SELECT * FROM books WHERE title ILIKE '%database%';
MySQL:
SELECT * FROM books WHERE LOWER(title) LIKE '%database%';
Sqlite:
SELECT * FROM books WHERE title LIKE '%database%';
Modify DataGo to video for this category
Insert Rows
Insert one value for each column in order:
INSERT INTO table_name VALUES('val1', 'val2', val3);
Or specify the column names:
INSERT INTO table_name(column1, column2, column3)
VALUES('val1', 'val2', val3);
- Put quotes around TEXT, no quotes on numeric.
- For multiple rows, separate with commas:
INSERT INTO table_name(column1, column2, column3) VALUES('val1', 'val2', val3), ('val1', 'val2', val3), ('val1', 'val2', val3);
Example
INSERT INTO books(title, description, isbn, price, available, published_date)
VALUES('Learn Databases', 'Lorem ipsum.', 1234567891011, 19.99, TRUE, '2024-01-01 00:00:00');
Update Rows
Update one column, all rows:
UPDATE table_name SET column_name = value;
Update multiple columns, all rows:
UPDATE table_name SET col1 = val, col2 = val;Update specific row id:
UPDATE table_name SET column_name = value
WHERE id = x;
Update rows that meet specific WHERE clause conditions:
UPDATE table_name SET column_name = value
WHERE condition1 AND condition2;
Examples
- Update all books. Set price to 9.99:
UPDATE books SET price = 9.99;
- Update all available books:
UPDATE books SET price = 9.99
WHERE available = true;
- Update all available books priced above 9.99:
UPDATE books SET price = 9.99
WHERE available = 1 AND price > 9.99;
- Update one column of specific book found by id:
UPDATE books SET price = 4.99 WHERE id = 1;
- Update multiple columns of specific book found by id:
UPDATE books SET price = 4.99, available = TRUE WHERE id = 1;
Delete Rows
Delete all rows:
DELETE FROM table_name;
Delete specific row id:
DELETE FROM table_name
WHERE id = x;
Delete rows that meet specific WHERE clause conditions:
DELETE FROM table_name
WHERE conditions;
Examples
- Delete all rows:
DELETE FROM books;
- Delete specific row id:
DELETE FROM books
WHERE id = 3;
- Delete rows that meet specific WHERE clause conditions:
DELETE FROM books
WHERE available = FALSE AND price = 0;
JoinsGo to video for this category
Joins are data queries on two (or more) tables.
Inner join using a condition
- You can join two associated tables using a WHERE clause condition.
- Prefixing the table name is optional unless the same column name is in both tables.
SELECT table1.column_name, table2.column_name
FROM table1, table2
WHERE table1.associating_column = table2.identifying_column;
Examples
- Query books table columns and name column from associated authors table:
SELECT title, price, name AS author
FROM books, authors
WHERE books.author_id = authors.id;
- With table name prefixed, ordered by title:
SELECT books.title, books.price, authors.name AS author
FROM books, authors
WHERE books.author_id = authors.id
ORDER BY books.title;
Inner Join
- INNER JOIN joins two associated tables ON the specified columns.
- Only rows with a valid association between the two tables are returned.
- The INNER keyword is optional because it is the default join type in SQL.
SELECT column1, column2, ...
FROM table1
[INNER] JOIN table2
ON table1.associating_column = table2.identifying_column;
Example
- Query books table columns and name column from associated authors table:
SELECT title, price, name AS author
FROM books
INNER JOIN authors
ON books.author_id = authors.id;
- Remove the INNER keyword since it is the default, and order by title:
SELECT title, price, name AS author
FROM books
JOIN authors
ON books.author_id = authors.id
ORDER BY title;
OUTER JOINS
- Include LEFT OUTER JOIN, RIGHT OUTER JOIN, FULL OUTER JOIN.
- Sqlite only supports LEFT OUTER JOIN.
LEFT OUTER JOIN / LEFT JOIN
- All rows from the first (left) table are returned. Rows without a valid associated row in the joined table show NULL in associate column(s).
- The OUTER keyword is optional.
SELECT column1, column2, ...
FROM left_table
LEFT [OUTER] JOIN right_table
ON left_table.associating_column = right_table.identifying_column;
Example
- Query all books and get author name where present from associated table:
SELECT title, price, name AS author
FROM books
LEFT OUTER JOIN authors
ON books.author_id = authors.id;
- Remove OUTER keyword, and order by title:
SELECT title, price, name AS author
FROM books
LEFT JOIN authors
ON books.author_id = authors.id
ORDER BY title;