@@ -12,6 +12,7 @@ namespace SubSonic.Infrastructure.Builders
1212 using Linq . Expressions ;
1313 using Infrastructure . Schema ;
1414 using SysLinq = System . Linq ;
15+ using System . Diagnostics ;
1516
1617 public partial class DbSqlQueryBuilder
1718 {
@@ -145,6 +146,24 @@ private Expression BuildSelect(Expression expression, IEnumerable<DbColumnDeclar
145146 #endregion
146147
147148 #region Build Where
149+ public Expression BuildWhere ( DbExpression expression , LambdaExpression predicate )
150+ {
151+ if ( expression is null )
152+ {
153+ throw Error . ArgumentNull ( nameof ( expression ) ) ;
154+ }
155+
156+ if ( predicate is null )
157+ {
158+ throw Error . ArgumentNull ( nameof ( predicate ) ) ;
159+ }
160+
161+ MethodInfo method = typeof ( Queryable ) . GetGenericMethod ( nameof ( Queryable . Where ) , new [ ] { expression . Type , predicate . GetType ( ) } ) ;
162+
163+ return DbWherePredicateBuilder . GetWhereTranslation (
164+ DbExpression . DbWhere ( method , new Expression [ ] { expression , predicate } ) ) ;
165+ }
166+
148167 public Expression BuildWhere ( DbTableExpression table , Expression where , Type type , LambdaExpression predicate )
149168 {
150169 if ( where . IsNotNull ( ) )
@@ -158,38 +177,39 @@ public Expression BuildWhere(DbTableExpression table, Expression where, Type typ
158177 where is DbWhereExpression _where )
159178 {
160179 Expression
161- logical = DbWherePredicateBuilder . GetBodyExpression ( _where . LambdaPredicate . Body , predicate . Body , DbGroupOperator . AndAlso ) ;
180+ logical = DbWherePredicateBuilder . GetBodyExpression ( _where . GetArgument ( 1 ) , predicate . Body , DbGroupOperator . AndAlso ) ;
162181 predicate = BuildLambda ( logical , LambdaType . Predicate ) as LambdaExpression ;
163182 }
164183 else
165184 {
166185 throw new NotSupportedException ( ) ;
167186 }
168187 }
169- return DbExpression . DbWhere ( table , type , predicate ) ;
188+
189+ throw Error . NotImplemented ( ) ;
170190 }
171191
172- public Expression BuildWhere ( DbTableExpression table , Expression where , Type type , Expression predicate )
173- {
174- LambdaExpression lambda = null ;
192+ // public Expression BuildWhere(DbTableExpression table, Expression where, Type type, Expression predicate)
193+ // {
194+ // LambdaExpression lambda = null;
175195
176- if ( predicate is UnaryExpression unary )
177- {
178- if ( unary . Operand is LambdaExpression _unary )
179- {
180- lambda = _unary ;
181- }
182- }
196+ // if (predicate is UnaryExpression unary)
197+ // {
198+ // if (unary.Operand is LambdaExpression _unary)
199+ // {
200+ // lambda = _unary;
201+ // }
202+ // }
183203
184- return BuildWhere ( table , where , type , lambda ) ;
185- }
204+ // return BuildWhere(table, where, type, lambda);
205+ // }
186206
187207 public Expression BuildWherePredicate ( Expression collection , Expression lambda )
188208 {
189209 return BuildCall ( "Where" , collection , lambda ) ;
190210 }
191211
192- public Expression BuildWhereFindByIDPredicate ( DbTableExpression dbTable , object [ ] keyData , params string [ ] keyNames )
212+ public Expression BuildWhereFindByIDPredicate ( DbExpression expression , object [ ] keyData , params string [ ] keyNames )
193213 {
194214 if ( keyData . IsNull ( ) )
195215 {
@@ -206,16 +226,7 @@ public Expression BuildWhereFindByIDPredicate(DbTableExpression dbTable, object[
206226
207227 LambdaExpression predicate = ( LambdaExpression ) BuildLambda ( logical , LambdaType . Predicate ) ;
208228
209- return BuildWhere ( dbTable , null , DbEntity . EntityModelType , predicate ) ;
210- }
211-
212- public Expression BuildWhereExists < TEntity > ( DbTableExpression from , Type type , Expression < Func < TEntity , System . Linq . IQueryable > > select )
213- {
214- return DbExpression . DbWhere ( from , type , select , DbExpressionType . Exists ) ;
215- }
216- public Expression BuildWhereNotExists < TEntity > ( DbTableExpression from , Type type , Expression < Func < TEntity , System . Linq . IQueryable > > select )
217- {
218- return DbExpression . DbWhere ( from , type , select , DbExpressionType . NotExists ) ;
229+ return BuildWhere ( expression , predicate ) ;
219230 }
220231 #endregion
221232
@@ -252,27 +263,31 @@ public Expression BuildCall(string nameofCallee, Expression collection, Expressi
252263 public Expression BuildLambda ( Expression body , LambdaType @call , params string [ ] properties )
253264 {
254265 Expression result ;
266+
255267 switch ( call )
256268 {
257269 case Infrastructure . LambdaType . Predicate :
258270 {
259- Type fnType = Expression . GetFuncType ( Parameter . Type , typeof ( bool ) ) ;
271+ if ( body is null )
272+ {
273+ throw Error . ArgumentNull ( nameof ( body ) ) ;
274+ }
260275
261- result = Expression . Lambda ( fnType , body , Parameter ) ;
276+ return Expression . Lambda (
277+ Expression . GetFuncType ( Parameter . Type , body . Type ) ,
278+ body ,
279+ Parameter ) ;
262280 }
263- break ;
264281 case Infrastructure . LambdaType . Selector :
265282 {
266283 PropertyInfo info = Parameter . Type . GetProperty ( properties [ 0 ] ) ;
267284 Expression property = Expression . Property ( Parameter , info ) ;
268285
269- result = Expression . Lambda ( Expression . GetFuncType ( Parameter . Type , info . PropertyType ) , property , Parameter ) ;
286+ return Expression . Lambda ( Expression . GetFuncType ( Parameter . Type , info . PropertyType ) , property , Parameter ) ;
270287 }
271- break ;
272288 default :
273289 throw new NotImplementedException ( ) ;
274290 }
275- return result ;
276291 }
277292
278293 public Expression BuildLogicalIn ( Expression body , PropertyInfo property , SysLinq . IQueryable queryable , DbGroupOperator @group )
@@ -665,16 +680,32 @@ private Expression BuildSelectWithWhere(MethodCallExpression expression)
665680 }
666681 else if ( argument is UnaryExpression unary )
667682 {
668- if ( unary . Operand is LambdaExpression _unary )
683+ if ( unary . Operand is LambdaExpression predicate )
669684 {
670- where = _unary ;
685+ if ( select . Where is DbWhereExpression existing )
686+ {
687+ if ( existing . GetArgument ( 1 ) is LambdaExpression predicate2 )
688+ {
689+ Expression
690+ body = Expression . AndAlso ( predicate2 . Body , predicate . Body ) ;
691+
692+ where = Expression . Lambda ( predicate2 . Type , body , predicate2 . Parameters . ToArray ( ) ) ;
693+ }
694+ }
695+ else
696+ {
697+ where = predicate ;
698+ }
671699 }
672700 }
673701 }
674702
703+ MethodInfo method = typeof ( Queryable ) . GetGenericMethod ( nameof ( Queryable . Where ) , new [ ] { select . Type , where . GetType ( ) } ) ;
704+
675705 return DbExpression . DbSelect (
676706 select ,
677- DbExpression . DbWhere ( select . From , select . Type , where ) ) ;
707+ DbWherePredicateBuilder . GetWhereTranslation (
708+ DbExpression . DbWhere ( method , new Expression [ ] { select , where } ) ) ) ;
678709 }
679710
680711 return expression ;
0 commit comments