This commit is contained in:
christianwade 2016-12-19 00:43:00 -08:00
Родитель 5dad63c146
Коммит 3c5b1a1347
5 изменённых файлов: 167 добавлений и 8 удалений

Просмотреть файл

@ -9,13 +9,14 @@ namespace AsPartitionProcessing.SampleClient
{
InitializeInline,
InitializeFromDatabase,
MergePartitions
MergePartitions,
DefragPartitionedTables
}
class Program
{
//Set sample execution mode here:
const SampleExecutionMode ExecutionMode = SampleExecutionMode.InitializeInline;
const SampleExecutionMode ExecutionMode = SampleExecutionMode.InitializeInline;
static void Main(string[] args)
{
@ -46,6 +47,10 @@ namespace AsPartitionProcessing.SampleClient
{
PartitionProcessor.MergePartitions(modelConfig, LogMessage, "Internet Sales", Granularity.Yearly, "2012");
}
else if (ExecutionMode == SampleExecutionMode.DefragPartitionedTables)
{
PartitionProcessor.DefragPartitionedTables(modelConfig, LogMessage);
}
else
{
PartitionProcessor.PerformProcessing(modelConfig, LogMessage);
@ -57,8 +62,10 @@ namespace AsPartitionProcessing.SampleClient
Console.ForegroundColor = ConsoleColor.Red;
Console.WriteLine();
Console.WriteLine(exc.Message, null);
Console.WriteLine();
}
Console.ForegroundColor = ConsoleColor.White;
Console.WriteLine("Press any key to exit.");
Console.ReadKey();
}
@ -164,7 +171,10 @@ namespace AsPartitionProcessing.SampleClient
}
catch (Exception exc)
{
Console.ForegroundColor = ConsoleColor.Red;
Console.WriteLine(exc.Message);
Console.WriteLine();
Console.ForegroundColor = ConsoleColor.White;
Console.WriteLine("Press any key to exit.");
Console.ReadKey();
Environment.Exit(0); //Avoid recursion if errored connecting to db

Просмотреть файл

@ -52,13 +52,12 @@ namespace AsPartitionProcessing
List<ModelConfiguration> modelConfigs = new List<ModelConfiguration>();
ModelConfiguration modelConfig = null;
int currentModelConfigurationID = -1;
TableConfiguration tableConfig = null;
int currentTableConfigurationID = -1;
SqlDataReader reader = command.ExecuteReader();
while (reader.Read())
{
TableConfiguration tableConfig = null;
int currentTableConfigurationID = -1;
if (modelConfig == null || currentModelConfigurationID != Convert.ToInt32(reader["ModelConfigurationID"]))
{
modelConfig = new ModelConfiguration();

Просмотреть файл

@ -86,13 +86,17 @@ namespace AsPartitionProcessing
}
else
{
//Partitioned table. Process based on partitioning configuration(s).
//Validate multiple granularity ranges.
tableConfiguration.ValidatePartitioningConfigurations();
//Find template partition.
Partition templatePartition = table.Partitions.Find(tableConfiguration.AnalysisServicesTable);
if (templatePartition == null)
{
throw new InvalidOperationException($"Table {tableConfiguration.AnalysisServicesTable} does not contain a partition with the same name to act as the template partition.");
}
//Process based on partitioning configuration(s).
foreach (PartitioningConfiguration partitioningConfiguration in tableConfiguration.PartitioningConfigurations)
{
LogMessage("", false);
@ -207,6 +211,7 @@ namespace AsPartitionProcessing
{
LogMessage($"Inner exception message: {exc.InnerException.Message}", false);
}
LogMessage("", false);
}
finally
{
@ -350,6 +355,79 @@ namespace AsPartitionProcessing
}
}
/// <summary>
/// Defragment all partitions tables in a tabular model based on configuration
/// </summary>
/// <param name="modelConfiguration">Configuration info for the model</param>
/// <param name="messageLogger">Pointer to logging method</param>
public static void DefragPartitionedTables(ModelConfiguration modelConfiguration, LogMessageDelegate messageLogger)
{
_modelConfiguration = modelConfiguration;
_messageLogger = messageLogger;
Server server = new Server();
try
{
Database database;
Connect(server, out database);
Console.ForegroundColor = ConsoleColor.White;
LogMessage($"Start: {DateTime.Now.ToString("hh:mm:ss tt")}", false);
LogMessage($"Server: {_modelConfiguration.AnalysisServicesServer}", false);
LogMessage($"Database: {_modelConfiguration.AnalysisServicesDatabase}", false);
Console.ForegroundColor = ConsoleColor.Yellow;
LogMessage("", false);
LogMessage($"Defrag partitioned tables in database {_modelConfiguration.AnalysisServicesDatabase}", false);
LogMessage(new String('-', _modelConfiguration.AnalysisServicesDatabase.Length + 38), false);
LogMessage("", false);
LogMessage("=>Actions & progress:", false);
foreach (TableConfiguration tableConfiguration in _modelConfiguration.TableConfigurations)
{
//Only interested in partitoned tables
if (tableConfiguration.PartitioningConfigurations.Count > 0)
{
Table table = database.Model.Tables.Find(tableConfiguration.AnalysisServicesTable);
if (table == null)
{
throw new Microsoft.AnalysisServices.ConnectionException($"Could not connect to table {tableConfiguration.AnalysisServicesTable}.");
}
LogMessage($"Defrag table {tableConfiguration.AnalysisServicesTable} ...", true);
table.RequestRefresh(RefreshType.Defragment);
database.Model.SaveChanges();
}
}
Console.ForegroundColor = ConsoleColor.White;
LogMessage("", false);
LogMessage("Finish: " + DateTime.Now.ToString("hh:mm:ss tt"), false);
}
catch (Exception exc)
{
Console.ForegroundColor = ConsoleColor.Red;
LogMessage("", false);
LogMessage($"Exception occurred: {DateTime.Now.ToString("hh:mm:ss tt")}", false);
LogMessage($"Exception message: {exc.Message}", false);
if (exc.InnerException != null)
{
LogMessage($"Inner exception message: {exc.InnerException.Message}", false);
}
LogMessage("", false);
}
finally
{
try
{
_modelConfiguration = null;
_messageLogger = null;
if (server != null) server.Disconnect();
}
catch { }
}
}
#endregion
#region Private Methods

Просмотреть файл

@ -5,7 +5,7 @@ namespace AsPartitionProcessing
/// <summary>
/// Configuration information for partitioning of a table within an AS tabular model.
/// </summary>
public class PartitioningConfiguration
public class PartitioningConfiguration : IComparable<PartitioningConfiguration>
{
/// <summary>
/// ID of the PartitioningConfiguration table.
@ -101,8 +101,8 @@ namespace AsPartitionProcessing
default:
break;
}
}
public int CompareTo(PartitioningConfiguration other) => string.Compare(this.LowerBoundary.ToString("yyyy-MM-dd"), other.LowerBoundary.ToString("yyyy-MM-dd"));
}
/// <summary>

Просмотреть файл

@ -47,5 +47,77 @@ namespace AsPartitionProcessing
public TableConfiguration()
{
}
/// <summary>
/// Validate multiple granularities to ensure no overlapping ranges, etc.
/// </summary>
public void ValidatePartitioningConfigurations()
{
if (this.PartitioningConfigurations.Count > 1)
{
this.PartitioningConfigurations.Sort(); //Sorts by LowerBoundary value
DateTime previousUpperBoundary = DateTime.MinValue;
Granularity previousGranularity = Granularity.Daily;
bool foundDaily = false, foundMonthly = false, foundYearly = false;
foreach (PartitioningConfiguration partitioningConfiguration in this.PartitioningConfigurations)
{
#region Check don't have multiple partitioning configurations with same granularity
string multiSameGrainErrorMessage = $"Table {this.AnalysisServicesTable} contains multiple {{0}} partitioning configurations, which is not allowed.";
switch (partitioningConfiguration.Granularity)
{
case Granularity.Daily:
if (foundDaily)
{
throw new InvalidOperationException(string.Format(multiSameGrainErrorMessage, "daily"));
}
else
{
foundDaily = true;
}
break;
case Granularity.Monthly:
if (foundMonthly)
{
throw new InvalidOperationException(string.Format(multiSameGrainErrorMessage, "monthly"));
}
else
{
foundMonthly = true;
}
break;
case Granularity.Yearly:
if (foundYearly)
{
throw new InvalidOperationException(string.Format(multiSameGrainErrorMessage, "yearly"));
}
else
{
foundYearly = true;
}
break;
default:
break;
}
#endregion
#region Check don't have overlapping date ranges
if (partitioningConfiguration.LowerBoundary <= previousUpperBoundary)
{
throw new InvalidOperationException($"Table {this.AnalysisServicesTable} contains partitioning configurations with overlapping date ranges, which is not allowed. {previousGranularity.ToString()} upper boundary is {previousUpperBoundary.ToString("yyyy-MM-dd")}; {partitioningConfiguration.Granularity.ToString()} lower boundary is {partitioningConfiguration.LowerBoundary.ToString("yyyy-MM-dd")}.");
}
else
{
previousUpperBoundary = partitioningConfiguration.UpperBoundary;
previousGranularity = partitioningConfiguration.Granularity;
}
#endregion
}
}
}
}
}