/// <summary> /// Gets the expression. /// </summary> /// <param name="entityType">Type of the entity.</param> /// <param name="serviceInstance">The service instance.</param> /// <param name="parameterExpression">The parameter expression.</param> /// <param name="selection">The selection.</param> /// <returns></returns> public override Expression GetExpression( Type entityType, IService serviceInstance, ParameterExpression parameterExpression, string selection ) { var values = selection.Split( '|' ); ComparisonType comparisonType = values[0].ConvertToEnum<ComparisonType>( ComparisonType.EqualTo ); int? memberCountValue = values[1].AsIntegerOrNull(); GroupMemberStatus? memberStatusValue = (GroupMemberStatus?)values[3].AsIntegerOrNull(); bool? isLeader = values[2].AsBooleanOrNull(); var memberCountQuery = new GroupService( (RockContext)serviceInstance.Context ).Queryable(); var memberCountEqualQuery = memberCountQuery.Where( p => p.Members.Count( a => ( !memberStatusValue.HasValue || a.GroupMemberStatus == memberStatusValue ) && ( !isLeader.HasValue || ( a.GroupRole.IsLeader == isLeader.Value ) ) ) == memberCountValue ); BinaryExpression compareEqualExpression = FilterExpressionExtractor.Extract<Rock.Model.Group>( memberCountEqualQuery, parameterExpression, "p" ) as BinaryExpression; BinaryExpression result = FilterExpressionExtractor.AlterComparisonType( comparisonType, compareEqualExpression, 0 ); return result; }
/// <summary> /// Creates a Linq Expression that can be applied to an IQueryable to filter the result set. /// </summary> /// <param name="entityType">The type of entity in the result set.</param> /// <param name="serviceInstance">A service instance that can be queried to obtain the result set.</param> /// <param name="parameterExpression">The input parameter that will be injected into the filter expression.</param> /// <param name="selection">A formatted string representing the filter settings.</param> /// <returns> /// A Linq Expression that can be used to filter an IQueryable. /// </returns> public override Expression GetExpression( Type entityType, IService serviceInstance, ParameterExpression parameterExpression, string selection ) { var settings = new FilterSettings( selection ); var context = (RockContext)serviceInstance.Context; // // Define Candidate People. // // Get the Person Data View that defines the set of candidates from which matching Group Members can be selected. var dataView = DataComponentSettingsHelper.GetDataViewForFilterComponent( settings.PersonDataViewGuid, context ); var personService = new PersonService( context ); var personQuery = personService.Queryable(); if (dataView != null) { personQuery = DataComponentSettingsHelper.FilterByDataView( personQuery, dataView, personService ); } var personKeys = personQuery.Select( x => x.Id ); // // Construct the Query to return the list of Groups matching the filter conditions. // var comparisonType = settings.PersonCountComparison; int memberCountValue = settings.PersonCount; var memberCountQuery = new GroupService( context ).Queryable(); var memberCountEqualQuery = memberCountQuery.Where( g => g.Members.Count( gm => personKeys.Contains( gm.PersonId ) ) == memberCountValue ); var compareEqualExpression = FilterExpressionExtractor.Extract<Model.Group>( memberCountEqualQuery, parameterExpression, "g" ) as BinaryExpression; var result = FilterExpressionExtractor.AlterComparisonType( comparisonType, compareEqualExpression, 0 ); return result; }
/// <summary> /// Binds the grid. /// </summary> private void BindGrid() { // Find all the Group Types var groupTypeIds = GetAvailableGroupTypes(); if ( ( GetAttributeValue( "DisplayFilter" ) ?? "false" ).AsBoolean() ) { int? groupTypeFilter = gfSettings.GetUserPreference( "Group Type" ).AsInteger( false ); if ( groupTypeFilter.HasValue ) { groupTypeIds = groupTypeIds.Where( g => g == groupTypeFilter.Value ).ToList(); } } var rockContext = new RockContext(); SortProperty sortProperty = gGroups.SortProperty; if ( sortProperty == null ) { sortProperty = new SortProperty( new GridViewSortEventArgs( "GroupTypeOrder, GroupTypeName, GroupOrder, Name", SortDirection.Ascending ) ); } bool onlySecurityGroups = GetAttributeValue( "LimittoSecurityRoleGroups" ).AsBoolean(); bool showDescriptionColumn = GetAttributeValue( "DisplayDescriptionColumn" ).AsBoolean(); bool showActiveStatusColumn = GetAttributeValue( "DisplayActiveStatusColumn" ).AsBoolean(); bool showSystemColumn = GetAttributeValue( "DisplaySystemColumn" ).AsBoolean(); if ( !showDescriptionColumn ) { gGroups.TooltipField = "Description"; } Dictionary<string, BoundField> boundFields = gGroups.Columns.OfType<BoundField>().ToDictionary( a => a.DataField ); boundFields["GroupTypeName"].Visible = GetAttributeValue( "DisplayGroupTypeColumn" ).AsBoolean(); boundFields["Description"].Visible = showDescriptionColumn; Dictionary<string, BoolField> boolFields = gGroups.Columns.OfType<BoolField>().ToDictionary( a => a.DataField ); boolFields["IsActive"].Visible = showActiveStatusColumn; boolFields["IsSystem"].Visible = showSystemColumn; // Person context will exist if used on a person detail page var personContext = ContextEntity<Person>(); if ( personContext != null ) { boundFields["GroupRole"].Visible = true; boundFields["DateAdded"].Visible = true; boundFields["MemberCount"].Visible = false; gGroups.Actions.ShowAdd = false; gGroups.IsDeleteEnabled = false; gGroups.Columns.OfType<DeleteField>().ToList().ForEach( f => f.Visible = false ); var qry = new GroupMemberService( rockContext ).Queryable() .Where( m => m.PersonId == personContext.Id && groupTypeIds.Contains( m.Group.GroupTypeId ) && ( !onlySecurityGroups || m.Group.IsSecurityRole ) ); // Filter by active/inactive if ( ddlActiveFilter.SelectedIndex > -1 ) { if ( ddlActiveFilter.SelectedValue == "inactive" ) { qry = qry.Where( a => a.Group.IsActive == false ); } else if ( ddlActiveFilter.SelectedValue == "active" ) { qry = qry.Where( a => a.Group.IsActive == true ); } } gGroups.DataSource = qry .Select( m => new { Id = m.Group.Id, Name = m.Group.Name, GroupTypeName = m.Group.GroupType.Name, GroupOrder = m.Group.Order, GroupTypeOrder = m.Group.GroupType.Order, Description = m.Group.Description, IsSystem = m.Group.IsSystem, GroupRole = m.GroupRole.Name, DateAdded = m.CreatedDateTime, IsActive = m.Group.IsActive, MemberCount = 0 } ) .Sort( sortProperty ) .ToList(); } else { bool canEdit = IsUserAuthorized( Authorization.EDIT ); gGroups.Actions.ShowAdd = canEdit; gGroups.IsDeleteEnabled = canEdit; boundFields["GroupRole"].Visible = false; boundFields["DateAdded"].Visible = false; boundFields["MemberCount"].Visible = true; var qry = new GroupService( rockContext ).Queryable() .Where( g => groupTypeIds.Contains( g.GroupTypeId ) && ( !onlySecurityGroups || g.IsSecurityRole ) ); // Filter by active/inactive if ( ddlActiveFilter.SelectedIndex > -1 ) { if ( ddlActiveFilter.SelectedValue == "inactive" ) { qry = qry.Where( a => a.IsActive == false ); } else if ( ddlActiveFilter.SelectedValue == "active" ) { qry = qry.Where( a => a.IsActive == true ); } } gGroups.DataSource = qry.Select( g => new { Id = g.Id, Name = g.Name, GroupTypeName = g.GroupType.Name, GroupOrder = g.Order, GroupTypeOrder = g.GroupType.Order, Description = g.Description, IsSystem = g.IsSystem, IsActive = g.IsActive, GroupRole = string.Empty, DateAdded = DateTime.MinValue, MemberCount = g.Members.Count() } ) .Sort( sortProperty ) .ToList(); } gGroups.DataBind(); }
private NavigationData GetNavigationData( CampusCache campus ) { using ( var rockContext = new RockContext() ) { var validLocationids = new List<int>(); if ( campus.LocationId.HasValue ) { // Get all the child locations validLocationids.Add( campus.LocationId.Value ); new LocationService( rockContext ) .GetAllDescendents( campus.LocationId.Value ) .Select( l => l.Id ) .ToList() .ForEach( l => validLocationids.Add( l ) ); } var groupTypeTemplateGuid = PageParameter( "Area" ).AsGuidOrNull(); if ( !groupTypeTemplateGuid.HasValue ) { groupTypeTemplateGuid = this.GetAttributeValue( "GroupTypeTemplate" ).AsGuidOrNull(); } if ( !groupTypeTemplateGuid.HasValue ) { // Check to see if a specific group was specified Guid? guid = Rock.SystemGuid.DefinedValue.GROUPTYPE_PURPOSE_CHECKIN_TEMPLATE.AsGuid(); int? groupId = PageParameter( "Group" ).AsIntegerOrNull(); if ( groupId.HasValue && guid.HasValue ) { var group = new GroupService( rockContext ).Get( groupId.Value ); if ( group != null && group.GroupType != null ) { var groupType = GetParentPurposeGroupType( group.GroupType, guid.Value ); if ( groupType != null ) { groupTypeTemplateGuid = groupType.Guid; } } } } if ( groupTypeTemplateGuid.HasValue ) { pnlContent.Visible = true; NavData = new NavigationData(); var chartTimes = GetChartTimes(); // Get the group types var parentGroupType = GroupTypeCache.Read( groupTypeTemplateGuid.Value ); if ( parentGroupType != null ) { foreach ( var childGroupType in parentGroupType.ChildGroupTypes ) { AddGroupType( childGroupType, chartTimes ); } } // Get the groups var groupTypeIds = NavData.GroupTypes.Select( t => t.Id ).ToList(); var groups = new GroupService( rockContext ) .Queryable( "GroupLocations" ).AsNoTracking() .Where( g => groupTypeIds.Contains( g.GroupTypeId ) && g.IsActive ) .ToList(); var groupIds = groups.Select( g => g.Id ).ToList(); foreach( var group in groups ) { var childGroupIds = groups .Where( g => g.ParentGroupId.HasValue && g.ParentGroupId.Value == group.Id ) .Select( g => g.Id ) .ToList(); var childLocationIds = group.GroupLocations .Where( l => validLocationids.Contains( l.LocationId ) ) .Select( l => l.LocationId ) .ToList(); if ( childLocationIds.Any() || childGroupIds.Any() ) { var navGroup = new NavigationGroup( group, chartTimes ); navGroup.ChildLocationIds = childLocationIds; navGroup.ChildGroupIds = childGroupIds; NavData.Groups.Add( navGroup ); if ( !group.ParentGroupId.HasValue || groupIds.Contains( group.ParentGroupId.Value ) ) { NavData.GroupTypes.Where( t => t.Id == group.GroupTypeId ).ToList() .ForEach( t => t.ChildGroupIds.Add( group.Id ) ); } } } // Remove any groups without child locations var emptyGroupIds = NavData.Groups .Where( g => !g.ChildGroupIds.Any() && !g.ChildLocationIds.Any() ) .Select( g => g.Id ) .ToList(); while ( emptyGroupIds.Any() ) { NavData.Groups = NavData.Groups.Where( g => !emptyGroupIds.Contains( g.Id ) ).ToList(); NavData.Groups.ForEach( g => g.ChildGroupIds = g.ChildGroupIds.Where( c => !emptyGroupIds.Contains( c ) ).ToList() ); emptyGroupIds = NavData.Groups .Where( g => !g.ChildGroupIds.Any() && !g.ChildLocationIds.Any() ) .Select( g => g.Id ) .ToList(); } // Remove any grouptype without groups var emptyGroupTypeIds = NavData.GroupTypes .Where( t => !t.ChildGroupIds.Any() && !t.ChildGroupTypeIds.Any() ) .Select( t => t.Id ) .ToList(); while ( emptyGroupTypeIds.Any() ) { NavData.GroupTypes = NavData.GroupTypes.Where( t => !emptyGroupTypeIds.Contains( t.Id ) ).ToList(); NavData.GroupTypes.ForEach( t => t.ChildGroupTypeIds = t.ChildGroupTypeIds.Where( c => !emptyGroupTypeIds.Contains( c ) ).ToList() ); emptyGroupTypeIds = NavData.GroupTypes .Where( t => !t.ChildGroupIds.Any() && !t.ChildGroupTypeIds.Any() ) .Select( t => t.Id ) .ToList(); } // If not group types left, redirect to area select page if ( NavData.GroupTypes.Count == 0 ) { NavigateToLinkedPage( "AreaSelectPage" ); } // Get the locations var locationIds = NavData.Groups.SelectMany( g => g.ChildLocationIds ).Distinct().ToList(); foreach ( var location in new LocationService( rockContext ) .Queryable( "ParentLocation" ).AsNoTracking() .Where( l => locationIds.Contains( l.Id ) ) ) { var navLocation = AddLocation( location, chartTimes ); navLocation.HasGroups = true; } // Get the attendance counts var dayStart = RockDateTime.Today; var now = RockDateTime.Now; groupIds = NavData.Groups.Select( g => g.Id ).ToList(); var attendances = new AttendanceService( rockContext ).Queryable() .Where( a => a.ScheduleId.HasValue && a.GroupId.HasValue && a.LocationId.HasValue && a.StartDateTime > dayStart && a.StartDateTime < now && a.DidAttend.HasValue && a.DidAttend.Value && groupIds.Contains( a.GroupId.Value ) && locationIds.Contains( a.LocationId.Value ) ) .ToList(); var schedules = new ScheduleService( rockContext ).Queryable() .Where( s => s.CheckInStartOffsetMinutes.HasValue ) .ToList(); foreach ( DateTime chartTime in chartTimes ) { // Get the active schedules var activeSchedules = new List<int>(); foreach ( var schedule in schedules ) { if ( schedule.WasScheduleOrCheckInActive( chartTime ) ) { activeSchedules.Add( schedule.Id ); } } bool current = chartTime.Equals( chartTimes.Max() ); foreach ( var groupLocSched in attendances .Where( a => a.StartDateTime < chartTime && a.PersonAlias != null && activeSchedules.Contains( a.ScheduleId.Value ) ) .GroupBy( a => new { ScheduleId = a.ScheduleId.Value, GroupId = a.GroupId.Value, LocationId = a.LocationId.Value } ) .Select( g => new { ScheduleId = g.Key.ScheduleId, GroupId = g.Key.GroupId, LocationId = g.Key.LocationId, PersonIds = g.Select( a => a.PersonAlias.PersonId ).Distinct().ToList() } ) ) { AddGroupCount( chartTime, groupLocSched.GroupId, groupLocSched.PersonIds, current ); AddLocationCount( chartTime, groupLocSched.LocationId, groupLocSched.PersonIds, current ); } } return NavData; } else { if ( string.IsNullOrWhiteSpace( PageParameter( "Area" ) ) ) { // If could not determine area and did not come from are select, redirect to area select page NavigateToLinkedPage( "AreaSelectPage" ); } nbWarning.Text = "Please select a valid Check-in type in the block settings."; nbWarning.Visible = true; pnlContent.Visible = false; } } return null; }
/// <summary> /// Binds the filter. /// </summary> private void BindFilter() { drpDates.DelimitedValues = rFilter.GetUserPreference( "Date Range" ); ppPerson.Visible = _person == null; ddlAttendanceGroup.Visible = _group == null && _person != null; ddlAttendanceGroup.Items.Clear(); ddlAttendanceGroup.Items.Add( new ListItem() ); if ( _person != null ) { var rockContext = new RockContext(); var qryGroup = new GroupService( rockContext ).Queryable(); var qryPersonAttendance = new AttendanceService( rockContext ).Queryable().Where( a => a.PersonAlias.PersonId == _person.Id ); // only list groups that this person has attended before var groupList = qryGroup.Where( g => qryPersonAttendance.Any( a => a.GroupId == g.Id ) ) .OrderBy( a => a.Name ) .Select( a => new { a.Name, a.Id } ).ToList(); foreach ( var group in groupList ) { ddlAttendanceGroup.Items.Add( new ListItem( group.Name, group.Id.ToString() ) ); } ddlAttendanceGroup.SetValue( rFilter.GetUserPreference( "Group" ).AsIntegerOrNull() ); } spSchedule.SetValue( rFilter.GetUserPreference( "Schedule" ).AsIntegerOrNull() ); }
/// <summary> /// Binds the grid. /// </summary> private void BindGrid() { // Find all the Group Types var groupTypeIds = GetAvailableGroupTypes(); if ( GetAttributeValue( "DisplayFilter" ).AsBooleanOrNull() ?? false ) { int? groupTypeFilter = gfSettings.GetUserPreference( "Group Type" ).AsIntegerOrNull(); if ( groupTypeFilter.HasValue ) { groupTypeIds = groupTypeIds.Where( g => g == groupTypeFilter.Value ).ToList(); } } var rockContext = new RockContext(); SortProperty sortProperty = gGroups.SortProperty; if ( sortProperty == null ) { sortProperty = new SortProperty( new GridViewSortEventArgs( "GroupTypeOrder, GroupTypeName, GroupOrder, Name", SortDirection.Ascending ) ); } bool onlySecurityGroups = GetAttributeValue( "LimittoSecurityRoleGroups" ).AsBoolean(); var qryGroups = new GroupService( rockContext ).Queryable().Where( g => groupTypeIds.Contains( g.GroupTypeId ) && ( !onlySecurityGroups || g.IsSecurityRole ) ); string limitToActiveStatus = GetAttributeValue( "LimittoActiveStatus" ); if ( limitToActiveStatus == "all" && gfSettings.Visible ) { // Filter by active/inactive unless the block settings restrict it if ( ddlActiveFilter.SelectedIndex > -1 ) { if ( ddlActiveFilter.SelectedValue == "inactive" ) { qryGroups = qryGroups.Where( a => a.IsActive == false ); } else if ( ddlActiveFilter.SelectedValue == "active" ) { qryGroups = qryGroups.Where( a => a.IsActive == true ); } } } else if ( limitToActiveStatus != "all") { // filter by the block settinf for Active Status if ( limitToActiveStatus == "inactive") { qryGroups = qryGroups.Where( a => a.IsActive == false ); } else if ( limitToActiveStatus == "active" ) { qryGroups = qryGroups.Where( a => a.IsActive == true ); } } // Person context will exist if used on a person detail page int personEntityTypeId = EntityTypeCache.Read( "Rock.Model.Person" ).Id; if ( ContextTypesRequired.Any( e => e.Id == personEntityTypeId ) ) { var personContext = ContextEntity<Person>(); if ( personContext != null ) { // limit to Groups that the person is a member of var qry = new GroupMemberService( rockContext ).Queryable( true ) .Where( m => m.PersonId == personContext.Id ) .Join( qryGroups, gm => gm.GroupId, g => g.Id, ( gm, g ) => new { Group = g, GroupMember = gm } ); gGroups.DataSource = qry .Select( m => new { Id = m.Group.Id, Name = m.Group.Name, GroupTypeName = m.Group.GroupType.Name, GroupOrder = m.Group.Order, GroupTypeOrder = m.Group.GroupType.Order, Description = m.Group.Description, IsSystem = m.Group.IsSystem, GroupRole = m.GroupMember.GroupRole.Name, DateAdded = m.GroupMember.CreatedDateTime, IsActive = m.Group.IsActive, MemberCount = 0 } ) .Sort( sortProperty ) .ToList(); } } else { var roleGroupType = GroupTypeCache.Read( Rock.SystemGuid.GroupType.GROUPTYPE_SECURITY_ROLE.AsGuid() ); int roleGroupTypeId = roleGroupType != null ? roleGroupType.Id : 0; bool useRolePrefix = onlySecurityGroups || groupTypeIds.Contains( roleGroupTypeId ); gGroups.DataSource = qryGroups.Select( g => new { Id = g.Id, Name = (( useRolePrefix && g.GroupType.Id != roleGroupTypeId ) ? "GROUP - " : "" ) + g.Name, GroupTypeName = g.GroupType.Name, GroupOrder = g.Order, GroupTypeOrder = g.GroupType.Order, Description = g.Description, IsSystem = g.IsSystem, IsActive = g.IsActive, GroupRole = string.Empty, DateAdded = DateTime.MinValue, MemberCount = g.Members.Count() } ) .Sort( sortProperty ) .ToList(); } gGroups.DataBind(); // hide the group type column if there's only one type; must come after DataBind() if ( _groupTypesCount == 1 ) { this.gGroups.Columns[1].Visible = false; } }