public void TestCopySchema() { SchemaCreator sc = new SchemaCreator(this); sc.Create(); string msg2 = "Hello, world, this used to be Func1!"; string func1q2 = "create procedure Func1 as select '" + msg2 + "'\n"; VxSchema origschema = dbus.Get(); VxSchemaChecksums origsums = dbus.GetChecksums(); string tmpdir = GetTempDir(); try { Directory.CreateDirectory(tmpdir); VxDiskSchema disk = new VxDiskSchema(tmpdir); // Test that the copy function will create new elements VxSchema.CopySchema(dbus, disk); VxSchema newschema = disk.Get(null); VxSchemaChecksums newsums = disk.GetChecksums(); WVPASS(1); TestSchemaEquality(origschema, newschema); WVPASS(2); TestChecksumEquality(origsums, newsums); WVPASS(3); // Test that the copy function updates changed elements, and // deletes old ones. origschema["Procedure/Func1"].text = func1q2; dbus.Put(origschema, null, VxPutOpts.None); dbus.DropSchema("Table/Tab2"); origschema.Remove("Table/Tab2"); origsums = dbus.GetChecksums(); VxSchema.CopySchema(dbus, disk); newschema = disk.Get(null); newsums = disk.GetChecksums(); WVPASS(4); TestSchemaEquality(origschema, newschema); WVPASS(5); TestChecksumEquality(origsums, newsums); WVPASS(6); } finally { Directory.Delete(tmpdir, true); } WVPASS(!Directory.Exists(tmpdir)); sc.Cleanup(); }
public void TestExportSchema() { SchemaCreator sc = new SchemaCreator(this); string tmpdir = GetTempDir(); DirectoryInfo tmpdirinfo = new DirectoryInfo(tmpdir); try { tmpdirinfo.Create(); // Establish a baseline for the number of existing elements. VxSchema schema = dbus.Get(); VxSchemaChecksums sums = dbus.GetChecksums(); VxDiskSchema disk = new VxDiskSchema(tmpdir); disk.Put(schema, sums, VxPutOpts.None); var base_filecounts = GetFileCounts(tmpdir); // Clobber the directory and start fresh. tmpdirinfo.Delete(true); tmpdirinfo.Create(); // Now create our test schema and do the real tests. sc.Create(); // Check that having mangled checksums fails schema = dbus.Get(); sums = new VxSchemaChecksums(); disk = new VxDiskSchema(tmpdir); try { WVEXCEPT(disk.Put(schema, sums, VxPutOpts.None)); } catch (Wv.Test.WvAssertionFailure e) { throw e; } catch (System.Exception e) { WVPASS(e is ArgumentException); WVPASS(e.Message.StartsWith("Missing checksum for ")); log.print(e.ToString() + "\n"); } // Check that the normal exporting works. schema = dbus.Get(); sums = dbus.GetChecksums(); WVPASSEQ(schema.Count, sums.Count); disk.Put(schema, sums, VxPutOpts.None); int backup_generation = 0; VerifyExportedSchema(tmpdir, schema, sums, sc, backup_generation, base_filecounts); // Check that we read back the same stuff VxSchema schemafromdisk = disk.Get(null); VxSchemaChecksums sumsfromdisk = disk.GetChecksums(); WVPASS(1); TestSchemaEquality(schema, schemafromdisk); TestChecksumEquality(sums, sumsfromdisk); WVPASS(2); // Doing it twice doesn't change anything. disk.Put(schema, sums, VxPutOpts.None); VerifyExportedSchema(tmpdir, schema, sums, sc, backup_generation, base_filecounts); WVPASS(3); // Check backup mode disk.Put(schema, sums, VxPutOpts.IsBackup); backup_generation++; VerifyExportedSchema(tmpdir, schema, sums, sc, backup_generation, base_filecounts); WVPASS(4); // Check backup mode again disk.Put(schema, sums, VxPutOpts.IsBackup); backup_generation++; VerifyExportedSchema(tmpdir, schema, sums, sc, backup_generation, base_filecounts); WVPASS(5); } finally { tmpdirinfo.Delete(true); sc.Cleanup(); } WVASSERT(!tmpdirinfo.Exists); }
public void TestReadChecksums() { SchemaCreator sc = new SchemaCreator(this); sc.Create(); string tmpdir = GetTempDir(); DirectoryInfo tmpdirinfo = new DirectoryInfo(tmpdir); try { tmpdirinfo.Create(); VxSchema schema = dbus.Get(); VxSchemaChecksums sums = dbus.GetChecksums(); VxDiskSchema backend = new VxDiskSchema(tmpdir); backend.Put(schema, sums, VxPutOpts.None); VxSchemaChecksums fromdisk = backend.GetChecksums(); foreach (KeyValuePair<string, VxSchemaChecksum> p in sums) WVPASSEQ(p.Value.GetSumString(), fromdisk[p.Key].GetSumString()); WVPASSEQ(sums.Count, fromdisk.Count); // Test that changing a file invalidates its checksums, and that // we skip directories named "DATA" using (StreamWriter sw = File.AppendText( wv.PathCombine(tmpdir, "Table", "Tab1"))) { sw.WriteLine("Ooga Booga"); } Directory.CreateDirectory(Path.Combine(tmpdir, "DATA")); File.WriteAllText(wv.PathCombine(tmpdir, "DATA", "Decoy"), "Decoy file, shouldn't have checksums"); VxSchemaChecksums mangled = backend.GetChecksums(); // Check that the decoy file didn't get read WVFAIL(mangled.ContainsKey("DATA/Decoy")); // Check that the mangled checksums exist, but are empty. WVASSERT(mangled.ContainsKey("Table/Tab1")); WVASSERT(mangled["Table/Tab1"].GetSumString() != sums["Table/Tab1"].GetSumString()); WVPASSEQ(mangled["Table/Tab1"].GetSumString(), ""); // Check that everything else is still sensible foreach (KeyValuePair<string, VxSchemaChecksum> p in sums) { if (p.Key != "Table/Tab1") WVPASSEQ(p.Value.GetSumString(), mangled[p.Key].GetSumString()); } } finally { tmpdirinfo.Delete(true); sc.Cleanup(); } WVASSERT(!tmpdirinfo.Exists); }
public void TestApplySchemaDiff(ISchemaBackend backend) { log.print("In TestApplySchemaDiff({0})\n", backend.GetType().ToString()); SchemaCreator sc = new SchemaCreator(this); sc.Create(); string msg2 = "Hello, world, this used to be Func1!"; string func1q2 = "create procedure Func1 as select '" + msg2 + "'\n"; VxSchema origschema = dbus.Get(); VxSchemaChecksums origsums = dbus.GetChecksums(); VxSchema newschema = new VxSchema(origschema); VxSchemaChecksums newsums = new VxSchemaChecksums(origsums); // Don't bother putting the data again if we're talking to dbus: // we already snuck it in the back door. if (backend != dbus) backend.Put(origschema, origsums, VxPutOpts.None); VxSchemaChecksums diffsums = new VxSchemaChecksums(newsums); // Make some changes to create an interesting diff. // Change the text and sums of Func1, schedule TestSchema for // deletion, and act like Tab2 is new. newschema["Procedure/Func1"].text = func1q2; newsums.AddSum("Procedure/Func1", 123); newsums.Remove("XMLSchema/TestSchema"); origsums.Remove("Table/Tab2"); WVASSERT(VxExec("drop table Tab2")); VxSchemaDiff diff = new VxSchemaDiff(origsums, newsums); using (IEnumerator<KeyValuePair<string,VxDiffType>> iter = diff.GetEnumerator()) { WVPASS(iter.MoveNext()); WVPASSEQ(iter.Current.Key, "XMLSchema/TestSchema"); WVPASSEQ((char)iter.Current.Value, (char)VxDiffType.Remove); WVPASS(iter.MoveNext()); WVPASSEQ(iter.Current.Key, "Table/Tab2"); WVPASSEQ((char)iter.Current.Value, (char)VxDiffType.Add); WVPASS(iter.MoveNext()); WVPASSEQ(iter.Current.Key, "Procedure/Func1"); WVPASSEQ((char)iter.Current.Value, (char)VxDiffType.Change); WVFAIL(iter.MoveNext()); } VxSchema diffschema = newschema.GetDiffElements(diff); WVPASSEQ(diffschema["XMLSchema/TestSchema"].type, "XMLSchema"); WVPASSEQ(diffschema["XMLSchema/TestSchema"].name, "TestSchema"); WVPASSEQ(diffschema["XMLSchema/TestSchema"].text, ""); WVPASSEQ(diffschema["Table/Tab2"].type, "Table"); WVPASSEQ(diffschema["Table/Tab2"].name, "Tab2"); WVPASSEQ(diffschema["Table/Tab2"].text, sc.tab2sch); WVPASSEQ(diffschema["Procedure/Func1"].type, "Procedure"); WVPASSEQ(diffschema["Procedure/Func1"].name, "Func1"); WVPASSEQ(diffschema["Procedure/Func1"].text, func1q2); VxSchemaErrors errs = backend.Put(diffschema, diffsums, VxPutOpts.None); WVPASSEQ(errs.Count, 0); VxSchema updated = backend.Get(null); WVASSERT(!updated.ContainsKey("XMLSchema/TestSchema")); WVPASSEQ(updated["Table/Tab1"].text, newschema["Table/Tab1"].text); WVPASSEQ(updated["Table/Tab2"].text, newschema["Table/Tab2"].text); WVPASSEQ(updated["Procedure/Func1"].text, newschema["Procedure/Func1"].text); sc.Cleanup(); }
public void TestPutSchemaErrors() { //WvLog.maxlevel = WvLog.L.Debug4; WVPASS("hello"); SchemaCreator sc = new SchemaCreator(this); sc.Create(); // Check that putting the same elements doesn't cause errors VxPutOpts no_opts = VxPutOpts.None; WVPASS("getting"); VxSchema schema = dbus.Get(); WVPASS("putting"); VxSchemaErrors errs = VxPutSchema(schema, no_opts); WVPASSEQ(errs.Count, 0); // Check that invalid SQL causes errors. schema = new VxSchema(); schema.Add("ScalarFunction", "ErrSF", "I am not valid SQL", false); schema.Add("TableFunction", "ErrTF", "I'm not valid SQL either", false); errs = VxPutSchema(schema, no_opts); log.print("Results: \n{0}", errs.ToString()); log.print("Done results.\n"); WVPASSEQ(errs.Count, 2); WVPASSEQ(errs["ScalarFunction/ErrSF"][0].key, "ScalarFunction/ErrSF"); WVPASSEQ(errs["ScalarFunction/ErrSF"][0].msg, "Incorrect syntax near the keyword 'not'."); WVPASSEQ(errs["ScalarFunction/ErrSF"][0].errnum, 156); WVPASSEQ(errs["ScalarFunction/ErrSF"].Count, 1); WVPASSEQ(errs["TableFunction/ErrTF"][0].key, "TableFunction/ErrTF"); WVPASSEQ(errs["TableFunction/ErrTF"][0].msg, "Unclosed quotation mark after the character string 'm not valid SQL either'."); WVPASSEQ(errs["TableFunction/ErrTF"][0].errnum, 105); WVPASSEQ(errs["TableFunction/ErrTF"].Count, 1); sc.Cleanup(); }
public void TestSchemaData() { SchemaCreator sc = new SchemaCreator(this); WVPASSEQ(VxPutSchema("Table", "Tab1", sc.tab1sch, VxPutOpts.None), null); var inserts = new List<string>(); var rows = new List<string>(); // headings string heading = "\"f1\",\"f2\",\"f3\""; rows.Add(heading); for (int ii = 21; ii >= 0; ii--) inserts.Add(wv.fmt("INSERT INTO Tab1 ([f1],[f2],[f3]) " + "VALUES ({0},{1},'{2}');", ii, ii + ".3400", "Hi" + ii)); // The rows will come back sorted alphabetically. int[] order = new int[] { 0, 1, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 2, 20, 21, 3, 4, 5, 6, 7, 8, 9 }; foreach (int ii in order) rows.Add(wv.fmt("{0},{1},{2}", ii, ii + ".3400", "Hi" + ii)); /* inserts.Add("INSERT INTO Tab1 ([f1],[f2],[f3]) " + "VALUES (9501,123.4567," + "'This string''s good for \"testing\" escaping, isn''t it?');");*/ inserts.Add("INSERT INTO Tab1 ([f1],[f2],[f3]) " + "VALUES (9500,234.5678,NULL);"); rows.Add("9500,234.5678,"); /* rows.Add("9501,123.4567," + "\"This string''s good for \\\"testing\\\" escaping, isn't it?\"");*/ // terminating blank rows.Add(""); foreach (string ins in inserts) WVASSERT(VxExec(ins)); string[] newrows = dbus.GetSchemaData("Tab1", 0, "", null, null).split("\n"); WVPASSEQ(newrows.Length, rows.Count); for (int i = 0; i < newrows.Length; i++) WVPASSEQ(newrows[i], rows[i]); VxExec("drop table Tab1"); try { WVEXCEPT(dbus.GetSchemaData("Tab1", 0, "", null, null)); } catch (Wv.Test.WvAssertionFailure e) { throw e; } catch (System.Exception e) { WVPASS(e is WvDbusError); WVPASSEQ(e.Message, "vx.db.sqlerror: Invalid object name 'Tab1'."); log.print(e.ToString() + "\n"); } WVPASSEQ(VxPutSchema("Table", "Tab1", sc.tab1sch, VxPutOpts.None), null); WVPASSEQ(dbus.GetSchemaData("Tab1", 0, "", null, null), heading + "\n"); dbus.PutSchemaData("Tab1", inserts.join(""), 0); WVPASSEQ(dbus.GetSchemaData("Tab1", 0, "", null, null), rows.join("\n")); WVPASSEQ(dbus.GetSchemaData("Tab1", 0, "f1 = 11", null, null), heading + "\n11,11.3400,Hi11\n"); sc.Cleanup(); }
public void TestPutSchema() { SchemaCreator sc = new SchemaCreator(this); VxPutOpts no_opts = VxPutOpts.None; WVPASSEQ(VxPutSchema("Table", "Tab1", sc.tab1sch, no_opts), null); WVPASSEQ(VxPutSchema("TableFunction", "TabFunc1", sc.tabfuncq, no_opts), null); WVPASSEQ(VxPutSchema("Procedure", "Func1", sc.func1q, no_opts), null); WVPASSEQ(VxPutSchema("Trigger", "Trigger1", sc.triggerq, no_opts), null); WVPASSEQ(VxPutSchema("View", "View1", sc.viewq, no_opts), null); WVPASSEQ(VxPutSchema("XMLSchema", "TestSchema", sc.xmlq, no_opts), null); VxSchema schema = dbus.Get(); WVASSERT(schema.ContainsKey("Procedure/Func1")); WVPASSEQ(schema["Procedure/Func1"].name, "Func1"); WVPASSEQ(schema["Procedure/Func1"].type, "Procedure"); WVPASSEQ(schema["Procedure/Func1"].text, sc.func1q); WVASSERT(schema.ContainsKey("Table/Tab1")); WVPASSEQ(schema["Table/Tab1"].name, "Tab1"); WVPASSEQ(schema["Table/Tab1"].type, "Table"); WVPASSEQ(schema["Table/Tab1"].text, sc.tab1sch); WVASSERT(schema.ContainsKey("TableFunction/TabFunc1")); WVPASSEQ(schema["TableFunction/TabFunc1"].name, "TabFunc1"); WVPASSEQ(schema["TableFunction/TabFunc1"].type, "TableFunction"); WVPASSEQ(schema["TableFunction/TabFunc1"].text, sc.tabfuncq); WVASSERT(schema.ContainsKey("Trigger/Trigger1")); WVPASSEQ(schema["Trigger/Trigger1"].name, "Trigger1"); WVPASSEQ(schema["Trigger/Trigger1"].type, "Trigger"); WVPASSEQ(schema["Trigger/Trigger1"].text, sc.triggerq); WVASSERT(schema.ContainsKey("View/View1")); WVPASSEQ(schema["View/View1"].name, "View1"); WVPASSEQ(schema["View/View1"].type, "View"); WVPASSEQ(schema["View/View1"].text, sc.viewq); WVASSERT(schema.ContainsKey("XMLSchema/TestSchema")); WVPASSEQ(schema["XMLSchema/TestSchema"].name, "TestSchema"); WVPASSEQ(schema["XMLSchema/TestSchema"].type, "XMLSchema"); WVPASSEQ(schema["XMLSchema/TestSchema"].text, sc.xmlq); // Check that putting again with no changes doesn't cause errors, even // without the destructive option. WVPASSEQ(VxPutSchema("Table", "Tab1", sc.tab1sch, no_opts), null); WVPASSEQ(VxPutSchema("TableFunction", "TabFunc1", sc.tabfuncq, no_opts), null); WVPASSEQ(VxPutSchema("Procedure", "Func1", sc.func1q, no_opts), null); WVPASSEQ(VxPutSchema("Trigger", "Trigger1", sc.triggerq, no_opts), null); WVPASSEQ(VxPutSchema("View", "View1", sc.viewq, no_opts), null); WVPASSEQ(VxPutSchema("XMLSchema", "TestSchema", sc.xmlq, no_opts), null); string tab1sch2 = "column: name=f4,type=binary,null=0,length=1\n"; VxSchemaError err = VxPutSchema("Table", "Tab1", tab1sch2, no_opts); WVPASS(err != null); WVPASSEQ(err.key, "Table/Tab1"); WVPASSEQ(err.msg, "Refusing to drop columns ([f1], [f2], [f3]) when the destructive option is not set."); WVPASSEQ(err.errnum, -1); schema = dbus.Get("Table/Tab1"); WVPASSEQ(schema["Table/Tab1"].name, "Tab1"); WVPASSEQ(schema["Table/Tab1"].type, "Table"); WVPASSEQ(schema["Table/Tab1"].text, sc.tab1sch); WVPASSEQ(VxPutSchema("Table", "Tab1", tab1sch2, VxPutOpts.Destructive), null); schema = dbus.Get("Table/Tab1"); WVPASSEQ(schema["Table/Tab1"].name, "Tab1"); WVPASSEQ(schema["Table/Tab1"].type, "Table"); WVPASSEQ(schema["Table/Tab1"].text, tab1sch2); string msg2 = "This is definitely not the Func1 you thought you knew."; string func1q2 = "create procedure Func1 as select '" + msg2 + "'"; WVPASSEQ(VxPutSchema("Procedure", "Func1", func1q2, no_opts), null); schema = dbus.Get("Procedure/Func1"); WVPASSEQ(schema["Procedure/Func1"].name, "Func1"); WVPASSEQ(schema["Procedure/Func1"].type, "Procedure"); WVPASSEQ(schema["Procedure/Func1"].text, func1q2); sc.Cleanup(); }
public void TestDropSchema() { SchemaCreator sc = new SchemaCreator(this); sc.Create(); VxSchemaChecksums sums = dbus.GetChecksums(); WVASSERT(sums.ContainsKey("Procedure/Func1")); WVASSERT(sums.ContainsKey("ScalarFunction/Func2")); WVASSERT(sums.ContainsKey("Table/Tab1")); WVASSERT(sums.ContainsKey("Table/Tab2")); WVASSERT(sums.ContainsKey("XMLSchema/TestSchema")); dbus.DropSchema("Procedure/Func1", "ScalarFunction/Func2", "Table/Tab2", "XMLSchema/TestSchema"); sums = dbus.GetChecksums(); WVASSERT(!sums.ContainsKey("Procedure/Func1")); WVASSERT(!sums.ContainsKey("ScalarFunction/Func2")); WVASSERT(sums.ContainsKey("Table/Tab1")); WVASSERT(!sums.ContainsKey("Table/Tab2")); WVASSERT(!sums.ContainsKey("XMLSchema/TestSchema")); VxSchemaErrors errs = dbus.DropSchema("Procedure/Func1"); WVPASSEQ(errs.Count, 1); WVPASSEQ(errs["Procedure/Func1"][0].msg, "Cannot drop the procedure 'Func1', because it does not exist " + "or you do not have permission."); sc.Cleanup(); }
public void TestXmlSchemaChecksums() { SchemaCreator sc = new SchemaCreator(this); WVASSERT(VxExec(sc.xmlq)); VxSchemaChecksums sums; sums = dbus.GetChecksums(); WVPASSEQ(sums["XMLSchema/TestSchema"].checksums.Count(), 1); WVPASSEQ(sums["XMLSchema/TestSchema"].checksums.First(), 4105357156); WVASSERT(VxExec("drop xml schema collection TestSchema")); sc.Cleanup(); }
public void TestTableChecksums() { SchemaCreator sc = new SchemaCreator(this); sc.Create(); VxSchemaChecksums sums; sums = dbus.GetChecksums(); // Three columns, and two indexes each with two columns, gives us // seven checksums WVPASSEQ(sums["Table/Tab1"].checksums.Count(), 7); WVPASSEQ(sums["Table/Tab1"].checksums.ElementAt(0), 0x00B0B636) WVPASSEQ(sums["Table/Tab1"].checksums.ElementAt(1), 0x1D32C7EA) WVPASSEQ(sums["Table/Tab1"].checksums.ElementAt(2), 0x968DBEDC) WVPASSEQ(sums["Table/Tab1"].checksums.ElementAt(3), 0xAB109B86) WVPASSEQ(sums["Table/Tab1"].checksums.ElementAt(4), 0xC1A74EA4) WVPASSEQ(sums["Table/Tab1"].checksums.ElementAt(5), 0xE50EE702) WVPASSEQ(sums["Table/Tab1"].checksums.ElementAt(6), 0xE8634548) WVASSERT(VxExec("drop table Tab1")); sc.Cleanup(); }