1
1
import { PipeTransform , Injectable , ArgumentMetadata } from '@nestjs/common' ;
2
+ import { Value } from 'src/movie/schemas/movie.schema' ;
2
3
import { IQuery } from '../interfaces/query.interface' ;
4
+ import { normalizeDate } from '../utils/query/parse-date.util' ;
3
5
4
6
const SYSTEM_KEYS = [
5
7
'sortField' ,
@@ -11,6 +13,58 @@ const SYSTEM_KEYS = [
11
13
'search' ,
12
14
] ;
13
15
16
+ const FIELDS = {
17
+ idKeys : [ 'id' , 'externalId.imdb' ] ,
18
+ regexSearchKeys : [
19
+ 'name' ,
20
+ 'alternativeName' ,
21
+ 'enName' ,
22
+ 'names.name' ,
23
+ 'tagline' ,
24
+ 'slogan' ,
25
+ 'description' ,
26
+ 'persons.name' ,
27
+ 'persons.enName' ,
28
+ 'persons.description' ,
29
+ ] ,
30
+ dateSearchKeys : [
31
+ 'premiere.world' ,
32
+ 'premiere.russia' ,
33
+ 'premiere.digital' ,
34
+ 'premiere.bluray' ,
35
+ 'premiere.dvd' ,
36
+ ] ,
37
+ numberSearchKeys : [
38
+ 'id' ,
39
+ 'externalId.imdb' ,
40
+ 'externalId.tmdb' ,
41
+ 'typeNumber' ,
42
+ 'movieLength' ,
43
+ 'year' ,
44
+ 'rating.kp' ,
45
+ 'rating.imdb' ,
46
+ 'rating.tmdb' ,
47
+ 'votes.kp' ,
48
+ 'votes.imdb' ,
49
+ 'votes.tmdb' ,
50
+ 'ratingAgeLimits' ,
51
+ 'persons.id' ,
52
+ 'budget.value' ,
53
+ 'fees.world' ,
54
+ 'fees.usa' ,
55
+ 'fees.russia' ,
56
+ 'image.postersCount' ,
57
+ 'image.backdropsCount' ,
58
+ 'image.framesCount' ,
59
+ 'reviewInfo.count' ,
60
+ 'reviewInfo.positiveCount' ,
61
+ 'seasonsInfo.number' ,
62
+ 'seasonsInfo.episodesCount' ,
63
+ 'videos.trailers.size' ,
64
+ 'videos.teasers.size' ,
65
+ ] ,
66
+ } ;
67
+
14
68
@Injectable ( )
15
69
export class QueryPipe implements PipeTransform {
16
70
transform ( value : any , metadata : ArgumentMetadata ) : IQuery {
@@ -31,6 +85,37 @@ export class QueryPipe implements PipeTransform {
31
85
}
32
86
} ;
33
87
88
+ const transformFieldValue = ( field : string , value : string ) : any => {
89
+ const isNullValue = value === '!null' ;
90
+ const isNumberField = FIELDS . numberSearchKeys . includes ( field ) ;
91
+ const isDateField = FIELDS . dateSearchKeys . includes ( field ) ;
92
+ const isRegexField = FIELDS . regexSearchKeys . includes ( field ) ;
93
+
94
+ if ( isNullValue ) {
95
+ return { $ne : null } ;
96
+ }
97
+
98
+ if ( ( isNumberField || isDateField ) && value . includes ( '-' ) ) {
99
+ const [ minValue , maxValue ] = value . split ( '-' ) ;
100
+ const result = maxValue
101
+ ? {
102
+ $gte : isDateField ? normalizeDate ( minValue ) : minValue ,
103
+ $lte : isDateField ? normalizeDate ( maxValue ) : maxValue ,
104
+ }
105
+ : isDateField
106
+ ? normalizeDate ( minValue )
107
+ : minValue ;
108
+
109
+ return result ;
110
+ }
111
+
112
+ if ( isRegexField ) {
113
+ return { $regex : new RegExp ( `.*${ value } .*` , 'i' ) } ;
114
+ }
115
+
116
+ return value ;
117
+ } ;
118
+
34
119
// Парсим параметры поиска в старом формате
35
120
if ( value . field && value . search ) {
36
121
if ( Array . isArray ( value . field ) && Array . isArray ( value . search ) ) {
@@ -50,10 +135,14 @@ export class QueryPipe implements PipeTransform {
50
135
// Форматируем данные, под валидный для mongo запрос
51
136
for ( const [ key , keyValue ] of Object . entries ( filter ) ) {
52
137
if ( ! SYSTEM_KEYS . includes ( key ) ) {
53
- if ( Array . isArray ( keyValue ) ) {
54
- filter [ key ] = { $in : keyValue } ;
138
+ const isArray = Array . isArray ( keyValue ) ;
139
+
140
+ if ( isArray ) {
141
+ filter [ key ] = {
142
+ $in : keyValue . map ( ( val ) => transformFieldValue ( key , val ) ) ,
143
+ } ;
55
144
} else {
56
- filter [ key ] = keyValue ;
145
+ filter [ key ] = transformFieldValue ( key , keyValue as string ) ;
57
146
}
58
147
}
59
148
}
0 commit comments