Merge branch 'master' of ssh://git.swordlost.top:222/SikongJueluo/FPGA_WebLab
This commit is contained in:
		@@ -145,6 +145,8 @@ try
 | 
			
		||||
    // 添加 HTTP 视频流服务
 | 
			
		||||
    builder.Services.AddSingleton<HttpVideoStreamService>();
 | 
			
		||||
    builder.Services.AddHostedService(provider => provider.GetRequiredService<HttpVideoStreamService>());
 | 
			
		||||
    builder.Services.AddSingleton<HttpHdmiVideoStreamService>();
 | 
			
		||||
    builder.Services.AddHostedService(provider => provider.GetRequiredService<HttpHdmiVideoStreamService>());
 | 
			
		||||
 | 
			
		||||
    // Application Settings
 | 
			
		||||
    var app = builder.Build();
 | 
			
		||||
 
 | 
			
		||||
							
								
								
									
										63
									
								
								server/src/Controllers/HdmiVideoStreamController.cs
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										63
									
								
								server/src/Controllers/HdmiVideoStreamController.cs
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,63 @@
 | 
			
		||||
using Microsoft.AspNetCore.Mvc;
 | 
			
		||||
using Microsoft.AspNetCore.Cors;
 | 
			
		||||
using Microsoft.AspNetCore.Authorization;
 | 
			
		||||
using System.Security.Claims;
 | 
			
		||||
using server.Services;
 | 
			
		||||
using Database;
 | 
			
		||||
 | 
			
		||||
namespace server.Controllers;
 | 
			
		||||
 | 
			
		||||
[ApiController]
 | 
			
		||||
[Route("api/[controller]")]
 | 
			
		||||
[EnableCors("Users")]
 | 
			
		||||
public class HdmiVideoStreamController : ControllerBase
 | 
			
		||||
{
 | 
			
		||||
    private readonly HttpHdmiVideoStreamService _videoStreamService;
 | 
			
		||||
    private readonly NLog.Logger logger = NLog.LogManager.GetCurrentClassLogger();
 | 
			
		||||
 | 
			
		||||
    public HdmiVideoStreamController(HttpHdmiVideoStreamService videoStreamService)
 | 
			
		||||
    {
 | 
			
		||||
        _videoStreamService = videoStreamService;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    // 管理员获取所有板子的 endpoints
 | 
			
		||||
    [HttpGet("AllEndpoints")]
 | 
			
		||||
    [Authorize("Admin")]
 | 
			
		||||
    public ActionResult<List<HdmiVideoStreamEndpoint>> GetAllEndpoints()
 | 
			
		||||
    {
 | 
			
		||||
        var endpoints = _videoStreamService.GetAllVideoEndpoints();
 | 
			
		||||
        if (endpoints == null)
 | 
			
		||||
            return NotFound("No boards found.");
 | 
			
		||||
        return Ok(endpoints);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    // 用户获取自己板子的 endpoint
 | 
			
		||||
    [HttpGet("MyEndpoint")]
 | 
			
		||||
    [Authorize]
 | 
			
		||||
    public ActionResult<HdmiVideoStreamEndpoint> GetMyEndpoint()
 | 
			
		||||
    {
 | 
			
		||||
        var userName = User.FindFirstValue(ClaimTypes.Name);
 | 
			
		||||
        if (string.IsNullOrEmpty(userName))
 | 
			
		||||
            return Unauthorized("User name not found in claims.");
 | 
			
		||||
 | 
			
		||||
        var db = new AppDataConnection();
 | 
			
		||||
        if (db == null)
 | 
			
		||||
            return NotFound("Database connection failed.");
 | 
			
		||||
 | 
			
		||||
        var userRet = db.GetUserByName(userName);
 | 
			
		||||
        if (!userRet.IsSuccessful || !userRet.Value.HasValue)
 | 
			
		||||
            return NotFound("User not found.");
 | 
			
		||||
 | 
			
		||||
        var user = userRet.Value.Value;
 | 
			
		||||
        var boardId = user.BoardID;
 | 
			
		||||
        if (boardId == Guid.Empty)
 | 
			
		||||
            return NotFound("No board bound to this user.");
 | 
			
		||||
 | 
			
		||||
        var boardRet = db.GetBoardByID(boardId);
 | 
			
		||||
        if (!boardRet.IsSuccessful || !boardRet.Value.HasValue)
 | 
			
		||||
            return NotFound("Board not found.");
 | 
			
		||||
 | 
			
		||||
        var endpoint = _videoStreamService.GetVideoEndpoint(boardId.ToString());
 | 
			
		||||
        return Ok(endpoint);
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -32,14 +32,16 @@ class HdmiIn
 | 
			
		||||
    /// </summary>
 | 
			
		||||
    /// <param name="address">HDMI输入设备IP地址</param>
 | 
			
		||||
    /// <param name="port">HDMI输入设备端口</param>
 | 
			
		||||
    /// <param name="taskID">任务ID</param>
 | 
			
		||||
    /// <param name="timeout">超时时间(毫秒)</param>
 | 
			
		||||
    public HdmiIn(string address, int port, int timeout = 500)
 | 
			
		||||
    public HdmiIn(string address, int port, int taskID, int timeout = 500)
 | 
			
		||||
    {
 | 
			
		||||
        if (timeout < 0)
 | 
			
		||||
            throw new ArgumentException("Timeout couldn't be negative", nameof(timeout));
 | 
			
		||||
        this.address = address;
 | 
			
		||||
        this.port = port;
 | 
			
		||||
        this.ep = new IPEndPoint(IPAddress.Parse(address), port);
 | 
			
		||||
        this.taskID = taskID;
 | 
			
		||||
        this.timeout = timeout;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
 
 | 
			
		||||
							
								
								
									
										234
									
								
								server/src/Services/HttpHdmiVideoStreamService.cs
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										234
									
								
								server/src/Services/HttpHdmiVideoStreamService.cs
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,234 @@
 | 
			
		||||
using System.Net;
 | 
			
		||||
using System.Collections.Concurrent;
 | 
			
		||||
using Peripherals.HdmiInClient;
 | 
			
		||||
 | 
			
		||||
namespace server.Services;
 | 
			
		||||
 | 
			
		||||
public class HdmiVideoStreamEndpoint
 | 
			
		||||
{
 | 
			
		||||
    public string BoardId { get; set; } = "";
 | 
			
		||||
    public string MjpegUrl { get; set; } = "";
 | 
			
		||||
    public string VideoUrl { get; set; } = "";
 | 
			
		||||
    public string SnapshotUrl { get; set; } = "";
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
public class HttpHdmiVideoStreamService : BackgroundService
 | 
			
		||||
{
 | 
			
		||||
    private readonly NLog.Logger logger = NLog.LogManager.GetCurrentClassLogger();
 | 
			
		||||
    private HttpListener? _httpListener;
 | 
			
		||||
    private readonly int _serverPort = 4322;
 | 
			
		||||
    private readonly ConcurrentDictionary<string, HdmiIn> _hdmiInDict = new();
 | 
			
		||||
    private bool _isEnabled = true;
 | 
			
		||||
 | 
			
		||||
    public override async Task StartAsync(CancellationToken cancellationToken)
 | 
			
		||||
    {
 | 
			
		||||
        _httpListener = new HttpListener();
 | 
			
		||||
        _httpListener.Prefixes.Add($"http://*:{_serverPort}/");
 | 
			
		||||
        _httpListener.Start();
 | 
			
		||||
        logger.Info($"HDMI Video Stream Service started on port {_serverPort}");
 | 
			
		||||
 | 
			
		||||
        await base.StartAsync(cancellationToken);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    protected override async Task ExecuteAsync(CancellationToken stoppingToken)
 | 
			
		||||
    {
 | 
			
		||||
        try
 | 
			
		||||
        {
 | 
			
		||||
            while (!stoppingToken.IsCancellationRequested)
 | 
			
		||||
            {
 | 
			
		||||
                HttpListenerContext? context = null;
 | 
			
		||||
                try
 | 
			
		||||
                {
 | 
			
		||||
                    context = await _httpListener.GetContextAsync();
 | 
			
		||||
                }
 | 
			
		||||
                catch (ObjectDisposedException)
 | 
			
		||||
                {
 | 
			
		||||
                    // Listener closed, exit loop
 | 
			
		||||
                    break;
 | 
			
		||||
                }
 | 
			
		||||
                catch (HttpListenerException)
 | 
			
		||||
                {
 | 
			
		||||
                    // Listener closed, exit loop
 | 
			
		||||
                    break;
 | 
			
		||||
                }
 | 
			
		||||
                catch (Exception ex)
 | 
			
		||||
                {
 | 
			
		||||
                    logger.Error(ex, "Error in GetContextAsync");
 | 
			
		||||
                    break;
 | 
			
		||||
                }
 | 
			
		||||
                if (context != null)
 | 
			
		||||
                    _ = HandleRequestAsync(context, stoppingToken);
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        finally
 | 
			
		||||
        {
 | 
			
		||||
            _httpListener?.Close();
 | 
			
		||||
            logger.Info("HDMI Video Stream Service stopped.");
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public override async Task StopAsync(CancellationToken cancellationToken)
 | 
			
		||||
    {
 | 
			
		||||
        logger.Info("Stopping HDMI Video Stream Service...");
 | 
			
		||||
        _isEnabled = false;
 | 
			
		||||
        _httpListener?.Close(); // 立即关闭监听器,唤醒阻塞
 | 
			
		||||
        await base.StopAsync(cancellationToken);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    // 获取/创建 HdmiIn 实例
 | 
			
		||||
    private HdmiIn? GetOrCreateHdmiIn(string boardId)
 | 
			
		||||
    {
 | 
			
		||||
        if (_hdmiInDict.TryGetValue(boardId, out var hdmiIn))
 | 
			
		||||
            return hdmiIn;
 | 
			
		||||
 | 
			
		||||
        var db = new Database.AppDataConnection();
 | 
			
		||||
        if (db == null)
 | 
			
		||||
        {
 | 
			
		||||
            logger.Error("Failed to create HdmiIn instance");
 | 
			
		||||
            return null;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        var boardRet = db.GetBoardByID(Guid.Parse(boardId));
 | 
			
		||||
        if (!boardRet.IsSuccessful || !boardRet.Value.HasValue)
 | 
			
		||||
        {
 | 
			
		||||
            logger.Error($"Failed to get board with ID {boardId}");
 | 
			
		||||
            return null;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        var board = boardRet.Value.Value;
 | 
			
		||||
 | 
			
		||||
        hdmiIn = new HdmiIn(board.IpAddr, board.Port, 0); // taskID 可根据实际需求调整
 | 
			
		||||
        _hdmiInDict[boardId] = hdmiIn;
 | 
			
		||||
        return hdmiIn;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    private async Task HandleRequestAsync(HttpListenerContext context, CancellationToken cancellationToken)
 | 
			
		||||
    {
 | 
			
		||||
        var path = context.Request.Url?.AbsolutePath ?? "/";
 | 
			
		||||
        var boardId = context.Request.QueryString["boardId"];
 | 
			
		||||
        if (string.IsNullOrEmpty(boardId))
 | 
			
		||||
        {
 | 
			
		||||
            await SendErrorAsync(context.Response, "Missing boardId");
 | 
			
		||||
            return;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        var hdmiIn = GetOrCreateHdmiIn(boardId);
 | 
			
		||||
        if (hdmiIn == null)
 | 
			
		||||
        {
 | 
			
		||||
            await SendErrorAsync(context.Response, "Invalid boardId or board not available");
 | 
			
		||||
            return;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        if (path == "/snapshot")
 | 
			
		||||
        {
 | 
			
		||||
            await HandleSnapshotRequestAsync(context.Response, hdmiIn, cancellationToken);
 | 
			
		||||
        }
 | 
			
		||||
        else if (path == "/mjpeg")
 | 
			
		||||
        {
 | 
			
		||||
            await HandleMjpegStreamAsync(context.Response, hdmiIn, cancellationToken);
 | 
			
		||||
        }
 | 
			
		||||
        else if (path == "/video")
 | 
			
		||||
        {
 | 
			
		||||
            await SendVideoHtmlPageAsync(context.Response, boardId);
 | 
			
		||||
        }
 | 
			
		||||
        else
 | 
			
		||||
        {
 | 
			
		||||
            await SendIndexHtmlPageAsync(context.Response, boardId);
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    private async Task HandleSnapshotRequestAsync(HttpListenerResponse response, HdmiIn hdmiIn, CancellationToken cancellationToken)
 | 
			
		||||
    {
 | 
			
		||||
        var frameResult = await hdmiIn.ReadFrame();
 | 
			
		||||
        if (frameResult.IsSuccessful)
 | 
			
		||||
        {
 | 
			
		||||
            response.ContentType = "image/jpeg";
 | 
			
		||||
            await response.OutputStream.WriteAsync(frameResult.Value, 0, frameResult.Value.Length, cancellationToken);
 | 
			
		||||
        }
 | 
			
		||||
        else
 | 
			
		||||
        {
 | 
			
		||||
            response.StatusCode = 500;
 | 
			
		||||
            await response.OutputStream.WriteAsync(System.Text.Encoding.UTF8.GetBytes("Failed to get snapshot"));
 | 
			
		||||
        }
 | 
			
		||||
        response.Close();
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    private async Task HandleMjpegStreamAsync(HttpListenerResponse response, HdmiIn hdmiIn, CancellationToken cancellationToken)
 | 
			
		||||
    {
 | 
			
		||||
        response.ContentType = "multipart/x-mixed-replace; boundary=--frame";
 | 
			
		||||
        while (!cancellationToken.IsCancellationRequested && _isEnabled)
 | 
			
		||||
        {
 | 
			
		||||
            var frameResult = await hdmiIn.ReadFrame();
 | 
			
		||||
            if (frameResult.IsSuccessful)
 | 
			
		||||
            {
 | 
			
		||||
                var header = $"--frame\r\nContent-Type: image/jpeg\r\nContent-Length: {frameResult.Value.Length}\r\n\r\n";
 | 
			
		||||
                await response.OutputStream.WriteAsync(System.Text.Encoding.ASCII.GetBytes(header));
 | 
			
		||||
                await response.OutputStream.WriteAsync(frameResult.Value, 0, frameResult.Value.Length, cancellationToken);
 | 
			
		||||
                await response.OutputStream.WriteAsync(System.Text.Encoding.ASCII.GetBytes("\r\n"));
 | 
			
		||||
            }
 | 
			
		||||
            await Task.Delay(33, cancellationToken); // ~30fps
 | 
			
		||||
        }
 | 
			
		||||
        response.Close();
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    private async Task SendVideoHtmlPageAsync(HttpListenerResponse response, string boardId)
 | 
			
		||||
    {
 | 
			
		||||
        string html = $@"<html><body>
 | 
			
		||||
                <h1>HDMI Video Stream for Board {boardId}</h1>
 | 
			
		||||
                <img src='/mjpeg?boardId={boardId}' />
 | 
			
		||||
                </body></html>";
 | 
			
		||||
        response.ContentType = "text/html";
 | 
			
		||||
        await response.OutputStream.WriteAsync(System.Text.Encoding.UTF8.GetBytes(html));
 | 
			
		||||
        response.Close();
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    private async Task SendIndexHtmlPageAsync(HttpListenerResponse response, string boardId)
 | 
			
		||||
    {
 | 
			
		||||
        string html = $@"<html><body>
 | 
			
		||||
                <h1>Welcome to HDMI Video Stream Service</h1>
 | 
			
		||||
                <a href='/video?boardId={boardId}'>View Video Stream for Board {boardId}</a>
 | 
			
		||||
                </body></html>";
 | 
			
		||||
        response.ContentType = "text/html";
 | 
			
		||||
        await response.OutputStream.WriteAsync(System.Text.Encoding.UTF8.GetBytes(html));
 | 
			
		||||
        response.Close();
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    private async Task SendErrorAsync(HttpListenerResponse response, string message)
 | 
			
		||||
    {
 | 
			
		||||
        response.StatusCode = 400;
 | 
			
		||||
        await response.OutputStream.WriteAsync(System.Text.Encoding.UTF8.GetBytes(message));
 | 
			
		||||
        response.Close();
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public List<HdmiVideoStreamEndpoint>? GetAllVideoEndpoints()
 | 
			
		||||
    {
 | 
			
		||||
        var db = new Database.AppDataConnection();
 | 
			
		||||
        var boards = db?.GetAllBoard();
 | 
			
		||||
        if (boards == null)
 | 
			
		||||
            return null;
 | 
			
		||||
 | 
			
		||||
        var endpoints = new List<HdmiVideoStreamEndpoint>();
 | 
			
		||||
        foreach (var board in boards)
 | 
			
		||||
        {
 | 
			
		||||
            endpoints.Add(new HdmiVideoStreamEndpoint
 | 
			
		||||
            {
 | 
			
		||||
                BoardId = board.ID.ToString(),
 | 
			
		||||
                MjpegUrl = $"http://{Global.localhost}:{_serverPort}/mjpeg?boardId={board.ID}",
 | 
			
		||||
                VideoUrl = $"http://{Global.localhost}:{_serverPort}/video?boardId={board.ID}",
 | 
			
		||||
                SnapshotUrl = $"http://{Global.localhost}:{_serverPort}/snapshot?boardId={board.ID}"
 | 
			
		||||
            });
 | 
			
		||||
        }
 | 
			
		||||
        return endpoints;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public HdmiVideoStreamEndpoint GetVideoEndpoint(string boardId)
 | 
			
		||||
    {
 | 
			
		||||
        return new HdmiVideoStreamEndpoint
 | 
			
		||||
        {
 | 
			
		||||
            BoardId = boardId,
 | 
			
		||||
            MjpegUrl = $"http://{Global.localhost}:{_serverPort}/mjpeg?boardId={boardId}",
 | 
			
		||||
            VideoUrl = $"http://{Global.localhost}:{_serverPort}/video?boardId={boardId}",
 | 
			
		||||
            SnapshotUrl = $"http://{Global.localhost}:{_serverPort}/snapshot?boardId={boardId}"
 | 
			
		||||
        };
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
							
								
								
									
										165
									
								
								src/APIClient.ts
									
									
									
									
									
								
							
							
						
						
									
										165
									
								
								src/APIClient.ts
									
									
									
									
									
								
							@@ -2944,6 +2944,123 @@ export class ExamClient {
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
export class HdmiVideoStreamClient {
 | 
			
		||||
    protected instance: AxiosInstance;
 | 
			
		||||
    protected baseUrl: string;
 | 
			
		||||
    protected jsonParseReviver: ((key: string, value: any) => any) | undefined = undefined;
 | 
			
		||||
 | 
			
		||||
    constructor(baseUrl?: string, instance?: AxiosInstance) {
 | 
			
		||||
 | 
			
		||||
        this.instance = instance || axios.create();
 | 
			
		||||
 | 
			
		||||
        this.baseUrl = baseUrl ?? "http://127.0.0.1:5000";
 | 
			
		||||
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    getAllEndpoints( cancelToken?: CancelToken): Promise<HdmiVideoStreamEndpoint[]> {
 | 
			
		||||
        let url_ = this.baseUrl + "/api/HdmiVideoStream/AllEndpoints";
 | 
			
		||||
        url_ = url_.replace(/[?&]$/, "");
 | 
			
		||||
 | 
			
		||||
        let options_: AxiosRequestConfig = {
 | 
			
		||||
            method: "GET",
 | 
			
		||||
            url: url_,
 | 
			
		||||
            headers: {
 | 
			
		||||
                "Accept": "application/json"
 | 
			
		||||
            },
 | 
			
		||||
            cancelToken
 | 
			
		||||
        };
 | 
			
		||||
 | 
			
		||||
        return this.instance.request(options_).catch((_error: any) => {
 | 
			
		||||
            if (isAxiosError(_error) && _error.response) {
 | 
			
		||||
                return _error.response;
 | 
			
		||||
            } else {
 | 
			
		||||
                throw _error;
 | 
			
		||||
            }
 | 
			
		||||
        }).then((_response: AxiosResponse) => {
 | 
			
		||||
            return this.processGetAllEndpoints(_response);
 | 
			
		||||
        });
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    protected processGetAllEndpoints(response: AxiosResponse): Promise<HdmiVideoStreamEndpoint[]> {
 | 
			
		||||
        const status = response.status;
 | 
			
		||||
        let _headers: any = {};
 | 
			
		||||
        if (response.headers && typeof response.headers === "object") {
 | 
			
		||||
            for (const k in response.headers) {
 | 
			
		||||
                if (response.headers.hasOwnProperty(k)) {
 | 
			
		||||
                    _headers[k] = response.headers[k];
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        if (status === 200) {
 | 
			
		||||
            const _responseText = response.data;
 | 
			
		||||
            let result200: any = null;
 | 
			
		||||
            let resultData200  = _responseText;
 | 
			
		||||
            if (Array.isArray(resultData200)) {
 | 
			
		||||
                result200 = [] as any;
 | 
			
		||||
                for (let item of resultData200)
 | 
			
		||||
                    result200!.push(HdmiVideoStreamEndpoint.fromJS(item));
 | 
			
		||||
            }
 | 
			
		||||
            else {
 | 
			
		||||
                result200 = <any>null;
 | 
			
		||||
            }
 | 
			
		||||
            return Promise.resolve<HdmiVideoStreamEndpoint[]>(result200);
 | 
			
		||||
 | 
			
		||||
        } else if (status !== 200 && status !== 204) {
 | 
			
		||||
            const _responseText = response.data;
 | 
			
		||||
            return throwException("An unexpected server error occurred.", status, _responseText, _headers);
 | 
			
		||||
        }
 | 
			
		||||
        return Promise.resolve<HdmiVideoStreamEndpoint[]>(null as any);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    getMyEndpoint( cancelToken?: CancelToken): Promise<HdmiVideoStreamEndpoint> {
 | 
			
		||||
        let url_ = this.baseUrl + "/api/HdmiVideoStream/MyEndpoint";
 | 
			
		||||
        url_ = url_.replace(/[?&]$/, "");
 | 
			
		||||
 | 
			
		||||
        let options_: AxiosRequestConfig = {
 | 
			
		||||
            method: "GET",
 | 
			
		||||
            url: url_,
 | 
			
		||||
            headers: {
 | 
			
		||||
                "Accept": "application/json"
 | 
			
		||||
            },
 | 
			
		||||
            cancelToken
 | 
			
		||||
        };
 | 
			
		||||
 | 
			
		||||
        return this.instance.request(options_).catch((_error: any) => {
 | 
			
		||||
            if (isAxiosError(_error) && _error.response) {
 | 
			
		||||
                return _error.response;
 | 
			
		||||
            } else {
 | 
			
		||||
                throw _error;
 | 
			
		||||
            }
 | 
			
		||||
        }).then((_response: AxiosResponse) => {
 | 
			
		||||
            return this.processGetMyEndpoint(_response);
 | 
			
		||||
        });
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    protected processGetMyEndpoint(response: AxiosResponse): Promise<HdmiVideoStreamEndpoint> {
 | 
			
		||||
        const status = response.status;
 | 
			
		||||
        let _headers: any = {};
 | 
			
		||||
        if (response.headers && typeof response.headers === "object") {
 | 
			
		||||
            for (const k in response.headers) {
 | 
			
		||||
                if (response.headers.hasOwnProperty(k)) {
 | 
			
		||||
                    _headers[k] = response.headers[k];
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        if (status === 200) {
 | 
			
		||||
            const _responseText = response.data;
 | 
			
		||||
            let result200: any = null;
 | 
			
		||||
            let resultData200  = _responseText;
 | 
			
		||||
            result200 = HdmiVideoStreamEndpoint.fromJS(resultData200);
 | 
			
		||||
            return Promise.resolve<HdmiVideoStreamEndpoint>(result200);
 | 
			
		||||
 | 
			
		||||
        } else if (status !== 200 && status !== 204) {
 | 
			
		||||
            const _responseText = response.data;
 | 
			
		||||
            return throwException("An unexpected server error occurred.", status, _responseText, _headers);
 | 
			
		||||
        }
 | 
			
		||||
        return Promise.resolve<HdmiVideoStreamEndpoint>(null as any);
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
export class JtagClient {
 | 
			
		||||
    protected instance: AxiosInstance;
 | 
			
		||||
    protected baseUrl: string;
 | 
			
		||||
@@ -8019,6 +8136,54 @@ export interface ICreateExamRequest {
 | 
			
		||||
    isVisibleToUsers: boolean;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
export class HdmiVideoStreamEndpoint implements IHdmiVideoStreamEndpoint {
 | 
			
		||||
    boardId!: string;
 | 
			
		||||
    mjpegUrl!: string;
 | 
			
		||||
    videoUrl!: string;
 | 
			
		||||
    snapshotUrl!: string;
 | 
			
		||||
 | 
			
		||||
    constructor(data?: IHdmiVideoStreamEndpoint) {
 | 
			
		||||
        if (data) {
 | 
			
		||||
            for (var property in data) {
 | 
			
		||||
                if (data.hasOwnProperty(property))
 | 
			
		||||
                    (<any>this)[property] = (<any>data)[property];
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    init(_data?: any) {
 | 
			
		||||
        if (_data) {
 | 
			
		||||
            this.boardId = _data["boardId"];
 | 
			
		||||
            this.mjpegUrl = _data["mjpegUrl"];
 | 
			
		||||
            this.videoUrl = _data["videoUrl"];
 | 
			
		||||
            this.snapshotUrl = _data["snapshotUrl"];
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    static fromJS(data: any): HdmiVideoStreamEndpoint {
 | 
			
		||||
        data = typeof data === 'object' ? data : {};
 | 
			
		||||
        let result = new HdmiVideoStreamEndpoint();
 | 
			
		||||
        result.init(data);
 | 
			
		||||
        return result;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    toJSON(data?: any) {
 | 
			
		||||
        data = typeof data === 'object' ? data : {};
 | 
			
		||||
        data["boardId"] = this.boardId;
 | 
			
		||||
        data["mjpegUrl"] = this.mjpegUrl;
 | 
			
		||||
        data["videoUrl"] = this.videoUrl;
 | 
			
		||||
        data["snapshotUrl"] = this.snapshotUrl;
 | 
			
		||||
        return data;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
export interface IHdmiVideoStreamEndpoint {
 | 
			
		||||
    boardId: string;
 | 
			
		||||
    mjpegUrl: string;
 | 
			
		||||
    videoUrl: string;
 | 
			
		||||
    snapshotUrl: string;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
/** 逻辑分析仪运行状态枚举 */
 | 
			
		||||
export enum CaptureStatus {
 | 
			
		||||
    None = 0,
 | 
			
		||||
 
 | 
			
		||||
		Reference in New Issue
	
	Block a user