mirror of
https://github.com/nsnail/FreeSql.git
synced 2025-06-19 20:38:16 +08:00
表达式函数,增加DateTime/TimeSpan,并且开始测试与整理
This commit is contained in:
@ -160,11 +160,27 @@ namespace FreeSql.Internal {
|
||||
case ExpressionType.Lambda: return ExpressionLambdaToSql((exp as LambdaExpression)?.Body, _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
case ExpressionType.Convert: return ExpressionLambdaToSql((exp as UnaryExpression)?.Operand, _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
case ExpressionType.Constant: return _common.FormatSql("{0}", (exp as ConstantExpression)?.Value);
|
||||
case ExpressionType.Call:
|
||||
var exp3 = exp as MethodCallExpression;
|
||||
if (exp3.Object.Type.FullName == "System.String") return ExpressionLambdaToSqlCallString(exp3, _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
if (exp3.Object.Type.FullName == "System.Math") return ExpressionLambdaToSqlCallMath(exp3, _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
if (exp3.Object.Type.FullName == "System.DateTime" || exp3.Object.Type.GenericTypeArguments.FirstOrDefault()?.FullName == "System.DateTime") return ExpressionLambdaToSqlCallDateTime(exp3, _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
if (exp3.Object.Type.FullName == "System.TimeSpan" || exp3.Object.Type.GenericTypeArguments.FirstOrDefault()?.FullName == "System.TimeSpan") return ExpressionLambdaToSqlCallTimeSpan(exp3, _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
throw new Exception($"MySqlExpression 未现实函数表达式 {exp3} 解析");
|
||||
case ExpressionType.MemberAccess:
|
||||
var exp4 = exp as MemberExpression;
|
||||
var extRet = "";
|
||||
if (exp4.Expression == null && exp4.Type.FullName == "System.DateTime" && exp4.Member.Name == "Now") return ExpressionLambdaToSqlMemberAccessDateTime(exp4, _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
if (exp4.Expression.Type.FullName == "System.String") extRet = ExpressionLambdaToSqlMemberAccessString(exp4, _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
else if (exp4.Expression.Type.FullName == "System.Math") extRet = ExpressionLambdaToSqlMemberAccessMath(exp4, _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
else if (exp4.Expression.Type.FullName == "System.DateTime" || exp4.Type.GenericTypeArguments.FirstOrDefault()?.FullName == "System.DateTime") extRet = ExpressionLambdaToSqlMemberAccessDateTime(exp4, _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
else if (exp4.Expression.Type.FullName == "System.TimeSpan" || exp4.Type.GenericTypeArguments.FirstOrDefault()?.FullName == "System.TimeSpan") extRet = ExpressionLambdaToSqlMemberAccessTimeSpan(exp4, _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
if (string.IsNullOrEmpty(extRet) == false) return extRet;
|
||||
|
||||
var expStack = new Stack<Expression>();
|
||||
expStack.Push(exp);
|
||||
MethodCallExpression callExp = null;
|
||||
var exp2 = (exp as MemberExpression).Expression;
|
||||
var exp2 = exp4.Expression;
|
||||
while (true) {
|
||||
switch(exp2.NodeType) {
|
||||
case ExpressionType.Constant:
|
||||
@ -188,7 +204,7 @@ namespace FreeSql.Internal {
|
||||
break;
|
||||
}
|
||||
if (expStack.First().NodeType != ExpressionType.Parameter) return _common.FormatSql("{0}", Expression.Lambda(exp).Compile().DynamicInvoke());
|
||||
if (callExp != null) return ExpressionLambdaToSqlCall(callExp, _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
if (callExp != null) return ExpressionLambdaToSql(callExp, _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
if (_tables == null) {
|
||||
var pp = expStack.Pop() as ParameterExpression;
|
||||
var memberExp = expStack.Pop() as MemberExpression;
|
||||
@ -255,7 +271,6 @@ namespace FreeSql.Internal {
|
||||
}
|
||||
if (isQuoteName) name2 = _common.QuoteSqlName(name2);
|
||||
return $"{alias2}.{name2}";
|
||||
case ExpressionType.Call: return ExpressionLambdaToSqlCall(exp as MethodCallExpression, _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
}
|
||||
if (dicExpressionOperator.TryGetValue(exp.NodeType, out var tryoper) == false) return "";
|
||||
var expBinary = exp as BinaryExpression;
|
||||
@ -268,10 +283,17 @@ namespace FreeSql.Internal {
|
||||
left = tmp;
|
||||
}
|
||||
if (right == "NULL") tryoper = tryoper == "=" ? " IS " : " IS NOT ";
|
||||
if (tryoper == "+" && (expBinary.Left.Type.FullName == "System.String" || expBinary.Right.Type.FullName == "System.String")) return _common.StringConcat(left, right, expBinary.Left.Type, expBinary.Right.Type);
|
||||
return $"{left} {tryoper} {right}";
|
||||
}
|
||||
|
||||
internal abstract string ExpressionLambdaToSqlCall(MethodCallExpression exp, List<SelectTableInfo> _tables, List<SelectColumnInfo> _selectColumnMap, SelectTableInfoType tbtype, bool isQuoteName);
|
||||
|
||||
internal abstract string ExpressionLambdaToSqlMemberAccessString(MemberExpression exp, List<SelectTableInfo> _tables, List<SelectColumnInfo> _selectColumnMap, SelectTableInfoType tbtype, bool isQuoteName);
|
||||
internal abstract string ExpressionLambdaToSqlMemberAccessMath(MemberExpression exp, List<SelectTableInfo> _tables, List<SelectColumnInfo> _selectColumnMap, SelectTableInfoType tbtype, bool isQuoteName);
|
||||
internal abstract string ExpressionLambdaToSqlMemberAccessDateTime(MemberExpression exp, List<SelectTableInfo> _tables, List<SelectColumnInfo> _selectColumnMap, SelectTableInfoType tbtype, bool isQuoteName);
|
||||
internal abstract string ExpressionLambdaToSqlMemberAccessTimeSpan(MemberExpression exp, List<SelectTableInfo> _tables, List<SelectColumnInfo> _selectColumnMap, SelectTableInfoType tbtype, bool isQuoteName);
|
||||
internal abstract string ExpressionLambdaToSqlCallString(MethodCallExpression exp, List<SelectTableInfo> _tables, List<SelectColumnInfo> _selectColumnMap, SelectTableInfoType tbtype, bool isQuoteName);
|
||||
internal abstract string ExpressionLambdaToSqlCallMath(MethodCallExpression exp, List<SelectTableInfo> _tables, List<SelectColumnInfo> _selectColumnMap, SelectTableInfoType tbtype, bool isQuoteName);
|
||||
internal abstract string ExpressionLambdaToSqlCallDateTime(MethodCallExpression exp, List<SelectTableInfo> _tables, List<SelectColumnInfo> _selectColumnMap, SelectTableInfoType tbtype, bool isQuoteName);
|
||||
internal abstract string ExpressionLambdaToSqlCallTimeSpan(MethodCallExpression exp, List<SelectTableInfo> _tables, List<SelectColumnInfo> _selectColumnMap, SelectTableInfoType tbtype, bool isQuoteName);
|
||||
}
|
||||
}
|
||||
|
@ -16,6 +16,7 @@ namespace FreeSql.Internal {
|
||||
internal abstract string QuoteSqlName(string name);
|
||||
internal abstract string QuoteParamterName(string name);
|
||||
internal abstract string IsNull(string sql, object value);
|
||||
internal abstract string StringConcat(string left, string right, Type leftType, Type rightType);
|
||||
|
||||
internal ICodeFirst CodeFirst { get; set; }
|
||||
internal TableInfo GetTableByEntity(Type entity) => Utils.GetTableByEntity(entity, this);
|
||||
|
@ -10,7 +10,10 @@ namespace FreeSql.MySql.Curd {
|
||||
|
||||
class MySqlSelect<T1> : FreeSql.Internal.CommonProvider.Select1Provider<T1> where T1 : class {
|
||||
|
||||
internal static string ToSqlStatic(CommonUtils _commonUtils, string _select, string field, StringBuilder _join, StringBuilder _where, string _groupby, string _having, string _orderby, int _skip, int _limit, List<SelectTableInfo> _tables) {
|
||||
internal static string ToSqlStatic(CommonUtils _commonUtils, string _select, string field, StringBuilder _join, StringBuilder _where, string _groupby, string _having, string _orderby, int _skip, int _limit, List<SelectTableInfo> _tables, IFreeSql _orm) {
|
||||
if (_orm.CodeFirst.IsAutoSyncStructure)
|
||||
_orm.CodeFirst.SyncStructure(_tables.Select(a => a.Table.Type).ToArray());
|
||||
|
||||
var sb = new StringBuilder();
|
||||
sb.Append(_select).Append(field).Append(" \r\nFROM ");
|
||||
var tbsjoin = _tables.Where(a => a.Type != SelectTableInfoType.From).ToArray();
|
||||
@ -73,42 +76,42 @@ namespace FreeSql.MySql.Curd {
|
||||
public override ISelect<T1, T2, T3, T4, T5, T6, T7, T8> From<T2, T3, T4, T5, T6, T7, T8>(Expression<Func<ISelectFromExpression<T1>, T2, T3, T4, T5, T6, T7, T8, ISelectFromExpression<T1>>> exp) { this.InternalFrom(exp?.Body); var ret = new MySqlSelect<T1, T2, T3, T4, T5, T6, T7, T8>(_orm, _commonUtils, _commonExpression, null); MySqlSelect<T1>.CopyData(this, ret); return ret; }
|
||||
public override ISelect<T1, T2, T3, T4, T5, T6, T7, T8, T9> From<T2, T3, T4, T5, T6, T7, T8, T9>(Expression<Func<ISelectFromExpression<T1>, T2, T3, T4, T5, T6, T7, T8, T9, ISelectFromExpression<T1>>> exp) { this.InternalFrom(exp?.Body); var ret = new MySqlSelect<T1, T2, T3, T4, T5, T6, T7, T8, T9>(_orm, _commonUtils, _commonExpression, null); MySqlSelect<T1>.CopyData(this, ret); return ret; }
|
||||
public override ISelect<T1, T2, T3, T4, T5, T6, T7, T8, T9, T10> From<T2, T3, T4, T5, T6, T7, T8, T9, T10>(Expression<Func<ISelectFromExpression<T1>, T2, T3, T4, T5, T6, T7, T8, T9, T10, ISelectFromExpression<T1>>> exp) { this.InternalFrom(exp?.Body); var ret = new MySqlSelect<T1, T2, T3, T4, T5, T6, T7, T8, T9, T10>(_orm, _commonUtils, _commonExpression, null); MySqlSelect<T1>.CopyData(this, ret); return ret; }
|
||||
public override string ToSql(string field = null) => ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables);
|
||||
public override string ToSql(string field = null) => ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables, _orm);
|
||||
}
|
||||
class MySqlSelect<T1, T2> : FreeSql.Internal.CommonProvider.Select2Provider<T1, T2> where T1 : class where T2 : class {
|
||||
public MySqlSelect(IFreeSql orm, CommonUtils commonUtils, CommonExpression commonExpression, object dywhere) : base(orm, commonUtils, commonExpression, dywhere) { }
|
||||
public override string ToSql(string field = null) => MySqlSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables);
|
||||
public override string ToSql(string field = null) => MySqlSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables, _orm);
|
||||
}
|
||||
class MySqlSelect<T1, T2, T3> : FreeSql.Internal.CommonProvider.Select3Provider<T1, T2, T3> where T1 : class where T2 : class where T3 : class {
|
||||
public MySqlSelect(IFreeSql orm, CommonUtils commonUtils, CommonExpression commonExpression, object dywhere) : base(orm, commonUtils, commonExpression, dywhere) { }
|
||||
public override string ToSql(string field = null) => MySqlSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables);
|
||||
public override string ToSql(string field = null) => MySqlSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables, _orm);
|
||||
}
|
||||
class MySqlSelect<T1, T2, T3, T4> : FreeSql.Internal.CommonProvider.Select4Provider<T1, T2, T3, T4> where T1 : class where T2 : class where T3 : class where T4 : class {
|
||||
public MySqlSelect(IFreeSql orm, CommonUtils commonUtils, CommonExpression commonExpression, object dywhere) : base(orm, commonUtils, commonExpression, dywhere) { }
|
||||
public override string ToSql(string field = null) => MySqlSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables);
|
||||
public override string ToSql(string field = null) => MySqlSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables, _orm);
|
||||
}
|
||||
class MySqlSelect<T1, T2, T3, T4, T5> : FreeSql.Internal.CommonProvider.Select5Provider<T1, T2, T3, T4, T5> where T1 : class where T2 : class where T3 : class where T4 : class where T5 : class {
|
||||
public MySqlSelect(IFreeSql orm, CommonUtils commonUtils, CommonExpression commonExpression, object dywhere) : base(orm, commonUtils, commonExpression, dywhere) { }
|
||||
public override string ToSql(string field = null) => MySqlSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables);
|
||||
public override string ToSql(string field = null) => MySqlSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables, _orm);
|
||||
}
|
||||
class MySqlSelect<T1, T2, T3, T4, T5, T6> : FreeSql.Internal.CommonProvider.Select6Provider<T1, T2, T3, T4, T5, T6> where T1 : class where T2 : class where T3 : class where T4 : class where T5 : class where T6 : class {
|
||||
public MySqlSelect(IFreeSql orm, CommonUtils commonUtils, CommonExpression commonExpression, object dywhere) : base(orm, commonUtils, commonExpression, dywhere) { }
|
||||
public override string ToSql(string field = null) => MySqlSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables);
|
||||
public override string ToSql(string field = null) => MySqlSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables, _orm);
|
||||
}
|
||||
class MySqlSelect<T1, T2, T3, T4, T5, T6, T7> : FreeSql.Internal.CommonProvider.Select7Provider<T1, T2, T3, T4, T5, T6, T7> where T1 : class where T2 : class where T3 : class where T4 : class where T5 : class where T6 : class where T7 : class {
|
||||
public MySqlSelect(IFreeSql orm, CommonUtils commonUtils, CommonExpression commonExpression, object dywhere) : base(orm, commonUtils, commonExpression, dywhere) { }
|
||||
public override string ToSql(string field = null) => MySqlSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables);
|
||||
public override string ToSql(string field = null) => MySqlSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables, _orm);
|
||||
}
|
||||
class MySqlSelect<T1, T2, T3, T4, T5, T6, T7, T8> : FreeSql.Internal.CommonProvider.Select8Provider<T1, T2, T3, T4, T5, T6, T7, T8> where T1 : class where T2 : class where T3 : class where T4 : class where T5 : class where T6 : class where T7 : class where T8 : class {
|
||||
public MySqlSelect(IFreeSql orm, CommonUtils commonUtils, CommonExpression commonExpression, object dywhere) : base(orm, commonUtils, commonExpression, dywhere) { }
|
||||
public override string ToSql(string field = null) => MySqlSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables);
|
||||
public override string ToSql(string field = null) => MySqlSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables, _orm);
|
||||
}
|
||||
class MySqlSelect<T1, T2, T3, T4, T5, T6, T7, T8, T9> : FreeSql.Internal.CommonProvider.Select9Provider<T1, T2, T3, T4, T5, T6, T7, T8, T9> where T1 : class where T2 : class where T3 : class where T4 : class where T5 : class where T6 : class where T7 : class where T8 : class where T9 : class {
|
||||
public MySqlSelect(IFreeSql orm, CommonUtils commonUtils, CommonExpression commonExpression, object dywhere) : base(orm, commonUtils, commonExpression, dywhere) { }
|
||||
public override string ToSql(string field = null) => MySqlSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables);
|
||||
public override string ToSql(string field = null) => MySqlSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables, _orm);
|
||||
}
|
||||
class MySqlSelect<T1, T2, T3, T4, T5, T6, T7, T8, T9, T10> : FreeSql.Internal.CommonProvider.Select10Provider<T1, T2, T3, T4, T5, T6, T7, T8, T9, T10> where T1 : class where T2 : class where T3 : class where T4 : class where T5 : class where T6 : class where T7 : class where T8 : class where T9 : class where T10 : class {
|
||||
public MySqlSelect(IFreeSql orm, CommonUtils commonUtils, CommonExpression commonExpression, object dywhere) : base(orm, commonUtils, commonExpression, dywhere) { }
|
||||
public override string ToSql(string field = null) => MySqlSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables);
|
||||
public override string ToSql(string field = null) => MySqlSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables, _orm);
|
||||
}
|
||||
}
|
||||
|
@ -23,6 +23,7 @@ namespace FreeSql.MySql {
|
||||
}
|
||||
}
|
||||
}
|
||||
static DateTime dt1970 = new DateTime(1970, 1, 1);
|
||||
public override object AddslashesProcessParam(object param) {
|
||||
if (param == null) return "NULL";
|
||||
if (param is bool || param is bool?)
|
||||
@ -33,21 +34,24 @@ namespace FreeSql.MySql {
|
||||
return ((Enum)param).ToInt64();
|
||||
else if (decimal.TryParse(string.Concat(param), out var trydec))
|
||||
return param;
|
||||
else if (param is DateTime) {
|
||||
DateTime dt = (DateTime)param;
|
||||
return string.Concat("'", dt.ToString("yyyy-MM-dd HH:mm:ss"), "'");
|
||||
} else if (param is DateTime?) {
|
||||
DateTime? dt = param as DateTime?;
|
||||
return string.Concat("'", dt.Value.ToString("yyyy-MM-dd HH:mm:ss"), "'");
|
||||
else if (param is DateTime)
|
||||
return string.Concat("'", ((DateTime)param).ToString("yyyy-MM-dd HH:mm:ss"), "'");
|
||||
else if (param is DateTime?)
|
||||
return string.Concat("'", (param as DateTime?).Value.ToString("yyyy-MM-dd HH:mm:ss"), "'");
|
||||
else if (param is TimeSpan) {
|
||||
var ts = (TimeSpan)param;
|
||||
return string.Concat("'", ts.Ticks > 0 ? "" : "-", ts.TotalHours, dt1970.AddTicks(Math.Abs(ts.Ticks)).ToString(":mm:ss.fff"), "'");
|
||||
} else if (param is TimeSpan) {
|
||||
var ts = (param as TimeSpan?).Value;
|
||||
return string.Concat("'", ts.Ticks > 0 ? "" : "-", ts.TotalHours, dt1970.AddTicks(Math.Abs(ts.Ticks)).ToString(":mm:ss.fff"), "'");
|
||||
} else if (param is IEnumerable) {
|
||||
var sb = new StringBuilder();
|
||||
var ie = param as IEnumerable;
|
||||
foreach (var z in ie) sb.Append(",").Append(AddslashesProcessParam(z));
|
||||
return sb.Length == 0 ? "(NULL)" : sb.Remove(0, 1).Insert(0, "(").Append(")").ToString();
|
||||
} else {
|
||||
return string.Concat("'", param.ToString().Replace("'", "''"), "'");
|
||||
//if (param is string) return string.Concat('N', nparms[a]);
|
||||
}
|
||||
return string.Concat("'", param.ToString().Replace("'", "''"), "'");
|
||||
//if (param is string) return string.Concat('N', nparms[a]);
|
||||
}
|
||||
|
||||
protected override DbCommand CreateCommand() {
|
||||
|
@ -169,12 +169,21 @@ where a.table_schema in ({0}) and a.table_name in ({1})".FormatMySql(isRenameTab
|
||||
return sb.Length == 0 ? null : sb.ToString();
|
||||
}
|
||||
|
||||
Dictionary<string, bool> dicSyced = new Dictionary<string, bool>();
|
||||
public bool SyncStructure<TEntity>() => this.SyncStructure(typeof(TEntity));
|
||||
public bool SyncStructure(params Type[] entityTypes) {
|
||||
var ddl = this.GetComparisonDDLStatements(entityTypes);
|
||||
if (string.IsNullOrEmpty(ddl)) return true;
|
||||
if (entityTypes == null) return true;
|
||||
var syncTypes = entityTypes.Where(a => dicSyced.ContainsKey(a.FullName) == false).ToArray();
|
||||
if (syncTypes.Any() == false) return true;
|
||||
var ddl = this.GetComparisonDDLStatements(syncTypes);
|
||||
if (string.IsNullOrEmpty(ddl)) {
|
||||
foreach (var syncType in syncTypes) dicSyced.Add(syncType.FullName, true);
|
||||
return true;
|
||||
}
|
||||
try {
|
||||
return _orm.Ado.ExecuteNonQuery(CommandType.Text, ddl) > 0;
|
||||
var affrows = _orm.Ado.ExecuteNonQuery(CommandType.Text, ddl);
|
||||
foreach (var syncType in syncTypes) dicSyced.Add(syncType.FullName, true);
|
||||
return affrows > 0;
|
||||
} catch {
|
||||
return false;
|
||||
}
|
||||
|
@ -2,6 +2,7 @@
|
||||
using FreeSql.Internal.Model;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Linq.Expressions;
|
||||
|
||||
namespace FreeSql.MySql {
|
||||
@ -9,150 +10,174 @@ namespace FreeSql.MySql {
|
||||
|
||||
public MySqlExpression(CommonUtils common) : base(common) { }
|
||||
|
||||
internal override string ExpressionLambdaToSqlCall(MethodCallExpression exp, List<SelectTableInfo> _tables, List<SelectColumnInfo> _selectColumnMap, SelectTableInfoType tbtype, bool isQuoteName) {
|
||||
if (exp.Object.Type.FullName == "System.String") {
|
||||
var left = ExpressionLambdaToSql(exp.Object, _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
switch (exp.Method.Name) {
|
||||
case "StartsWith":
|
||||
case "EndsWith":
|
||||
case "Contains":
|
||||
var args0Value = ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
if (args0Value == "NULL") return $"({left}) IS NULL";
|
||||
if (exp.Method.Name == "StartsWith") return $"({left}) LIKE {(args0Value.StartsWith("'") ? args0Value.Insert(1, "%") : $"concat('%', {args0Value})")}";
|
||||
if (exp.Method.Name == "EndsWith") return $"({left}) LIKE {(args0Value.EndsWith("'") ? args0Value.Insert(args0Value.Length - 1, "%") : $"concat({args0Value}, '%')")}";
|
||||
if (args0Value.StartsWith("'") && args0Value.EndsWith("'")) return $"({left}) LIKE {args0Value.Insert(1, "%").Insert(args0Value.Length, "%")}";
|
||||
return $"({left}) like concat('%', {args0Value}, '%')";
|
||||
case "ToLower": return $"lower({left})";
|
||||
case "ToUpper": return $"upper({left})";
|
||||
case "Substring": return $"substr({left}, {ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)} + 1, {ExpressionLambdaToSql(exp.Arguments[1], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Length": return $"char_length({left})";
|
||||
case "IndexOf":
|
||||
var indexOfFindStr = ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
if (exp.Arguments.Count > 1 && exp.Arguments[1].Type.FullName == "System.Int32") return $"(locate({left}, {indexOfFindStr}, ParseLambdaToSql(exp.Arguments[1], _tables, _selectColumnMap, tbtype, isQuoteName) + 1) - 1)";
|
||||
return $"(locate({left}, {indexOfFindStr}) - 1)";
|
||||
case "PadLeft": return $"lpad({left}, {ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)}, {ExpressionLambdaToSql(exp.Arguments[1], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "PadRight": return $"rpad({left}, {ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)}, {ExpressionLambdaToSql(exp.Arguments[1], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Trim":
|
||||
case "TrimStart":
|
||||
case "TrimEnd":
|
||||
if (exp.Arguments.Count == 0) {
|
||||
if (exp.Method.Name == "Trim") return $"trim({left})";
|
||||
if (exp.Method.Name == "TrimStart") return $"ltrim({left})";
|
||||
if (exp.Method.Name == "TrimStart") return $"rtrim({left})";
|
||||
internal override string ExpressionLambdaToSqlMemberAccessString(MemberExpression exp, List<SelectTableInfo> _tables, List<SelectColumnInfo> _selectColumnMap, SelectTableInfoType tbtype, bool isQuoteName) {
|
||||
var left = ExpressionLambdaToSql(exp.Expression, _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
switch (exp.Member.Name) {
|
||||
case "Length": return $"char_length({left})";
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
internal override string ExpressionLambdaToSqlMemberAccessMath(MemberExpression exp, List<SelectTableInfo> _tables, List<SelectColumnInfo> _selectColumnMap, SelectTableInfoType tbtype, bool isQuoteName) {
|
||||
var left = ExpressionLambdaToSql(exp.Expression, _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
switch (exp.Member.Name) {
|
||||
case "PI": return $"pi()";
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
internal override string ExpressionLambdaToSqlMemberAccessDateTime(MemberExpression exp, List<SelectTableInfo> _tables, List<SelectColumnInfo> _selectColumnMap, SelectTableInfoType tbtype, bool isQuoteName) {
|
||||
if (exp.Expression == null && exp.Member.Name == "Now") return "now()";
|
||||
var left = ExpressionLambdaToSql(exp.Expression, _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
switch (exp.Member.Name) {
|
||||
case "DayOfWeek": return $"(dayofweek({left}) - 1)";
|
||||
case "Day": return $"dayofmonth({left})";
|
||||
case "DayOfYear": return $"dayofyear({left})";
|
||||
case "Month": return $"month({left})";
|
||||
case "Year": return $"year({left})";
|
||||
case "Hour": return $"hour({left})";
|
||||
case "Minute": return $"minute({left})";
|
||||
case "Second": return $"second({left})";
|
||||
case "Millisecond": return $"floor(microsecond({left}) / 1000)";
|
||||
case "Ticks": return $"(time_to_sec({left}) * 10000000 + 621355968000000000)";
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
internal override string ExpressionLambdaToSqlMemberAccessTimeSpan(MemberExpression exp, List<SelectTableInfo> _tables, List<SelectColumnInfo> _selectColumnMap, SelectTableInfoType tbtype, bool isQuoteName) {
|
||||
var left = ExpressionLambdaToSql(exp.Expression, _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
switch (exp.Member.Name) {
|
||||
case "Days": return $"floor(time_to_sec({left}) / {60 * 60 * 24})";
|
||||
case "Hours": return $"extract(hour from {left})";
|
||||
case "Milliseconds": return $"floor(extract(microsecond from {left}) / 1000)";
|
||||
case "Minutes": return $"extract(minute from {left})";
|
||||
case "Seconds": return $"extract(second from {left})";
|
||||
case "Ticks": return $"(time_to_sec({left}) * 10000000 + extract(microsecond from {left}) * 10)";
|
||||
case "TotalDays": return $"floor(extract(hour from {left}) / 24)";
|
||||
case "TotalHours": return $"floor(time_to_sec({left}) / {60 * 60})";
|
||||
case "TotalMilliseconds": return $"(time_to_sec({left}) * 1000 + floor(extract(microsecond from {left}) / 1000))";
|
||||
case "TotalMinutes": return $"floor(time_to_sec({left}) / 60)";
|
||||
case "TotalSeconds": return $"time_to_sec({left})";
|
||||
}
|
||||
return null;
|
||||
}
|
||||
internal override string ExpressionLambdaToSqlCallString(MethodCallExpression exp, List<SelectTableInfo> _tables, List<SelectColumnInfo> _selectColumnMap, SelectTableInfoType tbtype, bool isQuoteName) {
|
||||
var left = ExpressionLambdaToSql(exp.Object, _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
switch (exp.Method.Name) {
|
||||
case "StartsWith":
|
||||
case "EndsWith":
|
||||
case "Contains":
|
||||
var args0Value = ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
if (args0Value == "NULL") return $"({left}) IS NULL";
|
||||
if (exp.Method.Name == "StartsWith") return $"({left}) LIKE {(args0Value.StartsWith("'") ? args0Value.Insert(1, "%") : $"concat('%', {args0Value})")}";
|
||||
if (exp.Method.Name == "EndsWith") return $"({left}) LIKE {(args0Value.EndsWith("'") ? args0Value.Insert(args0Value.Length - 1, "%") : $"concat({args0Value}, '%')")}";
|
||||
if (args0Value.StartsWith("'") && args0Value.EndsWith("'")) return $"({left}) LIKE {args0Value.Insert(1, "%").Insert(args0Value.Length, "%")}";
|
||||
return $"({left}) LIKE concat('%', {args0Value}, '%')";
|
||||
case "ToLower": return $"lower({left})";
|
||||
case "ToUpper": return $"upper({left})";
|
||||
case "Substring":
|
||||
var substrArgs1 = ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
if (long.TryParse(substrArgs1, out var testtrylng1)) substrArgs1 = (testtrylng1 + 1).ToString();
|
||||
else substrArgs1 += " + 1";
|
||||
if (exp.Arguments.Count == 1) return $"substr({left}, {substrArgs1})";
|
||||
return $"substr({left}, {substrArgs1}, {ExpressionLambdaToSql(exp.Arguments[1], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "IndexOf":
|
||||
var indexOfFindStr = ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
if (exp.Arguments.Count > 1 && exp.Arguments[1].Type.FullName == "System.Int32") {
|
||||
var locateArgs1 = ExpressionLambdaToSql(exp.Arguments[1], _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
if (long.TryParse(locateArgs1, out var testtrylng2)) locateArgs1 = (testtrylng2 + 1).ToString();
|
||||
else locateArgs1 += " + 1";
|
||||
return $"(locate({left}, {indexOfFindStr}, {locateArgs1}) - 1)";
|
||||
}
|
||||
return $"(locate({left}, {indexOfFindStr}) - 1)";
|
||||
case "PadLeft":
|
||||
if (exp.Arguments.Count == 1) return $"lpad({left}, {ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
return $"lpad({left}, {ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)}, {ExpressionLambdaToSql(exp.Arguments[1], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "PadRight":
|
||||
if (exp.Arguments.Count == 1) return $"rpad({left}, {ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
return $"rpad({left}, {ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)}, {ExpressionLambdaToSql(exp.Arguments[1], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Trim":
|
||||
case "TrimStart":
|
||||
case "TrimEnd":
|
||||
if (exp.Arguments.Count == 0) {
|
||||
if (exp.Method.Name == "Trim") return $"trim({left})";
|
||||
if (exp.Method.Name == "TrimStart") return $"ltrim({left})";
|
||||
if (exp.Method.Name == "TrimEnd") return $"rtrim({left})";
|
||||
}
|
||||
foreach (var argsTrim02 in exp.Arguments) {
|
||||
var argsTrim01s = new[] { argsTrim02 };
|
||||
if (argsTrim02.NodeType == ExpressionType.NewArrayInit) {
|
||||
var arritem = argsTrim02 as NewArrayExpression;
|
||||
argsTrim01s = arritem.Expressions.ToArray();
|
||||
}
|
||||
foreach (var argsTrim01 in exp.Arguments) {
|
||||
foreach (var argsTrim01 in argsTrim01s) {
|
||||
if (exp.Method.Name == "Trim") left = $"trim({ExpressionLambdaToSql(argsTrim01, _tables, _selectColumnMap, tbtype, isQuoteName)} from {left})";
|
||||
if (exp.Method.Name == "TrimStart") left = $"trim(leading {ExpressionLambdaToSql(argsTrim01, _tables, _selectColumnMap, tbtype, isQuoteName)} from {left})";
|
||||
if (exp.Method.Name == "TrimStart") left = $"trim(trailing {ExpressionLambdaToSql(argsTrim01, _tables, _selectColumnMap, tbtype, isQuoteName)} from {left})";
|
||||
if (exp.Method.Name == "TrimEnd") left = $"trim(trailing {ExpressionLambdaToSql(argsTrim01, _tables, _selectColumnMap, tbtype, isQuoteName)} from {left})";
|
||||
}
|
||||
return left;
|
||||
case "Replace": return $"replace({left}, {ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)}, {ExpressionLambdaToSql(exp.Arguments[1], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "CompareTo": return $"strcmp({left}, {ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
}
|
||||
}
|
||||
return left;
|
||||
case "Replace": return $"replace({left}, {ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)}, {ExpressionLambdaToSql(exp.Arguments[1], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "CompareTo": return $"strcmp({left}, {ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
}
|
||||
throw new Exception($"MySqlExpression 未现实函数表达式 {exp} 解析");
|
||||
}
|
||||
|
||||
if (exp.Object.Type.FullName == "System.Math") {
|
||||
switch (exp.Method.Name) {
|
||||
case "Abs": return $"abs({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Sign": return $"sign({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Floor": return $"floor({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Round":
|
||||
if (exp.Arguments.Count > 1 && exp.Arguments[1].Type.FullName == "System.Int32") return $"round({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)}, {ExpressionLambdaToSql(exp.Arguments[1], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
return $"round({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Exp": return $"exp({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Log": return $"log({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Log10": return $"log10({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Pow": return $"pow({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Sqrt": return $"sqrt({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "PI": return $"pi()";
|
||||
case "Cos": return $"cos({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Sin": return $"sin({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Tan": return $"tan({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Acos": return $"acos({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Asin": return $"asin({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Atan": return $"atan({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Atan2": return $"atan2({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)}, {ExpressionLambdaToSql(exp.Arguments[1], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Truncate": return $"truncate({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)}, 0)";
|
||||
}
|
||||
internal override string ExpressionLambdaToSqlCallMath(MethodCallExpression exp, List<SelectTableInfo> _tables, List<SelectColumnInfo> _selectColumnMap, SelectTableInfoType tbtype, bool isQuoteName) {
|
||||
switch (exp.Method.Name) {
|
||||
case "Abs": return $"abs({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Sign": return $"sign({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Floor": return $"floor({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Ceiling": return $"ceiling({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Round":
|
||||
if (exp.Arguments.Count > 1 && exp.Arguments[1].Type.FullName == "System.Int32") return $"round({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)}, {ExpressionLambdaToSql(exp.Arguments[1], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
return $"round({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Exp": return $"exp({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Log": return $"log({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Log10": return $"log10({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Pow": return $"pow({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)}, {ExpressionLambdaToSql(exp.Arguments[1], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Sqrt": return $"sqrt({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Cos": return $"cos({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Sin": return $"sin({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Tan": return $"tan({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Acos": return $"acos({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Asin": return $"asin({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Atan": return $"atan({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Atan2": return $"atan2({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)}, {ExpressionLambdaToSql(exp.Arguments[1], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Truncate": return $"truncate({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)}, 0)";
|
||||
}
|
||||
throw new Exception($"MySqlExpression 未现实函数表达式 {exp} 解析");
|
||||
}
|
||||
|
||||
//dayofweek = DayOfWeek
|
||||
//dayofmonth = Day
|
||||
//dayofyear = DayOfYear
|
||||
//month = Month
|
||||
//year = Year
|
||||
//hour = Hour
|
||||
//minute = Minute
|
||||
//second = Second
|
||||
/*
|
||||
* date_add(date,interval expr type)
|
||||
date_sub(date,interval expr type)
|
||||
adddate(date,interval expr type)
|
||||
subdate(date,interval expr type)
|
||||
对日期时间进行加减法运算
|
||||
(adddate()和subdate()是date_add()和date_sub()的同义词,也
|
||||
可以用运算符+和-而不是函数
|
||||
date是一个datetime或date值,expr对date进行加减法的一个表
|
||||
达式字符串type指明表达式expr应该如何被解释
|
||||
[type值 含义 期望的expr格式]:
|
||||
second 秒 seconds
|
||||
minute 分钟 minutes
|
||||
hour 时间 hours
|
||||
day 天 days
|
||||
month 月 months
|
||||
year 年 years
|
||||
minute_second 分钟和秒 "minutes:seconds"
|
||||
hour_minute 小时和分钟 "hours:minutes"
|
||||
day_hour 天和小时 "days hours"
|
||||
year_month 年和月 "years-months"
|
||||
hour_second 小时, 分钟, "hours:minutes:seconds"
|
||||
day_minute 天, 小时, 分钟 "days hours:minutes"
|
||||
day_second 天, 小时, 分钟, 秒 "days
|
||||
hours:minutes:seconds"
|
||||
expr中允许任何标点做分隔符,如果所有是date值时结果是一个
|
||||
date值,否则结果是一个datetime值)
|
||||
如果type关键词不完整,则mysql从右端取值,day_second因为缺
|
||||
少小时分钟等于minute_second)
|
||||
如果增加month、year_month或year,天数大于结果月份的最大天
|
||||
数则使用最大天数)
|
||||
mysql> select "1997-12-31 23:59:59" + interval 1 second;
|
||||
|
||||
-> 1998-01-01 00:00:00
|
||||
mysql> select interval 1 day + "1997-12-31";
|
||||
-> 1998-01-01
|
||||
mysql> select "1998-01-01" - interval 1 second;
|
||||
-> 1997-12-31 23:59:59
|
||||
mysql> select date_add("1997-12-31 23:59:59",interval 1
|
||||
second);
|
||||
-> 1998-01-01 00:00:00
|
||||
mysql> select date_add("1997-12-31 23:59:59",interval 1
|
||||
day);
|
||||
-> 1998-01-01 23:59:59
|
||||
mysql> select date_add("1997-12-31 23:59:59",interval
|
||||
"1:1" minute_second);
|
||||
-> 1998-01-01 00:01:00
|
||||
mysql> select date_sub("1998-01-01 00:00:00",interval "1
|
||||
1:1:1" day_second);
|
||||
-> 1997-12-30 22:58:59
|
||||
mysql> select date_add("1998-01-01 00:00:00", interval "-1
|
||||
10" day_hour);
|
||||
-> 1997-12-30 14:00:00
|
||||
mysql> select date_sub("1998-01-02", interval 31 day);
|
||||
-> 1997-12-02
|
||||
mysql> select extract(year from "1999-07-02");
|
||||
-> 1999
|
||||
mysql> select extract(year_month from "1999-07-02
|
||||
01:02:03");
|
||||
-> 199907
|
||||
mysql> select extract(day_minute from "1999-07-02
|
||||
01:02:03");
|
||||
-> 20102
|
||||
*/
|
||||
|
||||
//convert
|
||||
var xxx = DateTime.Now.ToString("");
|
||||
|
||||
|
||||
internal override string ExpressionLambdaToSqlCallDateTime(MethodCallExpression exp, List<SelectTableInfo> _tables, List<SelectColumnInfo> _selectColumnMap, SelectTableInfoType tbtype, bool isQuoteName) {
|
||||
var left = ExpressionLambdaToSql(exp.Object, _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
var args1 = ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
switch (exp.Method.Name) {
|
||||
case "Add": return $"date_add({left}, interval (time_to_sec({args1}) * 1000000 + extract(microsecond from {args1})) microsecond)";
|
||||
case "AddDays": return $"date_add({left}, interval {args1} day)";
|
||||
case "AddHours": return $"date_add({left}, interval {args1} hour)";
|
||||
case "AddMilliseconds": return $"date_add({left}, interval {args1} microsecond)";
|
||||
case "AddMinutes": return $"date_add({left}, interval {args1} minute)";
|
||||
case "AddMonths": return $"date_add({left}, interval {args1} month)";
|
||||
case "AddSeconds": return $"date_add({left}, interval {args1} second)";
|
||||
case "AddTicks": return $"date_add({left}, interval ({args1}) / 10 microsecond)";
|
||||
case "AddYears": return $"date_add({left}, interval {args1} year)";
|
||||
case "Subtract":
|
||||
if (exp.Arguments[0].Type.FullName == "System.DateTime" || exp.Arguments[0].Type.GenericTypeArguments.FirstOrDefault()?.FullName == "System.DateTime")
|
||||
return $"({left} - {args1})";
|
||||
if (exp.Arguments[0].Type.FullName == "System.TimeSpan" || exp.Arguments[0].Type.GenericTypeArguments.FirstOrDefault()?.FullName == "System.TimeSpan")
|
||||
return $"date_sub({left}, interval (time_to_sec({args1}) * 1000000 + extract(microsecond from {args1})) microsecond)";
|
||||
break;
|
||||
}
|
||||
throw new Exception($"MySqlExpression 未现实函数表达式 {exp} 解析");
|
||||
}
|
||||
internal override string ExpressionLambdaToSqlCallTimeSpan(MethodCallExpression exp, List<SelectTableInfo> _tables, List<SelectColumnInfo> _selectColumnMap, SelectTableInfoType tbtype, bool isQuoteName) {
|
||||
var left = ExpressionLambdaToSql(exp.Object, _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
var args1 = ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
switch (exp.Method.Name) {
|
||||
case "Add": return $"(date_add('1970-1-1', interval (time_to_sec({left}) * 1000000 + extract(microsecond from {left}) + time_to_sec({args1}) * 1000000 + extract(microsecond from {args1})) microsecond)) microsecond) - date_add('1970-1-1', interval 0 microsecond) second))";
|
||||
case "Subtract": return $"(date_add('1970-1-1', interval (time_to_sec({left}) * 1000000 + extract(microsecond from {left}) - time_to_sec({args1}) * 1000000 - extract(microsecond from {args1})) microsecond) - date_add('1970-1-1', interval 0 second))";
|
||||
}
|
||||
throw new Exception($"MySqlExpression 未现实函数表达式 {exp} 解析");
|
||||
}
|
||||
}
|
||||
|
@ -44,5 +44,6 @@ namespace FreeSql.MySql {
|
||||
internal override string QuoteSqlName(string name) => $"`{name.Trim('`').Replace(".", "`.`")}`";
|
||||
internal override string QuoteParamterName(string name) => $"?{name}";
|
||||
internal override string IsNull(string sql, object value) => $"ifnull({sql}, {value})";
|
||||
internal override string StringConcat(string left, string right, Type leftType, Type rightType) => $"concat({left}, {right})";
|
||||
}
|
||||
}
|
||||
|
@ -10,7 +10,10 @@ namespace FreeSql.PostgreSQL.Curd {
|
||||
|
||||
class PostgreSQLSelect<T1> : FreeSql.Internal.CommonProvider.Select1Provider<T1> where T1 : class {
|
||||
|
||||
internal static string ToSqlStatic(CommonUtils _commonUtils, string _select, string field, StringBuilder _join, StringBuilder _where, string _groupby, string _having, string _orderby, int _skip, int _limit, List<SelectTableInfo> _tables) {
|
||||
internal static string ToSqlStatic(CommonUtils _commonUtils, string _select, string field, StringBuilder _join, StringBuilder _where, string _groupby, string _having, string _orderby, int _skip, int _limit, List<SelectTableInfo> _tables, IFreeSql _orm) {
|
||||
if (_orm.CodeFirst.IsAutoSyncStructure)
|
||||
_orm.CodeFirst.SyncStructure(_tables.Select(a => a.Table.Type).ToArray());
|
||||
|
||||
var sb = new StringBuilder();
|
||||
sb.Append(_select).Append(field).Append(" \r\nFROM ");
|
||||
var tbsjoin = _tables.Where(a => a.Type != SelectTableInfoType.From).ToArray();
|
||||
@ -75,42 +78,42 @@ namespace FreeSql.PostgreSQL.Curd {
|
||||
public override ISelect<T1, T2, T3, T4, T5, T6, T7, T8> From<T2, T3, T4, T5, T6, T7, T8>(Expression<Func<ISelectFromExpression<T1>, T2, T3, T4, T5, T6, T7, T8, ISelectFromExpression<T1>>> exp) { this.InternalFrom(exp?.Body); var ret = new PostgreSQLSelect<T1, T2, T3, T4, T5, T6, T7, T8>(_orm, _commonUtils, _commonExpression, null); PostgreSQLSelect<T1>.CopyData(this, ret); return ret; }
|
||||
public override ISelect<T1, T2, T3, T4, T5, T6, T7, T8, T9> From<T2, T3, T4, T5, T6, T7, T8, T9>(Expression<Func<ISelectFromExpression<T1>, T2, T3, T4, T5, T6, T7, T8, T9, ISelectFromExpression<T1>>> exp) { this.InternalFrom(exp?.Body); var ret = new PostgreSQLSelect<T1, T2, T3, T4, T5, T6, T7, T8, T9>(_orm, _commonUtils, _commonExpression, null); PostgreSQLSelect<T1>.CopyData(this, ret); return ret; }
|
||||
public override ISelect<T1, T2, T3, T4, T5, T6, T7, T8, T9, T10> From<T2, T3, T4, T5, T6, T7, T8, T9, T10>(Expression<Func<ISelectFromExpression<T1>, T2, T3, T4, T5, T6, T7, T8, T9, T10, ISelectFromExpression<T1>>> exp) { this.InternalFrom(exp?.Body); var ret = new PostgreSQLSelect<T1, T2, T3, T4, T5, T6, T7, T8, T9, T10>(_orm, _commonUtils, _commonExpression, null); PostgreSQLSelect<T1>.CopyData(this, ret); return ret; }
|
||||
public override string ToSql(string field = null) => ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables);
|
||||
public override string ToSql(string field = null) => ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables, _orm);
|
||||
}
|
||||
class PostgreSQLSelect<T1, T2> : FreeSql.Internal.CommonProvider.Select2Provider<T1, T2> where T1 : class where T2 : class {
|
||||
public PostgreSQLSelect(IFreeSql orm, CommonUtils commonUtils, CommonExpression commonExpression, object dywhere) : base(orm, commonUtils, commonExpression, dywhere) { }
|
||||
public override string ToSql(string field = null) => PostgreSQLSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables);
|
||||
public override string ToSql(string field = null) => PostgreSQLSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables, _orm);
|
||||
}
|
||||
class PostgreSQLSelect<T1, T2, T3> : FreeSql.Internal.CommonProvider.Select3Provider<T1, T2, T3> where T1 : class where T2 : class where T3 : class {
|
||||
public PostgreSQLSelect(IFreeSql orm, CommonUtils commonUtils, CommonExpression commonExpression, object dywhere) : base(orm, commonUtils, commonExpression, dywhere) { }
|
||||
public override string ToSql(string field = null) => PostgreSQLSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables);
|
||||
public override string ToSql(string field = null) => PostgreSQLSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables, _orm);
|
||||
}
|
||||
class PostgreSQLSelect<T1, T2, T3, T4> : FreeSql.Internal.CommonProvider.Select4Provider<T1, T2, T3, T4> where T1 : class where T2 : class where T3 : class where T4 : class {
|
||||
public PostgreSQLSelect(IFreeSql orm, CommonUtils commonUtils, CommonExpression commonExpression, object dywhere) : base(orm, commonUtils, commonExpression, dywhere) { }
|
||||
public override string ToSql(string field = null) => PostgreSQLSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables);
|
||||
public override string ToSql(string field = null) => PostgreSQLSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables, _orm);
|
||||
}
|
||||
class PostgreSQLSelect<T1, T2, T3, T4, T5> : FreeSql.Internal.CommonProvider.Select5Provider<T1, T2, T3, T4, T5> where T1 : class where T2 : class where T3 : class where T4 : class where T5 : class {
|
||||
public PostgreSQLSelect(IFreeSql orm, CommonUtils commonUtils, CommonExpression commonExpression, object dywhere) : base(orm, commonUtils, commonExpression, dywhere) { }
|
||||
public override string ToSql(string field = null) => PostgreSQLSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables);
|
||||
public override string ToSql(string field = null) => PostgreSQLSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables, _orm);
|
||||
}
|
||||
class PostgreSQLSelect<T1, T2, T3, T4, T5, T6> : FreeSql.Internal.CommonProvider.Select6Provider<T1, T2, T3, T4, T5, T6> where T1 : class where T2 : class where T3 : class where T4 : class where T5 : class where T6 : class {
|
||||
public PostgreSQLSelect(IFreeSql orm, CommonUtils commonUtils, CommonExpression commonExpression, object dywhere) : base(orm, commonUtils, commonExpression, dywhere) { }
|
||||
public override string ToSql(string field = null) => PostgreSQLSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables);
|
||||
public override string ToSql(string field = null) => PostgreSQLSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables, _orm);
|
||||
}
|
||||
class PostgreSQLSelect<T1, T2, T3, T4, T5, T6, T7> : FreeSql.Internal.CommonProvider.Select7Provider<T1, T2, T3, T4, T5, T6, T7> where T1 : class where T2 : class where T3 : class where T4 : class where T5 : class where T6 : class where T7 : class {
|
||||
public PostgreSQLSelect(IFreeSql orm, CommonUtils commonUtils, CommonExpression commonExpression, object dywhere) : base(orm, commonUtils, commonExpression, dywhere) { }
|
||||
public override string ToSql(string field = null) => PostgreSQLSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables);
|
||||
public override string ToSql(string field = null) => PostgreSQLSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables, _orm);
|
||||
}
|
||||
class PostgreSQLSelect<T1, T2, T3, T4, T5, T6, T7, T8> : FreeSql.Internal.CommonProvider.Select8Provider<T1, T2, T3, T4, T5, T6, T7, T8> where T1 : class where T2 : class where T3 : class where T4 : class where T5 : class where T6 : class where T7 : class where T8 : class {
|
||||
public PostgreSQLSelect(IFreeSql orm, CommonUtils commonUtils, CommonExpression commonExpression, object dywhere) : base(orm, commonUtils, commonExpression, dywhere) { }
|
||||
public override string ToSql(string field = null) => PostgreSQLSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables);
|
||||
public override string ToSql(string field = null) => PostgreSQLSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables, _orm);
|
||||
}
|
||||
class PostgreSQLSelect<T1, T2, T3, T4, T5, T6, T7, T8, T9> : FreeSql.Internal.CommonProvider.Select9Provider<T1, T2, T3, T4, T5, T6, T7, T8, T9> where T1 : class where T2 : class where T3 : class where T4 : class where T5 : class where T6 : class where T7 : class where T8 : class where T9 : class {
|
||||
public PostgreSQLSelect(IFreeSql orm, CommonUtils commonUtils, CommonExpression commonExpression, object dywhere) : base(orm, commonUtils, commonExpression, dywhere) { }
|
||||
public override string ToSql(string field = null) => PostgreSQLSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables);
|
||||
public override string ToSql(string field = null) => PostgreSQLSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables, _orm);
|
||||
}
|
||||
class PostgreSQLSelect<T1, T2, T3, T4, T5, T6, T7, T8, T9, T10> : FreeSql.Internal.CommonProvider.Select10Provider<T1, T2, T3, T4, T5, T6, T7, T8, T9, T10> where T1 : class where T2 : class where T3 : class where T4 : class where T5 : class where T6 : class where T7 : class where T8 : class where T9 : class where T10 : class {
|
||||
public PostgreSQLSelect(IFreeSql orm, CommonUtils commonUtils, CommonExpression commonExpression, object dywhere) : base(orm, commonUtils, commonExpression, dywhere) { }
|
||||
public override string ToSql(string field = null) => PostgreSQLSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables);
|
||||
public override string ToSql(string field = null) => PostgreSQLSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables, _orm);
|
||||
}
|
||||
}
|
||||
|
@ -23,6 +23,7 @@ namespace FreeSql.PostgreSQL {
|
||||
}
|
||||
}
|
||||
}
|
||||
static DateTime dt1970 = new DateTime(1970, 1, 1);
|
||||
public override object AddslashesProcessParam(object param) {
|
||||
if (param == null) return "NULL";
|
||||
if (param is bool || param is bool?)
|
||||
@ -31,12 +32,16 @@ namespace FreeSql.PostgreSQL {
|
||||
return string.Concat("'", param.ToString().Replace("'", "''"), "'");
|
||||
else if (decimal.TryParse(string.Concat(param), out var trydec))
|
||||
return param;
|
||||
else if (param is DateTime) {
|
||||
DateTime dt = (DateTime)param;
|
||||
return string.Concat("'", dt.ToString("yyyy-MM-dd HH:mm:ss.ffffff"), "'");
|
||||
} else if (param is DateTime?) {
|
||||
DateTime? dt = param as DateTime?;
|
||||
return string.Concat("'", dt.Value.ToString("yyyy-MM-dd HH:mm:ss.ffffff"), "'");
|
||||
else if (param is DateTime)
|
||||
return string.Concat("'", ((DateTime)param).ToString("yyyy-MM-dd HH:mm:ss.ffffff"), "'");
|
||||
else if (param is DateTime?)
|
||||
return string.Concat("'", (param as DateTime?).Value.ToString("yyyy-MM-dd HH:mm:ss.ffffff"), "'");
|
||||
else if (param is TimeSpan) {
|
||||
var ts = (TimeSpan)param;
|
||||
return string.Concat("'", ts.Ticks > 0 ? "" : "-", ts.TotalHours, dt1970.AddTicks(Math.Abs(ts.Ticks)).ToString(":mm:ss.ffffff"), "'");
|
||||
} else if (param is TimeSpan) {
|
||||
var ts = (param as TimeSpan?).Value;
|
||||
return string.Concat("'", ts.Ticks > 0 ? "" : "-", ts.TotalHours, dt1970.AddTicks(Math.Abs(ts.Ticks)).ToString(":mm:ss.ffffff"), "'");
|
||||
} else if (param is IEnumerable) {
|
||||
var sb = new StringBuilder();
|
||||
var ie = param as IEnumerable;
|
||||
|
@ -100,8 +100,8 @@ namespace FreeSql.PostgreSQL {
|
||||
if (enumType == null && type.FullName.StartsWith("System.Nullable`1[") && type.GenericTypeArguments.Length == 1 && type.GenericTypeArguments.First().IsEnum) enumType = type.GenericTypeArguments.First();
|
||||
if (enumType != null) {
|
||||
var newItem = enumType.GetCustomAttributes(typeof(FlagsAttribute), false).Any() ?
|
||||
(NpgsqlDbType.Bigint, "int8", $"int8{(type.IsEnum ? " NOT NULL" : "")}", false, type.IsEnum ? false : true) :
|
||||
(NpgsqlDbType.Integer, "int4", $"int4{(type.IsEnum ? " NOT NULL" : "")}", false, type.IsEnum ? false : true);
|
||||
(NpgsqlDbType.Varchar, "varchar", $"varchar(32){(type.IsEnum ? " NOT NULL" : "")}", false, type.IsEnum ? false : true) :
|
||||
(NpgsqlDbType.Varchar, "varchar", $"varchar(32){(type.IsEnum ? " NOT NULL" : "")}", false, type.IsEnum ? false : true);
|
||||
if (_dicCsToDb.ContainsKey(type.FullName) == false) {
|
||||
lock (_dicCsToDbLock) {
|
||||
if (_dicCsToDb.ContainsKey(type.FullName) == false)
|
||||
@ -116,6 +116,7 @@ namespace FreeSql.PostgreSQL {
|
||||
public string GetComparisonDDLStatements<TEntity>() => this.GetComparisonDDLStatements(typeof(TEntity));
|
||||
public string GetComparisonDDLStatements(params Type[] entityTypes) {
|
||||
var sb = new StringBuilder();
|
||||
var seqcols = new List<(ColumnInfo, string[], bool)>(); //序列
|
||||
foreach (var entityType in entityTypes) {
|
||||
if (sb.Length > 0) sb.Append("\r\n");
|
||||
var tb = _commonUtils.GetTableByEntity(entityType);
|
||||
@ -134,13 +135,10 @@ namespace FreeSql.PostgreSQL {
|
||||
|
||||
} else {
|
||||
//创建表
|
||||
var seqcols = new List<ColumnInfo>();
|
||||
sb.Append("CREATE TABLE IF NOT EXISTS ").Append(_commonUtils.QuoteSqlName($"{tbname[0]}.{tbname[1]}")).Append(" (");
|
||||
foreach (var tbcol in tb.Columns.Values) {
|
||||
sb.Append(" \r\n ").Append(_commonUtils.QuoteSqlName(tbcol.Attribute.Name)).Append(" ");
|
||||
sb.Append(tbcol.Attribute.DbType.ToUpper());
|
||||
if (tbcol.Attribute.IsIdentity && tbcol.Attribute.DbType.IndexOf("serial", StringComparison.CurrentCultureIgnoreCase) == -1) seqcols.Add(tbcol);
|
||||
sb.Append(",");
|
||||
sb.Append(" \r\n ").Append(_commonUtils.QuoteSqlName(tbcol.Attribute.Name)).Append(" ").Append(tbcol.Attribute.DbType.ToUpper()).Append(",");
|
||||
if (tbcol.Attribute.IsIdentity) seqcols.Add((tbcol, tbname, true));
|
||||
}
|
||||
if (tb.Primarys.Any() == false)
|
||||
sb.Remove(sb.Length - 1, 1);
|
||||
@ -187,38 +185,54 @@ where ns.nspname = {0} and c.relname = {1}".FormatPostgreSQL(isRenameTable ? tbo
|
||||
|
||||
if (addcols.TryGetValue(column, out var trycol)) {
|
||||
if (trycol.Attribute.DbType.ToLower().StartsWith(sqlType.ToLower()) == false ||
|
||||
(trycol.Attribute.DbType.IndexOf("NOT NULL") == -1) != is_nullable ||
|
||||
trycol.Attribute.IsIdentity != is_identity) {
|
||||
sb.Append("ALTER TABLE ").Append(_commonUtils.QuoteSqlName($"{tbname[0]}.{tbname[1]}")).Append(" ALTER COLUMN ").Append(_commonUtils.QuoteSqlName(column)).Append(" TYPE ").Append(trycol.Attribute.DbType.ToUpper());
|
||||
if (trycol.Attribute.IsIdentity) sb.Append(" AUTO_INCREMENT");
|
||||
sb.Append(";\r\n");
|
||||
(trycol.Attribute.DbType.IndexOf("NOT NULL") == -1) != is_nullable) {
|
||||
sb.Append("ALTER TABLE ").Append(_commonUtils.QuoteSqlName($"{tbname[0]}.{tbname[1]}")).Append(" ALTER COLUMN ").Append(_commonUtils.QuoteSqlName(column)).Append(" TYPE ").Append(trycol.Attribute.DbType.ToUpper()).Append(";\r\n");
|
||||
}
|
||||
if (trycol.Attribute.IsIdentity != is_identity) seqcols.Add((trycol, tbname, trycol.Attribute.IsIdentity));
|
||||
addcols.Remove(column);
|
||||
} else
|
||||
} else {
|
||||
if (trycol.Attribute.IsIdentity != is_identity) seqcols.Add((trycol, tbname, trycol.Attribute.IsIdentity));
|
||||
surplus.Add(column, true); //记录剩余字段
|
||||
}
|
||||
}
|
||||
foreach (var addcol in addcols.Values) {
|
||||
if (string.IsNullOrEmpty(addcol.Attribute.OldName) == false && surplus.ContainsKey(addcol.Attribute.OldName)) { //修改列名
|
||||
sb.Append("ALTER TABLE ").Append(_commonUtils.QuoteSqlName($"{tbname[0]}.{tbname[1]}")).Append(" RENAME COLUMN ").Append(_commonUtils.QuoteSqlName(addcol.Attribute.OldName)).Append(" TO ").Append(_commonUtils.QuoteSqlName(addcol.Attribute.Name)).Append(";\r\n");
|
||||
if (addcol.Attribute.IsIdentity) sb.Append(" AUTO_INCREMENT");
|
||||
sb.Append(";\r\n");
|
||||
|
||||
} else { //添加列
|
||||
sb.Append("ALTER TABLE ").Append(_commonUtils.QuoteSqlName($"{tbname[0]}.{tbname[1]}")).Append(" ADD COLUMN ").Append(_commonUtils.QuoteSqlName(addcol.Attribute.Name)).Append(" ").Append(addcol.Attribute.DbType.ToUpper());
|
||||
if (addcol.Attribute.IsIdentity) sb.Append(" AUTO_INCREMENT");
|
||||
sb.Append(";\r\n");
|
||||
sb.Append("ALTER TABLE ").Append(_commonUtils.QuoteSqlName($"{tbname[0]}.{tbname[1]}")).Append(" ADD COLUMN ").Append(_commonUtils.QuoteSqlName(addcol.Attribute.Name)).Append(" ").Append(addcol.Attribute.DbType.ToUpper()).Append(";\r\n");
|
||||
}
|
||||
}
|
||||
}
|
||||
foreach(var seqcol in seqcols) {
|
||||
var tbname = seqcol.Item2;
|
||||
var seqname = Utils.GetCsName($"{tbname[0]}.{tbname[1]}_{seqcol.Item1.Attribute.Name}_sequence_name");
|
||||
var tbname2 = _commonUtils.QuoteSqlName($"{tbname[0]}.{tbname[1]}");
|
||||
var colname2 = _commonUtils.QuoteSqlName(seqcol.Item1.Attribute.Name);
|
||||
sb.Append("ALTER TABLE ").Append(tbname2).Append(" ALTER COLUMN ").Append(colname2).Append(" SET DEFAULT null;");
|
||||
sb.Append("DROP SEQUENCE IF EXISTS ").Append(seqname).Append(";");
|
||||
if (seqcol.Item3) {
|
||||
sb.Append("CREATE SEQUENCE ").Append(seqname).Append(" START WITH (select coalesce(max(").Append(colname2).Append("),1) from ").Append(tbname2).Append(");");
|
||||
sb.Append("ALTER TABLE ").Append(tbname2).Append(" ALTER COLUMN ").Append(colname2).Append(" SET DEFAULT nextval('").Append(seqname).Append("'::regclass);");
|
||||
}
|
||||
}
|
||||
return sb.Length == 0 ? null : sb.ToString();
|
||||
}
|
||||
|
||||
Dictionary<string, bool> dicSyced = new Dictionary<string, bool>();
|
||||
public bool SyncStructure<TEntity>() => this.SyncStructure(typeof(TEntity));
|
||||
public bool SyncStructure(params Type[] entityTypes) {
|
||||
var ddl = this.GetComparisonDDLStatements(entityTypes);
|
||||
if (string.IsNullOrEmpty(ddl)) return true;
|
||||
if (entityTypes == null) return true;
|
||||
var syncTypes = entityTypes.Where(a => dicSyced.ContainsKey(a.FullName) == false).ToArray();
|
||||
if (syncTypes.Any() == false) return true;
|
||||
var ddl = this.GetComparisonDDLStatements(syncTypes);
|
||||
if (string.IsNullOrEmpty(ddl)) {
|
||||
foreach (var syncType in syncTypes) dicSyced.Add(syncType.FullName, true);
|
||||
return true;
|
||||
}
|
||||
try {
|
||||
return _orm.Ado.ExecuteNonQuery(CommandType.Text, ddl) > 0;
|
||||
var affrows = _orm.Ado.ExecuteNonQuery(CommandType.Text, ddl);
|
||||
foreach (var syncType in syncTypes) dicSyced.Add(syncType.FullName, true);
|
||||
return affrows > 0;
|
||||
} catch {
|
||||
return false;
|
||||
}
|
||||
|
@ -2,6 +2,7 @@
|
||||
using FreeSql.Internal.Model;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Linq.Expressions;
|
||||
|
||||
namespace FreeSql.PostgreSQL {
|
||||
@ -9,151 +10,176 @@ namespace FreeSql.PostgreSQL {
|
||||
|
||||
public PostgreSQLExpression(CommonUtils common) : base(common) { }
|
||||
|
||||
internal override string ExpressionLambdaToSqlCall(MethodCallExpression exp, List<SelectTableInfo> _tables, List<SelectColumnInfo> _selectColumnMap, SelectTableInfoType tbtype, bool isQuoteName) {
|
||||
if (exp.Object.Type.FullName == "System.String") {
|
||||
var left = ExpressionLambdaToSql(exp.Object, _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
switch (exp.Method.Name) {
|
||||
case "StartsWith":
|
||||
case "EndsWith":
|
||||
case "Contains":
|
||||
var args0Value = ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
if (args0Value == "NULL") return $"({left}) IS NULL";
|
||||
if (exp.Method.Name == "StartsWith") return $"({left}) LIKE {(args0Value.StartsWith("'") ? args0Value.Insert(1, "%") : $"concat('%', {args0Value})")}";
|
||||
if (exp.Method.Name == "EndsWith") return $"({left}) LIKE {(args0Value.EndsWith("'") ? args0Value.Insert(args0Value.Length - 1, "%") : $"concat({args0Value}, '%')")}";
|
||||
if (args0Value.StartsWith("'") && args0Value.EndsWith("'")) return $"({left}) LIKE {args0Value.Insert(1, "%").Insert(args0Value.Length, "%")}";
|
||||
return $"({left}) like concat('%', {args0Value}, '%')";
|
||||
case "ToLower": return $"lower({left})";
|
||||
case "ToUpper": return $"upper({left})";
|
||||
case "Substring": return $"substr({left}, {ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)} + 1, {ExpressionLambdaToSql(exp.Arguments[1], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Length": return $"char_length({left})";
|
||||
case "IndexOf":
|
||||
var indexOfFindStr = ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
if (exp.Arguments.Count > 1 && exp.Arguments[1].Type.FullName == "System.Int32") return $"(locate({left}, {indexOfFindStr}, ParseLambdaToSql(exp.Arguments[1], _tables, _selectColumnMap, tbtype, isQuoteName) + 1) - 1)";
|
||||
return $"(locate({left}, {indexOfFindStr}) - 1)";
|
||||
case "PadLeft": return $"lpad({left}, {ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)}, {ExpressionLambdaToSql(exp.Arguments[1], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "PadRight": return $"rpad({left}, {ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)}, {ExpressionLambdaToSql(exp.Arguments[1], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Trim":
|
||||
case "TrimStart":
|
||||
case "TrimEnd":
|
||||
if (exp.Arguments.Count == 0) {
|
||||
if (exp.Method.Name == "Trim") return $"trim({left})";
|
||||
if (exp.Method.Name == "TrimStart") return $"ltrim({left})";
|
||||
if (exp.Method.Name == "TrimStart") return $"rtrim({left})";
|
||||
}
|
||||
foreach (var argsTrim01 in exp.Arguments) {
|
||||
if (exp.Method.Name == "Trim") left = $"trim({ExpressionLambdaToSql(argsTrim01, _tables, _selectColumnMap, tbtype, isQuoteName)} from {left})";
|
||||
if (exp.Method.Name == "TrimStart") left = $"trim(leading {ExpressionLambdaToSql(argsTrim01, _tables, _selectColumnMap, tbtype, isQuoteName)} from {left})";
|
||||
if (exp.Method.Name == "TrimStart") left = $"trim(trailing {ExpressionLambdaToSql(argsTrim01, _tables, _selectColumnMap, tbtype, isQuoteName)} from {left})";
|
||||
}
|
||||
return left;
|
||||
case "Replace": return $"replace({left}, {ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)}, {ExpressionLambdaToSql(exp.Arguments[1], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "CompareTo": return $"strcmp({left}, {ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
}
|
||||
internal override string ExpressionLambdaToSqlMemberAccessString(MemberExpression exp, List<SelectTableInfo> _tables, List<SelectColumnInfo> _selectColumnMap, SelectTableInfoType tbtype, bool isQuoteName) {
|
||||
var left = ExpressionLambdaToSql(exp.Expression, _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
switch (exp.Member.Name) {
|
||||
case "Length": return $"char_length({left})";
|
||||
}
|
||||
throw new Exception($"PostgreSQLExpression 未现实函数表达式 {exp} 解析");
|
||||
}
|
||||
|
||||
if (exp.Object.Type.FullName == "System.Math") {
|
||||
switch (exp.Method.Name) {
|
||||
case "Abs": return $"abs({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Sign": return $"sign({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Floor": return $"floor({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Round":
|
||||
if (exp.Arguments.Count > 1 && exp.Arguments[1].Type.FullName == "System.Int32") return $"round({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)}, {ExpressionLambdaToSql(exp.Arguments[1], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
return $"round({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Exp": return $"exp({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Log": return $"log({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Log10": return $"log10({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Pow": return $"pow({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Sqrt": return $"sqrt({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "PI": return $"pi()";
|
||||
case "Cos": return $"cos({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Sin": return $"sin({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Tan": return $"tan({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Acos": return $"acos({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Asin": return $"asin({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Atan": return $"atan({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Atan2": return $"atan2({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)}, {ExpressionLambdaToSql(exp.Arguments[1], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Truncate": return $"truncate({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)}, 0)";
|
||||
}
|
||||
internal override string ExpressionLambdaToSqlMemberAccessMath(MemberExpression exp, List<SelectTableInfo> _tables, List<SelectColumnInfo> _selectColumnMap, SelectTableInfoType tbtype, bool isQuoteName) {
|
||||
var left = ExpressionLambdaToSql(exp.Expression, _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
switch (exp.Member.Name) {
|
||||
case "PI": return $"pi()";
|
||||
}
|
||||
throw new Exception($"PostgreSQLExpression 未现实函数表达式 {exp} 解析");
|
||||
}
|
||||
|
||||
//dayofweek = DayOfWeek
|
||||
//dayofmonth = Day
|
||||
//dayofyear = DayOfYear
|
||||
//month = Month
|
||||
//year = Year
|
||||
//hour = Hour
|
||||
//minute = Minute
|
||||
//second = Second
|
||||
/*
|
||||
* date_add(date,interval expr type)
|
||||
date_sub(date,interval expr type)
|
||||
adddate(date,interval expr type)
|
||||
subdate(date,interval expr type)
|
||||
对日期时间进行加减法运算
|
||||
(adddate()和subdate()是date_add()和date_sub()的同义词,也
|
||||
可以用运算符+和-而不是函数
|
||||
date是一个datetime或date值,expr对date进行加减法的一个表
|
||||
达式字符串type指明表达式expr应该如何被解释
|
||||
[type值 含义 期望的expr格式]:
|
||||
second 秒 seconds
|
||||
minute 分钟 minutes
|
||||
hour 时间 hours
|
||||
day 天 days
|
||||
month 月 months
|
||||
year 年 years
|
||||
minute_second 分钟和秒 "minutes:seconds"
|
||||
hour_minute 小时和分钟 "hours:minutes"
|
||||
day_hour 天和小时 "days hours"
|
||||
year_month 年和月 "years-months"
|
||||
hour_second 小时, 分钟, "hours:minutes:seconds"
|
||||
day_minute 天, 小时, 分钟 "days hours:minutes"
|
||||
day_second 天, 小时, 分钟, 秒 "days
|
||||
hours:minutes:seconds"
|
||||
expr中允许任何标点做分隔符,如果所有是date值时结果是一个
|
||||
date值,否则结果是一个datetime值)
|
||||
如果type关键词不完整,则mysql从右端取值,day_second因为缺
|
||||
少小时分钟等于minute_second)
|
||||
如果增加month、year_month或year,天数大于结果月份的最大天
|
||||
数则使用最大天数)
|
||||
mysql> select "1997-12-31 23:59:59" + interval 1 second;
|
||||
internal override string ExpressionLambdaToSqlMemberAccessDateTime(MemberExpression exp, List<SelectTableInfo> _tables, List<SelectColumnInfo> _selectColumnMap, SelectTableInfoType tbtype, bool isQuoteName) {
|
||||
if (exp.Expression == null && exp.Member.Name == "Now") return "current_timestamp";
|
||||
var left = ExpressionLambdaToSql(exp.Expression, _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
switch (exp.Member.Name) {
|
||||
case "DayOfWeek": return $"extract(dow from ({left})::timestamp)";
|
||||
case "Day": return $"extract(day from ({left})::timestamp)";
|
||||
case "DayOfYear": return $"extract(doy from ({left})::timestamp)";
|
||||
case "Month": return $"extract(month from ({left})::timestamp)";
|
||||
case "Year": return $"extract(year from ({left})::timestamp)";
|
||||
case "Hour": return $"extract(hour from ({left})::timestamp)";
|
||||
case "Minute": return $"extract(minute from ({left})::timestamp)";
|
||||
case "Second": return $"extract(second from ({left})::timestamp)";
|
||||
case "Millisecond": return $"(extract(milliseconds from ({left})::timestamp) - extract(second from ({left})::timestamp) * 1000)";
|
||||
case "Ticks": return $"(extract(epoch from ({left})::timestamp) * 10000000 + 621355968000000000)";
|
||||
}
|
||||
throw new Exception($"PostgreSQLExpression 未现实函数表达式 {exp} 解析");
|
||||
}
|
||||
|
||||
-> 1998-01-01 00:00:00
|
||||
mysql> select interval 1 day + "1997-12-31";
|
||||
-> 1998-01-01
|
||||
mysql> select "1998-01-01" - interval 1 second;
|
||||
-> 1997-12-31 23:59:59
|
||||
mysql> select date_add("1997-12-31 23:59:59",interval 1
|
||||
second);
|
||||
-> 1998-01-01 00:00:00
|
||||
mysql> select date_add("1997-12-31 23:59:59",interval 1
|
||||
day);
|
||||
-> 1998-01-01 23:59:59
|
||||
mysql> select date_add("1997-12-31 23:59:59",interval
|
||||
"1:1" minute_second);
|
||||
-> 1998-01-01 00:01:00
|
||||
mysql> select date_sub("1998-01-01 00:00:00",interval "1
|
||||
1:1:1" day_second);
|
||||
-> 1997-12-30 22:58:59
|
||||
mysql> select date_add("1998-01-01 00:00:00", interval "-1
|
||||
10" day_hour);
|
||||
-> 1997-12-30 14:00:00
|
||||
mysql> select date_sub("1998-01-02", interval 31 day);
|
||||
-> 1997-12-02
|
||||
mysql> select extract(year from "1999-07-02");
|
||||
-> 1999
|
||||
mysql> select extract(year_month from "1999-07-02
|
||||
01:02:03");
|
||||
-> 199907
|
||||
mysql> select extract(day_minute from "1999-07-02
|
||||
01:02:03");
|
||||
-> 20102
|
||||
*/
|
||||
internal override string ExpressionLambdaToSqlMemberAccessTimeSpan(MemberExpression exp, List<SelectTableInfo> _tables, List<SelectColumnInfo> _selectColumnMap, SelectTableInfoType tbtype, bool isQuoteName) {
|
||||
var left = ExpressionLambdaToSql(exp.Expression, _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
switch (exp.Member.Name) {
|
||||
case "Days": return $"floor(extract(epoch from ({left})::interval) / {60 * 60 * 24})";
|
||||
case "Hours": return $"extract(hour from ({left})::interval)";
|
||||
case "Milliseconds": return $"(extract(milliseconds from ({left})::interval) - extract(second from ({left})::interval) * 1000)";
|
||||
case "Minutes": return $"extract(minute from ({left})::interval)";
|
||||
case "Seconds": return $"extract(second from ({left})::interval)";
|
||||
case "Ticks": return $"(extract(epoch from ({left})::interval) * 10000000)";
|
||||
case "TotalDays": return $"floor(extract(epoch from ({left})::interval) / {60 * 60 * 24})";
|
||||
case "TotalHours": return $"floor(extract(epoch from ({left})::interval) / {60 * 60})";
|
||||
case "TotalMilliseconds": return $"(epoch from ({left})::interval + extract(milliseconds from ({left})::interval) - extract(second from ({left})::interval) * 1000)";
|
||||
case "TotalMinutes": return $"floor(extract(epoch from ({left})::interval) / 60)";
|
||||
case "TotalSeconds": return $"extract(epoch from ({left})::interval)";
|
||||
}
|
||||
throw new Exception($"PostgreSQLExpression 未现实函数表达式 {exp} 解析");
|
||||
}
|
||||
internal override string ExpressionLambdaToSqlCallString(MethodCallExpression exp, List<SelectTableInfo> _tables, List<SelectColumnInfo> _selectColumnMap, SelectTableInfoType tbtype, bool isQuoteName) {
|
||||
var left = ExpressionLambdaToSql(exp.Object, _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
switch (exp.Method.Name) {
|
||||
case "StartsWith":
|
||||
case "EndsWith":
|
||||
case "Contains":
|
||||
var args0Value = ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
if (args0Value == "NULL") return $"({left}) IS NULL";
|
||||
var likeOpt = "LIKE";
|
||||
if (exp.Arguments.Count > 1) {
|
||||
if (exp.Arguments[1].Type == typeof(bool) ||
|
||||
exp.Arguments[1].Type == typeof(StringComparison) && ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName).Contains("IgnoreCase")) likeOpt = "ILIKE";
|
||||
}
|
||||
if (exp.Method.Name == "StartsWith") return $"({left}) {likeOpt} {(args0Value.StartsWith("'") ? args0Value.Insert(1, "%") : $"('%' || ({args0Value})::varchar)")}";
|
||||
if (exp.Method.Name == "EndsWith") return $"({left}) {likeOpt} {(args0Value.EndsWith("'") ? args0Value.Insert(args0Value.Length - 1, "%") : $"(({args0Value})::varchar || '%')")}";
|
||||
if (args0Value.StartsWith("'") && args0Value.EndsWith("'")) return $"({left}) {likeOpt} {args0Value.Insert(1, "%").Insert(args0Value.Length, "%")}";
|
||||
return $"({left}) {likeOpt} ('%' || ({args0Value})::varchar || '%')";
|
||||
case "ToLower": return $"lower({left})";
|
||||
case "ToUpper": return $"upper({left})";
|
||||
case "Substring":
|
||||
var substrArgs1 = ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
if (long.TryParse(substrArgs1, out var testtrylng1)) substrArgs1 = (testtrylng1 + 1).ToString();
|
||||
else substrArgs1 += " + 1";
|
||||
if (exp.Arguments.Count == 1) return $"substr({left}, {substrArgs1})";
|
||||
return $"substr({left}, {substrArgs1}, {ExpressionLambdaToSql(exp.Arguments[1], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "IndexOf": return $"(strpos({left}, {ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)}) - 1)";
|
||||
case "PadLeft":
|
||||
if (exp.Arguments.Count == 1) return $"lpad({left}, {ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
return $"lpad({left}, {ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)}, {ExpressionLambdaToSql(exp.Arguments[1], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "PadRight":
|
||||
if (exp.Arguments.Count == 1) return $"rpad({left}, {ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
return $"rpad({left}, {ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)}, {ExpressionLambdaToSql(exp.Arguments[1], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Trim":
|
||||
case "TrimStart":
|
||||
case "TrimEnd":
|
||||
if (exp.Arguments.Count == 0) {
|
||||
if (exp.Method.Name == "Trim") return $"trim({left})";
|
||||
if (exp.Method.Name == "TrimStart") return $"ltrim({left})";
|
||||
if (exp.Method.Name == "TrimEnd") return $"rtrim({left})";
|
||||
}
|
||||
var trimArg = "";
|
||||
foreach (var argsTrim02 in exp.Arguments) {
|
||||
var argsTrim01s = new[] { argsTrim02 };
|
||||
if (argsTrim02.NodeType == ExpressionType.NewArrayInit) {
|
||||
var arritem = argsTrim02 as NewArrayExpression;
|
||||
argsTrim01s = arritem.Expressions.ToArray();
|
||||
}
|
||||
foreach (var argsTrim01 in argsTrim01s) {
|
||||
var trimChr = ExpressionLambdaToSql(argsTrim01, _tables, _selectColumnMap, tbtype, isQuoteName).Trim('"');
|
||||
if (trimChr.Length == 1) trimArg += trimChr;
|
||||
else trimArg += $" || ({trimArg})";
|
||||
}
|
||||
}
|
||||
if (exp.Method.Name == "Trim") left = $"trim({left}, {trimArg})";
|
||||
if (exp.Method.Name == "TrimStart") left = $"ltrim({left}, {trimArg})";
|
||||
if (exp.Method.Name == "TrimEnd") left = $"rtrim({left}, {trimArg})";
|
||||
return left;
|
||||
case "Replace": return $"replace({left}, {ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)}, {ExpressionLambdaToSql(exp.Arguments[1], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "CompareTo": return $"strcmp({left}, {ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
}
|
||||
throw new Exception($"PostgreSQLExpression 未现实函数表达式 {exp} 解析");
|
||||
}
|
||||
|
||||
//convert
|
||||
var xxx = DateTime.Now.ToString("");
|
||||
internal override string ExpressionLambdaToSqlCallMath(MethodCallExpression exp, List<SelectTableInfo> _tables, List<SelectColumnInfo> _selectColumnMap, SelectTableInfoType tbtype, bool isQuoteName) {
|
||||
switch (exp.Method.Name) {
|
||||
case "Abs": return $"abs({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Sign": return $"sign({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Floor": return $"floor({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Ceiling": return $"ceiling({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Round":
|
||||
if (exp.Arguments.Count > 1 && exp.Arguments[1].Type.FullName == "System.Int32") return $"round({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)}, {ExpressionLambdaToSql(exp.Arguments[1], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
return $"round({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Exp": return $"exp({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Log": return $"log({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Log10": return $"log10({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Pow": return $"pow({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)}, {ExpressionLambdaToSql(exp.Arguments[1], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Sqrt": return $"sqrt({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Cos": return $"cos({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Sin": return $"sin({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Tan": return $"tan({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Acos": return $"acos({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Asin": return $"asin({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Atan": return $"atan({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Atan2": return $"atan2({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)}, {ExpressionLambdaToSql(exp.Arguments[1], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Truncate": return $"trunc({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)}, 0)";
|
||||
}
|
||||
throw new Exception($"PostgreSQLExpression 未现实函数表达式 {exp} 解析");
|
||||
}
|
||||
|
||||
|
||||
throw new Exception($"MySqlExpression 未现实函数表达式 {exp} 解析");
|
||||
internal override string ExpressionLambdaToSqlCallDateTime(MethodCallExpression exp, List<SelectTableInfo> _tables, List<SelectColumnInfo> _selectColumnMap, SelectTableInfoType tbtype, bool isQuoteName) {
|
||||
var left = ExpressionLambdaToSql(exp.Object, _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
var args1 = ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
switch (exp.Method.Name) {
|
||||
case "Add": return $"(({left})::timestamp + ({args1})::interval)";
|
||||
case "AddDays": return $"(({left})::timestamp + (({args1}) || ' day')::interval)";
|
||||
case "AddHours": return $"(({left})::timestamp + (({args1}) || ' hour')::interval)";
|
||||
case "AddMilliseconds": return $"(({left})::timestamp + (({args1}) || ' milliseconds')::interval)";
|
||||
case "AddMinutes": return $"(({left})::timestamp + (({args1}) || ' minute')::interval)";
|
||||
case "AddMonths": return $"(({left})::timestamp + (({args1}) || ' month')::interval)";
|
||||
case "AddSeconds": return $"(({left})::timestamp + (({args1}) || ' second')::interval)";
|
||||
case "AddTicks": return $"(({left})::timestamp + (({args1}) / 10 || ' microseconds')::interval)";
|
||||
case "AddYears": return $"(({left})::timestamp + (({args1}) || ' year')::interval)";
|
||||
case "Subtract":
|
||||
if (exp.Arguments[0].Type.FullName == "System.DateTime" || exp.Arguments[0].Type.GenericTypeArguments.FirstOrDefault()?.FullName == "System.DateTime")
|
||||
return $"(({left})::timestamp - ({args1})::timestamp)";
|
||||
if (exp.Arguments[0].Type.FullName == "System.TimeSpan" || exp.Arguments[0].Type.GenericTypeArguments.FirstOrDefault()?.FullName == "System.TimeSpan")
|
||||
return $"(({left})::timestamp - ({args1})::interval)";
|
||||
break;
|
||||
}
|
||||
throw new Exception($"PostgreSQLExpression 未现实函数表达式 {exp} 解析");
|
||||
}
|
||||
internal override string ExpressionLambdaToSqlCallTimeSpan(MethodCallExpression exp, List<SelectTableInfo> _tables, List<SelectColumnInfo> _selectColumnMap, SelectTableInfoType tbtype, bool isQuoteName) {
|
||||
var left = ExpressionLambdaToSql(exp.Object, _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
var args1 = ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
switch (exp.Method.Name) {
|
||||
case "Add": return $"(({left})::interval + ({args1})::interval)";
|
||||
case "Subtract": return $"(({left})::interval - ({args1})::interval)";
|
||||
}
|
||||
throw new Exception($"PostgreSQLExpression 未现实函数表达式 {exp} 解析");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -1,8 +1,10 @@
|
||||
using FreeSql.Internal;
|
||||
using MySql.Data.MySqlClient;
|
||||
using Npgsql;
|
||||
using NpgsqlTypes;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Data.Common;
|
||||
using System.Linq;
|
||||
|
||||
namespace FreeSql.PostgreSQL {
|
||||
|
||||
@ -14,35 +16,44 @@ namespace FreeSql.PostgreSQL {
|
||||
|
||||
internal override DbParameter AppendParamter(List<DbParameter> _params, string parameterName, object value) {
|
||||
if (string.IsNullOrEmpty(parameterName)) parameterName = $"p_{_params?.Count}";
|
||||
MySqlParameter ret = null;
|
||||
if (value == null) ret = new MySqlParameter { ParameterName = $"{parameterName}", Value = DBNull.Value };
|
||||
NpgsqlParameter ret = null;
|
||||
if (value == null) ret = new NpgsqlParameter { ParameterName = $"{parameterName}", Value = DBNull.Value };
|
||||
else {
|
||||
var type = value.GetType();
|
||||
ret = new MySqlParameter {
|
||||
ret = new NpgsqlParameter {
|
||||
ParameterName = parameterName,
|
||||
Value = value
|
||||
};
|
||||
var tp = _orm.CodeFirst.GetDbInfo(type)?.type;
|
||||
if (tp != null) ret.MySqlDbType = (MySqlDbType)tp.Value;
|
||||
if (value.GetType().IsEnum || value.GetType().GenericTypeArguments.FirstOrDefault()?.IsEnum == true) {
|
||||
ret.DataTypeName = "";
|
||||
} else {
|
||||
var tp = _orm.CodeFirst.GetDbInfo(type)?.type;
|
||||
if (tp != null) ret.NpgsqlDbType = (NpgsqlDbType)tp.Value;
|
||||
}
|
||||
}
|
||||
_params?.Add(ret);
|
||||
return ret;
|
||||
}
|
||||
|
||||
internal override DbParameter[] GetDbParamtersByObject(string sql, object obj) =>
|
||||
Utils.GetDbParamtersByObject<MySqlParameter>(sql, obj, "?", (name, type, value) => {
|
||||
var cp = new MySqlParameter {
|
||||
Utils.GetDbParamtersByObject<NpgsqlParameter>(sql, obj, "@", (name, type, value) => {
|
||||
var ret = new NpgsqlParameter {
|
||||
ParameterName = name,
|
||||
Value = value ?? DBNull.Value
|
||||
};
|
||||
var tp = _orm.CodeFirst.GetDbInfo(type)?.type;
|
||||
if (tp != null) cp.MySqlDbType = (MySqlDbType)tp.Value;
|
||||
return cp;
|
||||
if (value.GetType().IsEnum || value.GetType().GenericTypeArguments.FirstOrDefault()?.IsEnum == true) {
|
||||
ret.DataTypeName = "";
|
||||
} else {
|
||||
var tp = _orm.CodeFirst.GetDbInfo(type)?.type;
|
||||
if (tp != null) ret.NpgsqlDbType = (NpgsqlDbType)tp.Value;
|
||||
}
|
||||
return ret;
|
||||
});
|
||||
|
||||
internal override string FormatSql(string sql, params object[] args) => sql?.FormatMySql(args);
|
||||
internal override string QuoteSqlName(string name) => $"`{name.Trim('`').Replace(".", "`.`")}`";
|
||||
internal override string QuoteParamterName(string name) => $"?{name}";
|
||||
internal override string IsNull(string sql, object value) => $"ifnull({sql}, {value})";
|
||||
internal override string QuoteSqlName(string name) => $"\"{name.Trim('"').Replace(".", "\".\"")}\"";
|
||||
internal override string QuoteParamterName(string name) => $"@{name}";
|
||||
internal override string IsNull(string sql, object value) => $"coalesce({sql}, {value})";
|
||||
internal override string StringConcat(string left, string right, Type leftType, Type rightType) => $"{left} || {right}";
|
||||
}
|
||||
}
|
||||
|
@ -10,7 +10,10 @@ namespace FreeSql.SqlServer.Curd {
|
||||
|
||||
class SqlServerSelect<T1> : FreeSql.Internal.CommonProvider.Select1Provider<T1> where T1 : class {
|
||||
|
||||
internal static string ToSqlStatic(CommonUtils _commonUtils, string _select, string field, StringBuilder _join, StringBuilder _where, string _groupby, string _having, string _orderby, int _skip, int _limit, List<SelectTableInfo> _tables) {
|
||||
internal static string ToSqlStatic(CommonUtils _commonUtils, string _select, string field, StringBuilder _join, StringBuilder _where, string _groupby, string _having, string _orderby, int _skip, int _limit, List<SelectTableInfo> _tables, IFreeSql _orm) {
|
||||
if (_orm.CodeFirst.IsAutoSyncStructure)
|
||||
_orm.CodeFirst.SyncStructure(_tables.Select(a => a.Table.Type).ToArray());
|
||||
|
||||
var sb = new StringBuilder();
|
||||
sb.Append(_select);
|
||||
if (_limit > 0) sb.Append("TOP ").Append(_skip + _limit).Append(" ");
|
||||
@ -85,42 +88,42 @@ namespace FreeSql.SqlServer.Curd {
|
||||
public override ISelect<T1, T2, T3, T4, T5, T6, T7, T8> From<T2, T3, T4, T5, T6, T7, T8>(Expression<Func<ISelectFromExpression<T1>, T2, T3, T4, T5, T6, T7, T8, ISelectFromExpression<T1>>> exp) { this.InternalFrom(exp?.Body); var ret = new SqlServerSelect<T1, T2, T3, T4, T5, T6, T7, T8>(_orm, _commonUtils, _commonExpression, null); SqlServerSelect<T1>.CopyData(this, ret); return ret; }
|
||||
public override ISelect<T1, T2, T3, T4, T5, T6, T7, T8, T9> From<T2, T3, T4, T5, T6, T7, T8, T9>(Expression<Func<ISelectFromExpression<T1>, T2, T3, T4, T5, T6, T7, T8, T9, ISelectFromExpression<T1>>> exp) { this.InternalFrom(exp?.Body); var ret = new SqlServerSelect<T1, T2, T3, T4, T5, T6, T7, T8, T9>(_orm, _commonUtils, _commonExpression, null); SqlServerSelect<T1>.CopyData(this, ret); return ret; }
|
||||
public override ISelect<T1, T2, T3, T4, T5, T6, T7, T8, T9, T10> From<T2, T3, T4, T5, T6, T7, T8, T9, T10>(Expression<Func<ISelectFromExpression<T1>, T2, T3, T4, T5, T6, T7, T8, T9, T10, ISelectFromExpression<T1>>> exp) { this.InternalFrom(exp?.Body); var ret = new SqlServerSelect<T1, T2, T3, T4, T5, T6, T7, T8, T9, T10>(_orm, _commonUtils, _commonExpression, null); SqlServerSelect<T1>.CopyData(this, ret); return ret; }
|
||||
public override string ToSql(string field = null) => ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables);
|
||||
public override string ToSql(string field = null) => ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables, _orm);
|
||||
}
|
||||
class SqlServerSelect<T1, T2> : FreeSql.Internal.CommonProvider.Select2Provider<T1, T2> where T1 : class where T2 : class {
|
||||
public SqlServerSelect(IFreeSql orm, CommonUtils commonUtils, CommonExpression commonExpression, object dywhere) : base(orm, commonUtils, commonExpression, dywhere) { }
|
||||
public override string ToSql(string field = null) => SqlServerSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables);
|
||||
public override string ToSql(string field = null) => SqlServerSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables, _orm);
|
||||
}
|
||||
class SqlServerSelect<T1, T2, T3> : FreeSql.Internal.CommonProvider.Select3Provider<T1, T2, T3> where T1 : class where T2 : class where T3 : class {
|
||||
public SqlServerSelect(IFreeSql orm, CommonUtils commonUtils, CommonExpression commonExpression, object dywhere) : base(orm, commonUtils, commonExpression, dywhere) { }
|
||||
public override string ToSql(string field = null) => SqlServerSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables);
|
||||
public override string ToSql(string field = null) => SqlServerSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables, _orm);
|
||||
}
|
||||
class SqlServerSelect<T1, T2, T3, T4> : FreeSql.Internal.CommonProvider.Select4Provider<T1, T2, T3, T4> where T1 : class where T2 : class where T3 : class where T4 : class {
|
||||
public SqlServerSelect(IFreeSql orm, CommonUtils commonUtils, CommonExpression commonExpression, object dywhere) : base(orm, commonUtils, commonExpression, dywhere) { }
|
||||
public override string ToSql(string field = null) => SqlServerSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables);
|
||||
public override string ToSql(string field = null) => SqlServerSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables, _orm);
|
||||
}
|
||||
class SqlServerSelect<T1, T2, T3, T4, T5> : FreeSql.Internal.CommonProvider.Select5Provider<T1, T2, T3, T4, T5> where T1 : class where T2 : class where T3 : class where T4 : class where T5 : class {
|
||||
public SqlServerSelect(IFreeSql orm, CommonUtils commonUtils, CommonExpression commonExpression, object dywhere) : base(orm, commonUtils, commonExpression, dywhere) { }
|
||||
public override string ToSql(string field = null) => SqlServerSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables);
|
||||
public override string ToSql(string field = null) => SqlServerSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables, _orm);
|
||||
}
|
||||
class SqlServerSelect<T1, T2, T3, T4, T5, T6> : FreeSql.Internal.CommonProvider.Select6Provider<T1, T2, T3, T4, T5, T6> where T1 : class where T2 : class where T3 : class where T4 : class where T5 : class where T6 : class {
|
||||
public SqlServerSelect(IFreeSql orm, CommonUtils commonUtils, CommonExpression commonExpression, object dywhere) : base(orm, commonUtils, commonExpression, dywhere) { }
|
||||
public override string ToSql(string field = null) => SqlServerSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables);
|
||||
public override string ToSql(string field = null) => SqlServerSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables, _orm);
|
||||
}
|
||||
class SqlServerSelect<T1, T2, T3, T4, T5, T6, T7> : FreeSql.Internal.CommonProvider.Select7Provider<T1, T2, T3, T4, T5, T6, T7> where T1 : class where T2 : class where T3 : class where T4 : class where T5 : class where T6 : class where T7 : class {
|
||||
public SqlServerSelect(IFreeSql orm, CommonUtils commonUtils, CommonExpression commonExpression, object dywhere) : base(orm, commonUtils, commonExpression, dywhere) { }
|
||||
public override string ToSql(string field = null) => SqlServerSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables);
|
||||
public override string ToSql(string field = null) => SqlServerSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables, _orm);
|
||||
}
|
||||
class SqlServerSelect<T1, T2, T3, T4, T5, T6, T7, T8> : FreeSql.Internal.CommonProvider.Select8Provider<T1, T2, T3, T4, T5, T6, T7, T8> where T1 : class where T2 : class where T3 : class where T4 : class where T5 : class where T6 : class where T7 : class where T8 : class {
|
||||
public SqlServerSelect(IFreeSql orm, CommonUtils commonUtils, CommonExpression commonExpression, object dywhere) : base(orm, commonUtils, commonExpression, dywhere) { }
|
||||
public override string ToSql(string field = null) => SqlServerSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables);
|
||||
public override string ToSql(string field = null) => SqlServerSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables, _orm);
|
||||
}
|
||||
class SqlServerSelect<T1, T2, T3, T4, T5, T6, T7, T8, T9> : FreeSql.Internal.CommonProvider.Select9Provider<T1, T2, T3, T4, T5, T6, T7, T8, T9> where T1 : class where T2 : class where T3 : class where T4 : class where T5 : class where T6 : class where T7 : class where T8 : class where T9 : class {
|
||||
public SqlServerSelect(IFreeSql orm, CommonUtils commonUtils, CommonExpression commonExpression, object dywhere) : base(orm, commonUtils, commonExpression, dywhere) { }
|
||||
public override string ToSql(string field = null) => SqlServerSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables);
|
||||
public override string ToSql(string field = null) => SqlServerSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables, _orm);
|
||||
}
|
||||
class SqlServerSelect<T1, T2, T3, T4, T5, T6, T7, T8, T9, T10> : FreeSql.Internal.CommonProvider.Select10Provider<T1, T2, T3, T4, T5, T6, T7, T8, T9, T10> where T1 : class where T2 : class where T3 : class where T4 : class where T5 : class where T6 : class where T7 : class where T8 : class where T9 : class where T10 : class {
|
||||
public SqlServerSelect(IFreeSql orm, CommonUtils commonUtils, CommonExpression commonExpression, object dywhere) : base(orm, commonUtils, commonExpression, dywhere) { }
|
||||
public override string ToSql(string field = null) => SqlServerSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables);
|
||||
public override string ToSql(string field = null) => SqlServerSelect<T1>.ToSqlStatic(_commonUtils, _select, field ?? this.GetAllField().field, _join, _where, _groupby, _having, _orderby, _skip, _limit, _tables, _orm);
|
||||
}
|
||||
}
|
||||
|
@ -23,6 +23,7 @@ namespace FreeSql.SqlServer {
|
||||
}
|
||||
}
|
||||
}
|
||||
static DateTime dt1970 = new DateTime(1970, 1, 1);
|
||||
public override object AddslashesProcessParam(object param) {
|
||||
if (param == null) return "NULL";
|
||||
if (param is bool || param is bool?)
|
||||
@ -31,12 +32,16 @@ namespace FreeSql.SqlServer {
|
||||
return string.Concat("'", param.ToString().Replace("'", "''"), "'");
|
||||
else if (decimal.TryParse(string.Concat(param), out var trydec))
|
||||
return param;
|
||||
else if (param is DateTime) {
|
||||
DateTime dt = (DateTime)param;
|
||||
return string.Concat("'", dt.ToString("yyyy-MM-dd HH:mm:ss.ffffff"), "'");
|
||||
} else if (param is DateTime?) {
|
||||
DateTime? dt = param as DateTime?;
|
||||
return string.Concat("'", dt.Value.ToString("yyyy-MM-dd HH:mm:ss.ffffff"), "'");
|
||||
else if (param is DateTime)
|
||||
return string.Concat("'", ((DateTime)param).ToString("yyyy-MM-dd HH:mm:ss.fff"), "'");
|
||||
else if (param is DateTime?)
|
||||
return string.Concat("'", (param as DateTime?).Value.ToString("yyyy-MM-dd HH:mm:ss.fff"), "'");
|
||||
else if (param is TimeSpan) {
|
||||
var ts = (TimeSpan)param;
|
||||
return string.Concat("'", dt1970.Add(ts).ToString("yyyy-MM-dd HH:mm:ss.fff"), "'");
|
||||
} else if (param is TimeSpan) {
|
||||
var ts = (param as TimeSpan?).Value;
|
||||
return string.Concat("'", dt1970.Add(ts).ToString("yyyy-MM-dd HH:mm:ss.fff"), "'");
|
||||
} else if (param is IEnumerable) {
|
||||
var sb = new StringBuilder();
|
||||
var ie = param as IEnumerable;
|
||||
|
@ -160,12 +160,21 @@ where a.object_id in (object_id(N'[{0}].[{1}]'))", isRenameTable ? tboldname : t
|
||||
return sb.Length == 0 ? null : sb.ToString();
|
||||
}
|
||||
|
||||
Dictionary<string, bool> dicSyced = new Dictionary<string, bool>();
|
||||
public bool SyncStructure<TEntity>() => this.SyncStructure(typeof(TEntity));
|
||||
public bool SyncStructure(params Type[] entityTypes) {
|
||||
var ddl = this.GetComparisonDDLStatements(entityTypes);
|
||||
if (string.IsNullOrEmpty(ddl)) return true;
|
||||
if (entityTypes == null) return true;
|
||||
var syncTypes = entityTypes.Where(a => dicSyced.ContainsKey(a.FullName) == false).ToArray();
|
||||
if (syncTypes.Any() == false) return true;
|
||||
var ddl = this.GetComparisonDDLStatements(syncTypes);
|
||||
if (string.IsNullOrEmpty(ddl)) {
|
||||
foreach (var syncType in syncTypes) dicSyced.Add(syncType.FullName, true);
|
||||
return true;
|
||||
}
|
||||
try {
|
||||
return _orm.Ado.ExecuteNonQuery(CommandType.Text, ddl) > 0;
|
||||
var affrows = _orm.Ado.ExecuteNonQuery(CommandType.Text, ddl);
|
||||
foreach (var syncType in syncTypes) dicSyced.Add(syncType.FullName, true);
|
||||
return affrows > 0;
|
||||
} catch {
|
||||
return false;
|
||||
}
|
||||
|
@ -2,6 +2,7 @@
|
||||
using FreeSql.Internal.Model;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Linq.Expressions;
|
||||
|
||||
namespace FreeSql.SqlServer {
|
||||
@ -9,73 +10,146 @@ namespace FreeSql.SqlServer {
|
||||
|
||||
public SqlServerExpression(CommonUtils common) : base(common) { }
|
||||
|
||||
internal override string ExpressionLambdaToSqlCall(MethodCallExpression exp, List<SelectTableInfo> _tables, List<SelectColumnInfo> _selectColumnMap, SelectTableInfoType tbtype, bool isQuoteName) {
|
||||
if (exp.Object.Type.FullName == "System.String") {
|
||||
var left = ExpressionLambdaToSql(exp.Object, _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
switch (exp.Method.Name) {
|
||||
case "StartsWith":
|
||||
case "EndsWith":
|
||||
case "Contains":
|
||||
var args0Value = ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
if (args0Value == "NULL") return $"({left}) IS NULL";
|
||||
if (exp.Method.Name == "StartsWith") return $"({left}) LIKE {(args0Value.StartsWith("'") ? args0Value.Insert(1, "%") : $"concat('%', {args0Value})")}";
|
||||
if (exp.Method.Name == "EndsWith") return $"({left}) LIKE {(args0Value.EndsWith("'") ? args0Value.Insert(args0Value.Length - 1, "%") : $"concat({args0Value}, '%')")}";
|
||||
if (args0Value.StartsWith("'") && args0Value.EndsWith("'")) return $"({left}) LIKE {args0Value.Insert(1, "%").Insert(args0Value.Length, "%")}";
|
||||
return $"({left}) like concat('%', {args0Value}, '%')";
|
||||
case "ToLower": return $"lower({left})";
|
||||
case "ToUpper": return $"upper({left})";
|
||||
case "Substring": return $"substr({left}, {ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)} + 1, {ExpressionLambdaToSql(exp.Arguments[1], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Length": return $"char_length({left})";
|
||||
case "IndexOf":
|
||||
var indexOfFindStr = ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
if (exp.Arguments.Count > 1 && exp.Arguments[1].Type.FullName == "System.Int32") return $"(locate({left}, {indexOfFindStr}, ParseLambdaToSql(exp.Arguments[1], _tables, _selectColumnMap, tbtype, isQuoteName) + 1) - 1)";
|
||||
return $"(locate({left}, {indexOfFindStr}) - 1)";
|
||||
case "PadLeft": return $"lpad({left}, {ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)}, {ExpressionLambdaToSql(exp.Arguments[1], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "PadRight": return $"rpad({left}, {ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)}, {ExpressionLambdaToSql(exp.Arguments[1], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Trim":
|
||||
case "TrimStart":
|
||||
case "TrimEnd":
|
||||
if (exp.Arguments.Count == 0) {
|
||||
if (exp.Method.Name == "Trim") return $"trim({left})";
|
||||
if (exp.Method.Name == "TrimStart") return $"ltrim({left})";
|
||||
if (exp.Method.Name == "TrimStart") return $"rtrim({left})";
|
||||
}
|
||||
foreach (var argsTrim01 in exp.Arguments) {
|
||||
if (exp.Method.Name == "Trim") left = $"trim({ExpressionLambdaToSql(argsTrim01, _tables, _selectColumnMap, tbtype, isQuoteName)} from {left})";
|
||||
if (exp.Method.Name == "TrimStart") left = $"trim(leading {ExpressionLambdaToSql(argsTrim01, _tables, _selectColumnMap, tbtype, isQuoteName)} from {left})";
|
||||
if (exp.Method.Name == "TrimStart") left = $"trim(trailing {ExpressionLambdaToSql(argsTrim01, _tables, _selectColumnMap, tbtype, isQuoteName)} from {left})";
|
||||
}
|
||||
return left;
|
||||
case "Replace": return $"replace({left}, {ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)}, {ExpressionLambdaToSql(exp.Arguments[1], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "CompareTo": return $"strcmp({left}, {ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
}
|
||||
internal override string ExpressionLambdaToSqlMemberAccessString(MemberExpression exp, List<SelectTableInfo> _tables, List<SelectColumnInfo> _selectColumnMap, SelectTableInfoType tbtype, bool isQuoteName) {
|
||||
var left = ExpressionLambdaToSql(exp.Expression, _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
switch (exp.Member.Name) {
|
||||
case "Length": return $"len({left})";
|
||||
}
|
||||
throw new Exception($"SqlServerExpression 未现实函数表达式 {exp} 解析");
|
||||
}
|
||||
|
||||
if (exp.Object.Type.FullName == "System.Math") {
|
||||
switch (exp.Method.Name) {
|
||||
case "Abs": return $"abs({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Sign": return $"sign({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Floor": return $"floor({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Round":
|
||||
if (exp.Arguments.Count > 1 && exp.Arguments[1].Type.FullName == "System.Int32") return $"round({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)}, {ExpressionLambdaToSql(exp.Arguments[1], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
return $"round({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Exp": return $"exp({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Log": return $"log({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Log10": return $"log10({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Pow": return $"pow({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Sqrt": return $"sqrt({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "PI": return $"pi()";
|
||||
case "Cos": return $"cos({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Sin": return $"sin({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Tan": return $"tan({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Acos": return $"acos({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Asin": return $"asin({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Atan": return $"atan({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Atan2": return $"atan2({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)}, {ExpressionLambdaToSql(exp.Arguments[1], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Truncate": return $"truncate({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)}, 0)";
|
||||
}
|
||||
internal override string ExpressionLambdaToSqlMemberAccessMath(MemberExpression exp, List<SelectTableInfo> _tables, List<SelectColumnInfo> _selectColumnMap, SelectTableInfoType tbtype, bool isQuoteName) {
|
||||
var left = ExpressionLambdaToSql(exp.Expression, _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
switch (exp.Member.Name) {
|
||||
case "PI": return $"pi()";
|
||||
}
|
||||
throw new Exception($"SqlServerExpression 未现实函数表达式 {exp} 解析");
|
||||
}
|
||||
|
||||
internal override string ExpressionLambdaToSqlMemberAccessDateTime(MemberExpression exp, List<SelectTableInfo> _tables, List<SelectColumnInfo> _selectColumnMap, SelectTableInfoType tbtype, bool isQuoteName) {
|
||||
if (exp.Expression == null && exp.Member.Name == "Now") return "getdate()";
|
||||
var left = ExpressionLambdaToSql(exp.Expression, _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
switch (exp.Member.Name) {
|
||||
case "DayOfWeek": return $"(datepart(weekday, {left}) - 1)";
|
||||
case "Day": return $"datepart(day, {left})";
|
||||
case "DayOfYear": return $"datepart(dayofyear, {left})";
|
||||
case "Month": return $"datepart(month, {left})";
|
||||
case "Year": return $"datepart(year, {left})";
|
||||
case "Hour": return $"datepart(hour, {left})";
|
||||
case "Minute": return $"datepart(minute, {left})";
|
||||
case "Second": return $"datepart(second, {left})";
|
||||
case "Millisecond": return $"datepart(millisecond, {left})";
|
||||
case "Ticks": return $"(datediff(second, '1970-1-1', {left}) * 10000000 + 621355968000000000)";
|
||||
}
|
||||
throw new Exception($"SqlServerExpression 未现实函数表达式 {exp} 解析");
|
||||
}
|
||||
|
||||
internal override string ExpressionLambdaToSqlMemberAccessTimeSpan(MemberExpression exp, List<SelectTableInfo> _tables, List<SelectColumnInfo> _selectColumnMap, SelectTableInfoType tbtype, bool isQuoteName) {
|
||||
var left = ExpressionLambdaToSql(exp.Expression, _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
switch (exp.Member.Name) {
|
||||
case "Days": return $"datediff(day, '1970-1-1', {left})";
|
||||
case "Hours": return $"datepart(hour, '1970-1-1', {left})";
|
||||
case "Milliseconds": return $"datepart(millisecond, {left})";
|
||||
case "Minutes": return $"datepart(minute, {left})";
|
||||
case "Seconds": return $"datepart(second, {left})";
|
||||
case "Ticks": return $"(datediff(millisecond, '1970-1-1', {left}) * 10000)";
|
||||
case "TotalDays": return $"datediff(day, '1970-1-1', {left})";
|
||||
case "TotalHours": return $"datediff(hour, '1970-1-1', {left})";
|
||||
case "TotalMilliseconds": return $"datediff(millisecond, '1970-1-1', {left})";
|
||||
case "TotalMinutes": return $"datediff(minute, '1970-1-1', {left})";
|
||||
case "TotalSeconds": return $"datediff(second, '1970-1-1', {left})";
|
||||
}
|
||||
throw new Exception($"SqlServerExpression 未现实函数表达式 {exp} 解析");
|
||||
}
|
||||
internal override string ExpressionLambdaToSqlCallString(MethodCallExpression exp, List<SelectTableInfo> _tables, List<SelectColumnInfo> _selectColumnMap, SelectTableInfoType tbtype, bool isQuoteName) {
|
||||
var left = ExpressionLambdaToSql(exp.Object, _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
switch (exp.Method.Name) {
|
||||
case "StartsWith":
|
||||
case "EndsWith":
|
||||
case "Contains":
|
||||
var args0Value = ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
if (args0Value == "NULL") return $"({left}) IS NULL";
|
||||
if (exp.Method.Name == "StartsWith") return $"({left}) LIKE {(args0Value.StartsWith("'") ? args0Value.Insert(1, "%") : $"('%' + cast({args0Value} as nvarchar))")}";
|
||||
if (exp.Method.Name == "EndsWith") return $"({left}) LIKE {(args0Value.EndsWith("'") ? args0Value.Insert(args0Value.Length - 1, "%") : $"(cast({args0Value} as nvarchar) + '%')")}";
|
||||
if (args0Value.StartsWith("'") && args0Value.EndsWith("'")) return $"({left}) LIKE {args0Value.Insert(1, "%").Insert(args0Value.Length, "%")}";
|
||||
return $"({left}) LIKE ('%' + cast({args0Value} as nvarchar) + '%')";
|
||||
case "ToLower": return $"lower({left})";
|
||||
case "ToUpper": return $"upper({left})";
|
||||
case "Substring":
|
||||
var substrArgs1 = ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
if (long.TryParse(substrArgs1, out var testtrylng1)) substrArgs1 = (testtrylng1 + 1).ToString();
|
||||
else substrArgs1 += " + 1";
|
||||
if (exp.Arguments.Count == 1) return $"substring({left}, {substrArgs1})";
|
||||
return $"substring({left}, {substrArgs1}, {ExpressionLambdaToSql(exp.Arguments[1], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "IndexOf":
|
||||
var indexOfFindStr = ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
if (exp.Arguments.Count > 1 && exp.Arguments[1].Type.FullName == "System.Int32") return $"(charindex({left}, {indexOfFindStr}, {ExpressionLambdaToSql(exp.Arguments[1], _tables, _selectColumnMap, tbtype, isQuoteName)} + 1) - 1)";
|
||||
return $"(locate({left}, {indexOfFindStr}) - 1)";
|
||||
case "PadLeft":
|
||||
if (exp.Arguments.Count == 1) return $"lpad({left}, {ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
return $"lpad({left}, {ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)}, {ExpressionLambdaToSql(exp.Arguments[1], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "PadRight":
|
||||
if (exp.Arguments.Count == 1) return $"rpad({left}, {ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
return $"rpad({left}, {ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)}, {ExpressionLambdaToSql(exp.Arguments[1], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Trim": return $"ltrim(rtrim({left}))";
|
||||
case "TrimStart": return $"ltrim({left})";
|
||||
case "TrimEnd": return $"rtrim({left})";
|
||||
case "Replace": return $"replace({left}, {ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)}, {ExpressionLambdaToSql(exp.Arguments[1], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "CompareTo": return $"strcmp({left}, {ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
}
|
||||
throw new Exception($"SqlServerExpression 未现实函数表达式 {exp} 解析");
|
||||
}
|
||||
|
||||
internal override string ExpressionLambdaToSqlCallMath(MethodCallExpression exp, List<SelectTableInfo> _tables, List<SelectColumnInfo> _selectColumnMap, SelectTableInfoType tbtype, bool isQuoteName) {
|
||||
switch (exp.Method.Name) {
|
||||
case "Abs": return $"abs({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Sign": return $"sign({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Floor": return $"floor({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Ceiling": return $"ceiling({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Round":
|
||||
if (exp.Arguments.Count > 1 && exp.Arguments[1].Type.FullName == "System.Int32") return $"round({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)}, {ExpressionLambdaToSql(exp.Arguments[1], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
return $"round({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Exp": return $"exp({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Log": return $"log({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Log10": return $"log10({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Pow": return $"power({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)}, {ExpressionLambdaToSql(exp.Arguments[1], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Sqrt": return $"sqrt({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Cos": return $"cos({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Sin": return $"sin({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Tan": return $"tan({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Acos": return $"acos({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Asin": return $"asin({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Atan": return $"atan({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Atan2": return $"atan2({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)}, {ExpressionLambdaToSql(exp.Arguments[1], _tables, _selectColumnMap, tbtype, isQuoteName)})";
|
||||
case "Truncate": return $"floor({ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName)}, 0)";
|
||||
}
|
||||
throw new Exception($"SqlServerExpression 未现实函数表达式 {exp} 解析");
|
||||
}
|
||||
|
||||
internal override string ExpressionLambdaToSqlCallDateTime(MethodCallExpression exp, List<SelectTableInfo> _tables, List<SelectColumnInfo> _selectColumnMap, SelectTableInfoType tbtype, bool isQuoteName) {
|
||||
var left = ExpressionLambdaToSql(exp.Object, _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
var args1 = ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
switch (exp.Method.Name) {
|
||||
case "Add": return $"dateadd(millisecond, datediff(millisecond, '1970-1-1', {args1}), {left})";
|
||||
case "AddDays": return $"dateadd(day, {args1}, {left})";
|
||||
case "AddHours": return $"dateadd(hour, {args1}, {left})";
|
||||
case "AddMilliseconds": return $"dateadd(millisecond, {args1}, {left})";
|
||||
case "AddMinutes": return $"dateadd(minute, {args1}, {left})";
|
||||
case "AddMonths": return $"dateadd(month, {args1}, {left})";
|
||||
case "AddSeconds": return $"dateadd(second, {args1}, {left})";
|
||||
case "AddTicks": return $"dateadd(millisecond, {args1} / 10000, {left})";
|
||||
case "AddYears": return $"dateadd(year, {args1}, {left})";
|
||||
case "Subtract": return $"dateadd(millisecond, -datediff(millisecond, '1970-1-1', {args1}), {left})";
|
||||
}
|
||||
throw new Exception($"SqlServerExpression 未现实函数表达式 {exp} 解析");
|
||||
}
|
||||
internal override string ExpressionLambdaToSqlCallTimeSpan(MethodCallExpression exp, List<SelectTableInfo> _tables, List<SelectColumnInfo> _selectColumnMap, SelectTableInfoType tbtype, bool isQuoteName) {
|
||||
var left = ExpressionLambdaToSql(exp.Object, _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
var args1 = ExpressionLambdaToSql(exp.Arguments[0], _tables, _selectColumnMap, tbtype, isQuoteName);
|
||||
switch (exp.Method.Name) {
|
||||
case "Add": return $"dateadd(millisecond, datediff(millisecond, '1970-1-1', {args1}), {left})";
|
||||
case "Subtract": return $"dateadd(millisecond, -datediff(millisecond, '1970-1-1', {args1}), {left})";
|
||||
}
|
||||
throw new Exception($"SqlServerExpression 未现实函数表达式 {exp} 解析");
|
||||
}
|
||||
}
|
||||
|
@ -45,5 +45,6 @@ namespace FreeSql.SqlServer {
|
||||
internal override string QuoteSqlName(string name) => $"[{name.TrimStart('[').TrimEnd(']').Replace(".", "].[")}]";
|
||||
internal override string QuoteParamterName(string name) => $"@{name}";
|
||||
internal override string IsNull(string sql, object value) => $"isnull({sql}, {value})";
|
||||
internal override string StringConcat(string left, string right, Type leftType, Type rightType) => $"{(leftType.FullName == "System.String" ? left : $"cast({left} as nvarchar)")} + {(rightType.FullName == "System.String" ? right : $"cast({right} as nvarchar)")}";
|
||||
}
|
||||
}
|
||||
|
Reference in New Issue
Block a user