/// <summary>
        /// Sets the value.
        /// </summary>
        /// <param name="mergeTemplate">The merge template.</param>
        public void SetValue(MergeTemplate mergeTemplate)
        {
            if (mergeTemplate != null)
            {
                ItemId = mergeTemplate.Id.ToString();

                var parentCategoryIds = new List <string>();
                var parentCategory    = mergeTemplate.Category;
                while (parentCategory != null)
                {
                    if (!parentCategoryIds.Contains(parentCategory.Id.ToString()))
                    {
                        parentCategoryIds.Insert(0, parentCategory.Id.ToString());
                    }
                    else
                    {
                        // infinite recursion
                        break;
                    }

                    parentCategory = parentCategory.ParentCategory;
                }

                InitialItemParentIds = parentCategoryIds.AsDelimited(",");
                ItemName             = mergeTemplate.Name;
            }
            else
            {
                ItemId   = Constants.None.IdValue;
                ItemName = Constants.None.TextHtml;
            }
        }
        private async Task <IEnumerable <MergeTemplate> > GetLegacyMergeTemplates(string spreadsheetId,
                                                                                  CancellationToken cancellationToken = default(CancellationToken))
        {
            var returnValue = new List <MergeTemplate>();

            foreach (var row in await _sheetsService.GetValuesAsync(spreadsheetId, range: string.Concat("mm-config!", MM_CONFIG_ENTIRE_SHEET_RANGE)))
            {
                if (row.Count == 0)
                {
                    _logger.Warning("Row {RowNumber} had no data, not contributing to returned merge templates", returnValue.Count + 1);
                }
                else if (row.Count == 1)
                {
                    _logger.Warning("Row {RowNumber} had only 1 cell, not contributing to returned merge templates", returnValue.Count + 1);
                }
                else if (row[1] == null)
                {
                    _logger.Warning("Row {RowNumber} did not contain a value in the second cell, not contributing to returned merge templates", returnValue.Count + 1);
                }
                else
                {
                    returnValue.Add(MergeTemplate.CreateFrom(row[0].ToString(), spreadsheetId, row[1].ToString()));
                }
            }
            return(returnValue);
        }
        /// <summary>
        /// Sets the value.
        /// </summary>
        /// <param name="mergeTemplate">The merge template.</param>
        public void SetValue( MergeTemplate mergeTemplate )
        {
            if ( mergeTemplate != null )
            {
                ItemId = mergeTemplate.Id.ToString();

                var parentCategoryIds = new List<string>();
                var parentCategory = mergeTemplate.Category;
                while ( parentCategory != null )
                {
                    if ( !parentCategoryIds.Contains( parentCategory.Id.ToString() ) )
                    {
                        parentCategoryIds.Insert( 0, parentCategory.Id.ToString() );
                    }
                    else
                    {
                        // infinite recursion
                        break;
                    }

                    parentCategory = parentCategory.ParentCategory;
                }

                InitialItemParentIds = parentCategoryIds.AsDelimited( "," );
                ItemName = mergeTemplate.Name;
            }
            else
            {
                ItemId = Constants.None.IdValue;
                ItemName = Constants.None.TextHtml;
            }
        }
        public async Task <MergeTemplate> AddMergeTemplateAsync(MergeTemplate mergeTemplate, CancellationToken cancellationToken = default(CancellationToken))
        {
            _mergeTemplateContext.MergeTemplates.Add(mergeTemplate);
            await _mergeTemplateContext.SaveChangesAsync(cancellationToken);

            return(mergeTemplate);
        }
        /// <summary>
        /// Creates the document.
        /// </summary>
        /// <param name="mergeTemplate">The merge template.</param>
        /// <param name="mergeObjectList">The merge object list.</param>
        /// <param name="globalMergeFields">The global merge fields.</param>
        /// <returns></returns>
        public override BinaryFile CreateDocument( MergeTemplate mergeTemplate, List<object> mergeObjectList, Dictionary<string, object> globalMergeFields )
        {
            this.Exceptions = new List<Exception>();
            BinaryFile outputBinaryFile = null;

            var rockContext = new RockContext();
            var binaryFileService = new BinaryFileService( rockContext );

            var templateBinaryFile = binaryFileService.Get( mergeTemplate.TemplateBinaryFileId );
            if ( templateBinaryFile == null )
            {
                return null;
            }

            string templateHtml = templateBinaryFile.ContentsToString();
            var htmlMergeObjects = GetHtmlMergeObjects( mergeObjectList, globalMergeFields );
            string outputHtml = templateHtml.ResolveMergeFields( htmlMergeObjects );
            HtmlDocument outputDoc = new HtmlDocument();
            outputDoc.LoadHtml( outputHtml );
            var outputStream = new MemoryStream();
            outputDoc.Save( outputStream );

            outputBinaryFile = new BinaryFile();
            outputBinaryFile.IsTemporary = true;
            outputBinaryFile.ContentStream = outputStream;
            outputBinaryFile.FileName = "MergeTemplateOutput" + Path.GetExtension( templateBinaryFile.FileName );
            outputBinaryFile.MimeType = templateBinaryFile.MimeType;
            outputBinaryFile.BinaryFileTypeId = new BinaryFileTypeService( rockContext ).Get( Rock.SystemGuid.BinaryFiletype.DEFAULT.AsGuid() ).Id;

            binaryFileService.Add( outputBinaryFile );
            rockContext.SaveChanges();

            return outputBinaryFile;
        }
        public async Task <MergeTemplate> UpdateMergeTemplateAsync(MergeTemplate mergeTemplate, CancellationToken cancellationToken = default(CancellationToken))
        {
            var entry = _mergeTemplateContext.Entry(mergeTemplate);

            entry.State = EntityState.Modified;
            await _mergeTemplateContext.SaveChangesAsync(cancellationToken);

            return(mergeTemplate);
        }
Exemple #7
0
        /// <summary>
        /// Gets the type of the merge template.
        /// </summary>
        /// <param name="rockContext">The rock context.</param>
        /// <param name="mergeTemplate">The merge template.</param>
        /// <returns></returns>
        private MergeTemplateType GetMergeTemplateType(RockContext rockContext, MergeTemplate mergeTemplate)
        {
            mergeTemplate = new MergeTemplateService(rockContext).Get(mtPicker.SelectedValue.AsInteger());
            if (mergeTemplate == null)
            {
                return(null);
            }

            return(mergeTemplate.GetMergeTemplateType());
        }
        public void CreateMergeTemplateFromSerializedDataWithBadHeaderRowNumber()
        {
            dynamic templateJsonObject = JObject.Parse(Mocks.SAMPLE_MM_JSON);

            templateJsonObject.mergeData.headerRow = "NotANumber";
            string templateJson = templateJsonObject.ToString();

            var template = MergeTemplate.CreateFrom("Id1", "SheetId", templateJson);

            template.HeaderRowNumber.Should().Be(1);
        }
        public void CreateMergeTempalteFromSerializedDataWithInvalidTypeThrows()
        {
            dynamic templateJsonObject = JObject.Parse(Mocks.SAMPLE_MM_JSON);

            templateJsonObject.mergeData.type = "badType";
            string templateJson = templateJsonObject.ToString();

            Action action = () => MergeTemplate.CreateFrom("Id1", "SheetId", templateJson);

            action.Should().Throw <InvalidOperationException>();
        }
        public void CreateMergeTemplateFromSerializedData(bool timeStampShouldPrefixNameWithMergeTemplateTitle)
        {
            dynamic templateJsonObject = JObject.Parse(Mocks.SAMPLE_MM_JSON);

            // set "usetitle" as per the timeStampShouldPrefixNameWithMergeTemplateTitle parameter
            templateJsonObject.mergeData.usetitle = timeStampShouldPrefixNameWithMergeTemplateTitle ? "true" : "false";
            string templateJson = templateJsonObject.ToString();

            var template = MergeTemplate.CreateFrom("Id1", "SheetId", templateJson);

            ValidateTemplateFromJson(template, templateJson);
            template.SpreadSheetId.Should().Be("SheetId");
        }
        public void CreateMergeTemplateFromSerializedDataWithWithoutCreatedDate()
        {
            dynamic templateJsonObject = JObject.Parse(Mocks.SAMPLE_MM_JSON);

            templateJsonObject.createdDatetime = null;
            string templateJson = templateJsonObject.ToString();

            DateTime utcMin   = DateTime.UtcNow;
            var      template = MergeTemplate.CreateFrom("Id1", "SheetId", templateJson);
            DateTime utcMax   = DateTime.UtcNow;

            template.CreatedDateUtc.Should().BeOnOrAfter(utcMin).And.BeOnOrBefore(utcMax);
        }
        protected void ValidateTemplateFromJson(MergeTemplate template, string templateJson)
        {
            template.Should().NotBeNull();

            dynamic  templateJsonObject  = JObject.Parse(templateJson);
            string   expectedTitle       = templateJsonObject.mergeData.title;
            string   expectedCreatedBy   = templateJsonObject.createdBy;
            DateTime expectedCreatedDate = templateJsonObject.createdDatetime;

            expectedCreatedDate = expectedCreatedDate.ToUniversalTime();
            int    expectedHeaderRowNumber = templateJsonObject.mergeData.headerRow;
            string expectedSheetname       = templateJsonObject.mergeData.sheet;
            string expectedTimestampColumn = templateJsonObject.mergeData.timestampColumn;
            bool   expectedShouldPrefixNameWithMergeTemplateTitle = templateJsonObject.mergeData.usetitle;

            template.Title.Should().Be(expectedTitle);
            template.CreatedBy.Should().Be(expectedCreatedBy);
            template.CreatedDateUtc.Should().Be(expectedCreatedDate);

            template.HeaderRowNumber.Should().Be(expectedHeaderRowNumber);
            template.SheetName.Should().Be(expectedSheetname);
            template.TimestampColumn.Should().NotBeNull();
            template.TimestampColumn.Name.Should().Be(expectedTimestampColumn);

            // validation if the mergeTemplate is of type "Email"
            var emailMergeTemplate = template as EmailMergeTemplate;

            if (emailMergeTemplate != null)
            {
                template.Type.Should().Be(MergeTemplateType.Email);

                string expectedTo      = templateJsonObject.mergeData.data.to;
                string expectedCc      = templateJsonObject.mergeData.data.cc;
                string expectedBcc     = templateJsonObject.mergeData.data.bcc;
                string expectedSubject = templateJsonObject.mergeData.data.subject;
                string expectedBody    = templateJsonObject.mergeData.data.body;

                emailMergeTemplate.EmailTemplate.Should().NotBeNull();
                emailMergeTemplate.EmailTemplate.To.Should().Be(expectedTo);
                emailMergeTemplate.EmailTemplate.Cc.Should().Be(expectedCc);
                emailMergeTemplate.EmailTemplate.Bcc.Should().Be(expectedBcc);
                emailMergeTemplate.EmailTemplate.Subject.Should().Be(expectedSubject);
                emailMergeTemplate.EmailTemplate.Body.Should().Be(expectedBody);
            }

            // default should be to add
            template.TimestampColumn.ShouldPrefixNameWithMergeTemplateTitle.Should().Be(expectedShouldPrefixNameWithMergeTemplateTitle);
        }
        public void CreateMergeTemplateFromSerializedDataWithoutUser()
        {
            var template = MergeTemplate.CreateFrom("Id1", "SheetId", Mocks.SAMPLE_MM_JSON);

            template.Should().NotBeNull();
            template.CreatedBy.Should().Be("Unknown user");

            dynamic templateJsonObject = JObject.Parse(Mocks.SAMPLE_MM_JSON);

            templateJsonObject.createdBy = null;
            string templateJson = templateJsonObject.ToString();

            template = MergeTemplate.CreateFrom("Id1", "SheetId", templateJson);
            template.Should().NotBeNull();
            template.CreatedBy.Should().Be("Unknown user");
        }
        /// <summary>
        /// Gets the type of the merge template.
        /// </summary>
        /// <param name="rockContext">The rock context.</param>
        /// <param name="mergeTemplate">The merge template.</param>
        /// <returns></returns>
        private MergeTemplateType GetMergeTemplateType(RockContext rockContext, MergeTemplate mergeTemplate)
        {
            mergeTemplate = new MergeTemplateService(rockContext).Get(mtPicker.SelectedValue.AsInteger());
            if (mergeTemplate == null)
            {
                return(null);
            }

            var mergeTemplateTypeEntityType = EntityTypeCache.Read(mergeTemplate.MergeTemplateTypeEntityTypeId);

            if (mergeTemplateTypeEntityType == null)
            {
                return(null);
            }

            return(MergeTemplateTypeContainer.GetComponent(mergeTemplateTypeEntityType.Name));
        }
        /// <summary>
        /// Shows the readonly details.
        /// </summary>
        /// <param name="mergeTemplate">The merge template.</param>
        private void ShowReadonlyDetails(MergeTemplate mergeTemplate)
        {
            SetEditMode(false);
            hfMergeTemplateId.SetValue(mergeTemplate.Id);
            lReadOnlyTitle.Text = mergeTemplate.Name.FormatAsHtmlTitle();

            DescriptionList descriptionListCol1 = new DescriptionList()
                                                  .Add("Template File", string.Format("<a href='{0}'>{1}</a>", mergeTemplate.TemplateBinaryFile.Url, mergeTemplate.TemplateBinaryFile.FileName))
                                                  .Add("Description", mergeTemplate.Description ?? string.Empty)
                                                  .Add("Type", mergeTemplate.MergeTemplateTypeEntityType);

            DescriptionList descriptionListCol2 = new DescriptionList()
                                                  .Add("Category", mergeTemplate.Category != null ? mergeTemplate.Category.Name : string.Empty)
                                                  .Add("Person", mergeTemplate.PersonAlias, false);

            lblMainDetailsCol1.Text = descriptionListCol1.Html;
            lblMainDetailsCol2.Text = descriptionListCol2.Html;
        }
 private bool ShouldProcess(MergeTemplate mergeTemplate, IDictionary <string, object> values)
 {
     //TODO: skip rows that don't meet
     if (!string.IsNullOrWhiteSpace(mergeTemplate.Conditional))
     {
         string conditional = Render(mergeTemplate.Conditional, values);
         bool   shouldProcess;
         if (bool.TryParse(conditional, out shouldProcess))
         {
             return(shouldProcess);
         }
         else
         {
             _logger.Warning("Could not interpret conditional value {Conditional}", conditional);
         }
     }
     return(true);
 }
        /// <summary>
        /// Handles the Delete event of the gMergeTemplates control.
        /// </summary>
        /// <param name="sender">The source of the event.</param>
        /// <param name="e">The <see cref="RowEventArgs"/> instance containing the event data.</param>
        protected void gMergeTemplates_Delete(object sender, RowEventArgs e)
        {
            var rockContext = new RockContext();
            MergeTemplateService service = new MergeTemplateService(rockContext);
            MergeTemplate        item    = service.Get(e.RowKeyId);

            if (item != null)
            {
                string errorMessage;
                if (!service.CanDelete(item, out errorMessage))
                {
                    mdGridWarning.Show(errorMessage, ModalAlertType.Information);
                    return;
                }

                service.Delete(item);
                rockContext.SaveChanges();
            }

            BindGrid();
        }
        /// <summary>
        /// Sets the value.
        /// Expects value as a MergeTemplate.Guid as string
        /// </summary>
        /// <param name="control">The control.</param>
        /// <param name="configurationValues">The configuration values.</param>
        /// <param name="value">The value.</param>
        public override void SetEditValue(System.Web.UI.Control control, Dictionary <string, ConfigurationValue> configurationValues, string value)
        {
            var picker = control as MergeTemplatePicker;

            if (picker != null)
            {
                MergeTemplate item     = null;
                Guid?         itemGuid = value.AsGuidOrNull();
                if (itemGuid.HasValue)
                {
                    using (var rockContext = new RockContext())
                    {
                        item = new MergeTemplateService(rockContext).Get(itemGuid.Value);
                        picker.SetValue(item);
                    }
                }
                else
                {
                    picker.SetValue(null);
                }
            }
        }
Exemple #19
0
        /// <summary>
        /// Sets the value.
        /// </summary>
        /// <param name="mergeTemplate">The merge template.</param>
        public void SetValue( MergeTemplate mergeTemplate )
        {
            if ( mergeTemplate != null )
            {
                ItemId = mergeTemplate.Id.ToString();

                string parentCategoryIds = string.Empty;
                var parentCategory = mergeTemplate.Category;
                while ( parentCategory != null )
                {
                    parentCategoryIds = parentCategory.Id + "," + parentCategoryIds;
                    parentCategory = parentCategory.ParentCategory;
                }

                InitialItemParentIds = parentCategoryIds.TrimEnd( new[] { ',' } );
                ItemName = mergeTemplate.Name;
            }
            else
            {
                ItemId = Constants.None.IdValue;
                ItemName = Constants.None.TextHtml;
            }
        }
        /// <summary>
        /// Shows the readonly details.
        /// </summary>
        /// <param name="mergeTemplate">The merge template.</param>
        private void ShowReadonlyDetails(MergeTemplate mergeTemplate)
        {
            SetEditMode(false);
            hfMergeTemplateId.SetValue(mergeTemplate.Id);
            lReadOnlyTitle.Text = mergeTemplate.Name.FormatAsHtmlTitle();

            var getFileUrl = string.Format(
                "{0}GetFile.ashx?guid={1}",
                System.Web.VirtualPathUtility.ToAbsolute("~"),
                mergeTemplate.TemplateBinaryFile != null ? mergeTemplate.TemplateBinaryFile.Guid : (Guid?)null);

            DescriptionList descriptionListCol1 = new DescriptionList()
                                                  .Add("Template File", string.Format("<a href='{0}'>{1}</a>", getFileUrl, mergeTemplate.TemplateBinaryFile.FileName))
                                                  .Add("Description", mergeTemplate.Description ?? string.Empty)
                                                  .Add("Type", mergeTemplate.MergeTemplateTypeEntityType);

            DescriptionList descriptionListCol2 = new DescriptionList()
                                                  .Add("Category", mergeTemplate.Category != null ? mergeTemplate.Category.Name : string.Empty)
                                                  .Add("Person", mergeTemplate.PersonAlias, false);

            lblMainDetailsCol1.Text = descriptionListCol1.Html;
            lblMainDetailsCol2.Text = descriptionListCol2.Html;
        }
        /// <summary>
        /// Creates the document.
        /// </summary>
        /// <param name="mergeTemplate">The merge template.</param>
        /// <param name="mergeObjectList">The merge object list.</param>
        /// <param name="globalMergeFields">The global merge fields.</param>
        /// <returns></returns>
        public override BinaryFile CreateDocument(MergeTemplate mergeTemplate, List <object> mergeObjectList, Dictionary <string, object> globalMergeFields)
        {
            this.Exceptions = new List <Exception>();
            BinaryFile outputBinaryFile = null;

            var rockContext       = new RockContext();
            var binaryFileService = new BinaryFileService(rockContext);

            var templateBinaryFile = binaryFileService.Get(mergeTemplate.TemplateBinaryFileId);

            if (templateBinaryFile == null)
            {
                return(null);
            }

            string       templateHtml     = templateBinaryFile.ContentsToString();
            var          htmlMergeObjects = GetHtmlMergeObjects(mergeObjectList, globalMergeFields);
            string       outputHtml       = templateHtml.ResolveMergeFields(htmlMergeObjects);
            HtmlDocument outputDoc        = new HtmlDocument();

            outputDoc.LoadHtml(outputHtml);
            var outputStream = new MemoryStream();

            outputDoc.Save(outputStream);

            outputBinaryFile                  = new BinaryFile();
            outputBinaryFile.IsTemporary      = true;
            outputBinaryFile.ContentStream    = outputStream;
            outputBinaryFile.FileName         = "MergeTemplateOutput" + Path.GetExtension(templateBinaryFile.FileName);
            outputBinaryFile.MimeType         = templateBinaryFile.MimeType;
            outputBinaryFile.BinaryFileTypeId = new BinaryFileTypeService(rockContext).Get(Rock.SystemGuid.BinaryFiletype.DEFAULT.AsGuid()).Id;

            binaryFileService.Add(outputBinaryFile);
            rockContext.SaveChanges();

            return(outputBinaryFile);
        }
Exemple #22
0
        /// <summary>
        /// Shows the detail.
        /// </summary>
        /// <param name="mergeTemplateId">The merge template identifier.</param>
        /// <param name="parentCategoryId">The parent category identifier.</param>
        public void ShowDetail( int mergeTemplateId, int? parentCategoryId )
        {
            pnlDetails.Visible = false;

            var rockContext = new RockContext();
            var mergeTemplateService = new MergeTemplateService( rockContext );

            MergeTemplate mergeTemplate = null;

            if ( !mergeTemplateId.Equals( 0 ) )
            {
                mergeTemplate = mergeTemplateService.Get( mergeTemplateId );
            }

            var mergeTemplateOwnership = this.GetAttributeValue( "MergeTemplatesOwnership" ).ConvertToEnum<MergeTemplateOwnership>( MergeTemplateOwnership.Global );

            if ( mergeTemplate == null )
            {
                mergeTemplate = new MergeTemplate();
                mergeTemplate.CategoryId = parentCategoryId ?? 0;

                if ( mergeTemplateOwnership == MergeTemplateOwnership.Personal )
                {
                    mergeTemplate.PersonAliasId = this.CurrentPersonAliasId;
                    mergeTemplate.PersonAlias = this.CurrentPersonAlias;
                }
            }

            pnlDetails.Visible = true;
            hfMergeTemplateId.Value = mergeTemplateId.ToString();

            // render UI based on Authorized
            bool readOnly = false;

            nbEditModeMessage.Text = string.Empty;
            if ( mergeTemplate.PersonAliasId.HasValue && mergeTemplate.PersonAlias.PersonId == this.CurrentPersonId )
            {
                // Allow Person to edit their own Merge Templates
            }
            else if ( !IsUserAuthorized( Authorization.EDIT ) )
            {
                readOnly = true;
                nbEditModeMessage.Text = EditModeMessage.ReadOnlyEditActionNotAllowed( MergeTemplate.FriendlyTypeName );
            }

            if ( readOnly )
            {
                btnEdit.Visible = false;
                btnDelete.Visible = false;
                ShowReadonlyDetails( mergeTemplate );
            }
            else
            {
                btnEdit.Visible = true;
                string errorMessage = string.Empty;
                btnDelete.Visible = mergeTemplateService.CanDelete( mergeTemplate, out errorMessage );
                if ( mergeTemplate.Id > 0 )
                {
                    ShowReadonlyDetails( mergeTemplate );
                }
                else
                {
                    ShowEditDetails( mergeTemplate );
                }
            }
        }
Exemple #23
0
        /// <summary>
        /// Handles the Click event of the btnSave control.
        /// </summary>
        /// <param name="sender">The source of the event.</param>
        /// <param name="e">The <see cref="EventArgs"/> instance containing the event data.</param>
        protected void btnSave_Click( object sender, EventArgs e )
        {
            MergeTemplate mergeTemplate;
            var rockContext = new RockContext();
            MergeTemplateService mergeTemplateService = new MergeTemplateService( rockContext );

            int mergeTemplateId = hfMergeTemplateId.Value.AsInteger();
            int? origBinaryFileId = null;

            if ( mergeTemplateId == 0 )
            {
                mergeTemplate = new MergeTemplate();
                mergeTemplateService.Add( mergeTemplate );
            }
            else
            {
                mergeTemplate = mergeTemplateService.Get( mergeTemplateId );
                origBinaryFileId = mergeTemplate.TemplateBinaryFileId;
            }

            mergeTemplate.Name = tbName.Text;
            mergeTemplate.Description = tbDescription.Text;
            mergeTemplate.MergeTemplateTypeEntityTypeId = ddlMergeTemplateType.SelectedValue.AsInteger();
            mergeTemplate.TemplateBinaryFileId = fuTemplateBinaryFile.BinaryFileId ?? 0;
            mergeTemplate.PersonAliasId = ppPerson.PersonAliasId;
            mergeTemplate.CategoryId = cpCategory.SelectedValue.AsInteger();

            int personalMergeTemplateCategoryId = CategoryCache.Read( Rock.SystemGuid.Category.PERSONAL_MERGE_TEMPLATE.AsGuid() ).Id;
            if ( mergeTemplate.PersonAliasId.HasValue )
            {
                if ( mergeTemplate.CategoryId == 0 )
                {
                    // if the category picker isn't shown and/or the category isn't selected, and it's a personal filter...
                    mergeTemplate.CategoryId = personalMergeTemplateCategoryId;
                }

                // ensure Personal templates are only in the Personal merge template category
                if ( mergeTemplate.CategoryId != personalMergeTemplateCategoryId )
                {
                    // prohibit personal templates from being in something other than the Personal category
                    cpCategory.Visible = true;
                    cpCategory.ShowErrorMessage( "Personal Merge Templates must be in Personal category" );
                }
            }
            else
            {
                if ( mergeTemplate.CategoryId == personalMergeTemplateCategoryId )
                {
                    // prohibit global templates from being in Personal category
                    cpCategory.ShowErrorMessage( "Person is required when using the Personal category" );
                }
            }

            if ( !mergeTemplate.IsValid || !Page.IsValid )
            {
                // Controls will render the error messages
                return;
            }

            BinaryFileService binaryFileService = new BinaryFileService( rockContext );
            if ( origBinaryFileId.HasValue && origBinaryFileId.Value != mergeTemplate.TemplateBinaryFileId )
            {
                // if a new the binaryFile was uploaded, mark the old one as Temporary so that it gets cleaned up
                var oldBinaryFile = binaryFileService.Get( origBinaryFileId.Value );
                if ( oldBinaryFile != null && !oldBinaryFile.IsTemporary )
                {
                    oldBinaryFile.IsTemporary = true;
                }
            }

            // ensure the IsTemporary is set to false on binaryFile associated with this MergeTemplate
            var binaryFile = binaryFileService.Get( mergeTemplate.TemplateBinaryFileId );
            if ( binaryFile != null && binaryFile.IsTemporary )
            {
                binaryFile.IsTemporary = false;
            }

            rockContext.SaveChanges();

            var qryParams = new Dictionary<string, string>();
            qryParams["ExpandedIds"] = PageParameter( "ExpandedIds" );
            qryParams["MergeTemplateId"] = mergeTemplate.Id.ToString();
            NavigateToPage( RockPage.Guid, qryParams );
        }
Exemple #24
0
        /// <summary>
        /// Shows the readonly details.
        /// </summary>
        /// <param name="mergeTemplate">The merge template.</param>
        private void ShowReadonlyDetails( MergeTemplate mergeTemplate )
        {
            SetEditMode( false );
            hfMergeTemplateId.SetValue( mergeTemplate.Id );
            lReadOnlyTitle.Text = mergeTemplate.Name.FormatAsHtmlTitle();

            DescriptionList descriptionListCol1 = new DescriptionList()
                .Add( "Template File", string.Format( "<a href='{0}'>{1}</a>", mergeTemplate.TemplateBinaryFile.Url, mergeTemplate.TemplateBinaryFile.FileName ) )
                .Add( "Description", mergeTemplate.Description ?? string.Empty )
                .Add( "Type", mergeTemplate.MergeTemplateTypeEntityType );

            DescriptionList descriptionListCol2 = new DescriptionList()
                .Add( "Category", mergeTemplate.Category != null ? mergeTemplate.Category.Name : string.Empty )
                .Add( "Person", mergeTemplate.PersonAlias, false );

            lblMainDetailsCol1.Text = descriptionListCol1.Html;
            lblMainDetailsCol2.Text = descriptionListCol2.Html;
        }
        public async Task <RunMergeTemplateProgress> RunMergeTemplateAsync(
            MergeTemplate mergeTemplate,
            Action <RunMergeTemplateProgress> progressReporter = null,
            CancellationToken cancellationToken = default(CancellationToken))
        {
            if (mergeTemplate == null)
            {
                throw new ArgumentNullException(nameof(mergeTemplate));
            }
            var emailMergeTemplate = mergeTemplate as EmailMergeTemplate;

            if (emailMergeTemplate == null)
            {
                throw new InvalidOperationException("Currently only mergeTemplates of type Email are supported.");
            }
            if (emailMergeTemplate.EmailTemplate == null)
            {
                throw new InvalidOperationException("MergeTemplate.EmailTemplate cannot ben null");
            }

            string range     = mergeTemplate.SheetName;
            var    dataRange = await _sheetsService.GetDataRangeAsync(
                mergeTemplate.SpreadSheetId, mergeTemplate.SheetName);

            if (mergeTemplate.HeaderRowNumber > 1)
            {
                // we'll define a custom range
                range = new A1Notation(mergeTemplate.SheetName,
                                       dataRange.StartColumn,
                                       mergeTemplate.HeaderRowNumber,
                                       dataRange.EndColumn,
                                       dataRange.EndRow).ToString();
            }

            if (!dataRange.EndRow.HasValue)
            {
                throw new InvalidOperationException($"Could not retrieve the number of rows in sheet {mergeTemplate.SheetName}");
            }

            var progress = new RunMergeTemplateProgress(
                dataRange.EndRow.Value - (dataRange.StartRow ?? 1));
            await _sheetsService.GetValuesAsDictionaryDataPump(mergeTemplate.SpreadSheetId,
                                                               range, async values =>
            {
                if (!ShouldProcess(mergeTemplate, values))
                {
                    progress.AddSkipped();
                    return;
                }

                try
                {
                    await ProcessMergeTemplateAsync(emailMergeTemplate.EmailTemplate, values);
                    progress.AddProcessed();
                }
                catch (Exception err)
                {
                    _logger.Error(err, "Error processing merge template");
                    progress.AddError();
                }
                finally
                {
                    progressReporter?.Invoke(progress);
                }
            });

            return(progress);
        }
Exemple #26
0
        /// <summary>
        /// Shows the edit details.
        /// </summary>
        /// <param name="mergeTemplate">The merge template.</param>
        public void ShowEditDetails( MergeTemplate mergeTemplate )
        {
            if ( mergeTemplate.Id > 0 )
            {
                lActionTitle.Text = ActionTitle.Edit( mergeTemplate.ToString() ).FormatAsHtmlTitle();
            }
            else
            {
                lActionTitle.Text = ActionTitle.Add( MergeTemplate.FriendlyTypeName ).FormatAsHtmlTitle();
            }

            SetEditMode( true );

            var mergeTemplateOwnership = this.GetAttributeValue( "MergeTemplatesOwnership" ).ConvertToEnum<MergeTemplateOwnership>( MergeTemplateOwnership.Global );
            if ( this.IsUserAuthorized( Authorization.EDIT ) )
            {
                // If Authorized to EDIT, owner should be able to be changed, or converted to Global
                ppPerson.Visible = true;
                ppPerson.Required = false;
                cpCategory.Visible = true;
                cpCategory.ExcludedCategoryIds = string.Empty;
            }
            else if ( mergeTemplateOwnership == MergeTemplateOwnership.Global )
            {
                ppPerson.Visible = false;
                ppPerson.Required = false;
                cpCategory.Visible = true;
                cpCategory.ExcludedCategoryIds = CategoryCache.Read( Rock.SystemGuid.Category.PERSONAL_MERGE_TEMPLATE.AsGuid() ).Id.ToString();
            }
            else if ( mergeTemplateOwnership == MergeTemplateOwnership.Personal )
            {
                // if ONLY personal merge templates are permitted, hide the category since it'll always be saved in the personal category
                cpCategory.Visible = false;

                // merge template should be only for the current person, so hide the person picker
                ppPerson.Visible = false;

                // it is required, but not shown..
                ppPerson.Required = false;
            }
            else if ( mergeTemplateOwnership == MergeTemplateOwnership.PersonalAndGlobal )
            {
                ppPerson.Visible = true;
                ppPerson.Required = false;
                cpCategory.Visible = true;
                cpCategory.ExcludedCategoryIds = string.Empty;
            }

            tbName.Text = mergeTemplate.Name;
            tbDescription.Text = mergeTemplate.Description;

            LoadDropDowns();

            ddlMergeTemplateType.SetValue( mergeTemplate.MergeTemplateTypeEntityTypeId );

            fuTemplateBinaryFile.BinaryFileTypeGuid = Rock.SystemGuid.BinaryFiletype.MERGE_TEMPLATE.AsGuid();
            fuTemplateBinaryFile.BinaryFileId = mergeTemplate.TemplateBinaryFileId;

            cpCategory.AllowMultiSelect = false;
            cpCategory.SetValue( mergeTemplate.CategoryId );
            if ( mergeTemplate.PersonAliasId.HasValue )
            {
                ppPerson.SetValue( mergeTemplate.PersonAlias.Person );
            }
            else
            {
                ppPerson.SetValue( null );
            }
        }
        /// <summary>
        /// Shows the detail.
        /// </summary>
        /// <param name="mergeTemplateId">The merge template identifier.</param>
        /// <param name="parentCategoryId">The parent category identifier.</param>
        public void ShowDetail(int mergeTemplateId, int?parentCategoryId)
        {
            pnlDetails.Visible = false;

            var rockContext          = new RockContext();
            var mergeTemplateService = new MergeTemplateService(rockContext);

            MergeTemplate mergeTemplate = null;

            if (!mergeTemplateId.Equals(0))
            {
                mergeTemplate = mergeTemplateService.Get(mergeTemplateId);
                pdAuditDetails.SetEntity(mergeTemplate, ResolveRockUrl("~"));
            }

            var mergeTemplateOwnership = this.GetAttributeValue("MergeTemplatesOwnership").ConvertToEnum <MergeTemplateOwnership>(MergeTemplateOwnership.Global);

            if (mergeTemplate == null)
            {
                mergeTemplate            = new MergeTemplate();
                mergeTemplate.CategoryId = parentCategoryId ?? 0;

                if (mergeTemplateOwnership == MergeTemplateOwnership.Personal)
                {
                    mergeTemplate.PersonAliasId = this.CurrentPersonAliasId;
                    mergeTemplate.PersonAlias   = this.CurrentPersonAlias;

                    // Don't show security on a personal merge template.
                    btnSecurity.Visible = false;
                }

                // hide the panel drawer that show created and last modified dates
                pdAuditDetails.Visible = false;
            }

            pnlDetails.Visible      = true;
            hfMergeTemplateId.Value = mergeTemplateId.ToString();

            // render UI based on Authorized
            bool readOnly = false;

            nbEditModeMessage.Text = string.Empty;
            if (mergeTemplate.PersonAliasId.HasValue && mergeTemplate.PersonAlias.PersonId == this.CurrentPersonId)
            {
                // Allow Person to edit their own Merge Templates
            }
            else if (!IsUserAuthorized(Authorization.EDIT))
            {
                readOnly = true;
                nbEditModeMessage.Text = EditModeMessage.ReadOnlyEditActionNotAllowed(MergeTemplate.FriendlyTypeName);
            }

            btnSecurity.Visible  = mergeTemplate.IsAuthorized(Authorization.ADMINISTRATE, CurrentPerson);
            btnSecurity.Title    = mergeTemplate.Name;
            btnSecurity.EntityId = mergeTemplate.Id;

            if (readOnly)
            {
                btnEdit.Visible   = false;
                btnDelete.Visible = false;
                ShowReadonlyDetails(mergeTemplate);
            }
            else
            {
                btnEdit.Visible = true;
                string errorMessage = string.Empty;
                btnDelete.Visible = mergeTemplateService.CanDelete(mergeTemplate, out errorMessage);

                if (mergeTemplate.Id > 0)
                {
                    ShowReadonlyDetails(mergeTemplate);
                }
                else
                {
                    ShowEditDetails(mergeTemplate);
                }
            }
        }
        /// <summary>
        /// Shows the edit details.
        /// </summary>
        /// <param name="mergeTemplate">The merge template.</param>
        public void ShowEditDetails(MergeTemplate mergeTemplate)
        {
            if (mergeTemplate.Id > 0)
            {
                lActionTitle.Text = ActionTitle.Edit(mergeTemplate.ToString()).FormatAsHtmlTitle();
            }
            else
            {
                lActionTitle.Text = ActionTitle.Add(MergeTemplate.FriendlyTypeName).FormatAsHtmlTitle();
            }

            SetEditMode(true);

            var mergeTemplateOwnership = this.GetAttributeValue("MergeTemplatesOwnership").ConvertToEnum <MergeTemplateOwnership>(MergeTemplateOwnership.Global);

            if (this.IsUserAuthorized(Authorization.EDIT))
            {
                // If Authorized to EDIT, owner should be able to be changed, or converted to Global
                ppPerson.Visible               = true;
                ppPerson.Required              = false;
                cpCategory.Visible             = true;
                cpCategory.ExcludedCategoryIds = string.Empty;
            }
            else if (mergeTemplateOwnership == MergeTemplateOwnership.Global)
            {
                ppPerson.Visible               = false;
                ppPerson.Required              = false;
                cpCategory.Visible             = true;
                cpCategory.ExcludedCategoryIds = CategoryCache.Get(Rock.SystemGuid.Category.PERSONAL_MERGE_TEMPLATE.AsGuid()).Id.ToString();
            }
            else if (mergeTemplateOwnership == MergeTemplateOwnership.Personal)
            {
                // if ONLY personal merge templates are permitted, hide the category since it'll always be saved in the personal category
                cpCategory.Visible = false;

                // merge template should be only for the current person, so hide the person picker
                ppPerson.Visible = false;

                // it is required, but not shown..
                ppPerson.Required = false;
            }
            else if (mergeTemplateOwnership == MergeTemplateOwnership.PersonalAndGlobal)
            {
                ppPerson.Visible               = true;
                ppPerson.Required              = false;
                cpCategory.Visible             = true;
                cpCategory.ExcludedCategoryIds = string.Empty;
            }

            tbName.Text        = mergeTemplate.Name;
            tbDescription.Text = mergeTemplate.Description;

            LoadDropDowns();

            ddlMergeTemplateType.SetValue(mergeTemplate.MergeTemplateTypeEntityTypeId);

            fuTemplateBinaryFile.BinaryFileTypeGuid = Rock.SystemGuid.BinaryFiletype.MERGE_TEMPLATE.AsGuid();
            fuTemplateBinaryFile.BinaryFileId       = mergeTemplate.TemplateBinaryFileId;

            cpCategory.AllowMultiSelect = false;
            cpCategory.SetValue(mergeTemplate.CategoryId);
            if (mergeTemplate.PersonAliasId.HasValue)
            {
                ppPerson.SetValue(mergeTemplate.PersonAlias.Person);
            }
            else
            {
                ppPerson.SetValue(null);
            }
        }
Exemple #29
0
 /// <summary>
 /// Creates the document.
 /// </summary>
 /// <param name="mergeTemplate">The merge template.</param>
 /// <param name="mergeObjectList">The merge object list.</param>
 /// <param name="globalMergeFields">The global merge fields.</param>
 /// <returns></returns>
 public abstract BinaryFile CreateDocument( MergeTemplate mergeTemplate, List<object> mergeObjectList, Dictionary<string, object> globalMergeFields );
Exemple #30
0
 /// <summary>
 /// Creates the document.
 /// </summary>
 /// <param name="mergeTemplate">The merge template.</param>
 /// <param name="mergeObjectList">The merge object list.</param>
 /// <param name="globalMergeFields">The global merge fields.</param>
 /// <returns></returns>
 public abstract BinaryFile CreateDocument(MergeTemplate mergeTemplate, List <object> mergeObjectList, Dictionary <string, object> globalMergeFields);
 public async Task DeleteMergeTemplateAsync(MergeTemplate mergeTemplate, CancellationToken cancellationToken = default(CancellationToken))
 {
     _mergeTemplateContext.MergeTemplates.Remove(mergeTemplate);
     await _mergeTemplateContext.SaveChangesAsync(cancellationToken);
 }
        /// <summary>
        /// Gets the type of the merge template.
        /// </summary>
        /// <param name="rockContext">The rock context.</param>
        /// <param name="mergeTemplate">The merge template.</param>
        /// <returns></returns>
        private MergeTemplateType GetMergeTemplateType( RockContext rockContext, MergeTemplate mergeTemplate )
        {
            mergeTemplate = new MergeTemplateService( rockContext ).Get( mtPicker.SelectedValue.AsInteger() );
            if ( mergeTemplate == null )
            {
                return null;
            }

            return mergeTemplate.GetMergeTemplateType();
        }
        /// <summary>
        /// Creates the document.
        /// </summary>
        /// <param name="mergeTemplate">The merge template.</param>
        /// <param name="mergeObjectList">The merge object list.</param>
        /// <param name="globalMergeFields">The global merge fields.</param>
        /// <returns></returns>
        public override BinaryFile CreateDocument( MergeTemplate mergeTemplate, List<object> mergeObjectList, Dictionary<string, object> globalMergeFields )
        {
            this.Exceptions = new List<Exception>();
            BinaryFile outputBinaryFile = null;

            var rockContext = new RockContext();
            var binaryFileService = new BinaryFileService( rockContext );

            var templateBinaryFile = binaryFileService.Get( mergeTemplate.TemplateBinaryFileId );
            if ( templateBinaryFile == null )
            {
                return null;
            }

            var sourceTemplateStream = templateBinaryFile.ContentStream;

            // Start by creating a new document with the contents of the Template (so that Styles, etc get included)
            using ( MemoryStream outputDocStream = new MemoryStream() )
            {
                sourceTemplateStream.CopyTo( outputDocStream );
                outputDocStream.Seek( 0, SeekOrigin.Begin );

                // now that we have the outputdoc started, simplify the sourceTemplate
                var simplifiedDoc = WordprocessingDocument.Open( sourceTemplateStream, true );
                MarkupSimplifier.SimplifyMarkup( simplifiedDoc, this.simplifyMarkupSettingsAll );

                //// simplify any nodes that have Lava in it that might not have been caught by the MarkupSimplifier
                //// MarkupSimplifier only merges superfluous runs that are children of a paragraph
                var simplifiedDocX = simplifiedDoc.MainDocumentPart.GetXDocument();
                OpenXmlRegex.Match(
                                simplifiedDocX.Elements(),
                                this.lavaRegEx,
                                ( x, m ) =>
                                {
                                    foreach ( var nonParagraphRunsParent in x.DescendantNodes().OfType<XElement>().Where( a => a.Parent != null && a.Name != null )
                                .Where( a => ( a.Name.LocalName == "r" ) ).Select( a => a.Parent ).Distinct().ToList() )
                                    {
                                        if ( lavaRegEx.IsMatch( nonParagraphRunsParent.Value ) )
                                        {
                                            var tempParent = XElement.Parse( new Paragraph().OuterXml );
                                            tempParent.Add( nonParagraphRunsParent.Nodes() );
                                            tempParent = MarkupSimplifier.MergeAdjacentSuperfluousRuns( tempParent );
                                            nonParagraphRunsParent.ReplaceNodes( tempParent.Nodes() );
                                        }
                                    }
                                } );

                XElement lastLavaNode = simplifiedDocX.DescendantNodes().OfType<XElement>().LastOrDefault( a => lavaRegEx.IsMatch( a.Value ) );

                // ensure there is a { Next } indicator after the last lava node in the template
                if (lastLavaNode != null)
                {
                    var nextRecordMatch = nextRecordRegEx.Match( lastLavaNode.Value );
                    if ( nextRecordMatch == null || !nextRecordMatch.Success )
                    {
                        // if the last lava node doesn't have a { next }, append to the end
                        lastLavaNode.Value += " {% next %} ";
                    }
                    else
                    {
                        if ( !lastLavaNode.Value.EndsWith( nextRecordMatch.Value ) )
                        {
                            // if the last lava node does have a { next }, but there is stuff after it, add it (just in case)
                            lastLavaNode.Value += " {% next %} ";
                        }
                    }
                }

                simplifiedDoc.MainDocumentPart.PutXDocument();

                sourceTemplateStream.Seek( 0, SeekOrigin.Begin );

                bool? allSameParent = null;

                using ( WordprocessingDocument outputDoc = WordprocessingDocument.Open( outputDocStream, true ) )
                {
                    var xdoc = outputDoc.MainDocumentPart.GetXDocument();
                    var outputBodyNode = xdoc.DescendantNodes().OfType<XElement>().FirstOrDefault( a => a.Name.LocalName.Equals( "body" ) );
                    outputBodyNode.RemoveNodes();

                    int recordIndex = 0;
                    int? lastRecordIndex = null;
                    int recordCount = mergeObjectList.Count();
                    while ( recordIndex < recordCount )
                    {
                        if ( lastRecordIndex.HasValue && lastRecordIndex == recordIndex )
                        {
                            // something went wrong, so throw to avoid spinning infinately
                            throw new Exception( "Unexpected unchanged recordIndex" );
                        }

                        lastRecordIndex = recordIndex;
                        using ( var tempMergeTemplateStream = new MemoryStream() )
                        {
                            sourceTemplateStream.Position = 0;
                            sourceTemplateStream.CopyTo( tempMergeTemplateStream );
                            tempMergeTemplateStream.Position = 0;
                            var tempMergeWordDoc = WordprocessingDocument.Open( tempMergeTemplateStream, true );
                            var tempMergeTemplateX = tempMergeWordDoc.MainDocumentPart.GetXDocument();
                            var tempMergeTemplateBodyNode = tempMergeTemplateX.DescendantNodes().OfType<XElement>().FirstOrDefault( a => a.Name.LocalName.Equals( "body" ) );

                            // find all the Nodes that have a {% next %}.
                            List<XElement> nextIndicatorNodes = new List<XElement>();

                            OpenXmlRegex.Match(
                                tempMergeTemplateX.Elements(),
                                this.nextRecordRegEx,
                                ( x, m ) =>
                                {
                                    nextIndicatorNodes.Add( x );
                                } );

                            allSameParent = allSameParent ?? nextIndicatorNodes.Count > 1 && nextIndicatorNodes.Select( a => a.Parent ).Distinct().Count() == 1;

                            List<XContainer> recordContainerNodes = new List<XContainer>();

                            foreach ( var nextIndicatorNodeParent in nextIndicatorNodes.Select( a => a.Parent ).Where( a => a != null ) )
                            {
                                XContainer recordContainerNode = nextIndicatorNodeParent;
                                if ( !allSameParent.Value )
                                {
                                    // go up the parent nodes until we have more than one "Next" descendent so that we know what to consider our record container
                                    while ( recordContainerNode.Parent != null )
                                    {
                                        if ( this.nextRecordRegEx.Matches( recordContainerNode.Parent.Value ).Count == 1 )
                                        {
                                            // still just the one "next" indicator, so go out another parent
                                            recordContainerNode = recordContainerNode.Parent;
                                        }
                                        else
                                        {
                                            // we went too far up the parents and found multiple "next" children, so use this node as the recordContainerNode
                                            break;
                                        }
                                    }
                                }

                                if ( !recordContainerNodes.Contains( recordContainerNode ) )
                                {
                                    recordContainerNodes.Add( recordContainerNode );
                                }
                            }

                            foreach ( var recordContainerNode in recordContainerNodes )
                            {
                                //// loop thru each of the recordContainerNodes
                                //// If we have more records than nodes, we'll jump out to the outer "while" and append another template and keep going

                                XContainer mergedXRecord;

                                var recordContainerNodeXml = recordContainerNode.ToString( SaveOptions.DisableFormatting | SaveOptions.OmitDuplicateNamespaces ).ReplaceWordChars();

                                if ( recordIndex >= recordCount )
                                {
                                    // out of records, so clear out any remaining template nodes that haven't been merged
                                    string xml = recordContainerNodeXml;
                                    mergedXRecord = XElement.Parse( xml ) as XContainer;
                                    OpenXmlRegex.Replace( mergedXRecord.Nodes().OfType<XElement>(), this.regExDot, string.Empty, ( a, b ) => { return true; } );

                                    recordIndex++;
                                }
                                else
                                {
                                    //// just in case they have shared parent node, or if there is trailing {{ next }} after the last lava
                                    //// on the page, split the XML for each record and reassemble it when done
                                    List<string> xmlChunks = this.nextRecordRegEx.Split( recordContainerNodeXml ).ToList();

                                    string mergedXml = string.Empty;

                                    foreach ( var xml in xmlChunks )
                                    {
                                        if ( xml.HasMergeFields() )
                                        {
                                            if ( recordIndex < recordCount )
                                            {
                                                try
                                                {
                                                    DotLiquid.Hash wordMergeObjects = new DotLiquid.Hash();
                                                    wordMergeObjects.Add( "Row", mergeObjectList[recordIndex] );

                                                    foreach ( var field in globalMergeFields )
                                                    {
                                                        wordMergeObjects.Add( field.Key, field.Value );
                                                    }

                                                    mergedXml += xml.ResolveMergeFields( wordMergeObjects, true, true );
                                                }
                                                catch ( Exception ex )
                                                {
                                                    // if ResolveMergeFields failed, log the exception, then just return the orig xml
                                                    this.Exceptions.Add( ex );
                                                    mergedXml += xml;
                                                }

                                                recordIndex++;
                                            }
                                            else
                                            {
                                                // out of records, so just keep it as the templated xml
                                                mergedXml += xml;
                                            }
                                        }
                                        else
                                        {
                                            mergedXml += xml;
                                        }
                                    }

                                    mergedXRecord = XElement.Parse( mergedXml ) as XContainer;
                                }

                                // remove the orig nodes and replace with merged nodes
                                recordContainerNode.RemoveNodes();
                                recordContainerNode.Add( mergedXRecord.Nodes().OfType<XElement>() );

                                var mergedRecordContainer = XElement.Parse( recordContainerNode.ToString( SaveOptions.DisableFormatting ) );
                                if ( recordContainerNode.Parent != null )
                                {
                                    // the recordContainerNode is some child/descendent of <body>
                                    recordContainerNode.ReplaceWith( mergedRecordContainer );
                                }
                                else
                                {
                                    // the recordContainerNode is the <body>
                                    recordContainerNode.RemoveNodes();
                                    recordContainerNode.Add( mergedRecordContainer.Nodes() );

                                    if ( recordIndex < recordCount )
                                    {
                                        // add page break
                                        var pageBreakXml = new Paragraph( new Run( new Break() { Type = BreakValues.Page } ) ).OuterXml;
                                        var pageBreak = XElement.Parse( pageBreakXml, LoadOptions.None );
                                        var lastParagraph = recordContainerNode.Nodes().OfType<XElement>().Where( a => a.Name.LocalName == "p" ).LastOrDefault();
                                        if ( lastParagraph != null )
                                        {
                                            lastParagraph.AddAfterSelf( pageBreak );
                                        }
                                    }
                                }
                            }

                            outputBodyNode.Add( tempMergeTemplateBodyNode.Nodes() );
                        }
                    }

                    // remove all the 'next' delimiters
                    OpenXmlRegex.Replace( outputBodyNode.Nodes().OfType<XElement>(), this.nextRecordRegEx, string.Empty, ( xx, mm ) => { return true; } );

                    // remove all but the last SectionProperties element (there should only be one per section (body))
                    var sectPrItems = outputBodyNode.Nodes().OfType<XElement>().Where( a => a.Name.LocalName == "sectPr" );
                    foreach ( var extra in sectPrItems.Where( a => a != sectPrItems.Last() ).ToList() )
                    {
                        extra.Remove();
                    }

                    // renumber all the ids to make sure they are unique
                    var idAttrs = xdoc.DescendantNodes().OfType<XElement>().Where( a => a.HasAttributes ).Select( a => a.Attribute( "id" ) ).Where( s => s != null );
                    int lastId = 1;
                    foreach ( var attr in idAttrs )
                    {
                        attr.Value = lastId.ToString();
                        lastId++;
                    }

                    // remove the last pagebreak
                    MarkupSimplifier.SimplifyMarkup( outputDoc, new SimplifyMarkupSettings { RemoveLastRenderedPageBreak = true } );

                    // If you want to see validation errors
                    /*
                    var validator = new OpenXmlValidator();
                    var errors = validator.Validate( outputDoc ).ToList();
                    */
                }

                outputBinaryFile = new BinaryFile();
                outputBinaryFile.IsTemporary = true;
                outputBinaryFile.ContentStream = outputDocStream;
                outputBinaryFile.FileName = "MergeTemplateOutput" + Path.GetExtension( templateBinaryFile.FileName );
                outputBinaryFile.MimeType = templateBinaryFile.MimeType;
                outputBinaryFile.BinaryFileTypeId = new BinaryFileTypeService( rockContext ).Get( Rock.SystemGuid.BinaryFiletype.DEFAULT.AsGuid() ).Id;

                binaryFileService.Add( outputBinaryFile );
                rockContext.SaveChanges();
            }

            return outputBinaryFile;
        }
Exemple #34
0
        /// <summary>
        /// Creates the document.
        /// </summary>
        /// <param name="mergeTemplate">The merge template.</param>
        /// <param name="mergeObjectList">The merge object list.</param>
        /// <param name="globalMergeFields">The global merge fields.</param>
        /// <returns></returns>
        public override BinaryFile CreateDocument(MergeTemplate mergeTemplate, List <object> mergeObjectList, Dictionary <string, object> globalMergeFields)
        {
            this.Exceptions = new List <Exception>();
            BinaryFile outputBinaryFile = null;

            var rockContext       = new RockContext();
            var binaryFileService = new BinaryFileService(rockContext);

            var templateBinaryFile = binaryFileService.Get(mergeTemplate.TemplateBinaryFileId);

            if (templateBinaryFile == null)
            {
                return(null);
            }

            // Start by creating a new document with the contents of the Template (so that Styles, etc get included)
            XDocument sourceTemplateDocX;

            // NOTE: On using multiple IDisposable, see https://stackoverflow.com/a/12603126/1755417 and https://docs.microsoft.com/en-us/dotnet/csharp/language-reference/keywords/using-statement
            using (MemoryStream sourceTemplateStream = new MemoryStream(), outputDocStream = new MemoryStream())
            {
                templateBinaryFile.ContentStream.CopyTo(outputDocStream);
                outputDocStream.Seek(0, SeekOrigin.Begin);

                // now that we have the outputdoc started, simplify the sourceTemplate
                templateBinaryFile.ContentStream.CopyTo(sourceTemplateStream);
                sourceTemplateStream.Seek(0, SeekOrigin.Begin);
                var simplifiedDoc = WordprocessingDocument.Open(sourceTemplateStream, true);
                MarkupSimplifier.SimplifyMarkup(simplifiedDoc, this.simplifyMarkupSettingsAll);

                //// simplify any nodes that have Lava in it that might not have been caught by the MarkupSimplifier
                //// MarkupSimplifier only merges superfluous runs that are children of a paragraph
                sourceTemplateDocX = simplifiedDoc.MainDocumentPart.GetXDocument();
                OpenXmlRegex.Match(
                    sourceTemplateDocX.Elements(),
                    this.lavaRegEx,
                    (x, m) =>
                {
                    foreach (var nonParagraphRunsParent in x.DescendantNodes().OfType <XElement>().Where(a => a.Parent != null && a.Name != null)
                             .Where(a => (a.Name.LocalName == "r")).Select(a => a.Parent).Distinct().ToList())
                    {
                        if (lavaRegEx.IsMatch(nonParagraphRunsParent.Value))
                        {
                            var tempParent = XElement.Parse(new Paragraph().OuterXml);
                            tempParent.Add(nonParagraphRunsParent.Nodes());
                            tempParent = MarkupSimplifier.MergeAdjacentSuperfluousRuns(tempParent);
                            nonParagraphRunsParent.ReplaceNodes(tempParent.Nodes());
                        }
                    }
                });

                XElement lastLavaNode = sourceTemplateDocX.DescendantNodes().OfType <XElement>().LastOrDefault(a => lavaRegEx.IsMatch(a.Value));

                // ensure there is a { Next } indicator after the last lava node in the template
                if (lastLavaNode != null)
                {
                    var nextRecordMatch = nextRecordRegEx.Match(lastLavaNode.Value);
                    if (nextRecordMatch == null || !nextRecordMatch.Success)
                    {
                        // if the last lava node doesn't have a { next }, append to the end
                        lastLavaNode.Value += " {% next %} ";
                    }
                    else
                    {
                        if (!lastLavaNode.Value.EndsWith(nextRecordMatch.Value))
                        {
                            // if the last lava node does have a { next }, but there is stuff after it, add it (just in case)
                            lastLavaNode.Value += " {% next %} ";
                        }
                    }
                }

                bool?allSameParent = null;

                using (WordprocessingDocument outputDoc = WordprocessingDocument.Open(outputDocStream, true))
                {
                    var xdoc           = outputDoc.MainDocumentPart.GetXDocument();
                    var outputBodyNode = xdoc.DescendantNodes().OfType <XElement>().FirstOrDefault(a => a.Name.LocalName.Equals("body"));
                    outputBodyNode.RemoveNodes();

                    int recordIndex     = 0;
                    int?lastRecordIndex = null;
                    int recordCount     = mergeObjectList.Count();
                    while (recordIndex < recordCount)
                    {
                        if (lastRecordIndex.HasValue && lastRecordIndex == recordIndex)
                        {
                            // something went wrong, so throw to avoid spinning infinitely
                            throw new Exception("Unexpected unchanged recordIndex");
                        }

                        lastRecordIndex = recordIndex;
                        using (var tempMergeTemplateStream = new MemoryStream())
                        {
                            sourceTemplateStream.Position = 0;
                            sourceTemplateStream.CopyTo(tempMergeTemplateStream);
                            tempMergeTemplateStream.Position = 0;
                            var tempMergeTemplateX        = new XDocument(sourceTemplateDocX);
                            var tempMergeTemplateBodyNode = tempMergeTemplateX.DescendantNodes().OfType <XElement>().FirstOrDefault(a => a.Name.LocalName.Equals("body"));

                            // find all the Nodes that have a {% next %}.
                            List <XElement> nextIndicatorNodes = new List <XElement>();

                            OpenXmlRegex.Match(
                                tempMergeTemplateX.Elements(),
                                this.nextRecordRegEx,
                                (x, m) =>
                            {
                                nextIndicatorNodes.Add(x);
                            });

                            allSameParent = allSameParent ?? nextIndicatorNodes.Count > 1 && nextIndicatorNodes.Select(a => a.Parent).Distinct().Count() == 1;

                            List <XContainer> recordContainerNodes = new List <XContainer>();

                            foreach (var nextIndicatorNodeParent in nextIndicatorNodes.Select(a => a.Parent).Where(a => a != null))
                            {
                                XContainer recordContainerNode = nextIndicatorNodeParent;
                                if (!allSameParent.Value)
                                {
                                    // go up the parent nodes until we have more than one "Next" descendent so that we know what to consider our record container
                                    while (recordContainerNode.Parent != null)
                                    {
                                        if (this.nextRecordRegEx.Matches(recordContainerNode.Parent.Value).Count == 1)
                                        {
                                            // still just the one "next" indicator, so go out another parent
                                            recordContainerNode = recordContainerNode.Parent;
                                        }
                                        else
                                        {
                                            // we went too far up the parents and found multiple "next" children, so use this node as the recordContainerNode
                                            break;
                                        }
                                    }
                                }

                                if (!recordContainerNodes.Contains(recordContainerNode))
                                {
                                    recordContainerNodes.Add(recordContainerNode);
                                }
                            }

                            foreach (var recordContainerNode in recordContainerNodes)
                            {
                                //// loop thru each of the recordContainerNodes
                                //// If we have more records than nodes, we'll jump out to the outer "while" and append another template and keep going

                                XContainer mergedXRecord;

                                var recordContainerNodeXml = recordContainerNode.ToString(SaveOptions.DisableFormatting | SaveOptions.OmitDuplicateNamespaces).ReplaceWordChars();

                                if (recordIndex >= recordCount)
                                {
                                    // out of records, so clear out any remaining template nodes that haven't been merged
                                    string xml = recordContainerNodeXml;
                                    mergedXRecord = XElement.Parse(xml) as XContainer;
                                    OpenXmlRegex.Replace(mergedXRecord.Nodes().OfType <XElement>(), this.regExDot, string.Empty, (a, b) => { return(true); });

                                    recordIndex++;
                                }
                                else
                                {
                                    //// just in case they have shared parent node, or if there is trailing {{ next }} after the last lava
                                    //// on the page, split the XML for each record and reassemble it when done
                                    List <string> xmlChunks = this.nextRecordRegEx.Split(recordContainerNodeXml).ToList();

                                    string mergedXml = string.Empty;

                                    foreach (var xml in xmlChunks)
                                    {
                                        bool incRecordIndex = true;
                                        if (lavaRegEx.IsMatch(xml))
                                        {
                                            if (recordIndex < recordCount)
                                            {
                                                try
                                                {
                                                    var wordMergeObjects = new LavaDataDictionary();
                                                    wordMergeObjects.Add("Row", mergeObjectList[recordIndex]);

                                                    foreach (var field in globalMergeFields)
                                                    {
                                                        wordMergeObjects.Add(field.Key, field.Value);
                                                    }

                                                    var resolvedXml = xml.ResolveMergeFields(wordMergeObjects, true, true);
                                                    mergedXml += resolvedXml;
                                                    if (resolvedXml == xml)
                                                    {
                                                        // there weren't any MergeFields after all, so don't move to the next record
                                                        incRecordIndex = false;
                                                    }
                                                }
                                                catch (Exception ex)
                                                {
                                                    // if ResolveMergeFields failed, log the exception, then just return the orig xml
                                                    this.Exceptions.Add(ex);
                                                    mergedXml += xml;
                                                }

                                                if (incRecordIndex)
                                                {
                                                    recordIndex++;
                                                }
                                            }
                                            else
                                            {
                                                // out of records, so put a special '{% next_empty %}' that we can use to clear up unmerged parts of the template
                                                mergedXml += " {% next_empty %} " + xml;
                                            }
                                        }
                                        else
                                        {
                                            mergedXml += xml;
                                        }
                                    }

                                    mergedXRecord = XElement.Parse(mergedXml) as XContainer;
                                }

                                // remove the orig nodes and replace with merged nodes
                                recordContainerNode.RemoveNodes();
                                recordContainerNode.Add(mergedXRecord.Nodes().OfType <XElement>());

                                var mergedRecordContainer = XElement.Parse(recordContainerNode.ToString(SaveOptions.DisableFormatting));
                                if (recordContainerNode.Parent != null)
                                {
                                    // the recordContainerNode is some child/descendent of <body>
                                    recordContainerNode.ReplaceWith(mergedRecordContainer);
                                }
                                else
                                {
                                    // the recordContainerNode is the <body>
                                    recordContainerNode.RemoveNodes();
                                    recordContainerNode.Add(mergedRecordContainer.Nodes());

                                    if (recordIndex < recordCount)
                                    {
                                        // add page break
                                        var pageBreakXml = new Paragraph(new Run(new Break()
                                        {
                                            Type = BreakValues.Page
                                        })).OuterXml;
                                        var pageBreak     = XElement.Parse(pageBreakXml, LoadOptions.None);
                                        var lastParagraph = recordContainerNode.Nodes().OfType <XElement>().Where(a => a.Name.LocalName == "p").LastOrDefault();
                                        if (lastParagraph != null)
                                        {
                                            lastParagraph.AddAfterSelf(pageBreak);

                                            // Add page formatting for the page before the page break.
                                            var lastSectPr = recordContainerNode.Nodes().OfType <XElement>().Where(a => a.Name.LocalName == "sectPr").LastOrDefault();
                                            if (lastSectPr != null)
                                            {
                                                var paragraphPropertiesXml = new Paragraph(new ParagraphProperties(new SectionProperties(lastSectPr.ToString()))).OuterXml;
                                                var paragraphProperties    = XElement.Parse(paragraphPropertiesXml, LoadOptions.None);
                                                pageBreak.AddAfterSelf(paragraphProperties);
                                            }
                                        }
                                    }
                                }
                            }

                            outputBodyNode.Add(tempMergeTemplateBodyNode.Nodes());
                        }
                    }

                    // remove all the 'next' delimiters
                    OpenXmlRegex.Replace(outputBodyNode.Nodes().OfType <XElement>(), this.nextRecordRegEx, string.Empty, (xx, mm) => { return(true); });

                    // find all the 'next_empty' delimiters that we might have added and clear out the content in the paragraph nodes that follow
                    OpenXmlRegex.Match(
                        outputBodyNode.Nodes().OfType <XElement>(),
                        this.nextEmptyRecordRegEx,
                        (xx, mm) =>
                    {
                        var afterSiblings = xx.ElementsAfterSelf().ToList();

                        // get all the paragraph elements after the 'next_empty' node and clear out the content
                        var nodesToClean = afterSiblings.Where(a => a.Name.LocalName == "p").ToList();

                        // if the next_empty node has lava, clean that up too
                        var xxContent = xx.ToString();
                        if (lavaRegEx.IsMatch(xxContent))
                        {
                            nodesToClean.Add(xx);
                        }

                        foreach (var node in nodesToClean)
                        {
                            // remove all child nodes from each paragraph node
                            if (node.HasElements)
                            {
                                node.RemoveNodes();
                            }
                        }
                    });

                    // remove all the 'next_empty' delimiters
                    OpenXmlRegex.Replace(outputBodyNode.Nodes().OfType <XElement>(), this.nextEmptyRecordRegEx, string.Empty, (xx, mm) => { return(true); });

                    // remove all but the last SectionProperties element (there should only be one per section (body))
                    var sectPrItems = outputBodyNode.Nodes().OfType <XElement>().Where(a => a.Name.LocalName == "sectPr");
                    foreach (var extra in sectPrItems.Where(a => a != sectPrItems.Last()).ToList())
                    {
                        extra.Remove();
                    }

                    // renumber all the ids to make sure they are unique
                    var idAttrs = xdoc.DescendantNodes().OfType <XElement>().Where(a => a.HasAttributes).Select(a => a.Attribute("id")).Where(s => s != null);
                    int lastId  = 1;
                    foreach (var attr in idAttrs)
                    {
                        attr.Value = lastId.ToString();
                        lastId++;
                    }

                    LavaDataDictionary globalMergeHash = new LavaDataDictionary();
                    foreach (var field in globalMergeFields)
                    {
                        globalMergeHash.Add(field.Key, field.Value);
                    }

                    HeaderFooterGlobalMerge(outputDoc, globalMergeHash);

                    // sweep thru any remaining un-merged body parts for any Lava having to do with Global merge fields
                    foreach (var bodyTextPart in outputDoc.MainDocumentPart.Document.Body.Descendants <Text>())
                    {
                        string nodeText = bodyTextPart.Text.ReplaceWordChars();
                        if (lavaRegEx.IsMatch(nodeText))
                        {
                            bodyTextPart.Text = nodeText.ResolveMergeFields(globalMergeHash, true, true);
                        }
                    }

                    // remove the last pagebreak
                    MarkupSimplifier.SimplifyMarkup(outputDoc, new SimplifyMarkupSettings {
                        RemoveLastRenderedPageBreak = true
                    });

                    // If you want to see validation errors

                    /*
                     * var validator = new OpenXmlValidator();
                     * var errors = validator.Validate( outputDoc ).ToList();
                     */
                }

                outputBinaryFile                  = new BinaryFile();
                outputBinaryFile.IsTemporary      = true;
                outputBinaryFile.ContentStream    = outputDocStream;
                outputBinaryFile.FileName         = "MergeTemplateOutput" + Path.GetExtension(templateBinaryFile.FileName);
                outputBinaryFile.MimeType         = templateBinaryFile.MimeType;
                outputBinaryFile.BinaryFileTypeId = new BinaryFileTypeService(rockContext).Get(Rock.SystemGuid.BinaryFiletype.DEFAULT.AsGuid()).Id;

                binaryFileService.Add(outputBinaryFile);
                rockContext.SaveChanges();
            }

            return(outputBinaryFile);
        }
Exemple #35
0
        /// <summary>
        /// Creates the document.
        /// </summary>
        /// <param name="mergeTemplate">The merge template.</param>
        /// <param name="mergeObjectList">The list of merge objects (rows).</param>
        /// <param name="globalMergeFields">The global merge fields.</param>
        /// <returns></returns>
        public override BinaryFile CreateDocument(MergeTemplate mergeTemplate, List <object> mergeObjectList, Dictionary <string, object> globalMergeFields)
        {
            this.Exceptions = new List <Exception>();

            var rockContext = new RockContext();

            var binaryFileTypeService = new BinaryFileTypeService(rockContext);
            int defaultFileTypeId     = binaryFileTypeService.Get(Rock.SystemGuid.BinaryFiletype.DEFAULT.AsGuid()).Id;

            var binaryFileService = new BinaryFileService(rockContext);
            var outputBinaryFile  = new BinaryFile();

            int recordCount = mergeObjectList.Count();

            IDictionary <string, object> template;
            var results = new List <object>();

            // Load the template file
            BinaryFile templateBinaryFile = binaryFileService.Get(mergeTemplate.TemplateBinaryFileId);

            if (templateBinaryFile == null)
            {
                return(null);
            }

            using (var templateStream = new StreamReader(templateBinaryFile.ContentStream))
                using (var csv = new CsvReader(templateStream))
                {
                    // Read the headers
                    csv.Read();
                    csv.ReadHeader();

                    // Read the first row of values
                    csv.Read();
                    template = csv.GetRecord <dynamic>();
                }

            // Merge each row
            for (int recordIndex = 0; recordIndex < recordCount; recordIndex++)
            {
                var result       = new ExpandoObject() as IDictionary <string, object>;
                var mergeObjects = GetMergeObjects(mergeObjectList, globalMergeFields, recordIndex);

                // Merge each field in the row
                foreach (var field in template)
                {
                    result.Add(field.Key, field.Value.ToString().ResolveMergeFields(mergeObjects));
                }

                results.Add(result);
            }

            using (var outputStream = new MemoryStream())
                using (var outputWriter = new StreamWriter(outputStream))
                    using (var csv = new CsvWriter(outputWriter))
                    {
                        csv.WriteRecords(results);

                        outputWriter.Flush();

                        outputBinaryFile.IsTemporary      = true;
                        outputBinaryFile.ContentStream    = outputStream;
                        outputBinaryFile.FileName         = "MergeTemplateOutput" + Path.GetExtension(templateBinaryFile.FileName);
                        outputBinaryFile.MimeType         = templateBinaryFile.MimeType;
                        outputBinaryFile.BinaryFileTypeId = defaultFileTypeId;

                        binaryFileService.Add(outputBinaryFile);
                        rockContext.SaveChanges();
                    }

            return(outputBinaryFile);
        }
        /// <summary>
        /// Shows the detail.
        /// </summary>
        /// <param name="mergeTemplateId">The merge template identifier.</param>
        /// <param name="parentCategoryId">The parent category identifier.</param>
        public void ShowDetail(int mergeTemplateId, int?parentCategoryId)
        {
            pnlDetails.Visible = false;

            var rockContext          = new RockContext();
            var mergeTemplateService = new MergeTemplateService(rockContext);

            MergeTemplate mergeTemplate = null;

            if (!mergeTemplateId.Equals(0))
            {
                mergeTemplate = mergeTemplateService.Get(mergeTemplateId);
            }

            var mergeTemplateOwnership = this.GetAttributeValue("MergeTemplatesOwnership").ConvertToEnum <MergeTemplateOwnership>(MergeTemplateOwnership.Global);

            if (mergeTemplate == null)
            {
                mergeTemplate            = new MergeTemplate();
                mergeTemplate.CategoryId = parentCategoryId ?? 0;

                if (mergeTemplateOwnership == MergeTemplateOwnership.Personal)
                {
                    mergeTemplate.PersonAliasId = this.CurrentPersonAliasId;
                    mergeTemplate.PersonAlias   = this.CurrentPersonAlias;
                }
            }

            pnlDetails.Visible      = true;
            hfMergeTemplateId.Value = mergeTemplateId.ToString();

            // render UI based on Authorized
            bool readOnly = false;

            nbEditModeMessage.Text = string.Empty;
            if (mergeTemplate.PersonAliasId.HasValue && mergeTemplate.PersonAlias.PersonId == this.CurrentPersonId)
            {
                // Allow Person to edit their own Merge Templates
            }
            else if (!IsUserAuthorized(Authorization.EDIT))
            {
                readOnly = true;
                nbEditModeMessage.Text = EditModeMessage.ReadOnlyEditActionNotAllowed(MergeTemplate.FriendlyTypeName);
            }

            if (readOnly)
            {
                btnEdit.Visible   = false;
                btnDelete.Visible = false;
                ShowReadonlyDetails(mergeTemplate);
            }
            else
            {
                btnEdit.Visible = true;
                string errorMessage = string.Empty;
                btnDelete.Visible = mergeTemplateService.CanDelete(mergeTemplate, out errorMessage);
                if (mergeTemplate.Id > 0)
                {
                    ShowReadonlyDetails(mergeTemplate);
                }
                else
                {
                    ShowEditDetails(mergeTemplate);
                }
            }
        }
        /// <summary>
        /// Handles the Click event of the btnSave control.
        /// </summary>
        /// <param name="sender">The source of the event.</param>
        /// <param name="e">The <see cref="EventArgs"/> instance containing the event data.</param>
        protected void btnSave_Click(object sender, EventArgs e)
        {
            MergeTemplate        mergeTemplate;
            var                  rockContext          = new RockContext();
            MergeTemplateService mergeTemplateService = new MergeTemplateService(rockContext);

            int mergeTemplateId  = hfMergeTemplateId.Value.AsInteger();
            int?origBinaryFileId = null;

            if (mergeTemplateId == 0)
            {
                mergeTemplate = new MergeTemplate();
                mergeTemplateService.Add(mergeTemplate);
            }
            else
            {
                mergeTemplate    = mergeTemplateService.Get(mergeTemplateId);
                origBinaryFileId = mergeTemplate.TemplateBinaryFileId;
            }

            mergeTemplate.Name        = tbName.Text;
            mergeTemplate.Description = tbDescription.Text;
            mergeTemplate.MergeTemplateTypeEntityTypeId = ddlMergeTemplateType.SelectedValue.AsInteger();
            mergeTemplate.TemplateBinaryFileId          = fuTemplateBinaryFile.BinaryFileId ?? 0;
            mergeTemplate.PersonAliasId = ppPerson.PersonAliasId;
            mergeTemplate.CategoryId    = cpCategory.SelectedValue.AsInteger();

            int personalMergeTemplateCategoryId = CategoryCache.Get(Rock.SystemGuid.Category.PERSONAL_MERGE_TEMPLATE.AsGuid()).Id;

            if (mergeTemplate.PersonAliasId.HasValue)
            {
                if (mergeTemplate.CategoryId == 0)
                {
                    // if the category picker isn't shown and/or the category isn't selected, and it's a personal filter...
                    mergeTemplate.CategoryId = personalMergeTemplateCategoryId;
                }

                // ensure Personal templates are only in the Personal merge template category
                if (mergeTemplate.CategoryId != personalMergeTemplateCategoryId)
                {
                    // prohibit personal templates from being in something other than the Personal category
                    cpCategory.Visible = true;
                    cpCategory.ShowErrorMessage("Personal Merge Templates must be in Personal category");
                }
            }
            else
            {
                if (mergeTemplate.CategoryId == personalMergeTemplateCategoryId)
                {
                    // prohibit global templates from being in Personal category
                    cpCategory.ShowErrorMessage("Person is required when using the Personal category");
                }
            }

            if (!mergeTemplate.IsValid || !Page.IsValid)
            {
                // Controls will render the error messages
                return;
            }

            BinaryFileService binaryFileService = new BinaryFileService(rockContext);

            if (origBinaryFileId.HasValue && origBinaryFileId.Value != mergeTemplate.TemplateBinaryFileId)
            {
                // if a new the binaryFile was uploaded, mark the old one as Temporary so that it gets cleaned up
                var oldBinaryFile = binaryFileService.Get(origBinaryFileId.Value);
                if (oldBinaryFile != null && !oldBinaryFile.IsTemporary)
                {
                    oldBinaryFile.IsTemporary = true;
                }
            }

            // ensure the IsTemporary is set to false on binaryFile associated with this MergeTemplate
            var binaryFile = binaryFileService.Get(mergeTemplate.TemplateBinaryFileId);

            if (binaryFile != null && binaryFile.IsTemporary)
            {
                binaryFile.IsTemporary = false;
            }

            rockContext.SaveChanges();

            var qryParams = new Dictionary <string, string>();

            qryParams["ExpandedIds"]     = PageParameter("ExpandedIds");
            qryParams["MergeTemplateId"] = mergeTemplate.Id.ToString();
            NavigateToPage(RockPage.Guid, qryParams);
        }
        /// <summary>
        /// Shows the readonly details.
        /// </summary>
        /// <param name="mergeTemplate">The merge template.</param>
        private void ShowReadonlyDetails( MergeTemplate mergeTemplate )
        {
            SetEditMode( false );
            hfMergeTemplateId.SetValue( mergeTemplate.Id );
            lReadOnlyTitle.Text = mergeTemplate.Name.FormatAsHtmlTitle();

            var getFileUrl = string.Format(
                "{0}GetFile.ashx?guid={1}",
                System.Web.VirtualPathUtility.ToAbsolute( "~" ),
                mergeTemplate.TemplateBinaryFile != null ? mergeTemplate.TemplateBinaryFile.Guid : (Guid?)null );

            DescriptionList descriptionListCol1 = new DescriptionList()
                .Add( "Template File", string.Format( "<a href='{0}'>{1}</a>", getFileUrl, mergeTemplate.TemplateBinaryFile.FileName ) )
                .Add( "Description", mergeTemplate.Description ?? string.Empty )
                .Add( "Type", mergeTemplate.MergeTemplateTypeEntityType );

            DescriptionList descriptionListCol2 = new DescriptionList()
                .Add( "Category", mergeTemplate.Category != null ? mergeTemplate.Category.Name : string.Empty )
                .Add( "Person", mergeTemplate.PersonAlias, false );

            lblMainDetailsCol1.Text = descriptionListCol1.Html;
            lblMainDetailsCol2.Text = descriptionListCol2.Html;
        }
Exemple #39
0
        /// <summary>
        /// Gets the type of the merge template.
        /// </summary>
        /// <param name="rockContext">The rock context.</param>
        /// <param name="mergeTemplate">The merge template.</param>
        /// <returns></returns>
        private MergeTemplateType GetMergeTemplateType( RockContext rockContext, MergeTemplate mergeTemplate )
        {
            mergeTemplate = new MergeTemplateService( rockContext ).Get( mtPicker.SelectedValue.AsInteger() );
            if ( mergeTemplate == null )
            {
                return null;
            }

            var mergeTemplateTypeEntityType = EntityTypeCache.Read( mergeTemplate.MergeTemplateTypeEntityTypeId );
            if ( mergeTemplateTypeEntityType == null )
            {
                return null;
            }

            return MergeTemplateTypeContainer.GetComponent( mergeTemplateTypeEntityType.Name );
        }