mas_storage/
repository.rs

1// Copyright 2024, 2025 New Vector Ltd.
2// Copyright 2022-2024 The Matrix.org Foundation C.I.C.
3//
4// SPDX-License-Identifier: AGPL-3.0-only OR LicenseRef-Element-Commercial
5// Please see LICENSE files in the repository root for full details.
6
7use async_trait::async_trait;
8use futures_util::future::BoxFuture;
9use thiserror::Error;
10
11use crate::{
12    app_session::AppSessionRepository,
13    compat::{
14        CompatAccessTokenRepository, CompatRefreshTokenRepository, CompatSessionRepository,
15        CompatSsoLoginRepository,
16    },
17    oauth2::{
18        OAuth2AccessTokenRepository, OAuth2AuthorizationGrantRepository, OAuth2ClientRepository,
19        OAuth2DeviceCodeGrantRepository, OAuth2RefreshTokenRepository, OAuth2SessionRepository,
20    },
21    personal::{PersonalAccessTokenRepository, PersonalSessionRepository},
22    policy_data::PolicyDataRepository,
23    queue::{QueueJobRepository, QueueScheduleRepository, QueueWorkerRepository},
24    upstream_oauth2::{
25        UpstreamOAuthLinkRepository, UpstreamOAuthProviderRepository,
26        UpstreamOAuthSessionRepository,
27    },
28    user::{
29        BrowserSessionRepository, UserEmailRepository, UserPasswordRepository,
30        UserRecoveryRepository, UserRegistrationRepository, UserRegistrationTokenRepository,
31        UserRepository, UserTermsRepository,
32    },
33};
34
35/// A [`RepositoryFactory`] is a factory that can create a [`BoxRepository`]
36// XXX(quenting): this could be generic over the repository type, but it's annoying to make it
37// dyn-safe
38#[async_trait]
39pub trait RepositoryFactory {
40    /// Create a new [`BoxRepository`]
41    async fn create(&self) -> Result<BoxRepository, RepositoryError>;
42}
43
44/// A type-erased [`RepositoryFactory`]
45pub type BoxRepositoryFactory = Box<dyn RepositoryFactory + Send + Sync + 'static>;
46
47/// A [`Repository`] helps interacting with the underlying storage backend.
48pub trait Repository<E>:
49    RepositoryAccess<Error = E> + RepositoryTransaction<Error = E> + Send
50where
51    E: std::error::Error + Send + Sync + 'static,
52{
53}
54
55/// An opaque, type-erased error
56#[derive(Debug, Error)]
57#[error(transparent)]
58pub struct RepositoryError {
59    source: Box<dyn std::error::Error + Send + Sync + 'static>,
60}
61
62impl RepositoryError {
63    /// Construct a [`RepositoryError`] from any error kind
64    pub fn from_error<E>(value: E) -> Self
65    where
66        E: std::error::Error + Send + Sync + 'static,
67    {
68        Self {
69            source: Box::new(value),
70        }
71    }
72}
73
74/// A type-erased [`Repository`]
75pub type BoxRepository = Box<dyn Repository<RepositoryError> + Send + Sync + 'static>;
76
77/// A [`RepositoryTransaction`] can be saved or cancelled, after a series
78/// of operations.
79pub trait RepositoryTransaction {
80    /// The error type used by the [`Self::save`] and [`Self::cancel`] functions
81    type Error;
82
83    /// Commit the transaction
84    ///
85    /// # Errors
86    ///
87    /// Returns an error if the underlying storage backend failed to commit the
88    /// transaction.
89    fn save(self: Box<Self>) -> BoxFuture<'static, Result<(), Self::Error>>;
90
91    /// Rollback the transaction
92    ///
93    /// # Errors
94    ///
95    /// Returns an error if the underlying storage backend failed to rollback
96    /// the transaction.
97    fn cancel(self: Box<Self>) -> BoxFuture<'static, Result<(), Self::Error>>;
98}
99
100/// Access the various repositories the backend implements.
101///
102/// All the methods return a boxed trait object, which can be used to access a
103/// particular repository. The lifetime of the returned object is bound to the
104/// lifetime of the whole repository, so that only one mutable reference to the
105/// repository is used at a time.
106///
107/// When adding a new repository, you should add a new method to this trait, and
108/// update the implementations for [`crate::MapErr`] and [`Box<R>`] below.
109///
110/// Note: this used to have generic associated types to avoid boxing all the
111/// repository traits, but that was removed because it made almost impossible to
112/// box the trait object. This might be a shortcoming of the initial
113/// implementation of generic associated types, and might be fixed in the
114/// future.
115pub trait RepositoryAccess: Send {
116    /// The backend-specific error type used by each repository.
117    type Error: std::error::Error + Send + Sync + 'static;
118
119    /// Get an [`UpstreamOAuthLinkRepository`]
120    fn upstream_oauth_link<'c>(
121        &'c mut self,
122    ) -> Box<dyn UpstreamOAuthLinkRepository<Error = Self::Error> + 'c>;
123
124    /// Get an [`UpstreamOAuthProviderRepository`]
125    fn upstream_oauth_provider<'c>(
126        &'c mut self,
127    ) -> Box<dyn UpstreamOAuthProviderRepository<Error = Self::Error> + 'c>;
128
129    /// Get an [`UpstreamOAuthSessionRepository`]
130    fn upstream_oauth_session<'c>(
131        &'c mut self,
132    ) -> Box<dyn UpstreamOAuthSessionRepository<Error = Self::Error> + 'c>;
133
134    /// Get an [`UserRepository`]
135    fn user<'c>(&'c mut self) -> Box<dyn UserRepository<Error = Self::Error> + 'c>;
136
137    /// Get an [`UserEmailRepository`]
138    fn user_email<'c>(&'c mut self) -> Box<dyn UserEmailRepository<Error = Self::Error> + 'c>;
139
140    /// Get an [`UserPasswordRepository`]
141    fn user_password<'c>(&'c mut self)
142    -> Box<dyn UserPasswordRepository<Error = Self::Error> + 'c>;
143
144    /// Get an [`UserRecoveryRepository`]
145    fn user_recovery<'c>(&'c mut self)
146    -> Box<dyn UserRecoveryRepository<Error = Self::Error> + 'c>;
147
148    /// Get an [`UserRegistrationRepository`]
149    fn user_registration<'c>(
150        &'c mut self,
151    ) -> Box<dyn UserRegistrationRepository<Error = Self::Error> + 'c>;
152
153    /// Get an [`UserRegistrationTokenRepository`]
154    fn user_registration_token<'c>(
155        &'c mut self,
156    ) -> Box<dyn UserRegistrationTokenRepository<Error = Self::Error> + 'c>;
157
158    /// Get an [`UserTermsRepository`]
159    fn user_terms<'c>(&'c mut self) -> Box<dyn UserTermsRepository<Error = Self::Error> + 'c>;
160
161    /// Get a [`BrowserSessionRepository`]
162    fn browser_session<'c>(
163        &'c mut self,
164    ) -> Box<dyn BrowserSessionRepository<Error = Self::Error> + 'c>;
165
166    /// Get a [`AppSessionRepository`]
167    fn app_session<'c>(&'c mut self) -> Box<dyn AppSessionRepository<Error = Self::Error> + 'c>;
168
169    /// Get an [`OAuth2ClientRepository`]
170    fn oauth2_client<'c>(&'c mut self)
171    -> Box<dyn OAuth2ClientRepository<Error = Self::Error> + 'c>;
172
173    /// Get an [`OAuth2AuthorizationGrantRepository`]
174    fn oauth2_authorization_grant<'c>(
175        &'c mut self,
176    ) -> Box<dyn OAuth2AuthorizationGrantRepository<Error = Self::Error> + 'c>;
177
178    /// Get an [`OAuth2SessionRepository`]
179    fn oauth2_session<'c>(
180        &'c mut self,
181    ) -> Box<dyn OAuth2SessionRepository<Error = Self::Error> + 'c>;
182
183    /// Get an [`OAuth2AccessTokenRepository`]
184    fn oauth2_access_token<'c>(
185        &'c mut self,
186    ) -> Box<dyn OAuth2AccessTokenRepository<Error = Self::Error> + 'c>;
187
188    /// Get an [`OAuth2RefreshTokenRepository`]
189    fn oauth2_refresh_token<'c>(
190        &'c mut self,
191    ) -> Box<dyn OAuth2RefreshTokenRepository<Error = Self::Error> + 'c>;
192
193    /// Get an [`OAuth2DeviceCodeGrantRepository`]
194    fn oauth2_device_code_grant<'c>(
195        &'c mut self,
196    ) -> Box<dyn OAuth2DeviceCodeGrantRepository<Error = Self::Error> + 'c>;
197
198    /// Get a [`CompatSessionRepository`]
199    fn compat_session<'c>(
200        &'c mut self,
201    ) -> Box<dyn CompatSessionRepository<Error = Self::Error> + 'c>;
202
203    /// Get a [`CompatSsoLoginRepository`]
204    fn compat_sso_login<'c>(
205        &'c mut self,
206    ) -> Box<dyn CompatSsoLoginRepository<Error = Self::Error> + 'c>;
207
208    /// Get a [`CompatAccessTokenRepository`]
209    fn compat_access_token<'c>(
210        &'c mut self,
211    ) -> Box<dyn CompatAccessTokenRepository<Error = Self::Error> + 'c>;
212
213    /// Get a [`CompatRefreshTokenRepository`]
214    fn compat_refresh_token<'c>(
215        &'c mut self,
216    ) -> Box<dyn CompatRefreshTokenRepository<Error = Self::Error> + 'c>;
217
218    /// Get a [`PersonalAccessTokenRepository`]
219    fn personal_access_token<'c>(
220        &'c mut self,
221    ) -> Box<dyn PersonalAccessTokenRepository<Error = Self::Error> + 'c>;
222
223    /// Get a [`PersonalSessionRepository`]
224    fn personal_session<'c>(
225        &'c mut self,
226    ) -> Box<dyn PersonalSessionRepository<Error = Self::Error> + 'c>;
227
228    /// Get a [`QueueWorkerRepository`]
229    fn queue_worker<'c>(&'c mut self) -> Box<dyn QueueWorkerRepository<Error = Self::Error> + 'c>;
230
231    /// Get a [`QueueJobRepository`]
232    fn queue_job<'c>(&'c mut self) -> Box<dyn QueueJobRepository<Error = Self::Error> + 'c>;
233
234    /// Get a [`QueueScheduleRepository`]
235    fn queue_schedule<'c>(
236        &'c mut self,
237    ) -> Box<dyn QueueScheduleRepository<Error = Self::Error> + 'c>;
238
239    /// Get a [`PolicyDataRepository`]
240    fn policy_data<'c>(&'c mut self) -> Box<dyn PolicyDataRepository<Error = Self::Error> + 'c>;
241}
242
243/// Implementations of the [`RepositoryAccess`], [`RepositoryTransaction`] and
244/// [`Repository`] for the [`crate::MapErr`] wrapper and [`Box<R>`]
245mod impls {
246    use futures_util::{FutureExt, TryFutureExt, future::BoxFuture};
247
248    use super::RepositoryAccess;
249    use crate::{
250        MapErr, Repository, RepositoryTransaction,
251        app_session::AppSessionRepository,
252        compat::{
253            CompatAccessTokenRepository, CompatRefreshTokenRepository, CompatSessionRepository,
254            CompatSsoLoginRepository,
255        },
256        oauth2::{
257            OAuth2AccessTokenRepository, OAuth2AuthorizationGrantRepository,
258            OAuth2ClientRepository, OAuth2DeviceCodeGrantRepository, OAuth2RefreshTokenRepository,
259            OAuth2SessionRepository,
260        },
261        personal::{PersonalAccessTokenRepository, PersonalSessionRepository},
262        policy_data::PolicyDataRepository,
263        queue::{QueueJobRepository, QueueScheduleRepository, QueueWorkerRepository},
264        upstream_oauth2::{
265            UpstreamOAuthLinkRepository, UpstreamOAuthProviderRepository,
266            UpstreamOAuthSessionRepository,
267        },
268        user::{
269            BrowserSessionRepository, UserEmailRepository, UserPasswordRepository,
270            UserRegistrationRepository, UserRegistrationTokenRepository, UserRepository,
271            UserTermsRepository,
272        },
273    };
274
275    // --- Repository ---
276    impl<R, F, E1, E2> Repository<E2> for MapErr<R, F>
277    where
278        R: Repository<E1> + RepositoryAccess<Error = E1> + RepositoryTransaction<Error = E1>,
279        F: FnMut(E1) -> E2 + Send + Sync + 'static,
280        E1: std::error::Error + Send + Sync + 'static,
281        E2: std::error::Error + Send + Sync + 'static,
282    {
283    }
284
285    // --- RepositoryTransaction --
286    impl<R, F, E> RepositoryTransaction for MapErr<R, F>
287    where
288        R: RepositoryTransaction,
289        R::Error: 'static,
290        F: FnMut(R::Error) -> E + Send + Sync + 'static,
291        E: std::error::Error,
292    {
293        type Error = E;
294
295        fn save(self: Box<Self>) -> BoxFuture<'static, Result<(), Self::Error>> {
296            Box::new(self.inner).save().map_err(self.mapper).boxed()
297        }
298
299        fn cancel(self: Box<Self>) -> BoxFuture<'static, Result<(), Self::Error>> {
300            Box::new(self.inner).cancel().map_err(self.mapper).boxed()
301        }
302    }
303
304    // --- RepositoryAccess --
305    impl<R, F, E> RepositoryAccess for MapErr<R, F>
306    where
307        R: RepositoryAccess,
308        R::Error: 'static,
309        F: FnMut(R::Error) -> E + Send + Sync + 'static,
310        E: std::error::Error + Send + Sync + 'static,
311    {
312        type Error = E;
313
314        fn upstream_oauth_link<'c>(
315            &'c mut self,
316        ) -> Box<dyn UpstreamOAuthLinkRepository<Error = Self::Error> + 'c> {
317            Box::new(MapErr::new(
318                self.inner.upstream_oauth_link(),
319                &mut self.mapper,
320            ))
321        }
322
323        fn upstream_oauth_provider<'c>(
324            &'c mut self,
325        ) -> Box<dyn UpstreamOAuthProviderRepository<Error = Self::Error> + 'c> {
326            Box::new(MapErr::new(
327                self.inner.upstream_oauth_provider(),
328                &mut self.mapper,
329            ))
330        }
331
332        fn upstream_oauth_session<'c>(
333            &'c mut self,
334        ) -> Box<dyn UpstreamOAuthSessionRepository<Error = Self::Error> + 'c> {
335            Box::new(MapErr::new(
336                self.inner.upstream_oauth_session(),
337                &mut self.mapper,
338            ))
339        }
340
341        fn user<'c>(&'c mut self) -> Box<dyn UserRepository<Error = Self::Error> + 'c> {
342            Box::new(MapErr::new(self.inner.user(), &mut self.mapper))
343        }
344
345        fn user_email<'c>(&'c mut self) -> Box<dyn UserEmailRepository<Error = Self::Error> + 'c> {
346            Box::new(MapErr::new(self.inner.user_email(), &mut self.mapper))
347        }
348
349        fn user_password<'c>(
350            &'c mut self,
351        ) -> Box<dyn UserPasswordRepository<Error = Self::Error> + 'c> {
352            Box::new(MapErr::new(self.inner.user_password(), &mut self.mapper))
353        }
354
355        fn user_recovery<'c>(
356            &'c mut self,
357        ) -> Box<dyn crate::user::UserRecoveryRepository<Error = Self::Error> + 'c> {
358            Box::new(MapErr::new(self.inner.user_recovery(), &mut self.mapper))
359        }
360
361        fn user_registration<'c>(
362            &'c mut self,
363        ) -> Box<dyn UserRegistrationRepository<Error = Self::Error> + 'c> {
364            Box::new(MapErr::new(
365                self.inner.user_registration(),
366                &mut self.mapper,
367            ))
368        }
369
370        fn user_registration_token<'c>(
371            &'c mut self,
372        ) -> Box<dyn UserRegistrationTokenRepository<Error = Self::Error> + 'c> {
373            Box::new(MapErr::new(
374                self.inner.user_registration_token(),
375                &mut self.mapper,
376            ))
377        }
378
379        fn user_terms<'c>(&'c mut self) -> Box<dyn UserTermsRepository<Error = Self::Error> + 'c> {
380            Box::new(MapErr::new(self.inner.user_terms(), &mut self.mapper))
381        }
382
383        fn browser_session<'c>(
384            &'c mut self,
385        ) -> Box<dyn BrowserSessionRepository<Error = Self::Error> + 'c> {
386            Box::new(MapErr::new(self.inner.browser_session(), &mut self.mapper))
387        }
388
389        fn app_session<'c>(
390            &'c mut self,
391        ) -> Box<dyn AppSessionRepository<Error = Self::Error> + 'c> {
392            Box::new(MapErr::new(self.inner.app_session(), &mut self.mapper))
393        }
394
395        fn oauth2_client<'c>(
396            &'c mut self,
397        ) -> Box<dyn OAuth2ClientRepository<Error = Self::Error> + 'c> {
398            Box::new(MapErr::new(self.inner.oauth2_client(), &mut self.mapper))
399        }
400
401        fn oauth2_authorization_grant<'c>(
402            &'c mut self,
403        ) -> Box<dyn OAuth2AuthorizationGrantRepository<Error = Self::Error> + 'c> {
404            Box::new(MapErr::new(
405                self.inner.oauth2_authorization_grant(),
406                &mut self.mapper,
407            ))
408        }
409
410        fn oauth2_session<'c>(
411            &'c mut self,
412        ) -> Box<dyn OAuth2SessionRepository<Error = Self::Error> + 'c> {
413            Box::new(MapErr::new(self.inner.oauth2_session(), &mut self.mapper))
414        }
415
416        fn oauth2_access_token<'c>(
417            &'c mut self,
418        ) -> Box<dyn OAuth2AccessTokenRepository<Error = Self::Error> + 'c> {
419            Box::new(MapErr::new(
420                self.inner.oauth2_access_token(),
421                &mut self.mapper,
422            ))
423        }
424
425        fn oauth2_refresh_token<'c>(
426            &'c mut self,
427        ) -> Box<dyn OAuth2RefreshTokenRepository<Error = Self::Error> + 'c> {
428            Box::new(MapErr::new(
429                self.inner.oauth2_refresh_token(),
430                &mut self.mapper,
431            ))
432        }
433
434        fn oauth2_device_code_grant<'c>(
435            &'c mut self,
436        ) -> Box<dyn OAuth2DeviceCodeGrantRepository<Error = Self::Error> + 'c> {
437            Box::new(MapErr::new(
438                self.inner.oauth2_device_code_grant(),
439                &mut self.mapper,
440            ))
441        }
442
443        fn compat_session<'c>(
444            &'c mut self,
445        ) -> Box<dyn CompatSessionRepository<Error = Self::Error> + 'c> {
446            Box::new(MapErr::new(self.inner.compat_session(), &mut self.mapper))
447        }
448
449        fn compat_sso_login<'c>(
450            &'c mut self,
451        ) -> Box<dyn CompatSsoLoginRepository<Error = Self::Error> + 'c> {
452            Box::new(MapErr::new(self.inner.compat_sso_login(), &mut self.mapper))
453        }
454
455        fn compat_access_token<'c>(
456            &'c mut self,
457        ) -> Box<dyn CompatAccessTokenRepository<Error = Self::Error> + 'c> {
458            Box::new(MapErr::new(
459                self.inner.compat_access_token(),
460                &mut self.mapper,
461            ))
462        }
463
464        fn compat_refresh_token<'c>(
465            &'c mut self,
466        ) -> Box<dyn CompatRefreshTokenRepository<Error = Self::Error> + 'c> {
467            Box::new(MapErr::new(
468                self.inner.compat_refresh_token(),
469                &mut self.mapper,
470            ))
471        }
472
473        fn personal_access_token<'c>(
474            &'c mut self,
475        ) -> Box<dyn PersonalAccessTokenRepository<Error = Self::Error> + 'c> {
476            Box::new(MapErr::new(
477                self.inner.personal_access_token(),
478                &mut self.mapper,
479            ))
480        }
481
482        fn personal_session<'c>(
483            &'c mut self,
484        ) -> Box<dyn PersonalSessionRepository<Error = Self::Error> + 'c> {
485            Box::new(MapErr::new(self.inner.personal_session(), &mut self.mapper))
486        }
487
488        fn queue_worker<'c>(
489            &'c mut self,
490        ) -> Box<dyn QueueWorkerRepository<Error = Self::Error> + 'c> {
491            Box::new(MapErr::new(self.inner.queue_worker(), &mut self.mapper))
492        }
493
494        fn queue_job<'c>(&'c mut self) -> Box<dyn QueueJobRepository<Error = Self::Error> + 'c> {
495            Box::new(MapErr::new(self.inner.queue_job(), &mut self.mapper))
496        }
497
498        fn queue_schedule<'c>(
499            &'c mut self,
500        ) -> Box<dyn QueueScheduleRepository<Error = Self::Error> + 'c> {
501            Box::new(MapErr::new(self.inner.queue_schedule(), &mut self.mapper))
502        }
503
504        fn policy_data<'c>(
505            &'c mut self,
506        ) -> Box<dyn PolicyDataRepository<Error = Self::Error> + 'c> {
507            Box::new(MapErr::new(self.inner.policy_data(), &mut self.mapper))
508        }
509    }
510
511    impl<R: RepositoryAccess + ?Sized> RepositoryAccess for Box<R> {
512        type Error = R::Error;
513
514        fn upstream_oauth_link<'c>(
515            &'c mut self,
516        ) -> Box<dyn UpstreamOAuthLinkRepository<Error = Self::Error> + 'c> {
517            (**self).upstream_oauth_link()
518        }
519
520        fn upstream_oauth_provider<'c>(
521            &'c mut self,
522        ) -> Box<dyn UpstreamOAuthProviderRepository<Error = Self::Error> + 'c> {
523            (**self).upstream_oauth_provider()
524        }
525
526        fn upstream_oauth_session<'c>(
527            &'c mut self,
528        ) -> Box<dyn UpstreamOAuthSessionRepository<Error = Self::Error> + 'c> {
529            (**self).upstream_oauth_session()
530        }
531
532        fn user<'c>(&'c mut self) -> Box<dyn UserRepository<Error = Self::Error> + 'c> {
533            (**self).user()
534        }
535
536        fn user_email<'c>(&'c mut self) -> Box<dyn UserEmailRepository<Error = Self::Error> + 'c> {
537            (**self).user_email()
538        }
539
540        fn user_password<'c>(
541            &'c mut self,
542        ) -> Box<dyn UserPasswordRepository<Error = Self::Error> + 'c> {
543            (**self).user_password()
544        }
545
546        fn user_recovery<'c>(
547            &'c mut self,
548        ) -> Box<dyn crate::user::UserRecoveryRepository<Error = Self::Error> + 'c> {
549            (**self).user_recovery()
550        }
551
552        fn user_registration<'c>(
553            &'c mut self,
554        ) -> Box<dyn UserRegistrationRepository<Error = Self::Error> + 'c> {
555            (**self).user_registration()
556        }
557
558        fn user_registration_token<'c>(
559            &'c mut self,
560        ) -> Box<dyn UserRegistrationTokenRepository<Error = Self::Error> + 'c> {
561            (**self).user_registration_token()
562        }
563
564        fn user_terms<'c>(&'c mut self) -> Box<dyn UserTermsRepository<Error = Self::Error> + 'c> {
565            (**self).user_terms()
566        }
567
568        fn browser_session<'c>(
569            &'c mut self,
570        ) -> Box<dyn BrowserSessionRepository<Error = Self::Error> + 'c> {
571            (**self).browser_session()
572        }
573
574        fn app_session<'c>(
575            &'c mut self,
576        ) -> Box<dyn AppSessionRepository<Error = Self::Error> + 'c> {
577            (**self).app_session()
578        }
579
580        fn oauth2_client<'c>(
581            &'c mut self,
582        ) -> Box<dyn OAuth2ClientRepository<Error = Self::Error> + 'c> {
583            (**self).oauth2_client()
584        }
585
586        fn oauth2_authorization_grant<'c>(
587            &'c mut self,
588        ) -> Box<dyn OAuth2AuthorizationGrantRepository<Error = Self::Error> + 'c> {
589            (**self).oauth2_authorization_grant()
590        }
591
592        fn oauth2_session<'c>(
593            &'c mut self,
594        ) -> Box<dyn OAuth2SessionRepository<Error = Self::Error> + 'c> {
595            (**self).oauth2_session()
596        }
597
598        fn oauth2_access_token<'c>(
599            &'c mut self,
600        ) -> Box<dyn OAuth2AccessTokenRepository<Error = Self::Error> + 'c> {
601            (**self).oauth2_access_token()
602        }
603
604        fn oauth2_refresh_token<'c>(
605            &'c mut self,
606        ) -> Box<dyn OAuth2RefreshTokenRepository<Error = Self::Error> + 'c> {
607            (**self).oauth2_refresh_token()
608        }
609
610        fn oauth2_device_code_grant<'c>(
611            &'c mut self,
612        ) -> Box<dyn OAuth2DeviceCodeGrantRepository<Error = Self::Error> + 'c> {
613            (**self).oauth2_device_code_grant()
614        }
615
616        fn compat_session<'c>(
617            &'c mut self,
618        ) -> Box<dyn CompatSessionRepository<Error = Self::Error> + 'c> {
619            (**self).compat_session()
620        }
621
622        fn compat_sso_login<'c>(
623            &'c mut self,
624        ) -> Box<dyn CompatSsoLoginRepository<Error = Self::Error> + 'c> {
625            (**self).compat_sso_login()
626        }
627
628        fn compat_access_token<'c>(
629            &'c mut self,
630        ) -> Box<dyn CompatAccessTokenRepository<Error = Self::Error> + 'c> {
631            (**self).compat_access_token()
632        }
633
634        fn compat_refresh_token<'c>(
635            &'c mut self,
636        ) -> Box<dyn CompatRefreshTokenRepository<Error = Self::Error> + 'c> {
637            (**self).compat_refresh_token()
638        }
639
640        fn personal_access_token<'c>(
641            &'c mut self,
642        ) -> Box<dyn PersonalAccessTokenRepository<Error = Self::Error> + 'c> {
643            (**self).personal_access_token()
644        }
645
646        fn personal_session<'c>(
647            &'c mut self,
648        ) -> Box<dyn PersonalSessionRepository<Error = Self::Error> + 'c> {
649            (**self).personal_session()
650        }
651
652        fn queue_worker<'c>(
653            &'c mut self,
654        ) -> Box<dyn QueueWorkerRepository<Error = Self::Error> + 'c> {
655            (**self).queue_worker()
656        }
657
658        fn queue_job<'c>(&'c mut self) -> Box<dyn QueueJobRepository<Error = Self::Error> + 'c> {
659            (**self).queue_job()
660        }
661
662        fn queue_schedule<'c>(
663            &'c mut self,
664        ) -> Box<dyn QueueScheduleRepository<Error = Self::Error> + 'c> {
665            (**self).queue_schedule()
666        }
667
668        fn policy_data<'c>(
669            &'c mut self,
670        ) -> Box<dyn PolicyDataRepository<Error = Self::Error> + 'c> {
671            (**self).policy_data()
672        }
673    }
674}