private ReferenceDisplayFieldDefinition GetDisplayField(ReferenceHelperContext context, FieldInfoDto fieldInfo, bool throwOnError) { if (context.VisitedFields.Contains(Tuple.Create(fieldInfo.DefinedIn, fieldInfo.SystemName))) throw new CircularReferenceException("Circular reference detected."); var publishedProcess = Cache.GetProcessInfo(fieldInfo.DefinedIn); var fieldDefinition = new ReferenceDisplayFieldDefinition { Name = fieldInfo.Name, SystemName = fieldInfo.SystemName, ColumnType = (ColumnTypes)Enum.Parse(typeof(ColumnTypes), fieldInfo.DataType), DefinedIn = GetProcessDefinition(publishedProcess), IsRichTextField = fieldInfo.IsRichTextField, }; if (fieldDefinition.SystemName == Constants.CurrentStateColumnName) { fieldDefinition.ReferencedProcess = GetProcessDefinition(Constants.StateProcessName); var fd = GetFieldDefinition(context, Constants.StateProcessName, Constants.Name, throwOnError); fd.Order = 1; fd.Guid = Guid.NewGuid(); fd.ShowOnDetails = true; fd.ShowOnSearch = true; fieldDefinition.Subfields.Add(fd); return fieldDefinition; } if (fieldDefinition.SystemName.Equals(Constants.VersionDate)) { fieldDefinition.DateTimeFormat = DateTimeFormat.DateTime; return fieldDefinition; } // System fields are not stored in the database. if (fieldDefinition.SystemName.Equals(Constants.IdColumnName, StringComparison.OrdinalIgnoreCase) || fieldDefinition.SystemName.Equals(Constants.VersionNumber)) { return fieldDefinition; } var tuple = Tuple.Create(fieldDefinition.DefinedIn.SystemName, fieldDefinition.SystemName); try { context.VisitedFields.Add(tuple); if (fieldDefinition.IsRef) { var crStep = Cache.GetCrossReferenceRequiredStep(fieldDefinition.DefinedIn.SystemName, fieldDefinition.SystemName); if (!crStep.CrossRefProcessId.HasValue) throw new InvalidReferenceFieldExpcetion(fieldDefinition.DefinedIn.SystemName, fieldDefinition.SystemName, "Cross reference process is null."); var referencedProcess = Cache.GetProcessInfo(crStep.CrossRefProcessId.Value); fieldDefinition.ReferencedProcess = GetProcessDefinition(referencedProcess); if (fieldDefinition.ColumnType == ColumnTypes.MultiReference && !string.IsNullOrEmpty(crStep.LinkFieldSystemName)) { var referenceField = GetJoinField(referencedProcess.SystemName, crStep.LinkFieldSystemName); if (referenceField.ColumnType != ColumnTypes.Reference) throw new InvalidReferenceFieldExpcetion(fieldInfo.DefinedIn, fieldInfo.SystemName, "Invalid link field type."); if (referenceField.ReferencedProcess.SystemName != fieldInfo.DefinedIn) throw new InvalidReferenceFieldExpcetion(fieldInfo.DefinedIn, fieldInfo.SystemName, "Invalid link field."); fieldDefinition.ReferenceField = referenceField; } var order = 0; ReferenceDisplayFieldDefinition fd; foreach (var displayField in crStep.DisplayFields) { fd = GetFieldDefinition(context, referencedProcess.SystemName, displayField.FullPath, throwOnError); ++order; fd.Order = order; fd.Guid = displayField.Guid; fd.ShowOnDetails = true; fd.ShowOnSearch = false; fieldDefinition.Subfields.Add(fd); } fd = fieldDefinition.Subfields.FirstOrDefault(x => x.FullPath == crStep.DisplayFieldName); if (fd != null) { fd.ShowOnSearch = true; } else { fd = GetFieldDefinition(context, referencedProcess.SystemName, crStep.DisplayFieldName, throwOnError); fd.Order = 1; fd.Guid = Guid.NewGuid(); fd.ShowOnDetails = false; fd.ShowOnSearch = true; fieldDefinition.Subfields.Add(fd); } } if (fieldDefinition.IsReverseRef) { var rcrStep = Cache.GetReverseCrossReferenceRequiredStep(fieldDefinition.DefinedIn.SystemName, fieldDefinition.SystemName); if (!rcrStep.ReverseCrossRefProcessId.HasValue) throw new InvalidReferenceFieldExpcetion( fieldDefinition.DefinedIn.SystemName, fieldDefinition.SystemName, "Reverse cross reference process is null."); var referencedProcess = Cache.GetProcessInfo(rcrStep.ReverseCrossRefProcessId.Value); var rcrOptions = Cache.GetReverseCrossReferenceOptionsStep(fieldDefinition.DefinedIn.SystemName, fieldDefinition.SystemName); var referenceField = GetJoinField(referencedProcess.SystemName, rcrStep.CrossRefFieldName); fieldDefinition.ShowLatestVersion = rcrOptions.ShowLatestVersion && referencedProcess.ProcessOption == ProcessOption.VersionEnabled; fieldDefinition.ReferenceField = referenceField; var order = 0; ReferenceDisplayFieldDefinition fd; foreach (var displayField in rcrStep.SelectedDisplayFields.OrderBy(df => df.Order)) { fd = GetFieldDefinition(context, referencedProcess.SystemName, displayField.FullPath, throwOnError); if (fd != null) { ++order; fd.Order = order; fd.Guid = displayField.Guid; fd.ShowOnDetails = true; fd.ShowOnSearch = false; fieldDefinition.Subfields.Add(fd); } } fd = fieldDefinition.Subfields.FirstOrDefault(x => x.FullPath == rcrStep.DisplayFieldName); if (fd != null) fd.ShowOnSearch = true; else { fd = GetFieldDefinition(context, referencedProcess.SystemName, rcrStep.DisplayFieldName, throwOnError); fd.Order = 1; fd.Guid = Guid.NewGuid(); fd.ShowOnDetails = false; fd.ShowOnSearch = true; fieldDefinition.Subfields.Add(fd); } } if (fieldDefinition.ColumnType == ColumnTypes.Numeric) { var numericStep = Cache.GetNumericRequiredStep(fieldDefinition.DefinedIn.SystemName, fieldDefinition.SystemName); fieldDefinition.NumericType = NumericTypes.Numeric; if (numericStep.NumberOfDigits == 0 && numericStep.Minimum >= int.MinValue && numericStep.Maximum <= int.MaxValue && (NumericTypes)numericStep.NumericType == NumericTypes.Numeric) { fieldDefinition.ColumnType = ColumnTypes.Integer; } fieldDefinition.NumericType = (NumericTypes)numericStep.NumericType; fieldDefinition.NumberOfDigits = numericStep.NumberOfDigits; } if (fieldDefinition.ColumnType == ColumnTypes.DateTime) { var dateTimeStep = Cache.GetDateTimeRequiredStep(fieldDefinition.DefinedIn.SystemName, fieldDefinition.SystemName); fieldDefinition.DateTimeFormat = DateTimeFormat.DateTime; DateTimeFormat format; if (Enum.TryParse(dateTimeStep.DateTimeFormat, true, out format)) fieldDefinition.DateTimeFormat = format; } if (fieldDefinition.ColumnType == ColumnTypes.Boolean) { var checkboxStep = Cache.GetCheckboxOptionsStep(fieldDefinition.DefinedIn.SystemName, fieldDefinition.SystemName); fieldDefinition.MainLabel = checkboxStep.MainLabel; fieldDefinition.UndefinedLabel = checkboxStep.IsSwitchToggle ? checkboxStep.UndefinedLabel : string.Empty; fieldDefinition.TrueLabel = checkboxStep.IsSwitchToggle ? checkboxStep.TrueLabel : true.ToString(); fieldDefinition.FalseLabel = checkboxStep.IsSwitchToggle ? checkboxStep.FalseLabel : false.ToString(); fieldDefinition.IsSwitchToggle = checkboxStep.IsSwitchToggle; } if (fieldDefinition.ColumnType == ColumnTypes.Image) { var pictureStep = Cache.GetPictureStep(fieldDefinition.DefinedIn.SystemName, fieldDefinition.SystemName); fieldDefinition.SearchImageWidth = pictureStep.SearchWidth; fieldDefinition.SearchImageHeight = pictureStep.SearchHeight; fieldDefinition.DetailsImageWidth = pictureStep.DetailsWidth; fieldDefinition.DetailsImageHeight = pictureStep.DetailsHeight; fieldDefinition.UseOriginalImageSize = pictureStep.UseOriginalSize; } } finally { context.VisitedFields.Remove(tuple); } return fieldDefinition; }
/// <summary> /// Retrieves single cross references to process. /// </summary> /// <param name="definingProcessPublishedId">The defining process published id.</param> /// <param name="referencedProcessSystemName">The referenced process system name.</param> /// <returns>The <see cref="IList" />.</returns> public IEnumerable<FieldInfoDto> FetchSingleCrossReferencesToProcess(int definingProcessPublishedId, string referencedProcessSystemName) { const string CommandText = @" SELECT f.[Id] ,f.[Guid] ,f.[Name] ,f.[SystemName] ,f.[FieldTypeId] ,p.[SystemName] AS 'DefinedIn' FROM [dbo].[Fields] f INNER JOIN [dbo].[Sections] s ON s.[Id] = f.[SectionId] INNER JOIN [dbo].[Processes] p ON p.[Id] = s.[ProcessId] INNER JOIN [dbo].[PublishedProcesses] pp ON pp.[ProcessId] = p.[Id] INNER JOIN [dbo].[CrossRefRequredFieldStep] crrs ON crrs.[FieldId] = f.[Id] INNER JOIN [dbo].[PublishedProcesses] pp2 ON pp2.[Id] = crrs.[CrossRefProcessId] INNER JOIN [dbo].[Processes] p2 ON p2.[Id] = pp2.[ProcessId] WHERE f.[IsRemoved] = 0 AND pp.[Id] = @definingProcessPublishedId AND p2.[SystemName] = @referencedProcessSystemName AND crrs.[AllowMultiple] = 0"; var fields = new List<FieldInfoDto>(); using (var ctx = ConnectionManager<SqlConnection>.GetManager(Database.VeyronMeta, false)) { using (var cmd = new SqlCommand(CommandText, ctx.Connection)) { cmd.Parameters.AddWithValue("@definingProcessPublishedId", definingProcessPublishedId); cmd.Parameters.AddWithValue("@referencedProcessSystemName", referencedProcessSystemName); using (var reader = new SafeDataReader(cmd.ExecuteReader())) { while (reader.Read()) { var dto = new FieldInfoDto { Id = reader.GetInt32(0), Guid = reader.GetGuid(1), Name = reader.GetString(2), SystemName = reader.GetString(3), DataType = ColumnTypes.Reference.ToString(), FieldTypeId = reader.GetInt32(4), DefinedIn = reader.GetString(5) }; fields.Add(dto); } } } } return fields; }
private ReferenceJoinFieldDefinition GetJoinField(FieldInfoDto fieldInfo) { var columnType = (ColumnTypes)Enum.Parse(typeof(ColumnTypes), fieldInfo.DataType); var publishedProcess = Cache.GetProcessInfo(fieldInfo.DefinedIn); if (columnType == ColumnTypes.Reference || columnType == ColumnTypes.MultiReference) { if (fieldInfo.SystemName.Equals(Constants.CurrentStateColumnName, StringComparison.OrdinalIgnoreCase)) { return new ReferenceJoinFieldDefinition { Name = fieldInfo.Name, SystemName = fieldInfo.SystemName, ColumnType = columnType, DefinedIn = GetProcessDefinition(publishedProcess), ReferencedProcess = GetProcessDefinition(Constants.StateProcessName) }; } var crStep = Cache.GetCrossReferenceRequiredStep(fieldInfo.DefinedIn, fieldInfo.SystemName); if (!crStep.CrossRefProcessId.HasValue) throw new InvalidReferenceFieldExpcetion(fieldInfo.DefinedIn, fieldInfo.SystemName, "Cross reference process is null."); var referencedProcess = Cache.GetProcessInfo(crStep.CrossRefProcessId.Value); var joinField = new ReferenceJoinFieldDefinition { Name = fieldInfo.Name, SystemName = fieldInfo.SystemName, ColumnType = columnType, DefinedIn = GetProcessDefinition(publishedProcess), ReferencedProcess = GetProcessDefinition(referencedProcess) }; if (columnType == ColumnTypes.MultiReference && !string.IsNullOrEmpty(crStep.LinkFieldSystemName)) { var referenceField = GetJoinField(referencedProcess.SystemName, crStep.LinkFieldSystemName); if (referenceField.ColumnType != ColumnTypes.Reference) throw new InvalidReferenceFieldExpcetion(fieldInfo.DefinedIn, fieldInfo.SystemName, "Invalid link field type."); if (referenceField.ReferencedProcess.SystemName != fieldInfo.DefinedIn) throw new InvalidReferenceFieldExpcetion(fieldInfo.DefinedIn, fieldInfo.SystemName, "Invalid link field."); joinField.ReferenceField = referenceField; } return joinField; } if (columnType == ColumnTypes.ReverseReference || columnType == ColumnTypes.ReverseMultiReference || columnType == ColumnTypes.TreeView) { var rcrStep = Cache.GetReverseCrossReferenceRequiredStep(fieldInfo.DefinedIn, fieldInfo.SystemName); if (!rcrStep.ReverseCrossRefProcessId.HasValue) throw new InvalidReferenceFieldExpcetion(fieldInfo.DefinedIn, fieldInfo.SystemName, "Reverse cross reference process is null."); var rcrOptions = Cache.GetReverseCrossReferenceOptionsStep(fieldInfo.DefinedIn, fieldInfo.SystemName); var referencedProcess = Cache.GetProcessInfo(rcrStep.ReverseCrossRefProcessId.Value); var referenceField = GetJoinField(referencedProcess.SystemName, rcrStep.CrossRefFieldName); var joinField = new ReferenceJoinFieldDefinition { Name = fieldInfo.Name, SystemName = fieldInfo.SystemName, ColumnType = columnType, ShowLatestVersion = rcrOptions.ShowLatestVersion && referencedProcess.ProcessOption == ProcessOption.VersionEnabled, DefinedIn = GetProcessDefinition(publishedProcess), ReferencedProcess = GetProcessDefinition(referencedProcess), ReferenceField = referenceField }; return joinField; } if (columnType == ColumnTypes.Checklist) { var clStep = Cache.GetChecklistStep(fieldInfo.DefinedIn, fieldInfo.SystemName); if (string.IsNullOrEmpty(clStep.AnswerProcessSystemName)) throw new InvalidReferenceFieldExpcetion(fieldInfo.DefinedIn, fieldInfo.SystemName, "Checklist answer process is null."); var referencedProcess = Cache.GetProcessInfo(clStep.AnswerProcessSystemName); var joinField = new ReferenceJoinFieldDefinition { Name = fieldInfo.Name, SystemName = fieldInfo.SystemName, ColumnType = columnType, DefinedIn = GetProcessDefinition(publishedProcess), ReferencedProcess = GetProcessDefinition(referencedProcess) }; return joinField; } throw new InvalidReferenceFieldExpcetion(fieldInfo.DefinedIn, fieldInfo.SystemName, string.Format(@"Column type '{0}' is not valid for a join field.", columnType)); }