This guide covers creating and configuring Entity Lists in Power Pages to display Dataverse data to portal users. Entity Lists provide out-of-the-box (OOTB) functionality for showing filtered, searchable, and paginated data.
Prerequisites:
- Complete Data Model Design - Tables and relationships created
- Understand Dataverse views concept
Note: Table permissions will be configured as part of this guide. Basic table permission concepts are covered in the Data Model Design document.
Entity Lists are Power Pages components that display Dataverse data in a table format. They provide:
- Automatic Filtering: Based on table permissions and Dataverse views
- Search Functionality: Built-in search across displayed columns
- Pagination: Automatic pagination for large datasets
- Sorting: Click column headers to sort
- Actions: View details, edit, delete (based on permissions)
- Responsive Design: Mobile-friendly table layout
Before creating an Entity List, you need Dataverse views that define what data to display. The PawsFirst portal uses three customer-facing views: My Pets, My Booking Requests, and My Appointments (with Active and History variants).
Note: Each Dataverse table has an active view OOTB (out-of-the-box). You can use the default active view or create custom views. Filters are automatically applied based on table permissions configured in the portal, so you don't need to add filters to the views themselves.
- Navigate to Power Apps → Dataverse → Tables → Pet (
pa911_pet) - Go to Views tab
- Click New view → Public view
- Configure view:
| Column | Width | Sort |
|---|---|---|
| Pet Name (pa911_name) | 150 | Ascending |
| Species (pa911_species) | 100 | - |
| Breed (pa911_breed) | 120 | - |
| Date of Birth (pa911_dateofbirth) | 120 | - |
| Weight (pa911_weight) | 100 | - |
- Save the view as: My Pets
- Navigate to Power Apps → Dataverse → Tables → Booking Request (
pa911_bookingrequest) - Go to Views tab
- Click New view → Public view
- Configure view:
| Column | Width | Sort |
|---|---|---|
| Request Number (pa911_name) | 150 | Ascending |
| Pet Name (pa911_petname) | 120 | - |
| Service (pa911_service) | 150 | - |
| Preferred Slot (pa911_appointmentslot) | 200 | - |
| Request Status (pa911_requeststatus) | 120 | - |
| Created On (createdon) | 120 | Descending |
- Save the view as: My Booking Requests
Note: Table permissions will automatically filter records to show only the current user's booking requests (via the pa911_contact lookup field set by Power Automate after invitation).
- Navigate to Power Apps → Dataverse → Tables → Appointment (
appointment) - Go to Views tab
- Click New view → Public view
- Configure view:
| Column | Width | Sort |
|---|---|---|
| Subject (subject) | 200 | - |
| Scheduled Start (scheduledstart) | 150 | Ascending |
| Scheduled End (scheduledend) | 150 | - |
| Pet (pa911_pet) | 120 | - |
| Service (pa911_service) | 150 | - |
| Service Status (pa911_servicestatus) | 120 | - |
- Save the view as: My Active Appointments
Note: Table permissions will automatically filter records to show only appointments for the current user's pets. You can optionally filter by service status in the view if you want to separate active and completed appointments.
- Navigate to Power Apps → Dataverse → Tables → Appointment (
appointment) - Go to Views tab
- Click New view → Public view
- Configure view with the same columns as My Active Appointments
- Save the view as: My Appointment History
Note: Table permissions will automatically filter records to show only appointments for the current user's pets. You can optionally filter by service status in the view to show completed (144400002), cancelled (144400003), or no-show (144400004) appointments.
Note: You can create a single "All Appointments" view if you prefer to let users filter by status in the Entity List interface, or create separate views for different statuses.
Entity Lists respect table permissions. Ensure permissions are configured correctly for the three customer-facing tables. See the Data Model Design for complete table permission details.
- Navigate to Power Pages → Your Site → Security → Table Permissions
- Create or verify permission:
| Setting | Value |
|---|---|
| Name | Pet - User Read Own |
| Table | Pet (pa911_pet) |
| Web Role | Authenticated Users |
| Scope | Contact |
| Privileges | Read, Write |
| Contact Scope | Current user's Contact (via pa911_petowner field) |
This allows users to read and manage pets where they are the owner.
- Navigate to Power Pages → Your Site → Security → Table Permissions
- Create or verify permission:
| Setting | Value |
|---|---|
| Name | Booking Request - User Read Own |
| Table | Booking Request (pa911_bookingrequest) |
| Web Role | Authenticated Users |
| Scope | Contact |
| Privileges | Read, Write |
| Contact Scope | Current user's Contact (via pa911_contact field) |
This allows users to read and update their own booking requests (after the Contact is linked via Power Automate).
Note: You also need an anonymous permission for the booking form:
- Web Role: Anonymous Users
- Scope: Global
- Privileges: Create only
- Navigate to Power Pages → Your Site → Security → Table Permissions
- Create or verify permission:
| Setting | Value |
|---|---|
| Name | Appointment - User Read Own Pets |
| Table | Appointment (appointment) |
| Web Role | Authenticated Users |
| Scope | Parent |
| Privileges | Read, Write |
| Parent Table | Pet (pa911_pet) |
| Contact Scope | Current user's Contact (via pa911_pet.pa911_petowner) |
This allows users to read and manage appointments for their own pets.
Service and Appointment Slot tables require read permissions for anonymous/authenticated users (for booking form dropdowns), but these are not exposed as customer-facing Entity Lists. Any views created for these tables are for staff use in model-driven apps, not for the customer portal.
Create Entity Lists for each of the three customer-facing tables. Each list will be used on dedicated portal pages.
- Navigate to Power Pages → Your Site → Content → Entity Lists
- Click New to create a new list
- Configure basic settings:
| Setting | Value |
|---|---|
| Name | My Pets |
| Table | Pet (pa911_pet) |
| View | My Pets (the view you created) |
- Configure display options:
| Setting | Value | Notes |
|---|---|---|
| Enable Search | Yes | Allow users to search their pets |
| Records Per Page | 10 | Adjust based on data volume |
| Show View Selector | No | Hide view dropdown (using single view) |
| Show Bulk Actions | No | Disable bulk operations |
| Enable Sorting | Yes | Allow column sorting |
-
Configure actions:
- View Details: Enable (opens pet detail page)
- Edit: Enable (users can edit their pets)
- Delete: Optional (typically disabled to prevent accidental deletion)
-
Click Save
- Navigate to Power Pages → Your Site → Content → Entity Lists
- Click New to create a new list
- Configure basic settings:
| Setting | Value |
|---|---|
| Name | My Booking Requests |
| Table | Booking Request (pa911_bookingrequest) |
| View | My Booking Requests (the view you created) |
-
Configure display options (same as My Pets list above)
-
Configure actions:
- View Details: Enable
- Edit: Enable (users can update their requests)
- Delete: Disable (use status changes instead)
-
Click Save
- Navigate to Power Pages → Your Site → Content → Entity Lists
- Click New to create a new list
- Configure basic settings:
| Setting | Value |
|---|---|
| Name | My Appointments |
| Table | Appointment (appointment) |
| View | My Active Appointments (default view) |
-
Configure display options (same as above)
-
If you created both Active and History views, enable Show View Selector so users can switch between them
-
Configure actions:
- View Details: Enable
- Edit: Enable (users can update/cancel appointments)
- Delete: Disable (use cancellation status instead)
-
Click Save
For "View Details" actions, create detail pages for each entity type. These pages will display Entity Forms in read-only or edit mode.
-
Navigate to Power Pages → Your Site → Content → Web Pages
-
Create new page:
- Name: Pet Details
- Partial URL:
pet-details - Parent Page: My Pets (or appropriate parent)
-
Add Entity Form:
{% entityform name:"Pet View Form" mode:"readonly" %} -
Configure Entity Form:
- Table: Pet (
pa911_pet) - Mode: Read-only or Edit (based on requirements)
- Fields: Display pet fields (name, species, breed, date of birth, weight, notes)
- Table: Pet (
-
Create new page:
- Name: Booking Request Details
- Partial URL:
booking-request-details - Parent Page: My Booking Requests
-
Add Entity Form:
{% entityform name:"Booking Request View Form" mode:"readonly" %} -
Configure Entity Form:
- Table: Booking Request (
pa911_bookingrequest) - Mode: Read-only or Edit
- Fields: Display booking request fields
- Table: Booking Request (
-
Create new page:
- Name: Appointment Details
- Partial URL:
appointment-details - Parent Page: My Appointments
-
Add Entity Form:
{% entityform name:"Appointment View Form" mode:"readonly" %} -
Configure Entity Form:
- Table: Appointment (
appointment) - Mode: Read-only or Edit
- Fields: Display appointment fields (subject, scheduled start/end, pet, service, status)
- Table: Appointment (
Create dedicated pages for each Entity List. These pages will be part of the authenticated customer portal area.
-
Navigate to Power Pages → Your Site → Content → Web Pages
-
Create new page:
- Name: My Pets
- Partial URL:
my-pets - Parent Page: Dashboard (or appropriate authenticated parent)
-
Add Entity List to page:
<div class="container mt-4"> <h1>My Pets</h1> <p class="lead">Manage your pets' information and medical records.</p> {% entitylist name:"My Pets" %} <div class="mt-3"> <a href="/pet-form" class="btn btn-primary">Add New Pet</a> </div> </div>
-
Page Permissions:
- Allow Authenticated Users to view
- Require login to access
-
Create new page:
- Name: My Booking Requests
- Partial URL:
my-booking-requests - Parent Page: Dashboard
-
Add Entity List:
<div class="container mt-4"> <h1>My Booking Requests</h1> <p class="lead">View and manage your appointment booking requests.</p> {% entitylist name:"My Booking Requests" %} <div class="mt-3"> <a href="/book-appointment" class="btn btn-primary">Request New Appointment</a> </div> </div>
-
Page Permissions:
- Allow Authenticated Users to view
- Require login to access
-
Create new page:
- Name: My Appointments
- Partial URL:
my-appointments - Parent Page: Dashboard
-
Add Entity List:
<div class="container mt-4"> <h1>My Appointments</h1> <p class="lead">View your active appointments and appointment history.</p> {% entitylist name:"My Appointments" %} </div>
-
Page Permissions:
- Allow Authenticated Users to view
- Require login to access
The Dashboard is the default landing page for authenticated users. It displays summary sections for each entity type with "View all" links.
-
Create new page:
- Name: Dashboard
- Partial URL:
dashboard - Parent Page: Home (or root)
-
Add summary sections using Liquid and Entity Lists:
<div class="container mt-4"> <h1>Welcome, {{ user.firstname }}!</h1> <p class="lead">Here's an overview of your account.</p> <!-- My Pets Summary --> <div class="card mb-4"> <div class="card-header d-flex justify-content-between align-items-center"> <h2>My Pets</h2> <a href="/my-pets" class="btn btn-sm btn-outline-primary">View All</a> </div> <div class="card-body"> {% entitylist name:"My Pets" recordsperpage:5 %} </div> </div> <!-- My Active Appointments Summary --> <div class="card mb-4"> <div class="card-header d-flex justify-content-between align-items-center"> <h2>Active Appointments</h2> <a href="/my-appointments" class="btn btn-sm btn-outline-primary">View All</a> </div> <div class="card-body"> {% entitylist name:"My Appointments" view:"My Active Appointments" recordsperpage:5 %} </div> </div> <!-- My Booking Requests Summary --> <div class="card mb-4"> <div class="card-header d-flex justify-content-between align-items-center"> <h2>Booking Requests</h2> <a href="/my-booking-requests" class="btn btn-sm btn-outline-primary">View All</a> </div> <div class="card-body"> {% entitylist name:"My Booking Requests" recordsperpage:5 %} </div> </div> </div>
-
Page Permissions:
- Allow Authenticated Users to view
- Require login to access
- Configure as default landing page for authenticated users (via site settings or login redirect)
Note: The recordsperpage:5 parameter limits the summary lists to 5 items. Users can click "View All" to see the full list on the dedicated page.
Customize the list display with Liquid on each page. Examples are shown in Step 5 above. You can add:
- Page headers and descriptions
- Action buttons (e.g., "Add New Pet", "Request New Appointment")
- Custom HTML structure around the Entity List
- Conditional content based on user roles or data
Add custom CSS to web files or page-specific CSS:
.entitylist-table {
border-collapse: collapse;
width: 100%;
}
.entitylist-table th {
background-color: #f8f9fa;
font-weight: bold;
padding: 12px;
text-align: left;
}
.entitylist-table td {
padding: 10px;
border-bottom: 1px solid #dee2e6;
}
.entitylist-table tr:hover {
background-color: #f8f9fa;
}For the Dashboard summary sections, you can use Bootstrap cards or custom styling:
.dashboard-summary-card {
margin-bottom: 2rem;
border: 1px solid #dee2e6;
border-radius: 0.25rem;
}
.dashboard-summary-card .card-header {
background-color: #f8f9fa;
padding: 1rem;
border-bottom: 1px solid #dee2e6;
}Entity Lists automatically provide search functionality:
- Users can type in search box
- Searches across all displayed columns
- Real-time filtering as user types
Filter lists using URL parameters:
{% assign statusFilter = request.params['status'] %}
{% if statusFilter %}
{% entitylist name:"My Booking Requests" view:"My Booking Requests - Filtered" %}
{% else %}
{% entitylist name:"My Booking Requests" %}
{% endif %}Entity Lists automatically paginate:
- Shows "Records Per Page" setting
- Displays page numbers
- Shows "Previous" and "Next" buttons
Override default pagination:
- Set Records Per Page to desired number
- Use JavaScript to customize pagination controls
- Implement custom pagination with FetchXML and Liquid
Configure actions available for each row:
- View: Opens detail page
- Edit: Opens edit form (if permissions allow)
- Delete: Deletes record (if permissions allow)
- Custom Actions: Add custom buttons with JavaScript
Add "Cancel Request" button:
function cancelBookingRequest(requestId) {
// Call Power Pages Web API to update status
fetch('/_api/pa911_bookingrequests(' + requestId + ')', {
method: 'PATCH',
headers: {
'Content-Type': 'application/json',
'X-Requested-With': 'XMLHttpRequest'
},
body: JSON.stringify({
'pa911_requeststatus': 144400002 // Rejected
})
})
.then(response => {
if (response.ok) {
location.reload(); // Refresh list
}
});
}- Limit Columns: Only include necessary columns in view
- Add Indexes: Index columns used in table permission scopes (e.g.,
pa911_petowner,pa911_contact) - Limit Records: Set appropriate page size
- Table Permissions: Ensure table permissions are properly scoped to reduce data volume automatically
Entity Lists use server-side caching:
- Data is cached for performance
- Cache refreshes periodically
- Consider cache duration for real-time data needs
Display related data from multiple tables in views:
- Use FetchXML in view with
link-entityto join related tables - Include related table columns (e.g.,
pa911_pet.pa911_namefor pet name in appointments) - Entity List will display joined data automatically
Example: In the Appointment view, include pa911_pet.pa911_name to show the pet's name directly in the list.
Show different lists or content based on user role or data:
{% if user.roles contains 'Administrator' %}
{% entitylist name:"All Booking Requests" %}
{% else %}
{% entitylist name:"My Booking Requests" %}
{% endif %}Switch views based on URL parameters:
{% assign viewName = request.params['view'] | default: 'My Active Appointments' %}
{% entitylist name:"My Appointments" view:viewName %}This allows users to switch between "My Active Appointments" and "My Appointment History" views via URL parameters.
Display helpful messages when lists are empty:
{% entitylist name:"My Pets" %}
{% if entities.pa911_pet.total_record_count == 0 %}
<div class="alert alert-info mt-3">
<p>You haven't added any pets yet. <a href="/pet-form">Add your first pet</a> to get started!</p>
</div>
{% endif %}Service and Appointment Slot tables are not exposed as customer-facing Entity Lists. If you create views for these tables, they are for staff use in model-driven apps or Power Automate flows, not for the customer portal.
If needed for internal processes:
- Active Services: All active services for staff reference
- Service Catalog: Services with pricing and duration details
If needed for internal processes:
- Available Slots: Slots available for booking
- Booked Slots: Slots that have been assigned to appointments
- Upcoming Slots: Future slots by service type
These views are managed in Dataverse but are not used in Power Pages Entity Lists.
Issue: List shows no records
- Check: Table permissions are configured correctly (Contact scope for Pets, Booking Requests, Appointments)
- Check: User has appropriate web role (Authenticated Users)
- Check: For Booking Requests, verify
pa911_contactis linked (set by Power Automate flow) - Check: For Appointments, verify the pet's owner matches the current user's Contact
- Check: View is set as the active view or is properly selected in the Entity List configuration
Issue: Search not working
- Check: "Enable Search" is enabled in Entity List settings
- Check: Columns in view are searchable (text fields are searchable by default)
- Check: Table permissions allow read access
Issue: Actions not appearing
- Check: Table permissions include appropriate privileges (Read and Write for edit actions)
- Check: Action settings are enabled in Entity List configuration
- Check: Detail/edit pages exist and are accessible (if using "View Details" action)
Issue: Performance issues
- Check: Table permissions are properly scoped (Contact/Account scope reduces data volume automatically)
- Check: Number of columns is reasonable (limit to essential fields)
- Check: Records per page is not too high (10-20 records is typical)
- Check: Indexes are created on columns used in table permission scopes (especially
pa911_petowner,pa911_contact)
Issue: Dashboard summary lists showing too many records
- Check: Use
recordsperpage:5parameter in Entity List tag to limit summary display - Check: Verify "View All" links point to correct detail pages
- Keep Views Focused: One view per use case
- Limit Columns: Only show necessary information
- Sort Appropriately: Default sort by most relevant field
- Use OOTB Active Views: Consider using the default active view if it meets your needs, or create custom views for specific use cases
- Principle of Least Privilege: Grant minimum necessary access
- Scope Correctly: Use Contact/Account scope for user-specific data
- Test Permissions: Verify users see only their data
- Clear Labels: Use descriptive view and list names
- Helpful Messages: Show messages when no records found
- Quick Actions: Provide easy access to common actions
- Responsive Design: Ensure lists work on mobile devices
- Custom Web Templates - Build custom components for enhanced data display
- Power Automate Integration - Add automation to list actions