public void TestAlterSchemaBaseClass() { MockRepository mocks = new MockRepository(); FeatureSchema schema = new FeatureSchema("Default", ""); IConnection conn = mocks.DynamicMock <IConnection>(); ISchemaCapabilities caps = mocks.DynamicMock <ISchemaCapabilities>(); using (mocks.Record()) { SetupResult.For(conn.ConnectionState).Return(ConnectionState.ConnectionState_Open); SetupResult.For(conn.SchemaCapabilities).Return(caps); SetupResult.For(caps.ClassTypes).Return((ClassType[])Enum.GetValues(typeof(ClassType))); SetupResult.For(caps.DataTypes).Return((DataType[])Enum.GetValues(typeof(DataType))); SetupResult.For(caps.MaximumDecimalPrecision).Return(20); SetupResult.For(caps.MaximumDecimalScale).Return(20); SetupResult.For(caps.ReservedCharactersForName).Return(string.Empty); SetupResult.For(caps.SupportedAutoGeneratedTypes).Return(new DataType[] { DataType.DataType_Int32, DataType.DataType_Int64 }); SetupResult.For(caps.SupportedIdentityPropertyTypes).Return(new DataType[] { DataType.DataType_Int32, DataType.DataType_Int64 }); SetupResult.For(caps.SupportsAssociationProperties).Return(false); SetupResult.For(caps.SupportsAutoIdGeneration).Return(true); SetupResult.For(caps.SupportsCompositeId).Return(false); SetupResult.For(caps.SupportsCompositeUniqueValueConstraints).Return(false); SetupResult.For(caps.SupportsDataStoreScopeUniqueIdGeneration).Return(false); SetupResult.For(caps.SupportsDefaultValue).Return(true); SetupResult.For(caps.SupportsExclusiveValueRangeConstraints).Return(false); SetupResult.For(caps.SupportsInclusiveValueRangeConstraints).Return(false); SetupResult.For(caps.SupportsMultipleSchemas).Return(false); SetupResult.For(caps.SupportsNetworkModel).Return(false); SetupResult.For(caps.SupportsNullValueConstraints).Return(true); SetupResult.For(caps.SupportsObjectProperties).Return(false); SetupResult.For(caps.SupportsSchemaModification).Return(true); SetupResult.For(caps.SupportsSchemaOverrides).Return(false); SetupResult.For(caps.SupportsUniqueValueConstraints).Return(false); SetupResult.For(caps.SupportsValueConstraintsList).Return(false); SetupResult.For(caps.SupportsInheritance).Return(false); } FdoFeatureService service = mocks.DynamicMock <FdoFeatureService>(conn); mocks.ReplayAll(); ClassDefinition baseClass = new Class("Base", ""); //ID DataPropertyDefinition id = new DataPropertyDefinition("ID", ""); id.DataType = DataType.DataType_Int64; id.Nullable = false; baseClass.Properties.Add(id); baseClass.IdentityProperties.Add(id); //Name DataPropertyDefinition name = new DataPropertyDefinition("Name", ""); name.DataType = DataType.DataType_String; name.Nullable = true; name.Length = 100; baseClass.Properties.Add(name); ClassDefinition derivedClass = new Class("Derived", ""); derivedClass.BaseClass = baseClass; //DOB DataPropertyDefinition dob = new DataPropertyDefinition("DOB", ""); dob.DataType = DataType.DataType_DateTime; dob.Nullable = true; derivedClass.Properties.Add(dob); schema.Classes.Add(baseClass); schema.Classes.Add(derivedClass); IncompatibleSchema incSchema = null; bool canApply = service.CanApplySchema(schema, out incSchema); Assert.IsFalse(canApply); Assert.IsNotNull(incSchema); FeatureSchema newSchema = service.AlterSchema(schema, incSchema); ClassDefinition newClass = newSchema.Classes[newSchema.Classes.IndexOf("Derived")]; //Base class properties should be copied to derived class Assert.AreEqual("BASE_ID", newClass.IdentityProperties[0].Name); Assert.AreEqual(3, newClass.Properties.Count); Assert.IsTrue(newClass.Properties.IndexOf("BASE_ID") >= 0); Assert.IsTrue(newClass.Properties.IndexOf("BASE_Name") >= 0); }
public void TestAlterSchemaPassIdentityType() { MockRepository mocks = new MockRepository(); IConnection conn = mocks.DynamicMock <IConnection>(); ISchemaCapabilities caps = mocks.DynamicMock <ISchemaCapabilities>(); using (mocks.Record()) { SetupResult.For(conn.ConnectionState).Return(ConnectionState.ConnectionState_Open); SetupResult.For(conn.SchemaCapabilities).Return(caps); SetupResult.For(caps.ClassTypes).Return((ClassType[])Enum.GetValues(typeof(ClassType))); SetupResult.For(caps.DataTypes).Return((DataType[])Enum.GetValues(typeof(DataType))); SetupResult.For(caps.MaximumDecimalPrecision).Return(20); SetupResult.For(caps.MaximumDecimalScale).Return(20); SetupResult.For(caps.ReservedCharactersForName).Return(string.Empty); SetupResult.For(caps.SupportedAutoGeneratedTypes).Return(new DataType[] { DataType.DataType_Int64 }); //-- SetupResult.For(caps.SupportedIdentityPropertyTypes).Return(new DataType[] { DataType.DataType_Int32, DataType.DataType_Int64, DataType.DataType_String }); //-- SetupResult.For(caps.SupportsAssociationProperties).Return(false); SetupResult.For(caps.SupportsAutoIdGeneration).Return(true); SetupResult.For(caps.SupportsCompositeId).Return(false); SetupResult.For(caps.SupportsCompositeUniqueValueConstraints).Return(false); SetupResult.For(caps.SupportsDataStoreScopeUniqueIdGeneration).Return(false); SetupResult.For(caps.SupportsDefaultValue).Return(true); SetupResult.For(caps.SupportsExclusiveValueRangeConstraints).Return(false); SetupResult.For(caps.SupportsInclusiveValueRangeConstraints).Return(false); SetupResult.For(caps.SupportsMultipleSchemas).Return(false); SetupResult.For(caps.SupportsNetworkModel).Return(false); SetupResult.For(caps.SupportsNullValueConstraints).Return(true); SetupResult.For(caps.SupportsObjectProperties).Return(false); SetupResult.For(caps.SupportsSchemaModification).Return(true); SetupResult.For(caps.SupportsSchemaOverrides).Return(false); SetupResult.For(caps.SupportsUniqueValueConstraints).Return(false); SetupResult.For(caps.SupportsValueConstraintsList).Return(false); SetupResult.For(caps.SupportsInheritance).Return(false); } FdoFeatureService service = mocks.StrictMock <FdoFeatureService>(conn); mocks.ReplayAll(); FeatureSchema schema = new FeatureSchema("Default", ""); ClassDefinition cls = new Class("Test", ""); //ID - float DataPropertyDefinition id = new DataPropertyDefinition("ID", ""); id.DataType = DataType.DataType_Single; id.Nullable = false; cls.Properties.Add(id); cls.IdentityProperties.Add(id); //Name DataPropertyDefinition name = new DataPropertyDefinition("Name", ""); name.DataType = DataType.DataType_String; name.Nullable = true; name.Length = 100; cls.Properties.Add(name); schema.Classes.Add(cls); IncompatibleSchema incSchema = null; bool canApply = service.CanApplySchema(schema, out incSchema); Assert.IsFalse(canApply); Assert.IsNotNull(incSchema); FeatureSchema newSchema = service.AlterSchema(schema, incSchema); ClassDefinition newClass = newSchema.Classes[0]; //Should have been "promoted" to string Assert.AreEqual(DataType.DataType_String, newClass.IdentityProperties[0].DataType); }
/// <summary> /// Creates a FDO bulk copy task. The target file will be created as part of /// this method call. If the target path is a directory, it is assumed that /// SHP files are to be created and copied to. /// </summary> /// <param name="sourceFile">The path to the source file.</param> /// <param name="targetPath"> /// The path to the target file/directory. If it is a directory, it is assumed /// that SHP files are to be created and copied to. /// </param> /// <param name="copySpatialContexts">If true, will also copy spatial contexts</param> /// <param name="fixIncompatibleSchema">If true, will try to fix the source schema to make it compatible with the target connection. If false, an exception will be thrown</param> /// <param name="flattenGeometries">If true, will strip all Z and M coordinates from all geometries that are copied</param> /// <returns></returns> public static FdoBulkCopy CreateBulkCopy(string sourceFile, string targetPath, bool copySpatialContexts, bool fixIncompatibleSchema, bool flattenGeometries) { FdoBulkCopyOptions options = null; FdoConnection source = null; FdoConnection target = null; try { //Is a directory. Implies a SHP connection if (IsShp(targetPath)) { //SHP doesn't actually support CreateDataStore. We use the following technique: // - Connect to base directory // - Clone source schema and apply to SHP connection. // - A SHP file and related files are created for each feature class. string shpdir = Directory.Exists(targetPath) ? targetPath : Path.GetDirectoryName(targetPath); source = CreateFlatFileConnection(sourceFile); target = new FdoConnection("OSGeo.SHP", "DefaultFileLocation=" + shpdir); source.Open(); //Verify source has only classes with single geometry storage and only one geometry using (FdoFeatureService svc = source.CreateFeatureService()) { using (FeatureSchemaCollection schemas = svc.DescribeSchema()) { foreach (FeatureSchema sch in schemas) { foreach (ClassDefinition cd in sch.Classes) { int geomProps = 0; foreach (PropertyDefinition pd in cd.Properties) { if (pd.PropertyType == PropertyType.PropertyType_GeometricProperty) { GeometricPropertyDefinition gp = pd as GeometricPropertyDefinition; GeometricType[] types = FdoGeometryUtil.GetGeometricTypes(gp.GeometryTypes); if (types.Length != 1 || (types.Length == 1 && types[0] == GeometricType.GeometricType_All)) { throw new FdoETLException(string.Format("Source file cannot be copied to a SHP file. {0}:{1}.{2} has more than one geometry storage type", sch.Name, cd.Name, pd.Name)); } geomProps++; } } if (geomProps > 1) { throw new FdoETLException("Source file cannot be copied to a SHP file. One or more feature classes have more than one geometry property"); } } } } } } else { if (!CreateFlatFileDataSource(targetPath)) { throw new FdoException("Unable to create data source on: " + targetPath); } source = CreateFlatFileConnection(sourceFile); target = CreateFlatFileConnection(targetPath); } //Source and target connections may have been opened before this point if (source.State == FdoConnectionState.Closed) { source.Open(); } if (target.State == FdoConnectionState.Closed) { target.Open(); } string srcName = "SOURCE"; string dstName = "TARGET"; Dictionary <string, FdoConnection> connections = new Dictionary <string, FdoConnection>(); connections.Add(srcName, source); connections.Add(dstName, target); options = new FdoBulkCopyOptions(connections, true); if (copySpatialContexts) { CopyAllSpatialContexts(source, target, true); } using (FdoFeatureService srcService = source.CreateFeatureService()) using (FdoFeatureService destService = target.CreateFeatureService()) { FeatureSchemaCollection schemas = srcService.DescribeSchema(); //Assume single-schema FeatureSchema fs = schemas[0]; //Clone and apply to target FeatureSchema targetSchema = FdoSchemaUtil.CloneSchema(fs); IncompatibleSchema incSchema; string sourceSchemaName = fs.Name; string targetSchemaName = string.Empty; bool canApply = destService.CanApplySchema(targetSchema, out incSchema); if (canApply) { destService.ApplySchema(targetSchema); targetSchemaName = targetSchema.Name; } else { if (fixIncompatibleSchema) { FeatureSchema fixedSchema = destService.AlterSchema(targetSchema, incSchema); destService.ApplySchema(fixedSchema); targetSchemaName = fixedSchema.Name; } else { throw new Exception(incSchema.ToString()); } } //Copy all classes foreach (ClassDefinition cd in fs.Classes) { FdoClassCopyOptions copt = new FdoClassCopyOptions(srcName, dstName, sourceSchemaName, cd.Name, targetSchemaName, cd.Name); copt.Name = "Copy source to target [" + cd.Name + "]"; copt.FlattenGeometries = flattenGeometries; options.AddClassCopyOption(copt); //Flick on batch support if we can if (destService.SupportsBatchInsertion()) { copt.BatchSize = 300; //Madness? THIS IS SPARTA! } } } } catch (Exception) { if (source != null) { source.Dispose(); } if (target != null) { target.Dispose(); } throw; } return(new FdoBulkCopy(options)); }
public void TestAlterSchemaPassValueConstraints() { MockRepository mocks = new MockRepository(); IConnection conn = mocks.DynamicMock <IConnection>(); ISchemaCapabilities caps = mocks.DynamicMock <ISchemaCapabilities>(); using (mocks.Record()) { SetupResult.For(conn.ConnectionState).Return(ConnectionState.ConnectionState_Open); SetupResult.For(conn.SchemaCapabilities).Return(caps); SetupResult.For(caps.ClassTypes).Return((ClassType[])Enum.GetValues(typeof(ClassType))); SetupResult.For(caps.DataTypes).Return((DataType[])Enum.GetValues(typeof(DataType))); SetupResult.For(caps.MaximumDecimalPrecision).Return(20); SetupResult.For(caps.MaximumDecimalScale).Return(20); SetupResult.For(caps.ReservedCharactersForName).Return(string.Empty); SetupResult.For(caps.SupportedAutoGeneratedTypes).Return(new DataType[] { DataType.DataType_Int64 }); SetupResult.For(caps.SupportedIdentityPropertyTypes).Return(new DataType[] { DataType.DataType_Int32, DataType.DataType_Int64 }); SetupResult.For(caps.SupportsAssociationProperties).Return(false); SetupResult.For(caps.SupportsAutoIdGeneration).Return(true); SetupResult.For(caps.SupportsCompositeId).Return(false); SetupResult.For(caps.SupportsCompositeUniqueValueConstraints).Return(false); SetupResult.For(caps.SupportsDataStoreScopeUniqueIdGeneration).Return(false); SetupResult.For(caps.SupportsDefaultValue).Return(true); //-- SetupResult.For(caps.SupportsExclusiveValueRangeConstraints).Return(false); SetupResult.For(caps.SupportsInclusiveValueRangeConstraints).Return(false); //-- SetupResult.For(caps.SupportsMultipleSchemas).Return(false); SetupResult.For(caps.SupportsNetworkModel).Return(false); SetupResult.For(caps.SupportsNullValueConstraints).Return(true); SetupResult.For(caps.SupportsObjectProperties).Return(false); SetupResult.For(caps.SupportsSchemaModification).Return(true); SetupResult.For(caps.SupportsSchemaOverrides).Return(false); SetupResult.For(caps.SupportsUniqueValueConstraints).Return(false); //-- SetupResult.For(caps.SupportsValueConstraintsList).Return(false); //-- SetupResult.For(caps.SupportsInheritance).Return(false); } FdoFeatureService service = mocks.StrictMock <FdoFeatureService>(conn); mocks.ReplayAll(); FeatureSchema schema = new FeatureSchema("Default", ""); ClassDefinition cls = new Class("Test", ""); //ID DataPropertyDefinition id = new DataPropertyDefinition("ID", ""); id.DataType = DataType.DataType_Int64; id.IsAutoGenerated = true; //Should be converted to int64 id.ReadOnly = true; id.Nullable = false; cls.Properties.Add(id); cls.IdentityProperties.Add(id); //Age DataPropertyDefinition age = new DataPropertyDefinition("Age", ""); PropertyValueConstraintRange range = new PropertyValueConstraintRange(); range.MinValue = new Int32Value(0); range.MinInclusive = true; range.MaxValue = new Int32Value(100); range.MaxInclusive = true; age.ValueConstraint = range; age.DataType = DataType.DataType_Int32; age.Nullable = true; cls.Properties.Add(age); //Gender DataPropertyDefinition gender = new DataPropertyDefinition("Gender", ""); PropertyValueConstraintList list = new PropertyValueConstraintList(); list.ConstraintList.Add(new StringValue("M")); list.ConstraintList.Add(new StringValue("F")); gender.ValueConstraint = list; age.DataType = DataType.DataType_String; age.Nullable = false; age.Length = 1; cls.Properties.Add(gender); schema.Classes.Add(cls); IncompatibleSchema incSchema = null; bool canApply = service.CanApplySchema(schema, out incSchema); Assert.IsFalse(canApply); Assert.IsNotNull(incSchema); FeatureSchema newSchema = service.AlterSchema(schema, incSchema); ClassDefinition newClass = newSchema.Classes[0]; DataPropertyDefinition age2 = newClass.Properties[newClass.Properties.IndexOf("Age")] as DataPropertyDefinition; //Should have constraint removed Assert.IsNull(age2.ValueConstraint); DataPropertyDefinition gender2 = newClass.Properties[newClass.Properties.IndexOf("Gender")] as DataPropertyDefinition; //Should have constraint removed Assert.IsNull(gender2.ValueConstraint); }
public override int Execute() { CommandStatus retCode; FdoConnection srcConn = new FdoConnection(_srcProvider, _srcConnStr); FdoConnection destConn = null; //Directory given, assume SHP if (Directory.Exists(_destPath)) { destConn = new FdoConnection("OSGeo.SHP", "DefaultFileLocation=" + _destPath); } else { if (ExpressUtility.CreateFlatFileDataSource(_destPath)) { destConn = ExpressUtility.CreateFlatFileConnection(_destPath); } else { throw new FdoException("Could not create data source: " + _destPath); } } try { srcConn.Open(); destConn.Open(); string srcName = "SOURCE"; string dstName = "TARGET"; FdoBulkCopyOptions options = new FdoBulkCopyOptions(); options.RegisterConnection(srcName, srcConn); options.RegisterConnection(dstName, destConn); using (FdoFeatureService srcService = srcConn.CreateFeatureService()) using (FdoFeatureService destService = destConn.CreateFeatureService()) { //See if spatial context needs to be copied to target if (!string.IsNullOrEmpty(_srcSpatialContext)) { SpatialContextInfo srcCtx = srcService.GetSpatialContext(_srcSpatialContext); if (srcCtx != null) { Console.WriteLine("Copying spatial context: " + srcCtx.Name); ExpressUtility.CopyAllSpatialContexts(new SpatialContextInfo[] { srcCtx }, destConn, true); } } else { //Copy all ExpressUtility.CopyAllSpatialContexts(srcConn, destConn, true); } FeatureSchema srcSchema = null; //See if partial class list is needed if (_srcClasses.Count > 0) { WriteLine("Checking if partial schema discovery is supported: " + srcService.SupportsPartialSchemaDiscovery()); srcSchema = srcService.PartialDescribeSchema(_srcSchema, _srcClasses); } else //Full copy { WriteLine("No classes specified, reading full source schema"); srcSchema = srcService.GetSchemaByName(_srcSchema); } if (srcSchema == null) { WriteError("Could not find source schema: " + _srcSchema); retCode = CommandStatus.E_FAIL_SCHEMA_NOT_FOUND; } else { WriteLine("Checking source schema for incompatibilities"); FeatureSchema targetSchema = null; IncompatibleSchema incSchema; if (destService.CanApplySchema(srcSchema, out incSchema)) { int clsCount = srcSchema.Classes.Count; WriteLine("Applying source schema (containing " + clsCount + " classes) to target"); destService.ApplySchema(srcSchema, null, true); targetSchema = srcSchema; } else { WriteWarning("Incompatibilities were detected in source schema. Applying a modified version to target"); FeatureSchema fixedSchema = destService.AlterSchema(srcSchema, incSchema); int clsCount = fixedSchema.Classes.Count; WriteLine("Applying modified source schema (containing " + clsCount + " classes) to target"); destService.ApplySchema(fixedSchema, null, true); targetSchema = fixedSchema; } //Now set class copy options foreach (ClassDefinition cd in srcSchema.Classes) { FdoClassCopyOptions copt = new FdoClassCopyOptions(srcName, dstName, srcSchema.Name, cd.Name, targetSchema.Name, cd.Name); copt.FlattenGeometries = _flatten; options.AddClassCopyOption(copt); } if (_flatten) { WriteWarning("The switch -flatten has been defined. Geometries that are copied will have any Z or M coordinates removed"); } FdoBulkCopy copy = new FdoBulkCopy(options); copy.ProcessMessage += new MessageEventHandler(OnMessage); copy.ProcessCompleted += new EventHandler(OnCompleted); Console.WriteLine("Executing bulk copy"); copy.Execute(); List <Exception> errors = new List <Exception>(copy.GetAllErrors()); if (errors.Count > 0) { string file = GenerateLogFileName("bcp-error-"); LogErrors(errors, file); base.WriteError("Errors were encountered during bulk copy."); retCode = CommandStatus.E_FAIL_BULK_COPY_WITH_ERRORS; } else { retCode = CommandStatus.E_OK; } retCode = CommandStatus.E_OK; } } } catch (Exception ex) { WriteException(ex); retCode = CommandStatus.E_FAIL_UNKNOWN; } finally { srcConn.Dispose(); destConn.Dispose(); } return((int)retCode); }