Как выполнить подключение websocket eventbus из пользовательского клиента Angular6 с конечной точкой eventbus Vert.x verticle

#angular6 #vert.x

#angular6 #vert.x

Вопрос:

Я создал одну вершину vert.x, которая периодически публикует цену акций в шине событий «stock.price.event.bus».Verticle работает нормально, и при запуске он отправляет биржевую цену (в виде json) на адрес шины событий «stock.price.event.bus».

У меня есть проект пользовательского интерфейса angular-6, где мне нужно создать экран данных в реальном времени (реактивный), и этот json цены акций должен отображаться в пользовательском интерфейсе Angular-6. Пользовательский интерфейс Angular-6 должен подписаться на эту шину событий vertx, и экран пользовательского интерфейса должен периодически обновлять данные через 5 секунд.

URL-адрес пользовательского интерфейса Angular —http://localhost:4200 /
Серверная служба Vertx Java — http://localhost:8080

Запущены как пользовательский интерфейс, так и серверные службы

При доступе к локальному хосту: 4200

Получение ошибки HTTP404: НЕ НАЙДЕНО — сервер не нашел ничего, соответствующего запрошенному URI (унифицированный идентификатор ресурса). (XHR)ПОЛУЧИТЬ —http://localhost:8080/eventbus/info?t=1554681653888.***

Ошибка в браузере (Edge)

—Основной код Verticle, который развертывает StockPriceWebSocketVerticle

 package com.amit.vertx.MyVertxProject;

import io.vertx.core.AbstractVerticle;
import io.vertx.core.Vertx;

public class MainClass  extends AbstractVerticle
{
    public static void main( String[] args )
    {
        Vertx vertx = Vertx.factory.vertx();
        vertx.deployVerticle(new ServerVerticle());
        vertx.deployVerticle(new StockPriceWebSocketVerticle());

    }
}

  

— ServerVerticle

 package com.amit.vertx.MyVertxProject;

import io.vertx.core.AbstractVerticle;
import io.vertx.core.Vertx;
import io.vertx.core.http.HttpMethod;
import io.vertx.core.http.HttpServer;
import io.vertx.core.http.HttpServerResponse;
import io.vertx.core.json.Json;
import io.vertx.core.json.JsonObject;
import io.vertx.ext.web.Route;
import io.vertx.ext.web.Router;
import io.vertx.ext.web.RoutingContext;
import io.vertx.ext.web.handler.BodyHandler;
import io.vertx.ext.web.handler.CookieHandler;
import io.vertx.ext.web.handler.CorsHandler;
import io.vertx.ext.web.handler.SessionHandler;
import io.vertx.ext.web.sstore.LocalSessionStore;

public class ServerVerticle extends AbstractVerticle{


    @Override
    public void start() throws Exception {

        try {

            HttpServer httpServer = vertx.createHttpServer();
            //Main router
            Router router = Router.router(vertx);       
               //A cross origin request
                CorsHandler corsHandler = 
                CorsHandler.create("http://localhost:4200"); 
                corsHandler.allowedMethod(HttpMethod.OPTIONS);
                corsHandler.allowedMethod(HttpMethod.GET);
                corsHandler.allowedMethod(HttpMethod.POST);
                corsHandler.allowedMethod(HttpMethod.DELETE);   
                corsHandler.allowedHeader("x-requested-with");
                corsHandler.allowedHeader("Access-Control-Allow-Origin");
                corsHandler.allowedHeader("Origin");
                corsHandler.allowedHeader("Content-Type");
                corsHandler.allowedHeader("Accept");
                corsHandler.allowedHeader("Access-Control-Allow-Credentials");
                corsHandler.allowedHeader("Access-Control-Allow-Headers");
                corsHandler.allowCredentials(true);



            router.route().handler(corsHandler);                
            router.route().handler(BodyHandler.create());

            //for session handling

            SessionHandler sessionHandler = SessionHandler.create(LocalSessionStore.create(vertx));
            router.route().handler(sessionHandler);

            httpServer.requestHandler(router::accept).listen(8080);

            System.out.println("Server Started");              


        }catch (Exception e) {
            e.printStackTrace();
        }

    }

}

  
 public class StockPriceWebSocketVerticle extends AbstractVerticle{

    @Override
    public void start() throws Exception {

        vertx.setPeriodic(5000, new Handler<Long>() {

            @Override
            public void handle(Long timerId) {

                JsonObject obj_1 = new JsonObject();
                obj_1.put("company", "Amazon");
                obj_1.put("datetime", new Date().toString());
                obj_1.put("price", 100);

                JsonObject obj_2 = new JsonObject();
                obj_2.put("company", "Google");
                obj_2.put("datetime", new Date().toString());
                obj_2.put("price", 1005);

                 JsonArray jsonarray = new JsonArray();
                 jsonarray.add(obj_1);
                 jsonarray.add(obj_2);

                 vertx.eventBus().publish("stock.price.event.bus", jsonarray);

                 System.out.println("sent data to UI" jsonarray.toString());

            }

        });


    }
}


-----output---------
sent data to UI[{"company":"Amazon","datetime":"Sat Apr 06 17:11:37 EDT 2019","price":100},{"company":"Google","datetime":"Sat Apr 06 17:11:37 EDT 2019","price":1005}]
sent data to UI[{"company":"Amazon","datetime":"Sat Apr 06 17:11:42 EDT 2019","price":100},{"company":"Google","datetime":"Sat Apr 06 17:11:42 EDT 2019","price":1005}]

  

Компонент пользовательского интерфейса Angular-6 (таблица данных с использованием материала angular)

stockprice.component.html

  <div id="stockpricetable" style="width:60%; text-align: left; font-size: x-large;border:1px darksalmon;">
    <table mat-table [dataSource]="dataSource" matSort  style="width:95%;" >

        <ng-container matColumnDef="company">
          <th mat-header-cell *matHeaderCellDef mat-sort-header> Company. </th>
          <td mat-cell *matCellDef="let element"> {{element.company}} </td>
        </ng-container>

        <ng-container matColumnDef="datetime">
          <th mat-header-cell *matHeaderCellDef mat-sort-header> Date amp; Time. </th>
          <td mat-cell *matCellDef="let element"> {{element.datetime}} </td>
        </ng-container>

        <ng-container matColumnDef="price">
          <th mat-header-cell *matHeaderCellDef mat-sort-header> Price. </th>
          <td mat-cell *matCellDef="let element"> {{element.price}} </td>
        </ng-container>


        <tr mat-header-row *matHeaderRowDef="displayedColumns;sticky: true" ></tr>
        <tr mat-row *matRowDef="let row; columns: displayedColumns; "></tr>

      </table>

</div>  
  

Вызов службы Angular (для подписки на конечную точку vertx) и обновления источника данных

stockprice.component.ts

 import { Component, OnInit , ViewChild} from '@angular/core';
import { MatTableDataSource, MatSort, MatPaginator } from '@angular/material';
import {StockPriceService} from './stockprice.service';
import * as  EventBus from 'vertx3-eventbus-client';

@Component({
  selector: 'app-stockprice',
  templateUrl: './stockprice.component.html',
  styleUrls: ['./stockprice.component.css']
})
export class StockpriceComponent implements OnInit {

  @ViewChild(MatSort) sort: MatSort;

  displayedColumns: string[] = ['company','datetime','price'];
  dataSource = new MatTableDataSource();
  private eb;
  private url = 'http://localhost:8080/eventbus';

  constructor(private stockPriceService: StockPriceService) { }

  ngOnInit() {
    this.dataSource.sort = this.sort;
    this.eb = new EventBus(this.url);
    console.log("connecting to websocket-1");
    this.eb.onopen = function () {

      console.log("connecting to websocket-2");
      // set a handler to receive a message
      this.eb.registerHandler('stock.price.event.bus', function (error, message) {
        console.log('received a message: '   JSON.stringify(message.body));
        this.dataSource.data = JSON.stringify(message.body);
      });
    };

    this.eb.enableReconnect(true);

  }



  }



}