Token导航 LogoToken导航TokenDH.com
前端设计执行命令github未标认证来源可访问许可证需确认审计通过

vscode-extension-refactorerVS Code extension refactorer 命令行

Agent Skill

vscode-extension-refactorer 用于处理 GitHub 仓库、Issue、Pull Request 和代码协作信息,适合在 Codex、Claude、Cursor、Gemini CLI 中需要围绕仓库状态、代码变更或协作事项进行整理时使用。可结合来源仓库、安装命令和原始 README 继续核验具体用法。安装前建议确认权限范围、维护状态,以及是否会触发联网、命令执行或文件读写。

总安装

563

周安装

23

GitHub Stars

18

下载量

182
CodexClaudeCursorGemini CLI

安装说明

本站只整理中文说明和来源信息,不托管安装包,也不代用户安装。

GitHub

来源数

2

许可证

unknown

最后核验

2026-05-01

来源状态

来源可访问

安装方式

通过对话安装

复制提示词发给支持本地命令或 Skills 的 AI 助手,先确认命令和权限,再让它执行。

请帮我安装这个 Agent Skill:vscode-extension-refactorer(VS Code extension refactorer 命令行)
来源仓库:https://github.com/s-hiraoku/vscode-sidebar-terminal
仓库路径:skills/vscode-extension-refactorer
安装命令:
npx skills add https://github.com/s-hiraoku/vscode-sidebar-terminal --skill vscode-extension-refactorer
安装前请先检查当前环境是否支持对应 CLI,并向我确认将要执行的命令、安装目录、联网范围和文件读写权限;确认后再执行。

命令行安装

复制命令到本机终端执行。该命令会通过 npx skills 从第三方来源获取 Skill;本站只展示命令,不托管安装包,也不自动执行。

skills.shnpx skills
npx skills add https://github.com/s-hiraoku/vscode-sidebar-terminal --skill vscode-extension-refactorer

简介

用于处理 GitHub 仓库、Issue、Pull Request 等协作信息。

  • 适合在重构项目中跟踪代码变更与团队反馈。vscode-extension-refactorer 属于前端设计类 Skill,可作为该场景下的辅助能力补充。
  • 支持对 Issue 和 PR 进行归类与上下文提取。
  • 使用前需确认是否涉及文件修改或命令执行权限。
  • 建议查阅原始文档了解具体集成方式与安全边界。

SKILL.md

VS Code Extension Refactorer

Overview

This skill enables systematic and safe refactoring of VS Code extension code. It provides structured workflows for identifying improvement opportunities, applying proven refactoring techniques, and ensuring code quality while maintaining functionality.

When to Use This Skill

  • Extracting classes, methods, or modules from large files
  • Reducing code duplication across the codebase
  • Improving TypeScript type safety and interfaces
  • Reorganizing module structure and dependencies
  • Applying design patterns (Manager, Coordinator, Factory, etc.)
  • Optimizing performance-critical code paths
  • Preparing code for new feature development
  • Cleaning up after rapid prototyping

Refactoring Workflow

Phase 1: Analysis and Planning

Code Smell Detection

SmellIndicatorsRefactoring
Long Method>50 lines, multiple responsibilitiesExtract Method
Large Class>500 lines, >10 public methodsExtract Class
Duplicate CodeSimilar blocks in 2+ placesExtract Function/Class
Feature EnvyMethod uses other class data extensivelyMove Method
Data ClumpsSame parameters passed togetherIntroduce Parameter Object
Primitive ObsessionOveruse of primitives for domain conceptsReplace with Value Object
Long Parameter List>4 parametersIntroduce Parameter Object
Divergent ChangeClass changes for multiple reasonsExtract Class (SRP)
Shotgun SurgeryOne change requires many file editsMove Method, Inline Class
God ClassClass knows/does too muchExtract Class, Delegate

Impact Assessment

// Before refactoring, assess:
interface RefactoringAssessment {
  // Scope
  filesAffected: string[];
  publicApiChanges: boolean;
  breakingChanges: boolean;

  // Risk
  testCoverage: 'high' | 'medium' | 'low';
  complexity: 'high' | 'medium' | 'low';

  // Dependencies
  internalDependents: string[];
  externalDependents: string[];  // Other extensions, APIs
}

Phase 2: Safe Refactoring Techniques

Extract Method

Before:

async function processTerminals(): Promise<void> {
  // Validation logic (10 lines)
  if (!this.terminals) {
    throw new Error('Terminals not initialized');
  }
  if (this.terminals.size === 0) {
    console.log('No terminals to process');
    return;
  }

  // Processing logic (20 lines)
  for (const [id, terminal] of this.terminals) {
    const state = terminal.getState();
    if (state === 'running') {
      await terminal.sendCommand('status');
      const output = await terminal.waitForOutput();
      this.results.set(id, output);
    }
  }

  // Cleanup logic (10 lines)
  this.results.forEach((result, id) => {
    if (result.includes('error')) {
      this.terminals.get(id)?.restart();
    }
  });
}

After:

async function processTerminals(): Promise<void> {
  this.validateTerminals();
  await this.collectTerminalStatuses();
  this.handleErrorResults();
}

private validateTerminals(): void {
  if (!this.terminals) {
    throw new Error('Terminals not initialized');
  }
  if (this.terminals.size === 0) {
    console.log('No terminals to process');
    return;
  }
}

private async collectTerminalStatuses(): Promise<void> {
  for (const [id, terminal] of this.terminals) {
    const state = terminal.getState();
    if (state === 'running') {
      await terminal.sendCommand('status');
      const output = await terminal.waitForOutput();
      this.results.set(id, output);
    }
  }
}

private handleErrorResults(): void {
  this.results.forEach((result, id) => {
    if (result.includes('error')) {
      this.terminals.get(id)?.restart();
    }
  });
}

Extract Class

Before (God Class):

class TerminalManager {
  // Terminal management (proper responsibility)
  private terminals: Map<number, Terminal>;
  createTerminal(): Terminal { }
  disposeTerminal(id: number): void { }

  // UI concerns (wrong place)
  private statusBarItem: vscode.StatusBarItem;
  updateStatusBar(): void { }
  showNotification(msg: string): void { }

  // Persistence concerns (wrong place)
  saveState(): void { }
  loadState(): void { }
  migrateOldState(): void { }

  // Configuration concerns (wrong place)
  getConfig(key: string): unknown { }
  updateConfig(key: string, value: unknown): void { }
}

After (Single Responsibility):

// Core terminal management
class TerminalManager {
  private terminals: Map<number, Terminal>;

  constructor(
    private ui: TerminalUIManager,
    private persistence: TerminalPersistence,
    private config: TerminalConfig
  ) {}

  createTerminal(): Terminal {
    const terminal = new Terminal(this.config.getShellPath());
    this.terminals.set(terminal.id, terminal);
    this.ui.updateStatusBar(this.terminals.size);
    this.persistence.saveState(this.getState());
    return terminal;
  }

  disposeTerminal(id: number): void {
    this.terminals.delete(id);
    this.ui.updateStatusBar(this.terminals.size);
    this.persistence.saveState(this.getState());
  }
}

// UI responsibility
class TerminalUIManager {
  private statusBarItem: vscode.StatusBarItem;

  updateStatusBar(count: number): void { }
  showNotification(msg: string): void { }
}

// Persistence responsibility
class TerminalPersistence {
  saveState(state: TerminalState): void { }
  loadState(): TerminalState { }
  migrateOldState(): void { }
}

// Configuration responsibility
class TerminalConfig {
  getShellPath(): string { }
  get(key: string): unknown { }
  update(key: string, value: unknown): void { }
}

Replace Conditional with Polymorphism

Before:

function handleMessage(message: Message): void {
  switch (message.type) {
    case 'create':
      const terminal = createTerminal(message.config);
      sendResponse({ type: 'created', id: terminal.id });
      break;
    case 'write':
      const t = getTerminal(message.id);
      if (t) t.write(message.data);
      break;
    case 'resize':
      const term = getTerminal(message.id);
      if (term) term.resize(message.cols, message.rows);
      break;
    case 'dispose':
      disposeTerminal(message.id);
      sendResponse({ type: 'disposed', id: message.id });
      break;
    default:
      console.warn('Unknown message type:', message.type);
  }
}

After:

interface MessageHandler {
  handle(message: Message): void;
}

class CreateHandler implements MessageHandler {
  handle(message: CreateMessage): void {
    const terminal = this.manager.createTerminal(message.config);
    this.sender.send({ type: 'created', id: terminal.id });
  }
}

class WriteHandler implements MessageHandler {
  handle(message: WriteMessage): void {
    this.manager.getTerminal(message.id)?.write(message.data);
  }
}

class ResizeHandler implements MessageHandler {
  handle(message: ResizeMessage): void {
    this.manager.getTerminal(message.id)?.resize(message.cols, message.rows);
  }
}

class DisposeHandler implements MessageHandler {
  handle(message: DisposeMessage): void {
    this.manager.disposeTerminal(message.id);
    this.sender.send({ type: 'disposed', id: message.id });
  }
}

// Message router
class MessageRouter {
  private handlers = new Map<string, MessageHandler>([
    ['create', new CreateHandler()],
    ['write', new WriteHandler()],
    ['resize', new ResizeHandler()],
    ['dispose', new DisposeHandler()]
  ]);

  route(message: Message): void {
    const handler = this.handlers.get(message.type);
    if (handler) {
      handler.handle(message);
    } else {
      console.warn('Unknown message type:', message.type);
    }
  }
}

Introduce Parameter Object

Before:

function createTerminal(
  shell: string,
  cwd: string,
  env: Record<string, string>,
  cols: number,
  rows: number,
  scrollback: number,
  name?: string
): Terminal {
  // ...
}

// Caller must remember order
createTerminal('/bin/bash', '/home', {}, 80, 24, 1000, 'Main');

After:

interface TerminalOptions {
  shell: string;
  cwd: string;
  env?: Record<string, string>;
  dimensions?: {
    cols: number;
    rows: number;
  };
  scrollback?: number;
  name?: string;
}

const DEFAULT_OPTIONS: Partial<TerminalOptions> = {
  env: {},
  dimensions: { cols: 80, rows: 24 },
  scrollback: 1000
};

function createTerminal(options: TerminalOptions): Terminal {
  const opts = { ...DEFAULT_OPTIONS, ...options };
  // ...
}

// Clear, self-documenting call
createTerminal({
  shell: '/bin/bash',
  cwd: '/home',
  name: 'Main'
});

Phase 3: VS Code-Specific Patterns

Manager-Coordinator Pattern

Standard pattern for VS Code extensions with multiple concerns:

// Coordinator orchestrates managers
class TerminalWebviewManager implements ICoordinator {
  private managers: Map<string, IManager> = new Map();

  constructor(context: vscode.ExtensionContext) {
    // Initialize managers
    this.managers.set('message', new MessageManager(this));
    this.managers.set('ui', new UIManager(this));
    this.managers.set('input', new InputManager(this));
    this.managers.set('performance', new PerformanceManager(this));
  }

  getManager<T extends IManager>(name: string): T {
    return this.managers.get(name) as T;
  }

  async initialize(): Promise<void> {
    for (const manager of this.managers.values()) {
      await manager.initialize();
    }
  }

  dispose(): void {
    // Dispose in reverse order
    const managers = Array.from(this.managers.values()).reverse();
    for (const manager of managers) {
      manager.dispose();
    }
  }
}

// Individual manager interface
interface IManager extends vscode.Disposable {
  initialize(): Promise<void>;
}

// Example manager implementation
class MessageManager implements IManager {
  constructor(private coordinator: ICoordinator) {}

  async initialize(): Promise<void> {
    // Setup message handling
  }

  dispose(): void {
    // Cleanup
  }
}

Service Locator Pattern

For complex dependency management:

class ServiceContainer {
  private services = new Map<string, unknown>();
  private factories = new Map<string, () => unknown>();

  register<T>(key: string, instance: T): void {
    this.services.set(key, instance);
  }

  registerFactory<T>(key: string, factory: () => T): void {
    this.factories.set(key, factory);
  }

  get<T>(key: string): T {
    if (this.services.has(key)) {
      return this.services.get(key) as T;
    }

    const factory = this.factories.get(key);
    if (factory) {
      const instance = factory() as T;
      this.services.set(key, instance);
      return instance;
    }

    throw new Error(`Service not found: ${key}`);
  }
}

// Usage
const container = new ServiceContainer();
container.register('config', new ConfigService());
container.registerFactory('terminal', () => new TerminalService(
  container.get('config')
));

Disposable Chain Pattern

Proper resource cleanup:

class DisposableChain implements vscode.Disposable {
  private chain: vscode.Disposable[] = [];

  add<T extends vscode.Disposable>(disposable: T): T {
    this.chain.push(disposable);
    return disposable;
  }

  addFunction(fn: () => void): void {
    this.chain.push({ dispose: fn });
  }

  dispose(): void {
    // LIFO disposal
    while (this.chain.length) {
      const d = this.chain.pop();
      try {
        d?.dispose();
      } catch (e) {
        console.error('Dispose error:', e);
      }
    }
  }
}

// Usage in extension
export function activate(context: vscode.ExtensionContext) {
  const disposables = new DisposableChain();

  const config = disposables.add(new ConfigService());
  const terminal = disposables.add(new TerminalService(config));
  const ui = disposables.add(new UIService(terminal));

  context.subscriptions.push(disposables);
}

Phase 4: Type Safety Improvements

Replace any with Proper Types

Before:

function processMessage(message: any): any {
  if (message.type === 'data') {
    return message.payload.items.map((item: any) => item.value);
  }
  return null;
}

After:

interface DataMessage {
  type: 'data';
  payload: {
    items: Array<{ value: string }>;
  };
}

interface ErrorMessage {
  type: 'error';
  error: string;
}

type Message = DataMessage | ErrorMessage;

function processMessage(message: Message): string[] | null {
  if (message.type === 'data') {
    return message.payload.items.map(item => item.value);
  }
  return null;
}

Discriminated Unions

Before:

interface TerminalState {
  status: string;
  data?: string;
  error?: Error;
  progress?: number;
}

// Caller must check multiple fields
function render(state: TerminalState): void {
  if (state.status === 'loading' && state.progress !== undefined) {
    showProgress(state.progress);
  } else if (state.status === 'success' && state.data) {
    showData(state.data);
  } else if (state.status === 'error' && state.error) {
    showError(state.error);
  }
}

After:

type TerminalState =
  | { status: 'idle' }
  | { status: 'loading'; progress: number }
  | { status: 'success'; data: string }
  | { status: 'error'; error: Error };

// Type narrowing with exhaustive check
function render(state: TerminalState): void {
  switch (state.status) {
    case 'idle':
      showIdle();
      break;
    case 'loading':
      showProgress(state.progress); // progress guaranteed
      break;
    case 'success':
      showData(state.data); // data guaranteed
      break;
    case 'error':
      showError(state.error); // error guaranteed
      break;
    default:
      const _exhaustive: never = state;
      throw new Error(`Unhandled state: ${_exhaustive}`);
  }
}

Generic Constraints

Before:

class Repository<T> {
  private items: T[] = [];

  add(item: T): void {
    this.items.push(item);
  }

  findById(id: number): T | undefined {
    // Can't access .id because T is unconstrained
    return this.items.find((item: any) => item.id === id);
  }
}

After:

interface Identifiable {
  id: number;
}

class Repository<T extends Identifiable> {
  private items: T[] = [];

  add(item: T): void {
    this.items.push(item);
  }

  findById(id: number): T | undefined {
    return this.items.find(item => item.id === id); // Type-safe
  }

  update(id: number, updates: Partial<Omit<T, 'id'>>): boolean {
    const item = this.findById(id);
    if (item) {
      Object.assign(item, updates);
      return true;
    }
    return false;
  }
}

Phase 5: Verification

Refactoring Checklist

  • All tests pass after refactoring
  • No new TypeScript errors introduced
  • Public API maintained (or documented changes)
  • Performance not degraded
  • Memory usage stable
  • No circular dependencies introduced
  • Documentation updated if needed

Testing Strategy

// Before refactoring: Capture behavior
describe('TerminalManager (before refactor)', () => {
  it('creates terminal with correct config', () => {
    const result = manager.createTerminal(config);
    expect(result).toMatchSnapshot();
  });
});

// After refactoring: Same tests must pass
describe('TerminalManager (after refactor)', () => {
  it('creates terminal with correct config', () => {
    const result = manager.createTerminal(config);
    expect(result).toMatchSnapshot(); // Same snapshot
  });
});

Common Refactoring Scenarios

Scenario 1: Breaking Up a Large File

src/terminal.ts (2000 lines)
↓ Split by responsibility
src/terminal/
├── index.ts           # Public exports
├── TerminalManager.ts # Core management
├── TerminalFactory.ts # Creation logic
├── TerminalState.ts   # State management
├── types.ts           # Interfaces and types
└── utils.ts           # Helper functions

Scenario 2: Reducing Coupling

// Before: Tight coupling
class TerminalManager {
  private ui = new UIManager();  // Direct instantiation
  private config = new ConfigManager();
}

// After: Dependency injection
class TerminalManager {
  constructor(
    private ui: IUIManager,
    private config: IConfigManager
  ) {}
}

// Factory handles wiring
function createTerminalManager(): TerminalManager {
  return new TerminalManager(
    new UIManager(),
    new ConfigManager()
  );
}

Scenario 3: Async Refactoring

// Before: Callback hell
function loadData(callback: (data: Data) => void): void {
  readFile(path, (err, content) => {
    if (err) throw err;
    parseData(content, (err, parsed) => {
      if (err) throw err;
      validateData(parsed, (err, valid) => {
        if (err) throw err;
        callback(valid);
      });
    });
  });
}

// After: Async/await
async function loadData(): Promise<Data> {
  const content = await readFile(path);
  const parsed = await parseData(content);
  return validateData(parsed);
}

Resources

For detailed reference documentation:

  • references/code-smells.md - Complete code smell catalog with examples
  • references/design-patterns.md - VS Code-specific design pattern implementations
  • references/type-patterns.md - Advanced TypeScript type patterns

适合场景

01

用户想查找某类 Agent Skill 时

02

需要根据任务场景推荐可安装能力包时

03

需要对比不同来源的安装命令和来源信息时

能力概览

能力 1

按任务关键词查找相关 Skills

能力 2

展示可复制的安装命令

能力 3

保留来源站点、仓库和原始说明,方便继续核验

能力 4

展示第三方安全扫描或审计结果

安装后应在对应宿主中按原始 README 的触发条件使用;具体调用方式请以来源页面和 README 为准。

平台分布

Codex

35.14%
按下载量换算64

Claude

29.89%
按下载量换算54

Cursor

17.41%
按下载量换算32

Gemini CLI

8.8%
按下载量换算16

安全审计

Gen Agent Trust Hub

通过

Socket

通过

Snyk

通过

权限和风险

执行命令

安装流程涉及命令执行,可能通过 npx skills add https://github.com/s-hiraoku/vscode-sidebar-terminal --skill vscode-extension-refactorer 联网下载 Skill 或依赖。用户安装前应确认命令来源、仓库内容和执行环境。

安装前确认

本站仅展示第三方公开信息,不托管安装包,不提供自动安装或运行环境。安装前应自行审查源码、依赖和命令行为。当前只有一个来源,正式发布前建议补源仓库或其他目录站核验。

来源信息

继续浏览同类 Skills