public virtual object Insert <TEntity>(Expression <Func <TEntity> > content, string table) { Utils.CheckNull(content); TypeDescriptor typeDescriptor = EntityTypeContainer.GetDescriptor(typeof(TEntity)); if (typeDescriptor.PrimaryKeys.Count > 1) { /* 对于多主键的实体,暂时不支持调用这个方法进行插入 */ throw new NotSupportedException(string.Format("Can not call this method because entity '{0}' has multiple keys.", typeDescriptor.Definition.Type.FullName)); } PropertyDescriptor keyPropertyDescriptor = typeDescriptor.PrimaryKeys.FirstOrDefault(); Dictionary <MemberInfo, Expression> insertColumns = InitMemberExtractor.Extract(content); DbTable explicitDbTable = null; if (table != null) { explicitDbTable = new DbTable(table, typeDescriptor.Table.Schema); } DefaultExpressionParser expressionParser = typeDescriptor.GetExpressionParser(explicitDbTable); DbInsertExpression e = new DbInsertExpression(explicitDbTable ?? typeDescriptor.Table); object keyVal = null; foreach (var kv in insertColumns) { MemberInfo key = kv.Key; PropertyDescriptor propertyDescriptor = typeDescriptor.TryGetPropertyDescriptor(key); if (propertyDescriptor == null) { throw new ChloeException(string.Format("The member '{0}' does not map any column.", key.Name)); } if (propertyDescriptor.IsAutoIncrement) { throw new ChloeException(string.Format("Could not insert value into the identity column '{0}'.", propertyDescriptor.Column.Name)); } if (propertyDescriptor.IsPrimaryKey) { object val = ExpressionEvaluator.Evaluate(kv.Value); if (val == null) { throw new ChloeException(string.Format("The primary key '{0}' could not be null.", propertyDescriptor.Property.Name)); } else { keyVal = val; e.InsertColumns.Add(propertyDescriptor.Column, DbExpression.Parameter(keyVal, propertyDescriptor.PropertyType, propertyDescriptor.Column.DbType)); continue; } } e.InsertColumns.Add(propertyDescriptor.Column, expressionParser.Parse(kv.Value)); } if (keyPropertyDescriptor != null) { //主键为空并且主键又不是自增列 if (keyVal == null && !keyPropertyDescriptor.IsAutoIncrement) { throw new ChloeException(string.Format("The primary key '{0}' could not be null.", keyPropertyDescriptor.Property.Name)); } } if (keyPropertyDescriptor == null || !keyPropertyDescriptor.IsAutoIncrement) { this.ExecuteSqlCommand(e); return(keyVal); /* It will return null if an entity does not define primary key. */ } IDbExpressionTranslator translator = this.DatabaseProvider.CreateDbExpressionTranslator(); List <DbParam> parameters; string sql = translator.Translate(e, out parameters); sql = string.Concat(sql, ";", this.GetSelectLastInsertIdClause()); //SELECT @@IDENTITY 返回的是 decimal 类型 object retIdentity = this.Session.ExecuteScalar(sql, parameters.ToArray()); if (retIdentity == null || retIdentity == DBNull.Value) { throw new ChloeException("Unable to get the identity value."); } retIdentity = PublicHelper.ConvertObjType(retIdentity, typeDescriptor.AutoIncrement.PropertyType); return(retIdentity); }
public virtual TEntity Insert <TEntity>(TEntity entity, string table) { Utils.CheckNull(entity); TypeDescriptor typeDescriptor = EntityTypeContainer.GetDescriptor(entity.GetType()); Dictionary <PropertyDescriptor, object> keyValueMap = CreateKeyValueMap(typeDescriptor); Dictionary <PropertyDescriptor, DbExpression> insertColumns = new Dictionary <PropertyDescriptor, DbExpression>(); foreach (PropertyDescriptor propertyDescriptor in typeDescriptor.PropertyDescriptors) { if (propertyDescriptor.IsAutoIncrement) { continue; } object val = propertyDescriptor.GetValue(entity); if (propertyDescriptor.IsPrimaryKey) { keyValueMap[propertyDescriptor] = val; } DbParameterExpression valExp = DbExpression.Parameter(val, propertyDescriptor.PropertyType, propertyDescriptor.Column.DbType); insertColumns.Add(propertyDescriptor, valExp); } PropertyDescriptor nullValueKey = keyValueMap.Where(a => a.Value == null && !a.Key.IsAutoIncrement).Select(a => a.Key).FirstOrDefault(); if (nullValueKey != null) { /* 主键为空并且主键又不是自增列 */ throw new ChloeException(string.Format("The primary key '{0}' could not be null.", nullValueKey.Property.Name)); } DbTable dbTable = table == null ? typeDescriptor.Table : new DbTable(table, typeDescriptor.Table.Schema); DbInsertExpression e = new DbInsertExpression(dbTable); foreach (var kv in insertColumns) { e.InsertColumns.Add(kv.Key.Column, kv.Value); } PropertyDescriptor autoIncrementPropertyDescriptor = typeDescriptor.AutoIncrement; if (autoIncrementPropertyDescriptor == null) { this.ExecuteSqlCommand(e); return(entity); } IDbExpressionTranslator translator = this.DatabaseProvider.CreateDbExpressionTranslator(); List <DbParam> parameters; string sql = translator.Translate(e, out parameters); sql = string.Concat(sql, ";", this.GetSelectLastInsertIdClause()); //SELECT @@IDENTITY 返回的是 decimal 类型 object retIdentity = this.Session.ExecuteScalar(sql, parameters.ToArray()); if (retIdentity == null || retIdentity == DBNull.Value) { throw new ChloeException("Unable to get the identity value."); } retIdentity = PublicHelper.ConvertObjType(retIdentity, autoIncrementPropertyDescriptor.PropertyType); autoIncrementPropertyDescriptor.SetValue(entity, retIdentity); return(entity); }