public List <Tuple <string, bool, List <string> > > GetTableDefinitions() { var consolidator = new DacpacConsolidator(); var dacpacPath = consolidator.Consolidate(_dacpacPath); using (var model = new TSqlTypedModel(dacpacPath)) { var result = model.GetObjects <TSqlTable>(DacQueryScopes.UserDefined) .Select(m => new Tuple <string, bool, List <string> >($"[{m.Name.Parts[0]}].[{m.Name.Parts[1]}]", m.PrimaryKeyConstraints.Any(), m.Columns.Where(i => !i.GetProperty <bool>(Column.IsHidden) && i.ColumnType != ColumnType.ColumnSet && i.ColumnType != ColumnType.ComputedColumn) .Select(c => c.Name.Parts[2]) .ToList())) .OrderBy(m => m.Item1) .ToList(); var views = model.GetObjects <TSqlView>(DacQueryScopes.UserDefined) .Select(m => new Tuple <string, bool, List <string> >($"[{m.Name.Parts[0]}].[{m.Name.Parts[1]}]", false, null)) .OrderBy(m => m.Item1) .ToList(); result = result.Concat(views).ToList(); return(result); } }
public DatabaseModel Create(string dacpacPath, DatabaseModelFactoryOptions options) { if (string.IsNullOrEmpty(dacpacPath)) { throw new ArgumentException(@"invalid path", nameof(dacpacPath)); } if (!File.Exists(dacpacPath)) { throw new ArgumentException("Dacpac file not found"); } var schemas = options.Schemas; var tables = options.Tables; var dbModel = new DatabaseModel { DatabaseName = Path.GetFileNameWithoutExtension(dacpacPath), DefaultSchema = schemas.Count() > 0 ? schemas.First() : "dbo" }; //Sequences not created - not needed for scaffolding var model = new TSqlTypedModel(dacpacPath); var typeAliases = GetTypeAliases(model, dbModel); var items = model.GetObjects <TSqlTable>(DacQueryScopes.UserDefined) .Where(t => !t.GetProperty <bool>(Table.IsAutoGeneratedHistoryTable)) .Where(t => tables == null || !tables.Any() || tables.Contains($"[{t.Name.Parts[0]}].[{t.Name.Parts[1]}]")) .Where(t => $"{t.Name.Parts[1]}" != HistoryRepository.DefaultTableName) .ToList(); foreach (var item in items) { var dbTable = new DatabaseTable { Name = item.Name.Parts[1], Schema = item.Name.Parts[0], }; if (item.MemoryOptimized) { dbTable["SqlServer:MemoryOptimized"] = true; } GetColumns(item, dbTable, typeAliases, model.GetObjects <TSqlDefaultConstraint>(DacQueryScopes.UserDefined).ToList()); GetPrimaryKey(item, dbTable); dbModel.Tables.Add(dbTable); } foreach (var item in items) { GetForeignKeys(item, dbModel); GetUniqueConstraints(item, dbModel); GetIndexes(item, dbModel); } return(dbModel); }
public void BasicInstantiation() { using (TSqlModel model = new TSqlModel(SqlServerVersion.Sql120, new TSqlModelOptions() { })) { string createTable = @" CREATE TABLE [dbo].[Table1] ( [Id] INT NOT NULL PRIMARY KEY ) "; string createCheck = @" ALTER TABLE [dbo].[Table1] ADD CONSTRAINT [check1] CHECK (1 > 0) "; model.AddObjects(createTable); model.AddObjects(createCheck); IEnumerable <TSqlObject> tables = model.GetObjects(DacQueryScopes.Default, Table.TypeClass); tables.Single().GetReferencing(View.BodyDependencies); TSqlTypedModel typedModel = new TSqlTypedModel(model); var genericTables = typedModel.GetObjects <TSqlTable>(DacQueryScopes.Default); var sql90Tables = typedModel.GetObjects <ISql90TSqlTable>(DacQueryScopes.Default); TSqlTable genericTable = genericTables.First(); ISql90TSqlTable sql90Table = sql90Tables.First(); IList <TSqlColumn> genericColumns = genericTable.Columns.ToList(); IList <ISql90TSqlColumn> sql90Columns = sql90Table.Columns.ToList(); Assert.AreEqual(genericColumns.Count, sql90Columns.Count, "Column counts should not be different between implementations"); // iterate of generic columns for (int i = 0; i < genericColumns.Count; i++) { TSqlColumn col = genericColumns[i]; ISql90TSqlColumn sql90Col = sql90Columns[i]; Assert.AreEqual(col.Collation, sql90Col.Collation, "Collation is not the same"); Assert.AreEqual(col.Expression, sql90Col.Expression, "Expression is not equal"); } Assert.AreEqual(2, genericTable.AllConstraints.Count(), "Incorrect number of constraints"); Assert.AreEqual(1, genericTable.CheckConstraints.Count(), "Incorrect number of check constraints"); Assert.AreEqual(1, genericTable.PrimaryKeyConstraints.Count(), "Incorrect number of Primary Key Constraints"); //TODO: Code gen the Reverse relationships for all explicitly implemented interfaces Assert.AreEqual(2, ((TSqlTable)sql90Table).AllConstraints.Count(), "Incorrect number of constraints"); Assert.AreEqual(1, ((TSqlTable)sql90Table).CheckConstraints.Count(), "Incorrect number of check constraints"); Assert.AreEqual(1, ((TSqlTable)sql90Table).PrimaryKeyConstraints.Count(), "Incorrect number of Primary Key Constraints"); } }
public void BasicInstantiation() { using (TSqlModel model = new TSqlModel(SqlServerVersion.Sql120, new TSqlModelOptions() { })) { string createTable = @" CREATE TABLE [dbo].[Table1] ( [Id] INT NOT NULL PRIMARY KEY ) "; string createCheck = @" ALTER TABLE [dbo].[Table1] ADD CONSTRAINT [check1] CHECK (1 > 0) "; model.AddObjects(createTable); model.AddObjects(createCheck); IEnumerable<TSqlObject> tables = model.GetObjects(DacQueryScopes.Default, Table.TypeClass); tables.Single().GetReferencing(View.BodyDependencies); TSqlTypedModel typedModel = new TSqlTypedModel(model); var genericTables = typedModel.GetObjects<TSqlTable>(DacQueryScopes.Default); var sql90Tables = typedModel.GetObjects<ISql90TSqlTable>(DacQueryScopes.Default); TSqlTable genericTable = genericTables.First(); ISql90TSqlTable sql90Table = sql90Tables.First(); IList<TSqlColumn> genericColumns = genericTable.Columns.ToList(); IList<ISql90TSqlColumn> sql90Columns = sql90Table.Columns.ToList(); Assert.AreEqual(genericColumns.Count, sql90Columns.Count, "Column counts should not be different between implementations"); // iterate of generic columns for (int i = 0; i < genericColumns.Count; i++) { TSqlColumn col = genericColumns[i]; ISql90TSqlColumn sql90Col = sql90Columns[i]; Assert.AreEqual(ColumnType.Column, col.ColumnType, "Invalid metadata ColumnType"); Assert.AreEqual(col.Collation, sql90Col.Collation, "Collation is not the same"); Assert.AreEqual(col.Expression, sql90Col.Expression, "Expression is not equal"); } Assert.AreEqual(2, genericTable.AllConstraints.Count(), "Incorrect number of constraints"); Assert.AreEqual(1, genericTable.CheckConstraints.Count(), "Incorrect number of check constraints"); Assert.AreEqual(1, genericTable.PrimaryKeyConstraints.Count(), "Incorrect number of Primary Key Constraints"); //TODO: Code gen the Reverse relationships for all explicitly implemented interfaces Assert.AreEqual(2, ((TSqlTable)sql90Table).AllConstraints.Count(), "Incorrect number of constraints"); Assert.AreEqual(1, ((TSqlTable)sql90Table).CheckConstraints.Count(), "Incorrect number of check constraints"); Assert.AreEqual(1, ((TSqlTable)sql90Table).PrimaryKeyConstraints.Count(), "Incorrect number of Primary Key Constraints"); } }
/// <summary> /// Checks to see if there are any foreign keys defined on user objects. We can use this in calling app /// to flag a message that the diagram may be generated without any relationships as there are no /// foreign keys to infer them from /// </summary> public bool CheckModel() { var rels = model.GetObjects <TSqlForeignKeyConstraint>(DacQueryScopes.UserDefined); var strOut = new StringBuilder(); if (rels.Count() == 0) { return(false); } else { return(true); } }
private ProcedureModel GetStoredProcedures(string dacpacPath, ProcedureModelFactoryOptions options) { var result = new List <RevEng.Core.Abstractions.Metadata.Procedure>(); var errors = new List <string>(); if (options.FullModel && !options.Procedures.Any()) { return(new ProcedureModel { Procedures = result, Errors = errors, }); } var consolidator = new DacpacConsolidator(); dacpacPath = consolidator.Consolidate(dacpacPath); var model = new TSqlTypedModel(dacpacPath); var procedures = model.GetObjects <TSqlProcedure>(DacQueryScopes.UserDefined) .ToList(); var filter = new HashSet <string>(options.Procedures); foreach (var proc in procedures) { var procedure = new RevEng.Core.Abstractions.Metadata.Procedure { Schema = proc.Name.Parts[0], Name = proc.Name.Parts[1], }; if (filter.Count == 0 || filter.Contains($"[{procedure.Schema}].[{procedure.Name}]")) { if (options.FullModel) { procedure.Parameters = GetStoredProcedureParameters(proc); try { procedure.ResultElements = GetStoredProcedureResultElements(proc); } catch (Exception ex) { errors.Add($"Unable to get result set shape for {procedure.Schema}.{procedure.Name}" + Environment.NewLine + ex.Message); _logger?.Logger.LogWarning(ex, $"Unable to get result set shape for {procedure.Schema}.{procedure.Name}" + Environment.NewLine + ex.Message); } } result.Add(procedure); } } return(new ProcedureModel { Procedures = result, Errors = errors, }); }
public List <TableInformation> GetTableDefinitions() { var model = new TSqlTypedModel(_dacpacPath); return(model.GetObjects <TSqlTable>(DacQueryScopes.UserDefined) .Select(m => new TableInformation(m.Name.Parts[0], m.Name.Parts[1], m.PrimaryKeyConstraints.Any())) .ToList()); }
public List <TableInformationModel> GetTableDefinitions(bool includeViews = false) { var model = new TSqlTypedModel(_dacpacPath); var result = model.GetObjects <TSqlTable>(DacQueryScopes.UserDefined) .Select(m => new TableInformationModel(m.Name.Parts[0] + "." + m.Name.Parts[1], m.PrimaryKeyConstraints.Any())) .ToList(); if (includeViews) { var views = model.GetObjects <TSqlView>(DacQueryScopes.UserDefined) .Select(m => new TableInformationModel(m.Name.Parts[0] + "." + m.Name.Parts[1], false)) .ToList(); result = result.Concat(views).ToList(); } return(result); }
public List <TableInformationModel> GetTableDefinitions() { using (var model = new TSqlTypedModel(_dacpacPath)) { var result = model.GetObjects <TSqlTable>(DacQueryScopes.UserDefined) .Select(m => new TableInformationModel($"[{m.Name.Parts[0]}].[{m.Name.Parts[1]}]", m.PrimaryKeyConstraints.Any(), false)) .ToList(); return(result); } }
public List <Tuple <string, bool> > GetTableDefinitions() { var consolidator = new DacpacConsolidator(); var dacpacPath = consolidator.Consolidate(_dacpacPath); using (var model = new TSqlTypedModel(dacpacPath)) { var result = model.GetObjects <TSqlTable>(DacQueryScopes.UserDefined) .Select(m => new Tuple <string, bool>($"[{m.Name.Parts[0]}].[{m.Name.Parts[1]}]", m.PrimaryKeyConstraints.Any())) .OrderBy(m => m.Item1) .ToList(); var views = model.GetObjects <TSqlView>(DacQueryScopes.UserDefined) .Select(m => new Tuple <string, bool>($"[{m.Name.Parts[0]}].[{m.Name.Parts[1]}]", false)) .OrderBy(m => m.Item1) .ToList(); result = result.Concat(views).ToList(); return(result); } }
public List <TableInformationModel> GetTableDefinitions(bool includeViews) { var consolidator = new DacpacConsolidate.DacpacConsolidator(); var dacpacPath = consolidator.Consolidate(_dacpacPath); using (var model = new TSqlTypedModel(dacpacPath)) { var result = model.GetObjects <TSqlTable>(DacQueryScopes.UserDefined) .Select(m => new TableInformationModel($"[{m.Name.Parts[0]}].[{m.Name.Parts[1]}]", m.PrimaryKeyConstraints.Any(), false)) .ToList(); if (includeViews) { var views = model.GetObjects <TSqlView>(DacQueryScopes.UserDefined) .Select(m => new TableInformationModel($"[{m.Name.Parts[0]}].[{m.Name.Parts[1]}]", true, true)) .ToList(); result = result.Concat(views).ToList(); } return(result); } }
public List <string> GetTableNames() { var names = new List <string>(); var model = new TSqlTypedModel(_dacpacPath); var tables = model.GetObjects <TSqlTable>(DacQueryScopes.UserDefined) .Where(t => t.PrimaryKeyConstraints.Count() > 0) .ToList(); foreach (var table in tables) { names.Add($"{table.Name.Parts[0]}.{table.Name.Parts[1]}"); } return(names); }
private IReadOnlyDictionary <string, (string, string)> GetTypeAliases(TSqlTypedModel model, DatabaseModel dbModel) { var items = model.GetObjects <TSqlDataType>(DacQueryScopes.UserDefined) .ToList(); var typeAliasMap = new Dictionary <string, (string, string)>(StringComparer.OrdinalIgnoreCase); foreach (var udt in items) { int maxLength = udt.UddtIsMax ? -1 : udt.UddtLength; var storeType = GetStoreType(udt.Type.First().Name.Parts[0], maxLength, udt.UddtPrecision, udt.UddtScale); typeAliasMap.Add($"{udt.Name.Parts[0]}.{udt.Name.Parts[1]}", (storeType, udt.Type.First().Name.Parts[0])); } return(typeAliasMap); }
public void TestFullTextIndex() { using (var model = new TSqlTypedModel(SqlServerVersion.Sql120, new TSqlModelOptions() { })) { string createIndex = @"CREATE UNIQUE INDEX ui_ukJobCand ON HumanResources.JobCandidate(JobCandidateID)"; string createCatalog = "CREATE FULLTEXT CATALOG ft AS DEFAULT"; string createFTIIndex = @" CREATE FULLTEXT INDEX ON HumanResources.JobCandidate(Resume) KEY INDEX ui_ukJobCand WITH STOPLIST = SYSTEM"; model.AddObjects(createIndex); model.AddObjects(createCatalog); model.AddObjects(createFTIIndex); var indexes = model.GetObjects<TSqlFullTextIndex>(DacQueryScopes.UserDefined).ToList(); Assert.AreEqual(1, indexes.Count, "Incorrect number of full Text Indexes"); TSqlFullTextIndex ftIndex = indexes[0]; var ftColumns = ftIndex.Columns.ToList(); Assert.AreEqual(1, ftColumns.Count, "Incorrect number of columns"); } }
private static void Main(string[] args) { if (!CheckArgs(args)) return; var model = new TSqlTypedModel(args[0]); var outputFolder = args[1]; var schemaDir = CreateDirectory(outputFolder, "Schema"); var procDir = CreateDirectory(outputFolder, "Tests"); var procedures = model.GetObjects<TSqlProcedure>(DacQueryScopes.UserDefined); foreach (var procedure in procedures) { var schema = GenerateSchema(procedure); var test = GenerateTest(procedure); using (var writer = new StreamWriter(Path.Combine(schemaDir, procedure.Name.Parts.Last() + ".sql"))) { writer.Write(schema); } using ( var writer = new StreamWriter(Path.Combine(procDir, procedure.Name.Parts.Last() + "." + "test To Be Implemented.sql"))) { writer.Write(test); } } }
private static RoutineModel GetStoredProcedures(string dacpacPath, ModuleModelFactoryOptions options, bool mergeDacpacs) { var result = new List <RevEng.Core.Abstractions.Metadata.Procedure>(); var errors = new List <string>(); if (mergeDacpacs && dacpacPath != null) { var consolidator = new DacpacConsolidator(); dacpacPath = consolidator.Consolidate(dacpacPath); } using var model = new TSqlTypedModel(dacpacPath); var procedures = model.GetObjects <TSqlProcedure>(DacQueryScopes.UserDefined) .ToList(); var filter = new HashSet <string>(options.Modules); foreach (var proc in procedures) { var procedure = new RevEng.Core.Abstractions.Metadata.Procedure { Schema = proc.Name.Parts[0], Name = proc.Name.Parts[1], }; var key = $"[{procedure.Schema}].[{procedure.Name}]"; if (filter.Count == 0 || filter.Contains(key)) { if (options.FullModel) { procedure.Parameters = GetStoredProcedureParameters(proc); if (options.MappedModules?.ContainsKey(key) ?? false) { procedure.MappedType = options.MappedModules[key]; } #pragma warning disable CA1031 // Do not catch general exception types try { procedure.Results.Add(GetStoredProcedureResultElements(proc)); } catch (Exception ex) { errors.Add($"Unable to get result set shape for {procedure.Schema}.{procedure.Name}" + Environment.NewLine + ex.ToString()); } #pragma warning restore CA1031 // Do not catch general exception types } result.Add(procedure); } } return(new RoutineModel { Routines = result.Cast <Routine>().ToList(), Errors = errors, }); }
public DatabaseModel Create(string dacpacPath, DatabaseModelFactoryOptions options) { if (string.IsNullOrEmpty(dacpacPath)) { throw new ArgumentException(@"invalid path", nameof(dacpacPath)); } if (!File.Exists(dacpacPath)) { throw new ArgumentException("Dacpac file not found"); } var schemas = options.Schemas; var tables = options.Tables; var dbModel = new DatabaseModel { DatabaseName = Path.GetFileNameWithoutExtension(dacpacPath), DefaultSchema = schemas.Count() > 0 ? schemas.First() : "dbo" }; dbModel["Scaffolding:ConnectionString"] = $"Data Source=(local);Initial Catalog={dbModel.DatabaseName};Integrated Security=true"; //Sequences not created - not needed for scaffolding var consolidator = new DacpacConsolidator(); dacpacPath = consolidator.Consolidate(dacpacPath); var model = new TSqlTypedModel(dacpacPath); var typeAliases = GetTypeAliases(model, dbModel); var items = model.GetObjects <TSqlTable>(DacQueryScopes.UserDefined) .Where(t => !t.GetProperty <bool>(Table.IsAutoGeneratedHistoryTable)) .Where(t => tables == null || !tables.Any() || tables.Contains($"[{t.Name.Parts[0]}].[{t.Name.Parts[1]}]")) .Where(t => $"{t.Name.Parts[1]}" != HistoryRepository.DefaultTableName) .ToList(); foreach (var item in items) { var dbTable = new DatabaseTable { Name = item.Name.Parts[1], Schema = item.Name.Parts[0], }; if (item.MemoryOptimized) { dbTable["SqlServer:MemoryOptimized"] = true; } GetColumns(item, dbTable, typeAliases, model.GetObjects <TSqlDefaultConstraint>(DacQueryScopes.UserDefined).ToList(), model); GetPrimaryKey(item, dbTable); var description = model.GetObjects <TSqlExtendedProperty>(DacQueryScopes.UserDefined) .Where(p => p.Name.Parts.Count == 4) .Where(p => p.Name.Parts[0] == "SqlTableBase") .Where(p => p.Name.Parts[1] == dbTable.Schema) .Where(p => p.Name.Parts[2] == dbTable.Name) .Where(p => p.Name.Parts[3] == "MS_Description") .FirstOrDefault(); dbTable.Comment = FixExtendedPropertyValue(description?.Value); dbModel.Tables.Add(dbTable); } foreach (var item in items) { GetForeignKeys(item, dbModel); GetUniqueConstraints(item, dbModel); GetIndexes(item, dbModel); } var views = model.GetObjects <TSqlView>(DacQueryScopes.UserDefined) .Where(t => tables == null || !tables.Any() || tables.Contains($"[{t.Name.Parts[0]}].[{t.Name.Parts[1]}]")) .ToList(); foreach (var view in views) { var dbView = new DatabaseTable { Name = view.Name.Parts[1], Schema = view.Name.Parts[0], }; GetViewColumns(view, dbView, typeAliases); dbModel.Tables.Add(dbView); } return(dbModel); }
public void TestTableColumnMetadataProperties() { using (TSqlTypedModel model = new TSqlTypedModel(SqlServerVersion.Sql120, new TSqlModelOptions() { })) { string createTable = @" CREATE TABLE [dbo].[Table1] ( [Id] INT NOT NULL, [two] AS (ID +1), columnSet1 int sparse, columnSet2 int sparse, cs xml column_set for all_sparse_columns ) "; model.AddObjects(createTable); List<TSqlTable> tables = model.GetObjects<TSqlTable>(DacQueryScopes.Default).ToList(); Assert.AreEqual(1, tables.Count(), "Incorrect number of tables"); List<TSqlColumn> columns = tables[0].Columns.ToList(); TSqlColumn col = columns[0]; Assert.AreEqual(ColumnType.Column, col.ColumnType, "Incorrect ColumnType Metadata for column " + col.Name.Parts[2]); col = columns[1]; Assert.AreEqual(ColumnType.ComputedColumn, col.ColumnType, "Incorrect ColumnType Metadata for column " + col.Name.Parts[2]); col = columns[2]; Assert.AreEqual(ColumnType.Column, col.ColumnType, "Incorrect ColumnType Metadata for column " + col.Name.Parts[2]); col = columns[3]; Assert.AreEqual(ColumnType.Column, col.ColumnType, "Incorrect ColumnType Metadata for column " + col.Name.Parts[2]); col = columns[4]; Assert.AreEqual(ColumnType.ColumnSet, col.ColumnType, "Incorrect ColumnType Metadata for column " + col.Name.Parts[2]); } }
public void TestSignatures() { using (TSqlTypedModel model = new TSqlTypedModel(SqlServerVersion.Sql120, new TSqlModelOptions() { })) { model.AddObjects(@"CREATE CERTIFICATE cert_signature_demo ENCRYPTION BY PASSWORD = '******' WITH SUBJECT = 'ADD SIGNATURE demo';"); model.AddObjects(@"CREATE PROC [sp_signature_demo] AS PRINT 'This is the content of the procedure.' ; GO"); model.AddObjects(@"ADD SIGNATURE TO [sp_signature_demo] BY CERTIFICATE [cert_signature_demo] WITH PASSWORD = '******' ;"); var signatures = model.GetObjects<TSqlSignature>( DacQueryScopes.UserDefined); var signature = signatures.First(); TSqlSignatureEncryptionMechanism encryption = signature.EncryptionMechanism.FirstOrDefault() as TSqlSignatureEncryptionMechanism; Assert.IsNotNull(encryption, " Encryption Mechanism is null or missing"); Assert.AreEqual(1, encryption.Certificate.Count(), "Missing Certificate on signature"); TSqlCertificateReference certifcate = encryption.Certificate.First() as TSqlCertificateReference; Assert.AreEqual("ADD SIGNATURE demo", certifcate.Subject, "Incorrect Subject"); } }
public void TestFullTextIndexWithTypeColumn() { using (var model = new TSqlTypedModel(SqlServerVersion.Sql120, new TSqlModelOptions() { })) { string createIndex = @"CREATE FULLTEXT INDEX ON Production.Document ( Title Language 1033, DocumentSummary Language 1033, Document TYPE COLUMN FileExtension Language 1033 ) KEY INDEX PK_Document_DocumentID WITH STOPLIST = SYSTEM, SEARCH PROPERTY LIST = DocumentPropertyList, CHANGE_TRACKING OFF, NO POPULATION"; model.AddObjects(createIndex); var tc = Column.TypeClass; var indexes = model.GetObjects<TSqlFullTextIndex>(DacQueryScopes.UserDefined).ToList(); Assert.AreEqual(1, indexes.Count, "Incorrect number of full Text Indexes"); TSqlFullTextIndex ftIndex = indexes[0]; var ftColumns = ftIndex.Columns.ToList(); Assert.AreEqual(3, ftColumns.Count, "Incorrect number of columns"); } }