Some minor changes, bugfixes and improvements
parent
a1c1911b71
commit
dd67527c64
|
@ -746,7 +746,7 @@ export class ConnectionCommandHandler extends AbstractCommandHandler {
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
tree.moveChannel(channel, prev, parent, true);
|
tree.moveChannel(channel, prev, parent, false);
|
||||||
}
|
}
|
||||||
|
|
||||||
handleNotifyChannelEdited(json) {
|
handleNotifyChannelEdited(json) {
|
||||||
|
|
|
@ -1,7 +1,7 @@
|
||||||
import {AbstractServerConnection, ServerCommand, ServerConnectionEvents} from "tc-shared/connection/ConnectionBase";
|
import {AbstractServerConnection, ServerCommand, ServerConnectionEvents} from "tc-shared/connection/ConnectionBase";
|
||||||
import {ConnectionState} from "tc-shared/ConnectionHandler";
|
import {ConnectionState} from "tc-shared/ConnectionHandler";
|
||||||
import * as log from "tc-shared/log";
|
import * as log from "tc-shared/log";
|
||||||
import {LogCategory, logDebug, logError, logTrace, logWarn} from "tc-shared/log";
|
import {group, LogCategory, logDebug, logError, logGroupNative, logTrace, LogType, logWarn} from "tc-shared/log";
|
||||||
import {AbstractCommandHandler} from "tc-shared/connection/AbstractCommandHandler";
|
import {AbstractCommandHandler} from "tc-shared/connection/AbstractCommandHandler";
|
||||||
import {CommandResult} from "tc-shared/connection/ServerConnectionDeclaration";
|
import {CommandResult} from "tc-shared/connection/ServerConnectionDeclaration";
|
||||||
import {tr, tra} from "tc-shared/i18n/localize";
|
import {tr, tra} from "tc-shared/i18n/localize";
|
||||||
|
@ -11,7 +11,6 @@ import {SdpCompressor, SdpProcessor} from "./SdpUtils";
|
||||||
import {ErrorCode} from "tc-shared/connection/ErrorCode";
|
import {ErrorCode} from "tc-shared/connection/ErrorCode";
|
||||||
import {WhisperTarget} from "tc-shared/voice/VoiceWhisper";
|
import {WhisperTarget} from "tc-shared/voice/VoiceWhisper";
|
||||||
import {globalAudioContext} from "tc-backend/audio/player";
|
import {globalAudioContext} from "tc-backend/audio/player";
|
||||||
import * as sdpTransform from "sdp-transform";
|
|
||||||
|
|
||||||
const kSdpCompressionMode = 1;
|
const kSdpCompressionMode = 1;
|
||||||
|
|
||||||
|
@ -185,7 +184,10 @@ class CommandHandler extends AbstractCommandHandler {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if(RTCConnection.kEnableSdpTrace) {
|
if(RTCConnection.kEnableSdpTrace) {
|
||||||
logTrace(LogCategory.WEBRTC, tr("Received remote %s:\n%s"), data.mode, data.sdp);
|
const gr = logGroupNative(LogType.TRACE, LogCategory.WEBRTC, tra("Original remote SDP ({})", data.mode as string));
|
||||||
|
gr.collapsed(true);
|
||||||
|
gr.log("%s", data.sdp);
|
||||||
|
gr.end();
|
||||||
}
|
}
|
||||||
try {
|
try {
|
||||||
sdp = this.sdpProcessor.processIncomingSdp(sdp, data.mode);
|
sdp = this.sdpProcessor.processIncomingSdp(sdp, data.mode);
|
||||||
|
@ -195,7 +197,10 @@ class CommandHandler extends AbstractCommandHandler {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if(RTCConnection.kEnableSdpTrace) {
|
if(RTCConnection.kEnableSdpTrace) {
|
||||||
logTrace(LogCategory.WEBRTC, tr("Patched remote %s:\n%s"), data.mode, sdp);
|
const gr = logGroupNative(LogType.TRACE, LogCategory.WEBRTC, tra("Patched remote SDP ({})", data.mode as string));
|
||||||
|
gr.collapsed(true);
|
||||||
|
gr.log("%s", sdp);
|
||||||
|
gr.end();
|
||||||
}
|
}
|
||||||
if(data.mode === "answer") {
|
if(data.mode === "answer") {
|
||||||
this.handle["peer"].setRemoteDescription({
|
this.handle["peer"].setRemoteDescription({
|
||||||
|
@ -217,7 +222,10 @@ class CommandHandler extends AbstractCommandHandler {
|
||||||
}).then(() => this.handle["peer"].createAnswer())
|
}).then(() => this.handle["peer"].createAnswer())
|
||||||
.then(async answer => {
|
.then(async answer => {
|
||||||
if(RTCConnection.kEnableSdpTrace) {
|
if(RTCConnection.kEnableSdpTrace) {
|
||||||
logTrace(LogCategory.WEBRTC, tr("Generated local answer due to remote %s:\n%s"), data.mode, answer.sdp);
|
const gr = logGroupNative(LogType.TRACE, LogCategory.WEBRTC, tra("Original local SDP ({})", data.mode as string));
|
||||||
|
gr.collapsed(true);
|
||||||
|
gr.log("%s", answer.sdp);
|
||||||
|
gr.end();
|
||||||
}
|
}
|
||||||
answer.sdp = this.sdpProcessor.processOutgoingSdp(answer.sdp, "answer");
|
answer.sdp = this.sdpProcessor.processOutgoingSdp(answer.sdp, "answer");
|
||||||
|
|
||||||
|
@ -227,7 +235,10 @@ class CommandHandler extends AbstractCommandHandler {
|
||||||
.then(answer => {
|
.then(answer => {
|
||||||
answer.sdp = SdpCompressor.compressSdp(answer.sdp, kSdpCompressionMode);
|
answer.sdp = SdpCompressor.compressSdp(answer.sdp, kSdpCompressionMode);
|
||||||
if(RTCConnection.kEnableSdpTrace) {
|
if(RTCConnection.kEnableSdpTrace) {
|
||||||
logTrace(LogCategory.WEBRTC, tr("Patched answer to remote %s:\n%s"), data.mode, answer.sdp);
|
const gr = logGroupNative(LogType.TRACE, LogCategory.WEBRTC, tra("Patched local SDP ({})", data.mode as string));
|
||||||
|
gr.collapsed(true);
|
||||||
|
gr.log("%s", answer.sdp);
|
||||||
|
gr.end();
|
||||||
}
|
}
|
||||||
|
|
||||||
return this.connection.send_command("rtcsessiondescribe", {
|
return this.connection.send_command("rtcsessiondescribe", {
|
||||||
|
@ -898,11 +909,17 @@ export class RTCConnection {
|
||||||
if(this.peer !== peer) { return; }
|
if(this.peer !== peer) { return; }
|
||||||
|
|
||||||
if(RTCConnection.kEnableSdpTrace) {
|
if(RTCConnection.kEnableSdpTrace) {
|
||||||
logTrace(LogCategory.WEBRTC, tr("Generated initial local offer:\n%s"), offer.sdp);
|
const gr = logGroupNative(LogType.TRACE, LogCategory.WEBRTC, tra("Original initial local SDP (offer)"));
|
||||||
|
gr.collapsed(true);
|
||||||
|
gr.log("%s", offer.sdp);
|
||||||
|
gr.end();
|
||||||
}
|
}
|
||||||
try {
|
try {
|
||||||
offer.sdp = this.sdpProcessor.processOutgoingSdp(offer.sdp, "offer");
|
offer.sdp = this.sdpProcessor.processOutgoingSdp(offer.sdp, "offer");
|
||||||
logTrace(LogCategory.WEBRTC, tr("Patched initial local offer:\n%s"), offer.sdp);
|
const gr = logGroupNative(LogType.TRACE, LogCategory.WEBRTC, tra("Patched initial local SDP (offer)"));
|
||||||
|
gr.collapsed(true);
|
||||||
|
gr.log("%s", offer.sdp);
|
||||||
|
gr.end();
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
logError(LogCategory.WEBRTC, tr("Failed to preprocess outgoing initial offer: %o"), error);
|
logError(LogCategory.WEBRTC, tr("Failed to preprocess outgoing initial offer: %o"), error);
|
||||||
this.handleFatalError(tr("Failed to preprocess outgoing initial offer"), true);
|
this.handleFatalError(tr("Failed to preprocess outgoing initial offer"), true);
|
||||||
|
|
|
@ -33,7 +33,7 @@ export enum LogType {
|
||||||
ERROR
|
ERROR
|
||||||
}
|
}
|
||||||
|
|
||||||
let category_mapping = new Map<number, string>([
|
let categoryMapping = new Map<number, string>([
|
||||||
[LogCategory.CHANNEL, "Channel "],
|
[LogCategory.CHANNEL, "Channel "],
|
||||||
[LogCategory.CHANNEL_PROPERTIES, "Channel "],
|
[LogCategory.CHANNEL_PROPERTIES, "Channel "],
|
||||||
[LogCategory.CLIENT, "Client "],
|
[LogCategory.CLIENT, "Client "],
|
||||||
|
@ -92,7 +92,7 @@ enum GroupMode {
|
||||||
NATIVE,
|
NATIVE,
|
||||||
PREFIX
|
PREFIX
|
||||||
}
|
}
|
||||||
const group_mode: GroupMode = GroupMode.PREFIX;
|
const defaultGroupMode: GroupMode = GroupMode.PREFIX;
|
||||||
|
|
||||||
//Category Example: <url>?log.i18n.enabled=0
|
//Category Example: <url>?log.i18n.enabled=0
|
||||||
//Level Example A: <url>?log.level.trace.enabled=0
|
//Level Example A: <url>?log.level.trace.enabled=0
|
||||||
|
@ -134,7 +134,7 @@ function logDirect(type: LogType, message: string, ...optionalParams: any[]) {
|
||||||
export function log(type: LogType, category: LogCategory, message: string, ...optionalParams: any[]) {
|
export function log(type: LogType, category: LogCategory, message: string, ...optionalParams: any[]) {
|
||||||
if(!enabled_mapping.get(category)) return;
|
if(!enabled_mapping.get(category)) return;
|
||||||
|
|
||||||
optionalParams.unshift(category_mapping.get(category));
|
optionalParams.unshift(categoryMapping.get(category));
|
||||||
message = "[%s] " + message;
|
message = "[%s] " + message;
|
||||||
logDirect(type, message, ...optionalParams);
|
logDirect(type, message, ...optionalParams);
|
||||||
}
|
}
|
||||||
|
@ -182,13 +182,20 @@ export function logError(category: LogCategory, message: string, ...optionalPara
|
||||||
|
|
||||||
export function group(level: LogType, category: LogCategory, name: string, ...optionalParams: any[]) : Group {
|
export function group(level: LogType, category: LogCategory, name: string, ...optionalParams: any[]) : Group {
|
||||||
name = "[%s] " + name;
|
name = "[%s] " + name;
|
||||||
optionalParams.unshift(category_mapping.get(category));
|
optionalParams.unshift(categoryMapping.get(category));
|
||||||
|
|
||||||
return new Group(group_mode, level, category, name, optionalParams);
|
return new Group(defaultGroupMode, level, category, name, optionalParams);
|
||||||
|
}
|
||||||
|
|
||||||
|
export function logGroupNative(level: LogType, category: LogCategory, name: string, ...optionalParams: any[]) : Group {
|
||||||
|
name = "[%s] " + name;
|
||||||
|
optionalParams.unshift(categoryMapping.get(category));
|
||||||
|
|
||||||
|
return new Group(GroupMode.NATIVE, level, category, name, optionalParams);
|
||||||
}
|
}
|
||||||
|
|
||||||
export function table(level: LogType, category: LogCategory, title: string, args: any) {
|
export function table(level: LogType, category: LogCategory, title: string, args: any) {
|
||||||
if(group_mode == GroupMode.NATIVE) {
|
if(defaultGroupMode == GroupMode.NATIVE) {
|
||||||
console.groupCollapsed(title);
|
console.groupCollapsed(title);
|
||||||
console.table(args);
|
console.table(args);
|
||||||
console.groupEnd();
|
console.groupEnd();
|
||||||
|
@ -209,9 +216,9 @@ export class Group {
|
||||||
|
|
||||||
private readonly name: string;
|
private readonly name: string;
|
||||||
private readonly optionalParams: any[][];
|
private readonly optionalParams: any[][];
|
||||||
private _collapsed: boolean = false;
|
private isCollapsed: boolean = false;
|
||||||
private initialized = false;
|
private initialized = false;
|
||||||
private _log_prefix: string;
|
private logPrefix: string;
|
||||||
|
|
||||||
constructor(mode: GroupMode, level: LogType, category: LogCategory, name: string, optionalParams: any[][], owner: Group = undefined) {
|
constructor(mode: GroupMode, level: LogType, category: LogCategory, name: string, optionalParams: any[][], owner: Group = undefined) {
|
||||||
this.level = level;
|
this.level = level;
|
||||||
|
@ -227,7 +234,7 @@ export class Group {
|
||||||
}
|
}
|
||||||
|
|
||||||
collapsed(flag: boolean = true) : this {
|
collapsed(flag: boolean = true) : this {
|
||||||
this._collapsed = flag;
|
this.isCollapsed = flag;
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -238,17 +245,17 @@ export class Group {
|
||||||
|
|
||||||
if(!this.initialized) {
|
if(!this.initialized) {
|
||||||
if(this.mode == GroupMode.NATIVE) {
|
if(this.mode == GroupMode.NATIVE) {
|
||||||
if(this._collapsed && console.groupCollapsed) {
|
if(this.isCollapsed && console.groupCollapsed) {
|
||||||
console.groupCollapsed(this.name, ...this.optionalParams);
|
console.groupCollapsed(this.name, ...this.optionalParams);
|
||||||
} else {
|
} else {
|
||||||
console.group(this.name, ...this.optionalParams);
|
console.group(this.name, ...this.optionalParams);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
this._log_prefix = " ";
|
this.logPrefix = " ";
|
||||||
let parent = this.owner;
|
let parent = this.owner;
|
||||||
while(parent) {
|
while(parent) {
|
||||||
if(parent.mode == GroupMode.PREFIX) {
|
if(parent.mode == GroupMode.PREFIX) {
|
||||||
this._log_prefix = this._log_prefix + parent._log_prefix;
|
this.logPrefix = this.logPrefix + parent.logPrefix;
|
||||||
} else {
|
} else {
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
@ -259,7 +266,7 @@ export class Group {
|
||||||
if(this.mode == GroupMode.NATIVE) {
|
if(this.mode == GroupMode.NATIVE) {
|
||||||
logDirect(this.level, message, ...optionalParams);
|
logDirect(this.level, message, ...optionalParams);
|
||||||
} else {
|
} else {
|
||||||
logDirect(this.level, "[%s] " + this._log_prefix + message, category_mapping.get(this.category), ...optionalParams);
|
logDirect(this.level, "[%s] " + this.logPrefix + message, categoryMapping.get(this.category), ...optionalParams);
|
||||||
}
|
}
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
@ -272,11 +279,11 @@ export class Group {
|
||||||
}
|
}
|
||||||
|
|
||||||
get prefix() : string {
|
get prefix() : string {
|
||||||
return this._log_prefix;
|
return this.logPrefix;
|
||||||
}
|
}
|
||||||
|
|
||||||
set prefix(prefix: string) {
|
set prefix(prefix: string) {
|
||||||
this._log_prefix = prefix;
|
this.logPrefix = prefix;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -131,22 +131,24 @@ if(!JSON.map_to) {
|
||||||
|
|
||||||
if(!JSON.map_field_to) {
|
if(!JSON.map_field_to) {
|
||||||
JSON.map_field_to = function<T>(object: T, value: any, field: string) : boolean {
|
JSON.map_field_to = function<T>(object: T, value: any, field: string) : boolean {
|
||||||
let field_type = typeof(object[field]);
|
let fieldType = typeof object[field];
|
||||||
let new_object;
|
let newValue;
|
||||||
if(field_type == "string" || field_type == "object" || field_type == "undefined")
|
if(fieldType == "string" || fieldType == "object" || fieldType == "undefined") {
|
||||||
new_object = value;
|
newValue = value;
|
||||||
else if(field_type == "number")
|
} else if(fieldType == "number") {
|
||||||
new_object = parseFloat(value);
|
newValue = parseFloat(value);
|
||||||
else if(field_type == "boolean")
|
} else if(fieldType == "boolean") {
|
||||||
new_object = value == "1" || value == "true";
|
newValue = typeof value === "boolean" && value || value === "1" || value === "true";
|
||||||
else {
|
} else {
|
||||||
console.warn(tr("Invalid object type %s for entry %s"), field_type, field);
|
console.warn(tr("Invalid object type %s for entry %s"), fieldType, field);
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(new_object === object[field as string]) return false;
|
if(newValue === object[field]) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
object[field as string] = new_object;
|
object[field] = newValue;
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -194,8 +194,7 @@ export class ChannelEntry extends ChannelTreeEntry<ChannelEvents> {
|
||||||
this.properties = new ChannelProperties();
|
this.properties = new ChannelProperties();
|
||||||
this.channelId = channelId;
|
this.channelId = channelId;
|
||||||
this.properties.channel_name = channelName;
|
this.properties.channel_name = channelName;
|
||||||
|
this.parsed_channel_name = new ParsedChannelName(channelName, false);
|
||||||
this.parsed_channel_name = new ParsedChannelName("undefined", false);
|
|
||||||
|
|
||||||
this.clientPropertyChangedListener = (event: ClientEvents["notify_properties_updated"]) => {
|
this.clientPropertyChangedListener = (event: ClientEvents["notify_properties_updated"]) => {
|
||||||
if("client_nickname" in event.updated_properties || "client_talk_power" in event.updated_properties) {
|
if("client_nickname" in event.updated_properties || "client_talk_power" in event.updated_properties) {
|
||||||
|
@ -575,6 +574,7 @@ export class ChannelEntry extends ChannelTreeEntry<ChannelEvents> {
|
||||||
for(const variable of variables) {
|
for(const variable of variables) {
|
||||||
let key = variable.key;
|
let key = variable.key;
|
||||||
let value = variable.value;
|
let value = variable.value;
|
||||||
|
|
||||||
if(!JSON.map_field_to(this.properties, value, variable.key)) {
|
if(!JSON.map_field_to(this.properties, value, variable.key)) {
|
||||||
/* no update */
|
/* no update */
|
||||||
continue;
|
continue;
|
||||||
|
@ -584,7 +584,7 @@ export class ChannelEntry extends ChannelTreeEntry<ChannelEvents> {
|
||||||
this.parsed_channel_name = new ParsedChannelName(value, this.hasParent());
|
this.parsed_channel_name = new ParsedChannelName(value, this.hasParent());
|
||||||
} else if(key == "channel_order") {
|
} else if(key == "channel_order") {
|
||||||
let order = this.channelTree.findChannel(this.properties.channel_order);
|
let order = this.channelTree.findChannel(this.properties.channel_order);
|
||||||
this.channelTree.moveChannel(this, order, this.parent, true);
|
this.channelTree.moveChannel(this, order, this.parent, false);
|
||||||
} else if(key === "channel_icon_id") {
|
} else if(key === "channel_icon_id") {
|
||||||
this.properties.channel_icon_id = variable.value as any >>> 0; /* unsigned 32 bit number! */
|
this.properties.channel_icon_id = variable.value as any >>> 0; /* unsigned 32 bit number! */
|
||||||
} else if(key == "channel_description") {
|
} else if(key == "channel_description") {
|
||||||
|
|
|
@ -251,7 +251,7 @@ export class ChannelTree {
|
||||||
handleChannelCreated(previous: ChannelEntry, parent: ChannelEntry, channelId: number, channelName: string) : ChannelEntry {
|
handleChannelCreated(previous: ChannelEntry, parent: ChannelEntry, channelId: number, channelName: string) : ChannelEntry {
|
||||||
const channel = new ChannelEntry(this, channelId, channelName);
|
const channel = new ChannelEntry(this, channelId, channelName);
|
||||||
this.channels.push(channel);
|
this.channels.push(channel);
|
||||||
this.moveChannel(channel, previous, parent, false);
|
this.moveChannel(channel, previous, parent, true);
|
||||||
this.events.fire("notify_channel_created", { channel: channel });
|
this.events.fire("notify_channel_created", { channel: channel });
|
||||||
return channel;
|
return channel;
|
||||||
}
|
}
|
||||||
|
@ -300,12 +300,16 @@ export class ChannelTree {
|
||||||
channel.parent = undefined;
|
channel.parent = undefined;
|
||||||
}
|
}
|
||||||
|
|
||||||
moveChannel(channel: ChannelEntry, channelPrevious: ChannelEntry, parent: ChannelEntry, triggerMoveEvent: boolean) {
|
moveChannel(channel: ChannelEntry, channelPrevious: ChannelEntry, parent: ChannelEntry, isInsertMove: boolean) {
|
||||||
if(channelPrevious != null && channelPrevious.parent != parent) {
|
if(channelPrevious != null && channelPrevious.parent != parent) {
|
||||||
console.error(tr("Invalid channel move (different parents! (%o|%o)"), channelPrevious.parent, parent);
|
console.error(tr("Invalid channel move (different parents! (%o|%o)"), channelPrevious.parent, parent);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if(!isInsertMove && channel.channel_previous === channelPrevious && channel.parent === parent) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
const previousParent = channel.parent_channel();
|
const previousParent = channel.parent_channel();
|
||||||
const previousOrder = channel.channel_previous;
|
const previousOrder = channel.channel_previous;
|
||||||
|
|
||||||
|
@ -355,13 +359,15 @@ export class ChannelTree {
|
||||||
debugger;
|
debugger;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(triggerMoveEvent) {
|
if(!isInsertMove) {
|
||||||
this.events.fire("notify_channel_moved", {
|
this.events.fire("notify_channel_moved", {
|
||||||
channel: channel,
|
channel: channel,
|
||||||
previousOrder: previousOrder,
|
previousOrder: previousOrder,
|
||||||
previousParent: previousParent
|
previousParent: previousParent
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
channel.properties.channel_order = previousOrder ? previousOrder.channelId : 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
deleteClient(client: ClientEntry, reason: { reason: ViewReasonId, message?: string, serverLeave: boolean }) {
|
deleteClient(client: ClientEntry, reason: { reason: ViewReasonId, message?: string, serverLeave: boolean }) {
|
||||||
|
|
Loading…
Reference in New Issue