/// <summary> /// Handles the Click event of the DeleteConnectionOpportunity control. /// </summary> /// <param name="sender">The source of the event.</param> /// <param name="e">The <see cref="Rock.Web.UI.Controls.RowEventArgs" /> instance containing the event data.</param> protected void DeleteConnectionOpportunity_Click(object sender, Rock.Web.UI.Controls.RowEventArgs e) { using (RockContext rockContext = new RockContext()) { ConnectionOpportunityService connectionOpportunityService = new ConnectionOpportunityService(rockContext); ConnectionOpportunity connectionOpportunity = connectionOpportunityService.Get(e.RowKeyId); if (connectionOpportunity != null) { if (_canEdit) { string errorMessage; if (!connectionOpportunityService.CanDelete(connectionOpportunity, out errorMessage)) { mdGridWarning.Show(errorMessage, ModalAlertType.Information); return; } int connectionTypeId = connectionOpportunity.ConnectionTypeId; connectionOpportunityService.Delete(connectionOpportunity); rockContext.SaveChanges(); ConnectionWorkflowService.FlushCachedTriggers(); } else { mdGridWarning.Show("You are not authorized to delete this calendar item", ModalAlertType.Warning); } } } BindConnectionOpportunitiesGrid(); }
/// <summary> /// Handles the Edit event of the gConnectionOpportunities 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 gConnectionOpportunities_Edit(object sender, RowEventArgs e) { using (RockContext rockContext = new RockContext()) { ConnectionOpportunityService connectionOpportunityService = new ConnectionOpportunityService(rockContext); ConnectionOpportunity connectionOpportunity = connectionOpportunityService.Get(e.RowKeyId); if (connectionOpportunity != null) { NavigateToLinkedPage("DetailPage", "ConnectionOpportunityId", connectionOpportunity.Id, "ConnectionTypeId", _connectionType.Id); } } }
/// <summary> /// Get the entity (group or connection) for this signup /// </summary> /// <param name="context"></param> /// <returns></returns> public virtual IModel Entity(RockContext context = null) { if (context == null) { context = new RockContext(); } if (EntityTypeGuid == Rock.SystemGuid.EntityType.CONNECTION_OPPORTUNITY.AsGuid()) { ConnectionOpportunityService connectionOpportunityService = new ConnectionOpportunityService(context); return(connectionOpportunityService.Get(EntityGuid)); } if (EntityTypeGuid == Rock.SystemGuid.EntityType.GROUP.AsGuid()) { GroupService groupService = new GroupService(context); return(groupService.Get(EntityGuid)); } return(null); }
/// <summary> /// Assigns the connection requests from the SelectedCampaign's entity set. /// </summary> /// <param name="rockContext">The rock context.</param> /// <param name="selectedCampaignItem">The selected campaign item.</param> /// <param name="numberOfRequestsRemaining">The number of requests remaining.</param> /// <param name="connectorPerson">The connector person.</param> private static void AssignConnectionRequestsFromEntitySet(RockContext rockContext, CampaignItem selectedCampaignItem, ref int numberOfRequestsRemaining, Person connectorPerson) { var opportunityService = new ConnectionOpportunityService(rockContext); ConnectionOpportunity opportunity = opportunityService.Get(selectedCampaignItem.OpportunityGuid); if (opportunity == null || !opportunity.IsActive) { return; } int?defaultStatusId = opportunity.ConnectionType.ConnectionStatuses .Where(s => s.IsDefault) .Select(s => ( int? )s.Id) .FirstOrDefault(); // If opportunity doesn't have a default status, something is wrong if (defaultStatusId == null) { return; } var connectorCampusIds = GetConnectorCampusIds(selectedCampaignItem, connectorPerson); var connectionRequestService = new ConnectionRequestService(rockContext); var connectionRequestActivityService = new ConnectionRequestActivityService(rockContext); // get previous connections for the connector that have the same campus of the connector, or if the person's campus or connector person's campus is null var previousConnectedPersonIdsForCurrentPerson = connectionRequestService.Queryable() .Where(a => a.ConnectionOpportunityId == opportunity.Id) .Where(a => a.ConnectorPersonAlias.PersonId == connectorPerson.Id) .Where(a => (a.CampusId == null) || connectorCampusIds.Any(connectorCampusId => connectorCampusId == null || a.CampusId.Value == connectorCampusId)) .Select(a => a.PersonAlias.PersonId).Distinct().ToList(); var entitySetId = CampaignConnectionHelper.GetEntitySet(selectedCampaignItem); var entitySetItemService = new EntitySetItemService(rockContext); var entitySetItemList = entitySetItemService.Queryable().Where(a => a.EntitySetId == entitySetId).OrderBy(a => a.Order).Select(a => new { PersonId = a.EntityId, EntityItemOrder = a.Order }).ToList(); if (selectedCampaignItem.PreferPreviousConnector) { // sort them by any where the current person was assigned to this person before entitySetItemList = entitySetItemList .OrderBy(a => previousConnectedPersonIdsForCurrentPerson.Any(x => x == a.PersonId)) .ThenBy(a => a.EntityItemOrder).ToList(); } else { entitySetItemList = entitySetItemList.OrderBy(a => a.EntityItemOrder).ToList(); } var personService = new PersonService(rockContext); // get the last connection datetime. var lastConnectionDateTime = RockDateTime.Now.AddDays(-selectedCampaignItem.DaysBetweenConnection); // if DaysBetweenConnection is 0 then check for connection request for any time period. if (selectedCampaignItem.DaysBetweenConnection == default(int)) { lastConnectionDateTime = DateTime.MinValue; } foreach (var entitySetItem in entitySetItemList) { var entitySetPerson = personService.Get(entitySetItem.PersonId); if (entitySetPerson == null) { continue; } var entitySetPersonPrimaryCampusId = entitySetPerson.PrimaryCampusId; bool validCampus = IsValidCampus(connectorCampusIds, entitySetPersonPrimaryCampusId); if (!validCampus) { continue; } // double check that they haven't already been added bool personAlreadyHasConnectionRequest = PersonAlreadyHasConnectionRequest(opportunity.Id, rockContext, lastConnectionDateTime, entitySetPerson.Id); if (personAlreadyHasConnectionRequest) { continue; } var connectionRequest = new ConnectionRequest(); connectionRequest.ConnectionOpportunityId = opportunity.Id; /* * 3/30/2020 - NA * * When setting the connection request's Requester, we have to use the PrimaryAlias * to set the connectionRequest.PersonAlias property because the ConnectionRequestChangeTransaction * https://github.com/SparkabilityGroup/Rock/blob/a556a9285b7fdfe5594441286242f4feaa5847f2/Rock/Transactions/ConnectionRequestChangeTransaction.cs#L123 * (which handles triggered workflows) expects it. Also, it needs to be tracked by * the current rockContext... hence the change from GetAsNoTracking() to just Get() above: * var entitySetPerson = personService.Get( entitySetItem.PersonId ); * * In other words, this will not work correctly: * connectionRequest.PersonAliasId = entitySetPerson.PrimaryAliasId.Value; * * Reason: This plug-in cannot change Rock core assembly code. */ connectionRequest.PersonAlias = entitySetPerson.PrimaryAlias; connectionRequest.ConnectionState = ConnectionState.Active; connectionRequest.ConnectorPersonAliasId = connectorPerson.PrimaryAliasId; connectionRequest.CampusId = entitySetPersonPrimaryCampusId; connectionRequest.ConnectionStatusId = defaultStatusId.Value; if (selectedCampaignItem.RequestCommentsLavaTemplate.IsNotNullOrWhiteSpace()) { var mergeFields = new Dictionary <string, object>(); mergeFields.Add("Person", entitySetPerson); mergeFields.Add("Family", entitySetPerson.GetFamily()); connectionRequest.Comments = selectedCampaignItem.RequestCommentsLavaTemplate.ResolveMergeFields(mergeFields); } connectionRequestService.Add(connectionRequest); var connectionActivityTypeAssignedGuid = Rock.SystemGuid.ConnectionActivityType.ASSIGNED.AsGuid(); int?assignedActivityId = new ConnectionActivityTypeService(rockContext).GetId(connectionActivityTypeAssignedGuid); if (assignedActivityId.HasValue) { var connectionRequestActivity = new ConnectionRequestActivity(); connectionRequestActivity.ConnectionRequest = connectionRequest; connectionRequestActivity.ConnectionOpportunityId = connectionRequest.ConnectionOpportunityId; connectionRequestActivity.ConnectionActivityTypeId = assignedActivityId.Value; connectionRequestActivity.ConnectorPersonAliasId = connectorPerson.PrimaryAliasId; connectionRequestActivityService.Add(connectionRequestActivity); } numberOfRequestsRemaining--; if (numberOfRequestsRemaining <= 0) { break; } } }
/// <summary> /// creates or updates the entity set on the basis of campaign connection configuration, and returns the Id of the entitySetId /// </summary> /// <param name="campaignConfiguration">The campaign configuration.</param> /// <returns></returns> public static int GetEntitySet(CampaignItem campaignConfiguration) { var rockContext = new RockContext(); var connectionOpportunityService = new ConnectionOpportunityService(rockContext); var connectionRequestService = new ConnectionRequestService(rockContext); var entitySetService = new Rock.Model.EntitySetService(rockContext); var connectionOpportunity = connectionOpportunityService.Get(campaignConfiguration.OpportunityGuid); // list of person on the basis of Dataview result and optout group. var filteredPersonIds = GetFilteredPersonIds(campaignConfiguration, rockContext); // get the last connection datetime. var lastConnectionDateTime = RockDateTime.Now.AddDays(-campaignConfiguration.DaysBetweenConnection); // if DaysBetweenConnection is 0 then check for connection request for any time period. if (campaignConfiguration.DaysBetweenConnection == default(int)) { lastConnectionDateTime = DateTime.MinValue; } // list of person that has active connection request OR has connection closed in the past number of days between connection. var excludedPersonIds = connectionRequestService .Queryable() .Where(a => a.ConnectionOpportunityId == connectionOpportunity.Id && ( a.ConnectionState == ConnectionState.Active || a.ConnectionState == ConnectionState.FutureFollowUp || ((a.ConnectionState == ConnectionState.Connected || a.ConnectionState == ConnectionState.Inactive) && a.ModifiedDateTime > lastConnectionDateTime))) .Select(a => a.PersonAlias.PersonId) .ToList(); // filtered list of person removing all the personIds found in excludedPersonIds List filteredPersonIds = filteredPersonIds.Where(a => !excludedPersonIds.Contains(a)).ToList(); // get the ordered list of personIds based on the oldest previous connection request and connection opportunity /* 2020-05-06 MDP * If there are many filteredPersonIds, we'll get a SQL Exception, so let's get *all* the Connected connection Requests first, * and then use C# to filter. */ var orderedLastCompletedRequestForPerson = connectionRequestService .Queryable() .Where(a => a.ConnectionOpportunityId == connectionOpportunity.Id && a.ConnectionState == ConnectionState.Connected) .GroupBy(a => a.PersonAlias.PersonId) .Select(a => new { PersonId = a.Key, LastConnectionDateTime = a.OrderByDescending(b => b.ModifiedDateTime).Select(b => b.ModifiedDateTime).FirstOrDefault() }) .OrderBy(a => a.LastConnectionDateTime) .Select(a => a.PersonId).ToList(); // Use C# to filter persons so we can avoid a SQL Exception orderedLastCompletedRequestForPerson = orderedLastCompletedRequestForPerson.Where(a => filteredPersonIds.Contains(a)).ToList(); var random = new Random(); //// get the final ordered list of personIds based on the oldest previous connection request and //// connection opportunity otherwise order randomly for the person who don't have any previous connection request. var orderedPersonIds = filteredPersonIds .OrderBy(a => { var index = orderedLastCompletedRequestForPerson.IndexOf(a); if (index == -1) { return(random.Next(orderedLastCompletedRequestForPerson.Count, int.MaxValue)); } else { return(index); } }).ToList(); EntitySet entitySet = null; if (campaignConfiguration.EntitySetId != default(int)) { entitySet = entitySetService.Get(campaignConfiguration.EntitySetId); } List <Rock.Model.EntitySetItem> entitySetItems = new List <Rock.Model.EntitySetItem>(); var personEntityTypeId = EntityTypeCache.Get <Rock.Model.Person>().Id; if (entitySet == null || entitySet.EntityTypeId != personEntityTypeId) { entitySet = new Rock.Model.EntitySet(); entitySet.EntityTypeId = personEntityTypeId; entitySet.ExpireDateTime = null; entitySetService.Add(entitySet); } else { var entitySetItemQry = new EntitySetItemService(rockContext) .Queryable().AsNoTracking() .Where(i => i.EntitySetId == entitySet.Id); rockContext.BulkDelete(entitySetItemQry); } // Update the EntitySet name entitySet.Name = campaignConfiguration.Name; var orderIndex = 0; foreach (var personId in orderedPersonIds) { try { var item = new Rock.Model.EntitySetItem(); item.Order = orderIndex++; item.EntityId = personId; entitySetItems.Add(item); } catch { // ignore } } rockContext.SaveChanges(); entitySetItems.ForEach(a => { a.EntitySetId = entitySet.Id; }); rockContext.BulkInsert(entitySetItems); return(entitySet.Id); }
/// <summary> /// Shows the detail. /// </summary> /// <param name="connectionRequestId">The connection request identifier.</param> /// <param name="connectionOpportunityId">The connectionOpportunity id.</param> public void ShowDetail( int connectionRequestId, int? connectionOpportunityId ) { bool editAllowed = UserCanEdit; // autoexpand the person picker if this is an add this.Page.ClientScript.RegisterStartupScript( this.GetType(), "StartupScript", @"Sys.Application.add_load(function () { // if the person picker is empty then open it for quick entry var personPicker = $('.js-authorizedperson'); var currentPerson = personPicker.find('.picker-selectedperson').html(); if (currentPerson != null && currentPerson.length == 0) { $(personPicker).find('a.picker-label').trigger('click'); } });", true ); using ( var rockContext = new RockContext() ) { var connectionOpportunityService = new ConnectionOpportunityService( rockContext ); var connectionRequestService = new ConnectionRequestService( rockContext ); var connectionStatusService = new ConnectionStatusService( rockContext ); ConnectionOpportunity connectionOpportunity = null; ConnectionRequest connectionRequest = null; if ( connectionRequestId > 0 ) { connectionRequest = new ConnectionRequestService( rockContext ).Get( connectionRequestId ); } if ( connectionRequest == null ) { connectionOpportunity = connectionOpportunityService.Get( connectionOpportunityId.Value ); if ( connectionOpportunity != null ) { var connectionStatus = connectionStatusService .Queryable() .Where( s => s.ConnectionTypeId == connectionOpportunity.ConnectionTypeId && s.IsDefault ) .FirstOrDefault(); if ( connectionStatus != null ) { connectionRequest = new ConnectionRequest(); connectionRequest.ConnectionOpportunity = connectionOpportunity; connectionRequest.ConnectionOpportunityId = connectionOpportunity.Id; connectionRequest.ConnectionState = ConnectionState.Active; connectionRequest.ConnectionStatus = connectionStatus; connectionRequest.ConnectionStatusId = connectionStatus.Id; int? campusId = GetUserPreference( CAMPUS_SETTING ).AsIntegerOrNull(); if ( campusId.HasValue ) { connectionRequest.CampusId = campusId.Value; } } } } else { connectionOpportunity = connectionRequest.ConnectionOpportunity; } if ( connectionOpportunity != null && connectionRequest != null ) { hfConnectionOpportunityId.Value = connectionRequest.ConnectionOpportunityId.ToString(); hfConnectionRequestId.Value = connectionRequest.Id.ToString(); lConnectionOpportunityIconHtml.Text = string.Format( "<i class='{0}' ></i>", connectionOpportunity.IconCssClass ); pnlReadDetails.Visible = true; if ( connectionRequest.PersonAlias != null && connectionRequest.PersonAlias.Person != null ) { lTitle.Text = connectionRequest.PersonAlias.Person.FullName.FormatAsHtmlTitle(); } else { lTitle.Text = String.Format( "New {0} Connection Request", connectionOpportunity.Name ); } // Only users that have Edit rights to block, or edit rights to the opportunity if ( !editAllowed ) { editAllowed = connectionRequest.IsAuthorized( Authorization.EDIT, CurrentPerson ); } // Grants edit access to those in the opportunity's connector groups if ( !editAllowed && CurrentPersonId.HasValue ) { // Grant edit access to any of those in a non campus-specific connector group editAllowed = connectionOpportunity.ConnectionOpportunityConnectorGroups .Any( g => !g.CampusId.HasValue && g.ConnectorGroup != null && g.ConnectorGroup.Members.Any( m => m.PersonId == CurrentPersonId ) ); if ( !editAllowed ) { //If this is a new request, grant edit access to any connector group. Otherwise, match the request's campus to the corresponding campus-specific connector group foreach ( var groupCampus in connectionOpportunity .ConnectionOpportunityConnectorGroups .Where( g => ( connectionRequest.Id == 0 || ( connectionRequest.CampusId.HasValue && g.CampusId == connectionRequest.CampusId.Value ) ) && g.ConnectorGroup != null && g.ConnectorGroup.Members.Any( m => m.PersonId == CurrentPersonId ) ) ) { editAllowed = true; break; } } } lbConnect.Visible = editAllowed; lbEdit.Visible = editAllowed; lbTransfer.Visible = editAllowed; gConnectionRequestActivities.IsDeleteEnabled = editAllowed; gConnectionRequestActivities.Actions.ShowAdd = editAllowed; if ( !editAllowed ) { // User is not authorized nbEditModeMessage.Text = EditModeMessage.ReadOnlyEditActionNotAllowed( ConnectionRequest.FriendlyTypeName ); ShowReadonlyDetails( connectionRequest ); } else { nbEditModeMessage.Text = string.Empty; if ( connectionRequest.Id > 0 ) { ShowReadonlyDetails( connectionRequest ); } else { ShowEditDetails( connectionRequest, rockContext ); } } } } }
/// <summary> /// Checks the settings. /// </summary> /// <returns></returns> private bool CheckSettings() { _rockContext = _rockContext ?? new RockContext(); var connectionOpportunityService = new ConnectionOpportunityService(_rockContext); Guid?connectionOpportunityGuid = GetAttributeValue("ConnectionOpportunity").AsGuidOrNull(); if (connectionOpportunityGuid.HasValue) { _connectionOpportunity = connectionOpportunityService.Get(connectionOpportunityGuid.Value); } if (_connectionOpportunity == null) { connectionOpportunityGuid = PageParameter("ConnectionOpportunityGuid").AsGuidOrNull(); if (connectionOpportunityGuid.HasValue) { _connectionOpportunity = connectionOpportunityService.Get(connectionOpportunityGuid.Value); } } if (_connectionOpportunity == null) { int?connectionOpportunityId = PageParameter("ConnectionOpportunityId").AsIntegerOrNull(); if (connectionOpportunityId.HasValue) { _connectionOpportunity = connectionOpportunityService.Get(connectionOpportunityId.Value); } } if (_connectionOpportunity == null) { nbNotice.Heading = "Missing Connection Opportunity Setting"; nbNotice.Text = "<p>Please edit the block settings. This block requires a valid Connection Opportunity setting.</p>"; return(false); } _dvcConnectionStatus = DefinedValueCache.Get(GetAttributeValue("ConnectionStatus").AsGuid()); if (_dvcConnectionStatus == null) { nbNotice.Heading = "Invalid Connection Status"; nbNotice.Text = "<p>The selected Connection Status setting does not exist.</p>"; return(false); } _dvcChildConnectionStatus = DefinedValueCache.Get(GetAttributeValue("ChildConnectionStatus").AsGuid()); if (_dvcChildConnectionStatus == null) { nbNotice.Heading = "Invalid Child Connection Status"; nbNotice.Text = "<p>The selected Child Connection Status setting does not exist.</p>"; return(false); } _dvcRecordStatus = DefinedValueCache.Get(GetAttributeValue("RecordStatus").AsGuid()); if (_dvcRecordStatus == null) { nbNotice.Heading = "Invalid Record Status"; nbNotice.Text = "<p>The selected Record Status setting does not exist.</p>"; return(false); } _single = DefinedValueCache.Get(Rock.SystemGuid.DefinedValue.PERSON_MARITAL_STATUS_SINGLE.AsGuid()); _married = DefinedValueCache.Get(Rock.SystemGuid.DefinedValue.PERSON_MARITAL_STATUS_MARRIED.AsGuid()); _homeAddressType = DefinedValueCache.Get(Rock.SystemGuid.DefinedValue.GROUP_LOCATION_TYPE_HOME.AsGuid()); _familyType = GroupTypeCache.Get(Rock.SystemGuid.GroupType.GROUPTYPE_FAMILY.AsGuid()); _adultRole = _familyType.Roles.FirstOrDefault(r => r.Guid.Equals(Rock.SystemGuid.GroupRole.GROUPROLE_FAMILY_MEMBER_ADULT.AsGuid())); _childRole = _familyType.Roles.FirstOrDefault(r => r.Guid.Equals(Rock.SystemGuid.GroupRole.GROUPROLE_FAMILY_MEMBER_CHILD.AsGuid())); if (_single == null || _married == null || _homeAddressType == null || _familyType == null || _adultRole == null || _childRole == null) { nbNotice.Heading = "Missing System Value"; nbNotice.Text = "<p>There is a missing or invalid system value. Check the settings for Marital Status of 'Single'/'Married', Location Type of 'Home', Group Type of 'Family', and Family Group Role of 'Adult'.</p>"; return(false); } _isPrayerRequestEnabled = GetAttributeValue("IsPrayerRequestEnabled").AsBoolean(); return(true); }
/// <summary> /// Creates the connection requests. /// </summary> /// <param name="context">The context.</param> /// <param name="campaignItem">The campaign item.</param> /// <returns></returns> private int CreateConnectionRequests(IJobExecutionContext context, CampaignItem campaignItem) { context.UpdateLastStatusMessage($"Processing create connection requests for {campaignItem.Name}"); // Skip creating connection requests if set to "AsNeeded" and DailyLimitAssigned is 0 or null if (campaignItem.CreateConnectionRequestOption == CreateConnectionRequestOptions.AsNeeded && (campaignItem.DailyLimitAssigned <= 0 || campaignItem.DailyLimitAssigned == null)) { return(0); } int recordsProcessed = 0; var rockContext = new RockContext(); var connectionOpportunityService = new ConnectionOpportunityService(rockContext); var personAliasService = new PersonAliasService(rockContext); var entitySetItemService = new EntitySetItemService(rockContext); var connectionOpportunity = connectionOpportunityService.Get(campaignItem.OpportunityGuid); if (connectionOpportunity == null) { return(0); } // get cutoff for the last connection datetime. var lastConnectionDateTime = RockDateTime.Now.AddDays(-campaignItem.DaysBetweenConnection); // if DaysBetweenConnection is 0 then check for connection request for any time period. if (campaignItem.DaysBetweenConnection == default(int)) { lastConnectionDateTime = DateTime.MinValue; } var entitySetItemsQry = entitySetItemService .Queryable() .Where(a => a.EntitySetId == campaignItem.EntitySetId) .OrderBy(a => a.Order); bool autoAssignment = false; var eligibleConnectors = new List <ConnectionConnector>(); if (campaignItem.DailyLimitAssigned.HasValue && campaignItem.DailyLimitAssigned != default(int)) { autoAssignment = true; eligibleConnectors = GetEligibleConnectorWithLimit(connectionOpportunity.Id, rockContext, campaignItem.DailyLimitAssigned.Value); } var connectionStatusId = GetConnectionStatus(connectionOpportunity); if (!connectionStatusId.HasValue) { return(0); } var entitySetItemList = entitySetItemsQry.ToList(); foreach (var entitySetItem in entitySetItemList) { var entityItemPersonAlias = personAliasService.GetPrimaryAlias(entitySetItem.EntityId); int?connectorPersonId = null; if (autoAssignment) { connectorPersonId = GetConnector(campaignItem, connectionOpportunity, eligibleConnectors, entityItemPersonAlias, rockContext); if (campaignItem.CreateConnectionRequestOption == CreateConnectionRequestOptions.AsNeeded && !connectorPersonId.HasValue) { continue; } } // double check that they haven't already been added var personAlreadyHasConnectionRequest = CampaignConnectionHelper.PersonAlreadyHasConnectionRequest(connectionOpportunity.Id, rockContext, lastConnectionDateTime, entitySetItem.EntityId); if (personAlreadyHasConnectionRequest) { continue; } int?connectorPersonAliasId = null; if (connectorPersonId.HasValue) { foreach (var connectionConnector in eligibleConnectors.Where(a => a.PersonId == connectorPersonId.Value)) { connectorPersonAliasId = connectionConnector.PersonAliasId; connectionConnector.Current += 1; } } CreateConnectionRequest(entityItemPersonAlias, campaignItem.RequestCommentsLavaTemplate, connectionOpportunity.Id, connectionStatusId, connectorPersonAliasId, rockContext); recordsProcessed += 1; } return(recordsProcessed); }
/// <summary> /// Handles the Edit event of the gConnectionOpportunities 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 gConnectionOpportunities_Edit( object sender, RowEventArgs e ) { using ( RockContext rockContext = new RockContext() ) { ConnectionOpportunityService connectionOpportunityService = new ConnectionOpportunityService( rockContext ); ConnectionOpportunity connectionOpportunity = connectionOpportunityService.Get( e.RowKeyId ); if ( connectionOpportunity != null ) { NavigateToLinkedPage( "DetailPage", "ConnectionOpportunityId", connectionOpportunity.Id, "ConnectionTypeId", _connectionType.Id ); } } }
/// <summary> /// Handles the Click event of the DeleteConnectionOpportunity control. /// </summary> /// <param name="sender">The source of the event.</param> /// <param name="e">The <see cref="Rock.Web.UI.Controls.RowEventArgs" /> instance containing the event data.</param> protected void DeleteConnectionOpportunity_Click( object sender, Rock.Web.UI.Controls.RowEventArgs e ) { using ( RockContext rockContext = new RockContext() ) { ConnectionOpportunityService connectionOpportunityService = new ConnectionOpportunityService( rockContext ); ConnectionOpportunity connectionOpportunity = connectionOpportunityService.Get( e.RowKeyId ); if ( connectionOpportunity != null ) { if ( _canEdit ) { string errorMessage; if ( !connectionOpportunityService.CanDelete( connectionOpportunity, out errorMessage ) ) { mdGridWarning.Show( errorMessage, ModalAlertType.Information ); return; } int connectionTypeId = connectionOpportunity.ConnectionTypeId; connectionOpportunityService.Delete( connectionOpportunity ); rockContext.SaveChanges(); ConnectionWorkflowService.FlushCachedTriggers(); } else { mdGridWarning.Show( "You are not authorized to delete this calendar item", ModalAlertType.Warning ); } } } BindConnectionOpportunitiesGrid(); }
/// <summary> /// Creates the connection requests. /// </summary> /// <param name="context">The context.</param> /// <param name="campaignItem">The campaign item.</param> /// <returns></returns> private int CreateConnectionRequests(IJobExecutionContext context, CampaignItem campaignItem) { context.UpdateLastStatusMessage($"Processing create connection requests for {campaignItem.Name}"); // Skip creating connection requests if set to "AsNeeded" and DailyLimitAssigned is 0 or null if (campaignItem.CreateConnectionRequestOption == CreateConnectionRequestOptions.AsNeeded && (campaignItem.DailyLimitAssigned <= 0 || campaignItem.DailyLimitAssigned == null)) { return(0); } int recordsProcessed = 0; var rockContext = new RockContext(); var connectionOpportunityService = new ConnectionOpportunityService(rockContext); var personAliasService = new PersonAliasService(rockContext); var connectionRequestService = new ConnectionRequestService(rockContext); var connectionOpportunity = connectionOpportunityService.Get(campaignItem.OpportunityGuid); if (connectionOpportunity == null) { return(0); } // get cutoff for the last connection datetime. var lastConnectionDateTime = RockDateTime.Now.AddDays(-campaignItem.DaysBetweenConnection); // if DaysBetweenConnection is 0 then check for connection request for any time period. if (campaignItem.DaysBetweenConnection == default(int)) { lastConnectionDateTime = DateTime.MinValue; } var entitySetItemService = new EntitySetItemService(rockContext); var entitySetItemsQry = entitySetItemService .Queryable() .Where(a => a.EntitySetId == campaignItem.EntitySetId) .OrderBy(a => a.Order); bool autoAssignment = false; var eligibleConnectors = new List <ConnectionConnector>(); if (campaignItem.CreateConnectionRequestOption == CreateConnectionRequestOptions.AsNeeded && campaignItem.DailyLimitAssigned.HasValue && campaignItem.DailyLimitAssigned != default(int)) { autoAssignment = true; eligibleConnectors = GetEligibleConnectorWithLimit(connectionOpportunity.Id, rockContext, campaignItem.DailyLimitAssigned.Value); } int?connectionStatusId = connectionOpportunity.ConnectionType.ConnectionStatuses .Where(s => s.IsDefault) .Select(s => ( int? )s.Id) .FirstOrDefault(); // If opportunity doesn't have a default status, something is wrong if (connectionStatusId == null) { ExceptionLogService.LogException(new Exception($"Unable to determine default connection status for {connectionOpportunity.Name} while processing campaigns", null)); return(0); } var dayofWeek = RockDateTime.Now.DayOfWeek; var entitySetItemList = entitySetItemsQry.ToList(); foreach (var entitySetItem in entitySetItemList) { var personAlias = personAliasService.GetPrimaryAlias(entitySetItem.EntityId); var defaultCampus = personAlias.Person.GetCampus(); int?connectorPersonAliasId = null; if (autoAssignment) { int?connectorPersonId = null; if (campaignItem.PreferPreviousConnector) { var personIds = eligibleConnectors .Where(a => a.Limit - a.Current > 0 && (!a.DaysOfWeek.Any() || a.DaysOfWeek.Contains(dayofWeek)) && (!a.CampusId.HasValue || (a.CampusId.HasValue && defaultCampus != null && defaultCampus.Id == a.CampusId.Value))) .Select(a => a.PersonId) .ToList(); if (personIds.Any()) { var person = connectionRequestService .Queryable() .Where(a => a.ConnectionOpportunityId == connectionOpportunity.Id && a.PersonAlias.PersonId == personAlias.PersonId && a.ConnectionState == ConnectionState.Connected && a.ConnectorPersonAliasId.HasValue && personIds.Contains(a.ConnectorPersonAlias.PersonId)) .Select(a => a.ConnectorPersonAlias.Person) .FirstOrDefault(); if (person != null) { connectorPersonId = person.Id; } } } if (!connectorPersonId.HasValue) { var eligibleConnector = eligibleConnectors .Where(a => a.Limit - a.Current > 0 && (!a.DaysOfWeek.Any() || a.DaysOfWeek.Contains(dayofWeek)) && (!a.CampusId.HasValue || (a.CampusId.HasValue && defaultCampus != null && defaultCampus.Id == a.CampusId.Value))) .OrderBy(a => a.Current) // order from least assigned to most assigned .ThenBy(x => Guid.NewGuid()) // and then randomize .FirstOrDefault(); if (eligibleConnector != null) { connectorPersonId = eligibleConnector.PersonId; } } if (!connectorPersonId.HasValue) { continue; } foreach (var connectionConnector in eligibleConnectors.Where(a => a.PersonId == connectorPersonId.Value)) { connectorPersonAliasId = connectionConnector.PersonAliasId; connectionConnector.Current += 1; } } using (var insertRockContext = new RockContext()) { try { /* * 3/30/2020 - NA * * When setting the connection request's Requester, we have to use the PrimaryAlias * to set the connectionRequest.PersonAlias property because the ConnectionRequestChangeTransaction * https://github.com/SparkabilityGroup/Rock/blob/a556a9285b7fdfe5594441286242f4feaa5847f2/Rock/Transactions/ConnectionRequestChangeTransaction.cs#L123 * (which handles triggered workflows) expects it. Also, it needs to be tracked by * the current rockContext... * * In other words, this will not work correctly: * PersonAliasId = personAlias.Id, * * Reason: This plug-in cannot change Rock core assembly code. */ var personPrimaryAlias = new PersonAliasService(insertRockContext).GetPrimaryAlias(entitySetItem.EntityId); var connectionRequestActivityService = new ConnectionRequestActivityService(insertRockContext); var insertConnectionRequestService = new ConnectionRequestService(insertRockContext); // double check that they haven't already been added var personAlreadyHasConnectionRequest = CampaignConnectionHelper.PersonAlreadyHasConnectionRequest(connectionOpportunity.Id, rockContext, lastConnectionDateTime, entitySetItem.EntityId); if (personAlreadyHasConnectionRequest) { continue; } var connectionRequest = new ConnectionRequest() { ConnectionOpportunityId = connectionOpportunity.Id, PersonAlias = personPrimaryAlias, ConnectionState = ConnectionState.Active, ConnectorPersonAliasId = connectorPersonAliasId, CampusId = defaultCampus?.Id, ConnectionStatusId = connectionStatusId.Value, }; if (campaignItem.RequestCommentsLavaTemplate.IsNotNullOrWhiteSpace()) { var mergeFields = new Dictionary <string, object>(); mergeFields.Add("Person", personAlias.Person); mergeFields.Add("Family", personAlias.Person.GetFamily()); connectionRequest.Comments = campaignItem.RequestCommentsLavaTemplate.ResolveMergeFields(mergeFields); } insertConnectionRequestService.Add(connectionRequest); if (connectorPersonAliasId.HasValue) { var connectionActivityTypeAssignedGuid = Rock.SystemGuid.ConnectionActivityType.ASSIGNED.AsGuid(); int?assignedActivityId = new ConnectionActivityTypeService(rockContext).GetId(connectionActivityTypeAssignedGuid); if (assignedActivityId.HasValue) { var connectionRequestActivity = new ConnectionRequestActivity(); connectionRequestActivity.ConnectionRequest = connectionRequest; connectionRequestActivity.ConnectionOpportunityId = connectionRequest.ConnectionOpportunityId; connectionRequestActivity.ConnectionActivityTypeId = assignedActivityId.Value; connectionRequestActivity.ConnectorPersonAliasId = connectorPersonAliasId; connectionRequestActivityService.Add(connectionRequestActivity); } } insertRockContext.SaveChanges(); } catch (Exception ex) { // Log exception and keep on trucking. var exception = new Exception($"Exception occurred trying to create connection request:{personAlias.Id}.", ex); createConnectionRequestExceptions.Add(exception); ExceptionLogService.LogException(exception, null); } } recordsProcessed += 1; } return(recordsProcessed); }