Procházet zdrojové kódy

Corrected constant handling in sql condition formulae

frogsoftware před 10 měsíci
rodič
revize
c74054b84d
1 změnil soubory, kde provedl 60 přidání a 50 odebrání
  1. 60 50
      inabox.database.sqlite/SQLiteProvider.cs

+ 60 - 50
inabox.database.sqlite/SQLiteProvider.cs

@@ -1416,6 +1416,20 @@ public class SQLiteProvider : IProvider
         return value.ToString() ?? "";
 
     }
+    
+    internal static string EscapeValue(string? value, Type type)
+    {
+
+        if (type == typeof(string) || type.IsEnum || (type == typeof(Guid)))
+            return "\'" + $"{value?.Replace("\'", "\'\'")}" + "\'";
+        if (type == typeof(string[]))
+            return string.Format("hex({0})", BitConverter.ToString(Encoding.ASCII.GetBytes(value.ToString() ?? "")).Replace("-", ""));
+        if (type.GetInterface(nameof(IColumn)) != null)
+            return $"[{value}]";
+        return value.ToString() ?? "";
+
+    }
+    
     private static string GetFilterConstant(FilterConstant constant)
     {
         return constant switch
@@ -1782,9 +1796,12 @@ public class SQLiteProvider : IProvider
 
         var valuetype = intf.GenericTypeArguments[1];
         var defvalue = valuetype.GetDefault();
-
-        if (!fieldmap.ContainsKey(attribute.Left))
-            throw new Exception(string.Format("{0}.{1} -> {2} does not exist", columnname, attribute.GetType().Name, attribute.Left));
+        
+        var _left = fieldmap.TryGetValue(attribute.Left, out var _leftvalue)
+            ? _leftvalue
+            : EscapeValue(attribute.Left, valuetype);
+        
+        //throw new Exception(string.Format("{0}.{1} -> {2} does not exist", columnname, attribute.GetType().Name, attribute.Left));
 
         var condition = "";
         if (attribute.Condition == Condition.Equals)
@@ -1802,17 +1819,26 @@ public class SQLiteProvider : IProvider
         else
             throw new Exception(string.Format("{0}.{1} is not a valid condition", columnname, attribute.Calculator.GetType().Name));
 
-        if (!fieldmap.ContainsKey(attribute.Right))
-            throw new Exception(string.Format("{0}.{1} -> {2} does not exist", columnname, attribute.GetType().Name, attribute.Right));
-
-        if (!fieldmap.ContainsKey(attribute.True))
-            throw new Exception(string.Format("{0}.{1} -> {2} does not exist", columnname, attribute.GetType().Name, attribute.True));
+        //if (!fieldmap.ContainsKey(attribute.Right))
+        //    throw new Exception(string.Format("{0}.{1} -> {2} does not exist", columnname, attribute.GetType().Name, attribute.Right));
+        var _right = fieldmap.TryGetValue(attribute.Right, out var _rightvalue)
+            ? _rightvalue
+            : EscapeValue(attribute.Right, valuetype);
+        
+        //if (!fieldmap.ContainsKey(attribute.True))
+        //    throw new Exception(string.Format("{0}.{1} -> {2} does not exist", columnname, attribute.GetType().Name, attribute.True));
+        var _true = fieldmap.TryGetValue(attribute.True, out var _truevalue)
+            ? _truevalue
+            : EscapeValue(attribute.True, valuetype);
 
-        if (!fieldmap.ContainsKey(attribute.False))
-            throw new Exception(string.Format("{0}.{1} -> {2} does not exist", columnname, attribute.GetType().Name, attribute.False));
+        //if (!fieldmap.ContainsKey(attribute.False))
+        //    throw new Exception(string.Format("{0}.{1} -> {2} does not exist", columnname, attribute.GetType().Name, attribute.False));
+        var _false = fieldmap.TryGetValue(attribute.False, out var _falsevalue)
+            ? _falsevalue
+            : EscapeValue(attribute.False, valuetype);
 
-        return string.Format("CASE WHEN COALESCE({0},{1}) {2} {3} THEN {4} ELSE {5} END", fieldmap[attribute.Left], defvalue, condition,
-            fieldmap[attribute.Right], fieldmap[attribute.True], fieldmap[attribute.False]);
+        return string.Format("CASE WHEN COALESCE({0},{1}) {2} {3} THEN {4} ELSE {5} END", _left, defvalue, condition,
+            _right, _true, _false);
     }
 
     private string LoadComplexFormula(SQLiteCommand command, Type type, char prefix, Dictionary<string, string> fieldmap, List<Tuple<string, string, string, string>> tables, List<string> columns, IComplexFormulaNode node, bool useparams)
@@ -1892,7 +1918,7 @@ public class SQLiteProvider : IProvider
                 }
             case IComplexFormulaFieldNode field:
                 var col = Column.Create(type, field.GetField());
-                CheckColumn(columns, col.Property);
+                CheckColumn(type, columns, col.Property);
                 LoadFieldsAndTables(command, type, prefix, fieldmap, tables, columns, col, useparams);
                 return fieldmap[col.Name];
             case IComplexFormulaFormulaNode formula:
@@ -2093,7 +2119,7 @@ public class SQLiteProvider : IProvider
                             {
                                 if (CoreUtils.TryGetProperty(type,field,out var _))
                                 {
-                                    CheckColumn(columns, field);
+                                    CheckColumn(type, columns, field);
                                     LoadFieldsAndTables(command, type, prefix, fieldmap, tables, columns,
                                         Column.Create(type, field), useparams);
                                 }
@@ -2103,41 +2129,21 @@ public class SQLiteProvider : IProvider
                         else if(property.GetAttribute<ConditionAttribute>() is ConditionAttribute cnd)
                         {
                             var cndmap = new Dictionary<string, string>();
-                            // LogStart();
-                            CheckColumn(columns, cnd.Left);
-                            // LogStop("CheckColumn(Left)");
-
-                            // LogStart();
-                            CheckColumn(columns, cnd.Right);
-                            // LogStop("CheckColumn(Right)");
-
-                            // LogStart();
-                            CheckColumn(columns, cnd.True);
-                            // LogStop("CheckColumn(True)");
-
-                            // LogStart();
-                            CheckColumn(columns, cnd.False);
-                            // LogStop("CheckColumn(False)");
-
-                            //// LogStart();
-                            LoadFieldsAndTables(command, type, prefix, cndmap, tables, columns, Column.Create(type, cnd.Left), useparams);
-                            //// LogStop("LoadFieldsAndTables(Left)");
-
-                            //// LogStart();
-                            LoadFieldsAndTables(command, type, prefix, cndmap, tables, columns, Column.Create(type, cnd.Right), useparams);
-                            //// LogStop("LoadFieldsAndTables(Right)");
-
-                            //// LogStart();
-                            LoadFieldsAndTables(command, type, prefix, cndmap, tables, columns, Column.Create(type, cnd.True), useparams);
-                            //// LogStop("LoadFieldsAndTables(True)");
-
-                            //// LogStart();
-                            LoadFieldsAndTables(command, type, prefix, cndmap, tables, columns, Column.Create(type, cnd.False), useparams);
-                            //// LogStop("LoadFieldsAndTables(False)");
-
-                            // LogStart();
+                            
+                            if (CheckColumn(type, columns, cnd.Left))
+                                LoadFieldsAndTables(command, type, prefix, cndmap, tables, columns, Column.Create(type, cnd.Left), useparams);
+                                    
+                            if (CheckColumn(type, columns, cnd.Right))
+                                LoadFieldsAndTables(command, type, prefix, cndmap, tables, columns, Column.Create(type, cnd.Right), useparams);
+                            
+                            if (CheckColumn(type, columns, cnd.True))
+                                LoadFieldsAndTables(command, type, prefix, cndmap, tables, columns, Column.Create(type, cnd.True), useparams);
+                            
+                            if (CheckColumn(type, columns, cnd.False))
+                                LoadFieldsAndTables(command, type, prefix, cndmap, tables, columns, Column.Create(type, cnd.False), useparams);
+                            
                             fieldmap[baseCol.Name] = GetCondition(cnd, cndmap, baseCol.Name);
-                            // LogStop("GetCondition");
+
                         }
                         else
                         {
@@ -2312,10 +2318,14 @@ public class SQLiteProvider : IProvider
         }
     }
 
-    private static void CheckColumn(List<string> columns, string column)
+    private static bool CheckColumn(Type type, List<string> columns, string column)
     {
-        if (!columns.Contains(column))
+        if (CoreUtils.TryGetProperty(type, column, out _) && !columns.Contains(column))
+        {
             columns.Add(column);
+            return true;
+        }
+        return false;
     }
 
     public void AddFilterFields(IFilter? filter, List<string> fields)