Repository: diesel-rs/diesel (language: rust)

Issue:
MultiConnection not usable for queries containing `Selectable` or boxed queries.
<!--
If you want to report a bug, we added some points below which help us track down the problem faster.
-->

## Setup

### Versions

- **Rust:**
- **Diesel:** [e548447](https://github.com/diesel-rs/diesel/commit/e5484477b11eeae13054ab4c3b3a006d9eddfe82) 
- **Database:**
- **Operating System**

### Feature Flags

- **diesel: sqlite postgres**

## Problem Description


### What are you trying to accomplish?

I've tried the following code:

```rust
use diesel::prelude::*;

table! {
    users {
        id -> Integer,
        name -> Text,
    }
}

#[derive(Selectable, Queryable)]
struct User {
    id: i32,
}

#[derive(diesel::MultiConnection)]
enum DbConnection {
    Sqlite(SqliteConnection),
    Pg(PgConnection)
}

fn main() {
    let conn = &mut DbConnection::establish("…").unwrap();

    let u = users::table.into_boxed().load::<(i32, String)>(conn);

    let u = users::table
        .select(User::as_select())
        .load(conn);
}

```


### What is the expected output?

Code compiles


### What is the actual output?

Code does not compile:

```rust
error[E0277]: the trait bound `BoxedSelectStatement<'_, (diesel::sql_types::Integer, diesel::sql_types::Text), FromClause<users::table>, multi_connection_impl::backend::MultiBackend>: QueryFragment<Sqlite>` is not satisfied
    --> src/main.rs:24:61
     |
24   |     let u = users::table.into_boxed().load::<(i32, String)>(conn);
     |                                       ----                  ^^^^ the trait `QueryFragment<Sqlite>` is not implemented for `BoxedSelectStatement<'_, (diesel::sql_types::Integer, diesel::sql_types::Text), FromClause<users::table>, multi_connection_impl::backend::MultiBackend>`
     |                                       |
     |                                       required by a bound introduced by this call
     |
     = help: the following other types implement trait `QueryFragment<DB, SP>`:
               <BoxedSelectStatement<'a, ST, QS, DB, GB> as QueryFragment<DB, AnsiSqlSelectStatement>>
               <BoxedSelectStatement<'a, ST, QS, DB, GB> as QueryFragment<DB>>
               <BoxedSelectStatement<'a, ST, QS, multi_connection_impl::backend::MultiBackend, GB> as QueryFragment<multi_connection_impl::backend::MultiBackend, MultiSelectStatementSyntax>>
note: required for `BoxedSelectStatement<'_, (Integer, Text), FromClause<table>, MultiBackend>` to implement `QueryFragment<multi_connection_impl::backend::MultiBackend, MultiSelectStatementSyntax>`
    --> src/main.rs:15:10
     |
15   | #[derive(diesel::MultiConnection)]
     |          ^^^^^^^^^^^^^^^^^^^^^^^ unsatisfied trait bound introduced in this `derive` macro
     = note: the full type name has been written to '/tmp/diesel_test/target/debug/deps/diesel_test-e9839cd4beffff40.long-type-6862964700214725501.txt'
     = note: 1 redundant requirement hidden
     = note: required for `BoxedSelectStatement<'_, (Integer, Text), FromClause<table>, MultiBackend>` to implement `QueryFragment<multi_connection_impl::backend::MultiBackend>`
     = note: the full type name has been written to '/tmp/diesel_test/target/debug/deps/diesel_test-e9839cd4beffff40.long-type-17859806514065189679.txt'
     = note: required for `BoxedSelectStatement<'_, (Integer, Text), FromClause<table>, MultiBackend>` to implement `LoadQuery<'_, DbConnection, (i32, String)>`
     = note: the full type name has been written to '/tmp/diesel_test/target/debug/deps/diesel_test-e9839cd4beffff40.long-type-17859806514065189679.txt'
note: required by a bound in `diesel::RunQueryDsl::load`
    --> /home/weiznich/Documents/rust/diesel/diesel/src/query_dsl/mod.rs:1543:15
     |
1543 |         Self: LoadQuery<'query, Conn, U>,
     |               ^^^^^^^^^^^^^^^^^^^^^^^^^^ required by this bound in `RunQueryDsl::load`
     = note: this error originates in the derive macro `diesel::MultiConnection` (in Nightly builds, run with -Z macro-backtrace for more info)

error[E0277]: the trait bound `BoxedSelectStatement<'_, (diesel::sql_types::Integer, diesel::sql_types::Text), FromClause<users::table>, multi_connection_impl::backend::MultiBackend>: QueryFragment<Pg>` is not satisfied
    --> src/main.rs:24:61
     |
24   |     let u = users::table.into_boxed().load::<(i32, String)>(conn);
     |                                       ----                  ^^^^ the trait `QueryFragment<Pg>` is not implemented for `BoxedSelectStatement<'_, (diesel::sql_types::Integer, diesel::sql_types::Text), FromClause<users::table>, multi_connection_impl::backend::MultiBackend>`
     |                                       |
     |                                       required by a bound introduced by this call
     |
     = help: the following other types implement trait `QueryFragment<DB, SP>`:
               <BoxedSelectStatement<'a, ST, QS, DB, GB> as QueryFragment<DB, AnsiSqlSelectStatement>>
               <BoxedSelectStatement<'a, ST, QS, DB, GB> as QueryFragment<DB>>
               <BoxedSelectStatement<'a, ST, QS, multi_connection_impl::backend::MultiBackend, GB> as QueryFragment<multi_connection_impl::backend::MultiBackend, MultiSelectStatementSyntax>>
note: required for `BoxedSelectStatement<'_, (Integer, Text), FromClause<table>, MultiBackend>` to implement `QueryFragment<multi_connection_impl::backend::MultiBackend, MultiSelectStatementSyntax>`
    --> src/main.rs:15:10
     |
15   | #[derive(diesel::MultiConnection)]
     |          ^^^^^^^^^^^^^^^^^^^^^^^ unsatisfied trait bound introduced in this `derive` macro
     = note: the full type name has been written to '/tmp/diesel_test/target/debug/deps/diesel_test-e9839cd4beffff40.long-type-6862964700214725501.txt'
     = note: 1 redundant requirement hidden
     = note: required for `BoxedSelectStatement<'_, (Integer, Text), FromClause<table>, MultiBackend>` to implement `QueryFragment<multi_connection_impl::backend::MultiBackend>`
     = note: the full type name has been written to '/tmp/diesel_test/target/debug/deps/diesel_test-e9839cd4beffff40.long-type-17859806514065189679.txt'
     = note: required for `BoxedSelectStatement<'_, (Integer, Text), FromClause<table>, MultiBackend>` to implement `LoadQuery<'_, DbConnection, (i32, String)>`
     = note: the full type name has been written to '/tmp/diesel_test/target/debug/deps/diesel_test-e9839cd4beffff40.long-type-17859806514065189679.txt'
note: required by a bound in `diesel::RunQueryDsl::load`
    --> /home/weiznich/Documents/rust/diesel/diesel/src/query_dsl/mod.rs:1543:15
     |
1543 |         Self: LoadQuery<'query, Conn, U>,
     |               ^^^^^^^^^^^^^^^^^^^^^^^^^^ required by this bound in `RunQueryDsl::load`
     = note: this error originates in the derive macro `diesel::MultiConnection` (in Nightly builds, run with -Z macro-backtrace for more info)

error[E0277]: the trait bound `LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>: IntoBoxedClause<'_, multi_connection_impl::backend::MultiBackend>` is not satisfied
  --> src/main.rs:24:26
   |
24 |     let u = users::table.into_boxed().load::<(i32, String)>(conn);
   |                          ^^^^^^^^^^ the trait `IntoBoxedClause<'_, multi_connection_impl::backend::MultiBackend>` is not implemented for `LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>`
   |
   = help: the trait `IntoBoxedClause<'a, Sqlite>` is implemented for `LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>`
   = note: required for `SelectStatement<FromClause<users::table>>` to implement `BoxedDsl<'_, multi_connection_impl::backend::MultiBackend>`

error[E0277]: the trait bound `LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>: IntoBoxedClause<'_, multi_connection_impl::backend::MultiBackend>` is not satisfied
    --> src/main.rs:24:26
     |
24   |     let u = users::table.into_boxed().load::<(i32, String)>(conn);
     |                          ^^^^^^^^^^ the trait `IntoBoxedClause<'_, multi_connection_impl::backend::MultiBackend>` is not implemented for `LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>`
     |
     = help: the trait `IntoBoxedClause<'a, Sqlite>` is implemented for `LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>`
     = note: required for `SelectStatement<FromClause<users::table>>` to implement `BoxedDsl<'_, multi_connection_impl::backend::MultiBackend>`
     = note: 1 redundant requirement hidden
     = note: required for `users::table` to implement `BoxedDsl<'_, multi_connection_impl::backend::MultiBackend>`
note: required by a bound in `diesel::QueryDsl::into_boxed`
    --> /home/weiznich/Documents/rust/diesel/diesel/src/query_dsl/mod.rs:1299:15
     |
1299 |         Self: methods::BoxedDsl<'a, DB>,
     |               ^^^^^^^^^^^^^^^^^^^^^^^^^ required by this bound in `QueryDsl::into_boxed`

error[E0277]: the trait bound `SelectBy<User, multi_connection_impl::backend::MultiBackend>: QueryFragment<Sqlite>` is not satisfied
    --> src/main.rs:28:15
     |
28   |         .load(conn);
     |          ---- ^^^^ the trait `QueryFragment<Sqlite>` is not implemented for `SelectBy<User, multi_connection_impl::backend::MultiBackend>`
     |          |
     |          required by a bound introduced by this call
     |
     = help: the trait `QueryFragment<DB>` is implemented for `SelectBy<T, DB>`
     = note: required for `diesel::query_builder::select_clause::SelectClause<SelectBy<User, multi_connection_impl::backend::MultiBackend>>` to implement `QueryFragment<Sqlite>`
     = note: 4 redundant requirements hidden
     = note: required for `SelectStatement<FromClause<table>, SelectClause<SelectBy<User, MultiBackend>>>` to implement `QueryFragment<multi_connection_impl::backend::MultiBackend>`
     = note: the full type name has been written to '/tmp/diesel_test/target/debug/deps/diesel_test-e9839cd4beffff40.long-type-13019818345722010715.txt'
     = note: required for `SelectStatement<FromClause<table>, SelectClause<SelectBy<User, MultiBackend>>>` to implement `LoadQuery<'_, DbConnection, User>`
     = note: the full type name has been written to '/tmp/diesel_test/target/debug/deps/diesel_test-e9839cd4beffff40.long-type-13019818345722010715.txt'
note: required by a bound in `diesel::RunQueryDsl::load`
    --> /home/weiznich/Documents/rust/diesel/diesel/src/query_dsl/mod.rs:1543:15
     |
1543 |         Self: LoadQuery<'query, Conn, U>,
     |               ^^^^^^^^^^^^^^^^^^^^^^^^^^ required by this bound in `RunQueryDsl::load`

error[E0277]: the trait bound `SelectBy<User, multi_connection_impl::backend::MultiBackend>: QueryFragment<Pg>` is not satisfied
    --> src/main.rs:28:15
     |
28   |         .load(conn);
     |          ---- ^^^^ the trait `QueryFragment<Pg>` is not implemented for `SelectBy<User, multi_connection_impl::backend::MultiBackend>`
     |          |
     |          required by a bound introduced by this call
     |
     = help: the trait `QueryFragment<DB>` is implemented for `SelectBy<T, DB>`
     = note: required for `diesel::query_builder::select_clause::SelectClause<SelectBy<User, multi_connection_impl::backend::MultiBackend>>` to implement `QueryFragment<Pg>`
     = note: 4 redundant requirements hidden
     = note: required for `SelectStatement<FromClause<table>, SelectClause<SelectBy<User, MultiBackend>>>` to implement `QueryFragment<multi_connection_impl::backend::MultiBackend>`
     = note: the full type name has been written to '/tmp/diesel_test/target/debug/deps/diesel_test-e9839cd4beffff40.long-type-13019818345722010715.txt'
     = note: required for `SelectStatement<FromClause<table>, SelectClause<SelectBy<User, MultiBackend>>>` to implement `LoadQuery<'_, DbConnection, User>`
     = note: the full type name has been written to '/tmp/diesel_test/target/debug/deps/diesel_test-e9839cd4beffff40.long-type-13019818345722010715.txt'
note: required by a bound in `diesel::RunQueryDsl::load`
    --> /home/weiznich/Documents/rust/diesel/diesel/src/query_dsl/mod.rs:1543:15
     |
1543 |         Self: LoadQuery<'query, Conn, U>,
     |               ^^^^^^^^^^^^^^^^^^^^^^^^^^ required by this bound in `RunQueryDsl::load`

```

(That sounds that some queryfragment impls in diesel are to restrictive for using `selectable` and/or boxed queries with the new `MultiConnection` derive.


### Are you seeing any additional errors?

## Checklist

- [x] I have already looked over the [issue tracker](https://github.com/diesel-rs/diesel/issues)  and the [disussion forum](https://github.com/diesel-rs/diesel/discussions)  for similar possible closed issues.
<!--
If you are unsure if your issue is a duplicate of an existing issue please link the issue in question here
--> 
- [x] This issue can be reproduced on Rust's stable channel. (Your issue will be
  closed if this is not the case)
- [x] This issue can be reproduced without requiring a third party crate

<!--
Thank you for your submission!  You're helping make Diesel more robust 🎉

We'll try to respond as quickly as possible.
-->



Discussion / hints:
I did some work on this and it seems like that the problem with `SelectBy` is rather easy to solve by introducing the following trait:

```rust
    pub trait CompatibleBackend<DB>: Backend {}
    impl<DB> CompatibleBackend<DB> for DB where DB: Backend {}
```

then we can provide the corresponding additional impl for the generated multibackend type and restrict the `QueryFragment` impl for `SelectBy` on that.

Unfortunately that will not work for the boxed select statement case, due to the fact that a boxed select statement internally stores boxed query fragment trait objects for a specific backend type and we cannot simply convert them to something else. At that point I'm not even sure if that ever can be supported :(

Fix patch:
diff --git a/diesel/src/internal/derives.rs b/diesel/src/internal/derives.rs
index d18887ff47b7..be8929c8e486 100644
--- a/diesel/src/internal/derives.rs
+++ b/diesel/src/internal/derives.rs
@@ -58,4 +58,15 @@ pub mod multiconnection {
     pub use crate::query_builder::insert_statement::batch_insert::BatchInsert;
     #[doc(hidden)]
     pub use crate::row::private::PartialRow;
+
+    #[doc(hidden)]
+    pub use crate::query_builder::limit_clause::{LimitClause, NoLimitClause};
+    #[doc(hidden)]
+    pub use crate::query_builder::offset_clause::{NoOffsetClause, OffsetClause};
+
+    #[doc(hidden)]
+    pub use crate::query_builder::select_statement::boxed::BoxedQueryHelper;
+
+    #[doc(hidden)]
+    pub use crate::query_builder::select_statement::SelectStatementAccessor;
 }
diff --git a/diesel/src/lib.rs b/diesel/src/lib.rs
index f11c34ccfa35..f4c047eaef64 100644
--- a/diesel/src/lib.rs
+++ b/diesel/src/lib.rs
@@ -315,6 +315,7 @@ pub use diesel_derives::{
 
 pub use diesel_derives::MultiConnection;
 
+#[allow(unknown_lints, ambiguous_glob_reexports)]
 pub mod dsl {
     //! Includes various helper types and bare functions which are named too
     //! generically to be included in prelude, but are often used when using Diesel.
diff --git a/diesel/src/mysql/connection/stmt/iterator.rs b/diesel/src/mysql/connection/stmt/iterator.rs
index 6dedf11fae7e..d64cdb38d617 100644
--- a/diesel/src/mysql/connection/stmt/iterator.rs
+++ b/diesel/src/mysql/connection/stmt/iterator.rs
@@ -266,7 +266,7 @@ fn fun_with_row_iters() {
     let expected = vec![(1, String::from("Sean")), (2, String::from("Tess"))];
 
     {
-        let row_iter = conn.load(&query).unwrap();
+        let row_iter = conn.load(query).unwrap();
         for (row, expected) in row_iter.zip(&expected) {
             let row = row.unwrap();
 
@@ -281,7 +281,7 @@ fn fun_with_row_iters() {
     }
 
     {
-        let collected_rows = conn.load(&query).unwrap().collect::<Vec<_>>();
+        let collected_rows = conn.load(query).unwrap().collect::<Vec<_>>();
         assert_eq!(collected_rows.len(), 2);
         for (row, expected) in collected_rows.iter().zip(&expected) {
             let deserialized = row
@@ -297,7 +297,7 @@ fn fun_with_row_iters() {
         }
     }
 
-    let mut row_iter = conn.load(&query).unwrap();
+    let mut row_iter = conn.load(query).unwrap();
 
     let first_row = row_iter.next().unwrap().unwrap();
     let first_fields = (
diff --git a/diesel/src/pg/connection/cursor.rs b/diesel/src/pg/connection/cursor.rs
index cab624041f74..4e77dffdec84 100644
--- a/diesel/src/pg/connection/cursor.rs
+++ b/diesel/src/pg/connection/cursor.rs
@@ -170,7 +170,7 @@ mod tests {
 
         let expected = vec![(1, String::from("Sean")), (2, String::from("Tess"))];
 
-        let row_iter = LoadConnection::<DefaultLoadingMode>::load(conn, &query).unwrap();
+        let row_iter = LoadConnection::<DefaultLoadingMode>::load(conn, query).unwrap();
         for (row, expected) in row_iter.zip(&expected) {
             let row = row.unwrap();
 
@@ -184,7 +184,7 @@ mod tests {
         }
 
         {
-            let collected_rows = LoadConnection::<DefaultLoadingMode>::load(conn, &query)
+            let collected_rows = LoadConnection::<DefaultLoadingMode>::load(conn, query)
                 .unwrap()
                 .collect::<Vec<_>>();
 
@@ -203,7 +203,7 @@ mod tests {
             }
         }
 
-        let mut row_iter = LoadConnection::<DefaultLoadingMode>::load(conn, &query).unwrap();
+        let mut row_iter = LoadConnection::<DefaultLoadingMode>::load(conn, query).unwrap();
 
         let first_row = row_iter.next().unwrap().unwrap();
         let first_fields = (first_row.get(0).unwrap(), first_row.get(1).unwrap());
@@ -327,7 +327,7 @@ mod tests {
 
         let expected = vec![(1, String::from("Sean")), (2, String::from("Tess"))];
 
-        let row_iter = LoadConnection::<PgRowByRowLoadingMode>::load(conn, &query).unwrap();
+        let row_iter = LoadConnection::<PgRowByRowLoadingMode>::load(conn, query).unwrap();
         for (row, expected) in row_iter.zip(&expected) {
             let row = row.unwrap();
 
@@ -341,7 +341,7 @@ mod tests {
         }
 
         {
-            let collected_rows = LoadConnection::<PgRowByRowLoadingMode>::load(conn, &query)
+            let collected_rows = LoadConnection::<PgRowByRowLoadingMode>::load(conn, query)
                 .unwrap()
                 .collect::<Vec<_>>();
 
@@ -360,7 +360,7 @@ mod tests {
             }
         }
 
-        let mut row_iter = LoadConnection::<PgRowByRowLoadingMode>::load(conn, &query).unwrap();
+        let mut row_iter = LoadConnection::<PgRowByRowLoadingMode>::load(conn, query).unwrap();
 
         let first_row = row_iter.next().unwrap().unwrap();
         let first_fields = (first_row.get(0).unwrap(), first_row.get(1).unwrap());
diff --git a/diesel/src/query_builder/select_statement/boxed.rs b/diesel/src/query_builder/select_statement/boxed.rs
index c6935c9fbe1d..05e96a5f20b6 100644
--- a/diesel/src/query_builder/select_statement/boxed.rs
+++ b/diesel/src/query_builder/select_statement/boxed.rs
@@ -133,8 +133,26 @@ impl<'a, ST, DB, GB> BoxedSelectStatement<'a, ST, NoFromClause, DB, GB> {
     }
 }
 
-impl<'a, ST, QS, DB, GB> BoxedSelectStatement<'a, ST, QS, DB, GB> {
-    pub(crate) fn build_query<'b, 'c>(
+// that's a trait to control who can access these method
+#[doc(hidden)] // exported via internal::derives::multiconnection
+pub trait BoxedQueryHelper<'a, QS, DB> {
+    fn build_query<'b, 'c>(
+        &'b self,
+        out: AstPass<'_, 'c, DB>,
+        where_clause_handler: impl Fn(
+            &'b BoxedWhereClause<'a, DB>,
+            AstPass<'_, 'c, DB>,
+        ) -> QueryResult<()>,
+    ) -> QueryResult<()>
+    where
+        DB: Backend,
+        QS: QueryFragment<DB>,
+        BoxedLimitOffsetClause<'a, DB>: QueryFragment<DB>,
+        'b: 'c;
+}
+
+impl<'a, ST, QS, DB, GB> BoxedQueryHelper<'a, QS, DB> for BoxedSelectStatement<'a, ST, QS, DB, GB> {
+    fn build_query<'b, 'c>(
         &'b self,
         mut out: AstPass<'_, 'c, DB>,
         where_clause_handler: impl Fn(
diff --git a/diesel/src/query_builder/select_statement/mod.rs b/diesel/src/query_builder/select_statement/mod.rs
index 05715c0c0784..1edd620095f7 100644
--- a/diesel/src/query_builder/select_statement/mod.rs
+++ b/diesel/src/query_builder/select_statement/mod.rs
@@ -92,6 +92,100 @@ pub struct SelectStatement<
     pub(crate) locking: Locking,
 }
 
+/// Semi-Private trait for containing get-functions for all `SelectStatement` fields
+//
+// This is used by `#[derive(MultiConnection)]`
+pub trait SelectStatementAccessor {
+    /// The type of the select clause
+    type Select;
+    /// The type of the from clause
+    type From;
+    /// The type of the distinct clause
+    type Distinct;
+    /// The type of the where clause
+    type Where;
+    /// The type of the order clause
+    type Order;
+    /// The type of the limit offset clause
+    type LimitOffset;
+    /// The type of the group by clause
+    type GroupBy;
+    /// The type of the having clause
+    type Having;
+    /// The type of the locking clause
+    type Locking;
+
+    /// Access the select clause
+    fn select_clause(&self) -> &Self::Select;
+    /// Access the from clause
+    #[allow(clippy::wrong_self_convention)] // obviously wrong, as `from` refers to the clause name
+    fn from_clause(&self) -> &Self::From;
+    /// Access the distinct clause
+    fn distinct_clause(&self) -> &Self::Distinct;
+    /// Access the where clause
+    fn where_clause(&self) -> &Self::Where;
+    /// Access the order clause
+    fn order_clause(&self) -> &Self::Order;
+    /// Access the limit_offset clause
+    fn limit_offset_clause(&self) -> &Self::LimitOffset;
+    /// Access the group by clause
+    fn group_by_clause(&self) -> &Self::GroupBy;
+    /// Access the having clause
+    fn having_clause(&self) -> &Self::Having;
+    /// Access the locking clause
+    fn locking_clause(&self) -> &Self::Locking;
+}
+
+impl<F, S, D, W, O, LOf, G, H, LC> SelectStatementAccessor
+    for SelectStatement<F, S, D, W, O, LOf, G, H, LC>
+{
+    type Select = S;
+    type From = F;
+    type Distinct = D;
+    type Where = W;
+    type Order = O;
+    type LimitOffset = LOf;
+    type GroupBy = G;
+    type Having = H;
+    type Locking = LC;
+
+    fn select_clause(&self) -> &Self::Select {
+        &self.select
+    }
+
+    fn from_clause(&self) -> &Self::From {
+        &self.from
+    }
+
+    fn distinct_clause(&self) -> &Self::Distinct {
+        &self.distinct
+    }
+
+    fn where_clause(&self) -> &Self::Where {
+        &self.where_clause
+    }
+
+    fn order_clause(&self) -> &Self::Order {
+        &self.order
+    }
+
+    fn limit_offset_clause(&self) -> &Self::LimitOffset {
+        &self.limit_offset
+    }
+
+    fn group_by_clause(&self) -> &Self::GroupBy {
+        &self.group_by
+    }
+
+    fn having_clause(&self) -> &Self::Having {
+        &self.having
+    }
+
+    fn locking_clause(&self) -> &Self::Locking {
+        &self.locking
+    }
+}
+
 impl<F, S, D, W, O, LOf, G, H, LC> SelectStatement<F, S, D, W, O, LOf, G, H, LC> {
     #[allow(clippy::too_many_arguments)]
     pub(crate) fn new(
diff --git a/diesel/src/sqlite/connection/row.rs b/diesel/src/sqlite/connection/row.rs
index 13d3b6283bc5..d5a86de42fd5 100644
--- a/diesel/src/sqlite/connection/row.rs
+++ b/diesel/src/sqlite/connection/row.rs
@@ -168,7 +168,7 @@ fn fun_with_row_iters() {
 
     let expected = vec![(1, String::from("Sean")), (2, String::from("Tess"))];
 
-    let row_iter = conn.load(&query).unwrap();
+    let row_iter = conn.load(query).unwrap();
     for (row, expected) in row_iter.zip(&expected) {
         let row = row.unwrap();
 
@@ -182,7 +182,7 @@ fn fun_with_row_iters() {
     }
 
     {
-        let collected_rows = conn.load(&query).unwrap().collect::<Vec<_>>();
+        let collected_rows = conn.load(query).unwrap().collect::<Vec<_>>();
 
         for (row, expected) in collected_rows.iter().zip(&expected) {
             let deserialized = row
@@ -199,7 +199,7 @@ fn fun_with_row_iters() {
         }
     }
 
-    let mut row_iter = conn.load(&query).unwrap();
+    let mut row_iter = conn.load(query).unwrap();
 
     let first_row = row_iter.next().unwrap().unwrap();
     let first_fields = (first_row.get(0).unwrap(), first_row.get(1).unwrap());
diff --git a/diesel/src/sqlite/query_builder/query_fragment_impls.rs b/diesel/src/sqlite/query_builder/query_fragment_impls.rs
index 4c50f6c70c14..c7cfb0bfbda5 100644
--- a/diesel/src/sqlite/query_builder/query_fragment_impls.rs
+++ b/diesel/src/sqlite/query_builder/query_fragment_impls.rs
@@ -1,3 +1,4 @@
+use crate::query_builder::select_statement::boxed::BoxedQueryHelper;
 use crate::query_builder::upsert::into_conflict_clause::OnConflictSelectWrapper;
 use crate::query_builder::where_clause::BoxedWhereClause;
 use crate::query_builder::where_clause::WhereClause;
diff --git a/diesel_derives/src/lib.rs b/diesel_derives/src/lib.rs
index e9dbb3b0c153..8a1edd709a6d 100644
--- a/diesel_derives/src/lib.rs
+++ b/diesel_derives/src/lib.rs
@@ -735,7 +735,7 @@ pub fn derive_queryable(input: TokenStream) -> TokenStream {
 ///     DB: Backend,
 ///     String: FromSql<ST, DB>,
 /// {
-///     fn from_sql(bytes: backend::RawValue<DB>) -> deserialize::Result<Self> {
+///     fn from_sql(bytes: DB::RawValue<'_>) -> deserialize::Result<Self> {
 ///         String::from_sql(bytes)
 ///             .map(|s| LowercaseString(s.to_lowercase()))
 ///     }
diff --git a/diesel_derives/src/multiconnection.rs b/diesel_derives/src/multiconnection.rs
index 61922da6ede1..a18b0b35dc61 100644
--- a/diesel_derives/src/multiconnection.rs
+++ b/diesel_derives/src/multiconnection.rs
@@ -993,20 +993,9 @@ fn generate_querybuilder(connection_types: &[ConnectionVariant]) -> TokenStream
     };
 
     let query_fragment_impls = IntoIterator::into_iter([
-        quote::quote!{
-            #query_fragment for diesel::internal::derives::multiconnection::BoxedLimitOffsetClause<'_, super::backend::MultiBackend>
-        },
         quote::quote!{
             <L, O> #query_fragment for diesel::internal::derives::multiconnection::LimitOffsetClause<L, O>
         },
-        quote::quote! {
-            <F, S, D, W, O, LOf, G, H, LC> diesel::query_builder::QueryFragment<super::backend::MultiBackend, super::backend::MultiSelectStatementSyntax>
-                for diesel::internal::derives::multiconnection::SelectStatement<F, S, D, W, O, LOf, G, H, LC>
-        },
-        quote::quote! {
-            <'a, ST, QS, GB> diesel::query_builder::QueryFragment<super::backend::MultiBackend, super::backend::MultiSelectStatementSyntax>
-                for diesel::internal::derives::multiconnection::BoxedSelectStatement<'a, ST, QS, super::backend::MultiBackend, GB>
-        },
         quote::quote! {
             <L, R> diesel::query_builder::QueryFragment<super::backend::MultiBackend, super::backend::MultiConcatClauseSyntax>
                 for diesel::internal::derives::multiconnection::Concat<L, R>
@@ -1094,6 +1083,148 @@ fn generate_querybuilder(connection_types: &[ConnectionVariant]) -> TokenStream
         }
 
         #(#query_fragment_impls)*
+
+        impl<F, S, D, W, O, LOf, G, H, LC>
+            diesel::query_builder::QueryFragment<
+                super::backend::MultiBackend,
+                super::backend::MultiSelectStatementSyntax,
+            >
+            for diesel::internal::derives::multiconnection::SelectStatement<
+                F,
+                S,
+                D,
+                W,
+                O,
+                LOf,
+                G,
+                H,
+                LC,
+            >
+        where
+            S: diesel::query_builder::QueryFragment<super::backend::MultiBackend>,
+            F: diesel::query_builder::QueryFragment<super::backend::MultiBackend>,
+            D: diesel::query_builder::QueryFragment<super::backend::MultiBackend>,
+            W: diesel::query_builder::QueryFragment<super::backend::MultiBackend>,
+            O: diesel::query_builder::QueryFragment<super::backend::MultiBackend>,
+            LOf: diesel::query_builder::QueryFragment<super::backend::MultiBackend>,
+            G: diesel::query_builder::QueryFragment<super::backend::MultiBackend>,
+            H: diesel::query_builder::QueryFragment<super::backend::MultiBackend>,
+            LC: diesel::query_builder::QueryFragment<super::backend::MultiBackend>,
+        {
+            fn walk_ast<'b>(
+                &'b self,
+                mut out: diesel::query_builder::AstPass<'_, 'b, MultiBackend>,
+            ) -> diesel::QueryResult<()> {
+                use diesel::internal::derives::multiconnection::SelectStatementAccessor;
+
+                out.push_sql("SELECT ");
+                self.distinct_clause().walk_ast(out.reborrow())?;
+                self.select_clause().walk_ast(out.reborrow())?;
+                self.from_clause().walk_ast(out.reborrow())?;
+                self.where_clause().walk_ast(out.reborrow())?;
+                self.group_by_clause().walk_ast(out.reborrow())?;
+                self.having_clause().walk_ast(out.reborrow())?;
+                self.order_clause().walk_ast(out.reborrow())?;
+                self.limit_offset_clause().walk_ast(out.reborrow())?;
+                self.locking_clause().walk_ast(out.reborrow())?;
+                Ok(())
+            }
+        }
+
+        impl<'a, ST, QS, GB>
+            diesel::query_builder::QueryFragment<
+            super::backend::MultiBackend,
+            super::backend::MultiSelectStatementSyntax,
+        >
+            for diesel::internal::derives::multiconnection::BoxedSelectStatement<
+                'a,
+                ST,
+                QS,
+                super::backend::MultiBackend,
+                GB,
+            >
+        where
+            QS: diesel::query_builder::QueryFragment<super::backend::MultiBackend>
+        {
+            fn walk_ast<'b>(
+                &'b self,
+                pass: diesel::query_builder::AstPass<'_, 'b, MultiBackend>,
+            ) -> diesel::QueryResult<()> {
+                use diesel::internal::derives::multiconnection::BoxedQueryHelper;
+                self.build_query(pass, |where_clause, pass| where_clause.walk_ast(pass))
+            }
+        }
+
+        impl diesel::query_builder::QueryFragment<super::backend::MultiBackend>
+            for diesel::internal::derives::multiconnection::BoxedLimitOffsetClause<
+                '_,
+                super::backend::MultiBackend,
+            >
+        {
+            fn walk_ast<'b>(
+                &'b self,
+                mut pass: diesel::query_builder::AstPass<'_, 'b, MultiBackend>,
+            ) -> diesel::QueryResult<()> {
+                if let Some(ref limit) = self.limit {
+                    limit.walk_ast(pass.reborrow())?;
+                }
+                if let Some(ref offset) = self.offset {
+                    offset.walk_ast(pass.reborrow())?;
+                }
+                Ok(())
+            }
+        }
+
+        impl<'a> diesel::query_builder::IntoBoxedClause<'a, super::multi_connection_impl::backend::MultiBackend>
+            for diesel::internal::derives::multiconnection::LimitOffsetClause<diesel::internal::derives::multiconnection::NoLimitClause, diesel::internal::derives::multiconnection::NoOffsetClause>
+        {
+            type BoxedClause = diesel::internal::derives::multiconnection::BoxedLimitOffsetClause<'a, super::multi_connection_impl::backend::MultiBackend>;
+
+            fn into_boxed(self) -> Self::BoxedClause {
+                diesel::internal::derives::multiconnection::BoxedLimitOffsetClause {
+                    limit: None,
+                    offset: None,
+                }
+            }
+        }
+        impl<'a, L> diesel::query_builder::IntoBoxedClause<'a, super::multi_connection_impl::backend::MultiBackend>
+            for diesel::internal::derives::multiconnection::LimitOffsetClause<diesel::internal::derives::multiconnection::LimitClause<L>, diesel::internal::derives::multiconnection::NoOffsetClause>
+        where diesel::internal::derives::multiconnection::LimitClause<L>: diesel::query_builder::QueryFragment<super::backend::MultiBackend> + Send + 'static,
+        {
+            type BoxedClause = diesel::internal::derives::multiconnection::BoxedLimitOffsetClause<'a, super::multi_connection_impl::backend::MultiBackend>;
+            fn into_boxed(self) -> Self::BoxedClause {
+                diesel::internal::derives::multiconnection::BoxedLimitOffsetClause {
+                    limit: Some(Box::new(self.limit_clause)),
+                    offset: None,
+                }
+            }
+        }
+        impl<'a, O> diesel::query_builder::IntoBoxedClause<'a, super::multi_connection_impl::backend::MultiBackend>
+            for diesel::internal::derives::multiconnection::LimitOffsetClause<diesel::internal::derives::multiconnection::NoLimitClause, diesel::internal::derives::multiconnection::OffsetClause<O>>
+        where diesel::internal::derives::multiconnection::OffsetClause<O>: diesel::query_builder::QueryFragment<super::backend::MultiBackend> + Send + 'static,
+
+        {
+            type BoxedClause = diesel::internal::derives::multiconnection::BoxedLimitOffsetClause<'a, super::multi_connection_impl::backend::MultiBackend>;
+            fn into_boxed(self) -> Self::BoxedClause {
+                diesel::internal::derives::multiconnection::BoxedLimitOffsetClause {
+                    limit: None,
+                    offset: Some(Box::new(self.offset_clause)),
+                }
+            }
+        }
+        impl<'a, L, O> diesel::query_builder::IntoBoxedClause<'a, super::multi_connection_impl::backend::MultiBackend>
+            for diesel::internal::derives::multiconnection::LimitOffsetClause<diesel::internal::derives::multiconnection::LimitClause<L>, diesel::internal::derives::multiconnection::OffsetClause<O>>
+        where diesel::internal::derives::multiconnection::LimitClause<L>: diesel::query_builder::QueryFragment<super::backend::MultiBackend> + Send + 'static,
+              diesel::internal::derives::multiconnection::OffsetClause<O>: diesel::query_builder::QueryFragment<super::backend::MultiBackend> + Send + 'static,
+        {
+            type BoxedClause = diesel::internal::derives::multiconnection::BoxedLimitOffsetClause<'a, super::multi_connection_impl::backend::MultiBackend>;
+            fn into_boxed(self) -> Self::BoxedClause {
+                diesel::internal::derives::multiconnection::BoxedLimitOffsetClause {
+                    limit: Some(Box::new(self.limit_clause)),
+                    offset: Some(Box::new(self.offset_clause)),
+                }
+            }
+        }
     }
 }
 
diff --git a/diesel_migrations/src/file_based_migrations.rs b/diesel_migrations/src/file_based_migrations.rs
index b4f9df9e5243..931b9d0abfe4 100644
--- a/diesel_migrations/src/file_based_migrations.rs
+++ b/diesel_migrations/src/file_based_migrations.rs
@@ -139,7 +139,7 @@ fn migrations_directories(
     Ok(migrations_internals::migrations_directories(path)?.map(move |e| e.map_err(Into::into)))
 }
 
-fn migrations_in_directory<DB: Backend>(
+fn migrations_in_directory(
     path: &'_ Path,
 ) -> Result<impl Iterator<Item = Result<SqlFileMigration, MigrationError>> + '_, MigrationError> {
     Ok(migrations_directories(path)?.map(|entry| SqlFileMigration::from_path(&entry?.path())))
@@ -147,7 +147,7 @@ fn migrations_in_directory<DB: Backend>(
 
 impl<DB: Backend> MigrationSource<DB> for FileBasedMigrations {
     fn migrations(&self) -> migration::Result<Vec<Box<dyn Migration<DB>>>> {
-        migrations_in_directory::<DB>(&self.base_path)?
+        migrations_in_directory(&self.base_path)?
             .map(|r| Ok(Box::new(r?) as Box<dyn Migration<DB>>))
             .collect()
     }
@@ -337,15 +337,6 @@ mod tests {
         );
     }
 
-    #[cfg(feature = "sqlite")]
-    type Backend = diesel::sqlite::Sqlite;
-
-    #[cfg(feature = "postgres")]
-    type Backend = diesel::pg::Pg;
-
-    #[cfg(feature = "mysql")]
-    type Backend = diesel::mysql::Mysql;
-
     #[test]
     fn migration_paths_in_directory_ignores_files() {
         let dir = Builder::new().prefix("diesel").tempdir().unwrap();
@@ -356,7 +347,7 @@ mod tests {
         fs::create_dir(migrations_path.as_path()).unwrap();
         fs::File::create(file_path.as_path()).unwrap();
 
-        let migrations = migrations_in_directory::<Backend>(&migrations_path)
+        let migrations = migrations_in_directory(&migrations_path)
             .unwrap()
             .collect::<Result<Vec<_>, _>>()
             .unwrap();
@@ -374,7 +365,7 @@ mod tests {
         fs::create_dir(migrations_path.as_path()).unwrap();
         fs::create_dir(dot_path.as_path()).unwrap();
 
-        let migrations = migrations_in_directory::<Backend>(&migrations_path)
+        let migrations = migrations_in_directory(&migrations_path)
             .unwrap()
             .collect::<Result<Vec<_>, _>>()
             .unwrap();


Test patch:
diff --git a/diesel_compile_tests/Cargo.lock b/diesel_compile_tests/Cargo.lock
index 853e57a994b9..021b16f7f8a3 100644
--- a/diesel_compile_tests/Cargo.lock
+++ b/diesel_compile_tests/Cargo.lock
@@ -25,6 +25,12 @@ version = "1.3.2"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "bef38d45163c2f1dde094a7dfd33ccf595c92905c8f8f4fdc18d06fb1037718a"
 
+[[package]]
+name = "bitflags"
+version = "2.2.1"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "24a6904aef64d73cf10ab17ebace7befb918b82164785cb89907993be7f83813"
+
 [[package]]
 name = "bumpalo"
 version = "3.12.0"
@@ -61,7 +67,7 @@ name = "diesel"
 version = "2.0.2"
 dependencies = [
  "bigdecimal",
- "bitflags",
+ "bitflags 2.2.1",
  "byteorder",
  "chrono",
  "diesel_derives",
@@ -349,7 +355,7 @@ version = "0.2.10"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "8383f39639269cde97d255a32bdb68c047337295414940c68bdd30c2e13203ff"
 dependencies = [
- "bitflags",
+ "bitflags 1.3.2",
 ]
 
 [[package]]
diff --git a/diesel_compile_tests/tests/fail/boxed_queries_and_group_by.stderr b/diesel_compile_tests/tests/fail/boxed_queries_and_group_by.stderr
index b118bbdad0f2..bd3c46ea57bc 100644
--- a/diesel_compile_tests/tests/fail/boxed_queries_and_group_by.stderr
+++ b/diesel_compile_tests/tests/fail/boxed_queries_and_group_by.stderr
@@ -1,8 +1,8 @@
-error[E0277]: the trait bound `SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>, diesel::query_builder::group_by_clause::GroupByClause<users::columns::name>>: BoxedDsl<'_, _>` is not satisfied
+error[E0277]: the trait bound `SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<NoLimitClause, NoOffsetClause>, diesel::query_builder::group_by_clause::GroupByClause<users::columns::name>>: BoxedDsl<'_, _>` is not satisfied
   --> tests/fail/boxed_queries_and_group_by.rs:55:40
    |
 55 |     users::table.group_by(users::name).into_boxed();
-   |                                        ^^^^^^^^^^ the trait `BoxedDsl<'_, _>` is not implemented for `SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>, diesel::query_builder::group_by_clause::GroupByClause<users::columns::name>>`
+   |                                        ^^^^^^^^^^ the trait `BoxedDsl<'_, _>` is not implemented for `SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<NoLimitClause, NoOffsetClause>, diesel::query_builder::group_by_clause::GroupByClause<users::columns::name>>`
    |
    = help: the following other types implement trait `BoxedDsl<'a, DB>`:
              SelectStatement<FromClause<F>, S, D, W, O, LOf, G, H>
@@ -26,11 +26,11 @@ note: required for `users::columns::id` to implement `ValidGrouping<users::colum
    |         ^^
    = note: required for `SelectStatement<FromClause<table>, DefaultSelectClause<FromClause<table>>, ..., ..., ..., ..., ...>` to implement `SelectDsl<users::columns::id>`
 
-error[E0277]: the trait bound `SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::SelectClause<users::columns::id>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>, diesel::query_builder::group_by_clause::GroupByClause<users::columns::name>>: BoxedDsl<'_, _>` is not satisfied
+error[E0277]: the trait bound `SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::SelectClause<users::columns::id>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<NoLimitClause, NoOffsetClause>, diesel::query_builder::group_by_clause::GroupByClause<users::columns::name>>: BoxedDsl<'_, _>` is not satisfied
   --> tests/fail/boxed_queries_and_group_by.rs:60:10
    |
 60 |         .into_boxed();
-   |          ^^^^^^^^^^ the trait `BoxedDsl<'_, _>` is not implemented for `SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::SelectClause<users::columns::id>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>, diesel::query_builder::group_by_clause::GroupByClause<users::columns::name>>`
+   |          ^^^^^^^^^^ the trait `BoxedDsl<'_, _>` is not implemented for `SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::SelectClause<users::columns::id>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<NoLimitClause, NoOffsetClause>, diesel::query_builder::group_by_clause::GroupByClause<users::columns::name>>`
    |
    = help: the following other types implement trait `BoxedDsl<'a, DB>`:
              SelectStatement<FromClause<F>, S, D, W, O, LOf, G, H>
diff --git a/diesel_compile_tests/tests/fail/mysql_does_not_support_offset_without_limit.stderr b/diesel_compile_tests/tests/fail/mysql_does_not_support_offset_without_limit.stderr
index bd81cc62aaed..c22056833596 100644
--- a/diesel_compile_tests/tests/fail/mysql_does_not_support_offset_without_limit.stderr
+++ b/diesel_compile_tests/tests/fail/mysql_does_not_support_offset_without_limit.stderr
@@ -1,20 +1,20 @@
-error[E0277]: the trait bound `LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::OffsetClause<diesel::expression::bound::Bound<BigInt, i64>>>: QueryFragment<Mysql>` is not satisfied
+error[E0277]: the trait bound `LimitOffsetClause<NoLimitClause, OffsetClause<diesel::expression::bound::Bound<BigInt, i64>>>: QueryFragment<Mysql>` is not satisfied
   --> tests/fail/mysql_does_not_support_offset_without_limit.rs:16:57
    |
 16 |     users::table.offset(42).get_result::<(i32, String)>(&mut connection);
-   |                             ----------                  ^^^^^^^^^^^^^^^ the trait `QueryFragment<Mysql>` is not implemented for `LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::OffsetClause<diesel::expression::bound::Bound<BigInt, i64>>>`
+   |                             ----------                  ^^^^^^^^^^^^^^^ the trait `QueryFragment<Mysql>` is not implemented for `LimitOffsetClause<NoLimitClause, OffsetClause<diesel::expression::bound::Bound<BigInt, i64>>>`
    |                             |
    |                             required by a bound introduced by this call
    |
    = help: the following other types implement trait `QueryFragment<DB, SP>`:
              <LimitOffsetClause<L, O> as QueryFragment<Pg>>
-             <LimitOffsetClause<diesel::query_builder::limit_clause::LimitClause<L>, diesel::query_builder::offset_clause::NoOffsetClause> as QueryFragment<Mysql>>
-             <LimitOffsetClause<diesel::query_builder::limit_clause::LimitClause<L>, diesel::query_builder::offset_clause::NoOffsetClause> as QueryFragment<Sqlite>>
-             <LimitOffsetClause<diesel::query_builder::limit_clause::LimitClause<L>, diesel::query_builder::offset_clause::OffsetClause<O>> as QueryFragment<Mysql>>
-             <LimitOffsetClause<diesel::query_builder::limit_clause::LimitClause<L>, diesel::query_builder::offset_clause::OffsetClause<O>> as QueryFragment<Sqlite>>
-             <LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause> as QueryFragment<Mysql>>
-             <LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause> as QueryFragment<Sqlite>>
-             <LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::OffsetClause<O>> as QueryFragment<Sqlite>>
+             <LimitOffsetClause<LimitClause<L>, NoOffsetClause> as QueryFragment<Mysql>>
+             <LimitOffsetClause<LimitClause<L>, NoOffsetClause> as QueryFragment<Sqlite>>
+             <LimitOffsetClause<LimitClause<L>, OffsetClause<O>> as QueryFragment<Mysql>>
+             <LimitOffsetClause<LimitClause<L>, OffsetClause<O>> as QueryFragment<Sqlite>>
+             <LimitOffsetClause<NoLimitClause, NoOffsetClause> as QueryFragment<Mysql>>
+             <LimitOffsetClause<NoLimitClause, NoOffsetClause> as QueryFragment<Sqlite>>
+             <LimitOffsetClause<NoLimitClause, OffsetClause<O>> as QueryFragment<Sqlite>>
    = note: required for `SelectStatement<FromClause<table>, DefaultSelectClause<FromClause<table>>, NoDistinctClause, ..., ..., ...>` to implement `QueryFragment<Mysql, AnsiSqlSelectStatement>`
    = note: 1 redundant requirement hidden
    = note: required for `SelectStatement<FromClause<table>, DefaultSelectClause<FromClause<table>>, NoDistinctClause, ..., ..., ...>` to implement `QueryFragment<Mysql>`
@@ -25,38 +25,38 @@ note: required by a bound in `get_result`
    |         Self: LoadQuery<'query, Conn, U>,
    |               ^^^^^^^^^^^^^^^^^^^^^^^^^^ required by this bound in `RunQueryDsl::get_result`
 
-error[E0277]: the trait bound `LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::OffsetClause<diesel::expression::bound::Bound<BigInt, i64>>>: IntoBoxedClause<'_, Mysql>` is not satisfied
+error[E0277]: the trait bound `LimitOffsetClause<NoLimitClause, OffsetClause<diesel::expression::bound::Bound<BigInt, i64>>>: IntoBoxedClause<'_, Mysql>` is not satisfied
   --> tests/fail/mysql_does_not_support_offset_without_limit.rs:18:29
    |
 18 |     users::table.offset(42).into_boxed().get_result::<(i32, String)>(&mut connection);
-   |                             ^^^^^^^^^^ the trait `IntoBoxedClause<'_, Mysql>` is not implemented for `LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::OffsetClause<diesel::expression::bound::Bound<BigInt, i64>>>`
+   |                             ^^^^^^^^^^ the trait `IntoBoxedClause<'_, Mysql>` is not implemented for `LimitOffsetClause<NoLimitClause, OffsetClause<diesel::expression::bound::Bound<BigInt, i64>>>`
    |
    = help: the following other types implement trait `IntoBoxedClause<'a, DB>`:
              <LimitOffsetClause<L, O> as IntoBoxedClause<'a, Pg>>
-             <LimitOffsetClause<diesel::query_builder::limit_clause::LimitClause<L>, diesel::query_builder::offset_clause::NoOffsetClause> as IntoBoxedClause<'a, Mysql>>
-             <LimitOffsetClause<diesel::query_builder::limit_clause::LimitClause<L>, diesel::query_builder::offset_clause::NoOffsetClause> as IntoBoxedClause<'a, Sqlite>>
-             <LimitOffsetClause<diesel::query_builder::limit_clause::LimitClause<L>, diesel::query_builder::offset_clause::OffsetClause<O>> as IntoBoxedClause<'a, Mysql>>
-             <LimitOffsetClause<diesel::query_builder::limit_clause::LimitClause<L>, diesel::query_builder::offset_clause::OffsetClause<O>> as IntoBoxedClause<'a, Sqlite>>
-             <LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause> as IntoBoxedClause<'a, Mysql>>
-             <LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause> as IntoBoxedClause<'a, Sqlite>>
-             <LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::OffsetClause<O>> as IntoBoxedClause<'a, Sqlite>>
+             <LimitOffsetClause<LimitClause<L>, NoOffsetClause> as IntoBoxedClause<'a, Mysql>>
+             <LimitOffsetClause<LimitClause<L>, NoOffsetClause> as IntoBoxedClause<'a, Sqlite>>
+             <LimitOffsetClause<LimitClause<L>, OffsetClause<O>> as IntoBoxedClause<'a, Mysql>>
+             <LimitOffsetClause<LimitClause<L>, OffsetClause<O>> as IntoBoxedClause<'a, Sqlite>>
+             <LimitOffsetClause<NoLimitClause, NoOffsetClause> as IntoBoxedClause<'a, Mysql>>
+             <LimitOffsetClause<NoLimitClause, NoOffsetClause> as IntoBoxedClause<'a, Sqlite>>
+             <LimitOffsetClause<NoLimitClause, OffsetClause<O>> as IntoBoxedClause<'a, Sqlite>>
    = note: required for `SelectStatement<FromClause<table>, DefaultSelectClause<FromClause<table>>, NoDistinctClause, ..., ..., ...>` to implement `BoxedDsl<'_, Mysql>`
 
-error[E0277]: the trait bound `LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::OffsetClause<diesel::expression::bound::Bound<BigInt, i64>>>: IntoBoxedClause<'_, Mysql>` is not satisfied
+error[E0277]: the trait bound `LimitOffsetClause<NoLimitClause, OffsetClause<diesel::expression::bound::Bound<BigInt, i64>>>: IntoBoxedClause<'_, Mysql>` is not satisfied
   --> tests/fail/mysql_does_not_support_offset_without_limit.rs:18:29
    |
 18 |     users::table.offset(42).into_boxed().get_result::<(i32, String)>(&mut connection);
-   |                             ^^^^^^^^^^ the trait `IntoBoxedClause<'_, Mysql>` is not implemented for `LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::OffsetClause<diesel::expression::bound::Bound<BigInt, i64>>>`
+   |                             ^^^^^^^^^^ the trait `IntoBoxedClause<'_, Mysql>` is not implemented for `LimitOffsetClause<NoLimitClause, OffsetClause<diesel::expression::bound::Bound<BigInt, i64>>>`
    |
    = help: the following other types implement trait `IntoBoxedClause<'a, DB>`:
              <LimitOffsetClause<L, O> as IntoBoxedClause<'a, Pg>>
-             <LimitOffsetClause<diesel::query_builder::limit_clause::LimitClause<L>, diesel::query_builder::offset_clause::NoOffsetClause> as IntoBoxedClause<'a, Mysql>>
-             <LimitOffsetClause<diesel::query_builder::limit_clause::LimitClause<L>, diesel::query_builder::offset_clause::NoOffsetClause> as IntoBoxedClause<'a, Sqlite>>
-             <LimitOffsetClause<diesel::query_builder::limit_clause::LimitClause<L>, diesel::query_builder::offset_clause::OffsetClause<O>> as IntoBoxedClause<'a, Mysql>>
-             <LimitOffsetClause<diesel::query_builder::limit_clause::LimitClause<L>, diesel::query_builder::offset_clause::OffsetClause<O>> as IntoBoxedClause<'a, Sqlite>>
-             <LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause> as IntoBoxedClause<'a, Mysql>>
-             <LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause> as IntoBoxedClause<'a, Sqlite>>
-             <LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::OffsetClause<O>> as IntoBoxedClause<'a, Sqlite>>
+             <LimitOffsetClause<LimitClause<L>, NoOffsetClause> as IntoBoxedClause<'a, Mysql>>
+             <LimitOffsetClause<LimitClause<L>, NoOffsetClause> as IntoBoxedClause<'a, Sqlite>>
+             <LimitOffsetClause<LimitClause<L>, OffsetClause<O>> as IntoBoxedClause<'a, Mysql>>
+             <LimitOffsetClause<LimitClause<L>, OffsetClause<O>> as IntoBoxedClause<'a, Sqlite>>
+             <LimitOffsetClause<NoLimitClause, NoOffsetClause> as IntoBoxedClause<'a, Mysql>>
+             <LimitOffsetClause<NoLimitClause, NoOffsetClause> as IntoBoxedClause<'a, Sqlite>>
+             <LimitOffsetClause<NoLimitClause, OffsetClause<O>> as IntoBoxedClause<'a, Sqlite>>
    = note: required for `SelectStatement<FromClause<table>, DefaultSelectClause<FromClause<table>>, NoDistinctClause, ..., ..., ...>` to implement `BoxedDsl<'_, Mysql>`
 note: required by a bound in `diesel::QueryDsl::into_boxed`
   --> $DIESEL/src/query_dsl/mod.rs
diff --git a/diesel_compile_tests/tests/fail/select_for_update_cannot_be_mixed_with_some_clauses.stderr b/diesel_compile_tests/tests/fail/select_for_update_cannot_be_mixed_with_some_clauses.stderr
index b0c5d6836162..de3b7f82006a 100644
--- a/diesel_compile_tests/tests/fail/select_for_update_cannot_be_mixed_with_some_clauses.stderr
+++ b/diesel_compile_tests/tests/fail/select_for_update_cannot_be_mixed_with_some_clauses.stderr
@@ -8,11 +8,11 @@ error[E0271]: type mismatch resolving `<SelectStatement<FromClause<table>, Defau
               found struct `SelectStatement<FromClause<SelectStatement<FromClause<table>, ..., ..., ..., ..., ..., ..., ..., ...>>>`
    = note: required for `SelectStatement<FromClause<table>, DefaultSelectClause<FromClause<table>>, ..., ..., ..., ..., ..., ..., ...>` to implement `DistinctDsl`
 
-error[E0277]: the trait bound `SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>: Table` is not satisfied
+error[E0277]: the trait bound `SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<NoLimitClause, NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>: Table` is not satisfied
   --> tests/fail/select_for_update_cannot_be_mixed_with_some_clauses.rs:14:24
    |
 14 |     users.for_update().distinct();
-   |                        ^^^^^^^^ the trait `Table` is not implemented for `SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>`
+   |                        ^^^^^^^^ the trait `Table` is not implemented for `SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<NoLimitClause, NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>`
    |
    = help: the following other types implement trait `Table`:
              Only<S>
@@ -21,11 +21,11 @@ error[E0277]: the trait bound `SelectStatement<FromClause<users::table>, diesel:
              users::table
    = note: required for `SelectStatement<FromClause<table>, DefaultSelectClause<FromClause<table>>, ..., ..., ..., ..., ..., ..., ...>` to implement `DistinctDsl`
 
-error[E0277]: the trait bound `SelectStatement<FromClause<SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>>>: DistinctDsl` is not satisfied
+error[E0277]: the trait bound `SelectStatement<FromClause<SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<NoLimitClause, NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>>>: DistinctDsl` is not satisfied
   --> tests/fail/select_for_update_cannot_be_mixed_with_some_clauses.rs:14:24
    |
 14 |     users.for_update().distinct();
-   |                        ^^^^^^^^ the trait `DistinctDsl` is not implemented for `SelectStatement<FromClause<SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>>>`
+   |                        ^^^^^^^^ the trait `DistinctDsl` is not implemented for `SelectStatement<FromClause<SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<NoLimitClause, NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>>>`
    |
    = help: the trait `DistinctDsl` is implemented for `SelectStatement<F, S, D, W, O, LOf, G, H>`
 
@@ -70,11 +70,11 @@ error[E0271]: type mismatch resolving `<SelectStatement<FromClause<table>, Defau
               found struct `SelectStatement<FromClause<SelectStatement<FromClause<table>, ..., ..., ..., ..., ..., ..., ..., ...>>>`
    = note: required for `SelectStatement<FromClause<table>, DefaultSelectClause<FromClause<table>>, ..., ..., ..., ..., ..., ..., ...>` to implement `DistinctOnDsl<_>`
 
-error[E0277]: the trait bound `SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>: Table` is not satisfied
+error[E0277]: the trait bound `SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<NoLimitClause, NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>: Table` is not satisfied
   --> tests/fail/select_for_update_cannot_be_mixed_with_some_clauses.rs:16:24
    |
 16 |     users.for_update().distinct_on(id);
-   |                        ^^^^^^^^^^^ the trait `Table` is not implemented for `SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>`
+   |                        ^^^^^^^^^^^ the trait `Table` is not implemented for `SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<NoLimitClause, NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>`
    |
    = help: the following other types implement trait `Table`:
              Only<S>
@@ -83,20 +83,20 @@ error[E0277]: the trait bound `SelectStatement<FromClause<users::table>, diesel:
              users::table
    = note: required for `SelectStatement<FromClause<table>, DefaultSelectClause<FromClause<table>>, ..., ..., ..., ..., ..., ..., ...>` to implement `DistinctOnDsl<_>`
 
-error[E0277]: the trait bound `SelectStatement<FromClause<SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>>>: DistinctOnDsl<_>` is not satisfied
+error[E0277]: the trait bound `SelectStatement<FromClause<SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<NoLimitClause, NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>>>: DistinctOnDsl<_>` is not satisfied
   --> tests/fail/select_for_update_cannot_be_mixed_with_some_clauses.rs:16:24
    |
 16 |     users.for_update().distinct_on(id);
-   |                        ^^^^^^^^^^^ the trait `DistinctOnDsl<_>` is not implemented for `SelectStatement<FromClause<SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>>>`
+   |                        ^^^^^^^^^^^ the trait `DistinctOnDsl<_>` is not implemented for `SelectStatement<FromClause<SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<NoLimitClause, NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>>>`
    |
    = help: the trait `DistinctOnDsl<Selection>` is implemented for `SelectStatement<FromClause<F>, S, D, W, O, LOf, G, H>`
    = note: required for `SelectStatement<FromClause<table>, DefaultSelectClause<FromClause<table>>, ..., ..., ..., ..., ..., ..., ...>` to implement `DistinctOnDsl<_>`
 
-error[E0277]: the trait bound `SelectStatement<FromClause<SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>>>: DistinctOnDsl<_>` is not satisfied
+error[E0277]: the trait bound `SelectStatement<FromClause<SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<NoLimitClause, NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>>>: DistinctOnDsl<_>` is not satisfied
   --> tests/fail/select_for_update_cannot_be_mixed_with_some_clauses.rs:16:36
    |
 16 |     users.for_update().distinct_on(id);
-   |                        ----------- ^^ the trait `DistinctOnDsl<_>` is not implemented for `SelectStatement<FromClause<SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>>>`
+   |                        ----------- ^^ the trait `DistinctOnDsl<_>` is not implemented for `SelectStatement<FromClause<SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<NoLimitClause, NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>>>`
    |                        |
    |                        required by a bound introduced by this call
    |
@@ -108,15 +108,15 @@ note: required by a bound in `diesel::QueryDsl::distinct_on`
    |         Self: methods::DistinctOnDsl<Expr>,
    |               ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ required by this bound in `QueryDsl::distinct_on`
 
-error[E0277]: Cannot select `columns::id` from `SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>`
+error[E0277]: Cannot select `columns::id` from `SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<NoLimitClause, NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>`
   --> tests/fail/select_for_update_cannot_be_mixed_with_some_clauses.rs:16:36
    |
 16 |     users.for_update().distinct_on(id);
-   |                        ----------- ^^ the trait `SelectableExpression<SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>>` is not implemented for `columns::id`
+   |                        ----------- ^^ the trait `SelectableExpression<SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<NoLimitClause, NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>>` is not implemented for `columns::id`
    |                        |
    |                        required by a bound introduced by this call
    |
-   = note: `columns::id` is no valid selection for `SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>`
+   = note: `columns::id` is no valid selection for `SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<NoLimitClause, NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>`
    = help: the following other types implement trait `SelectableExpression<QS>`:
              <columns::id as SelectableExpression<JoinOn<Join, On>>>
              <columns::id as SelectableExpression<Only<users::table>>>
@@ -172,11 +172,11 @@ error[E0271]: type mismatch resolving `<SelectStatement<FromClause<table>, Defau
               found struct `SelectStatement<FromClause<SelectStatement<FromClause<table>, ..., ..., ..., ..., ..., ..., ..., ...>>>`
    = note: required for `SelectStatement<FromClause<table>, DefaultSelectClause<FromClause<table>>, ..., ..., ..., ..., ..., ..., ...>` to implement `GroupByDsl<_>`
 
-error[E0277]: the trait bound `SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>: Table` is not satisfied
+error[E0277]: the trait bound `SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<NoLimitClause, NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>: Table` is not satisfied
   --> tests/fail/select_for_update_cannot_be_mixed_with_some_clauses.rs:19:24
    |
 19 |     users.for_update().group_by(id);
-   |                        ^^^^^^^^ the trait `Table` is not implemented for `SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>`
+   |                        ^^^^^^^^ the trait `Table` is not implemented for `SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<NoLimitClause, NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>`
    |
    = help: the following other types implement trait `Table`:
              Only<S>
@@ -185,11 +185,11 @@ error[E0277]: the trait bound `SelectStatement<FromClause<users::table>, diesel:
              users::table
    = note: required for `SelectStatement<FromClause<table>, DefaultSelectClause<FromClause<table>>, ..., ..., ..., ..., ..., ..., ...>` to implement `GroupByDsl<_>`
 
-error[E0277]: the trait bound `SelectStatement<FromClause<SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>>>: GroupByDsl<_>` is not satisfied
+error[E0277]: the trait bound `SelectStatement<FromClause<SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<NoLimitClause, NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>>>: GroupByDsl<_>` is not satisfied
   --> tests/fail/select_for_update_cannot_be_mixed_with_some_clauses.rs:19:24
    |
 19 |     users.for_update().group_by(id);
-   |                        ^^^^^^^^ the trait `GroupByDsl<_>` is not implemented for `SelectStatement<FromClause<SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>>>`
+   |                        ^^^^^^^^ the trait `GroupByDsl<_>` is not implemented for `SelectStatement<FromClause<SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<NoLimitClause, NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>>>`
    |
    = help: the trait `GroupByDsl<Expr>` is implemented for `SelectStatement<F, S, D, W, O, LOf, G, H>`
 
@@ -203,11 +203,11 @@ error[E0271]: type mismatch resolving `<SelectStatement<FromClause<table>, Defau
               found struct `SelectStatement<FromClause<SelectStatement<FromClause<table>, ..., ..., ..., ..., ..., ...>>>`
    = note: required for `SelectStatement<FromClause<table>, DefaultSelectClause<FromClause<table>>, ..., ..., ..., ..., ...>` to implement `LockingDsl<diesel::query_builder::locking_clause::ForUpdate>`
 
-error[E0277]: the trait bound `SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>, diesel::query_builder::group_by_clause::GroupByClause<columns::id>>: Table` is not satisfied
+error[E0277]: the trait bound `SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<NoLimitClause, NoOffsetClause>, diesel::query_builder::group_by_clause::GroupByClause<columns::id>>: Table` is not satisfied
   --> tests/fail/select_for_update_cannot_be_mixed_with_some_clauses.rs:20:24
    |
 20 |     users.group_by(id).for_update();
-   |                        ^^^^^^^^^^ the trait `Table` is not implemented for `SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>, diesel::query_builder::group_by_clause::GroupByClause<columns::id>>`
+   |                        ^^^^^^^^^^ the trait `Table` is not implemented for `SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<NoLimitClause, NoOffsetClause>, diesel::query_builder::group_by_clause::GroupByClause<columns::id>>`
    |
    = help: the following other types implement trait `Table`:
              Only<S>
@@ -216,11 +216,11 @@ error[E0277]: the trait bound `SelectStatement<FromClause<users::table>, diesel:
              users::table
    = note: required for `SelectStatement<FromClause<table>, DefaultSelectClause<FromClause<table>>, ..., ..., ..., ..., ...>` to implement `LockingDsl<diesel::query_builder::locking_clause::ForUpdate>`
 
-error[E0277]: the trait bound `SelectStatement<FromClause<SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>, diesel::query_builder::group_by_clause::GroupByClause<columns::id>>>>: LockingDsl<diesel::query_builder::locking_clause::ForUpdate>` is not satisfied
+error[E0277]: the trait bound `SelectStatement<FromClause<SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<NoLimitClause, NoOffsetClause>, diesel::query_builder::group_by_clause::GroupByClause<columns::id>>>>: LockingDsl<diesel::query_builder::locking_clause::ForUpdate>` is not satisfied
   --> tests/fail/select_for_update_cannot_be_mixed_with_some_clauses.rs:20:24
    |
 20 |     users.group_by(id).for_update();
-   |                        ^^^^^^^^^^ the trait `LockingDsl<diesel::query_builder::locking_clause::ForUpdate>` is not implemented for `SelectStatement<FromClause<SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>, diesel::query_builder::group_by_clause::GroupByClause<columns::id>>>>`
+   |                        ^^^^^^^^^^ the trait `LockingDsl<diesel::query_builder::locking_clause::ForUpdate>` is not implemented for `SelectStatement<FromClause<SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<NoLimitClause, NoOffsetClause>, diesel::query_builder::group_by_clause::GroupByClause<columns::id>>>>`
    |
    = help: the trait `LockingDsl<Lock>` is implemented for `SelectStatement<F, S, diesel::query_builder::distinct_clause::NoDistinctClause, W, O, LOf>`
 
@@ -265,11 +265,11 @@ error[E0271]: type mismatch resolving `<SelectStatement<FromClause<table>, Defau
               found struct `SelectStatement<FromClause<SelectStatement<FromClause<table>, ..., ..., ..., ..., ..., ..., ..., ...>>>`
    = note: required for `SelectStatement<FromClause<table>, DefaultSelectClause<FromClause<table>>, ..., ..., ..., ..., ..., ..., ...>` to implement `BoxedDsl<'_, _>`
 
-error[E0277]: the trait bound `SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>: Table` is not satisfied
+error[E0277]: the trait bound `SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<NoLimitClause, NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>: Table` is not satisfied
   --> tests/fail/select_for_update_cannot_be_mixed_with_some_clauses.rs:23:24
    |
 23 |     users.for_update().into_boxed();
-   |                        ^^^^^^^^^^ the trait `Table` is not implemented for `SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>`
+   |                        ^^^^^^^^^^ the trait `Table` is not implemented for `SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<NoLimitClause, NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>`
    |
    = help: the following other types implement trait `Table`:
              Only<S>
@@ -278,22 +278,22 @@ error[E0277]: the trait bound `SelectStatement<FromClause<users::table>, diesel:
              users::table
    = note: required for `SelectStatement<FromClause<table>, DefaultSelectClause<FromClause<table>>, ..., ..., ..., ..., ..., ..., ...>` to implement `BoxedDsl<'_, _>`
 
-error[E0277]: the trait bound `SelectStatement<FromClause<SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>>>: BoxedDsl<'_, _>` is not satisfied
+error[E0277]: the trait bound `SelectStatement<FromClause<SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<NoLimitClause, NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>>>: BoxedDsl<'_, _>` is not satisfied
   --> tests/fail/select_for_update_cannot_be_mixed_with_some_clauses.rs:23:24
    |
 23 |     users.for_update().into_boxed();
-   |                        ^^^^^^^^^^ the trait `BoxedDsl<'_, _>` is not implemented for `SelectStatement<FromClause<SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>>>`
+   |                        ^^^^^^^^^^ the trait `BoxedDsl<'_, _>` is not implemented for `SelectStatement<FromClause<SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<NoLimitClause, NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>>>`
    |
    = help: the following other types implement trait `BoxedDsl<'a, DB>`:
              SelectStatement<FromClause<F>, S, D, W, O, LOf, G, H>
              SelectStatement<NoFromClause, S, D, W, O, LOf, G, H>
    = note: required for `SelectStatement<FromClause<table>, DefaultSelectClause<FromClause<table>>, ..., ..., ..., ..., ..., ..., ...>` to implement `BoxedDsl<'_, _>`
 
-error[E0277]: the trait bound `SelectStatement<FromClause<SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>>>: BoxedDsl<'_, _>` is not satisfied
+error[E0277]: the trait bound `SelectStatement<FromClause<SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<NoLimitClause, NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>>>: BoxedDsl<'_, _>` is not satisfied
   --> tests/fail/select_for_update_cannot_be_mixed_with_some_clauses.rs:23:24
    |
 23 |     users.for_update().into_boxed();
-   |                        ^^^^^^^^^^ the trait `BoxedDsl<'_, _>` is not implemented for `SelectStatement<FromClause<SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>>>`
+   |                        ^^^^^^^^^^ the trait `BoxedDsl<'_, _>` is not implemented for `SelectStatement<FromClause<SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<NoLimitClause, NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>>>`
    |
    = help: the following other types implement trait `BoxedDsl<'a, DB>`:
              SelectStatement<FromClause<F>, S, D, W, O, LOf, G, H>
@@ -315,11 +315,11 @@ error[E0271]: type mismatch resolving `<SelectStatement<FromClause<table>, Defau
               found struct `SelectStatement<FromClause<SelectStatement<FromClause<table>, ..., ..., ..., ..., ..., ..., ..., ...>>>`
    = note: required for `SelectStatement<FromClause<table>, DefaultSelectClause<FromClause<table>>, ..., ..., ..., ..., ..., ..., ...>` to implement `GroupByDsl<_>`
 
-error[E0277]: the trait bound `SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>: Table` is not satisfied
+error[E0277]: the trait bound `SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<NoLimitClause, NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>: Table` is not satisfied
   --> tests/fail/select_for_update_cannot_be_mixed_with_some_clauses.rs:25:24
    |
 25 |     users.for_update().group_by(id).having(id.gt(1));
-   |                        ^^^^^^^^ the trait `Table` is not implemented for `SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>`
+   |                        ^^^^^^^^ the trait `Table` is not implemented for `SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<NoLimitClause, NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>`
    |
    = help: the following other types implement trait `Table`:
              Only<S>
@@ -328,11 +328,11 @@ error[E0277]: the trait bound `SelectStatement<FromClause<users::table>, diesel:
              users::table
    = note: required for `SelectStatement<FromClause<table>, DefaultSelectClause<FromClause<table>>, ..., ..., ..., ..., ..., ..., ...>` to implement `GroupByDsl<_>`
 
-error[E0277]: the trait bound `SelectStatement<FromClause<SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>>>: GroupByDsl<_>` is not satisfied
+error[E0277]: the trait bound `SelectStatement<FromClause<SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<NoLimitClause, NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>>>: GroupByDsl<_>` is not satisfied
   --> tests/fail/select_for_update_cannot_be_mixed_with_some_clauses.rs:25:24
    |
 25 |     users.for_update().group_by(id).having(id.gt(1));
-   |                        ^^^^^^^^ the trait `GroupByDsl<_>` is not implemented for `SelectStatement<FromClause<SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>>>`
+   |                        ^^^^^^^^ the trait `GroupByDsl<_>` is not implemented for `SelectStatement<FromClause<SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<NoLimitClause, NoOffsetClause>, diesel::query_builder::group_by_clause::NoGroupByClause, diesel::query_builder::having_clause::NoHavingClause, diesel::query_builder::locking_clause::LockingClause>>>`
    |
    = help: the trait `GroupByDsl<Expr>` is implemented for `SelectStatement<F, S, D, W, O, LOf, G, H>`
 
@@ -346,11 +346,11 @@ error[E0271]: type mismatch resolving `<SelectStatement<FromClause<table>, Defau
               found struct `SelectStatement<FromClause<SelectStatement<FromClause<table>, ..., ..., ..., ..., ..., ..., ...>>>`
    = note: required for `SelectStatement<FromClause<table>, DefaultSelectClause<FromClause<table>>, ..., ..., ..., ..., ..., ...>` to implement `LockingDsl<diesel::query_builder::locking_clause::ForUpdate>`
 
-error[E0277]: the trait bound `SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>, diesel::query_builder::group_by_clause::GroupByClause<columns::id>, diesel::query_builder::having_clause::HavingClause<diesel::expression::grouped::Grouped<diesel::expression::operators::Gt<columns::id, diesel::expression::bound::Bound<diesel::sql_types::Integer, i32>>>>>: Table` is not satisfied
+error[E0277]: the trait bound `SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<NoLimitClause, NoOffsetClause>, diesel::query_builder::group_by_clause::GroupByClause<columns::id>, diesel::query_builder::having_clause::HavingClause<diesel::expression::grouped::Grouped<diesel::expression::operators::Gt<columns::id, diesel::expression::bound::Bound<diesel::sql_types::Integer, i32>>>>>: Table` is not satisfied
   --> tests/fail/select_for_update_cannot_be_mixed_with_some_clauses.rs:26:41
    |
 26 |     users.group_by(id).having(id.gt(1)).for_update();
-   |                                         ^^^^^^^^^^ the trait `Table` is not implemented for `SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>, diesel::query_builder::group_by_clause::GroupByClause<columns::id>, diesel::query_builder::having_clause::HavingClause<diesel::expression::grouped::Grouped<diesel::expression::operators::Gt<columns::id, diesel::expression::bound::Bound<diesel::sql_types::Integer, i32>>>>>`
+   |                                         ^^^^^^^^^^ the trait `Table` is not implemented for `SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<NoLimitClause, NoOffsetClause>, diesel::query_builder::group_by_clause::GroupByClause<columns::id>, diesel::query_builder::having_clause::HavingClause<diesel::expression::grouped::Grouped<diesel::expression::operators::Gt<columns::id, diesel::expression::bound::Bound<diesel::sql_types::Integer, i32>>>>>`
    |
    = help: the following other types implement trait `Table`:
              Only<S>
@@ -359,10 +359,10 @@ error[E0277]: the trait bound `SelectStatement<FromClause<users::table>, diesel:
              users::table
    = note: required for `SelectStatement<FromClause<table>, DefaultSelectClause<FromClause<table>>, ..., ..., ..., ..., ..., ...>` to implement `LockingDsl<diesel::query_builder::locking_clause::ForUpdate>`
 
-error[E0277]: the trait bound `SelectStatement<FromClause<SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>, diesel::query_builder::group_by_clause::GroupByClause<columns::id>, diesel::query_builder::having_clause::HavingClause<diesel::expression::grouped::Grouped<diesel::expression::operators::Gt<columns::id, diesel::expression::bound::Bound<diesel::sql_types::Integer, i32>>>>>>>: LockingDsl<diesel::query_builder::locking_clause::ForUpdate>` is not satisfied
+error[E0277]: the trait bound `SelectStatement<FromClause<SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<NoLimitClause, NoOffsetClause>, diesel::query_builder::group_by_clause::GroupByClause<columns::id>, diesel::query_builder::having_clause::HavingClause<diesel::expression::grouped::Grouped<diesel::expression::operators::Gt<columns::id, diesel::expression::bound::Bound<diesel::sql_types::Integer, i32>>>>>>>: LockingDsl<diesel::query_builder::locking_clause::ForUpdate>` is not satisfied
   --> tests/fail/select_for_update_cannot_be_mixed_with_some_clauses.rs:26:41
    |
 26 |     users.group_by(id).having(id.gt(1)).for_update();
-   |                                         ^^^^^^^^^^ the trait `LockingDsl<diesel::query_builder::locking_clause::ForUpdate>` is not implemented for `SelectStatement<FromClause<SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<diesel::query_builder::limit_clause::NoLimitClause, diesel::query_builder::offset_clause::NoOffsetClause>, diesel::query_builder::group_by_clause::GroupByClause<columns::id>, diesel::query_builder::having_clause::HavingClause<diesel::expression::grouped::Grouped<diesel::expression::operators::Gt<columns::id, diesel::expression::bound::Bound<diesel::sql_types::Integer, i32>>>>>>>`
+   |                                         ^^^^^^^^^^ the trait `LockingDsl<diesel::query_builder::locking_clause::ForUpdate>` is not implemented for `SelectStatement<FromClause<SelectStatement<FromClause<users::table>, diesel::query_builder::select_clause::DefaultSelectClause<FromClause<users::table>>, diesel::query_builder::distinct_clause::NoDistinctClause, diesel::query_builder::where_clause::NoWhereClause, diesel::query_builder::order_clause::NoOrderClause, LimitOffsetClause<NoLimitClause, NoOffsetClause>, diesel::query_builder::group_by_clause::GroupByClause<columns::id>, diesel::query_builder::having_clause::HavingClause<diesel::expression::grouped::Grouped<diesel::expression::operators::Gt<columns::id, diesel::expression::bound::Bound<diesel::sql_types::Integer, i32>>>>>>>`
    |
    = help: the trait `LockingDsl<Lock>` is implemented for `SelectStatement<F, S, diesel::query_builder::distinct_clause::NoDistinctClause, W, O, LOf>`
diff --git a/diesel_derives/tests/multiconnection.rs b/diesel_derives/tests/multiconnection.rs
new file mode 100644
index 000000000000..56f3249c69c6
--- /dev/null
+++ b/diesel_derives/tests/multiconnection.rs
@@ -0,0 +1,108 @@
+use crate::schema::users;
+use diesel::prelude::*;
+
+#[derive(diesel::MultiConnection)]
+pub enum InferConnection {
+    #[cfg(feature = "postgres")]
+    Pg(PgConnection),
+    #[cfg(feature = "sqlite")]
+    Sqlite(SqliteConnection),
+    #[cfg(feature = "mysql")]
+    Mysql(MysqlConnection),
+}
+
+#[derive(Queryable, Selectable)]
+pub struct User {
+    pub id: i32,
+    pub name: String,
+}
+
+#[test]
+fn check_queries_work() {
+    let database_url = if cfg!(feature = "mysql") {
+        dotenvy::var("MYSQL_UNIT_TEST_DATABASE_URL").or_else(|_| dotenvy::var("DATABASE_URL"))
+    } else if cfg!(feature = "postgres") {
+        dotenvy::var("PG_DATABASE_URL").or_else(|_| dotenvy::var("DATABASE_URL"))
+    } else {
+        Ok(dotenvy::var("DATABASE_URL").unwrap_or_else(|_| ":memory:".to_owned()))
+    };
+    let database_url = database_url.expect("DATABASE_URL must be set in order to run tests");
+
+    let mut conn = InferConnection::establish(&database_url).unwrap();
+
+    diesel::sql_query(
+        "CREATE TEMPORARY TABLE users(\
+         id INTEGER NOT NULL PRIMARY KEY, \
+         name TEXT NOT NULL)",
+    )
+    .execute(&mut conn)
+    .unwrap();
+
+    conn.begin_test_transaction().unwrap();
+
+    // these are mostly compile pass tests
+
+    // simple query
+    let _ = users::table
+        .select((users::id, users::name))
+        .load::<User>(&mut conn)
+        .unwrap();
+
+    // with bind
+    let _ = users::table
+        .select((users::id, users::name))
+        .find(42)
+        .load::<User>(&mut conn)
+        .unwrap();
+
+    // simple boxed query
+    let _ = users::table
+        .into_boxed()
+        .select((users::id, users::name))
+        .load::<User>(&mut conn)
+        .unwrap();
+
+    // with bind
+    let _ = users::table
+        .into_boxed()
+        .select((users::id, users::name))
+        .filter(users::id.eq(42))
+        .load::<User>(&mut conn)
+        .unwrap();
+
+    // as_select
+    let _ = users::table
+        .select(User::as_select())
+        .load(&mut conn)
+        .unwrap();
+
+    // boxable expression
+    let b = Box::new(users::name.eq("John"))
+        as Box<
+            dyn BoxableExpression<
+                users::table,
+                self::multi_connection_impl::MultiBackend,
+                SqlType = _,
+            >,
+        >;
+
+    let _ = users::table
+        .filter(b)
+        .select(users::id)
+        .load::<i32>(&mut conn)
+        .unwrap();
+
+    // insert
+    diesel::insert_into(users::table)
+        .values((users::id.eq(42), users::name.eq("John")))
+        .execute(&mut conn)
+        .unwrap();
+    // update
+    diesel::update(users::table)
+        .set(users::name.eq("John"))
+        .execute(&mut conn)
+        .unwrap();
+
+    // delete
+    diesel::delete(users::table).execute(&mut conn).unwrap();
+}
diff --git a/diesel_derives/tests/tests.rs b/diesel_derives/tests/tests.rs
index 91a99948a645..ab3afd70f351 100644
--- a/diesel_derives/tests/tests.rs
+++ b/diesel_derives/tests/tests.rs
@@ -11,6 +11,7 @@ mod as_expression;
 mod associations;
 mod identifiable;
 mod insertable;
+mod multiconnection;
 mod queryable;
 mod queryable_by_name;
 mod selectable;