Selaa lähdekoodia

优化分页查询

zhou-hao 5 vuotta sitten
vanhempi
commit
3c14f85c2a

+ 7 - 6
hsweb-commons/hsweb-commons-crud/src/main/java/org/hswebframework/web/crud/configuration/EasyormProperties.java

@@ -73,31 +73,31 @@ public class EasyormProperties {
     @Getter
     @AllArgsConstructor
     public enum DialectEnum {
-        mysql(Dialect.MYSQL) {
+        mysql(Dialect.MYSQL,"?") {
             @Override
             public RDBSchemaMetadata createSchema(String name) {
                 return new MysqlSchemaMetadata(name);
             }
         },
-        mssql(Dialect.MSSQL) {
+        mssql(Dialect.MSSQL,"@arg") {
             @Override
             public RDBSchemaMetadata createSchema(String name) {
                 return new SqlServerSchemaMetadata(name);
             }
         },
-        oracle(Dialect.ORACLE) {
+        oracle(Dialect.ORACLE,"?") {
             @Override
             public RDBSchemaMetadata createSchema(String name) {
                 return new OracleSchemaMetadata(name);
             }
         },
-        postgres(Dialect.POSTGRES) {
+        postgres(Dialect.POSTGRES,"$") {
             @Override
             public RDBSchemaMetadata createSchema(String name) {
                 return new PostgresqlSchemaMetadata(name);
             }
         },
-        h2(Dialect.H2) {
+        h2(Dialect.H2,"$") {
             @Override
             public RDBSchemaMetadata createSchema(String name) {
                 return new H2SchemaMetadata(name);
@@ -105,7 +105,8 @@ public class EasyormProperties {
         },
         ;
 
-        Dialect dialect;
+        private Dialect dialect;
+        private String bindSymbol;
 
         public abstract RDBSchemaMetadata createSchema(String name);
     }

+ 5 - 2
hsweb-commons/hsweb-commons-crud/src/main/java/org/hswebframework/web/crud/configuration/R2dbcSqlExecutorConfiguration.java

@@ -18,8 +18,11 @@ import org.springframework.context.annotation.Configuration;
 public class R2dbcSqlExecutorConfiguration {
     @Bean
     @ConditionalOnMissingBean
-    public ReactiveSqlExecutor reactiveSqlExecutor() {
-        return new DefaultR2dbcExecutor();
+    public ReactiveSqlExecutor reactiveSqlExecutor(EasyormProperties properties) {
+        DefaultR2dbcExecutor executor = new DefaultR2dbcExecutor();
+        executor.setBindSymbol(properties.getDialect().getBindSymbol());
+        executor.setBindCustomSymbol(!executor.getBindSymbol().equals("?"));
+        return executor;
     }
 
     @Bean

+ 15 - 9
hsweb-commons/hsweb-commons-crud/src/main/java/org/hswebframework/web/crud/service/ReactiveCrudService.java

@@ -83,15 +83,21 @@ public interface ReactiveCrudService<E, K> {
 
     @Transactional(readOnly = true)
     default Mono<PagerResult<E>> queryPager(Mono<? extends QueryParam> queryParamMono) {
-        return count(queryParamMono)
-                .zipWhen(total -> {
-                    if (total == 0) {
-                        return Mono.just(Collections.<E>emptyList());
-                    }
-                    return queryParamMono
-                            .map(QueryParam::clone)
-                            .flatMap(q -> query(Mono.just(q.rePaging(total))).collectList());
-                }, PagerResult::of);
+        return queryParamMono
+                .cast(QueryParam.class)
+                .flatMap(param -> getRepository()
+                        .createQuery()
+                        .setParam(param)
+                        .count()
+                        .flatMap(total -> {
+                            if (total == 0) {
+                                return Mono.just(PagerResult.empty());
+                            }
+                            return queryParamMono
+                                    .map(QueryParam::clone)
+                                    .flatMap(q -> query(Mono.just(q.rePaging(total))).collectList())
+                                    .map(list -> PagerResult.of(total, list, param));
+                        }));
     }
 
     @Transactional(readOnly = true)

+ 47 - 0
hsweb-commons/hsweb-commons-crud/src/main/java/org/hswebframework/web/crud/sql/DefaultR2dbcExecutor.java

@@ -2,9 +2,12 @@ package org.hswebframework.web.crud.sql;
 
 import io.r2dbc.spi.Connection;
 import io.r2dbc.spi.ConnectionFactory;
+import io.r2dbc.spi.Statement;
+import lombok.Setter;
 import org.hswebframework.ezorm.rdb.executor.SqlRequest;
 import org.hswebframework.ezorm.rdb.executor.reactive.r2dbc.R2dbcReactiveSqlExecutor;
 import org.hswebframework.ezorm.rdb.executor.wrapper.ResultWrapper;
+import org.hswebframework.web.crud.configuration.EasyormProperties;
 import org.hswebframework.web.datasource.DataSourceHolder;
 import org.hswebframework.web.datasource.R2dbcDataSource;
 import org.reactivestreams.Publisher;
@@ -17,11 +20,55 @@ import reactor.core.publisher.Flux;
 import reactor.core.publisher.Mono;
 import reactor.core.publisher.SignalType;
 
+import java.time.ZoneOffset;
+import java.util.Date;
+
 public class DefaultR2dbcExecutor extends R2dbcReactiveSqlExecutor {
 
     @Autowired
     private ConnectionFactory defaultFactory;
 
+    @Setter
+    private boolean bindCustomSymbol = false;
+
+    @Setter
+    private String bindSymbol = "$";
+
+    @Override
+    public String getBindSymbol() {
+        return bindSymbol;
+    }
+
+    @Override
+    protected SqlRequest convertRequest(SqlRequest sqlRequest) {
+        if (bindCustomSymbol) {
+            return super.convertRequest(sqlRequest);
+        }
+        return sqlRequest;
+    }
+
+    protected void bindNull(Statement statement, int index, Class type) {
+        if (bindCustomSymbol) {
+            statement.bindNull(getBindSymbol() + (index + getBindFirstIndex()), type);
+            return;
+        }
+        statement.bindNull(index, type);
+    }
+
+    protected void bind(Statement statement, int index, Object value) {
+        if (value instanceof Date) {
+            value = ((Date) value)
+                    .toInstant()
+                    .atZone(ZoneOffset.systemDefault())
+                    .toLocalDateTime();
+        }
+        if (bindCustomSymbol) {
+            statement.bind(getBindSymbol() + (index + getBindFirstIndex()), value);
+            return;
+        }
+        statement.bind(index, value);
+    }
+
     @Override
     protected Mono<Connection> getConnection() {
         if (DataSourceHolder.isDynamicDataSourceReady()) {

+ 3 - 1
hsweb-commons/hsweb-commons-crud/src/main/java/org/hswebframework/web/crud/web/ResponseMessageWrapper.java

@@ -44,7 +44,9 @@ public class ResponseMessageWrapper extends ResponseBodyResultHandler {
     public Mono<Void> handleResult(ServerWebExchange exchange, HandlerResult result) {
         Object body = result.getReturnValue();
         if (body instanceof Mono) {
-            body = ((Mono) body).map(ResponseMessage::ok);
+            body = ((Mono) body)
+                    .switchIfEmpty(Mono.just(ResponseMessage.ok()))
+                    .map(ResponseMessage::ok);
         }
         if (body == null) {
             body = Mono.just(ResponseMessage.ok());

+ 13 - 9
hsweb-commons/hsweb-commons-crud/src/main/java/org/hswebframework/web/crud/web/reactive/ReactiveQueryController.java

@@ -55,15 +55,19 @@ public interface ReactiveQueryController<E, K> {
     @QueryAction
     @SuppressWarnings("all")
     default Mono<PagerResult<E>> queryPager(Mono<QueryParamEntity> query) {
-        return count(query)
-                .zipWhen(total -> {
-                    if (total == 0) {
-                        return Mono.just(Collections.<E>emptyList());
-                    }
-                    return query
-                            .map(QueryParam::clone)
-                            .flatMap(q -> query(Mono.just(q.rePaging(total))).collectList());
-                }, PagerResult::of);
+        return  query
+                .flatMap(param->{
+                    return getRepository().createQuery().setParam(param).count()
+                            .flatMap(total->{
+                                if (total == 0) {
+                                    return Mono.just(PagerResult.empty());
+                                }
+                                return query
+                                        .map(QueryParam::clone)
+                                        .flatMap(q -> query(Mono.just(q.rePaging(total))).collectList())
+                                        .map(list->PagerResult.of(total,list,param));
+                            });
+                });
     }
 
     @PostMapping("/_count")

+ 1 - 11
hsweb-commons/hsweb-commons-crud/src/main/java/org/hswebframework/web/crud/web/reactive/ReactiveServiceQueryController.java

@@ -1,6 +1,5 @@
 package org.hswebframework.web.crud.web.reactive;
 
-import org.hswebframework.ezorm.core.param.QueryParam;
 import org.hswebframework.web.api.crud.entity.PagerResult;
 import org.hswebframework.web.api.crud.entity.QueryParamEntity;
 import org.hswebframework.web.authorization.annotation.Authorize;
@@ -13,7 +12,6 @@ import org.springframework.web.bind.annotation.PostMapping;
 import reactor.core.publisher.Flux;
 import reactor.core.publisher.Mono;
 
-import java.util.Collections;
 
 public interface ReactiveServiceQueryController<E, K> {
 
@@ -54,15 +52,7 @@ public interface ReactiveServiceQueryController<E, K> {
     @QueryAction
     @SuppressWarnings("all")
     default Mono<PagerResult<E>> queryPager(Mono<QueryParamEntity> query) {
-        return count(query)
-                .zipWhen(total -> {
-                    if (total == 0) {
-                        return Mono.just(Collections.<E>emptyList());
-                    }
-                    return query
-                            .map(QueryParam::clone)
-                            .flatMap(q -> query(Mono.just(q.rePaging(total))).collectList());
-                }, PagerResult::of);
+        return getService().queryPager(query);
     }
 
     @PostMapping("/_count")