diff --git a/README.md b/README.md index 15e2a7b5..7c63482d 100644 --- a/README.md +++ b/README.md @@ -1,7 +1,7 @@ # JetLinks 物联网基础平台 ![GitHub Workflow Status](https://img.shields.io/github/workflow/status/jetlinks/jetlinks-community/Auto%20Deploy%20Docker?label=docker) -![Version](https://img.shields.io/badge/Version-1.7--RELEASE-brightgreen) +![Version](https://img.shields.io/badge/Version-1.8--RELEASE-brightgreen) ![QQ群2021514](https://img.shields.io/badge/QQ群-2021514-brightgreen) ![jetlinks](https://visitor-badge.glitch.me/badge?page_id=jetlinks) diff --git a/docker/run-all/docker-compose.yml b/docker/run-all/docker-compose.yml index 2b73ad7e..5ffa7609 100644 --- a/docker/run-all/docker-compose.yml +++ b/docker/run-all/docker-compose.yml @@ -59,7 +59,7 @@ services: links: - jetlinks:jetlinks jetlinks: - image: registry.cn-shenzhen.aliyuncs.com/jetlinks/jetlinks-standalone:1.8.0-SNAPSHOT + image: registry.cn-shenzhen.aliyuncs.com/jetlinks/jetlinks-standalone:1.8.0 container_name: jetlinks-ce ports: - 8848:8848 # API端口 diff --git a/jetlinks-components/common-component/pom.xml b/jetlinks-components/common-component/pom.xml index 748fe8cf..38025290 100644 --- a/jetlinks-components/common-component/pom.xml +++ b/jetlinks-components/common-component/pom.xml @@ -5,7 +5,7 @@ jetlinks-components org.jetlinks.community - 1.8.0-SNAPSHOT + 1.8.0 4.0.0 diff --git a/jetlinks-components/common-component/src/main/java/org/jetlinks/community/Interval.java b/jetlinks-components/common-component/src/main/java/org/jetlinks/community/Interval.java index c7842b19..6829b000 100644 --- a/jetlinks-components/common-component/src/main/java/org/jetlinks/community/Interval.java +++ b/jetlinks-components/common-component/src/main/java/org/jetlinks/community/Interval.java @@ -1,26 +1,37 @@ package org.jetlinks.community; +import com.alibaba.fastjson.annotation.JSONType; +import com.fasterxml.jackson.core.JsonParser; +import com.fasterxml.jackson.databind.DeserializationContext; +import com.fasterxml.jackson.databind.JsonDeserializer; +import com.fasterxml.jackson.databind.JsonNode; +import com.fasterxml.jackson.databind.annotation.JsonDeserialize; import lombok.AllArgsConstructor; import lombok.Getter; +import lombok.NoArgsConstructor; +import lombok.SneakyThrows; import java.math.BigDecimal; @Getter @AllArgsConstructor +@NoArgsConstructor +@JsonDeserialize(using = Interval.IntervalJSONDeserializer.class) +@JSONType(deserializer = Interval.IntervalJSONDeserializer.class) public class Interval { - public static String year = "y"; - public static String quarter = "q"; - public static String month = "M"; - public static String weeks = "w"; - public static String days = "d"; - public static String hours = "h"; - public static String minutes = "m"; - public static String seconds = "s"; + public static final String year = "y"; + public static final String quarter = "q"; + public static final String month = "M"; + public static final String weeks = "w"; + public static final String days = "d"; + public static final String hours = "h"; + public static final String minutes = "m"; + public static final String seconds = "s"; - private final BigDecimal number; + private BigDecimal number; - private final String expression; + private String expression; public boolean isFixed() { return expression.equalsIgnoreCase(hours) || @@ -61,18 +72,55 @@ public class Interval { public static Interval of(String expr) { - char[] number = new char[32]; + char[] chars = expr.toCharArray(); int numIndex = 0; for (char c : expr.toCharArray()) { if (c == '-' || c == '.' || (c >= '0' && c <= '9')) { - number[numIndex++] = c; - continue; + numIndex++; + } else { + BigDecimal val = new BigDecimal(chars, 0, numIndex); + return new Interval(val, expr.substring(numIndex)); } - BigDecimal val = new BigDecimal(number, 0, numIndex); - return new Interval(val, expr.substring(numIndex)); + } throw new IllegalArgumentException("can not parse interval expression:" + expr); } + public String getDefaultFormat() { + switch (getExpression()) { + case year: + return "yyyy"; + case quarter: + case month: + return "yyyy-MM"; + case days: + return "yyyy-MM-dd"; + case hours: + return "MM-dd HH"; + case minutes: + return "MM-dd HH:mm"; + case seconds: + return "HH:mm:ss"; + default: + return "yyyy-MM-dd HH:mm:ss"; + } + } + + public static class IntervalJSONDeserializer extends JsonDeserializer { + + @Override + @SneakyThrows + public Interval deserialize(JsonParser jp, DeserializationContext ctxt) { + JsonNode node = jp.getCodec().readTree(jp); + + String currentName = jp.currentName(); + Object currentValue = jp.getCurrentValue(); + if (currentName == null || currentValue == null) { + return null; + } + return of(node.textValue()); + } + } + } diff --git a/jetlinks-components/common-component/src/main/java/org/jetlinks/community/Version.java b/jetlinks-components/common-component/src/main/java/org/jetlinks/community/Version.java index 72d8f746..ffdbefc0 100644 --- a/jetlinks-components/common-component/src/main/java/org/jetlinks/community/Version.java +++ b/jetlinks-components/common-component/src/main/java/org/jetlinks/community/Version.java @@ -8,6 +8,6 @@ public class Version { private final String edition = "community"; - private final String version = "1.8.0-SNAPSHOT"; + private final String version = "1.8.0"; } diff --git a/jetlinks-components/dashboard-component/pom.xml b/jetlinks-components/dashboard-component/pom.xml index 470470e3..1e2b9d45 100644 --- a/jetlinks-components/dashboard-component/pom.xml +++ b/jetlinks-components/dashboard-component/pom.xml @@ -5,7 +5,7 @@ jetlinks-components org.jetlinks.community - 1.8.0-SNAPSHOT + 1.8.0 4.0.0 diff --git a/jetlinks-components/elasticsearch-component/pom.xml b/jetlinks-components/elasticsearch-component/pom.xml index 4b7a198a..342b5a49 100644 --- a/jetlinks-components/elasticsearch-component/pom.xml +++ b/jetlinks-components/elasticsearch-component/pom.xml @@ -5,7 +5,7 @@ jetlinks-components org.jetlinks.community - 1.8.0-SNAPSHOT + 1.8.0 ../pom.xml 4.0.0 diff --git a/jetlinks-components/elasticsearch-component/src/main/java/org/jetlinks/community/elastic/search/service/reactive/ReactiveAggregationService.java b/jetlinks-components/elasticsearch-component/src/main/java/org/jetlinks/community/elastic/search/service/reactive/ReactiveAggregationService.java index c91bd8d8..8a41818c 100644 --- a/jetlinks-components/elasticsearch-component/src/main/java/org/jetlinks/community/elastic/search/service/reactive/ReactiveAggregationService.java +++ b/jetlinks-components/elasticsearch-component/src/main/java/org/jetlinks/community/elastic/search/service/reactive/ReactiveAggregationService.java @@ -88,17 +88,17 @@ public class ReactiveAggregationService implements AggregationService { builder.timeZone(ZoneId.systemDefault()); builder.order(BucketOrder.key(false)); if (timeGroup.getInterval() != null) { + Interval interval = timeGroup.getInterval(); + String intervalString = interval.toString(); if (restClient.serverVersion().after(Version.V_7_2_0)) { - Interval interval = timeGroup.getInterval(); - if (interval.isFixed()) { - builder.fixedInterval(new DateHistogramInterval(timeGroup.getInterval().toString())); - } else if (interval.isCalendar()) { - builder.calendarInterval(new DateHistogramInterval(timeGroup.getInterval().toString())); + if (DateHistogramAggregationBuilder.DATE_FIELD_UNITS.containsKey(intervalString)) { + builder.calendarInterval(new DateHistogramInterval(intervalString)); } else { - builder.dateHistogramInterval(new DateHistogramInterval(timeGroup.getInterval().toString())); + builder.fixedInterval(new DateHistogramInterval(intervalString)); +// builder.dateHistogramInterval(new DateHistogramInterval(intervalString)); } } else { - builder.dateHistogramInterval(new DateHistogramInterval(timeGroup.getInterval().toString())); + builder.dateHistogramInterval(new DateHistogramInterval(intervalString)); } } diff --git a/jetlinks-components/gateway-component/pom.xml b/jetlinks-components/gateway-component/pom.xml index 0da29ef3..225f5672 100644 --- a/jetlinks-components/gateway-component/pom.xml +++ b/jetlinks-components/gateway-component/pom.xml @@ -5,7 +5,7 @@ jetlinks-components org.jetlinks.community - 1.8.0-SNAPSHOT + 1.8.0 4.0.0 diff --git a/jetlinks-components/io-component/pom.xml b/jetlinks-components/io-component/pom.xml index 47247004..0405fc03 100644 --- a/jetlinks-components/io-component/pom.xml +++ b/jetlinks-components/io-component/pom.xml @@ -5,7 +5,7 @@ jetlinks-components org.jetlinks.community - 1.8.0-SNAPSHOT + 1.8.0 4.0.0 diff --git a/jetlinks-components/logging-component/pom.xml b/jetlinks-components/logging-component/pom.xml index 1d2eca47..efeb0d32 100644 --- a/jetlinks-components/logging-component/pom.xml +++ b/jetlinks-components/logging-component/pom.xml @@ -5,7 +5,7 @@ jetlinks-components org.jetlinks.community - 1.8.0-SNAPSHOT + 1.8.0 ../pom.xml 4.0.0 diff --git a/jetlinks-components/network-component/mqtt-component/pom.xml b/jetlinks-components/network-component/mqtt-component/pom.xml index d69575c6..cb0db429 100644 --- a/jetlinks-components/network-component/mqtt-component/pom.xml +++ b/jetlinks-components/network-component/mqtt-component/pom.xml @@ -5,7 +5,7 @@ network-component org.jetlinks.community - 1.8.0-SNAPSHOT + 1.8.0 ../pom.xml 4.0.0 diff --git a/jetlinks-components/network-component/network-core/pom.xml b/jetlinks-components/network-component/network-core/pom.xml index 2472d69f..77b3ae6e 100644 --- a/jetlinks-components/network-component/network-core/pom.xml +++ b/jetlinks-components/network-component/network-core/pom.xml @@ -5,7 +5,7 @@ network-component org.jetlinks.community - 1.8.0-SNAPSHOT + 1.8.0 ../pom.xml 4.0.0 diff --git a/jetlinks-components/network-component/pom.xml b/jetlinks-components/network-component/pom.xml index 61df5c8b..259295f3 100644 --- a/jetlinks-components/network-component/pom.xml +++ b/jetlinks-components/network-component/pom.xml @@ -5,7 +5,7 @@ jetlinks-components org.jetlinks.community - 1.8.0-SNAPSHOT + 1.8.0 ../pom.xml pom diff --git a/jetlinks-components/network-component/tcp-component/pom.xml b/jetlinks-components/network-component/tcp-component/pom.xml index c258e82d..58c4005e 100644 --- a/jetlinks-components/network-component/tcp-component/pom.xml +++ b/jetlinks-components/network-component/tcp-component/pom.xml @@ -5,7 +5,7 @@ network-component org.jetlinks.community - 1.8.0-SNAPSHOT + 1.8.0 ../pom.xml 4.0.0 diff --git a/jetlinks-components/notify-component/notify-core/pom.xml b/jetlinks-components/notify-component/notify-core/pom.xml index d717180f..218f5ef9 100644 --- a/jetlinks-components/notify-component/notify-core/pom.xml +++ b/jetlinks-components/notify-component/notify-core/pom.xml @@ -5,7 +5,7 @@ notify-component org.jetlinks.community - 1.8.0-SNAPSHOT + 1.8.0 4.0.0 diff --git a/jetlinks-components/notify-component/notify-dingtalk/pom.xml b/jetlinks-components/notify-component/notify-dingtalk/pom.xml index be1ab1ea..edbda015 100644 --- a/jetlinks-components/notify-component/notify-dingtalk/pom.xml +++ b/jetlinks-components/notify-component/notify-dingtalk/pom.xml @@ -5,7 +5,7 @@ notify-component org.jetlinks.community - 1.8.0-SNAPSHOT + 1.8.0 4.0.0 diff --git a/jetlinks-components/notify-component/notify-email/pom.xml b/jetlinks-components/notify-component/notify-email/pom.xml index 2f64407d..59141e38 100644 --- a/jetlinks-components/notify-component/notify-email/pom.xml +++ b/jetlinks-components/notify-component/notify-email/pom.xml @@ -5,7 +5,7 @@ notify-component org.jetlinks.community - 1.8.0-SNAPSHOT + 1.8.0 4.0.0 diff --git a/jetlinks-components/notify-component/notify-sms/pom.xml b/jetlinks-components/notify-component/notify-sms/pom.xml index c963c724..86a8f4d9 100644 --- a/jetlinks-components/notify-component/notify-sms/pom.xml +++ b/jetlinks-components/notify-component/notify-sms/pom.xml @@ -5,7 +5,7 @@ notify-component org.jetlinks.community - 1.8.0-SNAPSHOT + 1.8.0 4.0.0 diff --git a/jetlinks-components/notify-component/notify-voice/pom.xml b/jetlinks-components/notify-component/notify-voice/pom.xml index f64e1a4f..818baae1 100644 --- a/jetlinks-components/notify-component/notify-voice/pom.xml +++ b/jetlinks-components/notify-component/notify-voice/pom.xml @@ -5,7 +5,7 @@ notify-component org.jetlinks.community - 1.8.0-SNAPSHOT + 1.8.0 ../pom.xml 4.0.0 diff --git a/jetlinks-components/notify-component/notify-wechat/pom.xml b/jetlinks-components/notify-component/notify-wechat/pom.xml index 9f35e86e..3bac8ab5 100644 --- a/jetlinks-components/notify-component/notify-wechat/pom.xml +++ b/jetlinks-components/notify-component/notify-wechat/pom.xml @@ -5,7 +5,7 @@ notify-component org.jetlinks.community - 1.8.0-SNAPSHOT + 1.8.0 4.0.0 diff --git a/jetlinks-components/notify-component/pom.xml b/jetlinks-components/notify-component/pom.xml index 6753de95..0946e687 100644 --- a/jetlinks-components/notify-component/pom.xml +++ b/jetlinks-components/notify-component/pom.xml @@ -5,7 +5,7 @@ jetlinks-components org.jetlinks.community - 1.8.0-SNAPSHOT + 1.8.0 ../pom.xml 4.0.0 diff --git a/jetlinks-components/pom.xml b/jetlinks-components/pom.xml index a0a48689..5371be8e 100644 --- a/jetlinks-components/pom.xml +++ b/jetlinks-components/pom.xml @@ -5,7 +5,7 @@ jetlinks-community org.jetlinks.community - 1.8.0-SNAPSHOT + 1.8.0 ../pom.xml 4.0.0 diff --git a/jetlinks-components/rule-engine-component/pom.xml b/jetlinks-components/rule-engine-component/pom.xml index 5f3a3b22..c037ecdb 100644 --- a/jetlinks-components/rule-engine-component/pom.xml +++ b/jetlinks-components/rule-engine-component/pom.xml @@ -5,7 +5,7 @@ jetlinks-components org.jetlinks.community - 1.8.0-SNAPSHOT + 1.8.0 ../pom.xml 4.0.0 diff --git a/jetlinks-components/timeseries-component/pom.xml b/jetlinks-components/timeseries-component/pom.xml index ed96b4b7..844ea01c 100644 --- a/jetlinks-components/timeseries-component/pom.xml +++ b/jetlinks-components/timeseries-component/pom.xml @@ -5,7 +5,7 @@ jetlinks-components org.jetlinks.community - 1.8.0-SNAPSHOT + 1.8.0 ../pom.xml 4.0.0 diff --git a/jetlinks-manager/authentication-manager/pom.xml b/jetlinks-manager/authentication-manager/pom.xml index b2407591..70251614 100644 --- a/jetlinks-manager/authentication-manager/pom.xml +++ b/jetlinks-manager/authentication-manager/pom.xml @@ -7,7 +7,7 @@ org.jetlinks.community jetlinks-manager - 1.8.0-SNAPSHOT + 1.8.0 ../pom.xml authentication-manager diff --git a/jetlinks-manager/device-manager/pom.xml b/jetlinks-manager/device-manager/pom.xml index 83143dee..bddfaa76 100644 --- a/jetlinks-manager/device-manager/pom.xml +++ b/jetlinks-manager/device-manager/pom.xml @@ -7,7 +7,7 @@ org.jetlinks.community jetlinks-manager - 1.8.0-SNAPSHOT + 1.8.0 ../pom.xml device-manager diff --git a/jetlinks-manager/device-manager/src/main/java/org/jetlinks/community/device/entity/DeviceInstanceEntity.java b/jetlinks-manager/device-manager/src/main/java/org/jetlinks/community/device/entity/DeviceInstanceEntity.java index 6f38ce14..d64d6672 100644 --- a/jetlinks-manager/device-manager/src/main/java/org/jetlinks/community/device/entity/DeviceInstanceEntity.java +++ b/jetlinks-manager/device-manager/src/main/java/org/jetlinks/community/device/entity/DeviceInstanceEntity.java @@ -76,7 +76,7 @@ public class DeviceInstanceEntity extends GenericEntity implements Recor @Schema(description = "派生物模型(预留)") private String deriveMetadata; - @Column(name = "state") + @Column(name = "state",length = 16) @EnumCodec @ColumnType(javaType = String.class) @DefaultValue("notActive") diff --git a/jetlinks-manager/device-manager/src/main/java/org/jetlinks/community/device/entity/DeviceTagEntity.java b/jetlinks-manager/device-manager/src/main/java/org/jetlinks/community/device/entity/DeviceTagEntity.java index ed9f7720..ca2f8b88 100644 --- a/jetlinks-manager/device-manager/src/main/java/org/jetlinks/community/device/entity/DeviceTagEntity.java +++ b/jetlinks-manager/device-manager/src/main/java/org/jetlinks/community/device/entity/DeviceTagEntity.java @@ -11,6 +11,8 @@ import org.hswebframework.web.api.crud.entity.GenericEntity; import org.hswebframework.web.crud.annotation.EnableEntityEvent; import org.hswebframework.web.crud.generator.Generators; import org.hswebframework.web.validator.CreateGroup; +import org.jetlinks.core.metadata.Converter; +import org.jetlinks.core.metadata.DataType; import org.jetlinks.core.metadata.PropertyMetadata; import javax.persistence.Column; @@ -73,6 +75,21 @@ public class DeviceTagEntity extends GenericEntity { return entity; } + public static DeviceTagEntity of(PropertyMetadata property, Object value) { + DeviceTagEntity tag = of(property); + + DataType type = property.getValueType(); + if (type instanceof Converter) { + Object newValue = ((Converter) type).convert(value); + if (newValue != null) { + value = newValue; + } + } + tag.setValue(String.valueOf(value)); + return tag; + } + + public static String createTagId(String deviceId, String key) { return DigestUtils.md5Hex(deviceId + ":" + key); } diff --git a/jetlinks-manager/device-manager/src/main/java/org/jetlinks/community/device/response/DeviceDetail.java b/jetlinks-manager/device-manager/src/main/java/org/jetlinks/community/device/response/DeviceDetail.java index 690321b5..3ac70652 100644 --- a/jetlinks-manager/device-manager/src/main/java/org/jetlinks/community/device/response/DeviceDetail.java +++ b/jetlinks-manager/device-manager/src/main/java/org/jetlinks/community/device/response/DeviceDetail.java @@ -5,6 +5,7 @@ import lombok.Getter; import lombok.Setter; import org.apache.commons.collections4.MapUtils; import org.jetlinks.community.device.enums.DeviceType; +import org.jetlinks.core.Values; import org.jetlinks.core.device.DeviceOperator; import org.jetlinks.community.device.entity.DeviceInstanceEntity; import org.jetlinks.community.device.entity.DeviceProductEntity; @@ -116,6 +117,9 @@ public class DeviceDetail { @Schema(description = "标签信息") private List tags = new ArrayList<>(); + @Schema(description = "设备描述") + private String description; + public DeviceDetail notActive() { state = DeviceState.notActive; @@ -138,6 +142,7 @@ public class DeviceDetail { .stream() .map(ConfigPropertyMetadata::getProperty) .collect(Collectors.toList())) + .defaultIfEmpty(Values.of(Collections.emptyMap())) ) .doOnNext(tp -> { setOnlineTime(tp.getT2()); @@ -205,6 +210,7 @@ public class DeviceDetail { setState(device.getState()); setOrgId(device.getOrgId()); setParentId(device.getParentId()); + setDescription(device.getDescribe()); Optional.ofNullable(device.getRegistryTime()) .ifPresent(this::setRegisterTime); diff --git a/jetlinks-manager/device-manager/src/main/java/org/jetlinks/community/device/service/DeviceMessageBusinessHandler.java b/jetlinks-manager/device-manager/src/main/java/org/jetlinks/community/device/service/DeviceMessageBusinessHandler.java index 2b6dee04..a5fe8621 100644 --- a/jetlinks-manager/device-manager/src/main/java/org/jetlinks/community/device/service/DeviceMessageBusinessHandler.java +++ b/jetlinks-manager/device-manager/src/main/java/org/jetlinks/community/device/service/DeviceMessageBusinessHandler.java @@ -163,7 +163,7 @@ public class DeviceMessageBusinessHandler { .map(e -> { DeviceTagEntity tagEntity = metadata .getTag(e.getKey()) - .map(DeviceTagEntity::of) + .map(tagMeta -> DeviceTagEntity.of(tagMeta, e.getValue())) .orElseGet(() -> { DeviceTagEntity entity = new DeviceTagEntity(); entity.setKey(e.getKey()); @@ -171,9 +171,9 @@ public class DeviceMessageBusinessHandler { entity.setName(e.getKey()); entity.setCreateTime(new Date()); entity.setDescription("设备上报"); + entity.setValue(String.valueOf(e.getValue())); return entity; }); - tagEntity.setValue(String.valueOf(e.getValue())); tagEntity.setDeviceId(deviceId); tagEntity.setId(DeviceTagEntity.createTagId(deviceId, tagEntity.getKey())); return tagEntity; diff --git a/jetlinks-manager/device-manager/src/main/java/org/jetlinks/community/device/web/DeviceInstanceController.java b/jetlinks-manager/device-manager/src/main/java/org/jetlinks/community/device/web/DeviceInstanceController.java index 3e87f53a..f1f3c5b0 100644 --- a/jetlinks-manager/device-manager/src/main/java/org/jetlinks/community/device/web/DeviceInstanceController.java +++ b/jetlinks-manager/device-manager/src/main/java/org/jetlinks/community/device/web/DeviceInstanceController.java @@ -19,7 +19,9 @@ import org.hswebframework.web.authorization.annotation.*; import org.hswebframework.web.bean.FastBeanCopier; import org.hswebframework.web.crud.web.reactive.ReactiveServiceCrudController; import org.hswebframework.web.exception.BusinessException; +import org.hswebframework.web.exception.NotFoundException; import org.hswebframework.web.exception.ValidationException; +import org.hswebframework.web.id.IDGenerator; import org.jetlinks.community.device.entity.*; import org.jetlinks.community.device.enums.DeviceState; import org.jetlinks.community.device.response.DeviceDeployResult; @@ -37,17 +39,20 @@ import org.jetlinks.community.io.utils.FileUtils; import org.jetlinks.community.timeseries.query.AggregationData; import org.jetlinks.core.ProtocolSupport; import org.jetlinks.core.Values; -import org.jetlinks.core.device.DeviceConfigKey; -import org.jetlinks.core.device.DeviceOperator; -import org.jetlinks.core.device.DeviceProductOperator; -import org.jetlinks.core.device.DeviceRegistry; +import org.jetlinks.core.device.*; import org.jetlinks.core.device.manager.DeviceBindHolder; import org.jetlinks.core.device.manager.DeviceBindProvider; +import org.jetlinks.core.exception.DeviceOperationException; +import org.jetlinks.core.message.DeviceMessage; +import org.jetlinks.core.message.Message; +import org.jetlinks.core.message.MessageType; +import org.jetlinks.core.message.RepayableDeviceMessage; import org.jetlinks.core.metadata.ConfigMetadata; import org.jetlinks.core.metadata.ConfigPropertyMetadata; import org.jetlinks.core.metadata.DeviceMetadata; import org.springframework.core.io.buffer.DataBufferFactory; import org.springframework.core.io.buffer.DefaultDataBufferFactory; +import org.springframework.data.util.Lazy; import org.springframework.http.HttpHeaders; import org.springframework.http.MediaType; import org.springframework.http.server.reactive.ServerHttpResponse; @@ -64,6 +69,7 @@ import java.io.IOException; import java.net.URLEncoder; import java.nio.charset.StandardCharsets; import java.util.Collections; +import java.util.HashMap; import java.util.List; import java.util.Map; import java.util.function.Function; @@ -630,4 +636,106 @@ public class DeviceInstanceController implements .map(AggregationData::values); } + //发送设备指令 + @PostMapping("/{deviceId:.+}/message") + @SneakyThrows + @QueryAction + @Operation(summary = "发送指令到设备") + @SuppressWarnings("all") + public Flux sendMessage(@PathVariable @Parameter(description = "设备ID") String deviceId, + @RequestBody Mono> properties) { + return properties + .flatMapMany(props -> { + return Mono + .zip( + registry + .getDevice(deviceId) + .map(DeviceOperator::messageSender) + .switchIfEmpty(Mono.error(() -> new NotFoundException("设备不存在或未激活"))), + Mono.justOrEmpty(MessageType.convertMessage(props)) + .cast(DeviceMessage.class) + .switchIfEmpty(Mono.error(() -> new UnsupportedOperationException("不支持的消息格式"))) + ).flatMapMany(tp2 -> { + DeviceMessageSender sender = tp2.getT1(); + DeviceMessage message = tp2.getT2(); + + Map copy = new HashMap<>(); + copy.put("deviceId", deviceId); + if (!StringUtils.hasText(message.getMessageId())) { + copy.put("messageId", IDGenerator.SNOW_FLAKE_STRING.generate()); + } + FastBeanCopier.copy(copy, message); + return sender + .send(message) + .onErrorResume(DeviceOperationException.class, error -> { + if (message instanceof RepayableDeviceMessage) { + return Mono.just( + ((RepayableDeviceMessage) message).newReply().error(error) + ); + } + return Mono.error(error); + }); + }); + }); + } + + //发送设备指令 + @PostMapping("/messages") + @SneakyThrows + @QueryAction + @Operation(summary = "批量发送指令到设备") + @SuppressWarnings("all") + public Flux sendMessage(@RequestParam(required = false) + @Parameter(description = "按查询条件发送指令") String where, + @RequestBody Flux> messages) { + + Lazy> operators = Lazy.of(() -> { + if (StringUtils.isEmpty(where)) { + throw new ValidationException("where", "[where]参数不能为空"); + } + QueryParamEntity entity = new QueryParamEntity(); + entity.setWhere(where); + entity.includes("id"); + return service.query(entity) + .flatMap(device -> registry.getDevice(device.getId())) + .cache(); + }); + return messages + .flatMap(message -> { + DeviceMessage msg = MessageType + .convertMessage(message) + .filter(DeviceMessage.class::isInstance) + .map(DeviceMessage.class::cast) + .orElseThrow(() -> new UnsupportedOperationException("不支持的消息格式:" + message)); + + String deviceId = msg.getDeviceId(); + Flux devices = StringUtils.isEmpty(deviceId) + ? operators.get() + : registry.getDevice(deviceId).flux(); + + return devices + .flatMap(device -> { + Map copy = new HashMap<>(message); + copy.put("deviceId", device.getDeviceId()); + copy.putIfAbsent("messageId", IDGenerator.SNOW_FLAKE_STRING.generate()); + //复制为新的消息,防止冲突 + DeviceMessage copiedMessage = MessageType + .convertMessage(copy) + .map(DeviceMessage.class::cast) + .orElseThrow(() -> new UnsupportedOperationException("不支持的消息格式")); + return device + .messageSender() + .send(copiedMessage) + .onErrorResume(Exception.class, error -> { + if (copiedMessage instanceof RepayableDeviceMessage) { + return Mono.just( + ((RepayableDeviceMessage) copiedMessage).newReply().error(error) + ); + } + return Mono.error(error); + }); + }); + }); + } + } diff --git a/jetlinks-manager/device-manager/src/main/java/org/jetlinks/community/device/web/ProtocolSupportController.java b/jetlinks-manager/device-manager/src/main/java/org/jetlinks/community/device/web/ProtocolSupportController.java index 236a836f..2caa5725 100644 --- a/jetlinks-manager/device-manager/src/main/java/org/jetlinks/community/device/web/ProtocolSupportController.java +++ b/jetlinks-manager/device-manager/src/main/java/org/jetlinks/community/device/web/ProtocolSupportController.java @@ -102,6 +102,20 @@ public class ProtocolSupportController .flatMap(support -> support.getConfigMetadata(transport)); } + @GetMapping("/{id}/{transport}/metadata") + @QueryAction + @Authorize(merge = false) + @Operation(summary = "获取协议设置的默认物模型") + public Mono getDefaultMetadata(@PathVariable @Parameter(description = "协议ID") String id, + @PathVariable @Parameter(description = "传输协议") DefaultTransport transport) { + return protocolSupports + .getProtocol(id) + .flatMap(support ->support + .getDefaultMetadata(transport) + .flatMap(metadata-> support.getMetadataCodec().encode(metadata)) + ).defaultIfEmpty("{}"); + } + @GetMapping("/{id}/transports") @Authorize(merge = false) @Operation(summary = "获取协议支持的传输协议") diff --git a/jetlinks-manager/logging-manager/pom.xml b/jetlinks-manager/logging-manager/pom.xml index 78f97899..10ca5aa5 100644 --- a/jetlinks-manager/logging-manager/pom.xml +++ b/jetlinks-manager/logging-manager/pom.xml @@ -7,7 +7,7 @@ org.jetlinks.community jetlinks-manager - 1.8.0-SNAPSHOT + 1.8.0 logging-manager diff --git a/jetlinks-manager/network-manager/pom.xml b/jetlinks-manager/network-manager/pom.xml index 1aedd03a..0708c373 100644 --- a/jetlinks-manager/network-manager/pom.xml +++ b/jetlinks-manager/network-manager/pom.xml @@ -7,7 +7,7 @@ org.jetlinks.community jetlinks-manager - 1.8.0-SNAPSHOT + 1.8.0 ../pom.xml network-manager diff --git a/jetlinks-manager/notify-manager/pom.xml b/jetlinks-manager/notify-manager/pom.xml index e4f23150..f7db81e4 100644 --- a/jetlinks-manager/notify-manager/pom.xml +++ b/jetlinks-manager/notify-manager/pom.xml @@ -7,7 +7,7 @@ org.jetlinks.community jetlinks-manager - 1.8.0-SNAPSHOT + 1.8.0 ../pom.xml notify-manager diff --git a/jetlinks-manager/pom.xml b/jetlinks-manager/pom.xml index 32ac7452..180cad40 100644 --- a/jetlinks-manager/pom.xml +++ b/jetlinks-manager/pom.xml @@ -5,7 +5,7 @@ jetlinks-community org.jetlinks.community - 1.8.0-SNAPSHOT + 1.8.0 pom 4.0.0 diff --git a/jetlinks-manager/rule-engine-manager/pom.xml b/jetlinks-manager/rule-engine-manager/pom.xml index 92664c24..f3fabaa7 100644 --- a/jetlinks-manager/rule-engine-manager/pom.xml +++ b/jetlinks-manager/rule-engine-manager/pom.xml @@ -7,7 +7,7 @@ org.jetlinks.community jetlinks-manager - 1.8.0-SNAPSHOT + 1.8.0 ../pom.xml rule-engine-manager diff --git a/jetlinks-manager/rule-engine-manager/src/main/java/org/jetlinks/community/rule/engine/entity/RuleInstanceEntity.java b/jetlinks-manager/rule-engine-manager/src/main/java/org/jetlinks/community/rule/engine/entity/RuleInstanceEntity.java index 09e7bc6e..ea05a1f1 100644 --- a/jetlinks-manager/rule-engine-manager/src/main/java/org/jetlinks/community/rule/engine/entity/RuleInstanceEntity.java +++ b/jetlinks-manager/rule-engine-manager/src/main/java/org/jetlinks/community/rule/engine/entity/RuleInstanceEntity.java @@ -67,7 +67,7 @@ public class RuleInstanceEntity extends GenericEntity implements RecordC @Schema(description = "创建者ID") private String creatorId; - @Column(name = "state") + @Column(name = "state",length = 16) @EnumCodec @ColumnType(javaType = String.class) @DefaultValue("stopped") diff --git a/jetlinks-manager/visualization-manager/pom.xml b/jetlinks-manager/visualization-manager/pom.xml index a28c043c..0e71e6d4 100644 --- a/jetlinks-manager/visualization-manager/pom.xml +++ b/jetlinks-manager/visualization-manager/pom.xml @@ -7,7 +7,7 @@ org.jetlinks.community jetlinks-manager - 1.8.0-SNAPSHOT + 1.8.0 ../pom.xml visualization-manager diff --git a/jetlinks-standalone/pom.xml b/jetlinks-standalone/pom.xml index cfbae40c..2e6dfbb5 100644 --- a/jetlinks-standalone/pom.xml +++ b/jetlinks-standalone/pom.xml @@ -5,7 +5,7 @@ jetlinks-community org.jetlinks.community - 1.8.0-SNAPSHOT + 1.8.0 ../pom.xml 4.0.0 @@ -49,41 +49,6 @@ - - com.spotify - docker-maven-plugin - 1.2.0 - - ${docker.image.name} - - ${project.version} - - openjdk:8 - / - - Asia/Shanghai - /${project.build.finalName}.jar - - - chmod +x docker-entrypoint.sh - - ["/docker-entrypoint.sh"] - - - / - ${project.basedir} - docker-entrypoint.sh - - - / - ${project.build.directory} - ${project.build.finalName}.jar - - - docker-repo - - - @@ -115,7 +80,6 @@ io.projectreactor.netty reactor-netty - 0.9.10.RELEASE compile diff --git a/jetlinks-standalone/src/main/java/org/jetlinks/community/standalone/configuration/protocol/AutoDownloadJarProtocolSupportLoader.java b/jetlinks-standalone/src/main/java/org/jetlinks/community/standalone/configuration/protocol/AutoDownloadJarProtocolSupportLoader.java index cf331fe9..6f3958a2 100644 --- a/jetlinks-standalone/src/main/java/org/jetlinks/community/standalone/configuration/protocol/AutoDownloadJarProtocolSupportLoader.java +++ b/jetlinks-standalone/src/main/java/org/jetlinks/community/standalone/configuration/protocol/AutoDownloadJarProtocolSupportLoader.java @@ -96,24 +96,10 @@ public class AutoDownloadJarProtocolSupportLoader extends JarProtocolSupportLoad .retrieve() .bodyToFlux(DataBuffer.class) .as(dataStream -> { - Path filePath = file.toPath(); - log.debug("write protocol file {} to {}", location, file.getAbsolutePath()); - try { - @SuppressWarnings("all") - AsynchronousFileChannel asynchronousFileChannel = AsynchronousFileChannel.open(filePath, CREATE,WRITE); - return DataBufferUtils - .write(dataStream, asynchronousFileChannel) - .doOnNext(DataBufferUtils.releaseConsumer()) - .doAfterTerminate(() -> { - try { - asynchronousFileChannel.close(); - } catch (IOException ignored) { - } - }) - .then(Mono.just(file.getAbsolutePath())); - } catch (Exception e) { - throw new RuntimeException(e); - } + log.debug("download protocol file {} to {}", location, file.getAbsolutePath()); + return DataBufferUtils + .write(dataStream, file.toPath(), CREATE, WRITE) + .thenReturn(file.getAbsolutePath()); }) .subscribeOn(Schedulers.elastic()) .doOnNext(path -> config.put("location", path)) diff --git a/pom.xml b/pom.xml index 425ae6d8..c9627e5b 100644 --- a/pom.xml +++ b/pom.xml @@ -6,7 +6,7 @@ org.jetlinks.community jetlinks-community - 1.8.0-SNAPSHOT + 1.8.0 jetlinks-components jetlinks-manager @@ -16,13 +16,13 @@ UTF-8 zh_CN - 2.3.4.RELEASE + 2.3.8.RELEASE 1.8 ${java.version} - 4.0.9-SNAPSHOT - 4.0.9-SNAPSHOT + 4.0.9 + 4.0.9 3.0.2 - 1.1.5-SNAPSHOT + 1.1.5 Arabba-SR7 3.8.5 4.1.51.Final