11const cds = require ( '@sap/cds/lib' )
22const { expect } = cds . test
3- const CQL = ( [ cql ] ) => cds . parse . cql ( cql )
3+ const { cdr } = cds . ql
44const Foo = { name : 'Foo' }
55const Books = { name : 'capire.bookshop.Books' }
66
7- const { cdr } = cds . ql
87
9- // while jest has 'test' as alias to 'it', mocha doesn't
10- if ( ! global . test ) global . test = it
8+ const STAR = cdr ? '*' : { ref : [ '*' ] }
9+ const skip = { to :{ eql :( ) => skip } }
10+ const srv = new cds . Service
11+ let cqn
12+
13+ expect . plain = ( cqn ) => ! cqn . SELECT . one && ! cqn . SELECT . distinct ? expect ( cqn ) : skip
14+ expect . one = ( cqn ) => ! cqn . SELECT . distinct ? expect ( cqn ) : skip
1115
1216describe ( 'cds.ql → cqn' , ( ) => {
1317 //
14- let cqn
1518
1619 describe ( `SELECT...` , ( ) => {
1720
@@ -26,210 +29,206 @@ describe('cds.ql → cqn', () => {
2629 . to . eql ( SELECT . from ( Foo , [ '*' ] ) )
2730 } )
2831
29- test ( 'from ( Foo )' , ( ) => {
30- expect ( {
32+
33+ it ( 'should consistently handle lists' , ( ) => {
34+ const ID = 11 , args = [ { ref :[ 'foo' ] } , 'bar' , 3 ]
35+ const cqn = CQL `SELECT from Foo where ID=11 and x in (foo,'bar',3)`
36+ expect ( SELECT . from `Foo` . where `ID=${ ID } and x in ${ args } ` ) . to . eql ( cqn )
37+ expect ( SELECT . from ( Foo ) . where ( `ID=` , ID , `and x in` , args ) ) . to . eql ( cqn )
38+ expect ( SELECT . from ( Foo ) . where ( { ID , x :args } ) ) . to . eql ( cqn )
39+ } )
40+
41+ } )
42+
43+
44+ for ( let each of [ 'SELECT' , 'SELECT one' , 'SELECT distinct' ] ) {
45+ let SELECT ; beforeEach ( ( ) => SELECT = (
46+ each === 'SELECT distinct' ? cds . ql . SELECT . distinct :
47+ each === 'SELECT one' ? cds . ql . SELECT . one :
48+ cds . ql . SELECT
49+ ) )
50+ describe ( `${ each } ...` , ( ) => {
51+
52+ test ( `from Foo` , ( ) => {
53+ expect ( cqn = SELECT `from Foo` )
54+ . to . eql ( SELECT . from `Foo` )
55+ . to . eql ( SELECT . from ( 'Foo' ) )
56+ . to . eql ( SELECT . from ( Foo ) )
57+ . to . eql ( SELECT `Foo` )
58+ . to . eql ( SELECT ( 'Foo' ) )
59+ . to . eql ( SELECT ( Foo ) )
60+ expect . plain ( cqn )
61+ . to . eql ( CQL `SELECT from Foo` )
62+ . to . eql ( srv . read `Foo` )
63+ . to . eql ( srv . read ( 'Foo' ) )
64+ . to . eql ( srv . read ( Foo ) )
65+ . to . eql ( {
3166 SELECT : { from : { ref : [ 'Foo' ] } } ,
3267 } )
33- . to . eql ( CQL `SELECT from Foo` )
34- . to . eql ( SELECT . from ( Foo ) )
3568 } )
3669
37- test ( 'from ( ..., <key>)' , ( ) => {
38- // Compiler
39- expect ( CQL `SELECT from Foo[11]` ) . to . eql ( {
40- SELECT : {
41- // REVISIT: add one:true?
42- from : { ref : [ { id : 'Foo' , where : [ { val : 11 } ] } ] } ,
43- } ,
70+
71+ test ( 'from Foo [<key>]' , ( ) => {
72+
73+ expect ( cqn = SELECT `from Foo[11]` )
74+ . to . eql ( SELECT `from Foo[${ 11 } ]` )
75+ . to . eql ( SELECT . from `Foo[11]` )
76+ . to . eql ( SELECT . from `Foo[${ 11 } ]` )
77+ . to . eql ( SELECT `Foo[11]` )
78+ expect . plain ( cqn )
79+ . to . eql ( CQL `SELECT from Foo[11]` )
80+ . to . eql ( srv . read `Foo[11]` )
81+ . to . eql ( {
82+ SELECT : { from : {
83+ ref : [ { id : 'Foo' , where : [ { val : 11 } ] } ]
84+ } } ,
4485 } )
4586
46- expect ( CQL `SELECT from Foo[ID=11]` ) . to . eql ( {
47- SELECT : {
48- // REVISIT: add one:true
49- from : {
50- ref : [ { id : 'Foo' , where : [ { ref : [ 'ID' ] } , '=' , { val : 11 } ] } ] ,
51- } ,
52- } ,
87+ if ( cdr ) expect . plain ( cqn )
88+ . to . eql ( srv . read `Foo[${ 11 } ]` )
89+ . to . eql ( SELECT `Foo[${ 11 } ]` )
90+
91+ expect ( ( cqn = SELECT `from Foo[ID=11]` ) )
92+ . to . eql ( SELECT `from Foo[ID=${ 11 } ]` )
93+ . to . eql ( SELECT . from `Foo[ID=11]` )
94+ . to . eql ( SELECT . from `Foo[ID=${ 11 } ]` )
95+ . to . eql ( SELECT `Foo[ID=11]` )
96+ expect . plain ( cqn )
97+ . to . eql ( CQL `SELECT from Foo[ID=11]` )
98+ . to . eql ( srv . read `Foo[ID=11]` )
99+ . to . eql ( {
100+ SELECT : { from : {
101+ ref : [ { id : 'Foo' , where : [ { ref : [ 'ID' ] } , '=' , { val : 11 } ] } ] ,
102+ } } ,
53103 } )
54104
55- // Runtime ds.ql
56- expect ( SELECT . from ( Foo , 11 ) )
57- . to . eql ( SELECT . from ( Foo , { ID : 11 } ) )
58- . to . eql ( SELECT . from ( Foo ) . byKey ( 11 ) )
59- . to . eql ( SELECT . from ( Foo ) . byKey ( { ID : 11 } ) )
60- . to . eql ( SELECT . one . from ( Foo ) . where ( { ID : 11 } ) )
61- . to . eql ( {
62- // REVISIT: should produce CQN as the ones above?
63- SELECT : {
64- one : true ,
65- from : { ref : [ 'Foo' ] } ,
66- where : [ { ref : [ 'ID' ] } , '=' , { val : 11 } ] ,
67- } ,
68- } )
105+ if ( cdr ) expect . plain ( cqn )
106+ . to . eql ( SELECT `Foo[ID=${ 11 } ]` )
107+ . to . eql ( srv . read `Foo[ID=${ 11 } ]` )
69108
70- expect ( CQL `SELECT from Foo[11]{a}` ) . to . eql ( {
109+ // Following implicitly resolve to SELECT.one
110+ expect ( cqn = SELECT . from ( Foo , 11 ) )
111+ . to . eql ( SELECT . from ( Foo , { ID :11 } ) )
112+ . to . eql ( SELECT . from ( Foo ) . byKey ( 11 ) )
113+ . to . eql ( SELECT . from ( Foo ) . byKey ( { ID :11 } ) )
114+ expect . one ( cqn )
115+ . to . eql ( {
71116 SELECT : {
72- // REVISIT: add one:true?
73- from : { ref : [ { id : 'Foo' , where : [ { val : 11 } ] } ] } ,
74- columns : [ { ref : [ 'a' ] } ] ,
117+ one : true ,
118+ from : { ref : [ 'Foo' ] } ,
119+ where : [ { ref : [ 'ID' ] } , '=' , { val : 11 } ] ,
75120 } ,
76121 } )
77122
78- expect ( SELECT . from ( Foo , 11 , [ 'a' ] ) )
79- . to . eql ( SELECT . from ( Foo , 11 , ( foo ) => foo . a ) )
80- . to . eql ( {
81- // REVISIT: should produce CQN as the ones above?
82- SELECT : {
83- one : true ,
84- from : { ref : [ 'Foo' ] } ,
85- columns : [ { ref : [ 'a' ] } ] ,
86- where : [ { ref : [ 'ID' ] } , '=' , { val : 11 } ] ,
87- } ,
88- } )
89123 } )
90124
91- test ( 'from ( ..., => {...})' , ( ) => {
92- // single *, prefix and postfix, as array and function
93- let parsed , fluid
94- expect ( ( parsed = CQL `SELECT * from Foo` ) ) . to . eql ( CQL `SELECT from Foo{*}` )
95- //> .to.eql... FIXME: see skipped 'should handle * correctly' below
96- expect ( ( fluid = SELECT ( '*' ) . from ( Foo ) ) )
97- . to . eql ( SELECT . from ( Foo , [ '*' ] ) )
98- . to . eql ( SELECT . from ( Foo , ( foo ) => foo ( '*' ) ) )
99- . to . eql ( SELECT . from ( Foo ) . columns ( '*' ) )
100- . to . eql ( SELECT . from ( Foo ) . columns ( ( foo ) => foo ( '*' ) ) )
101- . to . eql ( {
102- SELECT : { from : { ref : [ 'Foo' ] } , columns : [ cdr ? '*' : { ref : [ '*' ] } ] } ,
103- } )
104-
105- if ( cdr === 'all' ) expect ( parsed ) . to . eql ( fluid )
106-
107- // single column, prefix and postfix, as array and function
108- expect ( CQL `SELECT a from Foo` )
109- expect ( CQL `SELECT from Foo {a}` )
110- . to . eql ( SELECT . from ( Foo , [ 'a' ] ) )
111- . to . eql ( SELECT . from ( Foo , ( foo ) => foo . a ) )
112- . to . eql ( {
113- SELECT : { from : { ref : [ 'Foo' ] } , columns : [ { ref : [ 'a' ] } ] } ,
114- } )
115-
116- // multiple columns, prefix and postfix, as array and function
117- expect ( CQL `SELECT a,b as c from Foo` )
118-
119- expect ( CQL `SELECT from Foo {a,b as c}` ) . to . eql ( cqn = {
125+ test ( 'from Foo {...}' , ( ) => {
126+
127+ expect ( cqn = SELECT `*,a,b as c` . from `Foo` )
128+ . to . eql ( SELECT `*,a,b as c` . from ( Foo ) )
129+ . to . eql ( SELECT ( '*' , 'a' , { b :'c' } ) . from `Foo` )
130+ . to . eql ( SELECT ( '*' , 'a' , { b :'c' } ) . from ( Foo ) )
131+ . to . eql ( SELECT ( [ '*' , 'a' , { b :'c' } ] ) . from ( Foo ) )
132+ . to . eql ( SELECT . columns ( '*' , 'a' , { b :'c' } ) . from ( Foo ) )
133+ . to . eql ( SELECT . columns ( [ '*' , 'a' , { b :'c' } ] ) . from ( Foo ) )
134+ . to . eql ( SELECT . columns ( ( foo ) => { foo `.*` , foo . a , foo . b `as c` } ) . from ( Foo ) )
135+ . to . eql ( SELECT . columns ( ( foo ) => { foo ( '*' ) , foo . a , foo . b . as ( 'c' ) } ) . from ( Foo ) )
136+ . to . eql ( SELECT . from ( Foo ) . columns ( '*' , 'a' , { b :'c' } ) )
137+ . to . eql ( SELECT . from ( Foo ) . columns ( [ '*' , 'a' , { b :'c' } ] ) )
138+ . to . eql ( SELECT . from ( Foo ) . columns ( ( foo ) => { foo `.*` , foo . a , foo . b `as c` } ) )
139+ . to . eql ( SELECT . from ( Foo ) . columns ( ( foo ) => { foo ( '*' ) , foo . a , foo . b . as ( 'c' ) } ) )
140+ . to . eql ( SELECT . from ( Foo , [ '*' , 'a' , { b :'c' } ] ) )
141+ . to . eql ( SELECT . from ( Foo , ( foo ) => { foo `.*` , foo . a , foo . b `as c` } ) )
142+ . to . eql ( SELECT . from ( Foo , ( foo ) => { foo ( '*' ) , foo . a , foo . b . as ( 'c' ) } ) )
143+
144+ expect . plain ( cqn )
145+ . to . eql ( {
120146 SELECT : {
121147 from : { ref : [ 'Foo' ] } ,
122- columns : [ { ref : [ 'a' ] } , { ref : [ 'b' ] , as : 'c' } ] ,
148+ columns : [ STAR , { ref : [ 'a' ] } , { ref : [ 'b' ] , as : 'c' } ] ,
123149 } ,
124150 } )
125- expect ( SELECT . from ( Foo , [ 'a' , { b : 'c' } ] ) ) . to . eql ( cqn )
126- expect (
127- SELECT . from ( Foo , ( foo ) => {
128- foo . a , foo . b . as ( 'c' )
129- } )
130- ) . to . eql ( cqn )
131- expect ( SELECT . from ( Foo ) . columns ( 'a' , { b : 'c' } ) ) . to . eql ( cqn )
132- expect ( SELECT . from ( Foo ) . columns ( [ 'a' , { b : 'c' } ] ) ) . to . eql ( cqn )
133- expect (
134- SELECT . from ( Foo ) . columns ( ( foo ) => {
135- foo . a , foo . b . as ( 'c' )
136- } )
137- ) . to . eql ( cqn )
138-
139- // multiple columns and *, prefix and postfix, as array and function
140- expect ( CQL `SELECT *,a,b from Foo` ) . to . eql ( CQL `SELECT from Foo{*,a,b}` )
141- //> .to.eql... FIXME: see skipped 'should handle * correctly' below
142- expect ( SELECT . from ( Foo , [ 'a' , 'b' , '*' ] ) )
143- . to . eql ( SELECT . from ( Foo ) . columns ( 'a' , 'b' , '*' ) )
144- . to . eql ( SELECT . from ( Foo ) . columns ( [ 'a' , 'b' , '*' ] ) )
145- . to . eql (
146- SELECT . from ( Foo , ( foo ) => {
147- foo . a , foo . b , foo ( '*' )
148- } )
149- )
151+
152+ cdr && expect . plain ( cqn )
153+ . to . eql ( CQL `SELECT *,a,b as c from Foo` )
154+ . to . eql ( CQL `SELECT from Foo {*,a,b as c}` )
155+
156+ // Test combination with key as second argument to .from
157+ expect ( cqn = SELECT . from ( Foo , 11 , [ 'a' ] ) )
158+ . to . eql ( SELECT . from ( Foo , 11 , foo => foo . a ) )
159+ expect . one ( cqn )
150160 . to . eql ( {
151161 SELECT : {
162+ one : true ,
152163 from : { ref : [ 'Foo' ] } ,
153- columns : [ { ref : [ 'a' ] } , { ref : [ 'b' ] } , cdr ? '*' : { ref : [ '*' ] } ] ,
164+ columns : [ { ref : [ 'a' ] } ] ,
165+ where : [ { ref : [ 'ID' ] } , '=' , { val : 11 } ] ,
154166 } ,
155167 } )
168+
156169 } )
157170
158- test ( 'from ( ..., => _.expand ( x=>{...})) ' , ( ) => {
171+ test ( 'with nested expands ' , ( ) => {
159172 // SELECT from Foo { *, x, bar.*, car{*}, boo { *, moo.zoo } }
160- expect (
161- SELECT . from ( Foo , ( foo ) => {
162- foo ( '*' ) ,
163- foo . x ,
164- foo . car ( '*' ) ,
165- foo . boo ( ( b ) => {
166- b ( '*' ) , b . moo . zoo ( ( x ) => x . y . z )
167- } )
173+ expect ( cqn =
174+ SELECT . from ( Foo , foo => {
175+ foo `*` , foo . x , foo . car `*` , foo . boo ( b => {
176+ b `*` , b . moo . zoo (
177+ x => x . y . z
178+ )
179+ } )
168180 } )
169- ) . to . eql ( {
181+ ) . to . eql (
182+ SELECT . from ( Foo , foo => {
183+ foo ( '*' ) , foo . x , foo . car ( '*' ) , foo . boo ( b => {
184+ b ( '*' ) , b . moo . zoo (
185+ x => x . y . z
186+ )
187+ } )
188+ } )
189+ )
190+
191+ expect . plain ( cqn )
192+ . to . eql ( {
170193 SELECT : {
171194 from : { ref : [ 'Foo' ] } ,
172195 columns : [
173- cdr ? '*' : { ref : [ '*' ] } ,
196+ STAR ,
174197 { ref : [ 'x' ] } ,
175198 { ref : [ 'car' ] , expand : [ '*' ] } ,
176199 {
177200 ref : [ 'boo' ] ,
178- expand : [ '*' , { ref : [ 'moo' , 'zoo' ] , expand : [ { ref : [ 'y' , 'z' ] } ] } ] ,
201+ expand : [ '*' , { ref : [ 'moo' , 'zoo' ] , expand : [ { ref : [ 'y' , 'z' ] } ] } ] ,
179202 } ,
180203 ] ,
181204 } ,
182205 } )
183206 } )
184207
185- test ( 'from ( ..., => _.inline ( _=>{...}))' , ( ) => {
208+ if ( each !== 'SELECT' ) return
209+
210+ test ( 'with nested inlines' , ( ) => {
186211 // SELECT from Foo { *, x, bar.*, car{*}, boo { *, moo.zoo } }
187212 expect (
188- SELECT . from ( Foo , ( foo ) => {
189- foo . bar ( '*' ) ,
190- foo . bar ( '.*' ) , //> leading dot indicates inline
191- foo . boo ( ( x ) => x . moo . zoo ) ,
192- foo . boo ( ( _ ) => _ . moo . zoo ) //> underscore arg name indicates inline
213+ SELECT . from ( Foo , foo => {
214+ foo . bar `*` ,
215+ foo . bar `.*` , //> leading dot indicates inline
216+ foo . boo ( _ => _ . moo . zoo ) , //> underscore arg name indicates inline
217+ foo . boo ( x => x . moo . zoo )
193218 } )
194219 ) . to . eql ( {
195220 SELECT : {
196221 from : { ref : [ 'Foo' ] } ,
197222 columns : [
198223 { ref : [ 'bar' ] , expand : [ '*' ] } ,
199224 { ref : [ 'bar' ] , inline : [ '*' ] } ,
200- { ref : [ 'boo' ] , expand : [ { ref : [ 'moo' , 'zoo' ] } ] } ,
201225 { ref : [ 'boo' ] , inline : [ { ref : [ 'moo' , 'zoo' ] } ] } ,
226+ { ref : [ 'boo' ] , expand : [ { ref : [ 'moo' , 'zoo' ] } ] } ,
202227 ] ,
203228 } ,
204229 } )
205230 } )
206231
207- test ( 'one / distinct ...' , ( ) => {
208- expect ( SELECT . distinct . from ( Foo ) . SELECT )
209- // .to.eql(CQL(`SELECT distinct from Foo`).SELECT)
210- . to . eql ( SELECT . distinct ( Foo ) . SELECT )
211- . to . eql ( { distinct : true , from : { ref : [ 'Foo' ] } } )
212-
213- expect ( SELECT . one . from ( Foo ) . SELECT )
214- // .to.eql(CQL(`SELECT one from Foo`).SELECT)
215- . to . eql ( SELECT . one ( Foo ) . SELECT )
216- . to . eql ( { one : true , from : { ref : [ 'Foo' ] } } )
217-
218- expect ( SELECT . one ( 'a' ) . from ( Foo ) . SELECT )
219- // .to.eql(CQL(`SELECT distinct a from Foo`).SELECT)
220- . to . eql ( SELECT . one ( [ 'a' ] ) . from ( Foo ) . SELECT )
221- . to . eql ( SELECT . one ( Foo , [ 'a' ] ) . SELECT )
222- . to . eql ( SELECT . one ( Foo , ( foo ) => foo . a ) . SELECT )
223- . to . eql ( SELECT . one . from ( Foo , ( foo ) => foo . a ) . SELECT )
224- . to . eql ( SELECT . one . from ( Foo , [ 'a' ] ) . SELECT )
225- . to . eql ( {
226- one : true ,
227- from : { ref : [ 'Foo' ] } ,
228- columns : [ { ref : [ 'a' ] } ] ,
229- } )
230- // same for works distinct
231- } )
232-
233232 it ( 'should correctly handle { ... and:{...} }' , ( ) => {
234233 expect ( SELECT . from ( Foo ) . where ( { x : 1 , and : { y : 2 , or : { z : 3 } } } ) ) . to . eql ( {
235234 SELECT : {
@@ -427,6 +426,7 @@ describe('cds.ql → cqn', () => {
427426
428427 //
429428 } )
429+ }
430430
431431 describe ( `INSERT...` , ( ) => {
432432 test ( 'entries ({a,b}, ...)' , ( ) => {
0 commit comments