Repository: getredash/redash

Issue:
The item count DashBoards View displayed per page is not correct
### Issue Summary

The item count DashBoards view displayed per page is not correct. By default, 20/page, but it actually shows only 12 items. If I switch to 5/page, it only shows 2 items. It can be reproduced on the deploy preview. https://redash-preview.netlify.app/dashboards?order=name&page=1&page_size=5

![image](https://user-images.githubusercontent.com/8188177/114211400-2c746580-9993-11eb-87a4-b5da5e3aabfc.png)


### Technical details:

* Redash Version: 9.0.0-beta (67263e1b)
* Browser/OS: Chrome 89.0.4389.114
* How did you install Redash: Docker



Discussion:
It's because of an issue with the `all` query. Haven't debugged the query yet, but here's why:

![image](https://user-images.githubusercontent.com/1129974/117486456-4b144f00-af87-11eb-86fc-bad8d26b5d82.png)

Presumably because of some join leading to extra rows in the query
Found the root cause here: https://github.com/getredash/redash/pull/5267/files#r628401694

Hi there, I can't reproduce this on the latest tip of master.
@susodapop I just tested the latest image on dockerhub ( redash:latest) and the bug is still present. 
Thank you @bratao. I have reproduced it locally now. Working on a patch today.

Resolving patch:
diff --git a/redash/models/__init__.py b/redash/models/__init__.py
--- a/redash/models/__init__.py
+++ b/redash/models/__init__.py
@@ -1120,7 +1120,7 @@ def all(cls, org, group_ids, user_id):
                 joinedload(Dashboard.user).load_only(
                     "id", "name", "_profile_image_url", "email"
                 )
-            )
+            ).distinct(Dashboard.created_at, Dashboard.slug)
             .outerjoin(Widget)
             .outerjoin(Visualization)
             .outerjoin(Query)


Test patch:
diff --git a/tests/models/test_dashboards.py b/tests/models/test_dashboards.py
--- a/tests/models/test_dashboards.py
+++ b/tests/models/test_dashboards.py
@@ -50,3 +50,32 @@ def test_returns_drafts_by_the_user(self):
         # not using self.assertIn/NotIn because otherwise this fails :O
         self.assertTrue(d in dashboards)
         self.assertFalse(d2 in dashboards)
+
+
+    def test_returns_correct_number_of_dashboards(self):
+        # Solving https://github.com/getredash/redash/issues/5466
+        
+        usr = self.factory.create_user()
+
+        ds1 = self.factory.create_data_source()
+        ds2 = self.factory.create_data_source()
+
+        qry1 = self.factory.create_query(data_source=ds1, user=usr)
+        qry2 = self.factory.create_query(data_source=ds2, user=usr)
+
+        viz1 = self.factory.create_visualization(query_rel=qry1, )
+        viz2 = self.factory.create_visualization(query_rel=qry2, )
+
+        def create_dashboard():
+            dash = self.factory.create_dashboard(name="boy howdy", user=usr)
+            self.factory.create_widget(dashboard=dash, visualization=viz1)
+            self.factory.create_widget(dashboard=dash, visualization=viz2)
+
+            return dash
+
+        d1 = create_dashboard()
+        d2 = create_dashboard()
+        
+        results = Dashboard.all(self.factory.org, usr.group_ids, usr.id)
+
+        self.assertEqual(2, results.count(), "The incorrect number of dashboards were returned")