public static Parameter Parse(WhereInfo whereInfo) { return(new Parameter() { Param = "@" + whereInfo.Column, Value = whereInfo.Value }); }
private WhereInfo GetFilledRandomWhereInfo(string OmitPropName) { WhereInfo whereInfo = new WhereInfo(); if (OmitPropName != "PropertyName") { whereInfo.PropertyName = GetRandomString("", 5); } if (OmitPropName != "PropertyType") { whereInfo.PropertyType = (PropertyTypeEnum)GetRandomEnumType(typeof(PropertyTypeEnum)); } if (OmitPropName != "WhereOperator") { whereInfo.WhereOperator = (WhereOperatorEnum)GetRandomEnumType(typeof(WhereOperatorEnum)); } if (OmitPropName != "Value") { whereInfo.Value = GetRandomString("", 5); } if (OmitPropName != "ValueInt") { whereInfo.ValueInt = GetRandomInt(-1, -1); } if (OmitPropName != "ValueDouble") { whereInfo.ValueDouble = GetRandomDouble(-1.0D, -1.0D); } if (OmitPropName != "ValueBool") { whereInfo.ValueBool = true; } if (OmitPropName != "ValueDateTime") { whereInfo.ValueDateTime = new DateTime(2005, 3, 6); } if (OmitPropName != "ValueEnumText") { whereInfo.ValueEnumText = GetRandomString("", 5); } //CSSPError: property [EnumType] and type [WhereInfo] is not implemented return(whereInfo); }
private void UpdateWhereInfo() { UnionSubQuery unionSubQuery = Builder.ActiveUnionSubQuery; StringBuilder stringBuilder = new StringBuilder(); SQLSubQuerySelectExpression unionSubQueryAst = unionSubQuery.ResultQueryAST; try { if (unionSubQueryAst.Where != null) { WhereInfo.DumpWhereInfo(stringBuilder, unionSubQueryAst.Where); } } finally { unionSubQueryAst.Dispose(); } tbWhere.Text = stringBuilder.ToString(); }
public WhereInfoTest() { whereInfo = new WhereInfo(); }
public ContentQueryBuilder SetWhereClause(String clause) { if (this.subscriptionGuid == null) throw new ApplicationException("The subscription guid must be set prior to calling this method"); if (!String.IsNullOrEmpty(clause)) { CmsContentTypeDao dao = new CmsContentTypeDao(); //Get the fields and their types for the content type CmsContentType type = dao.FindBySiteAndName(this.subscriptionGuid, this.contentType); IList<CmsContentTypeField> fields = dao.FindFieldsByContentTypeGuid(type.Guid); //Perform error checking and make sure that there's not more than one paren pair int leftParens = clause.Count(f => f == '('); int rightParens = clause.Count(f => f == ')'); if (leftParens > 1) throw new ArgumentException("The where clause '" + clause + "' is not currently supported. Only a single set of parens may be present"); if (leftParens != rightParens) throw new ArgumentException("The where clause '" + clause + "' is not valid. Parentheses mitmatch. Expected " + leftParens + " but found " + rightParens); //Make sure there are not any conditional statements if (ConditionalMatch.IsMatch(clause)) throw new ArgumentException("The where clause '" + clause + "' is not valid: GooeyCms does not currently support conditional where clauses"); //Parse the actual string clause = clause.Replace("'", ""); clause = clause.Replace("(", ""); clause = clause.Replace(")", ""); Match match = StatementMatch.Match(clause); if (!match.Success) throw new ArgumentException("The where clause '" + clause + "' is not in a valid format. Format should be: field-name [<,>,=] value. Greater-than and Less-than are only supported on datetime field types."); String fieldname = match.Groups["fieldname"].Value; String condition = match.Groups["condition"].Value; String value = match.Groups["value"].Value; //Make sure that this fieldname is valid for the content type CmsContentTypeField field = null; try { field = fields.Single(f => f.SystemName.Equals(fieldname)); } catch (InvalidOperationException e) { StringBuilder builder = new StringBuilder(); foreach (CmsContentTypeField temp in fields) { builder.Append(temp.SystemName + "|"); } throw new ArgumentException("The where clause '" + clause + "' is not valid: The content type '" + type.Name + "' does not contain the field '" + fieldname + "'. Available fields:" + builder.ToString()); } WhereInfo whereInfo = new WhereInfo(); whereInfo.Value1 = value; whereInfo.Field = field; whereInfo.ParseConditional(condition); this.whereClauses.Add(whereInfo); } return this; }
static void FKScanChildren(Parse parse, SrcList src, Table table, Index index, FKey fkey, int[] cols, int regDataId, int incr) { Context ctx = parse.Ctx; // Database handle Vdbe v = parse.GetVdbe(); Expr where_ = null; // WHERE clause to scan with Debug.Assert(index == null || index.Table == table); int fkIfZero = 0; // Address of OP_FkIfZero if (incr < 0) { fkIfZero = v.AddOp2(OP.FkIfZero, fkey.IsDeferred, 0); } // Create an Expr object representing an SQL expression like: // // <parent-key1> = <child-key1> AND <parent-key2> = <child-key2> ... // // The collation sequence used for the comparison should be that of the parent key columns. The affinity of the parent key column should // be applied to each child key value before the comparison takes place. for (int i = 0; i < fkey.Cols.length; i++) { int col; // Index of column in child table Expr left = Expr.Expr(ctx, TK.REGISTER, null); // Value from parent table row if (left != null) { // Set the collation sequence and affinity of the LHS of each TK_EQ expression to the parent key column defaults. if (index != null) { col = index.Columns[i]; Column colObj = table.Cols[col]; if (table.PKey == col) { col = -1; } left.TableId = regDataId + col + 1; left.Aff = colObj.Affinity; string collName = colObj.Coll; if (collName == null) { collName = ctx.DefaultColl.Name; } left = Expr.AddCollateString(parse, left, collName); } else { left.TableId = regDataId; left.Aff = AFF.INTEGER; } } col = (cols != null ? cols[i] : fkey.Cols[0].From); Debug.Assert(col >= 0); string colName = fkey.From.Cols[col].Name; // Name of column in child table Expr right = Expr.Expr(ctx, TK.ID, colName); // Column ref to child table Expr eq = Expr.PExpr(parse, TK.EQ, left, right, 0); // Expression (pLeft = pRight) where_ = Expr.And(ctx, where_, eq); } // If the child table is the same as the parent table, and this scan is taking place as part of a DELETE operation (operation D.2), omit the // row being deleted from the scan by adding ($rowid != rowid) to the WHERE clause, where $rowid is the rowid of the row being deleted. if (table == fkey.From && incr > 0) { Expr left = Expr.Expr(ctx, TK.REGISTER, null); // Value from parent table row Expr right = Expr.Expr(ctx, TK.COLUMN, null); // Column ref to child table if (left != null && right != null) { left.TableId = regDataId; left.Aff = AFF.INTEGER; right.TableId = src.Ids[0].Cursor; right.ColumnId = -1; } Expr eq = Expr.PExpr(parse, TK.NE, left, right, 0); // Expression (pLeft = pRight) where_ = Expr.And(ctx, where_, eq); } // Resolve the references in the WHERE clause. NameContext nameContext; // Context used to resolve WHERE clause nameContext = new NameContext(); // memset( &sNameContext, 0, sizeof( NameContext ) ); nameContext.SrcList = src; nameContext.Parse = parse; ResolveExprNames(nameContext, ref where_); // Create VDBE to loop through the entries in src that match the WHERE clause. If the constraint is not deferred, throw an exception for // each row found. Otherwise, for deferred constraints, increment the deferred constraint counter by incr for each row selected. ExprList dummy = null; WhereInfo whereInfo = Where.Begin(parse, src, where_, ref dummy, 0); // Context used by sqlite3WhereXXX() if (incr > 0 && !fkey.IsDeferred) { E.Parse_Toplevel(parse).MayAbort = true; } v.AddOp2(OP.FkCounter, fkey.IsDeferred, incr); if (whereInfo != null) { Where.End(whereInfo); } // Clean up the WHERE clause constructed above. Expr.Delete(ctx, ref where_); if (fkIfZero != 0) { v.JumpHere(fkIfZero); } }
/// <summary> /// searchRequest 生成 /// </summary> /// <param name="where"></param> /// <returns></returns> public static Func <SearchDescriptor <Student>, ISearchRequest> CreateSearchRequest(WhereInfo where) { //querys var mustQuerys = new List <Func <QueryContainerDescriptor <Student>, QueryContainer> >(); if (where.venId > 0) { mustQuerys.Add(t => t.Term(f => f.Id, where.venId)); } //filters var mustFilters = new List <Func <QueryContainerDescriptor <Student>, QueryContainer> >(); if (!string.IsNullOrEmpty(where.venName)) { mustFilters.Add(t => t.MatchPhrase(f => f.Field(fd => fd.Description).Query(where.venName))); } Func <SearchDescriptor <Student>, ISearchRequest> searchRequest = r => r.Query(q => q.Bool(b => b.Must(mustQuerys) .Filter(f => f.Bool(fb => fb.Must(mustFilters)) ) ) ); return(searchRequest); }
private IEnumerable <ValidationResult> Validate(ValidationContext validationContext, ActionDBTypeEnum actionDBType) { string retStr = ""; Enums enums = new Enums(LanguageRequest); WhereInfo whereInfo = validationContext.ObjectInstance as WhereInfo; whereInfo.HasErrors = false; if (string.IsNullOrWhiteSpace(whereInfo.PropertyName)) { whereInfo.HasErrors = true; yield return(new ValidationResult(string.Format(CSSPServicesRes._IsRequired, "PropertyName"), new[] { "PropertyName" })); } if (!string.IsNullOrWhiteSpace(whereInfo.PropertyName) && whereInfo.PropertyName.Length > 100) { whereInfo.HasErrors = true; yield return(new ValidationResult(string.Format(CSSPServicesRes._MaxLengthIs_, "PropertyName", "100"), new[] { "PropertyName" })); } retStr = enums.EnumTypeOK(typeof(PropertyTypeEnum), (int?)whereInfo.PropertyType); if (!string.IsNullOrWhiteSpace(retStr)) { whereInfo.HasErrors = true; yield return(new ValidationResult(string.Format(CSSPServicesRes._IsRequired, "PropertyType"), new[] { "PropertyType" })); } retStr = enums.EnumTypeOK(typeof(WhereOperatorEnum), (int?)whereInfo.WhereOperator); if (!string.IsNullOrWhiteSpace(retStr)) { whereInfo.HasErrors = true; yield return(new ValidationResult(string.Format(CSSPServicesRes._IsRequired, "WhereOperator"), new[] { "WhereOperator" })); } if (string.IsNullOrWhiteSpace(whereInfo.Value)) { whereInfo.HasErrors = true; yield return(new ValidationResult(string.Format(CSSPServicesRes._IsRequired, "Value"), new[] { "Value" })); } if (!string.IsNullOrWhiteSpace(whereInfo.Value) && whereInfo.Value.Length > 100) { whereInfo.HasErrors = true; yield return(new ValidationResult(string.Format(CSSPServicesRes._MaxLengthIs_, "Value", "100"), new[] { "Value" })); } if (whereInfo.ValueInt < -1 || whereInfo.ValueInt > -1) { whereInfo.HasErrors = true; yield return(new ValidationResult(string.Format(CSSPServicesRes._ValueShouldBeBetween_And_, "ValueInt", "-1", "-1"), new[] { "ValueInt" })); } if (whereInfo.ValueDouble < -1 || whereInfo.ValueDouble > -1) { whereInfo.HasErrors = true; yield return(new ValidationResult(string.Format(CSSPServicesRes._ValueShouldBeBetween_And_, "ValueDouble", "-1", "-1"), new[] { "ValueDouble" })); } if (whereInfo.ValueDateTime.Year == 1) { whereInfo.HasErrors = true; yield return(new ValidationResult(string.Format(CSSPServicesRes._IsRequired, "ValueDateTime"), new[] { "ValueDateTime" })); } else { if (whereInfo.ValueDateTime.Year < 1900) { whereInfo.HasErrors = true; yield return(new ValidationResult(string.Format(CSSPServicesRes._YearShouldBeBiggerThan_, "ValueDateTime", "1900"), new[] { "ValueDateTime" })); } } if (string.IsNullOrWhiteSpace(whereInfo.ValueEnumText)) { whereInfo.HasErrors = true; yield return(new ValidationResult(string.Format(CSSPServicesRes._IsRequired, "ValueEnumText"), new[] { "ValueEnumText" })); } if (!string.IsNullOrWhiteSpace(whereInfo.ValueEnumText) && whereInfo.ValueEnumText.Length > 100) { whereInfo.HasErrors = true; yield return(new ValidationResult(string.Format(CSSPServicesRes._MaxLengthIs_, "ValueEnumText", "100"), new[] { "ValueEnumText" })); } //CSSPError: Type not implemented [EnumType] of type [Type] //CSSPError: Type not implemented [EnumType] of type [Type] retStr = ""; // added to stop compiling CSSPError if (retStr != "") // will never be true { whereInfo.HasErrors = true; yield return(new ValidationResult("AAA", new[] { "AAA" })); } }
public static object GetEnumCasting(WhereInfo whereInfo) { switch (whereInfo.EnumType.Name) { case "IEnums": return((IEnums)whereInfo.ValueInt); case "ActionDBTypeEnum": return((ActionDBTypeEnum)whereInfo.ValueInt); case "AddContactTypeEnum": return((AddContactTypeEnum)whereInfo.ValueInt); case "EntityQueryTypeEnum": return((EntityQueryTypeEnum)whereInfo.ValueInt); case "PolSourceObsInfoTypeEnum": return((PolSourceObsInfoTypeEnum)whereInfo.ValueInt); case "AddressTypeEnum": return((AddressTypeEnum)whereInfo.ValueInt); case "AerationTypeEnum": return((AerationTypeEnum)whereInfo.ValueInt); case "AlarmSystemTypeEnum": return((AlarmSystemTypeEnum)whereInfo.ValueInt); case "AnalysisCalculationTypeEnum": return((AnalysisCalculationTypeEnum)whereInfo.ValueInt); case "AnalysisReportExportCommandEnum": return((AnalysisReportExportCommandEnum)whereInfo.ValueInt); case "AnalyzeMethodEnum": return((AnalyzeMethodEnum)whereInfo.ValueInt); case "AppTaskCommandEnum": return((AppTaskCommandEnum)whereInfo.ValueInt); case "AppTaskStatusEnum": return((AppTaskStatusEnum)whereInfo.ValueInt); case "BeaufortScaleEnum": return((BeaufortScaleEnum)whereInfo.ValueInt); case "BoxModelResultTypeEnum": return((BoxModelResultTypeEnum)whereInfo.ValueInt); case "CanOverflowTypeEnum": return((CanOverflowTypeEnum)whereInfo.ValueInt); case "ClassificationTypeEnum": return((ClassificationTypeEnum)whereInfo.ValueInt); case "CollectionSystemTypeEnum": return((CollectionSystemTypeEnum)whereInfo.ValueInt); case "ContactTitleEnum": return((ContactTitleEnum)whereInfo.ValueInt); case "CSSPWQInputSheetTypeEnum": return((CSSPWQInputSheetTypeEnum)whereInfo.ValueInt); case "CSSPWQInputTypeEnum": return((CSSPWQInputTypeEnum)whereInfo.ValueInt); case "DailyOrHourlyDataEnum": return((DailyOrHourlyDataEnum)whereInfo.ValueInt); case "DisinfectionTypeEnum": return((DisinfectionTypeEnum)whereInfo.ValueInt); case "DrogueTypeEnum": return((DrogueTypeEnum)whereInfo.ValueInt); case "EmailTypeEnum": return((EmailTypeEnum)whereInfo.ValueInt); case "ExcelExportShowDataTypeEnum": return((ExcelExportShowDataTypeEnum)whereInfo.ValueInt); case "FacilityTypeEnum": return((FacilityTypeEnum)whereInfo.ValueInt); case "FilePurposeEnum": return((FilePurposeEnum)whereInfo.ValueInt); case "FileStatusEnum": return((FileStatusEnum)whereInfo.ValueInt); case "FileTypeEnum": return((FileTypeEnum)whereInfo.ValueInt); case "InfrastructureTypeEnum": return((InfrastructureTypeEnum)whereInfo.ValueInt); case "KMZActionEnum": return((KMZActionEnum)whereInfo.ValueInt); case "LaboratoryEnum": return((LaboratoryEnum)whereInfo.ValueInt); case "LabSheetStatusEnum": return((LabSheetStatusEnum)whereInfo.ValueInt); case "LabSheetTypeEnum": return((LabSheetTypeEnum)whereInfo.ValueInt); case "LanguageEnum": return((LanguageEnum)whereInfo.ValueInt); case "LogCommandEnum": return((LogCommandEnum)whereInfo.ValueInt); case "MapInfoDrawTypeEnum": return((MapInfoDrawTypeEnum)whereInfo.ValueInt); case "MikeBoundaryConditionLevelOrVelocityEnum": return((MikeBoundaryConditionLevelOrVelocityEnum)whereInfo.ValueInt); case "MikeScenarioSpecialResultKMLTypeEnum": return((MikeScenarioSpecialResultKMLTypeEnum)whereInfo.ValueInt); case "MWQMSiteLatestClassificationEnum": return((MWQMSiteLatestClassificationEnum)whereInfo.ValueInt); case "PolSourceInactiveReasonEnum": return((PolSourceInactiveReasonEnum)whereInfo.ValueInt); case "PolSourceIssueRiskEnum": return((PolSourceIssueRiskEnum)whereInfo.ValueInt); case "PositionEnum": return((PositionEnum)whereInfo.ValueInt); case "PreliminaryTreatmentTypeEnum": return((PreliminaryTreatmentTypeEnum)whereInfo.ValueInt); case "PrimaryTreatmentTypeEnum": return((PrimaryTreatmentTypeEnum)whereInfo.ValueInt); case "PropertyTypeEnum": return((PropertyTypeEnum)whereInfo.ValueInt); case "ReportConditionEnum": return((ReportConditionEnum)whereInfo.ValueInt); case "ReportFieldTypeEnum": return((ReportFieldTypeEnum)whereInfo.ValueInt); case "ReportFileTypeEnum": return((ReportFileTypeEnum)whereInfo.ValueInt); case "ReportFormatingDateEnum": return((ReportFormatingDateEnum)whereInfo.ValueInt); case "ReportFormatingNumberEnum": return((ReportFormatingNumberEnum)whereInfo.ValueInt); case "ReportGenerateObjectsKeywordEnum": return((ReportGenerateObjectsKeywordEnum)whereInfo.ValueInt); case "ReportSortingEnum": return((ReportSortingEnum)whereInfo.ValueInt); case "ReportTreeNodeSubTypeEnum": return((ReportTreeNodeSubTypeEnum)whereInfo.ValueInt); case "ReportTreeNodeTypeEnum": return((ReportTreeNodeTypeEnum)whereInfo.ValueInt); case "SameDayNextDayEnum": return((SameDayNextDayEnum)whereInfo.ValueInt); case "SampleMatrixEnum": return((SampleMatrixEnum)whereInfo.ValueInt); case "SampleStatusEnum": return((SampleStatusEnum)whereInfo.ValueInt); case "SampleTypeEnum": return((SampleTypeEnum)whereInfo.ValueInt); case "SamplingPlanTypeEnum": return((SamplingPlanTypeEnum)whereInfo.ValueInt); case "ScenarioStatusEnum": return((ScenarioStatusEnum)whereInfo.ValueInt); case "SearchTagEnum": return((SearchTagEnum)whereInfo.ValueInt); case "SecondaryTreatmentTypeEnum": return((SecondaryTreatmentTypeEnum)whereInfo.ValueInt); case "SiteTypeEnum": return((SiteTypeEnum)whereInfo.ValueInt); case "SpecialTableTypeEnum": return((SpecialTableTypeEnum)whereInfo.ValueInt); case "StorageDataTypeEnum": return((StorageDataTypeEnum)whereInfo.ValueInt); case "StreetTypeEnum": return((StreetTypeEnum)whereInfo.ValueInt); case "TelTypeEnum": return((TelTypeEnum)whereInfo.ValueInt); case "TertiaryTreatmentTypeEnum": return((TertiaryTreatmentTypeEnum)whereInfo.ValueInt); case "TideDataTypeEnum": return((TideDataTypeEnum)whereInfo.ValueInt); case "TideTextEnum": return((TideTextEnum)whereInfo.ValueInt); case "TranslationStatusEnum": return((TranslationStatusEnum)whereInfo.ValueInt); case "TreatmentTypeEnum": return((TreatmentTypeEnum)whereInfo.ValueInt); case "TVAuthEnum": return((TVAuthEnum)whereInfo.ValueInt); case "TVTypeEnum": return((TVTypeEnum)whereInfo.ValueInt); case "ValveTypeEnum": return((ValveTypeEnum)whereInfo.ValueInt); case "WebTideDataSetEnum": return((WebTideDataSetEnum)whereInfo.ValueInt); case "PolSourceObsInfoEnum": return((PolSourceObsInfoEnum)whereInfo.ValueInt); default: return(null); } }
public static void sqlite3Update(Parse parse, SrcList tabList, ExprList changes, Expr where_, OE onError) { int i, j; // Loop counters AuthContext sContext = new AuthContext(); // The authorization context Context ctx = parse.Ctx; // The database structure if (parse.Errs != 0 || ctx.MallocFailed) { goto update_cleanup; } Debug.Assert(tabList.Srcs == 1); // Locate the table which we want to update. Table table = sqlite3SrcListLookup(parse, tabList); // The table to be updated if (table == null) { goto update_cleanup; } int db = sqlite3SchemaToIndex(ctx, table.Schema); // Database containing the table being updated // Figure out if we have any triggers and if the table being updated is a view. #if !OMIT_TRIGGER int tmask = 0; // Mask of TRIGGER_BEFORE|TRIGGER_AFTER Trigger trigger = sqlite3TriggersExist(parse, table, TK.UPDATE, changes, out tmask); // List of triggers on pTab, if required #if OMIT_VIEW const bool isView = false; #else bool isView = (table.Select != null); // True when updating a view (INSTEAD OF trigger) #endif Debug.Assert(trigger != null || tmask == 0); #else const Trigger trigger = null; const int tmask = 0; const bool isView = false; #endif if (sqlite3ViewGetColumnNames(parse, table) != 0 || sqlite3IsReadOnly(parse, table, tmask)) { goto update_cleanup; } int[] xrefs = new int[table.Cols.length]; // xrefs[i] is the index in pChanges->a[] of the an expression for the i-th column of the table. xrefs[i]==-1 if the i-th column is not changed. if (xrefs == null) { goto update_cleanup; } for (i = 0; i < table.Cols.length; i++) { xrefs[i] = -1; } // Allocate a cursors for the main database table and for all indices. The index cursors might not be used, but if they are used they // need to occur right after the database cursor. So go ahead and allocate enough space, just in case. int curId; // VDBE Cursor number of pTab tabList.Ids[0].Cursor = curId = parse.Tabs++; Index idx; // For looping over indices for (idx = table.Index; idx != null; idx = idx.Next) { parse.Tabs++; } // Initialize the name-context NameContext sNC = new NameContext(); // The name-context to resolve expressions in sNC.Parse = parse; sNC.SrcList = tabList; // Resolve the column names in all the expressions of the of the UPDATE statement. Also find the column index // for each column to be updated in the pChanges array. For each column to be updated, make sure we have authorization to change that column. bool chngRowid = false; // True if the record number is being changed Expr rowidExpr = null; // Expression defining the new record number for (i = 0; i < changes.Exprs; i++) { if (sqlite3ResolveExprNames(sNC, ref changes.Ids[i].Expr) != 0) { goto update_cleanup; } for (j = 0; j < table.Cols.length; j++) { if (string.Equals(table.Cols[j].Name, changes.Ids[i].Name, StringComparison.OrdinalIgnoreCase)) { if (j == table.PKey) { chngRowid = true; rowidExpr = changes.Ids[i].Expr; } xrefs[j] = i; break; } } if (j >= table.Cols.length) { if (Expr::IsRowid(changes.Ids[i].Name)) { chngRowid = true; rowidExpr = changes.Ids[i].Expr; } else { parse.ErrorMsg("no such column: %s", changes.Ids[i].Name); parse.CheckSchema = 1; goto update_cleanup; } } #if !OMIT_AUTHORIZATION { ARC rc = Auth.Check(parse, AUTH.UPDATE, table.Name, table.Cols[j].Name, ctx.DBs[db].Name); if (rc == ARC.DENY) { goto update_cleanup; } else if (rc == ARC.IGNORE) { xrefs[j] = -1; } } #endif } bool hasFK = sqlite3FkRequired(parse, table, xrefs, chngRowid ? 1 : 0); // True if foreign key processing is required // Allocate memory for the array aRegIdx[]. There is one entry in the array for each index associated with table being updated. Fill in // the value with a register number for indices that are to be used and with zero for unused indices. int idxLength; // Number of indices that need updating for (idxLength = 0, idx = table.Index; idx != null; idx = idx.Next, idxLength++) { ; } int[] regIdxs = null; // One register assigned to each index to be updated if (idxLength > 0) { regIdxs = new int[idxLength]; if (regIdxs == null) { goto update_cleanup; } } for (j = 0, idx = table.Index; idx != null; idx = idx.Next, j++) { int regId; if (hasFK || chngRowid) { regId = ++parse.Mems; } else { regId = 0; for (i = 0; i < idx.Columns.length; i++) { if (xrefs[idx.Columns[i]] >= 0) { regId = ++parse.Mems; break; } } } regIdxs[j] = regId; } // Begin generating code. Vdbe v = parse.GetVdbe(); // The virtual database engine if (v == null) { goto update_cleanup; } if (parse.Nested == 0) { v.CountChanges(); } parse.BeginWriteOperation(1, db); #if !OMIT_VIRTUALTABLE // Virtual tables must be handled separately if (IsVirtual(table)) { UpdateVirtualTable(parse, tabList, table, changes, rowidExpr, xrefs, where_, onError); where_ = null; tabList = null; goto update_cleanup; } #endif // Register Allocations int regRowCount = 0; // A count of rows changed int regOldRowid; // The old rowid int regNewRowid; // The new rowid int regNew; int regOld = 0; int regRowSet = 0; // Rowset of rows to be updated // Allocate required registers. regOldRowid = regNewRowid = ++parse.Mems; if (trigger != null || hasFK) { regOld = parse.Mems + 1; parse.Mems += table.Cols.length; } if (chngRowid || trigger != null || hasFK) { regNewRowid = ++parse.Mems; } regNew = parse.Mems + 1; parse.Mems += table.Cols.length; // Start the view context. if (isView) { Auth.ContextPush(parse, sContext, table.Name); } // If we are trying to update a view, realize that view into a ephemeral table. #if !OMIT_VIEW && !OMIT_TRIGGER if (isView) { sqlite3MaterializeView(parse, table, where_, curId); } #endif // Resolve the column names in all the expressions in the WHERE clause. if (sqlite3ResolveExprNames(sNC, ref where_) != 0) { goto update_cleanup; } // Begin the database scan v.AddOp2(OP.Null, 0, regOldRowid); ExprList dummy = null; WhereInfo winfo = Where.Begin(parse, tabList, where_, ref dummy, WHERE.ONEPASS_DESIRED); // Information about the WHERE clause if (winfo == null) { goto update_cleanup; } bool okOnePass = winfo.OkOnePass; // True for one-pass algorithm without the FIFO // Remember the rowid of every item to be updated. v.AddOp2(OP.Rowid, curId, regOldRowid); if (!okOnePass) { v.AddOp2(OP.RowSetAdd, regRowSet, regOldRowid); } // End the database scan loop. Where.End(winfo); // Initialize the count of updated rows if ((ctx.Flags & Context.FLAG.CountRows) != 0 && parse.TriggerTab == null) { regRowCount = ++parse.Mems; v.AddOp2(OP.Integer, 0, regRowCount); } bool openAll = false; // True if all indices need to be opened if (!isView) { // Open every index that needs updating. Note that if any index could potentially invoke a REPLACE conflict resolution // action, then we need to open all indices because we might need to be deleting some records. if (!okOnePass) { sqlite3OpenTable(parse, curId, db, table, OP.OpenWrite); } if (onError == OE.Replace) { openAll = true; } else { openAll = false; for (idx = table.Index; idx != null; idx = idx.Next) { if (idx.OnError == OE.Replace) { openAll = true; break; } } } for (i = 0, idx = table.Index; idx != null; idx = idx.Next, i++) { if (openAll || regIdxs[i] > 0) { KeyInfo key = sqlite3IndexKeyinfo(parse, idx); v.AddOp4(OP.OpenWrite, curId + i + 1, idx.Id, db, key, Vdbe.P4T.KEYINFO_HANDOFF); Debug.Assert(parse.Tabs > curId + i + 1); } } } // Top of the update loop int addr = 0; // VDBE instruction address of the start of the loop if (okOnePass) { int a1 = v.AddOp1(OP.NotNull, regOldRowid); addr = v.AddOp0(OP.Goto); v.JumpHere(a1); } else { addr = v.AddOp3(OP.RowSetRead, regRowSet, 0, regOldRowid); } // Make cursor iCur point to the record that is being updated. If this record does not exist for some reason (deleted by a trigger, // for example, then jump to the next iteration of the RowSet loop. v.AddOp3(OP.NotExists, curId, addr, regOldRowid); // If the record number will change, set register regNewRowid to contain the new value. If the record number is not being modified, // then regNewRowid is the same register as regOldRowid, which is already populated. Debug.Assert(chngRowid || trigger != null || hasFK || regOldRowid == regNewRowid); if (chngRowid) { Expr.Code(parse, rowidExpr, regNewRowid); v.AddOp1(OP.MustBeInt, regNewRowid); } // If there are triggers on this table, populate an array of registers with the required old.* column data. if (hasFK || trigger != null) { uint oldmask = (hasFK ? sqlite3FkOldmask(parse, table) : 0); oldmask |= sqlite3TriggerColmask(parse, trigger, changes, 0, TRIGGER_BEFORE | TRIGGER_AFTER, table, onError); for (i = 0; i < table.Cols.length; i++) { if (xrefs[i] < 0 || oldmask == 0xffffffff || (i < 32 && 0 != (oldmask & (1 << i)))) { Expr.CodeGetColumnOfTable(v, table, curId, i, regOld + i); } else { v.AddOp2(OP.Null, 0, regOld + i); } } if (!chngRowid) { v.AddOp2(OP.Copy, regOldRowid, regNewRowid); } } // Populate the array of registers beginning at regNew with the new row data. This array is used to check constaints, create the new // table and index records, and as the values for any new.* references made by triggers. // // If there are one or more BEFORE triggers, then do not populate the registers associated with columns that are (a) not modified by // this UPDATE statement and (b) not accessed by new.* references. The values for registers not modified by the UPDATE must be reloaded from // the database after the BEFORE triggers are fired anyway (as the trigger may have modified them). So not loading those that are not going to // be used eliminates some redundant opcodes. int newmask = (int)sqlite3TriggerColmask(parse, trigger, changes, 1, TRIGGER_BEFORE, table, onError); // Mask of NEW.* columns accessed by BEFORE triggers for (i = 0; i < table.Cols.length; i++) { if (i == table.PKey) { //v.AddOp2(OP.Null, 0, regNew + i); } else { j = xrefs[i]; if (j >= 0) { Expr.Code(parse, changes.Ids[j].Expr, regNew + i); } else if ((tmask & TRIGGER_BEFORE) == 0 || i > 31 || (newmask & (1 << i)) != 0) { // This branch loads the value of a column that will not be changed into a register. This is done if there are no BEFORE triggers, or // if there are one or more BEFORE triggers that use this value via a new.* reference in a trigger program. C.ASSERTCOVERAGE(i == 31); C.ASSERTCOVERAGE(i == 32); v.AddOp3(OP.Column, curId, i, regNew + i); v.ColumnDefault(table, i, regNew + i); } } } // Fire any BEFORE UPDATE triggers. This happens before constraints are verified. One could argue that this is wrong. if ((tmask & TRIGGER_BEFORE) != 0) { v.AddOp2(OP.Affinity, regNew, table.Cols.length); sqlite3TableAffinityStr(v, table); sqlite3CodeRowTrigger(parse, trigger, TK.UPDATE, changes, TRIGGER_BEFORE, table, regOldRowid, onError, addr); // The row-trigger may have deleted the row being updated. In this case, jump to the next row. No updates or AFTER triggers are // required. This behavior - what happens when the row being updated is deleted or renamed by a BEFORE trigger - is left undefined in the documentation. v.AddOp3(OP.NotExists, curId, addr, regOldRowid); // If it did not delete it, the row-trigger may still have modified some of the columns of the row being updated. Load the values for // all columns not modified by the update statement into their registers in case this has happened. for (i = 0; i < table.Cols.length; i++) { if (xrefs[i] < 0 && i != table.PKey) { v.AddOp3(OP.Column, curId, i, regNew + i); v.ColumnDefault(table, i, regNew + i); } } } if (!isView) { // Do constraint checks. int dummy2; sqlite3GenerateConstraintChecks(parse, table, curId, regNewRowid, regIdxs, (chngRowid ? regOldRowid : 0), true, onError, addr, out dummy2); // Do FK constraint checks. if (hasFK) { sqlite3FkCheck(parse, table, regOldRowid, 0); } // Delete the index entries associated with the current record. int j1 = v.AddOp3(OP.NotExists, curId, 0, regOldRowid); // Address of jump instruction sqlite3GenerateRowIndexDelete(parse, table, curId, regIdxs); // If changing the record number, delete the old record. if (hasFK || chngRowid) { v.AddOp2(OP.Delete, curId, 0); } v.JumpHere(j1); if (hasFK) { sqlite3FkCheck(parse, table, 0, regNewRowid); } // Insert the new index entries and the new record. sqlite3CompleteInsertion(parse, table, curId, regNewRowid, regIdxs, true, false, false); // Do any ON CASCADE, SET NULL or SET DEFAULT operations required to handle rows (possibly in other tables) that refer via a foreign key // to the row just updated. if (hasFK) { sqlite3FkActions(parse, table, changes, regOldRowid); } } // Increment the row counter if ((ctx.Flags & Context.FLAG.CountRows) != 0 && parse.TriggerTab == null) { v.AddOp2(OP.AddImm, regRowCount, 1); } sqlite3CodeRowTrigger(parse, trigger, TK.UPDATE, changes, TRIGGER_AFTER, table, regOldRowid, onError, addr); // Repeat the above with the next record to be updated, until all record selected by the WHERE clause have been updated. v.AddOp2(OP.Goto, 0, addr); v.JumpHere(addr); // Close all tables Debug.Assert(regIdxs != null); for (i = 0, idx = table.Index; idx != null; idx = idx.Next, i++) { if (openAll || regIdxs[i] > 0) { v.AddOp2(OP.Close, curId + i + 1, 0); } } v.AddOp2(OP.Close, curId, 0); // Update the sqlite_sequence table by storing the content of the maximum rowid counter values recorded while inserting into // autoincrement tables. if (parse.Nested == 0 && parse.TriggerTab == null) { sqlite3AutoincrementEnd(parse); } // Return the number of rows that were changed. If this routine is generating code because of a call to sqlite3NestedParse(), do not // invoke the callback function. if ((ctx.Flags & Context.FLAG.CountRows) != 0 && parse.TriggerTab == null && parse.Nested == 0) { v.AddOp2(OP.ResultRow, regRowCount, 1); v.SetNumCols(1); v.SetColName(0, COLNAME_NAME, "rows updated", SQLITE_STATIC); } update_cleanup: #if !OMIT_AUTHORIZATION Auth.ContextPop(sContext); #endif C._tagfree(ctx, ref regIdxs); C._tagfree(ctx, ref xrefs); SrcList.Delete(ctx, ref tabList); ExprList.Delete(ctx, ref changes); Expr.Delete(ctx, ref where_); return; }
public static void DeleteFrom(Parse parse, SrcList tabList, Expr where_) { AuthContext sContext = new AuthContext(); // Authorization context Context ctx = parse.Ctx; // Main database structure if (parse.Errs != 0 || ctx.MallocFailed) goto delete_from_cleanup; Debug.Assert(tabList.Srcs == 1); // Locate the table which we want to delete. This table has to be put in an SrcList structure because some of the subroutines we // will be calling are designed to work with multiple tables and expect an SrcList* parameter instead of just a Table* parameter. Table table = SrcList.Lookup(parse, tabList); // The table from which records will be deleted if (table == null) goto delete_from_cleanup; // Figure out if we have any triggers and if the table being deleted from is a view #if !OMIT_TRIGGER int dummy; Trigger trigger = Triggers.Exist(parse, table, TK.DELETE, null, out dummy); // List of table triggers, if required #if OMIT_VIEW const bool isView = false; #else bool isView = (table.Select != null); // True if attempting to delete from a view #endif #else const Trigger trigger = null; bool isView = false; #endif // If pTab is really a view, make sure it has been initialized. if (sqlite3ViewGetColumnNames(parse, table) != null || IsReadOnly(parse, table, (trigger != null))) goto delete_from_cleanup; int db = sqlite3SchemaToIndex(ctx, table.Schema); // Database number Debug.Assert(db < ctx.DBs.length); string dbName = ctx.DBs[db].Name; // Name of database holding pTab ARC rcauth = Auth.Check(parse, AUTH.DELETE, table.Name, 0, dbName); // Value returned by authorization callback Debug.Assert(rcauth == ARC.OK || rcauth == ARC.DENY || rcauth == ARC.IGNORE); if (rcauth == ARC.DENY) goto delete_from_cleanup; Debug.Assert(!isView || trigger != null); // Assign cursor number to the table and all its indices. Debug.Assert(tabList.Srcs == 1); int curId = tabList.Ids[0].Cursor = parse.Tabs++; // VDBE VdbeCursor number for pTab Index idx; // For looping over indices of the table for (idx = table.Index; idx != null; idx = idx.Next) parse.Tabs++; // Start the view context if (isView) Auth.ContextPush(parse, sContext, table.Name); // Begin generating code. Vdbe v = parse.GetVdbe(); // The virtual database engine if (v == null) goto delete_from_cleanup; if (parse.Nested == 0) v.CountChanges(); parse.BeginWriteOperation(1, db); // If we are trying to delete from a view, realize that view into a ephemeral table. #if !OMIT_VIEW && !OMIT_TRIGGER if (isView) MaterializeView(parse, table, where_, curId); #endif // Resolve the column names in the WHERE clause. NameContext sNC = new NameContext(); // Name context to resolve expressions in sNC.Parse = parse; sNC.SrcList = tabList; if (sqlite3ResolveExprNames(sNC, ref where_) != 0) goto delete_from_cleanup; // Initialize the counter of the number of rows deleted, if we are counting rows. int memCnt = -1; // Memory cell used for change counting if ((ctx.Flags & Context.FLAG.CountRows) != 0) { memCnt = ++parse.Mems; v.AddOp2(OP.Integer, 0, memCnt); } #if !OMIT_TRUNCATE_OPTIMIZATION // Special case: A DELETE without a WHERE clause deletes everything. It is easier just to erase the whole table. Prior to version 3.6.5, // this optimization caused the row change count (the value returned by API function sqlite3_count_changes) to be set incorrectly. if (rcauth == ARC.OK && where_ == null && trigger == null && !IsVirtual(table) && !FKey.FkRequired(parse, table, null, 0)) { Debug.Assert(!isView); v.AddOp4(OP.Clear, table.Id, db, memCnt, table.Name, Vdbe.P4T.STATIC); for (idx = table.Index; idx != null; idx = idx.Next) { Debug.Assert(idx.Schema == table.Schema); v.AddOp2(OP.Clear, idx.Id, db); } } else #endif // The usual case: There is a WHERE clause so we have to scan through the table and pick which records to delete. { int rowSet = ++parse.Mems; // Register for rowset of rows to delete int rowid = ++parse.Mems; // Used for storing rowid values. // Collect rowids of every row to be deleted. v.AddOp2(OP.Null, 0, rowSet); ExprList dummy = null; WhereInfo winfo = Where.Begin(parse, tabList, where_, ref dummy, WHERE_DUPLICATES_OK, 0); // Information about the WHERE clause if (winfo == null) goto delete_from_cleanup; int regRowid = Expr.CodeGetColumn(parse, table, -1, curId, rowid); // Actual register containing rowids v.AddOp2(OP.RowSetAdd, rowSet, regRowid); if ((ctx.Flags & Context.FLAG.CountRows) != 0) v.AddOp2(OP.AddImm, memCnt, 1); Where.End(winfo); // Delete every item whose key was written to the list during the database scan. We have to delete items after the scan is complete // because deleting an item can change the scan order. int end = v.MakeLabel(); // Unless this is a view, open cursors for the table we are deleting from and all its indices. If this is a view, then the // only effect this statement has is to fire the INSTEAD OF triggers. if (!isView) sqlite3OpenTableAndIndices(parse, table, curId, OP.OpenWrite); int addr = v.AddOp3(OP.RowSetRead, rowSet, end, rowid); // Delete the row #if !OMIT_VIRTUALTABLE if (IsVirtual(table)) { VTable vtable = VTable.GetVTable(ctx, table); VTable.MakeWritable(parse, table); v.AddOp4(OP.VUpdate, 0, 1, rowid, vtable, Vdbe.P4T.VTAB); v.ChangeP5(OE.Abort); sqlite3MayAbort(parse); } else #endif { int count = (parse.Nested == 0; // True to count changes GenerateRowDelete(parse, table, curId, rowid, count, trigger, OE.Default); } // End of the delete loop v.AddOp2(OP.Goto, 0, addr); v.ResolveLabel(end); // Close the cursors open on the table and its indexes. if (!isView && !IsVirtual(table)) { for (int i = 1, idx = table.Index; idx != null; i++, idx = idx.Next) v.AddOp2(OP.Close, curId + i, idx.Id); v.AddOp1(OP.Close, curId); } } // Update the sqlite_sequence table by storing the content of the maximum rowid counter values recorded while inserting into // autoincrement tables. if (parse.Nested == 0 && parse.TriggerTab == null) sqlite3AutoincrementEnd(parse); // Return the number of rows that were deleted. If this routine is generating code because of a call to sqlite3NestedParse(), do not // invoke the callback function. if ((ctx.Flags & Context.FLAG.CountRows) != 0 && parse.Nested == 0 && parse.TriggerTab == null) { v.AddOp2(OP.ResultRow, memCnt, 1); v.SetNumCols(1); v.SetColName(0, COLNAME_NAME, "rows deleted", SQLITE_STATIC); } delete_from_cleanup: Auth.ContextPop(sContext); SrcList.Delete(ctx, ref tabList); Expr.Delete(ctx, ref where_); return; }
public IEnumerable <ValidationResult> ValidateQuery(ValidationContext validationContext) { Enums enums = new Enums(LanguageRequest); Query query = validationContext.ObjectInstance as Query; query.HasErrors = false; if (query.ModelType == null) { query.HasErrors = true; yield return(new ValidationResult(string.Format(CSSPServicesRes._ShouldNotBeNullOrEmpty, "ModelType"), new[] { "ModelType" })); } else { if (!string.IsNullOrWhiteSpace(query.Extra)) { if (!(query.ModelType.Name.Length > 6 && !query.ModelType.Name.Substring(query.ModelType.Name.Length - 6).StartsWith("Extra"))) { string AllowableExtra = ""; bool QueryExtraExist = false; FileInfo fiDLL = new FileInfo($@"{ AppDomain.CurrentDomain.BaseDirectory }\CSSPModels.dll"); if (!fiDLL.Exists) { fiDLL = new FileInfo($@"{ AppDomain.CurrentDomain.BaseDirectory }\bin\CSSPModels.dll"); if (!fiDLL.Exists) { query.HasErrors = true; yield return(new ValidationResult(string.Format(CSSPServicesRes.CouldNotFindFile_, $@"{ AppDomain.CurrentDomain.BaseDirectory }\CSSPModels.dll or { AppDomain.CurrentDomain.BaseDirectory }\bin\CSSPModels.dll"), new[] { "Where" })); } } var importAssembly = Assembly.LoadFile(fiDLL.FullName); List <Type> TypeList = importAssembly.GetTypes().ToList(); foreach (string s in new List <string>() { "A", "B", "C", "D", "E" }) { bool exist = false; foreach (Type type in TypeList) { //string ExtraName = $"{ query.ModelType.Name }Extra{ s }"; if (query.ModelType.Name == type.Name) { exist = true; break; } } if (exist) { if (query.Extra == s) { QueryExtraExist = true; } AllowableExtra = AllowableExtra + s + ", "; } } if (!QueryExtraExist) { AllowableExtra = AllowableExtra.Trim(); AllowableExtra = AllowableExtra.Substring(0, AllowableExtra.Length - 1); query.HasErrors = true; yield return(new ValidationResult(string.Format(CSSPServicesRes.Extra_OfModel_IsInvalidAllowableValuesAre_, query.Extra, query.ModelType.Name, $"[{ AllowableExtra }]"), new[] { "extra" })); } } } } if (!(query.Lang == "fr" || query.Lang == "en")) { query.HasErrors = true; yield return(new ValidationResult(CSSPServicesRes.AllowableLanguagesAreFRAndEN, new[] { "Lang" })); } if (query.Skip < 0) { query.HasErrors = true; yield return(new ValidationResult(string.Format(CSSPServicesRes._ShouldBeAbove_, "Skip", "-1"), new[] { "Skip" })); } if (query.Skip > 1000000) { query.HasErrors = true; yield return(new ValidationResult(string.Format(CSSPServicesRes._ShouldBeBelow_, "Skip", "1000000"), new[] { "Skip" })); } if (query.Take < 1) { query.HasErrors = true; yield return(new ValidationResult(string.Format(CSSPServicesRes._ShouldBeAbove_, "Take", "0"), new[] { "Take" })); } if (query.Take > 1000000) { query.HasErrors = true; yield return(new ValidationResult(string.Format(CSSPServicesRes._ShouldBeBelow_, "Take", "1000000"), new[] { "Take" })); } query.AscList = new List <string>(); if (!string.IsNullOrWhiteSpace(query.Asc)) { query.AscList = query.Asc.Split(",".ToCharArray(), StringSplitOptions.RemoveEmptyEntries).Select(c => c.Trim()).ToList(); foreach (string PropertyName in query.AscList) { if (!query.ModelType.GetProperties().Where(c => c.Name == PropertyName).Any()) { query.HasErrors = true; yield return(new ValidationResult(string.Format(CSSPServicesRes._DoesNotExistForModelType_, PropertyName, query.ModelType.Name), new[] { "Order" })); } } } query.DescList = new List <string>(); if (!string.IsNullOrWhiteSpace(query.Desc)) { query.DescList = query.Desc.Split(",".ToCharArray(), StringSplitOptions.RemoveEmptyEntries).Select(c => c.Trim()).ToList(); foreach (string PropertyName in query.DescList) { if (!query.ModelType.GetProperties().Where(c => c.Name == PropertyName).Any()) { query.HasErrors = true; yield return(new ValidationResult(string.Format(CSSPServicesRes._DoesNotExistForModelType_, PropertyName, query.ModelType.Name), new[] { "Order" })); } } } query.WhereInfoList = new List <WhereInfo>(); if (!string.IsNullOrWhiteSpace(query.Where)) { List <string> WhereList = query.Where.Split("|".ToCharArray(), StringSplitOptions.RemoveEmptyEntries).Select(c => c.Trim()).ToList(); foreach (string w in WhereList) { // Example of where == "TVItemID,GT,5|TVItemID,LT,20" List <string> ValList = w.Split(",".ToCharArray(), StringSplitOptions.RemoveEmptyEntries).Select(c => c.Trim()).ToList(); if (ValList.Count != 3) { query.HasErrors = true; yield return(new ValidationResult(string.Format(CSSPServicesRes._NeedToHaveValidStringFormatEx_, "Where", "TVItemID,GT,5|TVItemID,LT,20"), new[] { "Where" })); } else { WhereInfo whereInfo = new WhereInfo(); PropertyInfo propertyInfo = query.ModelType.GetProperties().Where(c => c.Name == ValList[0]).FirstOrDefault(); if (propertyInfo == null) { query.HasErrors = true; yield return(new ValidationResult(string.Format(CSSPServicesRes._DoesNotExistForModelType_, ValList[0], query.ModelType.Name), new[] { "Where" })); } else { whereInfo.PropertyName = ValList[0]; whereInfo.Value = ValList[2]; string PropTypeName = propertyInfo.PropertyType.FullName; if (PropTypeName.Contains("Nullable")) { PropTypeName = PropTypeName.Substring(PropTypeName.IndexOf("[[") + 2); PropTypeName = PropTypeName.Substring(0, PropTypeName.IndexOf(",")); } switch (PropTypeName) { case "System.Boolean": { whereInfo.PropertyType = PropertyTypeEnum.Boolean; bool TempBool; if (bool.TryParse(whereInfo.Value, out TempBool)) { whereInfo.ValueBool = TempBool; } else { query.HasErrors = true; yield return(new ValidationResult(string.Format(CSSPServicesRes._NeedsToBeTrueOrFalseFor_OfModel_, whereInfo.Value, whereInfo.PropertyName, query.ModelType.Name), new[] { "Where" })); } } break; case "System.DateTime": { whereInfo.PropertyType = PropertyTypeEnum.DateTime; DateTime TempDateTime; if (DateTime.TryParse(whereInfo.Value, out TempDateTime)) { whereInfo.ValueDateTime = TempDateTime; } else { query.HasErrors = true; yield return(new ValidationResult(string.Format(CSSPServicesRes._NeedsToBeADateFor_OfModel_, whereInfo.Value, whereInfo.PropertyName, query.ModelType.Name), new[] { "Where" })); } } break; case "System.Double": { whereInfo.PropertyType = PropertyTypeEnum.Double; double TempDouble; if (Double.TryParse(whereInfo.Value, out TempDouble)) { whereInfo.ValueDouble = TempDouble; } else { query.HasErrors = true; yield return(new ValidationResult(string.Format(CSSPServicesRes._NeedsToBeANumberFor_OfModel_, whereInfo.Value, whereInfo.PropertyName, query.ModelType.Name), new[] { "Where" })); } } break; case "System.Int16": case "System.Int32": case "System.Int64": { whereInfo.PropertyType = PropertyTypeEnum.Int; int TempInt; if (int.TryParse(whereInfo.Value, out TempInt)) { whereInfo.ValueInt = TempInt; } else { query.HasErrors = true; yield return(new ValidationResult(string.Format(CSSPServicesRes._NeedsToBeANumberFor_OfModel_, whereInfo.Value, whereInfo.PropertyName, query.ModelType.Name), new[] { "Where" })); } } break; case "System.String": { whereInfo.PropertyType = PropertyTypeEnum.String; // no need to do anything here as the string value has already been saved under the whereInfo.Value } break; default: { if (propertyInfo.PropertyType.FullName.Contains("CSSPEnums.")) { whereInfo.PropertyType = PropertyTypeEnum.Enum; if (ValList[1] == "EQ") { string EnumTypeName = propertyInfo.PropertyType.FullName.Substring(propertyInfo.PropertyType.FullName.IndexOf("CSSPEnums.") + "CSSPEnums.".Length); if (EnumTypeName.Contains(",")) { EnumTypeName = EnumTypeName.Substring(0, EnumTypeName.IndexOf(",")); } FileInfo fiDLL = new FileInfo($@"{ AppDomain.CurrentDomain.BaseDirectory }\CSSPEnums.dll"); if (!fiDLL.Exists) { fiDLL = new FileInfo($@"{ AppDomain.CurrentDomain.BaseDirectory }\bin\CSSPEnums.dll"); if (!fiDLL.Exists) { query.HasErrors = true; yield return(new ValidationResult(string.Format(CSSPServicesRes.CouldNotFindFile_, $@"{ AppDomain.CurrentDomain.BaseDirectory }\CSSPEnums.dll or { AppDomain.CurrentDomain.BaseDirectory }\bin\CSSPEnums.dll"), new[] { "Where" })); } } var importAssembly = Assembly.LoadFile(fiDLL.FullName); List <Type> TypeList = importAssembly.GetTypes().ToList(); foreach (Type type in TypeList) { if (type.Name == EnumTypeName) { whereInfo.EnumType = type; if (Char.IsNumber(whereInfo.Value[0])) { if (int.TryParse(whereInfo.Value, out int TempInt)) { whereInfo.ValueInt = TempInt; } else { query.HasErrors = true; yield return(new ValidationResult(string.Format(CSSPServicesRes._NeedsToBeANumberFor_OfModel_, whereInfo.Value, whereInfo.PropertyName, query.ModelType.Name), new[] { "Where" })); } if (!(from c in Enum.GetValues(type) as int[] where c == whereInfo.ValueInt select c).Any()) { List <int> EnumValueList = (from c in Enum.GetValues(type) as int[] select c).ToList(); List <string> EnumValueTextList = (from c in Enum.GetNames(type) as string[] select c).ToList(); StringBuilder sb = new StringBuilder(); for (int i = 0, count = EnumValueList.Count; i < count; i++) { sb.Append($"{ EnumValueList[i] } = { EnumValueTextList[i] }, "); } query.HasErrors = true; yield return(new ValidationResult(string.Format(CSSPServicesRes._NeedsToBeAValidEnumNumberFor_OfModel_AllowableValuesAre_, whereInfo.Value, whereInfo.PropertyName, query.ModelType.Name, $"[{ sb.ToString() }]"), new[] { "Where" })); } else { int[] AllEnumIntList = Enum.GetValues(type) as int[]; string[] AllEnumTextList = Enum.GetNames(type) as string[]; for (int i = 0, count = AllEnumIntList.Count(); i < count; i++) { if (AllEnumIntList[i] == whereInfo.ValueInt) { whereInfo.ValueInt = AllEnumIntList[i]; whereInfo.ValueEnumText = AllEnumTextList[i]; break; } } } } else { if (!(from c in Enum.GetNames(type) where c == whereInfo.Value select c).Any()) { List <int> EnumValueList = (from c in Enum.GetValues(type) as int[] select c).ToList(); List <string> EnumValueTextList = (from c in Enum.GetNames(type) as string[] select c).ToList(); StringBuilder sb = new StringBuilder(); for (int i = 0, count = EnumValueList.Count; i < count; i++) { sb.Append($"{ EnumValueList[i] } = { EnumValueTextList[i] }, "); } query.HasErrors = true; yield return(new ValidationResult(string.Format(CSSPServicesRes._NeedsToBeAValidEnumTextFor_OfModel_AllowableValuesAre_, whereInfo.Value, whereInfo.PropertyName, query.ModelType.Name, $"[{ sb.ToString() }]"), new[] { "Where" })); } else { int[] AllEnumIntList = Enum.GetValues(type) as int[]; string[] AllEnumTextList = Enum.GetNames(type) as string[]; for (int i = 0, count = AllEnumIntList.Count(); i < count; i++) { if (AllEnumTextList[i] == whereInfo.Value) { whereInfo.ValueInt = AllEnumIntList[i]; whereInfo.ValueEnumText = AllEnumTextList[i]; break; } } } } break; } } } else { query.HasErrors = true; yield return(new ValidationResult(string.Format(CSSPServicesRes.WhereOperator_For_OfModel_IsNotValidOnlyEQIsAllowed, ValList[1], whereInfo.PropertyName, query.ModelType.Name), new[] { "Where" })); } } else { query.HasErrors = true; yield return(new ValidationResult(string.Format(CSSPServicesRes._NotImplementedYet, PropTypeName), new[] { "Where" })); } } break; } switch (ValList[1]) { case "EQ": { whereInfo.WhereOperator = WhereOperatorEnum.Equal; } break; case "LT": { whereInfo.WhereOperator = WhereOperatorEnum.LessThan; } break; case "GT": { whereInfo.WhereOperator = WhereOperatorEnum.GreaterThan; } break; case "C": { whereInfo.WhereOperator = WhereOperatorEnum.Contains; } break; case "SW": { whereInfo.WhereOperator = WhereOperatorEnum.StartsWith; } break; case "EW": { whereInfo.WhereOperator = WhereOperatorEnum.EndsWith; } break; default: { query.HasErrors = true; yield return(new ValidationResult(string.Format(CSSPServicesRes.WhereOperator_NotValidAllowableValuesAre_, ValList[1], "[EQ = EQUAL, LT = LESS THAN, GT = GREATER THAN, C = CONTAINS, SW = STARTS WITH, EW = ENDS WITH]"), new[] { "Where" })); } break; } query.WhereInfoList.Add(whereInfo); } } } } }