1
+ use chrono:: { DateTime , Utc } ;
1
2
use sqlx:: Acquire ;
2
3
3
4
use super :: { Blob , FileRange } ;
@@ -69,7 +70,16 @@ impl DatabaseBackend {
69
70
// https://www.postgresql.org/message-id/162867790712200946i7ba8eb92v908ac595c0c35aee%40mail.gmail.com
70
71
let max_size = max_size. min ( std:: i32:: MAX as usize ) as i32 ;
71
72
72
- let ( path, mime, date_updated, compression, content, is_too_big) = if let Some ( r) = range {
73
+ struct Result {
74
+ path : String ,
75
+ mime : String ,
76
+ date_updated : DateTime < Utc > ,
77
+ compression : Option < i32 > ,
78
+ content : Option < Vec < u8 > > ,
79
+ is_too_big : bool ,
80
+ }
81
+
82
+ let result = if let Some ( r) = range {
73
83
// when we only want to get a range we can validate already if the range is small enough
74
84
if ( r. end ( ) - r. start ( ) + 1 ) > max_size as u64 {
75
85
return Err ( std:: io:: Error :: new (
@@ -80,10 +90,12 @@ impl DatabaseBackend {
80
90
}
81
91
let range_start = i32:: try_from ( * r. start ( ) ) ?;
82
92
83
- sqlx:: query!(
93
+ sqlx:: query_as!(
94
+ Result ,
84
95
r#"SELECT
85
96
path, mime, date_updated, compression,
86
- substring(content from $2 for $3) as content
97
+ substring(content from $2 for $3) as content,
98
+ FALSE as "is_too_big!"
87
99
FROM files
88
100
WHERE path = $1;"# ,
89
101
path,
@@ -92,21 +104,12 @@ impl DatabaseBackend {
92
104
)
93
105
. fetch_optional ( & self . pool )
94
106
. await ?
95
- . ok_or ( super :: PathNotFoundError )
96
- . map ( |row| {
97
- (
98
- row. path ,
99
- row. mime ,
100
- row. date_updated ,
101
- row. compression ,
102
- row. content ,
103
- false ,
104
- )
105
- } ) ?
107
+ . ok_or ( super :: PathNotFoundError ) ?
106
108
} else {
107
109
// The size limit is checked at the database level, to avoid receiving data altogether if
108
110
// the limit is exceeded.
109
- sqlx:: query!(
111
+ sqlx:: query_as!(
112
+ Result ,
110
113
r#"SELECT
111
114
path, mime, date_updated, compression,
112
115
(CASE WHEN LENGTH(content) <= $2 THEN content ELSE NULL END) AS content,
@@ -118,36 +121,26 @@ impl DatabaseBackend {
118
121
)
119
122
. fetch_optional ( & self . pool )
120
123
. await ?
121
- . ok_or ( super :: PathNotFoundError )
122
- . map ( |row| {
123
- (
124
- row. path ,
125
- row. mime ,
126
- row. date_updated ,
127
- row. compression ,
128
- row. content ,
129
- row. is_too_big ,
130
- )
131
- } ) ?
124
+ . ok_or ( super :: PathNotFoundError ) ?
132
125
} ;
133
126
134
- if is_too_big {
127
+ if result . is_too_big {
135
128
return Err ( std:: io:: Error :: new (
136
129
std:: io:: ErrorKind :: Other ,
137
130
crate :: error:: SizeLimitReached ,
138
131
)
139
132
. into ( ) ) ;
140
133
}
141
134
142
- let compression = compression. map ( |i| {
135
+ let compression = result . compression . map ( |i| {
143
136
i. try_into ( )
144
137
. expect ( "invalid compression algorithm stored in database" )
145
138
} ) ;
146
139
Ok ( Blob {
147
- path,
148
- mime,
149
- date_updated,
150
- content : content. unwrap_or_default ( ) ,
140
+ path : result . path ,
141
+ mime : result . mime ,
142
+ date_updated : result . date_updated ,
143
+ content : result . content . unwrap_or_default ( ) ,
151
144
compression,
152
145
} )
153
146
}
0 commit comments