Browse Source

Reworks Logger to allow for re-use in webviews

Avoids static class
main
Eric Amodio 1 year ago
parent
commit
11c8edeae5
46 changed files with 357 additions and 275 deletions
  1. +2
    -1
      src/annotations/gutterBlameAnnotationProvider.ts
  2. +2
    -1
      src/annotations/gutterChangesAnnotationProvider.ts
  3. +2
    -1
      src/annotations/gutterHeatmapBlameAnnotationProvider.ts
  4. +3
    -2
      src/annotations/lineAnnotationController.ts
  5. +2
    -1
      src/commands/switchMode.ts
  6. +16
    -0
      src/config.ts
  7. +10
    -0
      src/constants.ts
  8. +2
    -2
      src/container.ts
  9. +34
    -6
      src/env/node/git/git.ts
  10. +3
    -2
      src/env/node/git/localGitProvider.ts
  11. +1
    -2
      src/env/node/git/locator.ts
  12. +1
    -1
      src/env/node/git/vslsGitProvider.ts
  13. +24
    -13
      src/extension.ts
  14. +2
    -1
      src/git/gitProviderService.ts
  15. +2
    -1
      src/git/models/repository.ts
  16. +2
    -1
      src/git/remotes/richRemoteProvider.ts
  17. +3
    -3
      src/hovers/hovers.ts
  18. +2
    -1
      src/keyboard.ts
  19. +41
    -0
      src/logScope.ts
  20. +86
    -114
      src/logger.ts
  21. +2
    -2
      src/messages.ts
  22. +5
    -3
      src/plus/github/github.ts
  23. +3
    -2
      src/plus/github/githubGitProvider.ts
  24. +5
    -3
      src/plus/gitlab/gitlab.ts
  25. +2
    -1
      src/plus/subscription/authenticationProvider.ts
  26. +2
    -1
      src/plus/subscription/serverConnection.ts
  27. +2
    -1
      src/plus/subscription/subscriptionService.ts
  28. +3
    -2
      src/statusbar/statusBarController.ts
  29. +5
    -38
      src/system/decorators/log.ts
  30. +18
    -27
      src/system/stopwatch.ts
  31. +2
    -1
      src/trackers/gitLineTracker.ts
  32. +2
    -1
      src/trackers/lineTracker.ts
  33. +2
    -1
      src/views/nodes/fileHistoryTrackerNode.ts
  34. +2
    -1
      src/views/nodes/lineHistoryTrackerNode.ts
  35. +2
    -1
      src/views/viewBase.ts
  36. +2
    -1
      src/vsls/guest.ts
  37. +2
    -1
      src/vsls/host.ts
  38. +2
    -2
      src/webviews/apps/commitDetails/commitDetails.ts
  39. +4
    -4
      src/webviews/apps/home/home.ts
  40. +7
    -9
      src/webviews/apps/plus/graph/graph.tsx
  41. +3
    -3
      src/webviews/apps/plus/timeline/timeline.ts
  42. +1
    -1
      src/webviews/apps/rebase/rebase.ts
  43. +29
    -6
      src/webviews/apps/shared/appBase.ts
  44. +6
    -8
      src/webviews/apps/shared/appWithConfigBase.ts
  45. +2
    -1
      src/webviews/commitDetails/commitDetailsWebviewView.ts
  46. +2
    -1
      src/webviews/webviewViewBase.ts

+ 2
- 1
src/annotations/gutterBlameAnnotationProvider.ts View File

@ -8,8 +8,9 @@ import type { CommitFormatOptions } from '../git/formatters/commitFormatter';
import { CommitFormatter } from '../git/formatters/commitFormatter';
import type { GitBlame } from '../git/models/blame';
import type { GitCommit } from '../git/models/commit';
import { getLogScope } from '../logScope';
import { filterMap } from '../system/array';
import { getLogScope, log } from '../system/decorators/log';
import { log } from '../system/decorators/log';
import { first } from '../system/iterable';
import { Stopwatch } from '../system/stopwatch';
import type { TokenOptions } from '../system/string';

+ 2
- 1
src/annotations/gutterChangesAnnotationProvider.ts View File

@ -12,7 +12,8 @@ import type { Container } from '../container';
import type { GitCommit } from '../git/models/commit';
import type { GitDiff } from '../git/models/diff';
import { localChangesMessage } from '../hovers/hovers';
import { getLogScope, log } from '../system/decorators/log';
import { getLogScope } from '../logScope';
import { log } from '../system/decorators/log';
import { Stopwatch } from '../system/stopwatch';
import type { GitDocumentState, TrackedDocument } from '../trackers/gitDocumentTracker';
import type { AnnotationContext } from './annotationProvider';

+ 2
- 1
src/annotations/gutterHeatmapBlameAnnotationProvider.ts View File

@ -3,7 +3,8 @@ import { Range } from 'vscode';
import { FileAnnotationType } from '../configuration';
import type { Container } from '../container';
import type { GitCommit } from '../git/models/commit';
import { getLogScope, log } from '../system/decorators/log';
import { getLogScope } from '../logScope';
import { log } from '../system/decorators/log';
import { Stopwatch } from '../system/stopwatch';
import type { GitDocumentState } from '../trackers/gitDocumentTracker';
import type { TrackedDocument } from '../trackers/trackedDocument';

+ 3
- 2
src/annotations/lineAnnotationController.ts View File

@ -13,9 +13,10 @@ import { CommitFormatter } from '../git/formatters/commitFormatter';
import type { GitCommit } from '../git/models/commit';
import type { PullRequest } from '../git/models/pullRequest';
import { RichRemoteProviders } from '../git/remotes/remoteProviderConnections';
import type { LogScope } from '../logger';
import { Logger } from '../logger';
import { debug, getLogScope, log } from '../system/decorators/log';
import type { LogScope } from '../logScope';
import { getLogScope } from '../logScope';
import { debug, log } from '../system/decorators/log';
import { once } from '../system/event';
import { count, every, filter } from '../system/iterable';
import type { PromiseCancelledErrorWithId } from '../system/promise';

+ 2
- 1
src/commands/switchMode.ts View File

@ -2,9 +2,10 @@ import { ConfigurationTarget } from 'vscode';
import { configuration } from '../configuration';
import { Commands } from '../constants';
import type { Container } from '../container';
import { getLogScope } from '../logScope';
import { ModePicker } from '../quickpicks/modePicker';
import { command } from '../system/command';
import { getLogScope, log } from '../system/decorators/log';
import { log } from '../system/decorators/log';
import { Command } from './base';
@command()

+ 16
- 0
src/config.ts View File

@ -1,3 +1,4 @@
import { LogLevel } from './constants';
import type { DateTimeFormat } from './system/date';
export interface Config {
@ -784,3 +785,18 @@ export interface ViewsFilesConfig {
layout: ViewFilesLayout;
threshold: number;
}
export function fromOutputLevel(level: LogLevel | OutputLevel): LogLevel {
switch (level) {
case OutputLevel.Silent:
return LogLevel.Off;
case OutputLevel.Errors:
return LogLevel.Error;
case OutputLevel.Verbose:
return LogLevel.Info;
case OutputLevel.Debug:
return LogLevel.Debug;
default:
return level;
}
}

+ 10
- 0
src/constants.ts View File

@ -1,4 +1,6 @@
export const quickPickTitleMaxChars = 80;
export const slowCallWarningThreshold = 500;
export const ImageMimetypes: Record<string, string> = {
'.png': 'image/png',
'.gif': 'image/gif',
@ -399,6 +401,14 @@ export const enum GlyphChars {
ZeroWidthSpace = '\u200b',
}
export const enum LogLevel {
Off = 'off',
Error = 'error',
Warn = 'warn',
Info = 'info',
Debug = 'debug',
}
export const enum Schemes {
DebugConsole = 'debug',
File = 'file',

+ 2
- 2
src/container.ts View File

@ -9,7 +9,7 @@ import { setDefaultGravatarsStyle } from './avatars';
import { GitCodeLensController } from './codelens/codeLensController';
import type { ToggleFileAnnotationCommandArgs } from './commands';
import type { FileAnnotationType, ModeConfig } from './configuration';
import { AnnotationsToggleMode, configuration, DateSource, DateStyle } from './configuration';
import { AnnotationsToggleMode, configuration, DateSource, DateStyle, fromOutputLevel } from './configuration';
import { Commands } from './constants';
import { EventBus } from './eventBus';
import { GitFileSystemProvider } from './git/fsProvider';
@ -259,7 +259,7 @@ export class Container {
this._mode = undefined;
if (configuration.changed(e, 'outputLevel')) {
Logger.logLevel = configuration.get('outputLevel');
Logger.logLevel = fromOutputLevel(configuration.get('outputLevel'));
}
if (configuration.changed(e, 'defaultGravatarsStyle')) {

+ 34
- 6
src/env/node/git/git.ts View File

@ -1,10 +1,10 @@
import type { ChildProcess, SpawnOptions } from 'child_process';
import { spawn } from 'child_process';
import * as process from 'process';
import type { CancellationToken } from 'vscode';
import type { CancellationToken, OutputChannel } from 'vscode';
import { Uri, window, workspace } from 'vscode';
import { hrtime } from '@env/hrtime';
import { GlyphChars } from '../../../constants';
import { GlyphChars, LogLevel, slowCallWarningThreshold } from '../../../constants';
import type { GitCommandOptions, GitSpawnOptions } from '../../../git/commandOptions';
import { GitErrorHandling } from '../../../git/commandOptions';
import type { GitDiffFilter } from '../../../git/models/diff';
@ -25,6 +25,7 @@ import { fsExists, run, RunError } from './shell';
const emptyArray = Object.freeze([]) as unknown as any[];
const emptyObj = Object.freeze({});
const emptyStr = '';
const gitBranchDefaultConfigs = Object.freeze(['-c', 'color.branch=false']);
const gitDiffDefaultConfigs = Object.freeze(['-c', 'color.diff=false']);
@ -186,7 +187,7 @@ export class Git {
this.pendingCommands.delete(command);
const duration = getDurationMilliseconds(start);
const slow = duration > Logger.slowCallWarningThreshold;
const slow = duration > slowCallWarningThreshold;
const status =
slow || waiting
? ` (${slow ? `slow${waiting ? ', waiting' : ''}` : ''}${waiting ? 'waiting' : ''})`
@ -205,7 +206,7 @@ export class Git {
} else {
Logger.log(`[GIT ] ${gitCommand} ${GlyphChars.Dot} ${duration} ms${status}`);
}
Logger.logGitCommand(
this.logGitCommand(
`${gitCommand}${exception != null ? ` ${GlyphChars.Dot} FAILED` : ''}${waiting ? ' (waited)' : ''}`,
duration,
exception,
@ -266,7 +267,7 @@ export class Git {
proc.once('error', e => (exception = e));
proc.once('exit', () => {
const duration = getDurationMilliseconds(start);
const slow = duration > Logger.slowCallWarningThreshold;
const slow = duration > slowCallWarningThreshold;
const status = slow ? ' (slow)' : '';
if (exception != null) {
@ -282,7 +283,7 @@ export class Git {
} else {
Logger.log(`[SGIT ] ${gitCommand} ${GlyphChars.Dot} ${duration} ms${status}`);
}
Logger.logGitCommand(
this.logGitCommand(
`${gitCommand}${exception != null ? ` ${GlyphChars.Dot} FAILED` : ''}`,
duration,
exception,
@ -1896,6 +1897,33 @@ export class Git {
return undefined;
}
}
private _gitOutput: OutputChannel | undefined;
private logGitCommand(command: string, duration: number, ex?: Error): void {
if (Logger.enabled(LogLevel.Debug) && !Logger.isDebugging) return;
const slow = duration > slowCallWarningThreshold;
if (Logger.isDebugging) {
if (ex != null) {
console.error(Logger.timestamp, '[GitLens (Git)]', command ?? emptyStr, ex);
} else if (slow) {
console.warn(Logger.timestamp, '[GitLens (Git)]', command ?? emptyStr);
} else {
console.log(Logger.timestamp, '[GitLens (Git)]', command ?? emptyStr);
}
}
if (this._gitOutput == null) {
this._gitOutput = window.createOutputChannel('GitLens (Git)');
}
this._gitOutput.appendLine(
`${Logger.timestamp} [${slow ? '*' : ' '}${duration.toString().padStart(6)}ms] ${command}${
ex != null ? `\n\n${ex.toString()}` : emptyStr
}`,
);
}
}
export function getShaInLogRegex(sha: string) {

+ 3
- 2
src/env/node/git/localGitProvider.ts View File

@ -116,8 +116,9 @@ import { getRemoteProviderMatcher, loadRemoteProviders } from '../../../git/remo
import type { RichRemoteProvider } from '../../../git/remotes/richRemoteProvider';
import type { GitSearch, GitSearchResultData, GitSearchResults, SearchQuery } from '../../../git/search';
import { getGitArgsFromSearchQuery, getSearchQueryComparisonKey } from '../../../git/search';
import type { LogScope } from '../../../logger';
import { Logger } from '../../../logger';
import type { LogScope } from '../../../logScope';
import { getLogScope } from '../../../logScope';
import {
showGenericErrorMessage,
showGitDisabledErrorMessage,
@ -135,7 +136,7 @@ import type {
import { countStringLength, filterMap } from '../../../system/array';
import { TimedCancellationSource } from '../../../system/cancellation';
import { gate } from '../../../system/decorators/gate';
import { debug, getLogScope, log } from '../../../system/decorators/log';
import { debug, log } from '../../../system/decorators/log';
import { filterMap as filterMapIterable, find, first, join, last, map, some } from '../../../system/iterable';
import {
commonBaseIndex,

+ 1
- 2
src/env/node/git/locator.ts View File

@ -1,7 +1,6 @@
import { join as joinPaths } from 'path';
import * as process from 'process';
import { GlyphChars } from '../../../constants';
import { LogLevel } from '../../../logger';
import { GlyphChars, LogLevel } from '../../../constants';
import { any } from '../../../system/promise';
import { Stopwatch } from '../../../system/stopwatch';
import { findExecutable, run } from './shell';

+ 1
- 1
src/env/node/git/vslsGitProvider.ts View File

@ -6,7 +6,7 @@ import type { GitProviderDescriptor } from '../../../git/gitProvider';
import { GitProviderId } from '../../../git/gitProvider';
import type { Repository } from '../../../git/models/repository';
import { Logger } from '../../../logger';
import { getLogScope } from '../../../system/decorators/log';
import { getLogScope } from '../../../logScope';
import { addVslsPrefixIfNeeded } from '../../../system/path';
import { Git } from './git';
import { LocalGitProvider } from './localGitProvider';

+ 24
- 13
src/extension.ts View File

@ -1,19 +1,19 @@
import type { ExtensionContext } from 'vscode';
import { version as codeVersion, env, extensions, window, workspace } from 'vscode';
import { version as codeVersion, env, ExtensionMode, extensions, Uri, window, workspace } from 'vscode';
import { hrtime } from '@env/hrtime';
import { isWeb } from '@env/platform';
import { Api } from './api/api';
import type { CreatePullRequestActionContext, GitLensApi, OpenPullRequestActionContext } from './api/gitlens';
import type { CreatePullRequestOnRemoteCommandArgs, OpenPullRequestOnRemoteCommandArgs } from './commands';
import { configuration, Configuration, OutputLevel } from './configuration';
import { Commands, ContextKeys, CoreCommands } from './constants';
import { configuration, Configuration, fromOutputLevel, OutputLevel } from './configuration';
import { Commands, ContextKeys, CoreCommands, LogLevel } from './constants';
import { Container } from './container';
import { setContext } from './context';
import { isGitUri } from './git/gitUri';
import { getBranchNameWithoutRemote, isBranch } from './git/models/branch';
import { isCommit } from './git/models/commit';
import { isTag } from './git/models/tag';
import { Logger, LogLevel } from './logger';
import { Logger } from './logger';
import {
showDebugLoggingWarningMessage,
showInsidersErrorMessage,
@ -36,17 +36,28 @@ export async function activate(context: ExtensionContext): Promise
const prerelease = insiders || satisfies(gitlensVersion, '> 2020.0.0');
const outputLevel = configuration.get('outputLevel');
Logger.configure(context, configuration.get('outputLevel'), o => {
if (isGitUri(o)) {
return `GitUri(${o.toString(true)}${o.repoPath ? ` repoPath=${o.repoPath}` : ''}${
o.sha ? ` sha=${o.sha}` : ''
})`;
}
Logger.configure(
{
name: 'GitLens',
createChannel: function (name: string) {
return window.createOutputChannel(name);
},
toLoggable: function (o: any) {
if (isGitUri(o)) {
return `GitUri(${o.toString(true)}${o.repoPath ? ` repoPath=${o.repoPath}` : ''}${
o.sha ? ` sha=${o.sha}` : ''
})`;
}
if (o instanceof Uri) return `Uri(${o.toString(true)})`;
if (isBranch(o) || isCommit(o) || isTag(o) || isViewNode(o)) return o.toString();
if (isBranch(o) || isCommit(o) || isTag(o) || isViewNode(o)) return o.toString();
return undefined;
});
return undefined;
},
},
fromOutputLevel(configuration.get('outputLevel')),
context.extensionMode === ExtensionMode.Development,
);
const sw = new Stopwatch(
`GitLens${prerelease ? (insiders ? ' (Insiders)' : ' (pre-release)') : ''} v${gitlensVersion}`,

+ 2
- 1
src/git/gitProviderService.ts View File

@ -18,6 +18,7 @@ import { setContext } from '../context';
import { AccessDeniedError, ProviderNotFoundError } from '../errors';
import type { FeatureAccess, Features, PlusFeatures, RepoFeatureAccess } from '../features';
import { Logger } from '../logger';
import { getLogScope } from '../logScope';
import type { SubscriptionChangeEvent } from '../plus/subscription/subscriptionService';
import type { RepoComparisonKey } from '../repositories';
import { asRepoComparisonKey, Repositories } from '../repositories';
@ -25,7 +26,7 @@ import type { Subscription } from '../subscription';
import { isSubscriptionPaidPlan, SubscriptionPlanId } from '../subscription';
import { groupByFilterMap, groupByMap, joinUnique } from '../system/array';
import { gate } from '../system/decorators/gate';
import { debug, getLogScope, log } from '../system/decorators/log';
import { debug, log } from '../system/decorators/log';
import { count, filter, first, flatMap, join, map, some } from '../system/iterable';
import { getBestPath, getScheme, isAbsolute, maybeUri, normalizePath } from '../system/path';
import { cancellable, fastestSettled, getSettledValue, isPromise, PromiseCancelledError } from '../system/promise';

+ 2
- 1
src/git/models/repository.ts View File

@ -8,13 +8,14 @@ import { CoreGitCommands, CoreGitConfiguration, Schemes } from '../../constants'
import type { Container } from '../../container';
import type { FeatureAccess, Features, PlusFeatures } from '../../features';
import { Logger } from '../../logger';
import { getLogScope } from '../../logScope';
import { showCreatePullRequestPrompt, showGenericErrorMessage } from '../../messages';
import { asRepoComparisonKey } from '../../repositories';
import { filterMap, groupByMap } from '../../system/array';
import { executeActionCommand, executeCoreGitCommand } from '../../system/command';
import { formatDate, fromNow } from '../../system/date';
import { gate } from '../../system/decorators/gate';
import { debug, getLogScope, log, logName } from '../../system/decorators/log';
import { debug, log, logName } from '../../system/decorators/log';
import { debounce } from '../../system/function';
import { filter, join, some } from '../../system/iterable';
import { updateRecordValue } from '../../system/object';

+ 2
- 1
src/git/remotes/richRemoteProvider.ts View File

@ -6,11 +6,12 @@ import { configuration } from '../../configuration';
import type { Container } from '../../container';
import { AuthenticationError, ProviderRequestClientError } from '../../errors';
import { Logger } from '../../logger';
import { getLogScope } from '../../logScope';
import { showIntegrationDisconnectedTooManyFailedRequestsWarningMessage } from '../../messages';
import type { IntegrationAuthenticationSessionDescriptor } from '../../plus/integrationAuthentication';
import { isSubscriptionPaidPlan, isSubscriptionPreviewTrialExpired } from '../../subscription';
import { gate } from '../../system/decorators/gate';
import { debug, getLogScope, log } from '../../system/decorators/log';
import { debug, log } from '../../system/decorators/log';
import { isPromise } from '../../system/promise';
import type { Account } from '../models/author';
import type { DefaultBranch } from '../models/defaultBranch';

+ 3
- 3
src/hovers/hovers.ts View File

@ -3,7 +3,7 @@ import { MarkdownString } from 'vscode';
import { hrtime } from '@env/hrtime';
import { DiffWithCommand, ShowQuickCommitCommand } from '../commands';
import { configuration } from '../configuration';
import { GlyphChars } from '../constants';
import { GlyphChars, LogLevel } from '../constants';
import { Container } from '../container';
import { CommitFormatter } from '../git/formatters/commitFormatter';
import { GitUri } from '../git/gitUri';
@ -12,8 +12,8 @@ import type { GitDiffHunk, GitDiffHunkLine } from '../git/models/diff';
import type { PullRequest } from '../git/models/pullRequest';
import { GitRevision } from '../git/models/reference';
import type { GitRemote } from '../git/models/remote';
import { Logger, LogLevel } from '../logger';
import { getNewLogScope } from '../system/decorators/log';
import { Logger } from '../logger';
import { getNewLogScope } from '../logScope';
import { count } from '../system/iterable';
import { getSettledValue, PromiseCancelledError } from '../system/promise';
import { getDurationMilliseconds } from '../system/string';

+ 2
- 1
src/keyboard.ts View File

@ -2,8 +2,9 @@ import { Disposable } from 'vscode';
import { ContextKeys } from './constants';
import { setContext } from './context';
import { Logger } from './logger';
import { getLogScope } from './logScope';
import { registerCommand } from './system/command';
import { getLogScope, log } from './system/decorators/log';
import { log } from './system/decorators/log';
export declare interface KeyCommand {
onDidPressKey?(key: Keys): void | Promise<void>;

+ 41
- 0
src/logScope.ts View File

@ -0,0 +1,41 @@
const maxSmallIntegerV8 = 2 ** 30; // Max number that can be stored in V8's smis (small integers)
const scopes = new Map<number, LogScope>();
let scopeCounter = 0;
export interface LogScope {
readonly scopeId?: number;
readonly prefix: string;
exitDetails?: string;
}
export function clearLogScope(scopeId: number) {
scopes.delete(scopeId);
}
export function getLogScope(): LogScope | undefined {
return scopes.get(scopeCounter);
}
export function getNewLogScope(prefix: string): LogScope {
const scopeId = getNextLogScopeId();
return {
scopeId: scopeId,
prefix: `[${String(scopeId).padStart(5)}] ${prefix}`,
};
}
export function getLogScopeId(): number {
return scopeCounter;
}
export function getNextLogScopeId(): number {
if (scopeCounter === maxSmallIntegerV8) {
scopeCounter = 0;
}
return ++scopeCounter;
}
export function setLogScope(scopeId: number, scope: LogScope) {
scopes.set(scopeId, scope);
}

+ 86
- 114
src/logger.ts View File

@ -1,27 +1,7 @@
import type { ExtensionContext, OutputChannel } from 'vscode';
import { ExtensionMode, Uri, window } from 'vscode';
import { OutputLevel } from './configuration';
import { LogLevel } from './constants';
import type { LogScope } from './logScope';
const emptyStr = '';
const outputChannelName = 'GitLens';
const consolePrefix = '[GitLens]';
const gitOutputChannelName = 'GitLens (Git)';
const gitConsolePrefix = '[GitLens (Git)]';
export const enum LogLevel {
Off = 'off',
Error = 'error',
Warn = 'warn',
Info = 'info',
Debug = 'debug',
}
export interface LogScope {
readonly scopeId?: number;
readonly prefix: string;
exitDetails?: string;
}
const enum OrderedLevel {
Off = 0,
@ -31,48 +11,63 @@ const enum OrderedLevel {
Debug = 4,
}
// eslint-disable-next-line @typescript-eslint/no-extraneous-class
export class Logger {
static readonly slowCallWarningThreshold = 500;
export interface LogChannelProvider {
readonly name: string;
createChannel(name: string): LogChannel;
toLoggable?(o: unknown): string | undefined;
}
private static output: OutputChannel | undefined;
private static customLoggableFn: ((o: object) => string | undefined) | undefined;
export interface LogChannel {
readonly name: string;
appendLine(value: string): void;
dispose(): void;
show(preserveFocus?: boolean): void;
}
static configure(context: ExtensionContext, outputLevel: OutputLevel, loggableFn?: (o: any) => string | undefined) {
this._isDebugging = context.extensionMode === ExtensionMode.Development;
this.logLevel = outputLevel;
this.customLoggableFn = loggableFn;
export const Logger = new (class Logger {
private output: LogChannel | undefined;
private provider: LogChannelProvider | undefined;
configure(provider: LogChannelProvider, logLevel: LogLevel, debugging: boolean = false) {
this.provider = provider;
this._isDebugging = debugging;
this.logLevel = logLevel;
}
static enabled(level: LogLevel): boolean {
enabled(level: LogLevel): boolean {
return this.level >= toOrderedLevel(level);
}
private static _isDebugging: boolean;
static get isDebugging() {
private _isDebugging = false;
get isDebugging() {
return this._isDebugging;
}
private static level: OrderedLevel = OrderedLevel.Off;
private static _logLevel: LogLevel = LogLevel.Off;
static get logLevel(): LogLevel {
private level: OrderedLevel = OrderedLevel.Off;
private _logLevel: LogLevel = LogLevel.Off;
get logLevel(): LogLevel {
return this._logLevel;
}
static set logLevel(value: LogLevel | OutputLevel) {
this._logLevel = fromOutputLevel(value);
set logLevel(value: LogLevel) {
this._logLevel = value;
this.level = toOrderedLevel(this._logLevel);
if (value === LogLevel.Off) {
this.output?.dispose();
this.output = undefined;
} else {
this.output = this.output ?? window.createOutputChannel(outputChannelName);
this.output = this.output ?? this.provider!.createChannel(this.provider!.name);
}
}
static debug(message: string, ...params: any[]): void;
static debug(scope: LogScope | undefined, message: string, ...params: any[]): void;
static debug(scopeOrMessage: LogScope | string | undefined, ...params: any[]): void {
get timestamp(): string {
return `[${new Date().toISOString().replace(/T/, ' ').slice(0, -1)}]`;
}
debug(message: string, ...params: any[]): void;
debug(scope: LogScope | undefined, message: string, ...params: any[]): void;
debug(scopeOrMessage: LogScope | string | undefined, ...params: any[]): void {
if (this.level < OrderedLevel.Debug && !this.isDebugging) return;
let message;
@ -87,16 +82,16 @@ export class Logger {
}
if (this.isDebugging) {
console.log(this.timestamp, consolePrefix, message ?? emptyStr, ...params);
console.log(this.timestamp, `[${this.provider!.name}]`, message ?? emptyStr, ...params);
}
if (this.output == null || this.level < OrderedLevel.Debug) return;
this.output.appendLine(`${this.timestamp} ${message ?? emptyStr}${this.toLoggableParams(true, params)}`);
}
static error(ex: Error | unknown, message?: string, ...params: any[]): void;
static error(ex: Error | unknown, scope?: LogScope, message?: string, ...params: any[]): void;
static error(ex: Error | unknown, scopeOrMessage: LogScope | string | undefined, ...params: any[]): void {
error(ex: Error | unknown, message?: string, ...params: any[]): void;
error(ex: Error | unknown, scope?: LogScope, message?: string, ...params: any[]): void;
error(ex: Error | unknown, scopeOrMessage: LogScope | string | undefined, ...params: any[]): void {
if (this.level < OrderedLevel.Error && !this.isDebugging) return;
let message;
@ -117,7 +112,7 @@ export class Logger {
}
if (this.isDebugging) {
console.error(this.timestamp, consolePrefix, message ?? emptyStr, ...params, ex);
console.error(this.timestamp, `[${this.provider!.name}]`, message ?? emptyStr, ...params, ex);
}
if (this.output == null || this.level < OrderedLevel.Error) return;
@ -126,9 +121,9 @@ export class Logger {
);
}
static log(message: string, ...params: any[]): void;
static log(scope: LogScope | undefined, message: string, ...params: any[]): void;
static log(scopeOrMessage: LogScope | string | undefined, ...params: any[]): void {
log(message: string, ...params: any[]): void;
log(scope: LogScope | undefined, message: string, ...params: any[]): void;
log(scopeOrMessage: LogScope | string | undefined, ...params: any[]): void {
if (this.level < OrderedLevel.Info && !this.isDebugging) return;
let message;
@ -143,16 +138,16 @@ export class Logger {
}
if (this.isDebugging) {
console.log(this.timestamp, consolePrefix, message ?? emptyStr, ...params);
console.log(this.timestamp, `[${this.provider!.name}]`, message ?? emptyStr, ...params);
}
if (this.output == null || this.level < OrderedLevel.Info) return;
this.output.appendLine(`${this.timestamp} ${message ?? emptyStr}${this.toLoggableParams(false, params)}`);
}
static warn(message: string, ...params: any[]): void;
static warn(scope: LogScope | undefined, message: string, ...params: any[]): void;
static warn(scopeOrMessage: LogScope | string | undefined, ...params: any[]): void {
warn(message: string, ...params: any[]): void;
warn(scope: LogScope | undefined, message: string, ...params: any[]): void;
warn(scopeOrMessage: LogScope | string | undefined, ...params: any[]): void {
if (this.level < OrderedLevel.Warn && !this.isDebugging) return;
let message;
@ -167,37 +162,31 @@ export class Logger {
}
if (this.isDebugging) {
console.warn(this.timestamp, consolePrefix, message ?? emptyStr, ...params);
console.warn(this.timestamp, `[${this.provider!.name}]`, message ?? emptyStr, ...params);
}
if (this.output == null || this.level < OrderedLevel.Warn) return;
this.output.appendLine(`${this.timestamp} ${message ?? emptyStr}${this.toLoggableParams(false, params)}`);
}
static showOutputChannel(): void {
this.output?.show();
showOutputChannel(preserveFocus?: boolean): void {
this.output?.show(preserveFocus);
}
static toLoggable(p: any, sanitize?: ((key: string, value: any) => any) | undefined) {
if (typeof p !== 'object') return String(p);
if (this.customLoggableFn != null) {
const loggable = this.customLoggableFn(p);
if (loggable != null) return loggable;
}
if (p instanceof Uri) return `Uri(${p.toString(true)})`;
toLoggable(o: any, sanitize?: ((key: string, value: any) => any) | undefined) {
if (typeof o !== 'object') return String(o);
const loggable = this.provider!.toLoggable?.(o);
if (loggable != null) return loggable;
try {
return JSON.stringify(p, sanitize);
return JSON.stringify(o, sanitize);
} catch {
return '<error>';
}
}
private static get timestamp(): string {
return `[${new Date().toISOString().replace(/T/, ' ').slice(0, -1)}]`;
}
private static toLoggableParams(debugOnly: boolean, params: any[]) {
private toLoggableParams(debugOnly: boolean, params: any[]) {
if (params.length === 0 || (debugOnly && this.level < OrderedLevel.Debug && !this.isDebugging)) {
return emptyStr;
}
@ -205,49 +194,7 @@ export class Logger {
const loggableParams = params.map(p => this.toLoggable(p)).join(', ');
return loggableParams.length !== 0 ? ` \u2014 ${loggableParams}` : emptyStr;
}
static gitOutput: OutputChannel | undefined;
static logGitCommand(command: string, duration: number, ex?: Error): void {
if (this.level < OrderedLevel.Debug && !this.isDebugging) return;
const slow = duration > Logger.slowCallWarningThreshold;
if (this.isDebugging) {
if (ex != null) {
console.error(this.timestamp, gitConsolePrefix, command ?? emptyStr, ex);
} else if (slow) {
console.warn(this.timestamp, gitConsolePrefix, command ?? emptyStr);
} else {
console.log(this.timestamp, gitConsolePrefix, command ?? emptyStr);
}
}
if (this.gitOutput == null) {
this.gitOutput = window.createOutputChannel(gitOutputChannelName);
}
this.gitOutput.appendLine(
`${this.timestamp} [${slow ? '*' : ' '}${duration.toString().padStart(6)}ms] ${command}${
ex != null ? `\n\n${ex.toString()}` : emptyStr
}`,
);
}
}
function fromOutputLevel(level: LogLevel | OutputLevel): LogLevel {
switch (level) {
case OutputLevel.Silent:
return LogLevel.Off;
case OutputLevel.Errors:
return LogLevel.Error;
case OutputLevel.Verbose:
return LogLevel.Info;
case OutputLevel.Debug:
return LogLevel.Debug;
default:
return level;
}
}
})();
function toOrderedLevel(logLevel: LogLevel): OrderedLevel {
switch (logLevel) {
@ -280,3 +227,28 @@ export function getLoggableName(instance: Function | object) {
const index = name.indexOf('_');
return index === -1 ? name : name.substr(index + 1);
}
export interface LogProvider {
enabled(logLevel: LogLevel): boolean;
log(logLevel: LogLevel, scope: LogScope | undefined, message: string, ...params: any[]): void;
}
export const defaultLogProvider: LogProvider = {
enabled: (logLevel: LogLevel) => Logger.enabled(logLevel),
log: (logLevel: LogLevel, scope: LogScope | undefined, message: string, ...params: any[]) => {
switch (logLevel) {
case LogLevel.Error:
Logger.error('', scope, message, ...params);
break;
case LogLevel.Warn:
Logger.warn(scope, message, ...params);
break;
case LogLevel.Info:
Logger.log(scope, message, ...params);
break;
default:
Logger.debug(scope, message, ...params);
break;
}
},
};

+ 2
- 2
src/messages.ts View File

@ -1,9 +1,9 @@
import type { MessageItem } from 'vscode';
import { ConfigurationTarget, env, Uri, window } from 'vscode';
import { configuration, SuppressedMessages } from './configuration';
import { Commands } from './constants';
import { Commands, LogLevel } from './constants';
import type { GitCommit } from './git/models/commit';
import { Logger, LogLevel } from './logger';
import { Logger } from './logger';
import { executeCommand } from './system/command';
export function showCommitHasNoPreviousCommitWarningMessage(commit?: GitCommit): Promise<MessageItem | undefined> {

+ 5
- 3
src/plus/github/github.ts View File

@ -8,6 +8,7 @@ import { Disposable, EventEmitter, Uri, window } from 'vscode';
import { fetch, getProxyAgent, wrapForForcedInsecureSSL } from '@env/fetch';
import { isWeb } from '@env/platform';
import { configuration } from '../../configuration';
import { LogLevel } from '../../constants';
import type { Container } from '../../container';
import {
AuthenticationError,
@ -26,13 +27,14 @@ import { GitRevision } from '../../git/models/reference';
import type { GitUser } from '../../git/models/user';
import { getGitHubNoReplyAddressParts } from '../../git/remotes/github';
import type { RichRemoteProvider } from '../../git/remotes/richRemoteProvider';
import type { LogScope } from '../../logger';
import { Logger, LogLevel } from '../../logger';
import { Logger } from '../../logger';
import type { LogScope } from '../../logScope';
import { getLogScope } from '../../logScope';
import {
showIntegrationRequestFailed500WarningMessage,
showIntegrationRequestTimedOutWarningMessage,
} from '../../messages';
import { debug, getLogScope } from '../../system/decorators/log';
import { debug } from '../../system/decorators/log';
import { Stopwatch } from '../../system/stopwatch';
import { base64 } from '../../system/string';
import type { Version } from '../../system/version';

+ 3
- 2
src/plus/github/githubGitProvider.ts View File

@ -78,10 +78,11 @@ import { getRemoteProviderMatcher, loadRemoteProviders } from '../../git/remotes
import type { RichRemoteProvider } from '../../git/remotes/richRemoteProvider';
import type { GitSearch, GitSearchResultData, GitSearchResults, SearchQuery } from '../../git/search';
import { getSearchQueryComparisonKey, parseSearchQuery } from '../../git/search';
import type { LogScope } from '../../logger';
import { Logger } from '../../logger';
import type { LogScope } from '../../logScope';
import { getLogScope } from '../../logScope';
import { gate } from '../../system/decorators/gate';
import { debug, getLogScope, log } from '../../system/decorators/log';
import { debug, log } from '../../system/decorators/log';
import { filterMap, first, last, some } from '../../system/iterable';
import { isAbsolute, isFolderGlob, maybeUri, normalizePath, relative } from '../../system/path';
import { fastestSettled, getSettledValue } from '../../system/promise';

+ 5
- 3
src/plus/gitlab/gitlab.ts View File

@ -4,6 +4,7 @@ import type { RequestInit, Response } from '@env/fetch';
import { fetch, getProxyAgent, wrapForForcedInsecureSSL } from '@env/fetch';
import { isWeb } from '@env/platform';
import { configuration } from '../../configuration';
import { LogLevel } from '../../constants';
import type { Container } from '../../container';
import {
AuthenticationError,
@ -19,13 +20,14 @@ import type { IssueOrPullRequest } from '../../git/models/issue';
import { IssueOrPullRequestType } from '../../git/models/issue';
import { PullRequest } from '../../git/models/pullRequest';
import type { RichRemoteProvider } from '../../git/remotes/richRemoteProvider';
import type { LogScope } from '../../logger';
import { Logger, LogLevel } from '../../logger';
import { Logger } from '../../logger';
import type { LogScope } from '../../logScope';
import { getLogScope } from '../../logScope';
import {
showIntegrationRequestFailed500WarningMessage,
showIntegrationRequestTimedOutWarningMessage,
} from '../../messages';
import { debug, getLogScope } from '../../system/decorators/log';
import { debug } from '../../system/decorators/log';
import { Stopwatch } from '../../system/stopwatch';
import { equalsIgnoreCase } from '../../system/string';
import type { GitLabCommit, GitLabIssue, GitLabUser } from './models';

+ 2
- 1
src/plus/subscription/authenticationProvider.ts View File

@ -7,7 +7,8 @@ import { authentication, Disposable, EventEmitter, extensions, window } from 'vs
import { uuid } from '@env/crypto';
import type { Container } from '../../container';
import { Logger } from '../../logger';
import { debug, getLogScope } from '../../system/decorators/log';
import { getLogScope } from '../../logScope';
import { debug } from '../../system/decorators/log';
import type { ServerConnection } from './serverConnection';
interface StoredSession {

+ 2
- 1
src/plus/subscription/serverConnection.ts View File

@ -5,7 +5,8 @@ import type { Response } from '@env/fetch';
import { fetch, getProxyAgent } from '@env/fetch';
import type { Container } from '../../container';
import { Logger } from '../../logger';
import { debug, getLogScope } from '../../system/decorators/log';
import { getLogScope } from '../../logScope';
import { debug } from '../../system/decorators/log';
import { memoize } from '../../system/decorators/memoize';
import type { DeferredEvent, DeferredEventExecutor } from '../../system/event';
import { promisifyDeferred } from '../../system/event';

+ 2
- 1
src/plus/subscription/subscriptionService.ts View File

@ -29,6 +29,7 @@ import { setContext } from '../../context';
import { AccountValidationError } from '../../errors';
import type { RepositoriesChangeEvent } from '../../git/gitProviderService';
import { Logger } from '../../logger';
import { getLogScope } from '../../logScope';
import type { Subscription } from '../../subscription';
import {
computeSubscriptionState,
@ -46,7 +47,7 @@ import {
import { executeCommand, registerCommand } from '../../system/command';
import { createFromDateDelta } from '../../system/date';
import { gate } from '../../system/decorators/gate';
import { debug, getLogScope, log } from '../../system/decorators/log';
import { debug, log } from '../../system/decorators/log';
import { memoize } from '../../system/decorators/memoize';
import type { Deferrable } from '../../system/function';
import { debounce, once } from '../../system/function';

+ 3
- 2
src/statusbar/statusBarController.ts View File

@ -8,10 +8,11 @@ import { CommitFormatter } from '../git/formatters/commitFormatter';
import type { GitCommit } from '../git/models/commit';
import type { PullRequest } from '../git/models/pullRequest';
import { detailsMessage } from '../hovers/hovers';
import type { LogScope } from '../logger';
import { Logger } from '../logger';
import type { LogScope } from '../logScope';
import { getLogScope } from '../logScope';
import { asCommand } from '../system/command';
import { debug, getLogScope } from '../system/decorators/log';
import { debug } from '../system/decorators/log';
import { once } from '../system/event';
import { PromiseCancelledError } from '../system/promise';
import { isTextEditor } from '../system/utils';

+ 5
- 38
src/system/decorators/log.ts View File

@ -1,47 +1,14 @@
/* eslint-disable @typescript-eslint/no-unsafe-return */
import { hrtime } from '@env/hrtime';
import type { LogScope } from '../../logger';
import { getLoggableName, Logger, LogLevel } from '../../logger';
import { LogLevel, slowCallWarningThreshold } from '../../constants';
import { getLoggableName, Logger } from '../../logger';
import type { LogScope } from '../../logScope';
import { clearLogScope, getNextLogScopeId, setLogScope } from '../../logScope';
import { getParameters } from '../function';
import { isPromise } from '../promise';
import { getDurationMilliseconds } from '../string';
const emptyStr = '';
const maxSmallIntegerV8 = 2 ** 30; // Max number that can be stored in V8's smis (small integers)
const scopes = new Map<number, LogScope>();
let scopeCounter = 0;
export function getLogScope(): LogScope | undefined {
return scopes.get(scopeCounter);
}
export function getNewLogScope(prefix: string): LogScope {
const scopeId = getNextLogScopeId();
return {
scopeId: scopeId,
prefix: `[${String(scopeId).padStart(5)}] ${prefix}`,
};
}
export function getLogScopeId(): number {
return scopeCounter;
}
export function getNextLogScopeId(): number {
if (scopeCounter === maxSmallIntegerV8) {
scopeCounter = 0;
}
return ++scopeCounter;
}
function clearLogScope(scopeId: number) {
scopes.delete(scopeId);
}
function setLogScope(scopeId: number, scope: LogScope) {
scopes.set(scopeId, scope);
}
export interface LogContext {
id: number;
@ -277,7 +244,7 @@ export function log any>(options?: LogOptions, deb
let timing;
if (start != null) {
duration = getDurationMilliseconds(start);
if (duration > Logger.slowCallWarningThreshold) {
if (duration > slowCallWarningThreshold) {
exitLogFn = warnFn;
timing = ` \u2022 ${duration} ms (slow)`;
} else {

+ 18
- 27
src/system/stopwatch.ts View File

@ -1,19 +1,22 @@
import { hrtime } from '@env/hrtime';
import { GlyphChars } from '../constants';
import type { LogScope } from '../logger';
import { Logger, LogLevel } from '../logger';
import { getNextLogScopeId } from './decorators/log';
import { GlyphChars, LogLevel } from '../constants';
import type { LogProvider } from '../logger';
import { defaultLogProvider } from '../logger';
import type { LogScope } from '../logScope';
import { getNextLogScopeId } from '../logScope';
type StopwatchLogOptions = { message?: string; suffix?: string };
type StopwatchOptions = {
log?: boolean | StopwatchLogOptions;
logLevel?: StopwatchLogLevel;
provider?: LogProvider;
};
type StopwatchLogLevel = Exclude<LogLevel, LogLevel.Off>;
export class Stopwatch {
private readonly instance = `[${String(getNextLogScopeId()).padStart(5)}] `;
private readonly logLevel: StopwatchLogLevel;
private readonly logProvider: LogProvider;
private _time: [number, number];
get startTime() {
@ -36,20 +39,21 @@ export class Stopwatch {
}
this.logLevel = options?.logLevel ?? LogLevel.Info;
this.logProvider = options?.provider ?? defaultLogProvider;
this._time = hrtime();
if (logOptions != null) {
if (!Logger.enabled(this.logLevel)) return;
if (!this.logProvider.enabled(this.logLevel)) return;
if (params.length) {
log(
this.logProvider.log(
this.logLevel,
logScope,
`${this.instance}${scope}${logOptions.message ?? ''}${logOptions.suffix ?? ''}`,
...params,
);
} else {
log(
this.logProvider.log(
this.logLevel,
logScope,
`${this.instance}${scope}${logOptions.message ?? ''}${logOptions.suffix ?? ''}`,
@ -81,7 +85,7 @@ export class Stopwatch {
options: StopwatchLogOptions | undefined,
logTotalElapsed: boolean,
): void {
if (!Logger.enabled(this.logLevel)) return;
if (!this.logProvider.enabled(this.logLevel)) return;
let logScope;
if (typeof scope !== 'string') {
@ -90,7 +94,11 @@ export class Stopwatch {
}
if (!logTotalElapsed) {
log(this.logLevel, logScope, `${this.instance}${scope}${options?.message ?? ''}${options?.suffix ?? ''}`);
this.logProvider.log(
this.logLevel,
logScope,
`${this.instance}${scope}${options?.message ?? ''}${options?.suffix ?? ''}`,
);
return;
}
@ -99,7 +107,7 @@ export class Stopwatch {
const ms = secs * 1000 + Math.floor(nanosecs / 1000000);
const prefix = `${this.instance}${scope}${options?.message ?? ''}`;
log(
this.logProvider.log(
ms > 250 ? LogLevel.Warn : this.logLevel,
logScope,
`${prefix ? `${prefix} ${GlyphChars.Dot} ` : ''}${ms} ms${options?.suffix ?? ''}`,
@ -122,20 +130,3 @@ export class Stopwatch {
Stopwatch.watches.delete(key);
}
}
function log(logLevel: StopwatchLogLevel, scope: LogScope | undefined, message: string, ...params: any[]) {
switch (logLevel) {
case LogLevel.Error:
Logger.error('', scope, message, ...params);
break;
case LogLevel.Warn:
Logger.warn(scope, message, ...params);
break;
case LogLevel.Info:
Logger.log(scope, message, ...params);
break;
default:
Logger.debug(scope, message, ...params);
break;
}
}

+ 2
- 1
src/trackers/gitLineTracker.ts View File

@ -4,7 +4,8 @@ import { configuration } from '../configuration';
import { GlyphChars } from '../constants';
import type { Container } from '../container';
import type { GitCommit } from '../git/models/commit';
import { debug, getLogScope } from '../system/decorators/log';
import { getLogScope } from '../logScope';
import { debug } from '../system/decorators/log';
import type {
DocumentBlameStateChangeEvent,
DocumentContentChangeEvent,

+ 2
- 1
src/trackers/lineTracker.ts View File

@ -1,7 +1,8 @@
import type { Event, Selection, TextEditor, TextEditorSelectionChangeEvent } from 'vscode';
import { Disposable, EventEmitter, window } from 'vscode';
import { Logger } from '../logger';
import { debug, getLogScope } from '../system/decorators/log';
import { getLogScope } from '../logScope';
import { debug } from '../system/decorators/log';
import type { Deferrable } from '../system/function';
import { debounce } from '../system/function';
import { isTextEditor } from '../system/utils';

+ 2
- 1
src/views/nodes/fileHistoryTrackerNode.ts View File

@ -7,9 +7,10 @@ import type { GitCommitish } from '../../git/gitUri';
import { GitUri, unknownGitUri } from '../../git/gitUri';
import { GitReference, GitRevision } from '../../git/models/reference';
import { Logger } from '../../logger';
import { getLogScope } from '../../logScope';
import { ReferencePicker } from '../../quickpicks/referencePicker';
import { gate } from '../../system/decorators/gate';
import { debug, getLogScope, log } from '../../system/decorators/log';
import { debug, log } from '../../system/decorators/log';
import type { Deferrable } from '../../system/function';
import { debounce } from '../../system/function';
import { isVirtualUri } from '../../system/utils';

+ 2
- 1
src/views/nodes/lineHistoryTrackerNode.ts View File

@ -7,9 +7,10 @@ import type { GitCommitish } from '../../git/gitUri';
import { GitUri, unknownGitUri } from '../../git/gitUri';
import { GitReference, GitRevision } from '../../git/models/reference';
import { Logger } from '../../logger';
import { getLogScope } from '../../logScope';
import { ReferencePicker } from '../../quickpicks/referencePicker';
import { gate } from '../../system/decorators/gate';
import { debug, getLogScope, log } from '../../system/decorators/log';
import { debug, log } from '../../system/decorators/log';
import { debounce } from '../../system/function';
import type { LinesChangeEvent } from '../../trackers/gitLineTracker';
import type { FileHistoryView } from '../fileHistoryView';

+ 2
- 1
src/views/viewBase.ts View File

@ -28,8 +28,9 @@ import type {
import { configuration, viewsCommonConfigKeys, viewsConfigKeys } from '../configuration';
import type { Container } from '../container';
import { Logger } from '../logger';
import { getLogScope } from '../logScope';
import { executeCommand } from '../system/command';
import { debug, getLogScope, log } from '../system/decorators/log';
import { debug, log } from '../system/decorators/log';
import { once } from '../system/event';
import { debounce } from '../system/function';
import { cancellable, isPromise } from '../system/promise';

+ 2
- 1
src/vsls/guest.ts View File

@ -4,7 +4,8 @@ import type { LiveShare, SharedServiceProxy } from '../@types/vsls';
import type { Container } from '../container';
import type { GitCommandOptions } from '../git/commandOptions';
import { Logger } from '../logger';
import { debug, getLogScope, log } from '../system/decorators/log';
import { getLogScope } from '../logScope';
import { debug, log } from '../system/decorators/log';
import { VslsHostService } from './host';
import type { RepositoryProxy, RequestType } from './protocol';
import { GetRepositoriesForUriRequestType, GitCommandRequestType } from './protocol';

+ 2
- 1
src/vsls/host.ts View File

@ -4,7 +4,8 @@ import { git } from '@env/providers';
import type { LiveShare, SharedService } from '../@types/vsls';
import type { Container } from '../container';
import { Logger } from '../logger';
import { debug, getLogScope, log } from '../system/decorators/log';
import { getLogScope } from '../logScope';
import { debug, log } from '../system/decorators/log';
import { join } from '../system/iterable';
import { isVslsRoot, normalizePath } from '../system/path';
import type {

+ 2
- 2
src/webviews/apps/commitDetails/commitDetails.ts View File

@ -50,7 +50,7 @@ export class CommitDetailsApp extends App> {
}
override onInitialize() {
this.log(`${this.appName}.onInitialize`);
this.log(`onInitialize()`);
this.renderContent();
}
@ -90,7 +90,7 @@ export class CommitDetailsApp extends App> {
protected override onMessageReceived(e: MessageEvent) {
const msg = e.data as IpcMessage;
this.log(`${this.appName}.onMessageReceived(${msg.id}): name=${msg.method}`);
this.log(`onMessageReceived(${msg.id}): name=${msg.method}`);
switch (msg.method) {
// case DidChangeRichStateNotificationType.method:

+ 4
- 4
src/webviews/apps/home/home.ts View File

@ -85,7 +85,7 @@ export class HomeApp extends App {
switch (msg.method) {
case DidChangeSubscriptionNotificationType.method:
this.log(`${this.appName}.onMessageReceived(${msg.id}): name=${msg.method}`);
this.log(`onMessageReceived(${msg.id}): name=${msg.method}`);
onIpc(DidChangeSubscriptionNotificationType, msg, params => {
this.state.subscription = params.subscription;
@ -96,7 +96,7 @@ export class HomeApp extends App {
});
break;
case DidChangeExtensionEnabledType.method:
this.log(`${this.appName}.onMessageReceived(${msg.id}): name=${msg.method}`);
this.log(`onMessageReceived(${msg.id}): name=${msg.method}`);
onIpc(DidChangeExtensionEnabledType, msg, params => {
this.state.extensionEnabled = params.extensionEnabled;
@ -104,7 +104,7 @@ export class HomeApp extends App {
});
break;
case DidChangeConfigurationType.method:
this.log(`${this.appName}.onMessageReceived(${msg.id}): name=${msg.method}`);
this.log(`onMessageReceived(${msg.id}): name=${msg.method}`);
onIpc(DidChangeConfigurationType, msg, params => {
this.state.plusEnabled = params.plusEnabled;
@ -112,7 +112,7 @@ export class HomeApp extends App {
});
break;
case DidChangeLayoutType.method:
this.log(`${this.appName}.onMessageReceived(${msg.id}): name=${msg.method}`);
this.log(`onMessageReceived(${msg.id}): name=${msg.method}`);
onIpc(DidChangeLayoutType, msg, params => {
this.state.layout = params.layout;

+ 7
- 9
src/webviews/apps/plus/graph/graph.tsx View File

@ -82,7 +82,7 @@ export class GraphApp extends App {
const disposables = super.onBind?.() ?? [];
// disposables.push(DOM.on(window, 'keyup', e => this.onKeyUp(e)));
this.log(`${this.appName}.onBind`);
this.log(`onBind()`);
this.ensureTheming(this.state);
@ -141,7 +141,7 @@ export class GraphApp extends App {
protected override onMessageReceived(e: MessageEvent) {
const msg = e.data as IpcMessage;
this.log(`${this.appName}.onMessageReceived(${msg.id}): name=${msg.method}`);
this.log(`onMessageReceived(${msg.id}): name=${msg.method}`);
switch (msg.method) {
case DidChangeNotificationType.method:
@ -215,7 +215,7 @@ export class GraphApp extends App {
const newRowsLength = params.rows.length;
this.log(
`${this.appName}.onMessageReceived(${msg.id}:${msg.method}): paging in ${newRowsLength} rows into existing ${previousRowsLength} rows at ${params.paging.startingCursor} (last existing row: ${lastId})`,
`onMessageReceived(${msg.id}:${msg.method}): paging in ${newRowsLength} rows into existing ${previousRowsLength} rows at ${params.paging.startingCursor} (last existing row: ${lastId})`,
);
rows = [];
@ -224,7 +224,7 @@ export class GraphApp extends App {
if (params.paging.startingCursor !== lastId) {
this.log(
`${this.appName}.onMessageReceived(${msg.id}:${msg.method}): searching for ${params.paging.startingCursor} in existing rows`,
`onMessageReceived(${msg.id}:${msg.method}): searching for ${params.paging.startingCursor} in existing rows`,
);
let i = 0;
@ -233,7 +233,7 @@ export class GraphApp extends App {
rows[i++] = row;
if (row.sha === params.paging.startingCursor) {
this.log(
`${this.appName}.onMessageReceived(${msg.id}:${msg.method}): found ${params.paging.startingCursor} in existing rows`,
`onMessageReceived(${msg.id}:${msg.method}): found ${params.paging.startingCursor} in existing rows`,
);
previousRowsLength = i;
@ -256,9 +256,7 @@ export class GraphApp extends App {
rows[previousRowsLength + i] = params.rows[i];
}
} else {
this.log(
`${this.appName}.onMessageReceived(${msg.id}:${msg.method}): setting to ${params.rows.length} rows`,
);
this.log(`onMessageReceived(${msg.id}:${msg.method}): setting to ${params.rows.length} rows`);
if (params.rows.length === 0) {
rows = this.state.rows;
@ -478,7 +476,7 @@ export class GraphApp extends App {
}
protected override setState(state: State, type?: IpcNotificationType<any> | InternalNotificationType) {
this.log(`${this.appName}.setState`);
this.log(`setState()`);
const themingChanged = this.ensureTheming(state);
// Avoid calling the base for now, since we aren't using the vscode state

+ 3
- 3
src/webviews/apps/plus/timeline/timeline.ts View File

@ -49,7 +49,7 @@ export class TimelineApp extends App {
switch (msg.method) {
case DidChangeNotificationType.method:
this.log(`${this.appName}.onMessageReceived(${msg.id}): name=${msg.method}`);
this.log(`onMessageReceived(${msg.id}): name=${msg.method}`);
onIpc(DidChangeNotificationType, msg, params => {
this.state = params.state;
@ -79,11 +79,11 @@ export class TimelineApp extends App {
}
}
private onPeriodChanged(e: Event, element: HTMLSelectElement) {
private onPeriodChanged(_e: Event, element: HTMLSelectElement) {
const value = element.options[element.selectedIndex].value;
assertPeriod(value);
this.log(`${this.appName}.onPeriodChanged: name=${element.name}, value=${value}`);
this.log(`onPeriodChanged(): name=${element.name}, value=${value}`);
this.sendCommand(UpdatePeriodCommandType, { period: value });
}

+ 1
- 1
src/webviews/apps/rebase/rebase.ts View File

@ -323,7 +323,7 @@ class RebaseEditor extends App {
switch (msg.method) {
case DidChangeNotificationType.method:
this.log(`${this.appName}.onMessageReceived(${msg.id}): name=${msg.method}`);
this.log(`onMessageReceived(${msg.id}): name=${msg.method}`);
onIpc(DidChangeNotificationType, msg, params => {
this.setState(params.state);

+ 29
- 6
src/webviews/apps/shared/appBase.ts View File

@ -1,4 +1,6 @@
/*global window document*/
import { LogLevel } from '../../../constants';
import { Logger } from '../../../logger';
import { debounce } from '../../../system/function';
import type {
IpcCommandType,
@ -42,8 +44,29 @@ export abstract class App {
this.state = (window as any).bootstrap;
(window as any).bootstrap = undefined;
this.log(`${this.appName}()`);
// this.log(`${this.appName}(${this.state ? JSON.stringify(this.state) : ''})`);
Logger.configure(
{
name: appName,
createChannel: function (name: string) {
return {
name: name,
appendLine: function (value: string) {
console.log(`[${name}] ${value}`);
},
dispose: function () {
// noop
},
show: function (_preserveFocus?: boolean) {
// noop
},
};
},
},
LogLevel.Debug,
);
this.log(`ctor()`);
// this.log(`ctor(${this.state ? JSON.stringify(this.state) : ''})`);
this._api = acquireVsCodeApi();
@ -55,7 +78,7 @@ export abstract class App {
disposables.push(initializeAndWatchThemeColors());
requestAnimationFrame(() => {
this.log(`${this.appName}.initializing`);
this.log(`ctor(): initializing...`);
try {
this.onInitialize?.();
@ -129,7 +152,7 @@ export abstract class App {
}
protected log(message: string, ...optionalParams: any[]) {
console.log(message, ...optionalParams);
Logger.log(message, ...optionalParams);
}
protected getState(): State {
@ -141,7 +164,7 @@ export abstract class App {
params: IpcMessageParams<TCommand>,
): void {
const id = nextIpcId();
this.log(`${this.appName}.sendCommand(${id}): name=${command.method}`);
this.log(`sendCommand(${id}): name=${command.method}`);
this.postMessage({ id: id, method: command.method, params: params });
}
@ -155,7 +178,7 @@ export abstract class App {
completion: TCompletion,
): Promise<IpcMessageParams<TCompletion>> {
const id = nextIpcId();
this.log(`${this.appName}.sendCommandWithCompletion(${id}): name=${command.method}`);
this.log(`sendCommandWithCompletion(${id}): name=${command.method}`);
const promise = new Promise<IpcMessageParams<TCompletion>>((resolve, reject) => {
let timeout: ReturnType<typeof setTimeout> | undefined;

+ 6
- 8
src/webviews/apps/shared/appWithConfigBase.ts View File

@ -70,7 +70,7 @@ export abstract class AppWithConfig extends Ap
protected override onMessageReceived(e: MessageEvent) {
const msg = e.data as IpcMessage;
this.log(`${this.appName}.onMessageReceived(${msg.id}): name=${msg.method}`);
this.log(`onMessageReceived(${msg.id}): name=${msg.method}`);
switch (msg.method) {
case DidOpenAnchorNotificationType.method: {
@ -108,7 +108,7 @@ export abstract class AppWithConfig extends Ap
}
protected onInputBlurred(element: HTMLInputElement) {
this.log(`${this.appName}.onInputBlurred: name=${element.name}, value=${element.value}`);
this.log(`onInputBlurred(${element.name}): value=${element.value})`);
const $popup = document.getElementById(`${element.name}.popup`);
if ($popup != null) {
@ -191,9 +191,7 @@ export abstract class AppWithConfig extends Ap
protected onInputChecked(element: HTMLInputElement) {
if (this._updating) return;
this.log(
`${this.appName}.onInputChecked: name=${element.name}, checked=${element.checked}, value=${element.value}`,
);
this.log(`onInputChecked(${element.name}): checked=${element.checked}, value=${element.value})`);
switch (element.dataset.settingType) {
case 'object': {
@ -273,7 +271,7 @@ export abstract class AppWithConfig extends Ap
}
protected onInputFocused(element: HTMLInputElement) {
this.log(`${this.appName}.onInputFocused: name=${element.name}, value=${element.value}`);
this.log(`onInputFocused(${element.name}): value=${element.value}`);
const $popup = document.getElementById(`${element.name}.popup`);
if ($popup != null) {
@ -292,7 +290,7 @@ export abstract class AppWithConfig extends Ap
const value = element.options[element.selectedIndex].value;
this.log(`${this.appName}.onInputSelected: name=${element.name}, value=${value}`);
this.log(`onInputSelected(${element.name}): value=${value}`);
this._changes[element.name] = ensureIfBooleanOrNull(value);
@ -302,7 +300,7 @@ export abstract class AppWithConfig extends Ap
protected onTokenMouseDown(element: HTMLElement, e: MouseEvent) {
if (this._updating) return;
this.log(`${this.appName}.onTokenClicked: id=${element.id}`);
this.log(`onTokenMouseDown(${element.id})`);
const setting = element.closest('.setting');
if (setting == null) return;

+ 2
- 1
src/webviews/commitDetails/commitDetailsWebviewView.ts View File

@ -28,10 +28,11 @@ import type { GitRevisionReference } from '../../git/models/reference';
import { GitReference } from '../../git/models/reference';
import type { GitRemote } from '../../git/models/remote';
import { Logger } from '../../logger';
import { getLogScope } from '../../logScope';
import type { ShowInCommitGraphCommandArgs } from '../../plus/webviews/graph/graphWebview';
import { executeCommand, executeCoreCommand } from '../../system/command';
import type { DateTimeFormat } from '../../system/date';
import { debug, getLogScope, log } from '../../system/decorators/log';
import { debug, log } from '../../system/decorators/log';
import type { Deferrable } from '../../system/function';
import { debounce } from '../../system/function';
import { map, union } from '../../system/iterable';

+ 2
- 1
src/webviews/webviewViewBase.ts View File

@ -12,8 +12,9 @@ import type { Commands, ContextKeys } from '../constants';
import type { Container } from '../container';
import { setContext } from '../context';
import { Logger } from '../logger';
import { getLogScope } from '../logScope';
import { executeCommand } from '../system/command';
import { debug, getLogScope, log, logName } from '../system/decorators/log';
import { debug, log, logName } from '../system/decorators/log';
import { serialize } from '../system/decorators/serialize';
import type { TrackedUsageFeatures } from '../usageTracker';
import type { IpcMessage, IpcMessageParams, IpcNotificationType, WebviewFocusChangedParams } from './protocol';

Loading…
Cancel
Save