SQL

**SQL**（/ˈɛs kjuː ˈɛl/ 或 /ˈsiːkwəl/，**Structured Query Language**，**結構化查詢語言**）是一種特定目的程式語言，用於管理關聯式資料庫管理系統（RDBMS），或在關係流資料管理系統（RDSMS）中進行流處理。

SQL 基於關係代數和元組關係演算，包括一個資料定義語言和資料操縱語言。SQL 的範圍包括資料插入、查詢、更新和刪除，資料庫模式建立和修改，以及資料存取控制。儘管 SQL 經常被描述為，而且很大程度上是一種聲明式編程（4GL），但是其也含有程序式編程的元素。

SQL 是對埃德加・科德的關係模型的第一個商業化語言實現，這一模型在其 1970 年的一篇具有影響力的論文《一個對於大型共享型資料庫的關係模型》中被描述。儘管 SQL 並非完全按照科德的關係模型設計，但其依然成為最為廣泛運用的資料庫語言。

SQL 在 1986 年成為美國國家標準學會（ANSI）的一項標準，在 1987 年成為國際標準化組織（ISO）標準。此後，這一標準經過了一系列的增訂，加入了大量新特性。雖然有這一標準的存在，但大部分的 SQL 代碼在不同的資料庫系統中並不具有完全的跨平台性。

## 歷史

在 1970 年代初，由 IBM 公司 San Jose,California 研究實驗室（IBM San Jose Research Laboratory）的埃德加・科德發表將資料組成表格的應用原則（Codd's Relational Algebra）。1974 年，同一實驗室的 D.D.Chamberlin 和 R.F. Boyce 對 Codd's Relational Algebra 在研製關聯式資料庫管理系統 System R 中，研製出一套規範語言 -SEQUEL（Structured English Query Language），並在 1976 年 11 月的 IBM Journal of R&D 上公布新版本的 SQL（叫 SEQUEL/2）。1980 年改名為 SQL。

1979 年甲骨文公司首先提供商用的 SQL，IBM 公司在 DB2 和 SQL/DS 資料庫系統中也實現了 SQL。

1986 年 10 月，美國 ANSI 採用 SQL 作為關聯式資料庫管理系統的標準語言（ANSI X3. 135-1986），後為國際標準化組織（ISO）採納為國際標準。

1989 年，美國 ANSI 採納在 ANSI X3.135-1989 報告中定義的關聯式資料庫管理系統的 SQL 標準語言，稱為 ANSI SQL 89，該標準替代 ANSI X3.135-1986 版本。該標準為下列組織所採納：

* 國際標準化組織（ISO），為 ISO 9075-1989 報告「Database Language SQL With Integrity Enhancement」
* 美國聯邦政府，發布在 The Federal Information Processing Standard Publication(FIPS PUB)127

目前，所有主要的關聯式資料庫管理系統支援某些形式的 SQL，大部分資料庫至少遵守 ANSI SQL89 標準。

ANSI SQL92 標準在交叉連接（cross join）和內部連接之上，新增加了外部連接，並支援在 FROM 子句中寫連接表達式。支援集合的並運算、交運算。支援 Case (SQL) 表達式。支援 CHECK 約束。建立臨時表。支援 cursor。支援事務隔離。

## 語法

SQL 語言分成了幾種要素，包括：

* 子句，是語句和查詢的組成成分。（在某些情況下，這些都是可選的。）
* 表達式，可以產生任何純量值，或由列和行組成的資料庫表
* 謂詞，給需要評估的 SQL 三值邏輯（3VL）（true/false/unknown）或布林真值指定條件，並限制語句和查詢的效果，或改變程式流程。
* 查詢，基於特定條件檢索資料。這是 _SQL_ 的一個重要組成部分。
* 語句，可以持久地影響綱要和資料，也可以控制資料庫事務、程式流程、連接、對談或診斷。
  * SQL 語句也包括分號（";"）語句終結符。儘管並不是每個平台都必需，但它是作為 SQL 語法的標準部分定義的。
* 無意義的空白在 SQL 語句和查詢中一般會被忽略，更容易格式化 SQL 代碼便於閱讀。

## 語言特點

SQL 是進階的非過程化編程語言，它允許使用者在高層資料結構上工作。它不要求使用者指定對資料的存放方法，也不需要使用者了解其具體的資料存放方式。而它的介面，能使具有底層結構完全不同的資料庫系統和不同資料庫之間，使用相同的 SQL 作為資料的輸入與管理。它以記錄專案〔records〕的合集（set）〔項集，record set〕作為操縱物件，所有 SQL 語句接受項集作為輸入，回送出的項集作為輸出，這種項集特性允許一條 SQL 語句的輸出作為另一條 SQL 語句的輸入，所以 SQL 語句可以巢狀，這使它擁有極大的靈活性和強大的功能。在多數情況下，在其他程式語言中需要用一大段程式才可實踐的一個單獨事件，而其在 SQL 上只需要一個語句就可以被表達出來。這也意味著用 SQL 可以寫出非常複雜的語句，在不特別考慮效能下。

SQL 同時也是資料庫檔案格式的副檔名。

SQL 包含四個部分：

* 資料定義語言
* 資料操縱語言
* 資料控制語言
* 事務控制語言

### SQL 函式

## 互操作性和標準化

供應商之間的 SQL 實現不相容，不一定完全遵循標準。各種資料庫的 SQL 方言通常不可移植，特別是在日期時間語法、字串連接、`NULL`、比較的大小寫敏感方面。只有 PostgreSQL 與 Mimer SQL 努力遵從標準。

### 標準化歷史

SQL 在 1986 年被 ANSI 標準化，1987 年被 ISO 標準化。由 _ISO/IEC JTC 1, Information technology, Subcommittee SC 32, Data management and interchange_ 維護。標準名稱通常為如下模式：_ISO/IEC 9075-n:yyyy Part n: title_。

### 當前標準

該標準通常用以下模式表示：**ISO/IEC 9075-n：yyyy 第 n 部分：標題**，或者簡稱為 **ISO/IEC 9075**。

ISO / IEC 9075 補充了 ISO / IEC 13249：SQL 多媒體和應用程式包（SQL/MM），該程式包定義了基於 SQL 的介面和包，給諸如影片，音訊和空間資料之類的廣泛的應用程式。感興趣的各方可以從 ISO、IEC 或 ANSI 購買 SQL 標準文件。SQL：2008 的草稿可作為 zip 存檔免費獲得。

#### SQL 標準剖析

SQL 標準包含 10 部分：

* ISO/IEC 9075-1:2016 Part 1: _Framework_ (SQL/Framework). 提供邏輯概念
* ISO/IEC 9075-2:2016 Part 2: _Foundation_ (SQL/Foundation). 包含語言的主要內容，強制與可選特性。
* ISO/IEC 9075-3:2016 Part 3: _Call-Level Interface_ (SQL/CLI). 定義了介面成分 (structures, procedures, variable bindings) 用於編寫能執行 SQL 的應用程式的語言：Ada，C/C++，COBOL，Fortran，MUMPS，Pascal，PL/I。對於 Java 語言見標準第 10 部分。ODBC 是一個著名的 SQL/CLI 的超集。這部分標準主要包含強制的特性。
* ISO/IEC 9075-4:2016 Part 4: _Persistent stored modules_ (SQL/PSM)。SQL 的程序式擴充，包括控制流、條件處理、語句條件 signals 與 resignals、cursors、本地變數、表達式賦值到變數與參數。此外，SQL/PSM 形式化聲明與維護了持續性（persistent）資料庫語言常式（例如儲存程序）。這部分標準主要包含可選的特性。
* Part-6（頁面存檔備份，存於網際網路檔案館）: _Support for JavaScript Object Notation (JSON)_. 2017 年首次整合 JSON 資料類型到 SQL 標準。
* ISO/IEC 9075-9:2016 Part 9: _Management of External Data_ (SQL/MED). 這部分標準主要包含可選的特性。
* ISO/IEC 9075-10:2016 Part 10: _Object language bindings_ (SQL/OLB)。定義了 SQLJ，SQL 嵌入到 Java，保證了 SQLJ 應用程式二進位可移植。這部分標準主要包含可選的特性。
* ISO/IEC 9075-11:2016 Part 11: _Information and definition schemas_ (SQL/Schemata). 定義了 Information Schema 與 Definition Schema，提供了常用工具集使得 SQL 資料庫與物件自描述。這些工具包括 SQL object identifier、structure 與 integrity constraints、security 與 authorization specifications, features 與 packages。這部分標準主要包含強制與可選的特性。
* ISO/IEC 9075-13:2016 Part 13: _SQL Routines and types using the Java TM programming language_ (SQL/JRT). SQL 應用程式呼叫靜態方法作為子程式的能力 ('Java-in-the-database')；Java 類別作為 SQL 結構化使用者定義類型。這部分標準主要包含可選的特性。
* ISO/IEC 9075-14:2016 Part 14: _XML-Related Specifications_ (SQL/XML). 這部分標準主要包含可選的特性。
* ISO/IEC 9075-15:2019 Part 15: 多維陣列 (SQL/MDA)。 它為 SQL 指定了多維陣列類型（MDarray），以及對 MDarray，MDarray 切片，MDarray 單元和相關功能的操作。 標準的這一部分僅包含可選功能。

#### ISO / IEC 標準的擴充

_ISO/IEC 9075_ 被 _ISO/IEC 13249: SQL Multimedia and Application Packages_ (SQL/MM) 補充。後者定義了基於 SQL 的音影片、空間資料的介面與包。包括：

* ISO/IEC 13249-1:2016 Part 1: _Framework_
* ISO/IEC 13249-2:2003 Part 2: _Full-Text_
* ISO/IEC 13249-3:2016 Part 3: _Spatial_
* ISO/IEC 13249-5:2003 Part 5: _Still image_
* ISO/IEC 13249-6:2006 Part 6: _Data mining_
* ISO/IEC 13249-7:2013 Part 7: _History_
* ISO/IEC 13249-8:xxxx Part 8: _Metadata Registry Access_ _MRA_ (work in progress)

## 以 SQL 為基礎的其他延伸語言

* Transact-SQL

　
: 微軟 MS SQL-Server，以及 Sybase Adaptive Server 系列資料庫所用的 SQL

* PL-SQL

　
: Oracle 資料庫所使用的 SQL

## 安全問題

由於 SQL 指令在部份進階使用時，語法會依照特定條件來變換，而且若是表格中的欄位過多時，許多開發人員都會習慣以字串組立的方式建立 SQL 指令，而且又使用系統管理員級的帳戶連到資料庫，因此讓駭客有機會利用 SQL 的組立方式進行攻擊，像是在指令中添加部份刺探性或破壞性的指令（例如 `DROP TABLE`、`DROP DATABASE` 或是 `DELETE * FROM myTable` 等具破壞性的指令），讓資料庫的資料或實體伺服器被破壞，導致服務中斷或是系統癱瘓等後果，或是以邏輯的漏洞，在密碼欄寫入特殊字串 (例如 ' or '1'='1)，讓該字串形成的邏輯判斷永遠為真，或直接取得非查詢條件的資料，而不需要知道密碼，以達成非法登入系統的目的，此種攻擊手法稱為 **SQL 注入**（SQL injection）。

目前實務上較有效的防禦方法，就是全面改用參數化查詢。

## 參考文獻

## 參見

* 關聯式資料庫
* 語言整合查詢

## 外部連結

* Comparison of different SQL implementations （頁面存檔備份，存於網際網路檔案館）