public async Task CanMigrateEmbedOnParent(MigrationProvider provider) { using (WithSqlDatabase(provider, out var connectionString, out string schemaName, "basic")) { var driver = DatabaseDriverDispatcher.CreateDriver(provider, connectionString); using (var store = GetDocumentStore()) { var collection = new RootCollection(schemaName, "order", "Orders") { NestedCollections = new List <EmbeddedCollection> { new EmbeddedCollection(schemaName, "order_item", RelationType.OneToMany, new List <string> { "order_id" }, "Items") } }; var db = await GetDocumentDatabaseInstanceFor(store); var settings = new MigrationSettings { Collections = new List <RootCollection> { collection } }; using (var cts = new CancellationTokenSource(TimeSpan.FromMinutes(1))) using (db.DocumentsStorage.ContextPool.AllocateOperationContext(out DocumentsOperationContext context)) { var schema = driver.FindSchema(); ApplyDefaultColumnNamesMapping(schema, settings); await driver.Migrate(settings, schema, db, context, token : cts.Token); } using (var session = store.OpenSession()) { var order = session.Load <JObject>("Orders/1"); Assert.NotNull(order); // total and metadata, Id (Orders/1), Items Assert.Equal(4, order.Properties().Count()); Assert.Equal("Orders", order["@metadata"]["@collection"]); Assert.Equal(440, order["Total"]); Assert.Equal("Orders/1", order["Id"]); var firstItem = order["Items"][0]; Assert.Equal(110, firstItem["Price"]); Assert.Equal(1, firstItem.Count()); var secondItem = order["Items"][1]; Assert.Equal(330, secondItem["Price"]); Assert.Equal(1, secondItem.Count()); } var collectionStatistics = store.Maintenance.Send(new GetCollectionStatisticsOperation()); Assert.Equal(1, collectionStatistics.CountOfDocuments); } } }
public async Task Attachments(MigrationProvider provider) { using (WithSqlDatabase(provider, out var connectionString, out string schemaName, "basic")) { var driver = DatabaseDriverDispatcher.CreateDriver(provider, connectionString); using (var store = GetDocumentStore()) { var db = await GetDocumentDatabaseInstanceFor(store); var settings = new MigrationSettings { Collections = new List <RootCollection> { new RootCollection(schemaName, "actor", "Actors") { NestedCollections = new List <EmbeddedCollection> { new EmbeddedCollection(schemaName, "actor_movie", RelationType.OneToMany, new List <string> { "a_id" }, "Movies") { NestedCollections = new List <EmbeddedCollection> { new EmbeddedCollection(schemaName, "movie", RelationType.ManyToOne, new List <string> { "m_id" }, "Movie") } } } } } }; using (db.DocumentsStorage.ContextPool.AllocateOperationContext(out DocumentsOperationContext context)) { var schema = driver.FindSchema(); ApplyDefaultColumnNamesMapping(schema, settings, true); await driver.Migrate(settings, schema, db, context); } using (var session = store.OpenSession()) { var actor32 = session.Load <JObject>("Actors/32"); Assert.False(actor32.ContainsKey("Photo")); Assert.False(actor32.ContainsKey("photo")); var attachments = session.Advanced.Attachments.GetNames(actor32) .Select(x => x.Name) .OrderBy(x => x) .ToArray(); Assert.Equal(new[] { "Movies_0_Movie_File", "Movies_1_Movie_File", "Photo" }, attachments); var actor34 = session.Load <JObject>("Actors/34"); Assert.False(actor34.ContainsKey("Photo")); Assert.False(actor34.ContainsKey("photo")); Assert.Equal(0, session.Advanced.Attachments.GetNames(actor34).Length); } } } }
public async Task CanTestWithSkip(MigrationProvider provider) { using (WithSqlDatabase(provider, out var connectionString, out string schemaName, "basic")) { var driver = DatabaseDriverDispatcher.CreateDriver(provider, connectionString); using (var store = GetDocumentStore()) { var db = await GetDocumentDatabaseInstanceFor(store); var settings = new MigrationTestSettings { Collection = new RootCollection(schemaName, "order", "Orders") { Patch = "throw 'skip';" } }; using (db.DocumentsStorage.ContextPool.AllocateOperationContext(out DocumentsOperationContext context)) { var schema = driver.FindSchema(); ApplyDefaultColumnNamesMapping(schema, settings.Collection, settings.BinaryToAttachment); var exception = Assert.Throws <InvalidOperationException>(() => { driver.Test(settings, schema, context); }); Assert.True(exception.Message.StartsWith("Document was skipped")); } } } }
public async Task CanLimitRows(MigrationProvider provider) { using (WithSqlDatabase(provider, out var connectionString, out string schemaName, "basic")) { var driver = DatabaseDriverDispatcher.CreateDriver(provider, connectionString); using (var store = GetDocumentStore()) { var db = await GetDocumentDatabaseInstanceFor(store); var settings = new MigrationSettings { Collections = new List <RootCollection> { new RootCollection(schemaName, "movie", "Movies") }, MaxRowsPerTable = 2 }; using (db.DocumentsStorage.ContextPool.AllocateOperationContext(out DocumentsOperationContext context)) { var schema = driver.FindSchema(); ApplyDefaultColumnNamesMapping(schema, settings); await driver.Migrate(settings, schema, db, context); } using (var session = store.OpenSession()) { Assert.Equal(2, session.Advanced.LoadStartingWith <JObject>("Movies/").Length); } } } }
public async Task CanTestWithPrimaryKeyValues(MigrationProvider provider) { const string tableName = "groups1"; const string collectionName = "Groups1"; using (WithSqlDatabase(provider, out var connectionString, out string schemaName, "basic")) { var driver = DatabaseDriverDispatcher.CreateDriver(provider, connectionString); using (var store = GetDocumentStore()) { var db = await GetDocumentDatabaseInstanceFor(store); var settings = new MigrationTestSettings { Collection = new RootCollection(schemaName, tableName, collectionName), Mode = MigrationTestMode.ByPrimaryKey, PrimaryKeyValues = new[] { "52" } }; using (db.DocumentsStorage.ContextPool.AllocateOperationContext(out DocumentsOperationContext context)) { var schema = driver.FindSchema(); ApplyDefaultColumnNamesMapping(schema, settings.Collection, settings.BinaryToAttachment); var(document, id) = driver.Test(settings, schema, context); Assert.Equal($"{collectionName}/52", id); Assert.True(document.TryGet("Name", out string name)); Assert.Equal("G1.1.1", name); } } } }
public async Task CanEmbedOnParent(MigrationProvider provider) { const string tableName = "groups1"; const string collectionName = "Groups1"; using (WithSqlDatabase(provider, out var connectionString, out string schemaName, "basic")) { var driver = DatabaseDriverDispatcher.CreateDriver(provider, connectionString); using (var store = GetDocumentStore()) { var db = await GetDocumentDatabaseInstanceFor(store); var settings = new MigrationSettings { Collections = new List <RootCollection> { new RootCollection(schemaName, tableName, collectionName) { NestedCollections = new List <EmbeddedCollection> { new EmbeddedCollection(schemaName, tableName, RelationType.ManyToOne, new List <string> { "parent_group_id" }, "Parent") { NestedCollections = new List <EmbeddedCollection> { new EmbeddedCollection(schemaName, tableName, RelationType.ManyToOne, new List <string> { "parent_group_id" }, "Grandparent") } } } } } }; using (db.DocumentsStorage.ContextPool.AllocateOperationContext(out DocumentsOperationContext context)) { var schema = driver.FindSchema(); ApplyDefaultColumnNamesMapping(schema, settings); await driver.Migrate(settings, schema, db, context); } using (var session = store.OpenSession()) { var group = session.Load <JObject>($"{collectionName}/53"); Assert.Equal("G1.1.1.1", group["Name"]); var parent = group["Parent"]; Assert.NotNull(parent); Assert.Equal("G1.1.1", parent["Name"]); var grandparent = parent["Grandparent"]; Assert.NotNull(grandparent); Assert.Equal("G1.1", grandparent["Name"]); } var collectionStatistics = store.Maintenance.Send(new GetCollectionStatisticsOperation()); Assert.Equal(7, collectionStatistics.CountOfDocuments); } } }
public async Task CanMigrateEmbedOnChild(MigrationProvider provider) { using (WithSqlDatabase(provider, out var connectionString, out string schemaName, "basic")) { var driver = DatabaseDriverDispatcher.CreateDriver(provider, connectionString); using (var store = GetDocumentStore()) { var collection = new RootCollection(schemaName, "order_item", "OrderItems") { NestedCollections = new List <EmbeddedCollection> { new EmbeddedCollection(schemaName, "order", RelationType.ManyToOne, new List <string> { "order_id" }, "Order") } }; var db = await GetDocumentDatabaseInstanceFor(store); var settings = new MigrationSettings { Collections = new List <RootCollection> { collection } }; using (db.DocumentsStorage.ContextPool.AllocateOperationContext(out DocumentsOperationContext context)) { var schema = driver.FindSchema(); ApplyDefaultColumnNamesMapping(schema, settings); await driver.Migrate(settings, schema, db, context); } using (var session = store.OpenSession()) { var orderItem = session.Load <JObject>("OrderItems/10"); Assert.NotNull(orderItem); // price and metadata, Id (OrderItems/10), Order Assert.Equal(4, orderItem.Properties().Count()); Assert.Equal("OrderItems", orderItem["@metadata"]["@collection"]); Assert.Equal(110, orderItem["Price"]); Assert.Equal("OrderItems/10", orderItem["Id"]); var nestedOrder = orderItem["Order"]; Assert.NotNull(nestedOrder); Assert.Equal(1, nestedOrder.Count()); Assert.Equal(440, nestedOrder["Total"]); var orderItem2 = session.Load <JObject>("OrderItems/11"); Assert.NotNull(orderItem2); } var collectionStatistics = store.Maintenance.Send(new GetCollectionStatisticsOperation()); Assert.Equal(2, collectionStatistics.CountOfDocuments); } } }
public async Task BinaryAsNoAttachment(MigrationProvider provider) { using (WithSqlDatabase(provider, out var connectionString, out string schemaName, "basic")) { var driver = DatabaseDriverDispatcher.CreateDriver(provider, connectionString); using (var store = GetDocumentStore()) { var db = await GetDocumentDatabaseInstanceFor(store); var settings = new MigrationSettings { Collections = new List <RootCollection> { new RootCollection(schemaName, "actor", "Actors") { NestedCollections = new List <EmbeddedCollection> { new EmbeddedCollection(schemaName, "actor_movie", RelationType.OneToMany, new List <string> { "a_id" }, "Movies") { NestedCollections = new List <EmbeddedCollection> { new EmbeddedCollection(schemaName, "movie", RelationType.ManyToOne, new List <string> { "m_id" }, "Movie") } } } } } }; using (var cts = new CancellationTokenSource(TimeSpan.FromMinutes(1))) using (db.DocumentsStorage.ContextPool.AllocateOperationContext(out DocumentsOperationContext context)) { var schema = driver.FindSchema(); ApplyDefaultColumnNamesMapping(schema, settings, binaryToAttachment: false); await driver.Migrate(settings, schema, db, context, token : cts.Token); } using (var session = store.OpenSession()) { var actor32 = session.Load <JObject>("Actors/32"); Assert.Equal(0, session.Advanced.Attachments.GetNames(actor32).Length); Assert.Equal("MzI=", actor32["Photo"]); Assert.Equal("MjE=", actor32["Movies"][0]["Movie"]["File"]); Assert.Equal("MjM=", actor32["Movies"][1]["Movie"]["File"]); Assert.Equal(JTokenType.Null, actor32["Movies"][2]["Movie"]["File"].Type); var actor34 = session.Load <JObject>("Actors/34"); Assert.Equal(0, session.Advanced.Attachments.GetNames(actor34).Length); Assert.Equal(JTokenType.Null, actor34["Photo"].Type); } } } }
public void CanFetchSchema() { using (WithSqlDatabase(MigrationProvider.MsSQL, out var connectionString, out string schemaName, includeData: false)) { var driver = DatabaseDriverDispatcher.CreateDriver(MigrationProvider.MsSQL, connectionString); var schema = driver.FindSchema(); Assert.NotNull(schema.CatalogName); Assert.Equal(10, schema.Tables.Count); // validate NoPkTable var tables = schema.Tables; var noPkTable = tables.First(x => x.TableName == "NoPkTable"); Assert.NotNull(noPkTable); Assert.Equal(new[] { "Id" }, noPkTable.Columns.Select(x => x.Name).ToList()); Assert.Equal(0, noPkTable.PrimaryKeyColumns.Count); // validate Order Table var orderTable = tables.First(x => x.TableName == "Order"); Assert.Equal(4, orderTable.Columns.Count); Assert.Equal(new[] { "Id", "OrderDate", "CustomerId", "TotalAmount" }, orderTable.Columns.Select(x => x.Name).ToList()); Assert.Equal(new[] { "Id" }, orderTable.PrimaryKeyColumns); var orderReferences = orderTable.References; Assert.Equal(1, orderReferences.Count); Assert.Equal("OrderItem", orderReferences[0].Table); Assert.Equal(new[] { "OrderId" }, orderReferences[0].Columns); // validate UnsupportedTable var unsupportedTable = tables.First(x => x.TableName == "UnsupportedTable"); Assert.True(unsupportedTable.Columns.Any(x => x.Type == ColumnType.Unsupported)); // validate OrderItem (2 columns in PK) var orderItemTable = tables.First(x => x.TableName == "OrderItem"); Assert.Equal(new[] { "OrderId", "ProductId" }, orderItemTable.PrimaryKeyColumns); Assert.Equal(1, orderItemTable.References.Count); Assert.Equal("Details", orderItemTable.References[0].Table); Assert.Equal(new[] { "OrderId", "ProductId" }, orderItemTable.References[0].Columns); // all types are supported (except UnsupportedTable) Assert.True(tables.Where(x => x.TableName != "UnsupportedTable") .All(x => x.Columns.All(y => y.Type != ColumnType.Unsupported))); // validate many - to - many var productsCategory = tables.First(x => x.TableName == "ProductCategory"); Assert.Equal(0, productsCategory.References.Count); Assert.Equal(1, tables.First(x => x.TableName == "Category").References.Count); Assert.Equal(2, tables.First(x => x.TableName == "Product").References.Count); } }
public void CanFetchSchema() { using (WithSqlDatabase(MigrationProvider.Oracle, out var connectionString, out string schemaName, includeData: false)) { var driver = DatabaseDriverDispatcher.CreateDriver(MigrationProvider.Oracle, connectionString); var schema = driver.FindSchema(); Assert.NotNull(schema.CatalogName); Assert.Equal(10, schema.Tables.Count); var tables = schema.Tables; // validate NoPkTable var noPkTable = tables.First(x => x.TableName == "NOPKTABLE"); Assert.NotNull(noPkTable); Assert.Equal(new[] { "ID" }, noPkTable.Columns.Select(x => x.Name).ToList()); Assert.Equal(0, noPkTable.PrimaryKeyColumns.Count); // validate Order Table var orderTable = tables.First(x => x.TableName == "Order"); Assert.Equal(4, orderTable.Columns.Count); Assert.Equal(new[] { "ID", "ORDERDATE", "CUSTOMERID", "TOTALAMOUNT" }, orderTable.Columns.Select(x => x.Name).ToList()); Assert.Equal(new[] { "ID" }, orderTable.PrimaryKeyColumns); var orderReferences = orderTable.References; Assert.Equal(1, orderReferences.Count); Assert.Equal("ORDERITEM", orderReferences[0].Table); Assert.Equal(new[] { "ORDERID" }, orderReferences[0].Columns); // validate UnsupportedTable var unsupportedTable = tables.First(x => x.TableName == "UNSUPPORTEDTABLE"); Assert.True(unsupportedTable.Columns.Any(x => x.Type == ColumnType.Unsupported)); // validate OrderItem (2 columns in PK) var orderItemTable = tables.First(x => x.TableName == "ORDERITEM"); Assert.Equal(new[] { "ORDERID", "PRODUCTID" }, orderItemTable.PrimaryKeyColumns); Assert.Equal(1, orderItemTable.References.Count); Assert.Equal("DETAILS", orderItemTable.References[0].Table); Assert.Equal(new[] { "ORDERID", "PRODUCTID" }, orderItemTable.References[0].Columns); // all types are supported (except UnsupportedTable) Assert.True(tables.Where(x => x.TableName != "UNSUPPORTEDTABLE") .All(x => x.Columns.All(y => y.Type != ColumnType.Unsupported))); // validate many - to - many var productsCategory = tables.First(x => x.TableName == "PRODUCTCATEGORY"); Assert.Equal(0, productsCategory.References.Count); Assert.Equal(1, tables.First(x => x.TableName == "CATEGORY").References.Count); Assert.Equal(2, tables.First(x => x.TableName == "PRODUCT").References.Count); } }
public async Task CanHandleMissingParentLink(MigrationProvider provider) { using (WithSqlDatabase(provider, out var connectionString, out string schemaName, "basic")) { var driver = DatabaseDriverDispatcher.CreateDriver(provider, connectionString); var query = provider.Equals(MigrationProvider.Oracle) == false ? "update order_item set order_id = null" : "update \"order_item\" set \"order_id\" = null"; ExecuteSqlQuery(provider, connectionString, query); using (var store = GetDocumentStore()) { var orderItemCollection = new RootCollection(schemaName, "order_item", "OrderItems") { LinkedCollections = new List <LinkedCollection> { new LinkedCollection(schemaName, "order", RelationType.ManyToOne, new List <string> { "order_id" }, "ParentOrder") } }; var orderCollection = new RootCollection(schemaName, "order", "Orders"); var db = await GetDocumentDatabaseInstanceFor(store); var settings = new MigrationSettings { Collections = new List <RootCollection> { orderItemCollection, orderCollection } }; using (db.DocumentsStorage.ContextPool.AllocateOperationContext(out DocumentsOperationContext context)) { var schema = driver.FindSchema(); ApplyDefaultColumnNamesMapping(schema, settings); await driver.Migrate(settings, schema, db, context); } using (var session = store.OpenSession()) { var orderItem = session.Load <JObject>("OrderItems/10"); Assert.NotNull(orderItem); Assert.True(orderItem.ContainsKey("ParentOrder")); Assert.Equal(JTokenType.Null, orderItem["ParentOrder"].Type); } } } }
public Task ImportSql() { using (ContextPool.AllocateOperationContext(out DocumentsOperationContext context)) { using (var sqlImportDoc = context.ReadForMemory(RequestBodyStream(), "sql-migration-request")) { MigrationRequest migrationRequest; // we can't use JsonDeserializationServer here as it doesn't support recursive processing var serializer = DocumentConventions.Default.CreateSerializer(); using (var blittableJsonReader = new BlittableJsonReader()) { blittableJsonReader.Init(sqlImportDoc); migrationRequest = serializer.Deserialize <MigrationRequest>(blittableJsonReader); } var operationId = Database.Operations.GetNextOperationId(); var sourceSqlDatabase = migrationRequest.Source; var dbDriver = DatabaseDriverDispatcher.CreateDriver(sourceSqlDatabase.Provider, sourceSqlDatabase.ConnectionString); var schema = dbDriver.FindSchema(); var token = CreateOperationToken(); var result = new MigrationResult(migrationRequest.Settings); var collectionsCount = migrationRequest.Settings.Collections.Count; var operationDescription = "Importing " + collectionsCount + " " + (collectionsCount == 1 ? "collection" : "collections") + " from SQL database: " + schema.CatalogName; Database.Operations.AddOperation(Database, operationDescription, Documents.Operations.Operations.OperationType.MigrationFromSql, onProgress => { return(Task.Run(async() => { try { // allocate new context as we executed this async using (ContextPool.AllocateOperationContext(out DocumentsOperationContext migrationContext)) { await dbDriver.Migrate(migrationRequest.Settings, schema, Database, migrationContext, result, onProgress, token.Token); } } catch (Exception e) { result.AddError($"Error occurred during import. Exception: {e.Message}"); onProgress.Invoke(result.Progress); throw; } return (IOperationResult)result; })); }, operationId, token: token);
public async Task CanLinkOnParent(MigrationProvider provider) { const string tableName = "groups1"; const string collectionName = "Groups1"; using (WithSqlDatabase(provider, out var connectionString, out string schemaName, "basic")) { var driver = DatabaseDriverDispatcher.CreateDriver(provider, connectionString); using (var store = GetDocumentStore()) { var db = await Databases.GetDocumentDatabaseInstanceFor(store); var settings = new MigrationSettings { Collections = new List <RootCollection> { new RootCollection(schemaName, tableName, collectionName) { LinkedCollections = new List <LinkedCollection> { new LinkedCollection(schemaName, tableName, RelationType.ManyToOne, new List <string> { "parent_group_id" }, "Parent") } } } }; using (var cts = new CancellationTokenSource(TimeSpan.FromMinutes(1))) using (db.DocumentsStorage.ContextPool.AllocateOperationContext(out DocumentsOperationContext context)) { var schema = driver.FindSchema(); ApplyDefaultColumnNamesMapping(schema, settings); await driver.Migrate(settings, schema, db, context, token : cts.Token); } using (var session = store.OpenSession()) { var g1111 = session.Load <JObject>($"{collectionName}/53"); Assert.Equal("G1.1.1.1", g1111["Name"]); var g111 = session.Load <JObject>(g1111["Parent"].ToString()); Assert.Equal("G1.1.1", g111["Name"]); var g11 = session.Load <JObject>(g111["Parent"].ToString()); Assert.Equal("G1.1", g11["Name"]); } var collectionStatistics = store.Maintenance.Send(new GetCollectionStatisticsOperation()); Assert.Equal(7, collectionStatistics.CountOfDocuments); } } }
public async Task CanLinkOnChild(MigrationProvider provider) { var tableName = "groups1"; var collectionName = "Groups1"; using (WithSqlDatabase(provider, out var connectionString, out string schemaName, "basic")) { var driver = DatabaseDriverDispatcher.CreateDriver(provider, connectionString); using (var store = GetDocumentStore()) { var db = await GetDocumentDatabaseInstanceFor(store); var settings = new MigrationSettings { Collections = new List <RootCollection> { new RootCollection(schemaName, tableName, collectionName) { LinkedCollections = new List <LinkedCollection> { new LinkedCollection(schemaName, tableName, RelationType.OneToMany, new List <string> { "parent_group_id" }, "NestedGroups") } } } }; using (db.DocumentsStorage.ContextPool.AllocateOperationContext(out DocumentsOperationContext context)) { var schema = driver.FindSchema(); ApplyDefaultColumnNamesMapping(schema, settings); await driver.Migrate(settings, schema, db, context); } using (var session = store.OpenSession()) { var g11 = session.Load <JObject>($"{collectionName}/51"); Assert.Equal(2, g11["NestedGroups"].Count()); Assert.Equal($"{collectionName}/52", g11["NestedGroups"][0]); Assert.Equal($"{collectionName}/54", g11["NestedGroups"][1]); } var collectionStatistics = store.Maintenance.Send(new GetCollectionStatisticsOperation()); Assert.Equal(7, collectionStatistics.CountOfDocuments); } } }
public async Task SqlSchema() { using (ContextPool.AllocateOperationContext(out DocumentsOperationContext context)) using (var sourceSqlDatabaseBlittable = await context.ReadForMemoryAsync(RequestBodyStream(), "source-database-info")) { var sourceSqlDatabase = JsonDeserializationServer.SourceSqlDatabase(sourceSqlDatabaseBlittable); var dbDriver = DatabaseDriverDispatcher.CreateDriver(sourceSqlDatabase.Provider, sourceSqlDatabase.ConnectionString); var schema = dbDriver.FindSchema(); await using (var writer = new AsyncBlittableJsonTextWriter(context, ResponseBodyStream())) { context.Write(writer, schema.ToJson()); } } }
public async Task CanMigrateSkipOnChild(MigrationProvider provider) { using (WithSqlDatabase(provider, out var connectionString, out string schemaName, "basic")) { var driver = DatabaseDriverDispatcher.CreateDriver(provider, connectionString); using (var store = GetDocumentStore()) { var collection = new RootCollection(schemaName, "order_item", "OrderItems"); var db = await GetDocumentDatabaseInstanceFor(store); var settings = new MigrationSettings { Collections = new List <RootCollection> { collection } }; using (var cts = new CancellationTokenSource(TimeSpan.FromMinutes(1))) using (db.DocumentsStorage.ContextPool.AllocateOperationContext(out DocumentsOperationContext context)) { var schema = driver.FindSchema(); ApplyDefaultColumnNamesMapping(schema, settings); await driver.Migrate(settings, schema, db, context, token : cts.Token); } using (var session = store.OpenSession()) { var orderItem = session.Load <JObject>("OrderItems/10"); Assert.NotNull(orderItem); // price and metadata, Id (OrderItems/1) Assert.Equal(3, orderItem.Properties().Count()); Assert.Equal("OrderItems", orderItem["@metadata"]["@collection"]); Assert.Equal(110, orderItem["Price"]); Assert.Equal("OrderItems/10", orderItem["Id"]); } var collectionStatistics = store.Maintenance.Send(new GetCollectionStatisticsOperation()); Assert.Equal(2, collectionStatistics.CountOfDocuments); } } }
public void CanFetchSchema() { using (WithSqlDatabase(MigrationProvider.MySQL, out var connectionString, out string schemaName, includeData: false)) { var driver = DatabaseDriverDispatcher.CreateDriver(MigrationProvider.MySQL, connectionString); var schema = driver.FindSchema(); Assert.NotNull(schema.CatalogName); Assert.Equal(21, schema.Tables.Count); // validate NoPkTable var tables = schema.Tables; var noPkTable = tables.First(x => x.TableName == "NoPkTable"); Assert.NotNull(noPkTable); Assert.Equal(new[] { "id" }, noPkTable.Columns.Select(x => x.Name).ToList()); Assert.Equal(0, noPkTable.PrimaryKeyColumns.Count); // validate Order Table var orderTable = tables.First(x => x.TableName == "orders"); Assert.Equal(20, orderTable.Columns.Count); Assert.Equal(new[] { "id" }, orderTable.PrimaryKeyColumns); var orderReferences = orderTable.References; Assert.Equal(3, orderReferences.Count); Assert.Equal( new[] { "inventory_transactions -> (customer_order_id)", "invoices -> (order_id)", "order_details -> (order_id)" }, orderReferences.Select(x => x.Table + " -> (" + string.Join(",", x.Columns) + ")").ToList()); // validate employee_privileges (2 columns in PK) var employeePrivileges = tables.First(x => x.TableName == "employee_privileges"); Assert.Equal(new[] { "employee_id", "privilege_id" }, employeePrivileges.PrimaryKeyColumns); Assert.True(tables.All(x => x.Columns.All(y => y.Type != ColumnType.Unsupported))); } }
public async Task CanMigrateSkipOnParent(MigrationProvider provider) { using (WithSqlDatabase(provider, out var connectionString, out string schemaName, "basic")) { var driver = DatabaseDriverDispatcher.CreateDriver(provider, connectionString); using (var store = GetDocumentStore()) { var collection = new RootCollection(schemaName, "order", "Orders"); var db = await GetDocumentDatabaseInstanceFor(store); var settings = new MigrationSettings { Collections = new List <RootCollection> { collection } }; using (db.DocumentsStorage.ContextPool.AllocateOperationContext(out DocumentsOperationContext context)) { var schema = driver.FindSchema(); ApplyDefaultColumnNamesMapping(schema, settings); await driver.Migrate(settings, schema, db, context); } using (var session = store.OpenSession()) { var order = session.Load <JObject>("Orders/1"); Assert.NotNull(order); // total and metadata, Id (Orders/1) Assert.Equal(3, order.Properties().Count()); Assert.Equal("Orders", order["@metadata"]["@collection"]); Assert.Equal(440, order["Total"]); Assert.Equal("Orders/1", order["Id"]); } var collectionStatistics = store.Maintenance.Send(new GetCollectionStatisticsOperation()); Assert.Equal(1, collectionStatistics.CountOfDocuments); } } }
public async Task PatchCanAccessNestedObjects() { using (WithSqlDatabase(MigrationProvider.MsSQL, out var connectionString, out string schemaName, "basic")) { var driver = DatabaseDriverDispatcher.CreateDriver(MigrationProvider.MsSQL, connectionString); using (var store = GetDocumentStore()) { var db = await GetDocumentDatabaseInstanceFor(store); var settings = new MigrationSettings { Collections = new List <RootCollection> { new RootCollection(schemaName, "order", "Orders") { Patch = "this.JsTotal = this.Items.map(x => x.price).reduce((acc, cur) => acc + cur, 0)", NestedCollections = new List <EmbeddedCollection> { new EmbeddedCollection(schemaName, "order_item", RelationType.OneToMany, new List <string> { "order_id" }, "Items") } } } }; using (var cts = new CancellationTokenSource(TimeSpan.FromMinutes(1))) using (db.DocumentsStorage.ContextPool.AllocateOperationContext(out DocumentsOperationContext context)) { var schema = driver.FindSchema(); ApplyDefaultColumnNamesMapping(schema, settings); await driver.Migrate(settings, schema, db, context, token : cts.Token); } using (var session = store.OpenSession()) { var order = session.Load <JObject>("Orders/1"); Assert.NotNull(order); Assert.Equal(440, order["JsTotal"]); } } } }
public async Task CanImportWithRelationToNonPrimaryKey(MigrationProvider provider) { using (WithSqlDatabase(provider, out var connectionString, out string schemaName, "basic")) { var driver = DatabaseDriverDispatcher.CreateDriver(provider, connectionString); using (var store = GetDocumentStore()) { var db = await GetDocumentDatabaseInstanceFor(store); var settings = new MigrationSettings { Collections = new List <RootCollection> { new RootCollection(schemaName, "orders2", "Orders2") } }; using (var cts = new CancellationTokenSource(TimeSpan.FromMinutes(1))) using (db.DocumentsStorage.ContextPool.AllocateOperationContext(out DocumentsOperationContext context)) { var schema = driver.FindSchema(); var customersSchema = schema.GetTable(schemaName, "customers2"); // vat id -> should not be reference! Assert.Equal(0, customersSchema.References.Count); Assert.True(customersSchema.Columns.Any(x => x.Name == "vatid")); ApplyDefaultColumnNamesMapping(schema, settings); await driver.Migrate(settings, schema, db, context, token : cts.Token); } using (var session = store.OpenSession()) { JObject[] objects = session.Advanced.LoadStartingWith <JObject>("Orders2/"); foreach (var jObject in objects) { Assert.True(jObject.GetValue("Customer_vatid").Value <int>() == 55555 || jObject.GetValue("Customer_vatid").Value <int>() == 44444); } } } } }
public async Task SupportsDocumentSkip(MigrationProvider provider) { using (WithSqlDatabase(provider, out var connectionString, out string schemaName, "basic")) { var driver = DatabaseDriverDispatcher.CreateDriver(provider, connectionString); using (var store = GetDocumentStore()) { var db = await GetDocumentDatabaseInstanceFor(store); var settings = new MigrationSettings { Collections = new List <RootCollection> { new RootCollection(schemaName, "order_item", "OrderItems") { Patch = "if (this.Price < 200) throw 'skip';" } } }; using (var cts = new CancellationTokenSource(TimeSpan.FromMinutes(1))) using (db.DocumentsStorage.ContextPool.AllocateOperationContext(out DocumentsOperationContext context)) { var schema = driver.FindSchema(); ApplyDefaultColumnNamesMapping(schema, settings); var result = new MigrationResult(settings); await driver.Migrate(settings, schema, db, context, result, token : cts.Token); Assert.Equal(2, result.PerCollectionCount["OrderItems"].ReadCount); Assert.Equal(0, result.PerCollectionCount["OrderItems"].ErroredCount); Assert.Equal(1, result.PerCollectionCount["OrderItems"].SkippedCount); } using (var session = store.OpenSession()) { Assert.Equal(1, session.Advanced.LoadStartingWith <JObject>("OrderItems/").Length); } } } }
public async Task CanTestWithEmbed(MigrationProvider provider) { using (WithSqlDatabase(provider, out var connectionString, out string schemaName, "basic")) { var driver = DatabaseDriverDispatcher.CreateDriver(provider, connectionString); using (var store = GetDocumentStore()) { var db = await GetDocumentDatabaseInstanceFor(store); var settings = new MigrationTestSettings { Collection = new RootCollection(schemaName, "order", "Orders") { NestedCollections = new List <EmbeddedCollection> { new EmbeddedCollection(schemaName, "order_item", RelationType.OneToMany, new List <string> { "order_id" }, "Items") } } }; using (db.DocumentsStorage.ContextPool.AllocateOperationContext(out DocumentsOperationContext context)) { var schema = driver.FindSchema(); ApplyDefaultColumnNamesMapping(schema, settings.Collection, settings.BinaryToAttachment); var(document, id) = driver.Test(settings, schema, context); Assert.Equal("Orders/1", id); Assert.True(document.TryGet("Total", out double total)); Assert.Equal(440, total); var items = document["Items"] as BlittableJsonReaderArray; Assert.NotNull(items); Assert.Equal(2, items.Length); } } } }
public async Task SimplePatch(MigrationProvider provider) { using (WithSqlDatabase(provider, out var connectionString, out string schemaName, "basic")) { var driver = DatabaseDriverDispatcher.CreateDriver(provider, connectionString); using (var store = GetDocumentStore()) { var db = await GetDocumentDatabaseInstanceFor(store); var settings = new MigrationSettings { Collections = new List <RootCollection> { new RootCollection(schemaName, "order", "Orders") { Patch = "this.NewField = 5;" } } }; using (var cts = new CancellationTokenSource(TimeSpan.FromMinutes(1))) using (db.DocumentsStorage.ContextPool.AllocateOperationContext(out DocumentsOperationContext context)) { var schema = driver.FindSchema(); ApplyDefaultColumnNamesMapping(schema, settings); await driver.Migrate(settings, schema, db, context, token : cts.Token); } using (var session = store.OpenSession()) { var order = session.Load <JObject>("Orders/1"); Assert.NotNull(order); Assert.Equal(5, order["NewField"]); } } } }