8
0
mirror of https://github.com/FirebirdSQL/firebird.git synced 2025-01-22 20:43:02 +01:00

added the ability to change sql security opt in alter procedure

This commit is contained in:
Alexander Zhdanov 2023-10-25 19:21:25 +03:00
parent 9b823e6996
commit 5b620936e2
5 changed files with 98 additions and 7 deletions

View File

@ -608,3 +608,8 @@ If not specified in the CREATE TABLE statement, the database-level default behav
(Alexander Zhdanov) (Alexander Zhdanov)
ALTER FUNCTION <name> [ {DETERMINISTIC | NOT DETERMINISTIC} ] [ SQL SECURITY {DEFINER | INVOKER} | DROP SQL SECURITY ] ALTER FUNCTION <name> [ {DETERMINISTIC | NOT DETERMINISTIC} ] [ SQL SECURITY {DEFINER | INVOKER} | DROP SQL SECURITY ]
25) Added the ability to change sql security option without specifying the entire body of the procedure
(Alexander Zhdanov)
ALTER PROCEDURE <name> SQL SECURITY {DEFINER | INVOKER} | DROP SQL SECURITY

View File

@ -2711,7 +2711,7 @@ DdlNode* CreateAlterProcedureNode::dsqlPass(DsqlCompilerScratch* dsqlScratch)
returns[i]->type->resolve(dsqlScratch); returns[i]->type->resolve(dsqlScratch);
// check SQL SECURITY is not set if procedure declared in package // check SQL SECURITY is not set if procedure declared in package
if (package.hasData() && ssDefiner.isAssigned()) if (package.hasData() && ssDefiner.has_value())
{ {
ERRD_post(Arg::Gds(isc_sqlerr) << Arg::Num(-204) << ERRD_post(Arg::Gds(isc_sqlerr) << Arg::Num(-204) <<
Arg::Gds(isc_invalid_clause) << Arg::Str("SQL SECURITY for procedures is prohibit in packages")); Arg::Gds(isc_invalid_clause) << Arg::Str("SQL SECURITY for procedures is prohibit in packages"));
@ -2742,11 +2742,22 @@ void CreateAlterProcedureNode::execute(thread_db* tdbb, DsqlCompilerScratch* dsq
AutoSavePoint savePoint(tdbb, transaction); AutoSavePoint savePoint(tdbb, transaction);
bool altered = false; bool altered = false;
const bool alterIndividualParameters = (alter && !(body || external));
// first pass // first pass
if (alter) if (alterIndividualParameters)
{
if (executeAlterIndividualParameters(tdbb, dsqlScratch, transaction, false, true))
altered = true;
else
status_exception::raise(Arg::Gds(isc_dyn_proc_not_found) << Arg::Str(name));
}
else if (alter)
{ {
if (executeAlter(tdbb, dsqlScratch, transaction, false, true)) if (executeAlter(tdbb, dsqlScratch, transaction, false, true))
{
altered = true; altered = true;
}
else else
{ {
if (create) // create or alter if (create) // create or alter
@ -2760,7 +2771,11 @@ void CreateAlterProcedureNode::execute(thread_db* tdbb, DsqlCompilerScratch* dsq
compile(tdbb, dsqlScratch); compile(tdbb, dsqlScratch);
executeAlter(tdbb, dsqlScratch, transaction, true, false); // second pass // second pass
if (alterIndividualParameters)
executeAlterIndividualParameters(tdbb, dsqlScratch, transaction, true, false);
else
executeAlter(tdbb, dsqlScratch, transaction, true, false);
if (package.isEmpty()) if (package.isEmpty())
{ {
@ -2909,10 +2924,10 @@ bool CreateAlterProcedureNode::executeAlter(thread_db* tdbb, DsqlCompilerScratch
else else
P.RDB$PRIVATE_FLAG.NULL = TRUE; P.RDB$PRIVATE_FLAG.NULL = TRUE;
if (ssDefiner.isAssigned()) if (ssDefiner.has_value())
{ {
P.RDB$SQL_SECURITY.NULL = FALSE; P.RDB$SQL_SECURITY.NULL = FALSE;
P.RDB$SQL_SECURITY = ssDefiner.asBool() ? FB_TRUE : FB_FALSE; P.RDB$SQL_SECURITY = ssDefiner.value() == SqlSecurity::SS_DEFINER ? FB_TRUE : FB_FALSE;
} }
else else
P.RDB$SQL_SECURITY.NULL = TRUE; P.RDB$SQL_SECURITY.NULL = TRUE;
@ -3024,6 +3039,52 @@ bool CreateAlterProcedureNode::executeAlter(thread_db* tdbb, DsqlCompilerScratch
return modified; return modified;
} }
bool CreateAlterProcedureNode::executeAlterIndividualParameters(thread_db* tdbb, DsqlCompilerScratch* dsqlScratch, jrd_tra* transaction, bool secondPass, bool runTriggers)
{
Attachment* const attachment = transaction->getAttachment();
bool modifed = false;
AutoCacheRequest requestHandle(tdbb, drq_m_prm_prcs2, DYN_REQUESTS);
FOR (REQUEST_HANDLE requestHandle TRANSACTION_HANDLE transaction)
P IN RDB$PROCEDURES
WITH P.RDB$PROCEDURE_NAME EQ name.c_str() AND
P.RDB$PACKAGE_NAME EQUIV NULLIF(package.c_str(), '')
{
if (P.RDB$SYSTEM_FLAG)
{
status_exception::raise(
Arg::Gds(isc_dyn_cannot_mod_sysproc) <<
MetaName(P.RDB$PROCEDURE_NAME));
}
if (!secondPass && runTriggers && package.isEmpty())
{
executeDdlTrigger(tdbb, dsqlScratch, transaction, DTW_BEFORE,
DDL_TRIGGER_ALTER_PROCEDURE, name, NULL);
}
MODIFY P
if (ssDefiner.has_value())
{
if(ssDefiner.value() != SqlSecurity::SS_DROP)
{
P.RDB$SQL_SECURITY.NULL = FALSE;
P.RDB$SQL_SECURITY = ssDefiner.value() == SqlSecurity::SS_DEFINER ? FB_TRUE : FB_FALSE;
}
else
P.RDB$SQL_SECURITY.NULL = TRUE;
}
modifed = true;
END_MODIFY
}
END_FOR
return modifed;
}
void CreateAlterProcedureNode::storeParameter(thread_db* tdbb, DsqlCompilerScratch* dsqlScratch, void CreateAlterProcedureNode::storeParameter(thread_db* tdbb, DsqlCompilerScratch* dsqlScratch,
jrd_tra* transaction, USHORT parameterType, unsigned pos, ParameterClause* parameter, jrd_tra* transaction, USHORT parameterType, unsigned pos, ParameterClause* parameter,
const CollectedParameter* collectedParameter) const CollectedParameter* collectedParameter)

View File

@ -600,6 +600,9 @@ private:
void executeCreate(thread_db* tdbb, DsqlCompilerScratch* dsqlScratch, jrd_tra* transaction); void executeCreate(thread_db* tdbb, DsqlCompilerScratch* dsqlScratch, jrd_tra* transaction);
bool executeAlter(thread_db* tdbb, DsqlCompilerScratch* dsqlScratch, jrd_tra* transaction, bool executeAlter(thread_db* tdbb, DsqlCompilerScratch* dsqlScratch, jrd_tra* transaction,
bool secondPass, bool runTriggers); bool secondPass, bool runTriggers);
bool executeAlterIndividualParameters(thread_db* tdbb, DsqlCompilerScratch* dsqlScratch, jrd_tra* transaction,
bool secondPass, bool runTriggers);
void storeParameter(thread_db* tdbb, DsqlCompilerScratch* dsqlScratch, jrd_tra* transaction, void storeParameter(thread_db* tdbb, DsqlCompilerScratch* dsqlScratch, jrd_tra* transaction,
USHORT parameterType, unsigned pos, ParameterClause* parameter, USHORT parameterType, unsigned pos, ParameterClause* parameter,
const CollectedParameter* collectedParameter); const CollectedParameter* collectedParameter);
@ -622,7 +625,7 @@ public:
MetaName packageOwner; MetaName packageOwner;
bool privateScope; bool privateScope;
bool preserveDefaults; bool preserveDefaults;
TriState ssDefiner; std::optional<SqlSecurity> ssDefiner;
}; };

View File

@ -2707,9 +2707,13 @@ procedure_clause
| external_procedure_clause | external_procedure_clause
; ;
%type <createAlterProcedureNode> change_opt_procedure_clause
change_opt_procedure_clause
;
%type <createAlterProcedureNode> psql_procedure_clause %type <createAlterProcedureNode> psql_procedure_clause
psql_procedure_clause psql_procedure_clause
: procedure_clause_start sql_security_clause_opt AS local_declarations_opt full_proc_block : procedure_clause_start optional_sql_security_full_alter_clause AS local_declarations_opt full_proc_block
{ {
$$ = $1; $$ = $1;
$$->ssDefiner = $2; $$->ssDefiner = $2;
@ -2738,6 +2742,17 @@ procedure_clause_start
{ $$ = $2; } { $$ = $2; }
; ;
%type <createAlterProcedureNode> change_opt_procedure_clause
change_opt_procedure_clause
: symbol_procedure_name
{ $$ = newNode<CreateAlterProcedureNode>(*$1); }
optional_sql_security_partial_alter_clause
{
$$ = $2;
$$->ssDefiner = $3;
}
;
%type <createAlterProcedureNode> alter_procedure_clause %type <createAlterProcedureNode> alter_procedure_clause
alter_procedure_clause alter_procedure_clause
: procedure_clause : procedure_clause
@ -2746,6 +2761,12 @@ alter_procedure_clause
$$->alter = true; $$->alter = true;
$$->create = false; $$->create = false;
} }
| change_opt_procedure_clause
{
$$ = $1;
$$->alter = true;
$$->create = false;
}
; ;
%type <createAlterProcedureNode> replace_procedure_clause %type <createAlterProcedureNode> replace_procedure_clause

View File

@ -182,6 +182,7 @@ enum drq_type_t
drq_s_prms4, drq_s_prms4,
drq_s_prm_src2, drq_s_prm_src2,
drq_m_prcs2, drq_m_prcs2,
drq_m_prm_prcs2, // modify individual procedure parameters (CreateAlterProcedureNode)
drq_e_prms2, drq_e_prms2,
drq_m_trigger2, drq_m_trigger2,
drq_e_prcs2, drq_e_prcs2,