You've already forked linux-packaging-mono
							
							
		
			
				
	
	
		
			349 lines
		
	
	
		
			16 KiB
		
	
	
	
		
			JavaScript
		
	
	
	
	
	
			
		
		
	
	
			349 lines
		
	
	
		
			16 KiB
		
	
	
	
		
			JavaScript
		
	
	
	
	
	
| /// <reference path="../Scripts/References.js" />
 | |
| 
 | |
| (function (upshot, ko, undefined) {
 | |
| 
 | |
|     module("ChangeTracking");
 | |
| 
 | |
|     var observability = upshot.observability;
 | |
| 
 | |
|     test("Explicit commit multiple property edits", 5, function () {
 | |
|         var submitCount = 0;
 | |
|         var propertyChangedCount = 0;
 | |
| 
 | |
|         var dc = createTestContext(function () {
 | |
|             submitCount++;
 | |
|         }, true);
 | |
| 
 | |
|         var entitySet = dc.getEntitySet("Product");
 | |
|         var prod = entitySet.getEntities()[0];
 | |
|         var state = entitySet.getEntityState(prod);
 | |
|         equal(state, upshot.EntityState.Unmodified);
 | |
| 
 | |
|         entitySet.bind("propertyChanged", function () {
 | |
|             propertyChangedCount++;
 | |
|         });
 | |
| 
 | |
|         $.observable(prod).property("Name", "xyz");
 | |
|         $.observable(prod).property("Name", "foo");
 | |
|         $.observable(prod).property("Price", 9.99);
 | |
| 
 | |
|         equal(propertyChangedCount, 3);
 | |
| 
 | |
|         state = entitySet.getEntityState(prod);
 | |
|         equal(state, upshot.EntityState.ClientUpdated);
 | |
| 
 | |
|         equal(submitCount, 0);
 | |
| 
 | |
|         dc.commitChanges();
 | |
| 
 | |
|         equal(submitCount, 1);
 | |
|     });
 | |
| 
 | |
|     asyncTest("Implicit commit multiple property edits", 5, function () {
 | |
|         var submitCount = 0;
 | |
|         var propertyChangedCount = 0;
 | |
| 
 | |
|         var dc = createTestContext(function () {
 | |
|             submitCount++;
 | |
|         }, false);
 | |
| 
 | |
|         var entitySet = dc.getEntitySet("Product");
 | |
|         var prod = entitySet.getEntities()[0];
 | |
|         var state = entitySet.getEntityState(prod);
 | |
|         equal(state, upshot.EntityState.Unmodified);
 | |
| 
 | |
|         entitySet.bind("propertyChanged", function () {
 | |
|             propertyChangedCount++;
 | |
|         });
 | |
| 
 | |
|         $.observable(prod).property("Name", "xyz");
 | |
|         $.observable(prod).property("Name", "foo");
 | |
|         $.observable(prod).property("Price", 9.99);
 | |
| 
 | |
|         // before the timeout has expired we shouldn't have committed anything
 | |
|         equal(submitCount, 0);
 | |
| 
 | |
|         equal(propertyChangedCount, 3);
 | |
| 
 | |
|         state = entitySet.getEntityState(prod);
 | |
|         equal(state, upshot.EntityState.ClientUpdated);
 | |
| 
 | |
|         // Here we queue the test verification and start so that it runs
 | |
|         // AFTER the queued commit
 | |
|         setTimeout(function () {
 | |
|             equal(submitCount, 1);
 | |
|             start();
 | |
|         }, 0);
 | |
| 
 | |
|     });
 | |
| 
 | |
|     asyncTest("Implicit commit multiple array operations", 5, function () {
 | |
|         var submitCount = 0;
 | |
| 
 | |
|         var dc = createTestContext(function (options, editedEntities) {
 | |
|             submitCount++;
 | |
|             equal(editedEntities.length, 2);
 | |
|         }, false);
 | |
| 
 | |
|         var entitySet = dc.getEntitySet("Product");
 | |
|         var prod = entitySet.getEntities()[0];
 | |
| 
 | |
|         // do an insert
 | |
|         var newProd = {
 | |
|             ID: 2,
 | |
|             Name: "Frish Gnarbles",
 | |
|             Category: "Snacks",
 | |
|             Price: 7.99
 | |
|         };
 | |
|         $.observable(entitySet.getEntities()).insert(newProd);
 | |
|         var state = entitySet.getEntityState(newProd);
 | |
|         equal(state, upshot.EntityState.ClientAdded);
 | |
| 
 | |
|         // do a delete
 | |
|         entitySet.deleteEntity(prod);
 | |
|         state = entitySet.getEntityState(prod);
 | |
|         equal(state, upshot.EntityState.ClientDeleted);
 | |
| 
 | |
|         // before the timeout has expired we shouldn't have committed anything
 | |
|         equal(submitCount, 0);
 | |
| 
 | |
|         // Here we queue the test verification and start so that it runs
 | |
|         // AFTER the queued commit
 | |
|         setTimeout(function () {
 | |
|             equal(submitCount, 1);
 | |
|             start();
 | |
|         }, 0);
 | |
|     });
 | |
| 
 | |
| /* TODO: We forced managed associations on for Dev11 beta, since unmanaged associations are broken.
 | |
|     test("Nested entities can be added to an entity, and navigation properties are untracked", 16, function () {
 | |
|         try {
 | |
|             upshot.observability.configuration = observability.knockout;
 | |
| 
 | |
|             var manageAssociations = false;
 | |
|             var dc = createKoTestContext(function () { }, false, manageAssociations);
 | |
| 
 | |
|             var orders = dc.getEntitySet("Order"),
 | |
|                 orderDetails = dc.getEntitySet("OrderDetail"),
 | |
|                 order = orders.getEntities()()[0],
 | |
|                 order2 = orders.getEntities()()[1],
 | |
|                 orderDetail = orderDetails.getEntities()()[0];
 | |
| 
 | |
|             order.OrderDetails.remove(orderDetail);
 | |
|             equal(1, order.OrderDetails().length, "There should only be a single order detail");
 | |
|             equal(upshot.EntityState.Unmodified, orders.getEntityState(order), "The order should not be modified");
 | |
|             equal(upshot.EntityState.Unmodified, orderDetails.getEntityState(orderDetail), "The order detail should not be modified");
 | |
| 
 | |
|             order.OrderDetails.push(orderDetail);
 | |
|             equal(2, order.OrderDetails().length, "There should be two order details");
 | |
|             equal(upshot.EntityState.Unmodified, orders.getEntityState(order), "The order should not be modified");
 | |
|             equal(upshot.EntityState.Unmodified, orderDetails.getEntityState(orderDetail), "The order detail should not be modified");
 | |
| 
 | |
|             orderDetail.Order(order2);
 | |
|             equal(orderDetail.OrderId(), order2.Id(), "Ids should be equal");
 | |
|             equal(upshot.EntityState.Unmodified, orders.getEntityState(order2), "The order should not be modified");
 | |
|             equal(upshot.EntityState.ClientUpdated, orderDetails.getEntityState(orderDetail), "The order detail should not be modified");
 | |
|             equal(true, orderDetails.isUpdated(orderDetail, "OrderId"), "The OrderId should be modified");
 | |
|             equal(false, orderDetails.isUpdated(orderDetail, "Order"), "The Order should not be tracked");
 | |
| 
 | |
|             var properties = [];
 | |
|             $.each(observability.knockout.unmap(orderDetail, "OrderDetail"), function (key, value) {
 | |
|                 properties.push(key);
 | |
|                 equal(ko.utils.unwrapObservable(orderDetail[key]), value, "Properties should be equal");
 | |
|             });
 | |
|             equal(properties.length, 4, "The should be 4 serialized properties");
 | |
| 
 | |
|         } finally {
 | |
|             upshot.observability.configuration = observability.jquery;
 | |
|         }
 | |
|     });
 | |
| */
 | |
| 
 | |
|     test("Nested entities can be added to an entity, and navigation properties are computed", 39, function () {
 | |
|         try {
 | |
|             upshot.observability.configuration = observability.knockout;
 | |
| 
 | |
|             var dc = createKoTestContext(function () { }, false);
 | |
| 
 | |
|             var orders = dc.getEntitySet("Order"),
 | |
|                 orderDetails = dc.getEntitySet("OrderDetail"),
 | |
|                 order = orders.getEntities()()[0],
 | |
|                 order2 = orders.getEntities()()[1],
 | |
|                 orderDetail = orderDetails.getEntities()()[0];
 | |
| 
 | |
|             ok(order.OrderDetails.indexOf(orderDetail) >= 0 && order2.OrderDetails.indexOf(orderDetail) < 0 && orderDetail.Order() === order, "The order detail is a child of order1");
 | |
|             equal(orders.getEntityState(order), upshot.EntityState.Unmodified, "order1 should not be modified");
 | |
|             equal(orders.getEntityState(order2), upshot.EntityState.Unmodified, "order2 should not be modified");
 | |
|             equal(orderDetails.getEntityState(orderDetail), upshot.EntityState.Unmodified, "The order detail should not be modified");
 | |
|             equal(orderDetails.isUpdated(orderDetail, "OrderId"), false, "The OrderId should not be modified");
 | |
|             equal(orderDetails.isUpdated(orderDetail, "Order"), false, "The Order should not be tracked");
 | |
| 
 | |
|             orderDetail.OrderId(order2.Id());
 | |
|             ok(order2.OrderDetails.indexOf(orderDetail) >= 0 && order.OrderDetails.indexOf(orderDetail) < 0 && orderDetail.Order() === order2, "The order detail is a child of order2");
 | |
|             equal(orders.getEntityState(order), upshot.EntityState.Unmodified, "order1 should not be modified");
 | |
|             equal(orders.getEntityState(order2), upshot.EntityState.Unmodified, "order2 should not be modified");
 | |
|             equal(orderDetails.getEntityState(orderDetail), upshot.EntityState.ClientUpdated, "The order detail should be ClientUpdated");
 | |
|             equal(orderDetails.isUpdated(orderDetail, "OrderId"), true, "The OrderId should be modified");
 | |
|             equal(orderDetails.isUpdated(orderDetail, "Order"), false, "The Order should not be tracked");
 | |
| 
 | |
|             orderDetails.revertUpdates(orderDetail);
 | |
|             ok(order.OrderDetails.indexOf(orderDetail) >= 0 && order2.OrderDetails.indexOf(orderDetail) < 0 && orderDetail.Order() === order, "The order detail is a child of order1");
 | |
|             equal(orders.getEntityState(order), upshot.EntityState.Unmodified, "order1 should not be modified");
 | |
|             equal(orders.getEntityState(order2), upshot.EntityState.Unmodified, "order2 should not be modified");
 | |
|             equal(orderDetails.getEntityState(orderDetail), upshot.EntityState.Unmodified, "The order detail should not be modified");
 | |
|             equal(orderDetails.isUpdated(orderDetail, "OrderId"), false, "The OrderId should not be modified");
 | |
|             equal(orderDetails.isUpdated(orderDetail, "Order"), false, "The Order should not be tracked");
 | |
| 
 | |
|             orderDetail.Order(order2);
 | |
|             ok(orderDetail.OrderId() === order2.Id(), "Ids should be equal");
 | |
|             equal(orders.getEntityState(order2), upshot.EntityState.Unmodified, "The order should not be modified");
 | |
|             equal(orderDetails.getEntityState(orderDetail), upshot.EntityState.ClientUpdated, "The order detail should be ClientUpdated");
 | |
|             equal(orderDetails.isUpdated(orderDetail, "OrderId"), true, "The OrderId should be modified");
 | |
|             equal(orderDetails.isUpdated(orderDetail, "Order"), false, "The Order should not be tracked");
 | |
| 
 | |
|             orderDetails.revertUpdates(orderDetail);
 | |
|             ok(order.OrderDetails.indexOf(orderDetail) >= 0 && order2.OrderDetails.indexOf(orderDetail) < 0 && orderDetail.Order() === order, "The order detail is a child of order1");
 | |
|             equal(orders.getEntityState(order), upshot.EntityState.Unmodified, "order1 should not be modified");
 | |
|             equal(orders.getEntityState(order2), upshot.EntityState.Unmodified, "order2 should not be modified");
 | |
|             equal(orderDetails.getEntityState(orderDetail), upshot.EntityState.Unmodified, "The order detail should not be modified");
 | |
|             equal(orderDetails.isUpdated(orderDetail, "OrderId"), false, "The OrderId should not be modified");
 | |
|             equal(orderDetails.isUpdated(orderDetail, "Order"), false, "The Order should not be tracked");
 | |
| 
 | |
|             orderDetail.Order(null);
 | |
|             equal(orderDetail.OrderId(), null, "FK should be null");
 | |
|             equal(orders.getEntityState(order), upshot.EntityState.Unmodified, "The old order should not be modified");
 | |
|             equal(orderDetails.getEntityState(orderDetail), upshot.EntityState.ClientUpdated, "The order detail should be ClientUpdated");
 | |
|             equal(orderDetails.isUpdated(orderDetail, "OrderId"), true, "The OrderId should be modified");
 | |
|             equal(orderDetails.isUpdated(orderDetail, "Order"), false, "The Order should not be tracked");
 | |
| 
 | |
|             var properties = [];
 | |
|             $.each(observability.knockout.unmap(orderDetail, "OrderDetail"), function (key, value) {
 | |
|                 properties.push(key);
 | |
|                 equal(ko.utils.unwrapObservable(orderDetail[key]), value, "Properties should be equal");
 | |
|             });
 | |
|             equal(properties.length, 4, "The should be 4 serialized properties");
 | |
| 
 | |
|         } finally {
 | |
|             upshot.observability.configuration = observability.jquery;
 | |
|         }
 | |
|     });
 | |
| 
 | |
|     test("Nested entities can be added to an entity, and property changes do not bubble to the parent", 2, function () {
 | |
|         try {
 | |
|             upshot.observability.configuration = observability.knockout;
 | |
| 
 | |
|             var dc = createKoTestContext(function () { }, false);
 | |
| 
 | |
|             var orders = dc.getEntitySet("Order"),
 | |
|                 orderDetails = dc.getEntitySet("OrderDetail"),
 | |
|                 order = orders.getEntities()()[0],
 | |
|                 orderDetail = orderDetails.getEntities()()[0];
 | |
| 
 | |
|             orderDetail.Name("asdf");
 | |
|             equal(orders.getEntityState(order), upshot.EntityState.Unmodified, "The order should not be modified");
 | |
|             equal(orderDetails.getEntityState(orderDetail), upshot.EntityState.ClientUpdated, "The order detail should not be modified");
 | |
|         } finally {
 | |
|             upshot.observability.configuration = observability.jquery;
 | |
|         }
 | |
|     });
 | |
| 
 | |
|     // Create and return a context using the specified submitChanges mock
 | |
|     function createTestContext(submitChangesMock, bufferChanges) {
 | |
|         var dataProvider = new upshot.DataProvider();
 | |
|         var implicitCommitHandler;
 | |
|         if (!bufferChanges) {
 | |
|             implicitCommitHandler = function () {
 | |
|                 dc._commitChanges({ providerParameters: {} });
 | |
|             }
 | |
|         }
 | |
|         var dc = new upshot.DataContext(dataProvider, implicitCommitHandler);
 | |
|         dc._submitChanges = submitChangesMock;
 | |
| 
 | |
|         // add a single product to the context
 | |
|         var type = "Product";
 | |
|         var products = [];
 | |
|         products.push({
 | |
|             ID: 1,
 | |
|             Name: "Crispy Snarfs",
 | |
|             Category: "Snacks",
 | |
|             Price: 12.99
 | |
|         });
 | |
|         products.push({
 | |
|             ID: 2,
 | |
|             Name: "Cheezy Snax",
 | |
|             Category: "Snacks",
 | |
|             Price: 1.99
 | |
|         });
 | |
| 
 | |
|         // mock out enough metadata to do the attach
 | |
|         upshot.metadata(type, { key: ["ID"] });
 | |
| 
 | |
|         dc.merge(products, type, null);
 | |
| 
 | |
|         return dc;
 | |
|     }
 | |
| 
 | |
|     function createKoTestContext(submitChangesMock, bufferChanges) {
 | |
|         var dataProvider = new upshot.DataProvider();
 | |
|         var implicitCommitHandler;
 | |
|         if (!bufferChanges) {
 | |
|             implicitCommitHandler = function () {
 | |
|                 dc._commitChanges({ providerParameters: {} });
 | |
|             }
 | |
|         }
 | |
|         var dc = new upshot.DataContext(dataProvider, implicitCommitHandler);
 | |
|         dc._submitChanges = submitChangesMock;
 | |
| 
 | |
|         // add a single product to the context
 | |
|         var manageAssociations = true;  // TODO: Lift this to a createKoTestContext parameter when unmanaged associations is supported.
 | |
|         var OrderDetail = function (data) {
 | |
|             this.Id = ko.observable(data.Id);
 | |
|             this.Name = ko.observable(data.Name);
 | |
|             this.Order = ko.observable();
 | |
|             this.OrderId = manageAssociations ? ko.observable(data.OrderId) : ko.computed(function () {
 | |
|                 return this.Order() ? this.Order().Id() : data.OrderId;
 | |
|             }, this);
 | |
|             this.Extra = ko.observable("extra");
 | |
|         };
 | |
|         var Order = function (data) {
 | |
|             this.Id = ko.observable(data.Id);
 | |
|             this.Name = ko.observable(data.Name);
 | |
|             this.OrderDetails = ko.observableArray(ko.utils.arrayMap(data.OrderDetails, function (od) { return new OrderDetail(od); }));
 | |
|             this.Extra = ko.observable("extra");
 | |
|         };
 | |
| 
 | |
|         var orders = [],
 | |
|             order = {
 | |
|                 Id: 1,
 | |
|                 Name: "Order 1",
 | |
|                 OrderDetails: []
 | |
|             };
 | |
|         orders.push(new Order(order));
 | |
|         orders.push(new Order({
 | |
|             Id: 2,
 | |
|             Name: "Order 2",
 | |
|             OrderDetails: []
 | |
|         }));
 | |
|         var orderDetails = [];
 | |
|         orderDetails.push(new OrderDetail({
 | |
|             Id: 1,
 | |
|             Name: "Order Detail 1",
 | |
|             OrderId: order.Id
 | |
|         }));
 | |
|         orderDetails.push(new OrderDetail({
 | |
|             Id: 2,
 | |
|             Name: "Order Detail 2",
 | |
|             OrderId: order.Id
 | |
|         }));
 | |
|         orders[0].OrderDetails(orderDetails);
 | |
| 
 | |
|         // mock out enough metadata to do the attach
 | |
|         upshot.metadata("Order", { key: ["Id"], fields: { Id: { type: "Int32:#System" }, Name: { type: "String:#System" }, OrderDetails: { type: "OrderDetail", association: { Name: "O_OD", isForeignKey: false, thisKey: ["Id"], otherKey: ["OrderId"] }, array: true } } });
 | |
|         upshot.metadata("OrderDetail", { key: ["Id"], fields: { Id: { type: "Int32:#System" }, Name: { type: "String:#System" }, Order: { type: "Order", association: { Name: "O_OD", isForeignKey: true, thisKey: ["OrderId"], otherKey: ["Id"]} }, OrderId: { type: "Int32:#System"}} });
 | |
| 
 | |
|         dc.merge(orders, "Order", null);
 | |
| 
 | |
|         return dc;
 | |
|     }
 | |
| })(upshot, ko);
 |