using System;\r
using System.Collections.Generic;\r
using System.Data;\r
+using System.IO;\r
using System.Linq;\r
\r
#if MONO_STRICT\r
#endif\r
\r
using DbLinq.Factory;\r
-using DbLinq.Logging;\r
using DbLinq.Schema;\r
using DbLinq.Schema.Dbml;\r
+using System.Text.RegularExpressions;\r
\r
namespace DbLinq.Vendor.Implementation\r
{\r
-#if MONO_STRICT\r
- internal\r
-#else\r
+#if !MONO_STRICT\r
public\r
#endif\r
- abstract partial class SchemaLoader : ISchemaLoader\r
+ abstract partial class SchemaLoader : ISchemaLoader\r
{\r
- public virtual string VendorName { get { return Vendor.VendorName; } }\r
- public abstract IVendor Vendor { get; }\r
- public abstract System.Type DataContextType { get; }\r
+ /// <summary>\r
+ /// Underlying vendor\r
+ /// </summary>\r
+ /// <value></value>\r
+ public abstract IVendor Vendor { get; set; }\r
+ /// <summary>\r
+ /// Connection used to read schema\r
+ /// </summary>\r
+ /// <value></value>\r
public IDbConnection Connection { get; set; }\r
+ /// <summary>\r
+ /// Gets or sets the name formatter.\r
+ /// </summary>\r
+ /// <value>The name formatter.</value>\r
public INameFormatter NameFormatter { get; set; }\r
- public ILogger Logger { get; set; }\r
\r
+ private TextWriter log;\r
+ /// <summary>\r
+ /// Log output\r
+ /// </summary>\r
+ public TextWriter Log\r
+ {\r
+ get { return log ?? Console.Out; }\r
+ set { log = value; }\r
+ }\r
+\r
+ /// <summary>\r
+ /// Loads database schema\r
+ /// </summary>\r
+ /// <param name="databaseName"></param>\r
+ /// <param name="nameAliases"></param>\r
+ /// <param name="nameFormat"></param>\r
+ /// <param name="loadStoredProcedures"></param>\r
+ /// <param name="contextNamespace"></param>\r
+ /// <param name="entityNamespace"></param>\r
+ /// <returns></returns>\r
public virtual Database Load(string databaseName, INameAliases nameAliases, NameFormat nameFormat,\r
bool loadStoredProcedures, string contextNamespace, string entityNamespace)\r
{\r
if (string.IsNullOrEmpty(databaseName))\r
throw new ArgumentException("A database name is required. Please specify /database=<databaseName>");\r
\r
+ databaseName = GetDatabaseNameAliased(databaseName, nameAliases);\r
+\r
var schemaName = NameFormatter.GetSchemaName(databaseName, GetExtraction(databaseName), nameFormat);\r
var names = new Names();\r
var schema = new Database\r
{\r
Name = schemaName.DbName,\r
- Class = schemaName.ClassName,\r
+ Class = GetRuntimeClassName(schemaName.ClassName, nameAliases),\r
BaseType = typeof(DataContext).FullName,\r
ContextNamespace = contextNamespace,\r
EntityNamespace = entityNamespace,\r
//CheckNamesSafety(schema);\r
\r
// generate backing fields name (since we have here correct names)\r
- GenerateStorageFields(schema);\r
+ GenerateStorageAndMemberFields(schema);\r
\r
return schema;\r
}\r
\r
+ /// <summary>\r
+ /// Gets a usable name for the database.\r
+ /// </summary>\r
+ /// <param name="databaseName">Name of the database.</param>\r
+ /// <returns></returns>\r
+ protected virtual string GetDatabaseName(string databaseName)\r
+ {\r
+ return databaseName;\r
+ }\r
+\r
+ protected virtual string GetDatabaseNameAliased(string databaseName, INameAliases nameAliases)\r
+ {\r
+ string databaseNameAliased = nameAliases != null ? nameAliases.GetDatabaseNameAlias(databaseName) : null;\r
+ return (databaseNameAliased != null) ? databaseNameAliased : GetDatabaseName(databaseName);\r
+ }\r
+\r
+ /// <summary>\r
+ /// Gets a usable name for the database class.\r
+ /// </summary>\r
+ /// <param name="databaseName">Name of the clas.</param>\r
+ /// <returns></returns>\r
+ protected virtual string GetRuntimeClassName(string className, INameAliases nameAliases)\r
+ {\r
+ string classNameAliased = nameAliases != null ? nameAliases.GetClassNameAlias(className) : null;\r
+ return (classNameAliased != null) ? classNameAliased : className;\r
+ }\r
+\r
+ /// <summary>\r
+ /// Writes an error line.\r
+ /// </summary>\r
+ /// <param name="format">The format.</param>\r
+ /// <param name="arg">The arg.</param>\r
+ protected void WriteErrorLine(string format, params object[] arg)\r
+ {\r
+ var o = Log;\r
+ if (o == Console.Out)\r
+ o = Console.Error;\r
+ o.WriteLine(format, arg);\r
+ }\r
+\r
protected SchemaLoader()\r
{\r
- Logger = ObjectFactory.Get<ILogger>();\r
NameFormatter = ObjectFactory.Create<INameFormatter>(); // the Pluralize property is set dynamically, so no singleton\r
}\r
\r
+ /// <summary>\r
+ /// Gets the extraction type from a columnname.\r
+ /// </summary>\r
+ /// <param name="dbColumnName">Name of the db column.</param>\r
+ /// <returns></returns>\r
protected virtual WordsExtraction GetExtraction(string dbColumnName)\r
{\r
bool isMixedCase = dbColumnName != dbColumnName.ToLower() && dbColumnName != dbColumnName.ToUpper();\r
return isMixedCase ? WordsExtraction.FromCase : WordsExtraction.FromDictionary;\r
}\r
\r
+ /// <summary>\r
+ /// Gets the full name of a name and schema.\r
+ /// </summary>\r
+ /// <param name="dbName">Name of the db.</param>\r
+ /// <param name="dbSchema">The db schema.</param>\r
+ /// <returns></returns>\r
protected virtual string GetFullDbName(string dbName, string dbSchema)\r
{\r
string fullDbName;\r
return fullDbName;\r
}\r
\r
+ /// <summary>\r
+ /// Creates the name of the table given a name and schema\r
+ /// </summary>\r
+ /// <param name="dbTableName">Name of the db table.</param>\r
+ /// <param name="dbSchema">The db schema.</param>\r
+ /// <param name="nameAliases">The name aliases.</param>\r
+ /// <param name="nameFormat">The name format.</param>\r
+ /// <param name="extraction">The extraction.</param>\r
+ /// <returns></returns>\r
protected virtual TableName CreateTableName(string dbTableName, string dbSchema, INameAliases nameAliases, NameFormat nameFormat, WordsExtraction extraction)\r
{\r
// if we have an alias, use it, and don't try to analyze it (a human probably already did the job)\r
return CreateTableName(dbTableName, dbSchema, nameAliases, nameFormat, GetExtraction(dbTableName));\r
}\r
\r
+ Regex startsWithNumber = new Regex(@"^\d", RegexOptions.Compiled);\r
+\r
+ /// <summary>\r
+ /// Creates the name of the column.\r
+ /// </summary>\r
+ /// <param name="dbColumnName">Name of the db column.</param>\r
+ /// <param name="dbTableName">Name of the db table.</param>\r
+ /// <param name="dbSchema">The db schema.</param>\r
+ /// <param name="nameAliases">The name aliases.</param>\r
+ /// <param name="nameFormat">The name format.</param>\r
+ /// <returns></returns>\r
protected virtual ColumnName CreateColumnName(string dbColumnName, string dbTableName, string dbSchema, INameAliases nameAliases, NameFormat nameFormat)\r
{\r
var columnNameAlias = nameAliases != null ? nameAliases.GetColumnMemberAlias(dbColumnName, dbTableName, dbSchema) : null;\r
var tableName = CreateTableName(dbTableName, dbSchema, nameAliases, nameFormat);\r
if (columnName.PropertyName == tableName.ClassName)\r
columnName.PropertyName = columnName.PropertyName + "1";\r
+\r
+ if (startsWithNumber.IsMatch(columnName.PropertyName))\r
+ columnName.PropertyName = "_" + columnName.PropertyName;\r
+\r
columnName.DbName = dbColumnName;\r
return columnName;\r
}\r
\r
+ /// <summary>\r
+ /// Creates the name of the procedure.\r
+ /// </summary>\r
+ /// <param name="dbProcedureName">Name of the db procedure.</param>\r
+ /// <param name="dbSchema">The db schema.</param>\r
+ /// <param name="nameFormat">The name format.</param>\r
+ /// <returns></returns>\r
protected virtual ProcedureName CreateProcedureName(string dbProcedureName, string dbSchema, NameFormat nameFormat)\r
{\r
var procedureName = NameFormatter.GetProcedureName(dbProcedureName, GetExtraction(dbProcedureName), nameFormat);\r
return procedureName;\r
}\r
\r
+ /// <summary>\r
+ /// Creates the name of the association.\r
+ /// </summary>\r
+ /// <param name="dbManyName">Name of the db many.</param>\r
+ /// <param name="dbManySchema">The db many schema.</param>\r
+ /// <param name="dbOneName">Name of the db one.</param>\r
+ /// <param name="dbOneSchema">The db one schema.</param>\r
+ /// <param name="dbConstraintName">Name of the db constraint.</param>\r
+ /// <param name="foreignKeyName">Name of the foreign key.</param>\r
+ /// <param name="nameFormat">The name format.</param>\r
+ /// <returns></returns>\r
protected virtual AssociationName CreateAssociationName(string dbManyName, string dbManySchema,\r
string dbOneName, string dbOneSchema, string dbConstraintName, string foreignKeyName, NameFormat nameFormat)\r
{\r
return associationName;\r
}\r
\r
+ /// <summary>\r
+ /// Creates the name of the schema.\r
+ /// </summary>\r
+ /// <param name="databaseName">Name of the database.</param>\r
+ /// <param name="connection">The connection.</param>\r
+ /// <param name="nameFormat">The name format.</param>\r
+ /// <returns></returns>\r
protected virtual SchemaName CreateSchemaName(string databaseName, IDbConnection connection, NameFormat nameFormat)\r
{\r
if (string.IsNullOrEmpty(databaseName))\r
}\r
}\r
\r
+ /// <summary>\r
+ /// Loads the tables in the given schema.\r
+ /// </summary>\r
+ /// <param name="schema">The schema.</param>\r
+ /// <param name="schemaName">Name of the schema.</param>\r
+ /// <param name="conn">The conn.</param>\r
+ /// <param name="nameAliases">The name aliases.</param>\r
+ /// <param name="nameFormat">The name format.</param>\r
+ /// <param name="names">The names.</param>\r
protected virtual void LoadTables(Database schema, SchemaName schemaName, IDbConnection conn, INameAliases nameAliases, NameFormat nameFormat, Names names)\r
{\r
var tables = ReadTables(conn, schemaName.DbName);\r
}\r
}\r
\r
+ /// <summary>\r
+ /// Loads the columns.\r
+ /// </summary>\r
+ /// <param name="schema">The schema.</param>\r
+ /// <param name="schemaName">Name of the schema.</param>\r
+ /// <param name="conn">The conn.</param>\r
+ /// <param name="nameAliases">The name aliases.</param>\r
+ /// <param name="nameFormat">The name format.</param>\r
+ /// <param name="names">The names.</param>\r
protected void LoadColumns(Database schema, SchemaName schemaName, IDbConnection conn, INameAliases nameAliases, NameFormat nameFormat, Names names)\r
{\r
var columnRows = ReadColumns(conn, schemaName.DbName);\r
DbLinq.Schema.Dbml.Table tableSchema = schema.Tables.FirstOrDefault(tblSchema => fullColumnDbName == tblSchema.Name);\r
if (tableSchema == null)\r
{\r
- Logger.Write(Level.Error, "ERROR L46: Table '" + columnRow.TableName + "' not found for column " + columnRow.ColumnName);\r
+ WriteErrorLine("ERROR L46: Table '" + columnRow.TableName + "' not found for column " + columnRow.ColumnName);\r
continue;\r
}\r
var column = new Column();\r
if (columnRow.PrimaryKey.HasValue)\r
column.IsPrimaryKey = columnRow.PrimaryKey.Value;\r
\r
- if (columnRow.Generated.HasValue)\r
- column.IsDbGenerated = columnRow.Generated.Value;\r
+ bool? generated = (nameAliases != null) ? nameAliases.GetColumnGenerated(columnRow.ColumnName, columnRow.TableName, columnRow.TableSchema) : null;\r
+ if (!generated.HasValue)\r
+ generated = columnRow.Generated;\r
+ if (generated.HasValue)\r
+ column.IsDbGenerated = generated.Value;\r
+\r
+ AutoSync? autoSync = (nameAliases != null) ? nameAliases.GetColumnAutoSync(columnRow.ColumnName, columnRow.TableName, columnRow.TableSchema) : null;\r
+ if (autoSync.HasValue)\r
+ column.AutoSync = autoSync.Value;\r
\r
// the Expression can originate from two sources:\r
// 1. DefaultValue\r
\r
column.CanBeNull = columnRow.Nullable;\r
\r
+ string columnTypeAlias = nameAliases != null ? nameAliases.GetColumnForcedType(columnRow.ColumnName, columnRow.TableName, columnRow.TableSchema) : null;\r
var columnType = MapDbType(columnName.DbName, columnRow);\r
\r
var columnEnumType = columnType as EnumType;\r
enumType[enumValue.Key] = enumValue.Value;\r
}\r
}\r
+ else if (columnTypeAlias != null)\r
+ column.Type = columnTypeAlias;\r
else\r
column.Type = columnType.ToString();\r
\r