// effects: Checks for key constraint implication problems from // leftViewConstraints to rightViewConstraints. Adds errors/warning to m_errorLog private void CheckImplicationKeyConstraints(ViewSchemaConstraints leftViewConstraints, ViewSchemaConstraints rightViewConstraints) { // if cImpliesS is true, every rightKeyConstraint must be implied // if it is false, at least one key constraint for each C-level // extent must be implied foreach (ViewKeyConstraint rightKeyConstraint in rightViewConstraints.KeyConstraints) { // Go through all the left Side constraints and check for implication bool found = false; foreach (ViewKeyConstraint leftKeyConstraint in leftViewConstraints.KeyConstraints) { if (leftKeyConstraint.Implies(rightKeyConstraint)) { found = true; break; // The implication holds - so no problem } } if (false == found) { // No C-side key constraint implies this S-level key constraint // Report a problem m_errorLog.AddEntry(ViewKeyConstraint.GetErrorRecord(rightKeyConstraint)); } } }
// effects: Performs the validation of the cells in this and returns // an error log of all the errors/warnings that were discovered internal ErrorLog Validate() { // Check for errors not checked by "C-implies-S principle" if (m_config.IsValidationEnabled) { if (PerformSingleCellChecks() == false) { return(m_errorLog); } } else //Note that Metadata loading guarantees that DISTINCT flag is not present { // when update views (and validation) is disabled if (CheckCellsWithDistinctFlag() == false) { return(m_errorLog); } } BasicSchemaConstraints cConstraints = new BasicSchemaConstraints(); BasicSchemaConstraints sConstraints = new BasicSchemaConstraints(); // Construct intermediate "view relations" and the basic cell // relations along with the basic constraints ConstructCellRelationsWithConstraints(cConstraints, sConstraints); if (m_config.IsVerboseTracing) { // Trace Basic constraints Trace.WriteLine(String.Empty); Trace.WriteLine("C-Level Basic Constraints"); Trace.WriteLine(cConstraints); Trace.WriteLine("S-Level Basic Constraints"); Trace.WriteLine(sConstraints); } // Propagate the constraints m_cViewConstraints = PropagateConstraints(cConstraints); m_sViewConstraints = PropagateConstraints(sConstraints); // Make some basic checks on the view and basic cell constraints CheckConstraintSanity(cConstraints, sConstraints, m_cViewConstraints, m_sViewConstraints); if (m_config.IsVerboseTracing) { // Trace View constraints Trace.WriteLine(String.Empty); Trace.WriteLine("C-Level View Constraints"); Trace.WriteLine(m_cViewConstraints); Trace.WriteLine("S-Level View Constraints"); Trace.WriteLine(m_sViewConstraints); } // Check for implication if (m_config.IsValidationEnabled) { CheckImplication(m_cViewConstraints, m_sViewConstraints); } return(m_errorLog); }
private static void CheckConstraintSanity(BasicSchemaConstraints cConstraints, BasicSchemaConstraints sConstraints, ViewSchemaConstraints cViewConstraints, ViewSchemaConstraints sViewConstraints) { Debug.Assert(cConstraints.KeyConstraints.Count() == cViewConstraints.KeyConstraints.Count(), "Mismatch in number of C basic and view key constraints"); Debug.Assert(sConstraints.KeyConstraints.Count() == sViewConstraints.KeyConstraints.Count(), "Mismatch in number of S basic and view key constraints"); }
// effects: Propagates baseConstraints derived from the cellrelations // to the corresponding viewCellRelations and returns the list of // propagated constraints private static ViewSchemaConstraints PropagateConstraints(BasicSchemaConstraints baseConstraints) { ViewSchemaConstraints propagatedConstraints = new ViewSchemaConstraints(); // Key constraint propagation foreach (BasicKeyConstraint keyConstraint in baseConstraints.KeyConstraints) { ViewKeyConstraint viewConstraint = keyConstraint.Propagate(); if (viewConstraint != null) { propagatedConstraints.Add(viewConstraint); } } return(propagatedConstraints); }
// effects: Checks if all sViewConstraints are implied by the // constraints in cViewConstraints. If some S-level constraints are // not implied, adds errors/warnings to m_errorLog private void CheckImplication(ViewSchemaConstraints cViewConstraints, ViewSchemaConstraints sViewConstraints) { // Check key constraints // i.e., if S has a key <k1, k2>, C must have a key that is a subset of this CheckImplicationKeyConstraints(cViewConstraints, sViewConstraints); // For updates, we need to ensure the following: for every // extent E, table T pair, some key of E is implied by T's key // Get all key constraints for each extent and each table KeyToListMap <ExtentPair, ViewKeyConstraint> extentPairConstraints = new KeyToListMap <ExtentPair, ViewKeyConstraint>(EqualityComparer <ExtentPair> .Default); foreach (ViewKeyConstraint cKeyConstraint in cViewConstraints.KeyConstraints) { ExtentPair pair = new ExtentPair(cKeyConstraint.Cell.CQuery.Extent, cKeyConstraint.Cell.SQuery.Extent); extentPairConstraints.Add(pair, cKeyConstraint); } // Now check that we guarantee at least one constraint per // extent/table pair foreach (ExtentPair extentPair in extentPairConstraints.Keys) { ReadOnlyCollection <ViewKeyConstraint> cKeyConstraints = extentPairConstraints.ListForKey(extentPair); bool sImpliesSomeC = false; // Go through all key constraints for the extent/table pair, and find one that S implies foreach (ViewKeyConstraint cKeyConstraint in cKeyConstraints) { foreach (ViewKeyConstraint sKeyConstraint in sViewConstraints.KeyConstraints) { if (sKeyConstraint.Implies(cKeyConstraint)) { sImpliesSomeC = true; break; // The implication holds - so no problem } } } if (sImpliesSomeC == false) { // Indicate that at least one key must be ensured on the S-side m_errorLog.AddEntry(ViewKeyConstraint.GetErrorRecord(cKeyConstraints)); } } }
// effects: Performs the validation of the cells in this and returns // an error log of all the errors/warnings that were discovered internal ErrorLog Validate() { // Check for errors not checked by "C-implies-S principle" if (m_config.IsValidationEnabled) { if (PerformSingleCellChecks() == false) { return m_errorLog; } } else //Note that Metadata loading guarantees that DISTINCT flag is not present { // when update views (and validation) is disabled if (CheckCellsWithDistinctFlag() == false) { return m_errorLog; } } BasicSchemaConstraints cConstraints = new BasicSchemaConstraints(); BasicSchemaConstraints sConstraints = new BasicSchemaConstraints(); // Construct intermediate "view relations" and the basic cell // relations along with the basic constraints ConstructCellRelationsWithConstraints(cConstraints, sConstraints); if (m_config.IsVerboseTracing) { // Trace Basic constraints Trace.WriteLine(String.Empty); Trace.WriteLine("C-Level Basic Constraints"); Trace.WriteLine(cConstraints); Trace.WriteLine("S-Level Basic Constraints"); Trace.WriteLine(sConstraints); } // Propagate the constraints m_cViewConstraints = PropagateConstraints(cConstraints); m_sViewConstraints = PropagateConstraints(sConstraints); // Make some basic checks on the view and basic cell constraints CheckConstraintSanity(cConstraints, sConstraints, m_cViewConstraints, m_sViewConstraints); if (m_config.IsVerboseTracing) { // Trace View constraints Trace.WriteLine(String.Empty); Trace.WriteLine("C-Level View Constraints"); Trace.WriteLine(m_cViewConstraints); Trace.WriteLine("S-Level View Constraints"); Trace.WriteLine(m_sViewConstraints); } // Check for implication if (m_config.IsValidationEnabled) { CheckImplication(m_cViewConstraints, m_sViewConstraints); } return m_errorLog; }
// effects: Checks if all sViewConstraints are implied by the // constraints in cViewConstraints. If some S-level constraints are // not implied, adds errors/warnings to m_errorLog private void CheckImplication(ViewSchemaConstraints cViewConstraints, ViewSchemaConstraints sViewConstraints) { // Check key constraints // i.e., if S has a key <k1, k2>, C must have a key that is a subset of this CheckImplicationKeyConstraints(cViewConstraints, sViewConstraints); // For updates, we need to ensure the following: for every // extent E, table T pair, some key of E is implied by T's key // Get all key constraints for each extent and each table KeyToListMap<ExtentPair, ViewKeyConstraint> extentPairConstraints = new KeyToListMap<ExtentPair, ViewKeyConstraint>(EqualityComparer<ExtentPair>.Default); foreach (ViewKeyConstraint cKeyConstraint in cViewConstraints.KeyConstraints) { ExtentPair pair = new ExtentPair(cKeyConstraint.Cell.CQuery.Extent, cKeyConstraint.Cell.SQuery.Extent); extentPairConstraints.Add(pair, cKeyConstraint); } // Now check that we guarantee at least one constraint per // extent/table pair foreach (ExtentPair extentPair in extentPairConstraints.Keys) { ReadOnlyCollection<ViewKeyConstraint> cKeyConstraints = extentPairConstraints.ListForKey(extentPair); bool sImpliesSomeC = false; // Go through all key constraints for the extent/table pair, and find one that S implies foreach (ViewKeyConstraint cKeyConstraint in cKeyConstraints) { foreach (ViewKeyConstraint sKeyConstraint in sViewConstraints.KeyConstraints) { if (sKeyConstraint.Implies(cKeyConstraint)) { sImpliesSomeC = true; break; // The implication holds - so no problem } } } if (sImpliesSomeC == false) { // Indicate that at least one key must be ensured on the S-side m_errorLog.AddEntry(ViewKeyConstraint.GetErrorRecord(cKeyConstraints)); } } }
// effects: Propagates baseConstraints derived from the cellrelations // to the corresponding viewCellRelations and returns the list of // propagated constraints private static ViewSchemaConstraints PropagateConstraints(BasicSchemaConstraints baseConstraints) { ViewSchemaConstraints propagatedConstraints = new ViewSchemaConstraints(); // Key constraint propagation foreach (BasicKeyConstraint keyConstraint in baseConstraints.KeyConstraints) { ViewKeyConstraint viewConstraint = keyConstraint.Propagate(); if (viewConstraint != null) { propagatedConstraints.Add(viewConstraint); } } return propagatedConstraints; }