OmniSciDB  72c90bc290
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
AlterForeignServerCommand Class Reference

#include <DdlCommandExecutor.h>

+ Inheritance diagram for AlterForeignServerCommand:
+ Collaboration diagram for AlterForeignServerCommand:

Public Member Functions

 AlterForeignServerCommand (const DdlCommandData &ddl_data, std::shared_ptr< Catalog_Namespace::SessionInfo const > session_ptr)
 
ExecutionResult execute (bool read_only_mode) override
 
- Public Member Functions inherited from DdlCommand
 DdlCommand (const DdlCommandData &ddl_data, std::shared_ptr< Catalog_Namespace::SessionInfo const > session_ptr)
 

Private Member Functions

void changeForeignServerOwner ()
 
void renameForeignServer ()
 
void setForeignServerOptions ()
 
void setForeignServerDataWrapper ()
 
bool hasAlterServerPrivileges ()
 

Additional Inherited Members

- Protected Attributes inherited from DdlCommand
const DdlCommandDataddl_data_
 
std::shared_ptr
< Catalog_Namespace::SessionInfo
const > 
session_ptr_
 

Detailed Description

Definition at line 66 of file DdlCommandExecutor.h.

Constructor & Destructor Documentation

AlterForeignServerCommand::AlterForeignServerCommand ( const DdlCommandData ddl_data,
std::shared_ptr< Catalog_Namespace::SessionInfo const >  session_ptr 
)

Definition at line 1015 of file DdlCommandExecutor.cpp.

References CHECK, DdlCommand::ddl_data_, anonymous_namespace{DdlCommandExecutor.cpp}::extractPayload(), g_enable_fsi, and UNREACHABLE.

1018  : DdlCommand(ddl_data, session_ptr) {
1019  if (!g_enable_fsi) {
1020  throw std::runtime_error("Unsupported command: ALTER FOREIGN SERVER");
1021  }
1022  auto& ddl_payload = extractPayload(ddl_data_);
1023  CHECK(ddl_payload.HasMember("serverName"));
1024  CHECK(ddl_payload["serverName"].IsString());
1025  CHECK(ddl_payload.HasMember("alterType"));
1026  CHECK(ddl_payload["alterType"].IsString());
1027  if (ddl_payload["alterType"] == "SET_OPTIONS") {
1028  CHECK(ddl_payload.HasMember("options"));
1029  CHECK(ddl_payload["options"].IsObject());
1030  } else if (ddl_payload["alterType"] == "SET_DATA_WRAPPER") {
1031  CHECK(ddl_payload.HasMember("dataWrapper"));
1032  CHECK(ddl_payload["dataWrapper"].IsString());
1033  } else if (ddl_payload["alterType"] == "RENAME_SERVER") {
1034  CHECK(ddl_payload.HasMember("newServerName"));
1035  CHECK(ddl_payload["newServerName"].IsString());
1036  } else if (ddl_payload["alterType"] == "CHANGE_OWNER") {
1037  CHECK(ddl_payload.HasMember("newOwner"));
1038  CHECK(ddl_payload["newOwner"].IsString());
1039  } else {
1040  UNREACHABLE(); // not-implemented alterType
1041  }
1042 }
#define UNREACHABLE()
Definition: Logger.h:338
const DdlCommandData & ddl_data_
const rapidjson::Value & extractPayload(const DdlCommandData &ddl_data)
DdlCommand(const DdlCommandData &ddl_data, std::shared_ptr< Catalog_Namespace::SessionInfo const > session_ptr)
#define CHECK(condition)
Definition: Logger.h:291
bool g_enable_fsi
Definition: Catalog.cpp:96

+ Here is the call graph for this function:

Member Function Documentation

void AlterForeignServerCommand::changeForeignServerOwner ( )
private

Definition at line 1077 of file DdlCommandExecutor.cpp.

References cat(), DdlCommand::ddl_data_, anonymous_namespace{DdlCommandExecutor.cpp}::extractPayload(), Catalog_Namespace::SysCatalog::instance(), ServerDBObjectType, DdlCommand::session_ptr_, and Catalog_Namespace::UserMetadata::userId.

Referenced by execute().

1077  {
1078  auto& ddl_payload = extractPayload(ddl_data_);
1079  std::string server_name = ddl_payload["serverName"].GetString();
1080  std::string new_owner = ddl_payload["newOwner"].GetString();
1081  auto& sys_cat = Catalog_Namespace::SysCatalog::instance();
1082  if (!session_ptr_->get_currentUser().isSuper) {
1083  throw std::runtime_error(
1084  "Only a super user can change a foreign server's owner. "
1085  "Current user is not a super-user. "
1086  "Foreign server with name \"" +
1087  server_name + "\" will not have owner changed.");
1088  }
1089  Catalog_Namespace::UserMetadata user, original_owner;
1090  if (!sys_cat.getMetadataForUser(new_owner, user)) {
1091  throw std::runtime_error("User with username \"" + new_owner + "\" does not exist. " +
1092  "Foreign server with name \"" + server_name +
1093  "\" can not have owner changed.");
1094  }
1095  auto& cat = session_ptr_->getCatalog();
1096  // get original owner metadata
1097  bool original_owner_exists = sys_cat.getMetadataForUserById(
1098  cat.getForeignServer(server_name)->user_id, original_owner);
1099  // update catalog
1100  cat.changeForeignServerOwner(server_name, user.userId);
1101  try {
1102  // update permissions
1103  DBObject db_object(server_name, DBObjectType::ServerDBObjectType);
1104  sys_cat.changeDBObjectOwnership(
1105  user, original_owner, db_object, cat, original_owner_exists);
1106  } catch (const std::runtime_error& e) {
1107  // update permissions failed, revert catalog update
1108  cat.changeForeignServerOwner(server_name, original_owner.userId);
1109  throw;
1110  }
1111 }
std::string cat(Ts &&...args)
const DdlCommandData & ddl_data_
static SysCatalog & instance()
Definition: SysCatalog.h:343
const rapidjson::Value & extractPayload(const DdlCommandData &ddl_data)
std::shared_ptr< Catalog_Namespace::SessionInfo const > session_ptr_

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

ExecutionResult AlterForeignServerCommand::execute ( bool  read_only_mode)
overridevirtual

Executes the DDL command corresponding to provided JSON payload.

Parameters
_returnresult of DDL command execution (if applicable)

Implements DdlCommand.

Definition at line 1044 of file DdlCommandExecutor.cpp.

References changeForeignServerOwner(), DdlCommand::ddl_data_, anonymous_namespace{DdlCommandExecutor.cpp}::extractPayload(), legacylockmgr::getExecuteWriteLock(), hasAlterServerPrivileges(), anonymous_namespace{DdlCommandExecutor.cpp}::is_default_server(), renameForeignServer(), DdlCommand::session_ptr_, setForeignServerDataWrapper(), and setForeignServerOptions().

Referenced by heavydb.cursor.Cursor::executemany().

1044  {
1045  auto execute_write_lock = legacylockmgr::getExecuteWriteLock();
1046 
1047  if (read_only_mode) {
1048  throw std::runtime_error("ALTER FOREIGN SERVER invalid in read only mode.");
1049  }
1050  auto& ddl_payload = extractPayload(ddl_data_);
1051  std::string server_name = ddl_payload["serverName"].GetString();
1052  if (is_default_server(server_name)) {
1053  throw std::runtime_error{"Default servers cannot be altered."};
1054  }
1055  if (!session_ptr_->getCatalog().getForeignServer(server_name)) {
1056  throw std::runtime_error{"Foreign server with name \"" + server_name +
1057  "\" does not exist and can not be altered."};
1058  }
1059  if (!hasAlterServerPrivileges()) {
1060  throw std::runtime_error("Server " + server_name +
1061  " can not be altered. User has no ALTER SERVER privileges.");
1062  }
1063  std::string alter_type = ddl_payload["alterType"].GetString();
1064  if (alter_type == "CHANGE_OWNER") {
1066  } else if (alter_type == "SET_DATA_WRAPPER") {
1068  } else if (alter_type == "SET_OPTIONS") {
1070  } else if (alter_type == "RENAME_SERVER") {
1072  }
1073 
1074  return ExecutionResult();
1075 }
const DdlCommandData & ddl_data_
bool is_default_server(const std::string &server_name)
const rapidjson::Value & extractPayload(const DdlCommandData &ddl_data)
auto getExecuteWriteLock()
std::shared_ptr< Catalog_Namespace::SessionInfo const > session_ptr_

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

bool AlterForeignServerCommand::hasAlterServerPrivileges ( )
private

Definition at line 1166 of file DdlCommandExecutor.cpp.

References AccessPrivileges::ALTER_SERVER, DdlCommand::ddl_data_, anonymous_namespace{DdlCommandExecutor.cpp}::extractPayload(), ServerDBObjectType, and DdlCommand::session_ptr_.

Referenced by execute().

1166  {
1167  // TODO: implement `GRANT/REVOKE ALTER_SERVER` DDL commands
1168  auto& ddl_payload = extractPayload(ddl_data_);
1169  std::string server_name = ddl_payload["serverName"].GetString();
1170  return session_ptr_->checkDBAccessPrivileges(
1172 }
static const AccessPrivileges ALTER_SERVER
Definition: DBObject.h:190
const DdlCommandData & ddl_data_
const rapidjson::Value & extractPayload(const DdlCommandData &ddl_data)
std::shared_ptr< Catalog_Namespace::SessionInfo const > session_ptr_

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

void AlterForeignServerCommand::renameForeignServer ( )
private

Definition at line 1113 of file DdlCommandExecutor.cpp.

References cat(), DdlCommand::ddl_data_, anonymous_namespace{DdlCommandExecutor.cpp}::extractPayload(), Catalog_Namespace::SysCatalog::instance(), anonymous_namespace{DdlCommandExecutor.cpp}::is_default_server(), ServerDBObjectType, DdlCommand::session_ptr_, and anonymous_namespace{DdlCommandExecutor.cpp}::throw_reserved_server_prefix_exception().

Referenced by execute().

1113  {
1114  auto& ddl_payload = extractPayload(ddl_data_);
1115  std::string server_name = ddl_payload["serverName"].GetString();
1116  std::string new_server_name = ddl_payload["newServerName"].GetString();
1117  if (is_default_server(new_server_name)) {
1119  }
1120  auto& cat = session_ptr_->getCatalog();
1121  // check for a conflicting server
1122  if (cat.getForeignServer(new_server_name)) {
1123  throw std::runtime_error("Foreign server with name \"" + server_name +
1124  "\" can not be renamed to \"" + new_server_name + "\"." +
1125  "Foreign server with name \"" + new_server_name +
1126  "\" exists.");
1127  }
1128  // update catalog
1129  cat.renameForeignServer(server_name, new_server_name);
1130  try {
1131  // migrate object privileges
1132  auto& sys_cat = Catalog_Namespace::SysCatalog::instance();
1133  sys_cat.renameDBObject(server_name,
1134  new_server_name,
1136  cat.getForeignServer(new_server_name)->id,
1137  cat);
1138  } catch (const std::runtime_error& e) {
1139  // permission migration failed, revert catalog update
1140  cat.renameForeignServer(new_server_name, server_name);
1141  throw;
1142  }
1143 }
std::string cat(Ts &&...args)
const DdlCommandData & ddl_data_
bool is_default_server(const std::string &server_name)
static SysCatalog & instance()
Definition: SysCatalog.h:343
const rapidjson::Value & extractPayload(const DdlCommandData &ddl_data)
std::shared_ptr< Catalog_Namespace::SessionInfo const > session_ptr_

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

void AlterForeignServerCommand::setForeignServerDataWrapper ( )
private

Definition at line 1157 of file DdlCommandExecutor.cpp.

References cat(), DdlCommand::ddl_data_, anonymous_namespace{DdlCommandExecutor.cpp}::extractPayload(), and DdlCommand::session_ptr_.

Referenced by execute().

1157  {
1158  auto& ddl_payload = extractPayload(ddl_data_);
1159  std::string server_name = ddl_payload["serverName"].GetString();
1160  std::string data_wrapper = ddl_payload["dataWrapper"].GetString();
1161  auto& cat = session_ptr_->getCatalog();
1162  // update catalog
1163  cat.setForeignServerDataWrapper(server_name, data_wrapper);
1164 }
std::string cat(Ts &&...args)
const DdlCommandData & ddl_data_
const rapidjson::Value & extractPayload(const DdlCommandData &ddl_data)
std::shared_ptr< Catalog_Namespace::SessionInfo const > session_ptr_

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

void AlterForeignServerCommand::setForeignServerOptions ( )
private

Definition at line 1145 of file DdlCommandExecutor.cpp.

References cat(), DdlCommand::ddl_data_, anonymous_namespace{DdlCommandExecutor.cpp}::extractPayload(), foreign_storage::OptionsContainer::getOptionsAsJsonString(), foreign_storage::OptionsContainer::populateOptionsMap(), and DdlCommand::session_ptr_.

Referenced by execute().

1145  {
1146  auto& ddl_payload = extractPayload(ddl_data_);
1147  std::string server_name = ddl_payload["serverName"].GetString();
1148  auto& cat = session_ptr_->getCatalog();
1149  // update catalog
1150  const auto foreign_server = cat.getForeignServer(server_name);
1152  opt.populateOptionsMap(foreign_server->getOptionsAsJsonString());
1153  opt.populateOptionsMap(ddl_payload["options"]);
1154  cat.setForeignServerOptions(server_name, opt.getOptionsAsJsonString());
1155 }
std::string cat(Ts &&...args)
std::string getOptionsAsJsonString() const
const DdlCommandData & ddl_data_
void populateOptionsMap(OptionsMap &&options_map, bool clear=false)
const rapidjson::Value & extractPayload(const DdlCommandData &ddl_data)
std::shared_ptr< Catalog_Namespace::SessionInfo const > session_ptr_

+ Here is the call graph for this function:

+ Here is the caller graph for this function:


The documentation for this class was generated from the following files: