@@ -719,6 +719,7 @@ impl<'a> Parser<'a> {
719719 self.parse_vacuum()
720720 }
721721 Keyword::RESET => self.parse_reset().map(Into::into),
722+ Keyword::SECURITY => self.parse_security_label().map(Into::into),
722723 _ => self.expected("an SQL statement", next_token),
723724 },
724725 Token::LParen => {
@@ -5172,7 +5173,11 @@ impl<'a> Parser<'a> {
51725173 } else if self.parse_keyword(Keyword::SECRET) {
51735174 self.parse_create_secret(or_replace, temporary, persistent)
51745175 } else if self.parse_keyword(Keyword::USER) {
5175- self.parse_create_user(or_replace).map(Into::into)
5176+ if self.parse_keyword(Keyword::MAPPING) {
5177+ self.parse_create_user_mapping().map(Into::into)
5178+ } else {
5179+ self.parse_create_user(or_replace).map(Into::into)
5180+ }
51765181 } else if self.parse_keyword(Keyword::AGGREGATE) {
51775182 self.parse_create_aggregate(or_replace).map(Into::into)
51785183 } else if or_replace {
@@ -5232,6 +5237,8 @@ impl<'a> Parser<'a> {
52325237 self.parse_create_publication().map(Into::into)
52335238 } else if self.parse_keyword(Keyword::SUBSCRIPTION) {
52345239 self.parse_create_subscription().map(Into::into)
5240+ } else if self.parse_keyword(Keyword::TABLESPACE) {
5241+ self.parse_create_tablespace().map(Into::into)
52355242 } else {
52365243 self.expected_ref("an object type after CREATE", self.peek_token_ref())
52375244 }
@@ -20268,6 +20275,136 @@ impl<'a> Parser<'a> {
2026820275 })
2026920276 }
2027020277
20278+ /// Parse a `SECURITY LABEL` statement.
20279+ ///
20280+ /// See <https://www.postgresql.org/docs/current/sql-securitylabel.html>
20281+ pub fn parse_security_label(&mut self) -> Result<SecurityLabel, ParserError> {
20282+ self.expect_keyword_is(Keyword::LABEL)?;
20283+
20284+ let provider = if self.parse_keyword(Keyword::FOR) {
20285+ Some(self.parse_identifier()?)
20286+ } else {
20287+ None
20288+ };
20289+
20290+ self.expect_keyword_is(Keyword::ON)?;
20291+
20292+ let object_kind = if self.parse_keywords(&[Keyword::MATERIALIZED, Keyword::VIEW]) {
20293+ SecurityLabelObjectKind::MaterializedView
20294+ } else if self.parse_keyword(Keyword::TABLE) {
20295+ SecurityLabelObjectKind::Table
20296+ } else if self.parse_keyword(Keyword::COLUMN) {
20297+ SecurityLabelObjectKind::Column
20298+ } else if self.parse_keyword(Keyword::DATABASE) {
20299+ SecurityLabelObjectKind::Database
20300+ } else if self.parse_keyword(Keyword::DOMAIN) {
20301+ SecurityLabelObjectKind::Domain
20302+ } else if self.parse_keyword(Keyword::FUNCTION) {
20303+ SecurityLabelObjectKind::Function
20304+ } else if self.parse_keyword(Keyword::ROLE) {
20305+ SecurityLabelObjectKind::Role
20306+ } else if self.parse_keyword(Keyword::SCHEMA) {
20307+ SecurityLabelObjectKind::Schema
20308+ } else if self.parse_keyword(Keyword::SEQUENCE) {
20309+ SecurityLabelObjectKind::Sequence
20310+ } else if self.parse_keyword(Keyword::TYPE) {
20311+ SecurityLabelObjectKind::Type
20312+ } else if self.parse_keyword(Keyword::VIEW) {
20313+ SecurityLabelObjectKind::View
20314+ } else {
20315+ return self.expected_ref(
20316+ "TABLE, COLUMN, DATABASE, DOMAIN, FUNCTION, MATERIALIZED VIEW, ROLE, SCHEMA, SEQUENCE, TYPE, or VIEW after ON",
20317+ self.peek_token_ref(),
20318+ );
20319+ };
20320+
20321+ let object_name = self.parse_object_name(false)?;
20322+
20323+ self.expect_keyword_is(Keyword::IS)?;
20324+
20325+ let label = if self.parse_keyword(Keyword::NULL) {
20326+ None
20327+ } else {
20328+ Some(self.parse_value()?.value)
20329+ };
20330+
20331+ Ok(SecurityLabel {
20332+ provider,
20333+ object_kind,
20334+ object_name,
20335+ label,
20336+ })
20337+ }
20338+
20339+ /// Parse a `CREATE USER MAPPING` statement.
20340+ ///
20341+ /// See <https://www.postgresql.org/docs/current/sql-createusermapping.html>
20342+ pub fn parse_create_user_mapping(&mut self) -> Result<CreateUserMapping, ParserError> {
20343+ let if_not_exists = self.parse_keywords(&[Keyword::IF, Keyword::NOT, Keyword::EXISTS]);
20344+
20345+ self.expect_keyword_is(Keyword::FOR)?;
20346+
20347+ let user = if self.parse_keyword(Keyword::CURRENT_ROLE) {
20348+ UserMappingUser::CurrentRole
20349+ } else if self.parse_keyword(Keyword::CURRENT_USER) {
20350+ UserMappingUser::CurrentUser
20351+ } else if self.parse_keyword(Keyword::PUBLIC) {
20352+ UserMappingUser::Public
20353+ } else if self.parse_keyword(Keyword::USER) {
20354+ UserMappingUser::User
20355+ } else {
20356+ UserMappingUser::Ident(self.parse_identifier()?)
20357+ };
20358+
20359+ self.expect_keyword_is(Keyword::SERVER)?;
20360+ let server_name = self.parse_identifier()?;
20361+
20362+ let options = if self.parse_keyword(Keyword::OPTIONS) {
20363+ self.expect_token(&Token::LParen)?;
20364+ let opts = self.parse_comma_separated(|p| {
20365+ let key = p.parse_identifier()?;
20366+ let value = p.parse_identifier()?;
20367+ Ok(CreateServerOption { key, value })
20368+ })?;
20369+ self.expect_token(&Token::RParen)?;
20370+ Some(opts)
20371+ } else {
20372+ None
20373+ };
20374+
20375+ Ok(CreateUserMapping {
20376+ if_not_exists,
20377+ user,
20378+ server_name,
20379+ options,
20380+ })
20381+ }
20382+
20383+ /// Parse a `CREATE TABLESPACE` statement.
20384+ ///
20385+ /// See <https://www.postgresql.org/docs/current/sql-createtablespace.html>
20386+ pub fn parse_create_tablespace(&mut self) -> Result<CreateTablespace, ParserError> {
20387+ let name = self.parse_identifier()?;
20388+
20389+ let owner = if self.parse_keyword(Keyword::OWNER) {
20390+ Some(self.parse_identifier()?)
20391+ } else {
20392+ None
20393+ };
20394+
20395+ self.expect_keyword_is(Keyword::LOCATION)?;
20396+ let location = self.parse_value()?.value;
20397+
20398+ let with_options = self.parse_options(Keyword::WITH)?;
20399+
20400+ Ok(CreateTablespace {
20401+ name,
20402+ owner,
20403+ location,
20404+ with_options,
20405+ })
20406+ }
20407+
2027120408 /// The index of the first unprocessed token.
2027220409 pub fn index(&self) -> usize {
2027320410 self.index
0 commit comments