in src/MIMConfigDocumenter/Documenter.cs [728:863]
protected static DataTable GetDiffgram(DataTable pilotTable, DataTable productionTable, int[] columnsIgnored)
{
Logger.Instance.WriteMethodEntry();
DataTable diffgramTable = CreateDiffgramTable(pilotTable);
try
{
if (columnsIgnored == null)
{
columnsIgnored = new int[] { -1 };
}
// Unchanged rows in pilotTable: pilotRow PrimaryKey matches productionRow PrimaryKey AND pilotRow also matches productionRow:
var unchangedPilotRows = from pilotRow in pilotTable.AsEnumerable()
from productionRow in productionTable.AsEnumerable()
where pilotTable.PrimaryKey.Aggregate(true, (match, keyColumn) => match && pilotRow[keyColumn].Equals(productionRow[keyColumn.Ordinal]))
&& pilotRow.ItemArray.Where((item, index) => !columnsIgnored.Contains(index)).SequenceEqual(productionRow.ItemArray.Where((item, index) => !columnsIgnored.Contains(index)))
select pilotRow;
// Unchanged rows in productionTable: pilotRow PrimaryKey matches productionRow PrimaryKey AND pilotRow also matches productionRow:
var unchangedProductionRows = from pilotRow in pilotTable.AsEnumerable()
from productionRow in productionTable.AsEnumerable()
where pilotTable.PrimaryKey.Aggregate(true, (match, keyColumn) => match && pilotRow[keyColumn].Equals(productionRow[keyColumn.Ordinal]))
&& pilotRow.ItemArray.Where((item, index) => !columnsIgnored.Contains(index)).SequenceEqual(productionRow.ItemArray.Where((item, index) => !columnsIgnored.Contains(index)))
select productionRow;
// Modified rows in pilotTable : pilotRow PrimaryKey matches productionRow PrimaryKey BUT pilotRow does not match productionRow:
var modifiedPilotRows = from pilotRow in pilotTable.AsEnumerable()
from productionRow in productionTable.AsEnumerable()
where pilotTable.PrimaryKey.Aggregate(true, (match, keyColumn) => match && pilotRow[keyColumn].Equals(productionRow[keyColumn.Ordinal]))
&& !pilotRow.ItemArray.Where((item, index) => !columnsIgnored.Contains(index)).SequenceEqual(productionRow.ItemArray.Where((item, index) => !columnsIgnored.Contains(index)))
select pilotRow;
// Modified rows in productionTable : pilotRow PrimaryKey matches productionRow PrimaryKey BUT pilotRow does not match productionRow:
var modifiedProductionRows = from pilotRow in pilotTable.AsEnumerable()
from productionRow in productionTable.AsEnumerable()
where pilotTable.PrimaryKey.Aggregate(true, (match, keyColumn) => match && pilotRow[keyColumn].Equals(productionRow[keyColumn.Ordinal]))
&& !pilotRow.ItemArray.Where((item, index) => !columnsIgnored.Contains(index)).SequenceEqual(productionRow.ItemArray.Where((item, index) => !columnsIgnored.Contains(index)))
select productionRow;
// Added rows : rows in pilotTable not modified AND not unchanged
var addedRows = pilotTable.AsEnumerable().Except(modifiedPilotRows, DataRowComparer.Default).Except(unchangedPilotRows, DataRowComparer.Default);
// Deleted rows : rows in productionTable not modified AND not unchanged
var deletedRows = productionTable.AsEnumerable().Except(modifiedProductionRows, DataRowComparer.Default).Except(unchangedProductionRows, DataRowComparer.Default);
// Populate unchanged rows
foreach (var row in unchangedPilotRows)
{
var newRow = diffgramTable.NewRow();
newRow[Documenter.RowStateColumn] = DataRowState.Unchanged;
foreach (DataColumn column in pilotTable.Columns)
{
newRow[column.ColumnName] = row[column.ColumnName];
}
Documenter.AddRow(diffgramTable, newRow);
}
// Populate modified rows
foreach (var row in modifiedPilotRows)
{
// Match the unmodified version of the row via the PrimaryKey
////var matchInProductionTable = modifiedProductionRows.Where(mondifiedProductionRow => productionTable.PrimaryKey.Aggregate(true, (match, keyColumn) => match && mondifiedProductionRow[keyColumn].Equals(row[keyColumn.Ordinal]))).First();
// revised query for perf improvements
var matchInProductionTable = (from productionRow in productionTable.AsEnumerable()
where productionTable.PrimaryKey.Aggregate(true, (match, keyColumn) => match && productionRow[keyColumn].Equals(row[keyColumn.Ordinal]))
select productionRow).First();
var newRow = diffgramTable.NewRow();
newRow[Documenter.RowStateColumn] = DataRowState.Modified;
// Set the row with the original values
foreach (DataColumn column in pilotTable.Columns)
{
if (!pilotTable.PrimaryKey.Contains(column))
{
newRow[Documenter.OldColumnPrefix + column.ColumnName] = matchInProductionTable[column.ColumnName];
}
}
// Set the modified values
foreach (DataColumn column in pilotTable.Columns)
{
newRow[column.ColumnName] = row[column.ColumnName];
}
Documenter.AddRow(diffgramTable, newRow);
}
// Populate added rows
foreach (var row in addedRows)
{
var newRow = diffgramTable.NewRow();
newRow[Documenter.RowStateColumn] = DataRowState.Added;
foreach (DataColumn column in pilotTable.Columns)
{
newRow[column.ColumnName] = row[column.ColumnName];
}
Documenter.AddRow(diffgramTable, newRow);
}
// Populate deleted rows
foreach (var row in deletedRows)
{
if (row.RowError == Documenter.VanityRow)
{
break;
}
var newRow = diffgramTable.NewRow();
newRow[Documenter.RowStateColumn] = DataRowState.Deleted;
foreach (DataColumn column in pilotTable.Columns)
{
if (!pilotTable.PrimaryKey.Contains(column))
{
newRow[column.ColumnName] = row[column.ColumnName]; // save the value in the orginal column as well in case it's used for Sorting table
newRow[Documenter.OldColumnPrefix + column.ColumnName] = row[column.ColumnName];
}
else
{
newRow[column.ColumnName] = row[column.ColumnName];
}
}
Documenter.AddRow(diffgramTable, newRow);
}
}
finally
{
Logger.Instance.WriteMethodExit();
}
return diffgramTable;
}