파이썬의 dotted path를 복제하는 VS 코드 확장 기능을 만들어 봤습니다.
35979 단어 PythonTypeScriptVS Codetech
🔧 만든 물건
복사Copy Python Path파이썬의dotted path(예
foo.hoge.class
의 확장 기능을 만들어 보았습니다.개발 이유는 Django가 unittest를 실행할 때dotted path를 사용하지만 수동으로 조립할 때마다 번거롭다는 것이다.
기능은 여기 있습니다.
!
기존에도dotted path를 복제하는 확장 기능이 있지만 파일 단위의 경로 복제이며 클래스 단위 복제는 지원되지 않습니다.
여기에 설치할 수 있습니다.댓글을 받으면 울고 기뻐요.
코드도 여기서 공개합니다.
🦾 구조 & 신경 쓴 곳
JS로 Python 코드 지우기, 해석 방법 클래스 정의
파일까지의 상대 경로만 있으면 VS 코드의 API에서 가져올 수 있지만 클래스 방법이 정의된 경로는 VS 코드의 API에서 가져올 수 없습니다.
클래스 방법의 이름을 정확하게 가져오고 위치를 정의하기 위해서 Python 코드를 지워야 합니다.
그래서 이번에 우리는 ANTLR4 기초의 Perser Generationdt-python-parser을 사용했다.
이 라이브러리 파이토존 코드를 주면AST(추상적 문법 나무)에 점을 찍고 ANTLR4의 기본적인 방법으로AST를 두루 돌아다닐 수 있습니다.
dt-ptyhon-parser의copy-ptyhon-path를 사용한 해석 부분의 코드가 여기 있습니다.
src/utils/getDefinedParentSymbols.ts
// ...
/**
* Get defined symbols related to the selected rows from a python file. e.g. Class name, function name
* @param {string} text - python code
* @param {number} lineNumber - current cursor line number
* @return {array} defined symbols
*/
export const getRelatedDefinedSymbols = (text: string, lineNumber: number): string[] => {
const parser = new Python3Parser();
const tree = parser.parse(text);
const symbols: DefinedSymbol[] = [];
class MyListener extends Python3Listener {
enterClassdef(ctx: any): void {
symbols.push({
name: ctx.children[1].getText(),
line: ctx.children[0].getSymbol().line,
column: ctx.children[0].getSymbol().column,
});
}
enterFuncdef(ctx: any): void {
symbols.push({
name: ctx.children[1].getText(),
line: ctx.children[0].getSymbol().line,
column: ctx.children[0].getSymbol().column,
});
}
}
const listenTableName = new MyListener();
parser.listen(listenTableName, tree);
const symbol = symbols.filter(s => s.line === lineNumber)[0];
if (!symbol) {
return [];
}
if (symbol.column === 0) {
return [symbol.name];
}
const parentSymbolNames = getDefinedParentSymbols(symbol, symbols).map(s => s.name);
return [...parentSymbolNames, symbol.name];
};
dt-parser에서 클래스 이름, 방법 이름과 그 정의 위치를 얻어 코드의 구조에 따라 배열한다.getDefinedParentSymbols
에서 코드 구조에 맞는 정렬을 진행하였다.E2E 테스트 보장 동작
패브릭은 단순한 확장 기능이지만 지속적인 유지 관리를 위해 E2E 테스트를 추가했습니다.
다음 그림과 같이 테스트를 진행하면 VScode는 다른 과정에서 실제 명령을 시작하고 실행합니다.
테스트 코드 여기 있습니다.
src/test/suite/extension.test.ts
// ...
const executeCommandWithWait = async (command: string): Promise<any> => {
await sleep(500);
await vscode.commands.executeCommand(COMMAND_NAME);
await sleep(1000);
};
const COMMAND_NAME = 'copy-python-path.copy-python-path';
// example.py is following code
/*
class ClassA:
def class_a_method_a():
pass
class ClassB:
def class_b_method_a():
pass
class ClassD:
def class_d_method_a():
pass
*/
const testFileLocation = '/pythonApp/example.py';
suite('Extension Test Suite', () => {
vscode.window.showInformationMessage('Start all tests.');
let editor: vscode.TextEditor;
setup(async () => {
// open folder
const fileUri = vscode.Uri.file(vscode.workspace.workspaceFolders![0].uri.fsPath + testFileLocation);
const document = await vscode.workspace.openTextDocument(fileUri);
editor = await vscode.window.showTextDocument(document);
});
test('selected class lines', async () => {
editor.selection = new vscode.Selection(new vscode.Position(0, 0), new vscode.Position(0, 0));
await executeCommandWithWait(COMMAND_NAME);
assert.strictEqual(await vscode.env.clipboard.readText(), 'pythonApp.example.ClassA');
});
test('selected method lines', async () => {
editor.selection = new vscode.Selection(new vscode.Position(1, 0), new vscode.Position(1, 0));
await executeCommandWithWait(COMMAND_NAME);
assert.strictEqual(await vscode.env.clipboard.readText(), 'pythonApp.example.ClassA.class_a_method_a');
});
test('selected nested class lines', async () => {
editor.selection = new vscode.Selection(new vscode.Position(4, 0), new vscode.Position(4, 0));
await executeCommandWithWait(COMMAND_NAME);
assert.strictEqual(await vscode.env.clipboard.readText(), 'pythonApp.example.ClassA.ClassB');
});
// ...
});
커서 위치를 이동하고 명령을 실행하여 클립보드에 복사한 결과를 확인합니다.setTimeout을 적당히 사용해서 실행 감각을 켜는 것이 중점입니다.
사실 VScode 확장 기능의 테스트 방법은 기본적으로 정보가 없어서 매우 고생스럽다.VS 코드의 문서에도 Hello World 등급의 간단한 테스트 기록만 있다. 마지막으로 나는 마이크로소프트가 발표한 확장 기능의 실제 테스트 코드를 보면서 테스트를 썼다.
※ 참고 창고
GiitHub Action의 CI 환경 정비
VS코드의 문서에 CI 정보가 있기 때문에 GiitHub Action으로 E2E 테스트와 확장 기능이 발표된 CI를 조합했습니다.
GiitHub Actions의 이미지에는 VScode 시작에 필요한 포장이 포함된 것 같아서 기본적으로 고려하지 않은 곳에서 실행할 수 있다.
다음은 E2E 테스트의 GiitHub Actions입니다.
Mac, Linux 및 Windows의 이미지를 동시에 테스트합니다.
.github/workflows/e2e-test.yml
name: E2E
on:
push:
branches:
- main
jobs:
build:
strategy:
matrix:
os: [macos-latest, ubuntu-latest, windows-latest]
runs-on: ${{ matrix.os }}
steps:
- name: Checkout
uses: actions/checkout@v3
- uses: actions/setup-node@v3
with:
node-version: '16'
cache: 'yarn'
- name: Install dependencies
run: yarn install
# xvfb is required to run vscode on linux
- name: Run test on linux
run: xvfb-run -a yarn test
if: runner.os == 'Linux'
- name: Run test on Mac and Windows
run: yarn test
if: runner.os != 'Linux'
!GiitHub Actions를 사용하여 직접 제작한 확장 기능을 실제로 이동할 때 Windows의 구축만 테스트한 결과 플랫폼에 의존하는 오류가 발견되었습니다.시험은 역시 중요하다.
발매는 여기 있습니다.
.github/workflows/release.yml
name: release
on:
workflow_dispatch:
inputs:
release_type:
description: 'select release type'
type: choice
options:
- patch
- minor
- major
required: true
jobs:
build:
strategy:
matrix:
os: [macos-latest, ubuntu-latest, windows-latest]
runs-on: ${{ matrix.os }}
steps:
- name: Checkout
uses: actions/checkout@v3
- uses: actions/setup-node@v3
with:
node-version: '16'
cache: 'yarn'
- name: Install dependencies
run: yarn install
# xvfb is required to run vscode on linux
- name: Run test on linux
run: xvfb-run -a yarn test
if: runner.os == 'Linux'
- name: Run test on Mac and Windows
run: yarn test
if: runner.os != 'Linux'
- name: Publish
if: success() && matrix.os == 'ubuntu-latest'
run: |
git config --global user.name "${GITHUB_ACTOR}"
git config --global user.email "${GITHUB_ACTOR}@users.noreply.github.com"
yarn run deploy -- ${{ github.event.inputs.release_type }}
env:
VSCE_PAT: ${{ secrets.VSCE_PAT }}
이것은 수동 작업 흐름으로 발표 버전을 관리하고 발표 유형을 선택할 수 있습니다.E2E 테스트의 CI와 동일한 처리를 수행한 후 스크립트 해제를 수행합니다.
발매 자체vsce를 사용했지만 버전이 제출되어 있기 때문에git config도 설정되었습니다.
끝말
개발을 생각해서 며칠 만에 공개됐기 때문에 상당히 빠른 속도로 개발할 수 있어서 다행이에요.이번에 VScode 확장기능 개발의 토대를 배웠고, 앞으로도 다양한 편리한 확장기능 개발과 기존 확장기능에 대한 홍보에 적극적으로 나설 계획이다.
Reference
이 문제에 관하여(파이썬의 dotted path를 복제하는 VS 코드 확장 기능을 만들어 봤습니다.), 우리는 이곳에서 더 많은 자료를 발견하고 링크를 클릭하여 보았다 https://zenn.dev/ryo_kawamata/articles/development-vscode-extensions텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
우수한 개발자 콘텐츠 발견에 전념 (Collection and Share based on the CC Protocol.)