@@ -2,7 +2,6 @@ use std::{collections::HashMap, sync::Arc};
2
2
3
3
use async_trait:: async_trait;
4
4
use dashmap:: DashMap ;
5
- use futures:: lock:: Mutex ;
6
5
use iceberg_rust:: {
7
6
catalog:: {
8
7
bucket:: Bucket ,
@@ -30,8 +29,9 @@ use iceberg_rust::{
30
29
} ;
31
30
use object_store:: ObjectStore ;
32
31
use sqlx:: {
33
- any:: { install_default_drivers, AnyRow } ,
34
- AnyConnection , Connection , Row ,
32
+ any:: { install_default_drivers, AnyPoolOptions , AnyRow } ,
33
+ pool:: PoolOptions ,
34
+ AnyPool , Row ,
35
35
} ;
36
36
use uuid:: Uuid ;
37
37
@@ -40,7 +40,7 @@ use crate::error::Error;
40
40
#[ derive( Debug ) ]
41
41
pub struct SqlCatalog {
42
42
name : String ,
43
- connection : Arc < Mutex < AnyConnection > > ,
43
+ pool : AnyPool ,
44
44
object_store : Arc < dyn ObjectStore > ,
45
45
cache : Arc < DashMap < Identifier , ( String , TabularMetadata ) > > ,
46
46
}
@@ -55,7 +55,13 @@ impl SqlCatalog {
55
55
) -> Result < Self , Error > {
56
56
install_default_drivers ( ) ;
57
57
58
- let mut pool = AnyConnection :: connect ( & url) . await ?;
58
+ let mut options = PoolOptions :: new ( ) ;
59
+
60
+ if url. starts_with ( "sqlite" ) {
61
+ options = options. max_connections ( 1 ) ;
62
+ }
63
+
64
+ let pool = AnyPoolOptions :: connect ( options, & url) . await ?;
59
65
60
66
sqlx:: query (
61
67
"create table if not exists iceberg_tables (
@@ -67,7 +73,7 @@ impl SqlCatalog {
67
73
primary key (catalog_name, table_namespace, table_name)
68
74
);" ,
69
75
)
70
- . execute ( & mut pool)
76
+ . execute ( & pool)
71
77
. await ?;
72
78
73
79
sqlx:: query (
@@ -79,21 +85,21 @@ impl SqlCatalog {
79
85
primary key (catalog_name, namespace, property_key)
80
86
);" ,
81
87
)
82
- . execute ( & mut pool)
88
+ . execute ( & pool)
83
89
. await
84
90
. map_err ( Error :: from) ?;
85
91
86
92
Ok ( SqlCatalog {
87
93
name : name. to_owned ( ) ,
88
- connection : Arc :: new ( Mutex :: new ( pool) ) ,
94
+ pool,
89
95
object_store,
90
96
cache : Arc :: new ( DashMap :: new ( ) ) ,
91
97
} )
92
98
}
93
99
94
100
pub fn catalog_list ( & self ) -> Arc < SqlCatalogList > {
95
101
Arc :: new ( SqlCatalogList {
96
- connection : self . connection . clone ( ) ,
102
+ pool : self . pool . clone ( ) ,
97
103
object_store : self . object_store . clone ( ) ,
98
104
} )
99
105
}
@@ -169,8 +175,7 @@ impl Catalog for SqlCatalog {
169
175
let namespace = namespace. to_string ( ) ;
170
176
171
177
let rows = {
172
- let mut connection = self . connection . lock ( ) . await ;
173
- sqlx:: query ( & format ! ( "select table_namespace, table_name, metadata_location, previous_metadata_location from iceberg_tables where catalog_name = '{}' and table_namespace = '{}';" , & name, & namespace) ) . fetch_all ( & mut * connection) . await . map_err ( Error :: from) ?
178
+ sqlx:: query ( & format ! ( "select table_namespace, table_name, metadata_location, previous_metadata_location from iceberg_tables where catalog_name = '{}' and table_namespace = '{}';" , & name, & namespace) ) . fetch_all ( & self . pool ) . await . map_err ( Error :: from) ?
174
179
} ;
175
180
let iter = rows. iter ( ) . map ( query_map) ;
176
181
@@ -188,12 +193,11 @@ impl Catalog for SqlCatalog {
188
193
let name = self . name . clone ( ) ;
189
194
190
195
let rows = {
191
- let mut connection = self . connection . lock ( ) . await ;
192
196
sqlx:: query ( & format ! (
193
197
"select distinct table_namespace from iceberg_tables where catalog_name = '{}';" ,
194
198
& name
195
199
) )
196
- . fetch_all ( & mut * connection )
200
+ . fetch_all ( & self . pool )
197
201
. await
198
202
. map_err ( Error :: from) ?
199
203
} ;
@@ -215,10 +219,9 @@ impl Catalog for SqlCatalog {
215
219
let name = identifier. name ( ) . to_string ( ) ;
216
220
217
221
let rows = {
218
- let mut connection = self . connection . lock ( ) . await ;
219
222
sqlx:: query ( & format ! ( "select table_namespace, table_name, metadata_location, previous_metadata_location from iceberg_tables where catalog_name = '{}' and table_namespace = '{}' and table_name = '{}';" , & catalog_name,
220
223
& namespace,
221
- & name) ) . fetch_all ( & mut * connection ) . await . map_err ( Error :: from) ?
224
+ & name) ) . fetch_all ( & self . pool ) . await . map_err ( Error :: from) ?
222
225
} ;
223
226
let mut iter = rows. iter ( ) . map ( query_map) ;
224
227
@@ -230,10 +233,9 @@ impl Catalog for SqlCatalog {
230
233
let name = identifier. name ( ) . to_string ( ) ;
231
234
232
235
{
233
- let mut connection = self . connection . lock ( ) . await ;
234
236
sqlx:: query ( & format ! ( "delete from iceberg_tables where catalog_name = '{}' and table_namespace = '{}' and table_name = '{}';" , & catalog_name,
235
237
& namespace,
236
- & name) ) . execute ( & mut * connection ) . await . map_err ( Error :: from) ?
238
+ & name) ) . execute ( & self . pool ) . await . map_err ( Error :: from) ?
237
239
} ;
238
240
Ok ( ( ) )
239
241
}
@@ -243,10 +245,9 @@ impl Catalog for SqlCatalog {
243
245
let name = identifier. name ( ) . to_string ( ) ;
244
246
245
247
{
246
- let mut connection = self . connection . lock ( ) . await ;
247
248
sqlx:: query ( & format ! ( "delete from iceberg_tables where catalog_name = '{}' and table_namespace = '{}' and table_name = '{}';" , & catalog_name,
248
249
& namespace,
249
- & name) ) . execute ( & mut * connection ) . await . map_err ( Error :: from) ?
250
+ & name) ) . execute ( & self . pool ) . await . map_err ( Error :: from) ?
250
251
} ;
251
252
Ok ( ( ) )
252
253
}
@@ -256,10 +257,9 @@ impl Catalog for SqlCatalog {
256
257
let name = identifier. name ( ) . to_string ( ) ;
257
258
258
259
{
259
- let mut connection = self . connection . lock ( ) . await ;
260
260
sqlx:: query ( & format ! ( "delete from iceberg_tables where catalog_name = '{}' and table_namespace = '{}' and table_name = '{}';" , & catalog_name,
261
261
& namespace,
262
- & name) ) . execute ( & mut * connection ) . await . map_err ( Error :: from) ?
262
+ & name) ) . execute ( & self . pool ) . await . map_err ( Error :: from) ?
263
263
} ;
264
264
Ok ( ( ) )
265
265
}
@@ -273,10 +273,9 @@ impl Catalog for SqlCatalog {
273
273
let name = identifier. name ( ) . to_string ( ) ;
274
274
275
275
let row = {
276
- let mut connection = self . connection . lock ( ) . await ;
277
276
sqlx:: query ( & format ! ( "select table_namespace, table_name, metadata_location, previous_metadata_location from iceberg_tables where catalog_name = '{}' and table_namespace = '{}' and table_name = '{}';" , & catalog_name,
278
277
& namespace,
279
- & name) ) . fetch_one ( & mut * connection ) . await . map_err ( Error :: from) ?
278
+ & name) ) . fetch_one ( & self . pool ) . await . map_err ( Error :: from) ?
280
279
} ;
281
280
let row = query_map ( & row) . map_err ( Error :: from) ?;
282
281
@@ -331,9 +330,7 @@ impl Catalog for SqlCatalog {
331
330
let name = identifier. name ( ) . to_string ( ) ;
332
331
let metadata_location = metadata_location. to_string ( ) ;
333
332
334
- let mut connection = self . connection . lock ( ) . await ;
335
-
336
- sqlx:: query ( & format ! ( "insert into iceberg_tables (catalog_name, table_namespace, table_name, metadata_location) values ('{}', '{}', '{}', '{}');" , catalog_name, namespace, name, metadata_location) ) . execute ( & mut * connection) . await . map_err ( Error :: from) ?;
333
+ sqlx:: query ( & format ! ( "insert into iceberg_tables (catalog_name, table_namespace, table_name, metadata_location) values ('{}', '{}', '{}', '{}');" , catalog_name, namespace, name, metadata_location) ) . execute ( & self . pool ) . await . map_err ( Error :: from) ?;
337
334
}
338
335
self . clone ( )
339
336
. load_tabular ( & identifier)
@@ -373,9 +370,7 @@ impl Catalog for SqlCatalog {
373
370
let name = identifier. name ( ) . to_string ( ) ;
374
371
let metadata_location = metadata_location. to_string ( ) ;
375
372
376
- let mut connection = self . connection . lock ( ) . await ;
377
-
378
- sqlx:: query ( & format ! ( "insert into iceberg_tables (catalog_name, table_namespace, table_name, metadata_location) values ('{}', '{}', '{}', '{}');" , catalog_name, namespace, name, metadata_location) ) . execute ( & mut * connection) . await . map_err ( Error :: from) ?;
373
+ sqlx:: query ( & format ! ( "insert into iceberg_tables (catalog_name, table_namespace, table_name, metadata_location) values ('{}', '{}', '{}', '{}');" , catalog_name, namespace, name, metadata_location) ) . execute ( & self . pool ) . await . map_err ( Error :: from) ?;
379
374
}
380
375
self . clone ( )
381
376
. load_tabular ( & identifier)
@@ -422,8 +417,7 @@ impl Catalog for SqlCatalog {
422
417
)
423
418
. await ?;
424
419
{
425
- let mut connection = self . connection . lock ( ) . await ;
426
- let mut transaction = connection. begin ( ) . await . map_err ( Error :: from) ?;
420
+ let mut transaction = self . pool . begin ( ) . await . map_err ( Error :: from) ?;
427
421
let catalog_name = self . name . clone ( ) ;
428
422
let namespace = identifier. namespace ( ) . to_string ( ) ;
429
423
let name = identifier. name ( ) . to_string ( ) ;
@@ -493,8 +487,7 @@ impl Catalog for SqlCatalog {
493
487
let previous_metadata_file_location = previous_metadata_location. to_string ( ) ;
494
488
495
489
{
496
- let mut connection = self . connection . lock ( ) . await ;
497
- sqlx:: query ( & format ! ( "update iceberg_tables set metadata_location = '{}', previous_metadata_location = '{}' where catalog_name = '{}' and table_namespace = '{}' and table_name = '{}';" , metadata_file_location, previous_metadata_file_location, catalog_name, namespace, name) ) . execute ( & mut * connection) . await . map_err ( Error :: from) ?
490
+ sqlx:: query ( & format ! ( "update iceberg_tables set metadata_location = '{}', previous_metadata_location = '{}' where catalog_name = '{}' and table_namespace = '{}' and table_name = '{}';" , metadata_file_location, previous_metadata_file_location, catalog_name, namespace, name) ) . execute ( & self . pool ) . await . map_err ( Error :: from) ?
498
491
} ;
499
492
}
500
493
}
@@ -557,8 +550,7 @@ impl Catalog for SqlCatalog {
557
550
let previous_metadata_file_location = previous_metadata_location. to_string ( ) ;
558
551
559
552
{
560
- let mut connection = self . connection . lock ( ) . await ;
561
- sqlx:: query ( & format ! ( "update iceberg_tables set metadata_location = '{}', previous_metadata_location = '{}' where catalog_name = '{}' and table_namespace = '{}' and table_name = '{}';" , metadata_file_location, previous_metadata_file_location, catalog_name, namespace, name) ) . execute ( & mut * connection) . await . map_err ( Error :: from) ?
553
+ sqlx:: query ( & format ! ( "update iceberg_tables set metadata_location = '{}', previous_metadata_location = '{}' where catalog_name = '{}' and table_namespace = '{}' and table_name = '{}';" , metadata_file_location, previous_metadata_file_location, catalog_name, namespace, name) ) . execute ( & self . pool ) . await . map_err ( Error :: from) ?
562
554
} ;
563
555
}
564
556
}
@@ -619,8 +611,7 @@ impl Catalog for SqlCatalog {
619
611
let previous_metadata_file_location = previous_metadata_location. to_string ( ) ;
620
612
621
613
{
622
- let mut connection = self . connection . lock ( ) . await ;
623
- sqlx:: query ( & format ! ( "update iceberg_tables set metadata_location = '{}', previous_metadata_location = '{}' where catalog_name = '{}' and table_namespace = '{}' and table_name = '{}';" , metadata_file_location, previous_metadata_file_location, catalog_name, namespace, name) ) . execute ( & mut * connection) . await . map_err ( Error :: from) ?
614
+ sqlx:: query ( & format ! ( "update iceberg_tables set metadata_location = '{}', previous_metadata_location = '{}' where catalog_name = '{}' and table_namespace = '{}' and table_name = '{}';" , metadata_file_location, previous_metadata_file_location, catalog_name, namespace, name) ) . execute ( & self . pool ) . await . map_err ( Error :: from) ?
624
615
} ;
625
616
}
626
617
}
@@ -678,8 +669,7 @@ impl Catalog for SqlCatalog {
678
669
let metadata_location = metadata_location. to_string ( ) ;
679
670
680
671
{
681
- let mut connection = self . connection . lock ( ) . await ;
682
- sqlx:: query ( & format ! ( "insert into iceberg_tables (catalog_name, table_namespace, table_name, metadata_location) values ('{}', '{}', '{}', '{}');" , catalog_name, namespace, name, metadata_location) ) . execute ( & mut * connection) . await . map_err ( Error :: from) ?
672
+ sqlx:: query ( & format ! ( "insert into iceberg_tables (catalog_name, table_namespace, table_name, metadata_location) values ('{}', '{}', '{}', '{}');" , catalog_name, namespace, name, metadata_location) ) . execute ( & self . pool ) . await . map_err ( Error :: from) ?
683
673
} ;
684
674
}
685
675
self . clone ( )
@@ -702,7 +692,7 @@ impl SqlCatalog {
702
692
pub fn duplicate ( & self , name : & str ) -> Self {
703
693
Self {
704
694
name : name. to_owned ( ) ,
705
- connection : self . connection . clone ( ) ,
695
+ pool : self . pool . clone ( ) ,
706
696
object_store : self . object_store . clone ( ) ,
707
697
cache : Arc :: new ( DashMap :: new ( ) ) ,
708
698
}
@@ -711,15 +701,15 @@ impl SqlCatalog {
711
701
712
702
#[ derive( Debug ) ]
713
703
pub struct SqlCatalogList {
714
- connection : Arc < Mutex < AnyConnection > > ,
704
+ pool : AnyPool ,
715
705
object_store : Arc < dyn ObjectStore > ,
716
706
}
717
707
718
708
impl SqlCatalogList {
719
709
pub async fn new ( url : & str , object_store : Arc < dyn ObjectStore > ) -> Result < Self , Error > {
720
710
install_default_drivers ( ) ;
721
711
722
- let mut connection = AnyConnection :: connect ( & url) . await ?;
712
+ let pool = AnyPoolOptions :: connect ( PoolOptions :: new ( ) . max_connections ( 1 ) , & url) . await ?;
723
713
724
714
sqlx:: query (
725
715
"create table if not exists iceberg_tables (
@@ -731,7 +721,7 @@ impl SqlCatalogList {
731
721
primary key (catalog_name, table_namespace, table_name)
732
722
);" ,
733
723
)
734
- . execute ( & mut connection )
724
+ . execute ( & pool )
735
725
. await ?;
736
726
737
727
sqlx:: query (
@@ -743,14 +733,11 @@ impl SqlCatalogList {
743
733
primary key (catalog_name, namespace, property_key)
744
734
);" ,
745
735
)
746
- . execute ( & mut connection )
736
+ . execute ( & pool )
747
737
. await
748
738
. map_err ( Error :: from) ?;
749
739
750
- Ok ( SqlCatalogList {
751
- connection : Arc :: new ( Mutex :: new ( connection) ) ,
752
- object_store,
753
- } )
740
+ Ok ( SqlCatalogList { pool, object_store } )
754
741
}
755
742
}
756
743
@@ -759,16 +746,15 @@ impl CatalogList for SqlCatalogList {
759
746
async fn catalog ( & self , name : & str ) -> Option < Arc < dyn Catalog > > {
760
747
Some ( Arc :: new ( SqlCatalog {
761
748
name : name. to_owned ( ) ,
762
- connection : self . connection . clone ( ) ,
749
+ pool : self . pool . clone ( ) ,
763
750
object_store : self . object_store . clone ( ) ,
764
751
cache : Arc :: new ( DashMap :: new ( ) ) ,
765
752
} ) )
766
753
}
767
754
async fn list_catalogs ( & self ) -> Vec < String > {
768
755
let rows = {
769
- let mut connection = self . connection . lock ( ) . await ;
770
756
sqlx:: query ( "select distinct catalog_name from iceberg_tables;" )
771
- . fetch_all ( & mut * connection )
757
+ . fetch_all ( & self . pool )
772
758
. await
773
759
. map_err ( Error :: from)
774
760
. unwrap_or_default ( )
0 commit comments