use of org.apache.derby.iapi.sql.depend.DependencyManager in project derby by apache.
the class DDLConstantAction method adjustUDTDependencies.
/**
* Add and drop dependencies of an object on UDTs.
*
* @param lcc Interpreter's state variable for this session.
* @param dd Metadata
* @param dependent Object which depends on UDT
* @param addUdtMap Map of UDTs for which dependencies should be added
* @param dropUdtMap Map of UDT for which dependencies should be dropped
*/
private void adjustUDTDependencies(LanguageConnectionContext lcc, DataDictionary dd, Dependent dependent, HashMap<String, AliasDescriptor> addUdtMap, HashMap<String, AliasDescriptor> dropUdtMap) throws StandardException {
// again, nothing to do if there are no columns of udt type
if ((addUdtMap.isEmpty()) && (dropUdtMap.isEmpty())) {
return;
}
TransactionController tc = lcc.getTransactionExecute();
DependencyManager dm = dd.getDependencyManager();
ContextManager cm = lcc.getContextManager();
// add new dependencies
for (AliasDescriptor ad : addUdtMap.values()) {
dm.addDependency(dependent, ad, cm);
}
// drop dependencies that are orphaned
for (AliasDescriptor ad : dropUdtMap.values()) {
DependencyDescriptor dep = new DependencyDescriptor(dependent, ad);
dd.dropStoredDependency(dep, tc);
}
}
use of org.apache.derby.iapi.sql.depend.DependencyManager in project derby by apache.
the class DDLConstantAction method addColumnDependencies.
/**
* Add dependencies of a column on providers. These can arise if a generated column depends
* on a user created function.
*/
protected void addColumnDependencies(LanguageConnectionContext lcc, DataDictionary dd, TableDescriptor td, ColumnInfo ci) throws StandardException {
ProviderInfo[] providers = ci.providers;
if (providers != null) {
DependencyManager dm = dd.getDependencyManager();
ContextManager cm = lcc.getContextManager();
int providerCount = providers.length;
ColumnDescriptor cd = td.getColumnDescriptor(ci.name);
DefaultDescriptor defDesc = cd.getDefaultDescriptor(dd);
for (int px = 0; px < providerCount; px++) {
ProviderInfo pi = providers[px];
DependableFinder finder = pi.getDependableFinder();
UUID providerID = pi.getObjectId();
Provider provider = (Provider) finder.getDependable(dd, providerID);
dm.addDependency(defDesc, provider, cm);
}
// end loop through providers
}
}
use of org.apache.derby.iapi.sql.depend.DependencyManager in project derby by apache.
the class DDLConstantAction method storeConstraintDependenciesOnPrivileges.
/**
* This method saves dependencies of constraints on privileges in the
* dependency system. It gets called by CreateConstraintConstantAction.
* Views and triggers and constraints run with definer's privileges. If
* one of the required privileges is revoked from the definer, the
* dependent view/trigger/constraint on that privilege will be dropped
* automatically. In order to implement this behavior, we need to save
* view/trigger/constraint dependencies on required privileges in the
* dependency system. Following method accomplishes that part of the
* equation for constraints only. The dependency collection for
* constraints is not same as for views and triggers and hence
* constraints are handled by this special method.
*
* Views and triggers can depend on many different kind of privileges
* where as constraints only depend on REFERENCES privilege on a table
* (FOREIGN KEY constraints) or EXECUTE privileges on one or more
* functions (CHECK constraints).
*
* Another difference is only one view or trigger can be defined by a
* sql statement and hence all the dependencies collected for the sql
* statement apply to the view or trigger in question. As for constraints,
* one sql statement can defined multiple constraints and hence the
* all the privileges required by the statement are not necessarily
* required by all the constraints defined by that sql statement. We need
* to identify right privileges for right constraints for a given sql
* statement. Because of these differences between constraints and views
* (and triggers), there are 2 different methods in this class to save
* their privileges in the dependency system.
*
* For each required privilege, we now register a dependency on a role if
* that role was required to find an applicable privilege.
*
* @param activation The execution environment for this constant action.
* @param dependent Make this object depend on required privileges
* @param refTableUUID Make sure we are looking for REFERENCES privilege
* for right table
* @param providers set of providers for this constraint
* @exception StandardException Thrown on failure
*/
protected void storeConstraintDependenciesOnPrivileges(Activation activation, Dependent dependent, UUID refTableUUID, ProviderInfo[] providers) throws StandardException {
LanguageConnectionContext lcc = activation.getLanguageConnectionContext();
DataDictionary dd = lcc.getDataDictionary();
DependencyManager dm = dd.getDependencyManager();
String currentUser = lcc.getCurrentUserId(activation);
SettableBoolean roleDepAdded = new SettableBoolean();
// access any objects without any restrictions
if (!currentUser.equals(dd.getAuthorizationDatabaseOwner())) {
PermissionsDescriptor permDesc;
// Now, it is time to add into dependency system the FOREIGN
// constraint's dependency on REFERENCES privilege, or, if it is a
// CHECK constraint, any EXECUTE or USAGE privileges. If the REFERENCES is
// revoked from the constraint owner, the constraint will get
// dropped automatically.
List<StatementPermission> requiredPermissionsList = activation.getPreparedStatement().getRequiredPermissionsList();
if (requiredPermissionsList != null && !requiredPermissionsList.isEmpty()) {
for (StatementPermission statPerm : requiredPermissionsList) {
// are not required for a foreign key constraint.
if (statPerm instanceof StatementTablePermission) {
// It is a table/column level privilege
StatementTablePermission statementTablePermission = (StatementTablePermission) statPerm;
// required privileges list
if (statementTablePermission.getPrivType() != Authorizer.REFERENCES_PRIV)
continue;
// privilege in the required privileges list
if (!statementTablePermission.getTableUUID().equals(refTableUUID))
continue;
} else if (statPerm instanceof StatementSchemaPermission || statPerm instanceof StatementRolePermission || statPerm instanceof StatementGenericPermission) {
continue;
} else {
if (SanityManager.DEBUG) {
SanityManager.ASSERT(statPerm instanceof StatementRoutinePermission, "only StatementRoutinePermission expected");
}
// skip if this permission concerns a function not
// referenced by this constraint
StatementRoutinePermission rp = (StatementRoutinePermission) statPerm;
if (!inProviderSet(providers, rp.getRoutineUUID())) {
continue;
}
}
// We know that we are working with a REFERENCES, EXECUTE, or USAGE
// privilege. Find all the PermissionDescriptors for this
// privilege and make constraint depend on it through
// dependency manager. The REFERENCES privilege could be
// defined at the table level or it could be defined at
// individual column levels. In addition, individual column
// REFERENCES privilege could be available at the user
// level, PUBLIC or role level. EXECUTE and USAGE privileges could be
// available at the user level, PUBLIC or role level.
permDesc = statPerm.getPermissionDescriptor(currentUser, dd);
if (permDesc == null) {
// No privilege exists for given user. The privilege
// has to exist at at PUBLIC level....
permDesc = statPerm.getPermissionDescriptor(Authorizer.PUBLIC_AUTHORIZATION_ID, dd);
// .... or at the role level. Additionally, for column
// level privileges, even if *some* were available at
// the PUBLIC level others may be still be missing,
// hence the call in the test below to
// allColumnsCoveredByUserOrPUBLIC.
boolean roleUsed = false;
if (permDesc == null || ((permDesc instanceof ColPermsDescriptor) && !((StatementColumnPermission) statPerm).allColumnsCoveredByUserOrPUBLIC(currentUser, dd))) {
roleUsed = true;
permDesc = findRoleUsage(activation, statPerm);
}
// for the owner.
if (!permDesc.checkOwner(currentUser)) {
dm.addDependency(dependent, permDesc, lcc.getContextManager());
if (roleUsed) {
// We had to rely on role, so track that
// dependency, too.
trackRoleDependency(activation, dependent, roleDepAdded);
}
}
} else // object's privilege dependency in the dependency system
if (!permDesc.checkOwner(currentUser)) {
dm.addDependency(dependent, permDesc, lcc.getContextManager());
if (permDesc instanceof ColPermsDescriptor) {
// The if statement above means we found a
// REFERENCES privilege at column level for the
// given authorizer. If this privilege doesn't
// cover all the column , then there has to exisit
// REFERENCES for the remaining columns at PUBLIC
// level or at role level. Get that permission
// descriptor and save it in dependency system
StatementColumnPermission statementColumnPermission = (StatementColumnPermission) statPerm;
permDesc = statementColumnPermission.getPUBLIClevelColPermsDescriptor(currentUser, dd);
// into the dependency system
if (permDesc != null && permDesc.getObjectID() != null) {
// User did not have all required column
// permissions and at least one column is
// covered by PUBLIC.
dm.addDependency(dependent, permDesc, lcc.getContextManager());
}
// upon.
if (!statementColumnPermission.allColumnsCoveredByUserOrPUBLIC(currentUser, dd)) {
// Role has been relied upon, so register a
// dependency.
trackRoleDependency(activation, dependent, roleDepAdded);
}
}
}
if (!(statPerm instanceof StatementRoutinePermission)) {
// for this sql statement.
break;
} else {
// For EXECUTE privilege there may be several functions
// referenced in the constraint, so continue looking.
}
}
}
}
}
use of org.apache.derby.iapi.sql.depend.DependencyManager in project derby by apache.
the class DDLConstantAction method trackRoleDependency.
/**
* The statement permission needed for dependent has been found to rely on
* the current role. If not already done, register the dependency so that
* if the current role (or any of the roles it inherits) is revoked (or
* dropped), we can invalidate dependent.
*
* @param activation the current activation
* @param dependent the view, constraint or trigger that is dependent on the
* current role for some privilege.
* @param roleDepAdded keeps track of whether a dependency on the
* current role has already been registered.
*/
private static void trackRoleDependency(Activation activation, Dependent dependent, SettableBoolean roleDepAdded) throws StandardException {
// fails for triggers at least).
if (!roleDepAdded.get()) {
LanguageConnectionContext lcc = activation.getLanguageConnectionContext();
DataDictionary dd = lcc.getDataDictionary();
DependencyManager dm = dd.getDependencyManager();
String role = lcc.getCurrentRoleId(activation);
RoleGrantDescriptor rgd = dd.getRoleDefinitionDescriptor(role);
dm.addDependency(dependent, rgd, lcc.getContextManager());
roleDepAdded.set(true);
}
}
use of org.apache.derby.iapi.sql.depend.DependencyManager in project derby by apache.
the class DropTableConstantAction method dropAllConstraintDescriptors.
private void dropAllConstraintDescriptors(TableDescriptor td, Activation activation) throws StandardException {
ConstraintDescriptor cd;
ConstraintDescriptorList cdl;
ConstraintDescriptor fkcd;
ConstraintDescriptorList fkcdl;
LanguageConnectionContext lcc = activation.getLanguageConnectionContext();
DataDictionary dd = lcc.getDataDictionary();
DependencyManager dm = dd.getDependencyManager();
TransactionController tc = lcc.getTransactionExecute();
cdl = dd.getConstraintDescriptors(td);
/* The current element will be deleted underneath
* the loop, so we only increment the counter when
* skipping an element. (HACK!)
*/
for (int index = 0; index < cdl.size(); ) {
cd = cdl.elementAt(index);
if (cd instanceof ReferencedKeyConstraintDescriptor) {
index++;
continue;
}
dm.invalidateFor(cd, DependencyManager.DROP_CONSTRAINT, lcc);
dropConstraint(cd, td, activation, lcc, true);
}
/* The current element will be deleted underneath
* the loop. (HACK!)
*/
while (cdl.size() > 0) {
cd = cdl.elementAt(0);
if (SanityManager.DEBUG) {
if (!(cd instanceof ReferencedKeyConstraintDescriptor)) {
SanityManager.THROWASSERT("Constraint descriptor not an instance of " + "ReferencedKeyConstraintDescriptor as expected. Is a " + cd.getClass().getName());
}
}
/*
** Drop the referenced constraint (after we got
** the primary keys) now. Do this prior to
** droping the referenced keys to avoid performing
** a lot of extra work updating the referencedcount
** field of sys.sysconstraints.
**
** Pass in false to dropConstraintsAndIndex so it
** doesn't clear dependencies, we'll do that ourselves.
*/
dropConstraint(cd, td, activation, lcc, false);
/*
** If we are going to cascade, get all the
** referencing foreign keys and zap them first.
*/
if (cascade) {
/*
** Go to the system tables to get the foreign keys
** to be safe
*/
fkcdl = dd.getForeignKeys(cd.getUUID());
/*
** For each FK that references this key, drop
** it.
*/
for (int inner = 0; inner < fkcdl.size(); inner++) {
fkcd = (ConstraintDescriptor) fkcdl.elementAt(inner);
dm.invalidateFor(fkcd, DependencyManager.DROP_CONSTRAINT, lcc);
dropConstraint(fkcd, td, activation, lcc, true);
activation.addWarning(StandardException.newWarning(SQLState.LANG_CONSTRAINT_DROPPED, fkcd.getConstraintName(), fkcd.getTableDescriptor().getName()));
}
}
/*
** Now that we got rid of the fks (if we were cascading), it is
** ok to do an invalidate for.
*/
dm.invalidateFor(cd, DependencyManager.DROP_CONSTRAINT, lcc);
dm.clearDependencies(lcc, cd);
}
}
Aggregations