Fix SSE stream discovery and add ESLint for WebUI
JavaScript fixes: - Fix Invalid URL error in stream-discovery.js by adding window.location.origin as base URL - Fix SSE race condition: ensure all stream_found events sent before complete event - Comment unused eventType variable in stream-discovery.js - Comment unused FrigateGenerator import in config-panel.js - Fix quote style (double to single quotes) Go fixes: - Add sync.WaitGroup for result collector to prevent premature SSE closure - Add logging for stream_found events - Fix ERR_INCOMPLETE_CHUNKED_ENCODING by waiting for all streams to be sent ESLint setup: - Add ESLint v8.57.1 with .eslintrc.cjs config for ES2022 modules - Add npm scripts for lint and lint:fix - Update .gitignore for node_modules and package-lock.json 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude <noreply@anthropic.com>
This commit is contained in:
+5
-1
@@ -43,4 +43,8 @@ temp/
|
||||
*_output.txt
|
||||
|
||||
# Configuration (user-specific)
|
||||
strix.yaml
|
||||
strix.yaml
|
||||
|
||||
# Node.js / NPM
|
||||
node_modules/
|
||||
package-lock.json
|
||||
@@ -434,10 +434,15 @@ func (s *Scanner) testStreamsConcurrently(ctx context.Context, streams []models.
|
||||
}()
|
||||
|
||||
// Start result collector
|
||||
var collectorWg sync.WaitGroup
|
||||
collectorWg.Add(1)
|
||||
go func() {
|
||||
defer collectorWg.Done()
|
||||
for stream := range streamsChan {
|
||||
result.Streams = append(result.Streams, stream)
|
||||
|
||||
s.logger.Info("sending stream_found event", "url", stream.URL, "type", stream.Type)
|
||||
|
||||
// Send to SSE
|
||||
_ = streamWriter.SendJSON("stream_found", map[string]interface{}{
|
||||
"stream": stream,
|
||||
@@ -522,6 +527,9 @@ TestLoop:
|
||||
wg.Wait()
|
||||
close(streamsChan)
|
||||
|
||||
// Wait for result collector to finish processing all streams
|
||||
collectorWg.Wait()
|
||||
|
||||
// Update final counts
|
||||
result.TotalTested = int(atomic.LoadInt32(&tested))
|
||||
result.TotalFound = int(atomic.LoadInt32(&found))
|
||||
|
||||
@@ -0,0 +1,25 @@
|
||||
module.exports = {
|
||||
env: {
|
||||
browser: true,
|
||||
es2021: true,
|
||||
},
|
||||
extends: 'eslint:recommended',
|
||||
parserOptions: {
|
||||
ecmaVersion: 2022,
|
||||
sourceType: 'module',
|
||||
},
|
||||
globals: {
|
||||
EventSource: 'readonly',
|
||||
},
|
||||
rules: {
|
||||
'no-unused-vars': 'warn',
|
||||
'no-undef': 'error',
|
||||
'no-console': 'off', // Allow console for debugging
|
||||
'semi': ['error', 'always'],
|
||||
'quotes': ['warn', 'single', { avoidEscape: true }],
|
||||
'no-var': 'error',
|
||||
'prefer-const': 'warn',
|
||||
'eqeqeq': ['error', 'always'],
|
||||
'no-unreachable': 'error',
|
||||
},
|
||||
};
|
||||
@@ -0,0 +1,18 @@
|
||||
{
|
||||
"name": "webui",
|
||||
"version": "1.0.0",
|
||||
"type": "module",
|
||||
"description": "",
|
||||
"main": "index.js",
|
||||
"scripts": {
|
||||
"test": "echo \"Error: no test specified\" && exit 1",
|
||||
"lint": "eslint web/js/**/*.js",
|
||||
"lint:fix": "eslint web/js/**/*.js --fix"
|
||||
},
|
||||
"keywords": [],
|
||||
"author": "",
|
||||
"license": "ISC",
|
||||
"devDependencies": {
|
||||
"eslint": "^8.57.1"
|
||||
}
|
||||
}
|
||||
@@ -12,7 +12,7 @@ export class StreamDiscoveryAPI {
|
||||
discover(request, callbacks) {
|
||||
this.close();
|
||||
|
||||
const url = new URL(`${this.baseURL}/api/v1/streams/discover`);
|
||||
const url = new URL(`${this.baseURL}/api/v1/streams/discover`, window.location.origin);
|
||||
|
||||
fetch(url, {
|
||||
method: 'POST',
|
||||
@@ -39,7 +39,8 @@ export class StreamDiscoveryAPI {
|
||||
|
||||
for (const line of lines) {
|
||||
if (line.startsWith('event:')) {
|
||||
const eventType = line.substring(6).trim();
|
||||
// Parse event type (not currently used, but available for future features)
|
||||
// const eventType = line.substring(6).trim();
|
||||
continue;
|
||||
}
|
||||
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
import { Go2RTCGenerator } from '../config-generators/go2rtc/index.js';
|
||||
import { FrigateGenerator } from '../config-generators/frigate/index.js';
|
||||
// import { FrigateGenerator } from '../config-generators/frigate/index.js'; // Reserved for future use
|
||||
|
||||
export class ConfigPanel {
|
||||
constructor() {
|
||||
|
||||
@@ -45,7 +45,7 @@ export class StreamCarousel {
|
||||
<div class="stream-url">${this.truncateURL(stream.url)}</div>
|
||||
${stream.resolution ? `<div class="stream-meta">Resolution: ${stream.resolution}</div>` : ''}
|
||||
${stream.codec ? `<div class="stream-meta">Codec: ${stream.codec}${stream.fps ? ` • ${stream.fps} fps` : ''}${stream.bitrate ? ` • ${Math.round(stream.bitrate / 1000)} Kbps` : ''}</div>` : ''}
|
||||
${stream.has_audio ? `<div class="stream-meta">Audio: Yes</div>` : ''}
|
||||
${stream.has_audio ? '<div class="stream-meta">Audio: Yes</div>' : ''}
|
||||
<div class="stream-actions">
|
||||
<button class="btn btn-primary btn-use" data-index="${index}">Use Stream</button>
|
||||
</div>
|
||||
|
||||
Reference in New Issue
Block a user