Here are the examples of the java api org.springframework.messaging.simp.SimpMessagingTemplate taken from open source projects. By voting up you can indicate which examples are most useful and appropriate.
192 Examples
19
View Source File : NotificationService.java
License : Apache License 2.0
Project Creator : zeebe-io
License : Apache License 2.0
Project Creator : zeebe-io
@Controller
public clreplaced NotificationService {
@Autowired
private SimpMessagingTemplate webSocket;
public void sendNewTask() {
final TaskNotification notification = new TaskNotification("new tasks");
webSocket.convertAndSend("/notifications/tasks", notification);
}
public void sendTaskCanceled() {
final TaskNotification notification = new TaskNotification("tasks canceled");
webSocket.convertAndSend("/notifications/tasks", notification);
}
}
19
View Source File : LauncherController.java
License : Apache License 2.0
Project Creator : zebrunner
License : Apache License 2.0
Project Creator : zebrunner
@CrossOrigin
@RequestMapping(path = "api/launchers", produces = MediaType.APPLICATION_JSON_VALUE)
@RestController
@RequiredArgsConstructor
public clreplaced LauncherController extends AbstractController implements LauncherDoreplacedentedController {
private final LauncherService launcherService;
private final Mapper mapper;
private final SimpMessagingTemplate websocketTemplate;
@PreAuthorize("hasPermission('MODIFY_LAUNCHERS')")
@PostMapping()
@Override
public LauncherDTO createLauncher(@RequestBody @Valid LauncherDTO launcherDTO, @RequestParam(name = "automationServerId") Long automationServerId) {
Launcher launcher = mapper.map(launcherDTO, Launcher.clreplaced);
Long principalId = Long.valueOf(getPrincipalId());
launcher = launcherService.createLauncher(launcher, principalId, automationServerId);
return mapper.map(launcher, LauncherDTO.clreplaced);
}
@PreAuthorize("hasAnyPermission('MODIFY_LAUNCHERS', 'VIEW_LAUNCHERS')")
@GetMapping("/{id}")
@Override
public LauncherDTO getLauncherById(@PathVariable("id") Long id) {
Launcher launcher = launcherService.getLauncherById(id);
return mapper.map(launcher, LauncherDTO.clreplaced);
}
@PreAuthorize("hasAnyPermission('MODIFY_LAUNCHERS', 'VIEW_LAUNCHERS')")
@GetMapping()
@Override
public List<LauncherDTO> getAllLaunchers() {
List<Launcher> launchers = launcherService.getAllLaunchers(Long.valueOf(getPrincipalId()));
return launchers.stream().map(launcher -> mapper.map(launcher, LauncherDTO.clreplaced)).collect(Collectors.toList());
}
@PreAuthorize("hasPermission('MODIFY_LAUNCHERS')")
@PutMapping()
@Override
public LauncherDTO updateLauncher(@RequestBody @Valid LauncherDTO launcherDTO) {
Launcher launcher = mapper.map(launcherDTO, Launcher.clreplaced);
launcher = launcherService.updateLauncher(launcher);
return mapper.map(launcher, LauncherDTO.clreplaced);
}
@PreAuthorize("hasPermission('MODIFY_LAUNCHERS')")
@DeleteMapping("/{id}")
@Override
public void deleteLauncherById(@PathVariable("id") Long id) {
launcherService.deleteLauncherById(id);
}
@PreAuthorize("hasAnyPermission('MODIFY_LAUNCHERS', 'VIEW_LAUNCHERS')")
@PostMapping("/build")
@Override
public void build(@RequestBody @Valid LauncherDTO launcherDTO, @RequestParam(name = "providerId", required = false) Long providerId) throws IOException {
Launcher launcher = mapper.map(launcherDTO, Launcher.clreplaced);
String ciRunId = launcherService.buildLauncherJob(launcher, Long.valueOf(getPrincipalId()), providerId);
websocketTemplate.convertAndSend(getLauncherRunsWebsocketPath(), new LauncherRunPush(launcher, ciRunId));
}
@GetMapping("/hooks/{ref}")
@Override
public String buildByWebHook(@PathVariable("ref") String ref, @RequestParam(value = "callbackUrl", required = false) String callbackUrl) throws IOException {
return launcherService.buildLauncherJobByPresetRef(ref, callbackUrl, Long.valueOf(getPrincipalId()));
}
@PreAuthorize("hasAnyPermission('MODIFY_LAUNCHERS', 'VIEW_LAUNCHERS')")
@GetMapping("/build/number")
@Override
public Integer getBuildNumber(@RequestParam("queueItemUrl") String queueItemUrl, @RequestParam(name = "automationServerId") Long automationServerId) {
return launcherService.getBuildNumber(queueItemUrl, automationServerId);
}
@PreAuthorize("hasPermission('MODIFY_LAUNCHERS')")
@PostMapping("/scanner")
@Override
public JobResult runScanner(@RequestBody @Valid LauncherScannerType launcherScannerType, @RequestParam(name = "automationServerId") Long automationServerId) {
return launcherService.buildScannerJob(Long.valueOf(getPrincipalId()), launcherScannerType.getBranch(), launcherScannerType.getScmAccountId(), launcherScannerType.isRescan(), automationServerId);
}
@PreAuthorize("hasPermission('MODIFY_LAUNCHERS')")
@DeleteMapping("/scanner/{buildNumber}")
@Override
public void cancelScanner(@PathVariable("buildNumber") int buildNumber, @RequestParam("scmAccountId") Long scmAccountId, @RequestParam("rescan") boolean rescan, @RequestParam(name = "automationServerId") Long automationServerId) {
launcherService.abortScannerJob(scmAccountId, buildNumber, rescan, automationServerId);
}
@PreAuthorize("hasPermission('MODIFY_LAUNCHERS')")
@GetMapping("/scanner/{buildNumber}/status")
public boolean getScannerStatus(@PathVariable("buildNumber") int buildNumber, @RequestParam("scmAccountId") Long scmAccountId, @RequestParam("rescan") boolean rescan, @RequestParam(name = "automationServerId") Long automationServerId) {
return launcherService.isScannerJobInProgress(scmAccountId, buildNumber, rescan, automationServerId);
}
@PreAuthorize("hasPermission('MODIFY_LAUNCHERS')")
@PostMapping("/create")
@Override
public List<LauncherDTO> scanLaunchersFromJenkins(@RequestBody @Valid JenkinsJobsScanResultDTO jenkinsJobsScanResultDTO) {
Long principalId = Long.valueOf(getPrincipalId());
List<JenkinsJob> jenkinsJobs = jenkinsJobsScanResultDTO.getJenkinsJobs().stream().map(jenkinsLauncher -> mapper.map(jenkinsLauncher, JenkinsJob.clreplaced)).collect(Collectors.toList());
List<Launcher> launchers = launcherService.mergeLaunchersWithJenkinsJobs(jenkinsJobs, jenkinsJobsScanResultDTO.getRepo(), jenkinsJobsScanResultDTO.isSuccess(), principalId);
List<LauncherDTO> launcherDTOS = launchers.stream().map(launcher -> mapper.map(launcher, LauncherDTO.clreplaced)).collect(Collectors.toList());
websocketTemplate.convertAndSend(getLaunchersWebsocketPath(), new LauncherPush(launcherDTOS, jenkinsJobsScanResultDTO.getUserId(), jenkinsJobsScanResultDTO.isSuccess()));
return launcherDTOS;
}
@PreAuthorize("hasAnyPermission('MODIFY_LAUNCHERS', 'VIEW_LAUNCHERS')")
@PatchMapping("/{id}")
@Override
public UserLauncherPreference patchUserLauncherPreference(@RequestBody @Valid PatchDescriptor descriptor, @PathVariable("id") Long id) {
return PatchDecorator.<UserLauncherPreference, PatchOperation>instance().descriptor(descriptor).operation(PatchOperation.clreplaced).<Boolean>when(PatchOperation.SAVE_FAVORITE).withParameter(Boolean::valueOf).then(favorite -> launcherService.markLauncherAsFavorite(id, Long.valueOf(getPrincipalId()), favorite)).after().decorate();
}
enum PatchOperation {
SAVE_FAVORITE
}
}
19
View Source File : OrderCompleteUpdaterRestApi.java
License : MIT License
Project Creator : youhusky
License : MIT License
Project Creator : youhusky
@RestController
@RequestMapping("/api")
@Slf4j
public clreplaced OrderCompleteUpdaterRestApi {
@Autowired
private SimpMessagingTemplate template;
@RequestMapping(value = "/orders", method = RequestMethod.POST)
public void orderComplete(@RequestBody Order order) {
log.info("Receive order = " + order.toString());
if (order.getUserInfo().getId() == null) {
order.getUserInfo().setId("");
}
if (order.getPaymentId() == null) {
order.setPaymentId("");
}
if (order.getSpecialNote() == null) {
order.setSpecialNote("");
}
template.convertAndSend("/topic/orders", order);
}
@RequestMapping(value = "/errors", method = RequestMethod.POST)
public void orderComplete(@RequestBody String errorMessage) {
log.info("Receive error = " + errorMessage);
template.convertAndSend("/topic/orders", errorMessage);
}
}
19
View Source File : WsController.java
License : MIT License
Project Creator : yidao620c
License : MIT License
Project Creator : yidao620c
/**
* WsController
*
* @author XiongNeng
* @version 1.0
* @since 2018/2/28
*/
@Controller
public clreplaced WsController {
private final SimpMessagingTemplate messagingTemplate;
@Autowired
public WsController(SimpMessagingTemplate messagingTemplate) {
this.messagingTemplate = messagingTemplate;
}
@MessageMapping("/welcome")
@SendTo("/topic/say")
public ResponseMessage say(RequestMessage message) {
System.out.println(message.getName());
return new ResponseMessage("welcome," + message.getName() + " !");
}
/**
* 定时推送消息
*/
@Scheduled(fixedRate = 1000)
public void callback() {
// 发现消息
DateFormat df = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
messagingTemplate.convertAndSend("/topic/callback", "定时推送消息时间: " + df.format(new Date()));
}
}
19
View Source File : ExchangePushJob.java
License : Apache License 2.0
Project Creator : xunibidev
License : Apache License 2.0
Project Creator : xunibidev
@Slf4j
@Component
public clreplaced ExchangePushJob {
@Autowired
private SimpMessagingTemplate messagingTemplate;
@Autowired
private NettyHandler nettyHandler;
private Map<String, List<ExchangeTrade>> tradesQueue = new HashMap<>();
private Map<String, List<TradePlate>> plateQueue = new HashMap<>();
private Map<String, List<CoinThumb>> thumbQueue = new HashMap<>();
private Random rand = new Random();
// 最后一次推送的盘口,仅仅是为了虚拟推送二设立的
private Map<String, TradePlate> plateLastBuy = new HashMap<>();
// 最后一次推送的盘口,仅仅是为了虚拟推送二设立的
private Map<String, TradePlate> plateLastSell = new HashMap<>();
public void addTrades(String symbol, List<ExchangeTrade> trades) {
List<ExchangeTrade> list = tradesQueue.get(symbol);
if (list == null) {
list = new ArrayList<>();
tradesQueue.put(symbol, list);
}
synchronized (list) {
list.addAll(trades);
}
}
public void addPlates(String symbol, TradePlate plate) {
List<TradePlate> list = plateQueue.get(symbol);
if (list == null) {
list = new ArrayList<>();
plateQueue.put(symbol, list);
}
synchronized (list) {
list.add(plate);
}
if (plate.getDirection() == ExchangeOrderDirection.BUY) {
// 更新最新盘口
synchronized (plateLastBuy) {
plateLastBuy.put(symbol, plate);
}
}
if (plate.getDirection() == ExchangeOrderDirection.SELL) {
// 更新最新盘口
synchronized (plateLastSell) {
plateLastSell.put(symbol, plate);
}
}
}
public void addThumb(String symbol, CoinThumb thumb) {
List<CoinThumb> list = thumbQueue.get(symbol);
if (list == null) {
list = new ArrayList<>();
thumbQueue.put(symbol, list);
}
synchronized (list) {
list.add(thumb);
}
}
@Scheduled(fixedRate = 300)
public void pushTrade() {
Iterator<Map.Entry<String, List<ExchangeTrade>>> entryIterator = tradesQueue.entrySet().iterator();
while (entryIterator.hasNext()) {
Map.Entry<String, List<ExchangeTrade>> entry = entryIterator.next();
String symbol = entry.getKey();
List<ExchangeTrade> trades = entry.getValue();
if (trades.size() > 0) {
synchronized (trades) {
messagingTemplate.convertAndSend("/topic/market/trade/" + symbol, trades);
trades.clear();
}
}
}
}
@Scheduled(fixedDelay = 500)
public void pushPlate() {
Iterator<Map.Entry<String, List<TradePlate>>> entryIterator = plateQueue.entrySet().iterator();
while (entryIterator.hasNext()) {
Map.Entry<String, List<TradePlate>> entry = entryIterator.next();
String symbol = entry.getKey();
List<TradePlate> plates = entry.getValue();
if (plates.size() > 0) {
boolean hasPushAskPlate = false;
boolean hasPushBidPlate = false;
synchronized (plates) {
for (TradePlate plate : plates) {
if (plate.getDirection() == ExchangeOrderDirection.BUY && !hasPushBidPlate) {
hasPushBidPlate = true;
} else if (plate.getDirection() == ExchangeOrderDirection.SELL && !hasPushAskPlate) {
hasPushAskPlate = true;
} else {
continue;
}
// websocket推送盘口信息
messagingTemplate.convertAndSend("/topic/market/trade-plate/" + symbol, plate.toJSON(24));
// websocket推送深度信息
messagingTemplate.convertAndSend("/topic/market/trade-depth/" + symbol, plate.toJSON(50));
// netty推送
nettyHandler.handlePlate(symbol, plate);
}
plates.clear();
}
} else {
// 不管盘口有没有变化,都推送一下数据,显得盘口交易很活跃的样子(这里获取到的盘口有可能是买盘,也可能是卖盘)
TradePlate plateBuy = plateLastBuy.get(symbol);
TradePlate plateSell = plateLastSell.get(symbol);
if (plateBuy != null) {
// 随机修改盘口数据,然后推送
List<TradePlateItem> list = plateBuy.gereplacedems();
if (list.size() > 9) {
// 只要大于随机数的种子就行,这里的4是随意设置的
int randInt = rand.nextInt(9);
// 随机挑选一个,让盘口订单数量+50%
list.get(randInt).setAmount(list.get(randInt).getAmount().multiply(BigDecimal.valueOf(0.5)));
if (randInt > 0 && randInt < list.size() - 1) {
// 如果在中间,就可以变动价格
// 价格取前后价格居中的价格
list.get(randInt).setPrice(list.get(randInt - 1).getPrice().add(list.get(randInt + 1).getPrice()).divide(BigDecimal.valueOf(2), 8, RoundingMode.HALF_DOWN));
}
// websocket推送盘口信息
messagingTemplate.convertAndSend("/topic/market/trade-plate/" + symbol, plateBuy.toJSON(24));
// websocket推送深度信息
messagingTemplate.convertAndSend("/topic/market/trade-depth/" + symbol, plateBuy.toJSON(50));
// netty推送
nettyHandler.handlePlate(symbol, plateBuy);
}
}
if (plateSell != null) {
// 随机修改盘口数据,然后推送
List<TradePlateItem> list = plateSell.gereplacedems();
if (list.size() > 9) {
// 只要大于随机数的种子就行,这里的4是随意设置的
int randInt = rand.nextInt(9);
// 随机挑选一个,让盘口订单数量+50%
list.get(randInt).setAmount(list.get(randInt).getAmount().multiply(BigDecimal.valueOf(0.5)));
if (randInt > 0 && randInt < list.size() - 1) {
// 如果在中间,就可以变动价格
// 价格取前后价格居中的价格
list.get(randInt).setPrice(list.get(randInt - 1).getPrice().add(list.get(randInt + 1).getPrice()).divide(BigDecimal.valueOf(2), 8, RoundingMode.HALF_DOWN));
}
// websocket推送盘口信息
messagingTemplate.convertAndSend("/topic/market/trade-plate/" + symbol, plateSell.toJSON(24));
// websocket推送深度信息
messagingTemplate.convertAndSend("/topic/market/trade-depth/" + symbol, plateSell.toJSON(50));
// netty推送
nettyHandler.handlePlate(symbol, plateSell);
}
}
}
}
}
@Scheduled(fixedRate = 300)
public void pushThumb() {
Iterator<Map.Entry<String, List<CoinThumb>>> entryIterator = thumbQueue.entrySet().iterator();
log.info("thumbQueue::::" + JSON.toJSONString(thumbQueue));
while (entryIterator.hasNext()) {
Map.Entry<String, List<CoinThumb>> entry = entryIterator.next();
String symbol = entry.getKey();
List<CoinThumb> thumbs = entry.getValue();
if (thumbs.size() > 0) {
synchronized (thumbs) {
messagingTemplate.convertAndSend("/topic/market/thumb", thumbs.get(thumbs.size() - 1));
thumbs.clear();
}
}
}
}
}
19
View Source File : WebsocketMarketHandler.java
License : Apache License 2.0
Project Creator : xunibidev
License : Apache License 2.0
Project Creator : xunibidev
@Slf4j
@Component
public clreplaced WebsocketMarketHandler implements MarketHandler {
@Autowired
private SimpMessagingTemplate messagingTemplate;
@Autowired
private ExchangePushJob pushJob;
/**
* 推送币种简化信息
* @param symbol
* @param exchangeTrade
* @param thumb
*/
@Override
public void handleTrade(String symbol, ExchangeTrade exchangeTrade, CoinThumb thumb) {
// 推送缩略行情
pushJob.addThumb(symbol, thumb);
}
@Override
public void handleKLine(String symbol, KLine kLine) {
// 推送K线数据
messagingTemplate.convertAndSend("/topic/market/kline/" + symbol, kLine);
}
}
19
View Source File : NettyHandler.java
License : Apache License 2.0
Project Creator : xunibidev
License : Apache License 2.0
Project Creator : xunibidev
/**
* 处理Netty订阅与取消订阅
*/
@HawkBean
public clreplaced NettyHandler {
@Autowired
private HawkPushServiceApi hawkPushService;
@Autowired
private OrderService orderService;
@Autowired
private MessageHandler chatMessageHandler;
@Autowired
private SimpMessagingTemplate messagingTemplate;
/*
@Autowired
private ApnsHandler apnsHandler;
*/
public void subscribeTopic(Channel channel, String topic) {
String userKey = channel.id().asLongText();
NettyCacheUtils.keyChannelCache.put(channel, userKey);
NettyCacheUtils.storeChannel(topic, channel);
if (NettyCacheUtils.userKey.containsKey(userKey)) {
NettyCacheUtils.userKey.get(userKey).add(topic);
} else {
Set<String> userkeys = new HashSet<>();
userkeys.add(topic);
NettyCacheUtils.userKey.put(userKey, userkeys);
}
}
public void unsubscribeTopic(Channel channel, String topic) {
String userKey = channel.id().asLongText();
if (NettyCacheUtils.userKey.containsKey(userKey)) {
NettyCacheUtils.userKey.get(userKey).remove(topic);
}
NettyCacheUtils.keyChannelCache.remove(channel);
}
/*@HawkMethod(cmd = NettyCommand.SUBSCRIBE_CHAT,version = NettyCommand.COMMANDS_VERSION)
public QuoteMessage.SimpleResponse subscribeChat(byte[] body, ChannelHandlerContext ctx){
JSONObject json = JSON.parseObject(new String(body));
System.out.println("订阅:"+json.toJSONString());
QuoteMessage.SimpleResponse.Builder response = QuoteMessage.SimpleResponse.newBuilder();
String orderId = json.getString("orderId");
String uid = json.getString("uid");
if(StringUtils.isEmpty(uid) || StringUtils.isEmpty(orderId)){
response.setCode(500).setMessage("订阅失败,参数错误");
}
else {
String key = orderId + "-" + uid;
subscribeTopic(ctx.channel(),key);
response.setCode(0).setMessage("订阅成功");
}
return response.build();
}*/
@HawkMethod(cmd = NettyCommand.SUBSCRIBE_GROUP_CHAT)
public QuoteMessage.SimpleResponse subscribeGroupChat(byte[] body, ChannelHandlerContext ctx) {
JSONObject json = JSON.parseObject(new String(body));
System.out.println("订阅GroupChat:" + json.toJSONString());
QuoteMessage.SimpleResponse.Builder response = QuoteMessage.SimpleResponse.newBuilder();
String uid = json.getString("uid");
if (StringUtils.isEmpty(uid)) {
response.setCode(500).setMessage("订阅失败,参数错误");
} else {
String key = uid;
subscribeTopic(ctx.channel(), key);
response.setCode(0).setMessage("订阅成功");
}
return response.build();
}
/*@HawkMethod(cmd = NettyCommand.UNSUBSCRIBE_CHAT)
public QuoteMessage.SimpleResponse unsubscribeChat(byte[] body, ChannelHandlerContext ctx){
System.out.println(ctx.channel().id());
JSONObject json = JSON.parseObject(new String(body));
String orderId = json.getString("orderId");
String uid = json.getString("uid");
String key = orderId+"-"+uid;
unsubscribeTopic(ctx.channel(),key);
apnsHandler.removeToken(uid);
QuoteMessage.SimpleResponse.Builder response = QuoteMessage.SimpleResponse.newBuilder();
response.setCode(0).setMessage("取消订阅成功");
return response.build();
}*/
@HawkMethod(cmd = NettyCommand.UNSUBSCRIBE_GROUP_CHAT)
public QuoteMessage.SimpleResponse unsubscribeGroupChat(byte[] body, ChannelHandlerContext ctx) {
JSONObject json = JSON.parseObject(new String(body));
String uid = json.getString("uid");
String key = uid;
unsubscribeTopic(ctx.channel(), key);
// apnsHandler.removeToken(uid);
QuoteMessage.SimpleResponse.Builder response = QuoteMessage.SimpleResponse.newBuilder();
response.setCode(0).setMessage("取消订阅成功");
return response.build();
}
@HawkMethod(cmd = NettyCommand.SUBSCRIBE_APNS)
public QuoteMessage.SimpleResponse subscribeApns(byte[] body, ChannelHandlerContext ctx) {
JSONObject json = JSON.parseObject(new String(body));
System.out.println("订阅APNS推送:" + json.toJSONString());
QuoteMessage.SimpleResponse.Builder response = QuoteMessage.SimpleResponse.newBuilder();
String token = json.getString("token");
String uid = json.getString("uid");
if (StringUtils.isEmpty(uid) || StringUtils.isEmpty(token)) {
response.setCode(500).setMessage("订阅失败,参数错误");
} else {
// apnsHandler.setToken(uid,token);
response.setCode(0).setMessage("订阅成功");
}
return response.build();
}
@HawkMethod(cmd = NettyCommand.UNSUBSCRIBE_APNS)
public QuoteMessage.SimpleResponse unsubscribeApns(byte[] body, ChannelHandlerContext ctx) {
JSONObject json = JSON.parseObject(new String(body));
System.out.println("取消订阅APNS推送:" + json.toJSONString());
String uid = json.getString("uid");
// apnsHandler.removeToken(uid);
QuoteMessage.SimpleResponse.Builder response = QuoteMessage.SimpleResponse.newBuilder();
response.setCode(0).setMessage("取消订阅成功");
return response.build();
}
@HawkMethod(cmd = NettyCommand.SEND_CHAT)
public QuoteMessage.SimpleResponse sendMessage(byte[] body, ChannelHandlerContext ctx) {
System.out.println("发送消息:" + new String(body));
RealTimeChatMessage message = JSON.parseObject(new String(body), RealTimeChatMessage.clreplaced);
handleMessage(message);
QuoteMessage.SimpleResponse.Builder response = QuoteMessage.SimpleResponse.newBuilder();
response.setCode(0).setMessage("发送成功");
return response.build();
}
/**
* 推送消息
* @param key
* @param result
*/
public void push(String key, Object result, short command) {
byte[] body = JSON.toJSONString(result).getBytes();
Set<Channel> channels = NettyCacheUtils.getChannel(key);
if (channels != null && channels.size() > 0) {
System.out.println("下发消息:key=" + key + ",result=" + JSON.toJSONString(result) + ",channel size=" + channels.size());
hawkPushService.pushMsg(channels, command, body);
}
}
public void handleMessage(RealTimeChatMessage message) {
if (message.getMessageType() == MessageTypeEnum.NOTICE) {
Order order = orderService.findOneByOrderId(message.getOrderId());
ConfirmResult result = new ConfirmResult(message.getContent(), order.getStatus().getOrdinal());
result.setUidFrom(message.getUidFrom());
result.setOrderId(message.getOrderId());
result.setNameFrom(message.getNameFrom());
// push(message.getOrderId() + "-" + message.getUidTo(),result,NettyCommand.PUSH_CHAT);
push(message.getUidTo(), result, NettyCommand.PUSH_GROUP_CHAT);
messagingTemplate.convertAndSendToUser(message.getUidTo(), "/order-notice/" + message.getOrderId(), result);
} else if (message.getMessageType() == MessageTypeEnum.NORMAL_CHAT) {
ChatMessageRecord chatMessageRecord = new ChatMessageRecord();
BeanUtils.copyProperties(message, chatMessageRecord);
chatMessageRecord.setSendTime(DateUtils.getCurrentDate().getTime());
chatMessageRecord.setFromAvatar(message.getAvatar());
// 聊天消息保存到mogondb
chatMessageHandler.handleMessage(chatMessageRecord);
chatMessageRecord.setSendTimeStr(DateUtils.getDateStr(chatMessageRecord.getSendTime()));
// 发送给指定用户(客户端订阅路径:/user/+uid+/+key)
push(message.getUidTo(), chatMessageRecord, NettyCommand.PUSH_GROUP_CHAT);
// push(message.getOrderId() + "-" + message.getUidTo(),chatMessageRecord,NettyCommand.PUSH_CHAT);
// apnsHandler.handleMessage(message.getUidTo(),chatMessageRecord);
messagingTemplate.convertAndSendToUser(message.getUidTo(), "/" + message.getOrderId(), chatMessageRecord);
}
}
}
19
View Source File : WebSocketController.java
License : MIT License
Project Creator : xlui
License : MIT License
Project Creator : xlui
@Controller
@Slf4j
public clreplaced WebSocketController {
// You cannot integrate WebSocket with JWT for token validate.
private static final String token = "this is a token generated by your code!";
private final SimpMessagingTemplate simpMessagingTemplate;
public WebSocketController(SimpMessagingTemplate simpMessagingTemplate) {
this.simpMessagingTemplate = simpMessagingTemplate;
}
/**
* <code>@MessageMapping</code> defines the endpoint for receiving messages, client will send websocket message
* to endpoints defined in this annotation.
* <code>@SendTo</code> defines the return value's target endpoint of this method, clients which subscribe to
* this endpoint will receive the return value of this method.
* This method will simply send messages received to all clients that subscribe to endpoint specified in
* <code>@SendTo</code>, just like a broadcast
*
* <code>@MessageMapping</code> 定义接收消息的端点,客户端发送 WebSocket 消息到此端点。
* <code>@SendTo</code> 定义方法返回值发送的端点,订阅该端点的客户端可以收到服务器端的回复。
* 此端点默认将收到的消息发送到所有订阅了 <code>@SendTo</code> 端点的客户端,相当于广播。
*
* @param message client message
* @param authorizationToken customize header, for token validate
* @return return client message to all clients that subscribe to <code>/b</code>
*/
//
@MessageMapping("/broadcast")
@SendTo("/b")
public Response broadcast(Message message, @Header(value = "authorization") String authorizationToken) {
val response = new Response("Token check failed!");
if (authorizationToken.equals(token)) {
log.info("Token check success!!!");
response.setResponse("Welcome, " + message.getName() + "!");
} else {
log.info(response.getResponse());
}
return response;
}
/**
* Add a placeholder in <code>@MessageMapping</code> to get the dynamic param in websocket url, for dynamic
* resending. Message sent to this endpoint will be resent to any clients that subscribe endpoint {@code /g/<groupId>}.
* Just like a group chat.
* <p>
* 通过在 <code>@MessageMapping</code> 中添加消息占位符来获取 url 内容,从而动态转发。
* 消息会发送到所有订阅了 {@code /g/<groupId>} 的客户端,实现效果相当于群聊
*
* @param groupID group id
* @param message client message
*/
@MessageMapping("/group/{groupID}")
public void group(@DestinationVariable int groupID, Message message) {
log.info("Receive group message: [" + groupID + " -> " + message.getName() + "]");
Response response = new Response("Welcome to group " + groupID + ", " + message.getName() + "!");
simpMessagingTemplate.convertAndSend("/g/" + groupID, response);
}
/**
* Send message to specify user depend on {@link ChatMessage#getUserID}, each user will subscribe himself/herself's endpoint
* {@code /user/<userId>/msg}, just like point to point chat.
* <p>
* 依据 {@code ChatMessage} 中的内容发送消息给特定用户,每个用户都订阅自己接受消息的端点
* {@code /user/<userId>/msg},实现效果类似点对点聊天
*
* @param chatMessage 聊天消息
*/
@MessageMapping("/chat")
public void chat(ChatMessage chatMessage) {
log.info("Receive point-to-point chat message: [" + chatMessage.getFromUserID() + " -> " + chatMessage.getUserID() + ", " + chatMessage.getMessage() + "]");
Response response = new Response("Receive message from user " + chatMessage.getFromUserID() + ": " + chatMessage.getMessage());
simpMessagingTemplate.convertAndSendToUser(String.valueOf(chatMessage.getUserID()), "/msg", response);
}
}
19
View Source File : ServerTask.java
License : MIT License
Project Creator : xkcoding
License : MIT License
Project Creator : xkcoding
/**
* <p>
* 服务器定时推送任务
* </p>
*
* @author yangkai.shen
* @date Created in 2018-12-14 16:04
*/
@Slf4j
@Component
public clreplaced ServerTask {
@Autowired
private SimpMessagingTemplate wsTemplate;
/**
* 按照标准时间来算,每隔 2s 执行一次
*/
@Scheduled(cron = "0/2 * * * * ?")
public void websocket() throws Exception {
log.info("【推送消息】开始执行:{}", DateUtil.formatDateTime(new Date()));
// 查询服务器状态
Server server = new Server();
server.copyTo();
ServerVO serverVO = ServerUtil.wrapServerVO(server);
Dict dict = ServerUtil.wrapServerDict(serverVO);
wsTemplate.convertAndSend(WebSocketConsts.PUSH_SERVER, JSONUtil.toJsonStr(dict));
log.info("【推送消息】执行结束:{}", DateUtil.formatDateTime(new Date()));
}
}
19
View Source File : ChatServiceTest.java
License : MIT License
Project Creator : woowacourse-teams
License : MIT License
Project Creator : woowacourse-teams
@ExtendWith(MockitoExtension.clreplaced)
clreplaced ChatServiceTest {
@Mock
ChatRoomRepository chatRoomRepository;
@Mock
ChatRepository chatRepository;
@Mock
SimpMessagingTemplate simpMessagingTemplate;
@Mock
ChatSessionInformations chatSessionInformations;
private ChatService chatService;
@BeforeEach
void setUp() {
this.chatService = new ChatService(chatRoomRepository, chatRepository, simpMessagingTemplate, chatSessionInformations);
}
@Test
void sendMessage() {
Long noticeId = 1L;
List<Chat> chats = Arrays.asList(Chat.of("하늘하늘한 동글", replacedleColor.AMBER, "message1", ChatRoom.from(noticeId)), Chat.of("찬란한 코일", replacedleColor.BAROSSA, "message2", ChatRoom.from(noticeId)), Chat.of("어슴프레한 유안", replacedleColor.DARK_ORCHID, "message3", ChatRoom.from(noticeId)));
Set<ChatName> chatNames = new HashSet<>(Arrays.asList(ChatName.of("하늘하늘한 동글", replacedleColor.AMBER), ChatName.of("찬란한 코일", replacedleColor.BAROSSA), ChatName.of("어슴프레한 유안", replacedleColor.DARK_ORCHID)));
ChatRoom chatRoom = ChatRoom.builder().noticeId(noticeId).chats(chats).build();
MessageSendRequest messageSendRequest = new MessageSendRequest(noticeId, "하늘하늘한 동글", "메세지", replacedleColor.AMBER.getColor());
given(chatRoomRepository.findByNoticeId(anyLong())).willReturn(Optional.of(chatRoom));
given(chatRepository.save(any(Chat.clreplaced))).willReturn(Chat.of("하늘하늘한 동글", replacedleColor.AMBER, "메세지", chatRoom));
doNothing().when(simpMessagingTemplate).convertAndSend(any(String.clreplaced), any(StompMessageResponse.clreplaced));
chatService.sendMessage(messageSendRequest);
verify(chatRoomRepository).findByNoticeId(eq(noticeId));
verify(chatRepository).save(any());
verify(simpMessagingTemplate).convertAndSend(any(), any(StompMessageResponse.clreplaced));
}
@DisplayName("noticeId에 해당하는 Chatroom이 존재할 경우 Chatroom 생성 하지 않음")
@Test
void connectWhenChatRoomDoesNotExist() {
Long noticeId = 1L;
List<Chat> chats = Arrays.asList(Chat.of("하늘하늘한 동글", replacedleColor.AMBER, "message1", ChatRoom.from(noticeId)), Chat.of("찬란한 코일", replacedleColor.BAROSSA, "message2", ChatRoom.from(noticeId)), Chat.of("어슴프레한 유안", replacedleColor.DARK_ORCHID, "message3", ChatRoom.from(noticeId)));
ChatRoom chatRoom = ChatRoom.builder().noticeId(noticeId).chats(chats).build();
given(chatRoomRepository.findByNoticeId(anyLong())).willReturn(Optional.of(chatRoom));
given(chatSessionInformations.countSessionOn(anyLong())).willReturn(4);
ChatRoomResponse chatRoomResponse = chatService.fetchChatRoomInfo(noticeId);
verify(chatRoomRepository).findByNoticeId(eq(noticeId));
verify(chatRoomRepository, never()).save(any());
replacedertThat(chatRoomResponse).isNotNull();
replacedertThat(chatRoomResponse.getMessageResponses()).isNotNull();
List<MessageResponse> messageResponses = chatRoomResponse.getMessageResponses().getMessageResponses();
replacedertAll(() -> replacedertEquals(messageResponses.get(0).getName(), "하늘하늘한 동글"), () -> replacedertEquals(messageResponses.get(1).getName(), "찬란한 코일"), () -> replacedertEquals(messageResponses.get(2).getName(), "어슴프레한 유안"), () -> replacedertThat(chatRoomResponse.getHeadCount()).isEqualTo(4));
}
@DisplayName("noticeId에 해당하는 Chatroom이 존재할 경우 Chatroom 생성")
@Test
void connectWhenChatRoomExist() {
Long noticeId = 1L;
List<Chat> chats = Arrays.asList(Chat.of("하늘하늘한 동글", replacedleColor.AMBER, "message1", ChatRoom.from(noticeId)), Chat.of("찬란한 코일", replacedleColor.BAROSSA, "message2", ChatRoom.from(noticeId)), Chat.of("어슴프레한 유안", replacedleColor.DARK_ORCHID, "message3", ChatRoom.from(noticeId)));
ChatRoom chatRoom = ChatRoom.builder().noticeId(noticeId).chats(chats).build();
given(chatRoomRepository.findByNoticeId(anyLong())).willReturn(Optional.of(chatRoom));
given(chatSessionInformations.countSessionOn(anyLong())).willReturn(4);
ChatRoomResponse chatRoomResponse = chatService.fetchChatRoomInfo(noticeId);
verify(chatRoomRepository).findByNoticeId(eq(noticeId));
replacedertThat(chatRoomResponse).isNotNull();
replacedertThat(chatRoomResponse.getMessageResponses()).isNotNull();
List<MessageResponse> messageResponses = chatRoomResponse.getMessageResponses().getMessageResponses();
replacedertAll(() -> replacedertEquals(messageResponses.get(0).getName(), "하늘하늘한 동글"), () -> replacedertEquals(messageResponses.get(1).getName(), "찬란한 코일"), () -> replacedertEquals(messageResponses.get(2).getName(), "어슴프레한 유안"), () -> replacedertThat(chatRoomResponse.getHeadCount()).isEqualTo(4));
}
}
19
View Source File : ChatService.java
License : MIT License
Project Creator : woowacourse-teams
License : MIT License
Project Creator : woowacourse-teams
@Service
@Transactional(readOnly = true)
@RequiredArgsConstructor
public clreplaced ChatService {
public static final String PUBLISH_URL = "/channel/";
private final ChatRoomRepository chatRoomRepository;
private final ChatRepository chatRepository;
private final SimpMessagingTemplate simpMessagingTemplate;
private final ChatSessionInformations chatSessionInformations;
@Transactional
public void sendMessage(MessageSendRequest messageSendRequest) {
ChatRoom chatRoom = getChatRoom(messageSendRequest.getNoticeId());
Chat savedChat = saveChat(messageSendRequest, chatRoom);
MessageResponse messageResponse = MessageResponse.from(savedChat);
simpMessagingTemplate.convertAndSend(PUBLISH_URL + messageSendRequest.getNoticeId(), StompMessageResponse.of(StompMethodType.TALK, messageResponse));
}
private ChatRoom getChatRoom(Long noticeId) {
return chatRoomRepository.findByNoticeId(noticeId).orElseThrow(() -> new NotExistException(String.format("noticeId = %s 를 가진 채팅방이 존재하지 않습니다.", noticeId)));
}
private Chat saveChat(MessageSendRequest messageSendRequest, ChatRoom chatRoom) {
Chat chat = Chat.of(messageSendRequest.getName(), replacedleColor.from(messageSendRequest.getreplacedleColor()), messageSendRequest.getMessage(), chatRoom);
return chatRepository.save(chat);
}
@Transactional
public ChatRoomResponse fetchChatRoomInfo(Long noticeId) {
ChatRoom chatRoom = getOrCreateChatRoom(noticeId);
return ChatRoomResponse.of(chatRoom.getChats(), chatSessionInformations.countSessionOn(noticeId));
}
private ChatRoom getOrCreateChatRoom(Long noticeId) {
return chatRoomRepository.findByNoticeId(noticeId).orElseGet(() -> chatRoomRepository.save(ChatRoom.from(noticeId)));
}
public void addNewSessionInfo(String sessionId, long noticeId) {
ChatSessionInformation chatSessionInformation = chatSessionInformations.addSessionInfo(sessionId, noticeId);
sendConnectionInformation(StompMethodType.ENTER, chatSessionInformation, sessionId);
}
public void disconnectSession(String sessionId) {
ChatSessionInformation chatSessionInformation = chatSessionInformations.removeSession(sessionId);
sendConnectionInformation(StompMethodType.QUIT, chatSessionInformation, sessionId);
}
private void sendConnectionInformation(StompMethodType stompMethodType, ChatSessionInformation info, String sessionId) {
long noticeId = info.getNoticeId();
ChatName chatName = info.getChatName();
simpMessagingTemplate.convertAndSend(PUBLISH_URL + noticeId, StompMessageResponse.of(stompMethodType, ChatNameResponse.of(chatName, sessionId)));
}
}
19
View Source File : KafkaTransactionsConsumerService.java
License : GNU General Public License v3.0
Project Creator : wlhbdp
License : GNU General Public License v3.0
Project Creator : wlhbdp
@Service
@Slf4j
public clreplaced KafkaTransactionsConsumerService implements ConsumerSeekAware {
private final SimpMessagingTemplate simpTemplate;
private final ObjectMapper mapper = new ObjectMapper();
@Value("${web-socket.topic.transactions}")
private String transactionsWebSocketTopic;
@Autowired
public KafkaTransactionsConsumerService(SimpMessagingTemplate simpTemplate) {
this.simpTemplate = simpTemplate;
}
@KafkaListener(id = "${kafka.listeners.transactions.id}", topics = "${kafka.topic.transactions}", groupId = "transactions")
public void consumeTransactions(@Payload String message) {
log.debug("{}", message);
simpTemplate.convertAndSend(transactionsWebSocketTopic, message);
}
@Override
public void registerSeekCallback(ConsumerSeekCallback callback) {
}
@Override
public void onParreplacedionsreplacedigned(Map<TopicParreplacedion, Long> replacedignments, ConsumerSeekCallback callback) {
replacedignments.forEach((t, o) -> callback.seekToEnd(t.topic(), t.parreplacedion()));
}
@Override
public void onIdleContainer(Map<TopicParreplacedion, Long> replacedignments, ConsumerSeekCallback callback) {
}
}
19
View Source File : WelComeJob.java
License : MIT License
Project Creator : wayn111
License : MIT License
Project Creator : wayn111
public void welCome() {
SimpMessagingTemplate simpMessagingTemplate = SpringContextUtil.getBean(SimpMessagingTemplate.clreplaced);
String sysName = configService.getValueByKey("sys.name");
simpMessagingTemplate.convertAndSend("/topic/getResponse", "WelCome to " + sysName + "!");
logger.info("执行自定义定时任务");
}
19
View Source File : WsController.java
License : MIT License
Project Creator : wayn111
License : MIT License
Project Creator : wayn111
/**
* stomp消息路由
*/
@Controller
public clreplaced WsController {
@Autowired
private SimpMessagingTemplate simpMessagingTemplate;
@MessageMapping("/message")
public void message(Response message) {
System.out.println(message);
simpMessagingTemplate.convertAndSend("/topic/getResponse", Response.success("tip"));
}
}
19
View Source File : NotifyRecordController.java
License : MIT License
Project Creator : wayn111
License : MIT License
Project Creator : wayn111
@RequestMapping("/oa/notifyRecord")
@Controller
public clreplaced NotifyRecordController extends BaseController {
private static final String PREFIX = "oa/notifyRecord";
@Autowired
private NotifyRecordService notifyRecordService;
@Autowired
private UserService userService;
@Autowired
private SimpMessagingTemplate simpMessagingTemplate;
@RequiresPermissions("oa:notifyRecord:list")
@GetMapping
public String NotifyRecordIndex(ModelMap modelMap) {
modelMap.addAttribute("users", userService.selectUser2JsonObj());
return PREFIX + "/notifyRecord";
}
@Log(value = "我的通知")
@RequiresPermissions("oa:notifyRecord:list")
@ResponseBody
@PostMapping("/list")
public Page<NotifyRecordVO> list(Model model, NotifyRecordVO notifyRecordVO) {
notifyRecordVO.setReceiveUserId(getCurUserId());
Page<NotifyRecordVO> page = getPage();
// 设置通用查询字段
ParameterUtil.set(notifyRecordVO);
return notifyRecordService.selectNotifyRecordList(page, notifyRecordVO);
}
@RequiresPermissions("oa:notifyRecord:add")
@GetMapping("/add")
public String add(ModelMap modelMap) {
return PREFIX + "/add";
}
@RequiresPermissions("oa:notifyRecord:list")
@GetMapping("/{option}/{id}")
public String option(ModelMap modelMap, @PathVariable("option") String option, @PathVariable("id") Long id) {
NotifyRecordVO notifyRecordVO = notifyRecordService.selectNotifyByNotifyRecordId(id);
// 将状态变为已读
if (!notifyRecordVO.getRead()) {
notifyRecordService.update().set("isRead", 1).eq("id", id).update();
}
simpMessagingTemplate.convertAndSendToUser(getCurUserId(), "/queue/notifyRecordTip", "");
modelMap.put("notifyRecordVO", notifyRecordVO);
return PREFIX + "/" + option;
}
@RequiresPermissions("oa:notifyRecord:add")
@ResponseBody
@PostMapping("/addSave")
public Response addSave(ModelMap modelMap, NotifyRecord notifyRecord) {
return Response.result(notifyRecordService.save(notifyRecord), "新增成功");
}
@RequiresPermissions("oa:notifyRecord:edit")
@ResponseBody
@PostMapping("/editSave")
public Response editSave(ModelMap modelMap, NotifyRecord notifyRecord) {
return Response.result(notifyRecordService.update(notifyRecord), "修改成功");
}
@Log(value = "我的通知", operator = Operator.DELETE)
@RequiresPermissions("oa:notifyRecord:remove")
@ResponseBody
@DeleteMapping("/remove/{id}")
public Response remove(ModelMap modelMap, @PathVariable("id") Long id) {
return Response.result(notifyRecordService.remove(id), "删除成功");
}
@Log(value = "我的通知", operator = Operator.DELETE)
@RequiresPermissions("oa:notifyRecord:remove")
@ResponseBody
@PostMapping("/batchRemove")
public Response batchRemove(ModelMap modelMap, @RequestParam("ids[]") Long[] ids) {
return Response.result(notifyRecordService.batchRemove(ids), "删除成功");
}
@PostMapping("/export")
public void export(NotifyRecordVO notifyRecordVO, HttpServletResponse response) throws IOException {
notifyRecordVO.setReceiveUserId(getCurUserId());
// 设置通用查询字段
ParameterUtil.set(notifyRecordVO);
notifyRecordService.export(notifyRecordVO, response, request);
}
/**
* 获取右上角通知图标最新状态
*
* @return
*/
@ResponseBody
@GetMapping("/notifyRecordTip")
public Page<NotifyRecordTip> notifyRecordTip() {
Page<NotifyRecordTip> page = getPage(1, 5);
return notifyRecordService.selectNotifyRecordTipList(page, getCurUserId());
}
}
19
View Source File : MyRealm.java
License : MIT License
Project Creator : wayn111
License : MIT License
Project Creator : wayn111
public clreplaced MyRealm extends AuthorizingRealm {
@Autowired
private UserService userService;
@Autowired
private UserRoleService userRoleService;
@Autowired
private RoleMenuService roleMenuService;
@Autowired
private LogininforService logininforService;
@Autowired
private ConfigService configService;
@Autowired
private SessionDAO sessionDAO;
@Autowired
private SimpMessagingTemplate simpMessagingTemplate;
/**
* 密码加密 测试
*
* @param args 测试
*/
public static void main(String[] args) {
// MD5,"原密码","盐",加密次数
String pwd = new SimpleHash("MD5", "123456", "admin", 1024).toString();
System.out.println(pwd);
System.out.println(Boolean.valueOf("true"));
}
/**
* 授权
*/
@Override
protected AuthorizationInfo doGetAuthorizationInfo(PrincipalCollection principals) {
User sysUser = (User) principals.getPrimaryPrincipal();
SimpleAuthorizationInfo info = new SimpleAuthorizationInfo();
Set<String> roles = userRoleService.findRolesByUid(sysUser.getId());
Set<String> permissions = roleMenuService.findMenusByUid(sysUser.getId());
info.setRoles(roles);
info.setStringPermissions(permissions);
return info;
}
/**
* 认证
*/
@Override
protected AuthenticationInfo doGetAuthenticationInfo(AuthenticationToken token) throws AuthenticationException {
UsernamePreplacedwordToken token2 = (UsernamePreplacedwordToken) token;
String username = token2.getUsername();
// String preplacedword = ShiroUtil.md5encrypt(new String(token2.getPreplacedword()), username);
User sysUser = userService.getOne(new QueryWrapper<User>().eq("userName", username));
if (sysUser == null) {
logininforService.addLog(username, Constants.LOGIN_FAIL, "用户不存在");
throw new UnknownAccountException("用户不存在");
}
if (sysUser.getUserState() == -1) {
logininforService.addLog(username, Constants.LOGIN_FAIL, "用户已被禁用");
throw new UnknownAccountException("用户已被禁用");
}
// 此处不再需要做密码验证,由CredentialsMatch的实现做密码校验
/*if (!sysUser.getPreplacedword().equals(preplacedword)) {
throw new IncorrectCredentialsException("账号或密码不正确");
}*/
if (sysUser.getUserState().equals(StateEnum.DISABLE.getState())) {
logininforService.addLog(username, Constants.LOGIN_FAIL, "该用户已被锁定,请稍后再试");
throw new LockedAccountException("该用户已被锁定,请稍后再试");
}
// 是否进行单一用户登陆处理
boolean singeUserAuth = Boolean.parseBoolean(configService.getValueByKey("sys.user.singeUserAuth"));
if (singeUserAuth) {
Collection<Session> activeSessions = sessionDAO.getActiveSessions();
for (Session activeSession : activeSessions) {
if (activeSession.getAttribute(DefaultSubjectContext.PRINCIPALS_SESSION_KEY) != null) {
SimplePrincipalCollection principalCollection = (SimplePrincipalCollection) activeSession.getAttribute(DefaultSubjectContext.PRINCIPALS_SESSION_KEY);
Object primaryPrincipal = principalCollection.getPrimaryPrincipal();
User user = (User) primaryPrincipal;
if (user.getUserName().equals(username)) {
// 单一用户登出逻辑,是否强制登出前一用户
boolean singeKickoutBefore = Boolean.parseBoolean(configService.getValueByKey("sys.user.singeKickoutBefore"));
if (!singeKickoutBefore) {
logininforService.addLog(username, Constants.LOGIN_FAIL, "该用户已登陆,请先登出!");
throw new AuthenticationException("该用户已登陆,请先登出!");
}
Session session = sessionDAO.readSession(activeSession.getId());
if (session != null) {
session.stop();
sessionDAO.delete(session);
simpMessagingTemplate.convertAndSendToUser(user.getId(), "/queue/getResponse", "新消息:" + "该账号已在其他机器登陆!");
}
}
}
}
}
// 盐值加密
ByteSource byteSource = ByteSource.Util.bytes(username);
return new SimpleAuthenticationInfo(sysUser, sysUser.getPreplacedword(), byteSource, getName());
}
public void clearCachedAuthorizationInfo() {
doClearCache(SecurityUtils.getSubject().getPrincipals());
clearCachedAuthorizationInfo(SecurityUtils.getSubject().getPrincipals());
}
}
19
View Source File : HelloController.java
License : Apache License 2.0
Project Creator : wangzihaogithub
License : Apache License 2.0
Project Creator : wangzihaogithub
/**
* 我的房间Controller (供websocket客户端订阅或请求)
*
* @author wangzihao
*/
@RestController
public clreplaced HelloController {
private Logger logger = LoggerFactory.getLogger(getClreplaced());
// 所有在线的用户
@Autowired
private SimpUserRegistry userRegistry;
// 发送消息的工具类 (可以主动回复客户端)
@Autowired
private SimpMessagingTemplate messagingTemplate;
/**
* 订阅房间
*
* @param message 消息
* @param principal 订阅人的用户身份(当前登录人的信息)
* @param username 被订阅人的账号
* @param roomName 被订阅的房间名
*/
@SubscribeMapping("/user/room/{username}/{roomName}")
public void subscribeMyRoom(Message message, Principal principal, @DestinationVariable("username") String username, @DestinationVariable("roomName") String roomName) {
logger.info("[" + principal.getName() + "]订阅了[" + username + "]的 [" + roomName + "] 房间");
}
/**
* 接收消息
*
* @param message 客户端的数据
* @param principal 当前登录人的信息
*/
@MessageMapping("/receiveMessage")
public void receiveMessage(Message message, Principal principal) {
String payload = new String((byte[]) message.getPayload());
logger.info("已收到[" + principal.getName() + "]的消息[" + payload + "] 当前在线人数[" + userRegistry.getUserCount() + "]");
}
}
19
View Source File : UserRegistryMessageHandler.java
License : MIT License
Project Creator : Vip-Augus
License : MIT License
Project Creator : Vip-Augus
/**
* {@code MessageHandler} that handles user registry broadcasts from other
* application servers and periodically broadcasts the content of the local
* user registry.
*
* <p>The aggregated information is maintained in a {@link MultiServerUserRegistry}.
*
* @author Rossen Stoyanchev
* @since 4.2
*/
public clreplaced UserRegistryMessageHandler implements MessageHandler, ApplicationListener<BrokerAvailabilityEvent> {
private final MultiServerUserRegistry userRegistry;
private final SimpMessagingTemplate brokerTemplate;
private final String broadcastDestination;
private final TaskScheduler scheduler;
private final UserRegistryTask schedulerTask = new UserRegistryTask();
@Nullable
private volatile ScheduledFuture<?> scheduledFuture;
private long registryExpirationPeriod = TimeUnit.SECONDS.toMillis(20);
/**
* Constructor.
* @param userRegistry the registry with local and remote user registry information
* @param brokerTemplate template for broadcasting local registry information
* @param broadcastDestination the destination to broadcast to
* @param scheduler the task scheduler to use
*/
public UserRegistryMessageHandler(MultiServerUserRegistry userRegistry, SimpMessagingTemplate brokerTemplate, String broadcastDestination, TaskScheduler scheduler) {
replacedert.notNull(userRegistry, "'userRegistry' is required");
replacedert.notNull(brokerTemplate, "'brokerTemplate' is required");
replacedert.hasText(broadcastDestination, "'broadcastDestination' is required");
replacedert.notNull(scheduler, "'scheduler' is required");
this.userRegistry = userRegistry;
this.brokerTemplate = brokerTemplate;
this.broadcastDestination = broadcastDestination;
this.scheduler = scheduler;
}
/**
* Return the configured destination for broadcasting UserRegistry information.
*/
public String getBroadcastDestination() {
return this.broadcastDestination;
}
/**
* Configure the amount of time (in milliseconds) before a remote user
* registry snapshot is considered expired.
* <p>By default this is set to 20 seconds (value of 20000).
* @param milliseconds the expiration period in milliseconds
*/
@SuppressWarnings("unused")
public void setRegistryExpirationPeriod(long milliseconds) {
this.registryExpirationPeriod = milliseconds;
}
/**
* Return the configured registry expiration period.
*/
public long getRegistryExpirationPeriod() {
return this.registryExpirationPeriod;
}
@Override
public void onApplicationEvent(BrokerAvailabilityEvent event) {
if (event.isBrokerAvailable()) {
long delay = getRegistryExpirationPeriod() / 2;
this.scheduledFuture = this.scheduler.scheduleWithFixedDelay(this.schedulerTask, delay);
} else {
ScheduledFuture<?> future = this.scheduledFuture;
if (future != null) {
future.cancel(true);
this.scheduledFuture = null;
}
}
}
@Override
public void handleMessage(Message<?> message) throws MessagingException {
MessageConverter converter = this.brokerTemplate.getMessageConverter();
this.userRegistry.addRemoteRegistryDto(message, converter, getRegistryExpirationPeriod());
}
private clreplaced UserRegistryTask implements Runnable {
@Override
public void run() {
try {
SimpMessageHeaderAccessor accessor = SimpMessageHeaderAccessor.create(SimpMessageType.MESSAGE);
accessor.setHeader(SimpMessageHeaderAccessor.IGNORE_ERROR, true);
accessor.setLeaveMutable(true);
Object payload = userRegistry.getLocalRegistryDto();
brokerTemplate.convertAndSend(getBroadcastDestination(), payload, accessor.getMessageHeaders());
} finally {
userRegistry.purgeExpiredRegistries();
}
}
}
}
19
View Source File : Communication.java
License : Apache License 2.0
Project Creator : ververica
License : Apache License 2.0
Project Creator : ververica
@Slf4j
@Component
public clreplaced Communication implements PreplacedengerMessaging, DriverMessaging {
private final KafkaPreplacedengerPublisher preplacedengerPublisher;
private final KafkaDriverPublisher driverPublisher;
private final SimpMessagingTemplate simpSender;
private final String preplacedengerWebSocketTopic;
private final String driverWebSocketTopic;
private final ObjectMapper objectMapper = new ObjectMapper();
private final Scheduler scheduler;
@Autowired
public Communication(KafkaPreplacedengerPublisher preplacedengerPublisher, KafkaDriverPublisher driverPublisher, SimpMessagingTemplate simpSender, @Value("${web-socket.topic.preplacedenger}") String preplacedengerWebSocketTopic, @Value("${web-socket.topic.driver}") String driverWebSocketTopic, Scheduler scheduler) {
this.preplacedengerPublisher = Objects.requireNonNull(preplacedengerPublisher);
this.driverPublisher = Objects.requireNonNull(driverPublisher);
this.simpSender = Objects.requireNonNull(simpSender);
this.preplacedengerWebSocketTopic = Objects.requireNonNull(preplacedengerWebSocketTopic);
this.driverWebSocketTopic = Objects.requireNonNull(driverWebSocketTopic);
this.scheduler = Objects.requireNonNull(scheduler);
}
public void incomingPreplacedengerEvent(OutboundPreplacedengerMessage message) {
scheduler.enqueueTaskMessage(message.getPreplacedengerId(), message);
}
public void incomingDriverEvent(OutboundDriverMessage message) {
scheduler.enqueueTaskMessage(message.getDriverId(), message);
}
public void outgoingPreplacedengerEvent(InboundPreplacedengerMessage message) {
preplacedengerPublisher.accept(message);
}
public void outgoingDriverEvent(InboundDriverMessage message) {
driverPublisher.accept(message);
}
public void broadcastPreplacedengerSimulationEvent(WebsocketPreplacedengerEvent preplacedengerEvent) {
String json = toJsonString(preplacedengerEvent);
simpSender.convertAndSend(preplacedengerWebSocketTopic, json);
}
public void broadcastDriverSimulationEvent(WebsocketDriverEvent driverEvent) {
if (driverEvent.getDriverStatus() == WebsocketDriverEvent.DriverStatus.IDLE) {
// don't broadcast idle drivers, this is slightly too much.
return;
}
String json = toJsonString(driverEvent);
simpSender.convertAndSend(driverWebSocketTopic, json);
}
private String toJsonString(Object what) {
try {
return objectMapper.writeValuereplacedtring(what);
} catch (JsonProcessingException e) {
throw new RuntimeException(e);
}
}
}
19
View Source File : FileUploadControllerTest.java
License : Apache License 2.0
Project Creator : usdot-jpo-ode
License : Apache License 2.0
Project Creator : usdot-jpo-ode
public clreplaced FileUploadControllerTest {
FileUploadController testFileUploadController;
@Mocked
StorageService mockStorageService;
@Injectable
OdeProperties injectableOdeProperties;
@Injectable
SimpMessagingTemplate injectableSimpMessagingTemplate;
@Capturing
Executors capturingExecutors;
@Capturing
ImporterDirectoryWatcher capturingImporterDirectoryWatcher;
@Mocked
ExecutorService mockExecutorService;
@Mocked
OdeProperties mockOdeProperties;
@Mocked
MultipartFile mockMultipartFile;
@Before
public void constructorShouldLaunchSevenThreads() {
new Expectations() {
{
mockOdeProperties.getUploadLocationRoot();
result = "testRootDir";
mockOdeProperties.getUploadLocationObuLog();
result = "testLogFileDir";
Executors.newCachedThreadPool();
result = mockExecutorService;
mockExecutorService.submit((Runnable) any);
times = 7;
}
};
testFileUploadController = new FileUploadController(mockStorageService, mockOdeProperties, injectableSimpMessagingTemplate);
}
@Test
public void handleFileUploadReturnsErrorOnStorageException() {
new Expectations() {
{
mockStorageService.store((MultipartFile) any, anyString);
result = new StorageFileNotFoundException("testException123");
}
};
replacedertEquals(HttpStatus.BAD_REQUEST, testFileUploadController.handleFileUpload(mockMultipartFile, "type").getStatusCode());
}
@Test
public void successfulUploadReturnsHttpOk() {
new Expectations() {
{
mockStorageService.store((MultipartFile) any, anyString);
times = 1;
}
};
replacedertEquals(HttpStatus.OK, testFileUploadController.handleFileUpload(mockMultipartFile, "type").getStatusCode());
}
@Test
public void testStorageFileNotFoundException() {
replacedertEquals(HttpStatus.NOT_FOUND, testFileUploadController.handleStorageFileNotFound(new StorageFileNotFoundException("testException123")).getStatusCode());
}
}
19
View Source File : StompStringMessageDistributorTest.java
License : Apache License 2.0
Project Creator : usdot-jpo-ode
License : Apache License 2.0
Project Creator : usdot-jpo-ode
@Test
public void shouldConstructAndConvertAndSend(@Injectable SimpMessagingTemplate mockSimpMessagingTemplate, @Injectable ConsumerRecord<String, String> mockConsumerRecord) {
String testTopic = "testTopic123";
new Expectations() {
{
mockSimpMessagingTemplate.convertAndSend(testTopic, (StompContent) any);
mockConsumerRecord.value();
result = anyString;
}
};
StompStringMessageDistributor testSSNMP = new StompStringMessageDistributor(mockSimpMessagingTemplate, testTopic);
testSSNMP.setRecord(mockConsumerRecord);
try {
replacedertNull(testSSNMP.call());
} catch (Exception e) {
fail("Unexpected exception: " + e);
}
}
19
View Source File : StompStringExporterTest.java
License : Apache License 2.0
Project Creator : usdot-jpo-ode
License : Apache License 2.0
Project Creator : usdot-jpo-ode
public clreplaced StompStringExporterTest {
@Tested
StompStringExporter testStompExporter;
@Injectable
OdeProperties injectableOdeProperties;
@Injectable
String stompTopic = "testTopic";
@Injectable
SimpMessagingTemplate simpMessagingTemplate;
@Injectable
String odeTopic;
@SuppressWarnings({ "rawtypes", "unchecked" })
@Test
public void testSubscribe(@Capturing MessageConsumer capturingMessageConsumer, @Mocked MessageConsumer mockMessageConsumer) {
new Expectations() {
{
MessageConsumer.defaultStringMessageConsumer(anyString, anyString, (MessageProcessor) any);
result = mockMessageConsumer;
mockMessageConsumer.setName(anyString);
times = 1;
mockMessageConsumer.subscribe(anyString);
times = 1;
}
};
testStompExporter.subscribe();
}
}
19
View Source File : ExporterTest.java
License : Apache License 2.0
Project Creator : usdot-jpo-ode
License : Apache License 2.0
Project Creator : usdot-jpo-ode
@Test
public void shouldRun(@Mocked OdeProperties mockOdeProperties, @Injectable SimpMessagingTemplate mockSimpMessagingTemplate, @Mocked final MessageConsumer<String, byte[]> mockByteArrayConsumer, @Mocked final MessageConsumer<String, String> mockStringConsumer) {
String testTopic = "testTopic123";
new Expectations() {
{
mockOdeProperties.getKafkaBrokers();
result = anyString;
mockOdeProperties.getHostId();
result = anyString;
mockStringConsumer.close();
}
};
try {
Exporter odeBsmExporter = new StompStringExporter(mockOdeProperties, testTopic, mockSimpMessagingTemplate, "odeTopic");
odeBsmExporter.setConsumer(mockStringConsumer);
odeBsmExporter.run();
Exporter exporter = new Exporter("testTopic") {
@Override
protected void subscribe() {
;
}
};
exporter.run();
replacedertNull(exporter.getConsumer());
replacedertEquals("testTopic", exporter.getTopic());
exporter = new Exporter("topic", null) {
@Override
protected void subscribe() {
;
}
};
exporter.run();
replacedertNull(exporter.getConsumer());
replacedertEquals("topic", exporter.getTopic());
exporter.setTopic("topic2");
replacedertEquals("topic2", exporter.getTopic());
} catch (Exception e) {
fail("Unexpected exception: " + e);
}
}
19
View Source File : StompController.java
License : Apache License 2.0
Project Creator : usdot-jpo-ode
License : Apache License 2.0
Project Creator : usdot-jpo-ode
@Controller
public clreplaced StompController {
@Autowired
private SimpMessagingTemplate template;
@MessageMapping("/connect")
@SendTo("/topic/StompContent")
public StompContent greeting(RegistrationMessage message) throws InterruptedException {
// simulated delay
Thread.sleep(10);
return new StompContent(message.getName());
}
@PostMapping(value = "/newMessage")
@ResponseBody
public String messages() {
template.convertAndSend("/topic/messages", new StompContent("test"));
return "{\"success\": true}";
}
@GetMapping("/")
public String test() {
return "index";
}
}
19
View Source File : StompStringMessageDistributor.java
License : Apache License 2.0
Project Creator : usdot-jpo-ode
License : Apache License 2.0
Project Creator : usdot-jpo-ode
public clreplaced StompStringMessageDistributor extends AbstractSubscriberProcessor<String, String> {
private static Logger logger = LoggerFactory.getLogger(StompStringMessageDistributor.clreplaced);
private SimpMessagingTemplate template;
private String topic;
public StompStringMessageDistributor(SimpMessagingTemplate template, String topic) {
this.template = template;
this.topic = topic;
logger.info("Distributing messages to API layer topic {}", topic);
}
@Override
protected Object process(String consumedData) {
template.convertAndSend(topic, new StompContent(consumedData));
return null;
}
}
19
View Source File : StompStringExporter.java
License : Apache License 2.0
Project Creator : usdot-jpo-ode
License : Apache License 2.0
Project Creator : usdot-jpo-ode
/**
* Created by anthonychen on 10/16/17.
*/
public clreplaced StompStringExporter extends Exporter {
private OdeProperties odeProperties;
private SimpMessagingTemplate template;
private String odeTopic;
public StompStringExporter(OdeProperties odeProperties, String stompTopic, SimpMessagingTemplate template, String odeTopic) {
super(stompTopic);
this.odeProperties = odeProperties;
this.template = template;
this.odeTopic = odeTopic;
}
@Override
protected void subscribe() {
setConsumer(MessageConsumer.defaultStringMessageConsumer(odeProperties.getKafkaBrokers(), odeProperties.getHostId() + this.getClreplaced().getSimpleName(), new StompStringMessageDistributor(template, getTopic())));
getConsumer().setName(this.getClreplaced().getSimpleName());
getConsumer().subscribe(odeTopic);
}
}
19
View Source File : WebSocketController.java
License : Apache License 2.0
Project Creator : turoDog
License : Apache License 2.0
Project Creator : turoDog
/**
* Project Name:springboot_websocket_demo <br/>
* Package Name:com.nasus.websocket.controller <br/>
* Date:2019/3/4 22:16 <br/>
* <b>Description:</b> TODO: 描述该类的作用 <br/>
*
* @author <a href="[email protected]">nasus</a><br/>
* Copyright Notice =========================================================
* This file contains proprietary information of Eastcom Technologies Co. Ltd.
* Copying or reproduction without prior written approval is prohibited.
* Copyright (c) 2019 =======================================================
*/
@RestController
public clreplaced WebSocketController {
@Autowired
private SimpMessagingTemplate // 使用 SimpMessagingTemplate 向浏览器发送信息
messagingTemplate;
// @MessageMapping 和 @RequestMapping 功能类似,浏览器向服务器发起请求时,映射到该地址。
@MessageMapping("/hello")
// 如果服务器接受到了消息,就会对订阅了 @SendTo 括号中的地址的浏览器发送消息。
@SendTo("/nasus/getResponse")
public Server2ClientMessage say(Client2ServerMessage message) throws Exception {
Thread.sleep(3000);
return new Server2ClientMessage("Hello," + message.getName() + "!");
}
@MessageMapping("/chat")
public void handleChat(Principal principal, String msg) {
// 在 SpringMVC 中,可以直接在参数中获得 principal,principal 中包含当前用户信息
if (principal.getName().equals("nasus")) {
// 硬编码,如果发送人是 nasus 则接收人是 chenzy 反之也成立。
// 通过 messageingTemplate.convertAndSendToUser 方法向用户发送信息,参数一是接收消息用户,参数二是浏览器订阅地址,参数三是消息本身
messagingTemplate.convertAndSendToUser("chenzy", "/queue/notifications", principal.getName() + "-send:" + msg);
} else {
messagingTemplate.convertAndSendToUser("nasus", "/queue/notifications", principal.getName() + "-send:" + msg);
}
}
}
19
View Source File : RecordSender.java
License : MIT License
Project Creator : Toparvion
License : MIT License
Project Creator : Toparvion
/**
* A service for sending main payload - log records - to clients.
*
* @author Toparvion
* @since v0.7
*/
@Service
public clreplaced RecordSender {
private static final Logger log = LoggerFactory.getLogger(RecordSender.clreplaced);
private final RecordLevelDetector recordLevelDetector;
private final SimpMessagingTemplate messagingTemplate;
private final ColorPicker colorPicker;
@Autowired
public RecordSender(RecordLevelDetector recordLevelDetector, SimpMessagingTemplate messagingTemplate, ColorPicker colorPicker) {
this.recordLevelDetector = recordLevelDetector;
this.messagingTemplate = messagingTemplate;
this.colorPicker = colorPicker;
}
void sendRecord(Message<?> recordMessage) {
String destination = recordMessage.getHeaders().get(CLIENT_DESTINATION__HEADER, String.clreplaced);
String sourceNode = recordMessage.getHeaders().get(SOURCE_NODE__HEADER, String.clreplaced);
String sourcePath = requireNonNull(recordMessage.getHeaders().get(ORIGINAL_FILE, File.clreplaced)).getAbsolutePath();
String level = recordMessage.getHeaders().get(RECORD_LEVEL__HEADER, String.clreplaced);
LocalDateTime timestamp = recordMessage.getHeaders().get(LOG_TIMESTAMP_VALUE__HEADER, LocalDateTime.clreplaced);
Object payload = recordMessage.getPayload();
replacedert.isInstanceOf(Collection.clreplaced, payload);
@SuppressWarnings("unchecked")
List<String> payloadAsList = new ArrayList<>((Collection<String>) payload);
// much like with log config entry, the absence of timestamp means that the payload is a flat list of records
boolean isFlatMessage = (timestamp == null);
List<StyledLine> styledLines = isFlatMessage ? prepareFlatMessage(payloadAsList) : prepareGroupMessage(payloadAsList, level);
if (log.isTraceEnabled()) {
log.trace("Fragment being sent:\n{}", styledLines.stream().map(rec -> String.format("%7s: %s", rec.getStyle(), rec.getText())).collect(joining("\n")));
}
LinesPart linesPart;
if (isFlatMessage) {
linesPart = new LinesPart(styledLines);
} else {
long timestampMillis = timestamp.toInstant(ZoneOffset.UTC).toEpochMilli();
String highlightColor = colorPicker.pickColor(sourcePath, sourceNode, destination);
linesPart = new CompositeLinesPart(styledLines, sourceNode, sourcePath, timestampMillis, highlightColor);
}
messagingTemplate.convertAndSend(WEBSOCKET_TOPIC_PREFIX + destination, linesPart, singletonMap(MESSAGE_TYPE_HEADER, MessageType.RECORD));
}
/*private*/
List<StyledLine> prepareGroupMessage(List<String> payloadAsList, String firstLineLevel) {
List<StyledLine> parsedLines = new ArrayList<>();
if (payloadAsList.isEmpty()) {
return parsedLines;
}
// самую первую строку записи обрабатываем отдельно, так как только она содержит метку уровня
String firstLine = replacedogUtils.distinguishXml4Group(payloadAsList, 0);
if (isXmlPrefixed(firstLine)) {
throw new IllegalStateException(format("The very first line of the record is distinguished as XML but it " + "must contain timestamp only: '%s'", firstLine));
}
parsedLines.add(new StyledLine(replacedogUtils.escapeSpecialCharacters(firstLine), firstLineLevel));
// остальные проверяем в цикле и проставляем им либо XML, либо PLAIN, так как других уровней быть не должно
for (int i = 1; i < payloadAsList.size(); i++) {
// check the line for the presence of XML
String curLine = replacedogUtils.distinguishXml4Group(payloadAsList, i);
// вставляем текст строки
String text = replacedogUtils.escapeSpecialCharacters(curLine);
// определяем и вставляем уровень важности сообщения
String style;
if (isXmlPrefixed(text)) {
style = "XML";
text = stripXmlPrefix(text);
} else {
style = PLAIN_RECORD_LEVEL_NAME;
}
// завершаем оформление текущей строки
parsedLines.add(new StyledLine(text, style));
}
return parsedLines;
}
/*private*/
List<StyledLine> prepareFlatMessage(List<String> payloadAsList) {
List<StyledLine> parsedLines = new ArrayList<>();
for (int i = 0; i < payloadAsList.size(); i++) {
// check the line for the presence of XML
String curLine = replacedogUtils.distinguishXml(payloadAsList, i);
// insert the text of the line
String text = replacedogUtils.escapeSpecialCharacters(curLine);
// detect and set the importance level of the line (this also may appear an XML line)
String style = recordLevelDetector.detectLevel(curLine).orElseGet(() -> replacedogUtils.checkIfXml(curLine));
// finish current line construction
parsedLines.add(new StyledLine(text, style));
}
return parsedLines;
}
private boolean isXmlPrefixed(String text) {
return text.startsWith("__XML__");
}
private String stripXmlPrefix(String text) {
return text.substring("__XML__".length());
}
}
19
View Source File : RssLoadService.java
License : MIT License
Project Creator : tarpha
License : MIT License
Project Creator : tarpha
@Service
@Slf4j
public clreplaced RssLoadService {
@Autowired
private RssListRepository rssListRepository;
@Autowired
private RssFeedRepository rssFeedRepository;
@Autowired
private WatchListRepository watchListRepository;
@Autowired
private SeenListRepository seenListRepository;
@Autowired
private SettingRepository settingRepository;
@Autowired
private DownloadListRepository downloadListRepository;
@Autowired
private DownloadPathRepository downloadPathRepository;
@Autowired
private TransmissionService transmissionService;
@Autowired
private HttpDownloadService httpDownloadService;
@Autowired
private DownloadStationService downloadStationService;
@Autowired
private DaumMovieTvService daumMovieTvService;
@Autowired
private RssMakeService rssMakeService;
@Autowired
private SimpMessagingTemplate simpMessagingTemplate;
public void loadRss() {
log.info("=== Load RSS ===");
deleteFeed();
List<RssFeed> rssFeedList = new ArrayList<RssFeed>();
for (RssFeed rssFeed : rssMakeService.makeRss()) {
if (!rssFeedRepository.findByLink(rssFeed.getLink()).isPresent()) {
rssFeedList.add(rssFeed);
Optional<RssList> optioalRss = rssListRepository.findByName(rssFeed.getRssSite());
if (optioalRss.isPresent()) {
if (optioalRss.get().getDownloadAll()) {
download(rssFeed, optioalRss.get());
}
}
// Watch List를 체크하여 다운로드 요청한다.
checkWatchList(rssFeed, null);
}
}
for (RssList rss : rssListRepository.findByUseDbAndInternal(true, false)) {
log.info("Load RSS Site : " + rss.getName());
try {
URL feedSource = new URL(rss.getUrl());
SyndFeedInput input = new SyndFeedInput();
SyndFeed feedList = input.build(new XmlReader(feedSource));
for (int i = feedList.getEntries().size() - 1; i >= 0; i--) {
// Feed 한 건이 오류가 발생하여도 전체 로드에는 문제 없도록 예외처리를 추가한다.
try {
SyndEntry feed = feedList.getEntries().get(i);
RssFeed rssFeed = new RssFeed();
// log.debug(feed.toString());
if (!rssFeedRepository.findByLink(rssFeed.getLinkByKey(rss.getLinkKey(), feed)).isPresent()) {
rssFeed.setreplacedle(feed.getreplacedle());
rssFeed.setRssSite(rss.getName());
rssFeed.setTvSeries(rss.getTvSeries());
rssFeed.setRssreplacedleByreplacedle(feed.getreplacedle());
rssFeed.setRssEpisodeByreplacedle(feed.getreplacedle());
rssFeed.setRssSeasonByreplacedle(feed.getreplacedle());
rssFeed.setRssQualityByreplacedle(feed.getreplacedle());
rssFeed.setRssReleaseGroupByreplacedle(feed.getreplacedle());
rssFeed.setRssDateByreplacedle(feed.getreplacedle());
rssFeed.setLinkByKey(rss.getLinkKey(), feed);
try {
if (!StringUtils.isEmpty(feed.getDescription().getValue())) {
rssFeed.setDesc(feed.getDescription().getValue());
}
} catch (NullPointerException ne) {
log.debug("description: " + ne.toString());
}
String[] rssreplacedleSplit = StringUtils.split(rssFeed.getRssreplacedle());
if (rssreplacedleSplit.length == 1) {
rssFeed.setRssPoster(daumMovieTvService.getPoster(rssFeed.getRssreplacedle()));
} else {
for (int j = rssreplacedleSplit.length - 1; j > 0; j--) {
StringBuffer posterreplacedle = new StringBuffer();
for (int k = 0; k <= j; k++) {
posterreplacedle.append(rssreplacedleSplit[k] + " ");
}
String posterUrl = daumMovieTvService.getPoster(StringUtils.trim(posterreplacedle.toString()));
if (!StringUtils.isEmpty(posterUrl)) {
rssFeed.setRssPoster(posterUrl);
break;
}
}
}
// rssFeed.setRssPoster(daumMovieTvService.getPoster(rssFeed.getRssreplacedle()));
rssFeedList.add(rssFeed);
log.debug("Add Feed: " + rssFeed.getreplacedle());
if (rss.getDownloadAll()) {
log.debug("RSS Download Repuest All: " + rssFeed.getreplacedle());
download(rssFeed, rss);
}
// Watch List를 체크하여 다운로드 요청한다.
checkWatchList(rssFeed, null);
}
} catch (Exception e) {
// Feed 개별 건에 대한 Exception 처리
log.error(e.getMessage());
}
}
} catch (Exception e) {
// Feed Site에 대한 Exception 처리
log.error(e.getMessage());
}
}
rssFeedRepository.saveAll(rssFeedList);
// rssFeedRepository.saveAll(rssMakeService.makeRss());
simpMessagingTemplate.convertAndSend("/topic/feed/update", true);
}
public void checkWatchListFromDb(List<WatchList> list) {
for (RssFeed rssFeed : rssFeedRepository.findAll()) {
checkWatchList(rssFeed, list);
}
}
@Async
public void asyncLoadRss() {
loadRss();
}
public boolean checkWatchListQuality(RssFeed rssFeed, WatchList watchList) {
boolean checkQuality = false;
if (StringUtils.isBlank(watchList.getQuality())) {
watchList.setQuality("100p");
}
try {
if (StringUtils.contains(watchList.getQuality(), ',')) {
checkQuality = StringUtils.containsIgnoreCase(watchList.getQuality(), rssFeed.getRssQuality());
} else if (StringUtils.endsWithIgnoreCase(watchList.getQuality(), "P+")) {
checkQuality = Integer.parseInt(StringUtils.removeIgnoreCase(rssFeed.getRssQuality(), "P")) >= Integer.parseInt(StringUtils.removeIgnoreCase(watchList.getQuality(), "P+"));
} else {
checkQuality = Integer.parseInt(StringUtils.removeIgnoreCase(rssFeed.getRssQuality(), "P")) == Integer.parseInt(StringUtils.removeIgnoreCase(watchList.getQuality(), "P"));
}
} catch (NumberFormatException e) {
log.error(e.getMessage());
}
return checkQuality;
}
/**
* Feed가 WatchList에 존재할 경우 다운로드 요청을 한다.
*
* @param rssFeed WatchList에 존재하는지 검사할 대상이 되는 개별 RSS Feed
* @param list 사용자가 화면에서 WatchList 개별 건을 선택해서 직접 실행 했을 때 그 List를 받아올 인자
*/
private void checkWatchList(RssFeed rssFeed, List<WatchList> list) {
if (StringUtils.isBlank(rssFeed.getRssQuality())) {
rssFeed.setRssQuality("100p");
}
Optional<WatchList> optionalWatchList = watchListRepository.findByreplacedleRegex(rssFeed.getreplacedle(), rssFeed.getRssQuality());
if (optionalWatchList.isPresent()) {
WatchList watchList = optionalWatchList.get();
log.info("Matched Feed: " + rssFeed.getreplacedle());
rssFeed.sereplacedchreplacedle(watchList.getreplacedle());
try {
if (watchList.getRssList() != null && watchList.getRssList().size() > 0) {
if (!watchList.getRssList().contains(rssFeed.getRssSite())) {
log.info("Skipped by RSS List");
return;
}
}
} catch (NullPointerException e) {
log.error(e.toString());
}
if (list != null) {
log.info("Custom Execute");
boolean isExists = false;
for (WatchList wl : list) {
if (StringUtils.equals(watchList.getreplacedle(), wl.getreplacedle())) {
log.info("Custom Execute Matched: " + rssFeed.getreplacedle());
isExists = true;
break;
}
}
if (!isExists) {
log.info("Custom Execute Not Matched: " + rssFeed.getreplacedle());
return;
}
}
boolean seenDone = false;
boolean subreplacedleDone = false;
// boolean checkQuality = false;
// if (StringUtils.isBlank(watchList.getQuality())) {
// watchList.setQuality("100p");
// }
// try {
// if (StringUtils.endsWithIgnoreCase(watchList.getQuality(), "P+")) {
// checkQuality = Integer.parseInt(StringUtils.removeIgnoreCase(rssFeed.getRssQuality(), "P"))
// >= Integer.parseInt(StringUtils.removeIgnoreCase(watchList.getQuality(), "P+"));
// } else {
// checkQuality = Integer.parseInt(StringUtils.removeIgnoreCase(rssFeed.getRssQuality(), "P"))
// == Integer.parseInt(StringUtils.removeIgnoreCase(watchList.getQuality(), "P"));
// }
// } catch (NumberFormatException e) {
// log.error(e.getMessage());
// }
// if (!checkQuality) {
if (!checkWatchListQuality(rssFeed, watchList)) {
log.info("Rejected by Quality: " + rssFeed.getreplacedle());
return;
}
if (watchList.getSeries()) {
if (StringUtils.contains(watchList.getQuality(), ',')) {
// if (seenListRepository.countByParams(rssFeed.getLink(), rssFeed.getRssreplacedle(), rssFeed.getRssSeason(),
if (seenListRepository.countByParams(rssFeed.getLink(), rssFeed.gereplacedchreplacedle(), rssFeed.getRssSeason(), rssFeed.getRssEpisode(), false, rssFeed.getRssQuality()) > 0) {
seenDone = true;
}
// if (seenListRepository.countByParams(rssFeed.getLink(), rssFeed.getRssreplacedle(), rssFeed.getRssSeason(),
if (seenListRepository.countByParams(rssFeed.getLink(), rssFeed.gereplacedchreplacedle(), rssFeed.getRssSeason(), rssFeed.getRssEpisode(), true, rssFeed.getRssQuality()) > 0 || !watchList.getSubreplacedle()) {
subreplacedleDone = true;
}
} else {
// if (seenListRepository.countByParams(rssFeed.getLink(), rssFeed.getRssreplacedle(), rssFeed.getRssSeason(),
if (seenListRepository.countByParams(rssFeed.getLink(), rssFeed.gereplacedchreplacedle(), rssFeed.getRssSeason(), rssFeed.getRssEpisode(), false) > 0) {
seenDone = true;
}
// if (seenListRepository.countByParams(rssFeed.getLink(), rssFeed.getRssreplacedle(), rssFeed.getRssSeason(),
if (seenListRepository.countByParams(rssFeed.getLink(), rssFeed.gereplacedchreplacedle(), rssFeed.getRssSeason(), rssFeed.getRssEpisode(), true) > 0 || !watchList.getSubreplacedle()) {
subreplacedleDone = true;
}
}
} else {
if (seenListRepository.findFirstByLinkAndSubreplacedle(rssFeed.getLink(), false).isPresent()) {
seenDone = true;
}
if (seenListRepository.findFirstByLinkAndSubreplacedle(rssFeed.getLink(), true).isPresent() || !watchList.getSubreplacedle()) {
subreplacedleDone = true;
}
}
if (seenDone && subreplacedleDone) {
log.info("Rejected by Seen: " + rssFeed.getreplacedle());
} else {
if (!watchList.getSubreplacedle() && StringUtils.contains(rssFeed.getreplacedle(), "자막") && !StringUtils.startsWith(rssFeed.getLink(), "magnet")) {
log.info("Rejected by Subreplacedle: " + rssFeed.getreplacedle());
return;
}
if (watchList.getSeries()) {
try {
int startSeason = Integer.parseInt(watchList.getStartSeason());
int endSeason = Integer.parseInt(watchList.getEndSeason());
int startEpisode = Integer.parseInt(watchList.getStartEpisode());
int endEpisode = Integer.parseInt(watchList.getEndEpisode());
int currSeason = Integer.parseInt(rssFeed.getRssSeason());
int currEpisode = Integer.parseInt(rssFeed.getRssEpisode());
if (currSeason < startSeason || currSeason > endSeason) {
log.info("Rejected by Season: Start: " + startSeason + " End: " + endSeason + " Feed: " + currSeason);
return;
}
if (currEpisode < startEpisode || currEpisode > endEpisode) {
log.info("Rejected by Episode: Start: " + startEpisode + " End: " + endEpisode + " Feed: " + currEpisode);
return;
}
} catch (NumberFormatException e) {
log.error(e.toString());
}
}
log.info("Download Repuest: " + rssFeed.getreplacedle());
download(rssFeed, watchList);
}
}
}
private void addToSeenList(RssFeed rssFeed, String path, String rename) {
SeenList seenList = new SeenList();
// seenList.setreplacedle(rssFeed.getRssreplacedle());
seenList.setreplacedle(rssFeed.gereplacedchreplacedle());
seenList.setLink(rssFeed.getLink());
seenList.setDownloadPath(path);
seenList.setSeason(rssFeed.getRssSeason());
seenList.setEpisode(rssFeed.getRssEpisode());
seenList.setRenameStatus(StringUtils.isBlank(rename) ? "N/A" : "false");
seenList.setQuality(rssFeed.getRssQuality());
if (StringUtils.contains(rssFeed.getreplacedle(), "자막") && !StringUtils.startsWith(rssFeed.getLink(), "magnet")) {
seenList.setSubreplacedle(true);
seenList.setreplacedle("[자막]" + rssFeed.getRssreplacedle());
}
seenListRepository.save(seenList);
}
private void addToDownloadList(Long id, RssFeed rssFeed, WatchList watchList, String path) {
DownloadList download = new DownloadList();
download.setId(id);
download.setName(rssFeed.getreplacedle());
download.setUri(rssFeed.getLink());
download.setDownloadPath(path);
if (!StringUtils.isBlank(watchList.getRename())) {
download.setRename(CommonUtils.getRename(watchList.getRename(), rssFeed.getRssreplacedle(), rssFeed.getRssSeason(), rssFeed.getRssEpisode(), rssFeed.getRssQuality(), rssFeed.getRssReleaseGroup(), rssFeed.getRssDate()));
}
downloadListRepository.save(download);
}
private void addToDownloadList(Long id, RssFeed rssFeed, String path) {
DownloadList download = new DownloadList();
download.setId(id);
download.setName(rssFeed.getreplacedle());
download.setUri(rssFeed.getLink());
download.setDownloadPath(path);
downloadListRepository.save(download);
}
private void addToDownloadList(DownloadList download, RssFeed rssFeed, WatchList watchList) {
if (!StringUtils.isBlank(watchList.getRename())) {
download.setRename(CommonUtils.getRename(watchList.getRename(), rssFeed.getRssreplacedle(), rssFeed.getRssSeason(), rssFeed.getRssEpisode(), rssFeed.getRssQuality(), rssFeed.getRssReleaseGroup(), rssFeed.getRssDate()));
}
downloadListRepository.save(download);
}
@Transactional
private void deleteFeed() {
Optional<Setting> optionalSetting = settingRepository.findByKey("USE_LIMIT");
if (optionalSetting.isPresent()) {
if (Boolean.parseBoolean(optionalSetting.get().getValue())) {
Optional<Setting> limitCnt = settingRepository.findByKey("LIMIT_COUNT");
if (limitCnt.isPresent()) {
int cnt = Integer.parseInt(limitCnt.get().getValue());
rssFeedRepository.deleteByLimitCount(cnt);
downloadListRepository.deleteByLimitCount(cnt);
}
}
}
}
private void download(RssFeed rssFeed, WatchList watchList) {
String path = downloadPathRepository.computedPath(watchList.getDownloadPath(), rssFeed.getRssreplacedle(), rssFeed.getRssSeason());
if (StringUtils.isBlank(path)) {
path = watchList.getDownloadPath();
}
Optional<Setting> optionalSetting = settingRepository.findByKey("DOWNLOAD_APP");
if (optionalSetting.isPresent()) {
if (StringUtils.equals(optionalSetting.get().getValue(), "TRANSMISSION")) {
// Request Download to Transmission
if (StringUtils.startsWith(rssFeed.getLink(), "magnet") || StringUtils.equalsIgnoreCase(FilenameUtils.getExtension(rssFeed.getLink()), "torrent")) {
int torrentAddedId = transmissionService.torrentAdd(rssFeed.getLink(), path);
log.debug("Transmission ID: " + torrentAddedId);
if (torrentAddedId > 0) {
// Add to Seen
addToSeenList(rssFeed, path, watchList.getRename());
// Add to Download List
addToDownloadList((long) torrentAddedId, rssFeed, watchList, path);
}
} else {
Optional<DownloadList> optionalSeq = downloadListRepository.findTopByOrderByIdDesc();
long tempId;
if (optionalSeq.isPresent()) {
Long id = optionalSeq.get().getId() + 100L;
log.debug("id: " + id);
tempId = id;
} else {
tempId = 100L;
}
DownloadList download = new DownloadList();
download.setUri(rssFeed.getLink());
download.setDownloadPath(path);
download.setId(tempId);
httpDownloadService.createTransmission(download);
addToSeenList(rssFeed, path, watchList.getRename());
}
} else if (StringUtils.equals(optionalSetting.get().getValue(), "DOWNLOAD_STATION")) {
// Request Download to Download Station
if (downloadStationService.create(rssFeed.getLink(), path)) {
// Add to Seen
addToSeenList(rssFeed, path, watchList.getRename());
// Add to Download List
boolean isExist = false;
for (DownloadList down : downloadStationService.list()) {
if (StringUtils.equals(rssFeed.getLink(), down.getUri())) {
isExist = true;
// downloadListRepository.save(down);
addToDownloadList(down, rssFeed, watchList);
}
}
if (isExist == false) {
addToDownloadList(0L, rssFeed, watchList, path);
}
}
}
}
}
private void download(RssFeed rssFeed, RssList rssList) {
String path = downloadPathRepository.computedPath(rssList.getDownloadPath(), rssFeed.getRssreplacedle(), rssFeed.getRssSeason());
if (StringUtils.isBlank(path)) {
path = rssList.getDownloadPath();
}
Optional<Setting> optionalSetting = settingRepository.findByKey("DOWNLOAD_APP");
if (optionalSetting.isPresent()) {
if (StringUtils.equals(optionalSetting.get().getValue(), "TRANSMISSION")) {
// Request Download to Transmission
if (StringUtils.startsWith(rssFeed.getLink(), "magnet") || StringUtils.equalsIgnoreCase(FilenameUtils.getExtension(rssFeed.getLink()), "torrent")) {
int torrentAddedId = transmissionService.torrentAdd(rssFeed.getLink(), path);
log.debug("Transmission ID: " + torrentAddedId);
if (torrentAddedId > 0) {
// Add to Seen
// addToSeenList(rssFeed, path);
// Add to Download List
addToDownloadList((long) torrentAddedId, rssFeed, path);
}
} else {
Optional<DownloadList> optionalSeq = downloadListRepository.findTopByOrderByIdDesc();
long tempId;
if (optionalSeq.isPresent()) {
Long id = optionalSeq.get().getId() + 100L;
log.debug("id: " + id);
tempId = id;
} else {
tempId = 100L;
}
DownloadList download = new DownloadList();
download.setUri(rssFeed.getLink());
download.setDownloadPath(path);
download.setId(tempId);
httpDownloadService.createTransmission(download);
}
} else if (StringUtils.equals(optionalSetting.get().getValue(), "DOWNLOAD_STATION")) {
// Request Download to Download Station
if (downloadStationService.create(rssFeed.getLink(), path)) {
// Add to Seen
// addToSeenList(rssFeed, path);
// Add to Download List
boolean isExist = false;
for (DownloadList down : downloadStationService.list()) {
if (StringUtils.equals(rssFeed.getLink(), down.getUri())) {
isExist = true;
downloadListRepository.save(down);
}
}
if (isExist == false) {
addToDownloadList(0L, rssFeed, path);
}
}
}
}
}
}
19
View Source File : HttpDownloadService.java
License : MIT License
Project Creator : tarpha
License : MIT License
Project Creator : tarpha
@Service
@Slf4j
public clreplaced HttpDownloadService {
@Autowired
private TransmissionService transmissionService;
@Autowired
private DownloadListRepository downloadListRepository;
@Autowired
private SimpMessagingTemplate simpMessagingTemplate;
private Map<Long, HttpVo> jobs = new HashMap<>();
@Data
private clreplaced HttpVo {
private Long id;
private String name;
private String filename;
private String path;
private int percentDone = 0;
private Boolean done = false;
}
@Async
public void createTransmission(DownloadList download) {
String link = download.getUri();
String path = download.getDownloadPath();
long currentId = download.getId();
try {
CloseableHttpClient httpClient = HttpClientBuilder.create().build();
URIBuilder builder = new URIBuilder(link);
HttpGet httpGet = new HttpGet(builder.build());
CloseableHttpResponse response = httpClient.execute(httpGet);
Header[] header = response.getHeaders("Content-Disposition");
String content = header[0].getValue();
for (String str : StringUtils.split(content, ";")) {
if (StringUtils.containsIgnoreCase(str, "filename=")) {
log.debug(str);
String[] attachment = StringUtils.split(str, "=");
File directory = new File(path);
if (!directory.isDirectory()) {
FileUtils.forceMkdir(directory);
}
String filename = StringUtils.remove(attachment[1], "\"");
HttpVo vo = new HttpVo();
vo.setId(currentId);
vo.setName(download.getName());
vo.setFilename(filename);
vo.setPath(download.getDownloadPath());
jobs.put(currentId, vo);
download.setFileName(filename);
download.setDbid("http_" + vo.getId());
downloadListRepository.save(download);
BufferedInputStream bis = new BufferedInputStream(response.getEnreplacedy().getContent());
BufferedOutputStream bos = new BufferedOutputStream(new FileOutputStream(new File(path, filename)));
int inByte;
while ((inByte = bis.read()) != -1) bos.write(inByte);
bis.close();
bos.close();
vo.setDone(true);
vo.setPercentDone(100);
jobs.put(currentId, vo);
downloadListRepository.save(download);
// if(StringUtils.equalsIgnoreCase(FilenameUtils.getExtension(attachment[1]), "torrent")) {
if (StringUtils.containsIgnoreCase(filename, ".torrent")) {
long ret = transmissionService.torrentAdd(path + File.separator + filename, path);
if (ret > 0L) {
download.setId(ret);
downloadListRepository.save(download);
simpMessagingTemplate.convertAndSend("/topic/feed/download", download);
}
}
}
}
response.close();
httpClient.close();
} catch (Exception e) {
log.error(e.getMessage());
}
}
public DownloadList getInfo(Long id) {
if (jobs.containsKey(id)) {
DownloadList download = new DownloadList();
HttpVo vo = jobs.get(id);
download.setId(vo.getId());
download.setDbid("http_" + vo.getId());
download.setPercentDone(vo.getPercentDone());
download.setDone(vo.getDone());
download.setDownloadPath(vo.getPath());
download.setFileName(vo.getFilename());
download.setName(vo.getName());
if (vo.getDone()) {
jobs.remove(vo.getId());
}
return download;
}
return null;
}
}
19
View Source File : TodoCollaborationService.java
License : Apache License 2.0
Project Creator : stratospheric-dev
License : Apache License 2.0
Project Creator : stratospheric-dev
@Service
@Transactional
public clreplaced TodoCollaborationService {
private final TodoRepository todoRepository;
private final PersonRepository personRepository;
private final TodoCollaborationRequestRepository todoCollaborationRequestRepository;
private final QueueMessagingTemplate queueMessagingTemplate;
private final String todoSharingQueueName;
private final SimpMessagingTemplate simpMessagingTemplate;
private static final Logger LOG = LoggerFactory.getLogger(TodoCollaborationService.clreplaced.getName());
private static final String INVALID_TODO_ID = "Invalid todo ID: ";
private static final String INVALID_PERSON_ID = "Invalid person ID: ";
public TodoCollaborationService(@Value("${custom.sharing-queue}") String todoSharingQueueName, TodoRepository todoRepository, PersonRepository personRepository, TodoCollaborationRequestRepository todoCollaborationRequestRepository, QueueMessagingTemplate queueMessagingTemplate, SimpMessagingTemplate simpMessagingTemplate) {
this.todoRepository = todoRepository;
this.personRepository = personRepository;
this.todoCollaborationRequestRepository = todoCollaborationRequestRepository;
this.queueMessagingTemplate = queueMessagingTemplate;
this.todoSharingQueueName = todoSharingQueueName;
this.simpMessagingTemplate = simpMessagingTemplate;
}
public String shareWithCollaborator(String todoOwnerEmail, Long todoId, Long collaboratorId) {
Todo todo = todoRepository.findByIdAndOwnerEmail(todoId, todoOwnerEmail).orElseThrow(() -> new IllegalArgumentException(INVALID_TODO_ID + todoId));
Person collaborator = personRepository.findById(collaboratorId).orElseThrow(() -> new IllegalArgumentException(INVALID_PERSON_ID + collaboratorId));
if (todoCollaborationRequestRepository.findByTodoAndCollaborator(todo, collaborator) != null) {
LOG.info("Collaboration request for todo {} with collaborator {} already exists", todoId, collaboratorId);
return collaborator.getName();
}
LOG.info("About to share todo with id {} with collaborator {}", todoId, collaboratorId);
TodoCollaborationRequest collaboration = new TodoCollaborationRequest();
String token = UUID.randomUUID().toString();
collaboration.setToken(token);
collaboration.setCollaborator(collaborator);
collaboration.setTodo(todo);
todo.getCollaborationRequests().add(collaboration);
todoCollaborationRequestRepository.save(collaboration);
queueMessagingTemplate.convertAndSend(todoSharingQueueName, new TodoCollaborationNotification(collaboration));
return collaborator.getName();
}
public boolean confirmCollaboration(Long todoId, Long collaboratorId, String token) {
TodoCollaborationRequest collaborationRequest = todoCollaborationRequestRepository.findByTodoIdAndCollaboratorId(todoId, collaboratorId);
LOG.info("Collaboration request: {}", collaborationRequest);
if (collaborationRequest != null) {
LOG.info("Original collaboration token: {}", collaborationRequest.getToken());
LOG.info("Request token: {}", token);
}
if (collaborationRequest != null && collaborationRequest.getToken().equals(token)) {
Todo todo = todoRepository.findById(todoId).orElseThrow(() -> new IllegalArgumentException(INVALID_TODO_ID + todoId));
Person collaborator = personRepository.findById(collaboratorId).orElseThrow(() -> new IllegalArgumentException(INVALID_PERSON_ID + collaboratorId));
todo.addCollaborator(collaborator);
todoCollaborationRequestRepository.delete(collaborationRequest);
String name = collaborationRequest.getCollaborator().getName();
String subject = "Collaboration confirmed.";
String message = "User " + name + " has accepted your collaboration request for todo #" + collaborationRequest.getTodo().getId() + ".";
String ownerEmail = collaborationRequest.getTodo().getOwner().getEmail();
simpMessagingTemplate.convertAndSend("/topic/todoUpdates/" + ownerEmail, subject + " " + message);
LOG.info("Successfully informed owner about accepted request.");
return true;
}
return false;
}
}
19
View Source File : CalendarWebSocket.java
License : Apache License 2.0
Project Creator : speedment
License : Apache License 2.0
Project Creator : speedment
/**
* @author Emil Forslund
* @since 1.0.0
*/
@Component
public final clreplaced CalendarWebSocket {
@Autowired
private BookingView view;
@Autowired
private SimpMessagingTemplate template;
@PostConstruct
void listenForChanges() {
view.addAcceptedListener(this::pushNotification);
view.addRefusedListener(this::pushNotification);
}
private void pushNotification(BookingConfirmation notification) {
template.convertAndSend("/calendar", notification);
}
}
19
View Source File : WebSocketConsumersManager.java
License : MIT License
Project Creator : SourceLabOrg
License : MIT License
Project Creator : SourceLabOrg
/**
* Manages background kafka consumers and transfers consumed messages from them to their
* corresponding WebSocket connections.
*/
public clreplaced WebSocketConsumersManager implements Runnable {
private static final Logger logger = LoggerFactory.getLogger(WebSocketConsumersManager.clreplaced);
/**
* Holds a map of ConsumerKey to ConsumerEntry, which is basically a container
* for the running consumers.
*/
private final Map<ConsumerKey, ConsumerEntry> consumers = new ConcurrentHashMap<>();
/**
* For creating new consumers.
*/
private final WebKafkaConsumerFactory webKafkaConsumerFactory;
/**
* For sending responses to connected client.
*/
private final SimpMessagingTemplate simpMessagingTemplate;
/**
* Thread pool where we run consumers within background threads.
*/
private final ThreadPoolExecutor threadPoolExecutor;
/**
* Constructor.
* @param webKafkaConsumerFactory For creating new Consumers.
* @param messagingTemplate For publishing consumed messages back through the web socket.
* @param maxConcurrentConsumers Configuration, how many consumers to run.
*/
public WebSocketConsumersManager(final WebKafkaConsumerFactory webKafkaConsumerFactory, final SimpMessagingTemplate messagingTemplate, final int maxConcurrentConsumers) {
this(webKafkaConsumerFactory, messagingTemplate, // Setup managed thread pool with number of concurrent threads.
new ThreadPoolExecutor(maxConcurrentConsumers, maxConcurrentConsumers, 5, TimeUnit.MINUTES, new LinkedBlockingQueue<>(100)));
}
/**
* Constructor for injecting a ThreadPoolExecutor.
*
* @param webKafkaConsumerFactory For creating new Consumers.
* @param messagingTemplate For publishing consumed messages back through the web socket.
* @param threadPoolExecutor executor pool for async processing.
*/
public WebSocketConsumersManager(final WebKafkaConsumerFactory webKafkaConsumerFactory, final SimpMessagingTemplate messagingTemplate, final ThreadPoolExecutor threadPoolExecutor) {
this.webKafkaConsumerFactory = webKafkaConsumerFactory;
this.simpMessagingTemplate = messagingTemplate;
// TODO add handler for when a new connection comes in that exceeds the maximum running concurrent consumers.
this.threadPoolExecutor = threadPoolExecutor;
}
/**
* Start up a new consumer for the given view.
* @param view The view to consume from
* @param startingPosition What position to resume consuming from.
* @param sessionIdentifier The user who is consuming.
*/
public void addNewConsumer(final View view, final Collection<FilterDefinition> filters, final StartingPosition startingPosition, final SessionIdentifier sessionIdentifier) {
synchronized (consumers) {
// createWebClient a key
final ConsumerKey consumerKey = new ConsumerKey(view.getId(), sessionIdentifier);
if (consumers.containsKey(consumerKey)) {
// TODO handle better
throw new RuntimeException("Consumer already exists!");
}
// Create consumer
final SocketKafkaConsumer webKafkaConsumer = webKafkaConsumerFactory.createWebSocketClient(view, filters, startingPosition, sessionIdentifier);
// Create entry
final ConsumerEntry consumerEntry = new ConsumerEntry(webKafkaConsumer);
consumers.put(consumerKey, consumerEntry);
// Toss into executor
threadPoolExecutor.execute(webKafkaConsumer);
// Add logger statement
logger.info("Added new web socket consumer, now has {}/{} running consumers", threadPoolExecutor.getActiveCount(), threadPoolExecutor.getMaximumPoolSize());
}
}
/**
* Remove consumer based on their private session id.
* Typically this is called when a consumer disconnects from the websocket.
*/
public void removeConsumersForSessionId(final String sessionId) {
synchronized (consumers) {
consumers.entrySet().stream().filter((entry) -> entry.getKey().getSessionId().equals(sessionId)).forEach((entry) -> entry.getValue().requestStop());
}
}
/**
* Remove consumer based on their public session hash.
* Typically this is called when a request to disconnect a consumer is made by the consumer manager
* web UI.
*/
public boolean removeConsumersForSessionHash(final String sessionHash) {
synchronized (consumers) {
for (final Map.Entry<ConsumerKey, ConsumerEntry> entry : consumers.entrySet()) {
if (!entry.getKey().getSessionHash().equals(sessionHash)) {
continue;
}
entry.getValue().requestStop();
return true;
}
}
return false;
}
/**
* Pause a consumer.
*/
public void pauseConsumer(final long viewId, final SessionIdentifier sessionIdentifier) {
// createWebClient a key
final ConsumerKey consumerKey = new ConsumerKey(viewId, sessionIdentifier);
synchronized (consumers) {
if (!consumers.containsKey(consumerKey)) {
return;
}
// Get entry
final ConsumerEntry consumerEntry = consumers.get(consumerKey);
// Lets pause it
consumerEntry.requestPause();
}
}
/**
* Resume a consumer.
*/
public void resumeConsumer(final long viewId, final SessionIdentifier sessionIdentifier) {
synchronized (consumers) {
// createWebClient a key
final ConsumerKey consumerKey = new ConsumerKey(viewId, sessionIdentifier);
if (!consumers.containsKey(consumerKey)) {
return;
}
// Get entry
final ConsumerEntry consumerEntry = consumers.get(consumerKey);
// Lets pause it
consumerEntry.requestResume();
}
}
/**
* @return Returns all of the currently active consumers.
*/
public Collection<StreamConsumerDetails> getConsumers() {
final Collection<StreamConsumerDetails> details = consumers.entrySet().stream().map((entry) -> new StreamConsumerDetails(entry.getKey().getUserId(), entry.getKey().getViewId(), entry.getKey().getSessionHash(), entry.getValue().getStartTimestamp(), entry.getValue().getRecordCount(), entry.getValue().isPaused())).collect(Collectors.toList());
// Return immutable
return Collections.unmodifiableCollection(details);
}
/**
* @return Current number of active consumers.
*/
public int countActiveConsumers() {
return consumers.size();
}
/**
* Main processing loop for the Manager.
*/
@Override
public void run() {
// Loop thru consumers, consume, and publish to socket.
do {
boolean foundResult = false;
final List<ConsumerKey> consumerKeysToRemove = new ArrayList<>();
// Loop over each consumer
for (final Map.Entry<ConsumerKey, ConsumerEntry> entry : consumers.entrySet()) {
try {
final ConsumerKey consumerKey = entry.getKey();
final ConsumerEntry consumerEntry = entry.getValue();
if (consumerEntry.isShouldStop()) {
// Add to remove list
consumerKeysToRemove.add(consumerKey);
continue;
}
// Consume
final Optional<KafkaResult> kafkaResult = consumerEntry.nextResult();
if (!kafkaResult.isPresent()) {
continue;
}
// Flip flag to true
foundResult = true;
// publish
final String target = "/topic/view/" + consumerKey.getViewId() + "/" + consumerKey.getUserId();
// Define header so we can send the message to a specific session id.
final SimpMessageHeaderAccessor headerAccessor = SimpMessageHeaderAccessor.create(SimpMessageType.MESSAGE);
headerAccessor.setSessionId(consumerKey.getSessionId());
headerAccessor.setLeaveMutable(true);
// Only send it to the specific user's sesison Id.
simpMessagingTemplate.convertAndSendToUser(consumerKey.getSessionId(), target, kafkaResult.get(), headerAccessor.getMessageHeaders());
} catch (final Exception exception) {
// Handle
logger.error(exception.getMessage(), exception);
}
}
// Remove any consumers
for (final ConsumerKey consumerKey : consumerKeysToRemove) {
consumers.remove(consumerKey);
// Add logger statement, this isn't completely accurate because the thread
// may not have shut down yet..
logger.info("Removed web socket consumer, now has ~ {}/{} running consumers", threadPoolExecutor.getActiveCount(), threadPoolExecutor.getMaximumPoolSize());
}
// Throttle with sleep
if (!foundResult) {
try {
Thread.sleep(500L);
} catch (final InterruptedException e) {
break;
}
}
} while (true);
// Shut down
threadPoolExecutor.shutdown();
}
/**
* Small wrapper around the Socket Consumer.
*/
private static final clreplaced ConsumerEntry {
/**
* Our wrapped SocketKafkaConsumer instance.
*/
private final SocketKafkaConsumer socketKafkaConsumer;
/**
* Holds how many records we have consumed.
*/
private final AtomicLong recordCount = new AtomicLong(0);
/**
* Holds when we started consuming.
*/
private final long startTimestamp = Clock.systemUTC().millis();
/**
* Flag if we should requestStop.
*/
private boolean shouldStop = false;
/**
* Flag if we should be paused.
*/
private AtomicBoolean isPaused = new AtomicBoolean(false);
/**
* Constructor.
* @param socketKafkaConsumer The consumer to wrap.
*/
public ConsumerEntry(final SocketKafkaConsumer socketKafkaConsumer) {
this.socketKafkaConsumer = socketKafkaConsumer;
}
/**
* Retrieve the next record from Kafka.
* @return Optional of KafkaResult. This could return null if there are no new records to consume.
*/
public Optional<KafkaResult> nextResult() {
// If paused
if (isPaused.get()) {
// always return false. This will cause the internal buffer to block
// on the consumer side.
return Optional.empty();
}
final Optional<KafkaResult> result = socketKafkaConsumer.nextResult();
// Increment counter if record returned.
result.ifPresent((record) -> recordCount.incrementAndGet());
// Return result
return result;
}
/**
* @return True if a stop has been requested.
*/
public synchronized boolean isShouldStop() {
return shouldStop;
}
/**
* Request the Consumer to shutdown/stop.
*/
public synchronized void requestStop() {
this.socketKafkaConsumer.requestStop();
this.shouldStop = true;
}
/**
* Request the consumer to be paused.
*/
public synchronized void requestPause() {
isPaused.set(true);
}
/**
* Request the consumer to be resumed.
*/
public synchronized void requestResume() {
isPaused.set(false);
}
public long getRecordCount() {
return recordCount.get();
}
public long getStartTimestamp() {
return startTimestamp;
}
public boolean isPaused() {
return isPaused.get();
}
}
/**
* Represents a unique consumer key.
* This could probably simplified down to just the sessionId.
*/
static final clreplaced ConsumerKey {
// viewId, userId, and sessionId make a unique consumer key.
private final long viewId;
private final long userId;
// Session id should be considered private and should not be shared with other users.
// TODO probably should deprecate this.
private final String sessionId;
// Session hash can be shared publicly to identify a session.
private final String sessionHash;
ConsumerKey(final long viewId, final SessionIdentifier sessionIdentifier) {
this.viewId = viewId;
this.userId = sessionIdentifier.getUserId();
this.sessionId = sessionIdentifier.getSessionId();
this.sessionHash = Sha1Tools.sha1(this.sessionId);
}
public long getViewId() {
return viewId;
}
public long getUserId() {
return userId;
}
public String getSessionId() {
return sessionId;
}
public String getSessionHash() {
return sessionHash;
}
@Override
public boolean equals(final Object other) {
if (this == other) {
return true;
}
if (other == null || getClreplaced() != other.getClreplaced()) {
return false;
}
final ConsumerKey that = (ConsumerKey) other;
if (viewId != that.viewId) {
return false;
}
if (userId != that.userId) {
return false;
}
return sessionId.equals(that.sessionId);
}
@Override
public int hashCode() {
int result = (int) (viewId ^ (viewId >>> 32));
result = 31 * result + (int) (userId ^ (userId >>> 32));
result = 31 * result + sessionId.hashCode();
return result;
}
}
}
19
View Source File : ExchangePushJob.java
License : MIT License
Project Creator : sengeiou
License : MIT License
Project Creator : sengeiou
@Component
public clreplaced ExchangePushJob {
@Autowired
private SimpMessagingTemplate messagingTemplate;
@Autowired
private NettyHandler nettyHandler;
private Map<String, List<ExchangeTrade>> tradesQueue = new HashMap<>();
private Map<String, List<TradePlate>> plateQueue = new HashMap<>();
private Map<String, List<CoinThumb>> thumbQueue = new HashMap<>();
public void addTrades(String symbol, List<ExchangeTrade> trades) {
List<ExchangeTrade> list = tradesQueue.get(symbol);
if (list == null) {
list = new ArrayList<>();
tradesQueue.put(symbol, list);
}
synchronized (list) {
list.addAll(trades);
}
}
public void addPlates(String symbol, TradePlate plate) {
List<TradePlate> list = plateQueue.get(symbol);
if (list == null) {
list = new ArrayList<>();
plateQueue.put(symbol, list);
}
synchronized (list) {
list.add(plate);
}
}
public void addThumb(String symbol, CoinThumb thumb) {
List<CoinThumb> list = thumbQueue.get(symbol);
if (list == null) {
list = new ArrayList<>();
thumbQueue.put(symbol, list);
}
synchronized (list) {
list.add(thumb);
}
}
@Scheduled(fixedRate = 500)
public void pushTrade() {
Iterator<Map.Entry<String, List<ExchangeTrade>>> entryIterator = tradesQueue.entrySet().iterator();
while (entryIterator.hasNext()) {
Map.Entry<String, List<ExchangeTrade>> entry = entryIterator.next();
String symbol = entry.getKey();
List<ExchangeTrade> trades = entry.getValue();
if (trades.size() > 0) {
synchronized (trades) {
messagingTemplate.convertAndSend("/topic/market/trade/" + symbol, trades);
trades.clear();
}
}
}
}
@Scheduled(fixedRate = 500)
public void pushPlate() {
Iterator<Map.Entry<String, List<TradePlate>>> entryIterator = plateQueue.entrySet().iterator();
while (entryIterator.hasNext()) {
Map.Entry<String, List<TradePlate>> entry = entryIterator.next();
String symbol = entry.getKey();
List<TradePlate> plates = entry.getValue();
if (plates.size() > 0) {
boolean hasPushAskPlate = false;
boolean hasPushBidPlate = false;
synchronized (plates) {
for (TradePlate plate : plates) {
if (plate.getDirection() == ExchangeOrderDirection.BUY && !hasPushBidPlate) {
hasPushBidPlate = true;
} else if (plate.getDirection() == ExchangeOrderDirection.SELL && !hasPushAskPlate) {
hasPushAskPlate = true;
} else {
continue;
}
// websocket推送盘口信息
messagingTemplate.convertAndSend("/topic/market/trade-plate/" + symbol, plate.toJSON(24));
// websocket推送深度信息
messagingTemplate.convertAndSend("/topic/market/trade-depth/" + symbol, plate.toJSON());
// netty推送
nettyHandler.handlePlate(symbol, plate);
}
plates.clear();
}
}
}
}
@Scheduled(fixedRate = 500)
public void pushThumb() {
Iterator<Map.Entry<String, List<CoinThumb>>> entryIterator = thumbQueue.entrySet().iterator();
while (entryIterator.hasNext()) {
Map.Entry<String, List<CoinThumb>> entry = entryIterator.next();
String symbol = entry.getKey();
List<CoinThumb> thumbs = entry.getValue();
if (thumbs.size() > 0) {
synchronized (thumbs) {
messagingTemplate.convertAndSend("/topic/market/thumb", thumbs.get(thumbs.size() - 1));
thumbs.clear();
}
}
}
}
}
19
View Source File : ExchangeTradeConsumer.java
License : MIT License
Project Creator : sengeiou
License : MIT License
Project Creator : sengeiou
@Component
@Slf4j
public clreplaced ExchangeTradeConsumer {
private Logger logger = LoggerFactory.getLogger(ExchangeTradeConsumer.clreplaced);
@Autowired
private CoinProcessorFactory coinProcessorFactory;
@Autowired
private SimpMessagingTemplate messagingTemplate;
@Autowired
private ExchangeOrderService exchangeOrderService;
@Autowired
private NettyHandler nettyHandler;
@Value("${second.referrer.award}")
private boolean secondReferrerAward;
private ExecutorService executor = new ThreadPoolExecutor(30, 100, 0L, TimeUnit.MILLISECONDS, new LinkedBlockingQueue<Runnable>(1024), new ThreadPoolExecutor.AbortPolicy());
@Autowired
private ExchangePushJob pushJob;
/**
* 处理成交明细
*
* @param records
*/
@KafkaListener(topics = "exchange-trade", containerFactory = "kafkaListenerContainerFactory")
public void handleTrade(List<ConsumerRecord<String, String>> records) {
for (int i = 0; i < records.size(); i++) {
ConsumerRecord<String, String> record = records.get(i);
executor.submit(new HandleTradeThread(record));
}
}
@KafkaListener(topics = "exchange-order-completed", containerFactory = "kafkaListenerContainerFactory")
public void handleOrderCompleted(List<ConsumerRecord<String, String>> records) {
try {
for (int i = 0; i < records.size(); i++) {
ConsumerRecord<String, String> record = records.get(i);
logger.info("订单交易处理完成消息topic={},value={}", record.topic(), record.value());
List<ExchangeOrder> orders = JSON.parseArray(record.value(), ExchangeOrder.clreplaced);
for (ExchangeOrder order : orders) {
String symbol = order.getSymbol();
// 委托成交完成处理
exchangeOrderService.tradeCompleted(order.getOrderId(), order.getTradedAmount(), order.getTurnover());
// 推送订单成交
messagingTemplate.convertAndSend("/topic/market/order-completed/" + symbol + "/" + order.getMemberId(), order);
nettyHandler.handleOrder(NettyCommand.PUSH_EXCHANGE_ORDER_COMPLETED, order);
}
}
} catch (Exception e) {
e.printStackTrace();
}
}
/**
* 处理模拟交易
*
* @param records
*/
@KafkaListener(topics = "exchange-trade-mocker", containerFactory = "kafkaListenerContainerFactory")
public void handleMockerTrade(List<ConsumerRecord<String, String>> records) {
try {
for (int i = 0; i < records.size(); i++) {
ConsumerRecord<String, String> record = records.get(i);
logger.info("mock数据topic={},value={},size={}", record.topic(), record.value(), records.size());
List<ExchangeTrade> trades = JSON.parseArray(record.value(), ExchangeTrade.clreplaced);
String symbol = trades.get(0).getSymbol();
// 处理行情
CoinProcessor coinProcessor = coinProcessorFactory.getProcessor(symbol);
if (coinProcessor != null) {
coinProcessor.process(trades);
}
pushJob.addTrades(symbol, trades);
}
} catch (Exception e) {
e.printStackTrace();
}
}
/**
* 消费交易盘口信息
*
* @param records
*/
@KafkaListener(topics = "exchange-trade-plate", containerFactory = "kafkaListenerContainerFactory")
public void handleTradePlate(List<ConsumerRecord<String, String>> records) {
try {
for (int i = 0; i < records.size(); i++) {
ConsumerRecord<String, String> record = records.get(i);
logger.info("推送盘口信息topic={},value={},size={}", record.topic(), record.value(), records.size());
TradePlate plate = JSON.parseObject(record.value(), TradePlate.clreplaced);
String symbol = plate.getSymbol();
pushJob.addPlates(symbol, plate);
}
} catch (Exception e) {
e.printStackTrace();
}
}
/**
* 订单取消成功
*
* @param records
*/
@KafkaListener(topics = "exchange-order-cancel-success", containerFactory = "kafkaListenerContainerFactory")
public void handleOrderCanceled(List<ConsumerRecord<String, String>> records) {
try {
for (int i = 0; i < records.size(); i++) {
ConsumerRecord<String, String> record = records.get(i);
logger.info("取消订单消息topic={},value={},size={}", record.topic(), record.value(), records.size());
ExchangeOrder order = JSON.parseObject(record.value(), ExchangeOrder.clreplaced);
String symbol = order.getSymbol();
// 调用服务处理
exchangeOrderService.cancelOrder(order.getOrderId(), order.getTradedAmount(), order.getTurnover());
// 推送实时成交
messagingTemplate.convertAndSend("/topic/market/order-canceled/" + symbol + "/" + order.getMemberId(), order);
nettyHandler.handleOrder(NettyCommand.PUSH_EXCHANGE_ORDER_CANCELED, order);
}
} catch (Exception e) {
e.printStackTrace();
}
}
public clreplaced HandleTradeThread implements Runnable {
private ConsumerRecord<String, String> record;
private HandleTradeThread(ConsumerRecord<String, String> record) {
this.record = record;
}
@Override
public void run() {
logger.info("topic={},value={}", record.topic(), record.value());
try {
List<ExchangeTrade> trades = JSON.parseArray(record.value(), ExchangeTrade.clreplaced);
String symbol = trades.get(0).getSymbol();
CoinProcessor coinProcessor = coinProcessorFactory.getProcessor(symbol);
for (ExchangeTrade trade : trades) {
// 成交明细处理
exchangeOrderService.processExchangeTrade(trade, secondReferrerAward);
// 推送订单成交订阅
ExchangeOrder buyOrder = exchangeOrderService.findOne(trade.getBuyOrderId());
ExchangeOrder sellOrder = exchangeOrderService.findOne(trade.getSellOrderId());
messagingTemplate.convertAndSend("/topic/market/order-trade/" + symbol + "/" + buyOrder.getMemberId(), buyOrder);
messagingTemplate.convertAndSend("/topic/market/order-trade/" + symbol + "/" + sellOrder.getMemberId(), sellOrder);
nettyHandler.handleOrder(NettyCommand.PUSH_EXCHANGE_ORDER_TRADE, buyOrder);
nettyHandler.handleOrder(NettyCommand.PUSH_EXCHANGE_ORDER_TRADE, sellOrder);
}
// 处理K线行情
if (coinProcessor != null) {
coinProcessor.process(trades);
}
pushJob.addTrades(symbol, trades);
} catch (Exception e) {
e.printStackTrace();
}
}
}
}
19
View Source File : NettyHandler.java
License : MIT License
Project Creator : sengeiou
License : MIT License
Project Creator : sengeiou
/**
* 处理Netty订阅与取消订阅
*/
@HawkBean
public clreplaced NettyHandler {
@Autowired
private HawkPushServiceApi hawkPushService;
@Autowired
private OrderService orderService;
@Autowired
private MessageHandler chatMessageHandler;
@Autowired
private SimpMessagingTemplate messagingTemplate;
@Autowired
private ApnsHandler apnsHandler;
public void subscribeTopic(Channel channel, String topic) {
String userKey = channel.id().asLongText();
NettyCacheUtils.keyChannelCache.put(channel, userKey);
NettyCacheUtils.storeChannel(topic, channel);
if (NettyCacheUtils.userKey.containsKey(userKey)) {
NettyCacheUtils.userKey.get(userKey).add(topic);
} else {
Set<String> userkeys = new HashSet<>();
userkeys.add(topic);
NettyCacheUtils.userKey.put(userKey, userkeys);
}
}
public void unsubscribeTopic(Channel channel, String topic) {
String userKey = channel.id().asLongText();
if (NettyCacheUtils.userKey.containsKey(userKey)) {
NettyCacheUtils.userKey.get(userKey).remove(topic);
}
NettyCacheUtils.keyChannelCache.remove(channel);
}
/*@HawkMethod(cmd = NettyCommand.SUBSCRIBE_CHAT,version = NettyCommand.COMMANDS_VERSION)
public QuoteMessage.SimpleResponse subscribeChat(byte[] body, ChannelHandlerContext ctx){
JSONObject json = JSON.parseObject(new String(body));
System.out.println("订阅:"+json.toJSONString());
QuoteMessage.SimpleResponse.Builder response = QuoteMessage.SimpleResponse.newBuilder();
String orderId = json.getString("orderId");
String uid = json.getString("uid");
if(StringUtils.isEmpty(uid) || StringUtils.isEmpty(orderId)){
response.setCode(500).setMessage("订阅失败,参数错误");
}
else {
String key = orderId + "-" + uid;
subscribeTopic(ctx.channel(),key);
response.setCode(0).setMessage("订阅成功");
}
return response.build();
}*/
@HawkMethod(cmd = NettyCommand.SUBSCRIBE_GROUP_CHAT)
public QuoteMessage.SimpleResponse subscribeGroupChat(byte[] body, ChannelHandlerContext ctx) {
JSONObject json = JSON.parseObject(new String(body));
System.out.println("订阅GroupChat:" + json.toJSONString());
QuoteMessage.SimpleResponse.Builder response = QuoteMessage.SimpleResponse.newBuilder();
String uid = json.getString("uid");
if (StringUtils.isEmpty(uid)) {
response.setCode(500).setMessage("订阅失败,参数错误");
} else {
String key = uid;
subscribeTopic(ctx.channel(), key);
response.setCode(0).setMessage("订阅成功");
}
return response.build();
}
/*@HawkMethod(cmd = NettyCommand.UNSUBSCRIBE_CHAT)
public QuoteMessage.SimpleResponse unsubscribeChat(byte[] body, ChannelHandlerContext ctx){
System.out.println(ctx.channel().id());
JSONObject json = JSON.parseObject(new String(body));
String orderId = json.getString("orderId");
String uid = json.getString("uid");
String key = orderId+"-"+uid;
unsubscribeTopic(ctx.channel(),key);
apnsHandler.removeToken(uid);
QuoteMessage.SimpleResponse.Builder response = QuoteMessage.SimpleResponse.newBuilder();
response.setCode(0).setMessage("取消订阅成功");
return response.build();
}*/
@HawkMethod(cmd = NettyCommand.UNSUBSCRIBE_GROUP_CHAT)
public QuoteMessage.SimpleResponse unsubscribeGroupChat(byte[] body, ChannelHandlerContext ctx) {
JSONObject json = JSON.parseObject(new String(body));
String uid = json.getString("uid");
String key = uid;
unsubscribeTopic(ctx.channel(), key);
apnsHandler.removeToken(uid);
QuoteMessage.SimpleResponse.Builder response = QuoteMessage.SimpleResponse.newBuilder();
response.setCode(0).setMessage("取消订阅成功");
return response.build();
}
@HawkMethod(cmd = NettyCommand.SUBSCRIBE_APNS)
public QuoteMessage.SimpleResponse subscribeApns(byte[] body, ChannelHandlerContext ctx) {
JSONObject json = JSON.parseObject(new String(body));
System.out.println("订阅APNS推送:" + json.toJSONString());
QuoteMessage.SimpleResponse.Builder response = QuoteMessage.SimpleResponse.newBuilder();
String token = json.getString("token");
String uid = json.getString("uid");
if (StringUtils.isEmpty(uid) || StringUtils.isEmpty(token)) {
response.setCode(500).setMessage("订阅失败,参数错误");
} else {
apnsHandler.setToken(uid, token);
response.setCode(0).setMessage("订阅成功");
}
return response.build();
}
@HawkMethod(cmd = NettyCommand.UNSUBSCRIBE_APNS)
public QuoteMessage.SimpleResponse unsubscribeApns(byte[] body, ChannelHandlerContext ctx) {
JSONObject json = JSON.parseObject(new String(body));
System.out.println("取消订阅APNS推送:" + json.toJSONString());
String uid = json.getString("uid");
apnsHandler.removeToken(uid);
QuoteMessage.SimpleResponse.Builder response = QuoteMessage.SimpleResponse.newBuilder();
response.setCode(0).setMessage("取消订阅成功");
return response.build();
}
@HawkMethod(cmd = NettyCommand.SEND_CHAT)
public QuoteMessage.SimpleResponse sendMessage(byte[] body, ChannelHandlerContext ctx) {
System.out.println("发送消息:" + new String(body));
RealTimeChatMessage message = JSON.parseObject(new String(body), RealTimeChatMessage.clreplaced);
handleMessage(message);
QuoteMessage.SimpleResponse.Builder response = QuoteMessage.SimpleResponse.newBuilder();
response.setCode(0).setMessage("发送成功");
return response.build();
}
/**
* 推送消息
* @param key
* @param result
*/
public void push(String key, Object result, short command) {
byte[] body = JSON.toJSONString(result).getBytes();
Set<Channel> channels = NettyCacheUtils.getChannel(key);
if (channels != null && channels.size() > 0) {
System.out.println("下发消息:key=" + key + ",result=" + JSON.toJSONString(result) + ",channel size=" + channels.size());
hawkPushService.pushMsg(channels, command, body);
}
}
public void handleMessage(RealTimeChatMessage message) {
if (message.getMessageType() == MessageTypeEnum.NOTICE) {
Order order = orderService.findOneByOrderId(message.getOrderId());
ConfirmResult result = new ConfirmResult(message.getContent(), order.getStatus().getOrdinal());
result.setUidFrom(message.getUidFrom());
result.setOrderId(message.getOrderId());
result.setNameFrom(message.getNameFrom());
// push(message.getOrderId() + "-" + message.getUidTo(),result,NettyCommand.PUSH_CHAT);
push(message.getUidTo(), result, NettyCommand.PUSH_GROUP_CHAT);
messagingTemplate.convertAndSendToUser(message.getUidTo(), "/order-notice/" + message.getOrderId(), result);
} else if (message.getMessageType() == MessageTypeEnum.NORMAL_CHAT) {
ChatMessageRecord chatMessageRecord = new ChatMessageRecord();
BeanUtils.copyProperties(message, chatMessageRecord);
chatMessageRecord.setSendTime(DateUtils.getCurrentDate().getTime());
chatMessageRecord.setFromAvatar(message.getAvatar());
// 聊天消息保存到mogondb
chatMessageHandler.handleMessage(chatMessageRecord);
chatMessageRecord.setSendTimeStr(DateUtils.getDateStr(chatMessageRecord.getSendTime()));
// 发送给指定用户(客户端订阅路径:/user/+uid+/+key)
push(message.getUidTo(), chatMessageRecord, NettyCommand.PUSH_GROUP_CHAT);
// push(message.getOrderId() + "-" + message.getUidTo(),chatMessageRecord,NettyCommand.PUSH_CHAT);
apnsHandler.handleMessage(message.getUidTo(), chatMessageRecord);
messagingTemplate.convertAndSendToUser(message.getUidTo(), "/" + message.getOrderId(), chatMessageRecord);
}
}
}
19
View Source File : MachineStatusHandler.java
License : MIT License
Project Creator : qmdx00
License : MIT License
Project Creator : qmdx00
/**
* @author yuanweimin
* @date 19/06/13 10:54
* @description 机器设备实时数据的消息处理类
*/
@Slf4j
@Component
public clreplaced MachineStatusHandler implements MessageHandler {
private final MachineStatusService machineStatusService;
private final MachineService machineService;
private final SimpMessagingTemplate template;
@Autowired
public MachineStatusHandler(SimpMessagingTemplate template, MachineService machineService, MachineStatusService machineStatusService) {
this.template = template;
this.machineService = machineService;
this.machineStatusService = machineStatusService;
}
@Override
public synchronized void handle(long msgId, String msgBody) {
// 封装成 Message 实体
Message msg = MessageUtil.replacedysis(msgId, msgBody);
// log.info("receive machine status: {}", msg);
// 映射成 MachineStatus 实体类对象
MachineStatus status = translate(msg.getDeviceId(), msg.getTimestamp(), msg.getBody());
// 保存状态数据到数据库中
machineStatusService.saveStatus(status);
// 转发到前端 websocket 中
template.convertAndSend("/topic/msg", status);
}
/**
* 将一条数据流转换成状态数据实体,并生成机器设备信息
*
* @param deviceId 设备 ID
* @param timeStamp 数据上传的时间戳
* @param body 类型的值
* @return MachineStatus
*/
private MachineStatus translate(String deviceId, String timeStamp, String body) {
// 如果设备信息不存在则根据deviceID创建,需要修改其它描述信息
Machine machine = machineService.findMachineById(deviceId);
if (machine == null) {
machineService.saveMachine(Machine.builder().machineId(deviceId).build());
}
// 数据串解析为 Map
Map<String, String> map = Arrays.stream(body.split("-")).map(et -> et.split("@")).filter(et -> et.length == 2).collect(Collectors.toMap(et -> et[0], et -> et[1]));
// 构建 MachineStatus 对象
return MachineStatus.builder().statusId(UUIDUtil.getUUID()).machineId(deviceId).createTime(TimeUtil.toDate(timeStamp)).temperature(map.get("TM")).temperatureWarn(map.get("TR")).fan(map.get("FA")).humidity(map.get("HU")).humidityWarn(map.get("HR")).voltage(map.get("VO")).electric(map.get("CU")).power(map.get("PO")).weight(map.get("WE")).weightWarn(map.get("WR")).motorOpen(map.get("MW")).motorSpeed(map.get("MP")).motorDir(map.get("MI")).slideOpen(map.get("TW")).slideDir(map.get("TD")).slideSpeed(map.get("TS")).rodDistance(map.get("PD")).machineError(map.get("ME")).reservedA(map.get("RA")).reservedB(map.get("RB")).reservedC(map.get("RC")).reservedD(map.get("RD")).build();
}
}
19
View Source File : ServerController.java
License : Apache License 2.0
Project Creator : pro-cloud
License : Apache License 2.0
Project Creator : pro-cloud
@RestController
@RequestMapping("/serverv")
public clreplaced ServerController {
@Autowired
private SimpMessagingTemplate simpMessagingTemplate;
@GetMapping
public Result login() {
Server server = new Server();
List<Cpu> cpus = Lists.newArrayList();
Cpu cpu = new Cpu();
cpu.setKey("22");
cpu.setValue("444");
cpus.add(cpu);
server.setCpus(cpus);
simpMessagingTemplate.convertAndSend("/topic/server", JSONUtil.toJsonStr(server));
return Result.success("22");
}
@GetMapping("ai")
public Result loginv() {
Server server = new Server();
List<Cpu> cpus = Lists.newArrayList();
Cpu cpu = new Cpu();
cpu.setKey("272");
cpu.setValue("444");
cpus.add(cpu);
server.setCpus(cpus);
simpMessagingTemplate.convertAndSendToUser("1", "/topic/server", JSONUtil.toJsonStr(server));
simpMessagingTemplate.convertAndSendToUser("3", "/topic/server", JSONUtil.toJsonStr(server));
return Result.success("22");
}
@GetMapping("aiv")
public Result loginvai() {
Server server = new Server();
List<Cpu> cpus = Lists.newArrayList();
Cpu cpu = new Cpu();
cpu.setKey("272");
cpu.setValue("444");
cpus.add(cpu);
server.setCpus(cpus);
simpMessagingTemplate.convertAndSendToUser("2", "/topic/server", JSONUtil.toJsonStr(server));
return Result.success("22");
}
}
19
View Source File : WebSocketController.java
License : MIT License
Project Creator : pram
License : MIT License
Project Creator : pram
@Controller
@Slf4j
public clreplaced WebSocketController {
private final SimpMessagingTemplate template;
@Autowired
WebSocketController(SimpMessagingTemplate template) {
this.template = template;
}
@Scheduled(fixedRate = 5000)
public void sendUpdate() {
String formattedDate = DateFormat.getTimeInstance().format(new Date());
log.debug("Sending Update {}", formattedDate);
this.template.convertAndSend("/topic/update", formattedDate);
}
@MessageMapping("/hello")
public String greeting(String message) throws Exception {
log.info("Message received {}", message);
return String.format("Hello %s ", message);
}
}
19
View Source File : ChatController.java
License : MIT License
Project Creator : PacktPublishing
License : MIT License
Project Creator : PacktPublishing
/**
* @author Greg Turnquist
*/
// tag::code[]
@Controller
public clreplaced ChatController {
private final SimpMessagingTemplate template;
public ChatController(SimpMessagingTemplate template) {
this.template = template;
}
// tag::newChatMessage[]
@MessageMapping("/chatMessage.new")
public void newChatMessage(String newChatMessage, Principal principal) {
if (newChatMessage.startsWith("@")) {
String user = newChatMessage.substring(0, newChatMessage.indexOf(" "));
String message = principal.getName() + "(direct): " + newChatMessage;
// Send message to target user
template.convertAndSendToUser(user.substring(1), "/queue/chatMessage.new", message);
// Send copy of message to user who wrote it
template.convertAndSendToUser(principal.getName(), "/queue/chatMessage.new", message);
} else {
String message = principal.getName() + "(channel): " + newChatMessage;
template.convertAndSend("/topic/chatMessage.new", message);
}
}
// end::newChatMessage[]
}
19
View Source File : GreetingController.java
License : Apache License 2.0
Project Creator : onblog
License : Apache License 2.0
Project Creator : onblog
/**
* Create by [email protected] 2018/6/19/019 23:49
*/
@Controller
public clreplaced GreetingController {
@Autowired
private SimpMessagingTemplate messagingTemplate;
@Autowired
private GcService gcService;
@Autowired
private ClreplacedService clreplacedService;
@Autowired
private ThreadService threadService;
@MessageMapping("/gc")
@SendTo("/topic/gc")
public List<GcEnreplacedy> socketGc(String name) {
return gcService.findAllByName(name);
}
@MessageMapping("/cl")
@SendTo("/topic/cl")
public List<ClreplacedLoadEnreplacedy> socketCl(String name) {
return clreplacedService.findAllByName(name);
}
@MessageMapping("/thread")
@SendTo("/topic/thread")
public List<ThreadEnreplacedy> socketThread(String name) {
return threadService.findAllByName(name);
}
}
19
View Source File : InfoController.java
License : MIT License
Project Creator : ocinpp
License : MIT License
Project Creator : ocinpp
/**
* Reference: https://docs.spring.io/spring/docs/current/spring-framework-reference/html/websocket.html
*/
@Controller
public clreplaced InfoController {
@Autowired
private SimpMessagingTemplate messageTemplate;
@Scheduled(fixedDelay = 10000)
public void priceManualConvert() throws Exception {
double val1 = (new BigDecimal(Math.random() * 1000 + "")).setScale(3, BigDecimal.ROUND_HALF_UP).doubleValue();
double val2 = (new BigDecimal(Math.random() * 1000 + "")).setScale(3, BigDecimal.ROUND_HALF_UP).doubleValue();
StockQuote stock1 = new StockQuote("Fantastic Food", val1);
StockQuote stock2 = new StockQuote("Marvellous Car", val2);
List<StockQuote> list = new ArrayList<>();
list.add(stock1);
list.add(stock2);
// convert from object to JSON
ObjectMapper mapper = new ObjectMapper();
String jsonInString = mapper.writeValuereplacedtring(list);
this.messageTemplate.convertAndSend("/stock/price", jsonInString);
}
@Scheduled(fixedDelay = 5000)
public void priceAutoConvert() throws Exception {
double val1 = (new BigDecimal(Math.random() * 1000 + "")).setScale(3, BigDecimal.ROUND_HALF_UP).doubleValue();
double val2 = (new BigDecimal(Math.random() * 1000 + "")).setScale(3, BigDecimal.ROUND_HALF_UP).doubleValue();
StockQuote stock1 = new StockQuote("Airplane 1", val1);
StockQuote stock2 = new StockQuote("Electricity", val2);
List<StockQuote> list = new ArrayList<>();
list.add(stock1);
list.add(stock2);
// convert from object to JSON
ObjectMapper mapper = new ObjectMapper();
String jsonInString = mapper.writeValuereplacedtring(list);
this.messageTemplate.convertAndSend("/stock/price-fast", jsonInString);
}
}
19
View Source File : TimeSender.java
License : MIT License
Project Creator : nielsutrecht
License : MIT License
Project Creator : nielsutrecht
@Component
@Slf4j
public clreplaced TimeSender {
private static final DateTimeFormatter TIME_FORMAT = DateTimeFormatter.ofPattern("HH:mm:ss");
@Autowired
private SimpMessagingTemplate broker;
@Autowired
public TimeSender(final SimpMessagingTemplate broker) {
this.broker = broker;
}
@Scheduled(fixedRate = 5000)
public void run() {
String time = LocalTime.now().format(TIME_FORMAT);
log.info("Time broadcast: {}", time);
broker.convertAndSend("/topic/greetings", new Greeting("Current time is " + time));
}
}
19
View Source File : WebSocketController.java
License : Apache License 2.0
Project Creator : mploed
License : Apache License 2.0
Project Creator : mploed
@Controller
public clreplaced WebSocketController {
private SimpMessagingTemplate template;
@Autowired
public WebSocketController(SimpMessagingTemplate template) {
this.template = template;
}
@EventListener
public void greeting(PartOfScoringPerformed event) throws Exception {
this.template.convertAndSend("/topic/greetings", new WebSocketMessage(event.getCluster() + " has been scored for Application Number: " + event.getApplicationNumber()));
}
@EventListener
public void greeting(ScoringPerformed event) throws Exception {
this.template.convertAndSend("/topic/greetings", new WebSocketMessage(event.getApplicationNumber() + " has been scored with " + event.getPoints() + " and final result " + event.getScoreColor()));
}
@EventListener
public void greeting(CreditAgencyResultArrived event) throws Exception {
this.template.convertAndSend("/topic/greetings", new WebSocketMessage("Credit Agency Result has arrived for Person" + event.getPersonId().toString()));
}
@EventListener
public void greeting(CreditApplicationArrived event) throws Exception {
this.template.convertAndSend("/topic/greetings", new WebSocketMessage("Credit Application has arrived with ID " + event.getApplicationNumber().toString()));
}
}
19
View Source File : EventManager.java
License : GNU General Public License v3.0
Project Creator : MoeraOrg
License : GNU General Public License v3.0
Project Creator : MoeraOrg
@Service
public clreplaced EventManager {
private static Logger log = LoggerFactory.getLogger(EventManager.clreplaced);
private static final String USER_PREFIX = "/user";
private static final String EVENT_DESTINATION = "/queue";
private static final String TOKEN_HEADER = "token";
@Inject
private Domains domains;
@Inject
private SimpMessagingTemplate messagingTemplate;
@Inject
private AuthenticationManager authenticationManager;
private Map<String, EventSubscriber> subscribers = new ConcurrentHashMap<>();
private List<EventPacket> queue = new ArrayList<>();
private final long startedAt = Instant.now().getEpochSecond();
private int lastOrdinal = 0;
private ReadWriteLock eventsLock = new ReentrantReadWriteLock();
private final Object deliverySignal = new Object();
@EventListener(SessionConnectEvent.clreplaced)
public void sessionConnect(SessionConnectEvent event) {
StompHeaderAccessor accessor = StompHeaderAccessor.wrap(event.getMessage());
if (accessor.getHost() == null) {
log.debug("Ignoring session {} without a host", accessor.getSessionId());
return;
}
UUID nodeId = domains.getDomainNodeId(accessor.getHost());
nodeId = nodeId != null ? nodeId : domains.getDomainNodeId(Domains.DEFAULT_DOMAIN);
boolean admin = false;
try {
admin = authenticationManager.isAdminToken(accessor.getFirstNativeHeader(TOKEN_HEADER), nodeId);
} catch (InvalidTokenException e) {
// Ignore, the client will detect the problem from REST API requests
}
MDC.put("domain", domains.getDomainEffectiveName(accessor.getHost()));
log.info("Session connect, id = {} {}", accessor.getSessionId(), admin ? "admin" : "non-admin");
EventSubscriber subscriber = new EventSubscriber();
subscriber.setNodeId(nodeId);
subscriber.setSessionId(accessor.getSessionId());
subscriber.setAdmin(admin);
subscribers.put(accessor.getSessionId(), subscriber);
}
@EventListener(SessionSubscribeEvent.clreplaced)
public void subscribed(SessionSubscribeEvent event) {
StompHeaderAccessor accessor = StompHeaderAccessor.wrap(event.getMessage());
if (!(USER_PREFIX + EVENT_DESTINATION).equals(accessor.getDestination())) {
return;
}
SeenHeader.Details seen = SeenHeader.parse(accessor);
initLoggingDomain(accessor.getSessionId());
log.info("Session subscribed, id = {} seen = {}/{}", accessor.getSessionId(), LogUtil.format(seen.queueStartedAt), LogUtil.format(seen.lastEvent));
EventSubscriber subscriber = subscribers.get(accessor.getSessionId());
if (subscriber == null) {
return;
}
if (seen.queueStartedAt == null) {
subscriber.setLastEventSeen(lastOrdinal);
} else if (seen.queueStartedAt != startedAt) {
subscriber.setLastEventSeen(0);
} else {
subscriber.setLastEventSeen(seen.lastEvent);
}
subscriber.setSubscribed(true);
Map<String, Object> attributes = accessor.getSessionAttributes();
String clientIp = (String) attributes.get("ip");
send(subscriber.getNodeId(), new SubscribedEvent(subscriber.getSessionId(), clientIp));
}
@EventListener(SessionUnsubscribeEvent.clreplaced)
public void unsubscribed(SessionUnsubscribeEvent event) {
StompHeaderAccessor accessor = StompHeaderAccessor.wrap(event.getMessage());
if (!(USER_PREFIX + EVENT_DESTINATION).equals(accessor.getDestination())) {
return;
}
initLoggingDomain(accessor.getSessionId());
subscribers.remove(accessor.getSessionId());
log.info("Session unsubscribed, id = {}", accessor.getSessionId());
}
@EventListener(SessionDisconnectEvent.clreplaced)
public void disconnect(SessionDisconnectEvent event) {
StompHeaderAccessor accessor = StompHeaderAccessor.wrap(event.getMessage());
initLoggingDomain(accessor.getSessionId());
subscribers.remove(accessor.getSessionId());
log.info("Session disconnected, id = {}", accessor.getSessionId());
}
private void initLoggingDomain(String sessionId) {
EventSubscriber subscriber = subscribers.get(sessionId);
if (subscriber != null) {
MDC.put("domain", domains.getDomainName(subscriber.getNodeId()));
}
}
@PostConstruct
public void init() {
Thread deliveryThread = new Thread(() -> {
while (true) {
try {
synchronized (deliverySignal) {
deliverySignal.wait();
}
} catch (InterruptedException e) {
}
deliver();
}
});
deliveryThread.setName("eventDelivery");
deliveryThread.setDaemon(true);
deliveryThread.start();
}
private void purge() {
long boundary = Instant.now().minus(10, ChronoUnit.MINUTES).getEpochSecond();
queue.removeIf(packet -> packet.getSentAt() < boundary);
}
public void send(UUID nodeId, Event event) {
send(nodeId, null, event);
}
public void send(UUID nodeId, String clientId, Event event) {
MDC.put("domain", domains.getDomainName(nodeId));
log.info("Event arrived: {}", event.getType());
eventsLock.writeLock().lock();
try {
purge();
EventPacket packet = new EventPacket();
packet.setNodeId(nodeId);
packet.setQueueStartedAt(startedAt);
packet.setOrdinal(++lastOrdinal);
packet.setSentAt(Instant.now().getEpochSecond());
packet.setCid(clientId);
packet.setEvent(event);
queue.add(packet);
} finally {
eventsLock.writeLock().unlock();
}
synchronized (deliverySignal) {
deliverySignal.notifyAll();
}
}
@Scheduled(fixedDelayString = "PT1M")
public void everyMinute() {
retryDelivery();
pingAll();
}
private void retryDelivery() {
synchronized (deliverySignal) {
deliverySignal.notifyAll();
}
}
private void pingAll() {
Set<UUID> nodeIds = subscribers.values().stream().filter(EventSubscriber::isSubscribed).filter(EventSubscriber::isAdmin).map(EventSubscriber::getNodeId).collect(Collectors.toSet());
nodeIds.forEach(nodeId -> send(nodeId, new PingEvent()));
}
private void deliver() {
log.debug("Delivery of events");
eventsLock.readLock().lock();
try {
if (queue.isEmpty()) {
return;
}
int last = queue.get(0).getOrdinal() + queue.size() - 1;
subscribers.values().stream().filter(EventSubscriber::isSubscribed).filter(sub -> sub.getLastEventSeen() < last).forEach(this::deliver);
} finally {
eventsLock.readLock().unlock();
}
}
private void deliver(EventSubscriber subscriber) {
initLoggingDomain(subscriber.getSessionId());
log.debug("Delivering events to {}", subscriber.getSessionId());
SimpMessageHeaderAccessor headerAccessor = SimpMessageHeaderAccessor.create(SimpMessageType.MESSAGE);
headerAccessor.setSessionId(subscriber.getSessionId());
MessageHeaders headers = headerAccessor.getMessageHeaders();
int first = queue.get(0).getOrdinal();
int beginIndex = Math.max(0, subscriber.getLastEventSeen() - first + 1);
try {
for (int i = beginIndex; i < queue.size(); i++) {
EventPacket packet = queue.get(i);
if (!Objects.equals(packet.getNodeId(), subscriber.getNodeId()) || !packet.getEvent().isPermitted(subscriber)) {
subscriber.setLastEventSeen(first + i);
continue;
}
log.debug("Sending event {}: {}", first + i, packet.getEvent().getType());
messagingTemplate.convertAndSendToUser(subscriber.getSessionId(), EVENT_DESTINATION, packet, headers);
subscriber.setLastEventSeen(first + i);
}
} catch (MessagingException e) {
log.error("Error sending event", e);
}
}
}
19
View Source File : WebsocketDisconnectListener.java
License : GNU General Public License v3.0
Project Creator : MicroIoT
License : GNU General Public License v3.0
Project Creator : MicroIoT
@Component
public clreplaced WebsocketDisconnectListener implements ApplicationListener<SessionDisconnectEvent> {
private Logger logger = LoggerFactory.getLogger(this.getClreplaced());
@Autowired
private DeviceRepository deviceRepository;
@Autowired
private AlarmRepository alarmRepository;
@Autowired
private SimpMessagingTemplate template;
@Override
public void onApplicationEvent(SessionDisconnectEvent event) {
SessionDisconnectEvent e = (SessionDisconnectEvent) event;
Date date = new Date(e.getTimestamp());
if ((Authentication) e.getUser() != null) {
CustomUserDetails user = (CustomUserDetails) ((Authentication) e.getUser()).getPrincipal();
if (user.isDevice()) {
Device device = deviceRepository.findByDeviceAccountUsername(user.getUsername());
logger.debug("disconnected device is " + user.getUsername() + " at " + date);
Alarm last = alarmRepository.queryLastAlarm(device.getId());
if (last == null || (last != null && last.getReportTime().before(date))) {
if (device.isConnected()) {
device.setConnected(false);
deviceRepository.save(device);
}
Alarm alarm = new Alarm(device, AlarmType.DISCONNECTED_ALARM, null, date);
alarm = alarmRepository.save(alarm);
String destination = "/topic/alarm." + device.getId();
template.convertAndSend(destination, alarm);
}
}
}
}
}
19
View Source File : WebsocketConnectedListener.java
License : GNU General Public License v3.0
Project Creator : MicroIoT
License : GNU General Public License v3.0
Project Creator : MicroIoT
@Component
public clreplaced WebsocketConnectedListener implements ApplicationListener<SessionConnectedEvent> {
private Logger logger = LoggerFactory.getLogger(this.getClreplaced());
@Autowired
private DeviceRepository deviceRepository;
@Autowired
private AlarmRepository alarmRepository;
@Autowired
private SimpMessagingTemplate template;
@Override
public void onApplicationEvent(SessionConnectedEvent event) {
SessionConnectedEvent e = (SessionConnectedEvent) event;
Date date = new Date(e.getTimestamp());
if ((Authentication) e.getUser() != null) {
CustomUserDetails user = (CustomUserDetails) ((Authentication) e.getUser()).getPrincipal();
if (user.isDevice()) {
Device device = deviceRepository.findByDeviceAccountUsername(user.getUsername());
logger.debug("connected device is " + user.getUsername() + " at " + date);
Alarm last = alarmRepository.queryLastAlarm(device.getId());
if (last == null || (last != null && last.getReportTime().before(date))) {
if (!device.isConnected()) {
device.setConnected(true);
deviceRepository.save(device);
}
Alarm alarm = new Alarm(device, AlarmType.CONNECTED_ALARM, null, date);
alarm = alarmRepository.save(alarm);
String destination = "/topic/alarm." + device.getId();
template.convertAndSend(destination, alarm);
}
}
}
}
}
19
View Source File : AlarmService.java
License : GNU General Public License v3.0
Project Creator : MicroIoT
License : GNU General Public License v3.0
Project Creator : MicroIoT
@Service
public clreplaced AlarmService extends IoTService {
@Autowired
private AlarmRepository alarmRepository;
@Autowired
private DeviceRepository deviceRepository;
@Autowired
private DeviceService deviceService;
@Autowired
private SimpMessagingTemplate template;
@Transactional
public Alarm report(AlarmInfo info) {
Device device = getCurrentDevice();
return reportAlarm(info, device);
}
@Transactional
public Alarm report(SubDeviceAlarmInfo info) {
Device subDevice = deviceRepository.findById(info.getDeviceId()).get();
if (deviceService.isChild(subDevice.getId()))
return reportAlarm(info, subDevice);
else
throw new StatusException("device id error");
}
private Alarm reportAlarm(AlarmInfo info, Device device) {
if (device.getDeviceType().getAlarmTypes() == null || !device.getDeviceType().getAlarmTypes().containsKey(info.getAlarmType()))
throw new NotFoundException("alarm type: " + info.getAlarmType() + " in this device: " + device.getName());
AttributeType alarmType = device.getDeviceType().getAlarmTypes().get(info.getAlarmType());
DataValue value = DataValue.getDataValue(info.getAlarmInfo(), alarmType.getDataType());
Alarm alarm = new Alarm(device, info.getAlarmType(), value, info.getReportTime());
alarm = alarmRepository.save(alarm);
String destination = Topic.TOPIC_ALARM + device.getId();
template.convertAndSend(destination, alarm);
return alarm;
}
public Alarm listAlarm(String id) {
return alarmRepository.findById(id).get();
}
public Page<Alarm> listAll() {
Pageable pageable = getPageable(null);
return alarmRepository.findAll(pageable);
}
public Page<Alarm> listAlarms(AlarmPageInfo info) {
Pageable pageable = getPageable(info);
Domain domain = getCurrentDomain();
return alarmRepository.queryAlarm(domain.getId(), info.getNotifyObjectId(), info.getAlarmType(), info.getReportFrom(), info.getReportTo(), info.getReceiveFrom(), info.getReceiveTo(), pageable);
}
}
19
View Source File : EventSender.java
License : GNU Affero General Public License v3.0
Project Creator : MatagTheGame
License : GNU Affero General Public License v3.0
Project Creator : MatagTheGame
/**
* Sends events to the browser.
*/
@Component
@AllArgsConstructor
public clreplaced EventSender {
private static final Logger LOGGER = LoggerFactory.getLogger(EventSender.clreplaced);
private final SimpMessagingTemplate webSocketTemplate;
private final ObjectMapper objectMapper;
public void sendToUser(String sessionId, String username, Event event) {
var eventString = serializeToString(event);
if (!event.getType().equals("HEALTHCHECK")) {
if (username != null) {
LOGGER.info("Sending event to {} - {}: {}", sessionId, username, eventString);
} else {
LOGGER.info("Sending event to {}: {}", sessionId, eventString);
}
}
webSocketTemplate.convertAndSendToUser(sessionId, "/events", eventString);
}
public void sendToUser(String sessionId, Event event) {
sendToUser(sessionId, null, event);
}
public void sendToPlayer(Player player, Event event) {
sendToUser(player.getToken().getSessionId(), player.getName(), event);
}
public void sendToPlayers(List<Player> players, Event event) {
players.forEach(player -> sendToPlayer(player, event));
}
private String serializeToString(Object event) {
try {
return objectMapper.writeValuereplacedtring(event);
} catch (JsonProcessingException e) {
throw new RuntimeException(e);
}
}
}
19
View Source File : NotificationSimpAspect.java
License : GNU General Public License v3.0
Project Creator : marcinadd
License : GNU General Public License v3.0
Project Creator : marcinadd
@Aspect
@Component
public clreplaced NotificationSimpAspect {
private final SimpMessagingTemplate messagingTemplate;
private final NotificationService notificationService;
public NotificationSimpAspect(SimpMessagingTemplate messagingTemplate, NotificationService notificationService) {
this.messagingTemplate = messagingTemplate;
this.notificationService = notificationService;
}
@AfterReturning(value = "execution (* com.projecty.projectyweb.notifications.NotificationService.createNotificationAndSave(..))", returning = "notification")
public void sendSimpNotificationToSpecificUser(Notification notification) {
notification.setStringValue(notificationService.buildNotificationString(notification));
messagingTemplate.convertAndSendToUser(notification.getUser().getUsername(), "/secured/user/queue/specific-user", notification);
}
}
See More Examples