Introduction to the

About vscode

VSCode is a lightweight code editor from Microsoft, free and powerful, with powerful functions, prompt friendly, good performance and appearance level captured a large number of developers favor, JavaScript and NodeJS support is very good, with many features, such as code formatting, code intelligent prompt completion, etc.. No matter how powerful the IDE is, it will only make the IDE too bloated. Many powerful functions of VScode are implemented based on plug-ins. IDE only provides a basic framework and the most basic functions, which are enriched and extended by plug-ins.

What is vscode plug-in

Because vscode itself is implemented in the browser, so its plug-in needless to say is based on HTML+JS and other front-end technology implementation, from the form is similar to the NPM package vsix file, but according to some special specifications to achieve some special functions.

How to develop a vscode plug-in

1. Install official scaffolding

npm install -g yo generator-code
Copy the code

Select the configuration

The generated file directory is

Extension.js is the main entry of the project

Package. json configures the project

2. Package. json interprets and executes HelloWorld

Let’s start with an example

{
 "name": "wx-command"."displayName": "wx-command"."description": "Wechat small program File Assistant"."version": "Hundreds"."engines": {
   "vscode": "^ 1.36.0"
 },
 "categories": [
   "Other"]."activationEvents": [
   "onCommand:extension.wxPage"."onCommand:extension.wxComponents"]."main": "./out/extension.js"."contributes": {
   "commands": [{"command": "extension.wxPage"."title": "wx page"
     },
     {
       "command": "extension.wxComponents"."title": "wx components"}]."menus": {
     "explorer/context": [{"command": "extension.wxPage"
       },
       {
         "command": "extension.wxComponents"}},"snippets": [{"language": "vue"."path": "./snippets/ts.json"}},"scripts": {
   "vscode:prepublish": "npm run compile"."compile": "tsc -p ./"."watch": "tsc -watch -p ./"."pretest": "npm run compile"."test": "node ./out/test/runTest.js"
 },
 "devDependencies": {
   "@types/glob": "^ 7.1.1." "."@types/mocha": "^ 5.2.6." "."@types/node": "^ 10.12.21"."@types/vscode": "^ 1.36.0"."glob": "^" 7.1.4."mocha": "^ 6.1.4." "."tslint": "^ 5.19.0"."typescript": "^ 3.3.1"."vscode-test": "^ 1.0.2"}}Copy the code

It looks no different from our usual project, but one contributes configuration is added, which is also the configuration entry for all our commands

Combine to implement a HelloWord to deepen understanding

First contribute is configured in package.json

{
   // Extended activation events
   "activationEvents": [
   	"onCommand:extension.sayHello"].// Import file
   "main": "./src/extension".// contribution point, vscode plug-in most of the function configuration here
   "contributes": {
   	"commands": [{"command": "extension.sayHello"."title": "Hello vscode"}}}]Copy the code

Configure the events we want to activate in activationEvents (which can be directly configured to * activate all commands) and then contribute the custom command, sayHello, which then contributes to Commands and then implements the specific functionality in extensions

const vscode = require('vscode');

/** * Triggered when the plug-in is activated, all code entry *@param {*} Context Plug-in context */
exports.activate = function(context) {
   console.log('Congratulations, your extension' vscode-plugin-demo 'has been activated! ');
   // Register the command
   context.subscriptions.push(vscode.commands.registerCommand('extension.sayHello'.function () {
   	vscode.window.showInformationMessage('Hello vscode popover! ');
   }));
};

/** * triggers */ when plug-ins are released
exports.deactivate = function() {
   console.log('your extension' vscode-plugin-demo 'has been released! ')};Copy the code

Where activate and deactivate are plug-in lifecycle names that are executed when the plug-in is inserted and released, respectively

Vscode.com mands registerCommand is registered command API that returns an object of the Disposable after execution, all of the API to perform after registered need to return results in the context. Subscriptions.

Vscode. Window. ShowInformationMessage is a plug-in popup window method

After debugging, command+shift+p opens the vscode command to execute the custom command Hello vscode- visible execution popup

3. Automatic generation of template files

Expected effect, imitate wechat developer tools right menu to generate files, and automatically fill the template

Look at the configuration in package.json first

"activationEvents": [
    "onCommand:extension.wxPage"."onCommand:extension.wxComponents"]."contributes": {
    "commands": [{"command": "extension.wxPage"."title": "wx page"
      },
      {
        "command": "extension.wxComponents"."title": "wx components"}]."menus": {
      "explorer/context": [{"command": "extension.wxPage"
        },
        {
          "command": "extension.wxComponents"}},Copy the code

Do our commands configuration as before in the keys that contribute

Then proceed to the Menus configuration menu

Several API

  • Explorer/Context is the key that defines where this menu appears;

    • Resource Manager Context menu – Explorer/Context
    • Editor context menu – Editor/Context
    • Edit the title menu bar – Editor /title
    • Editor title Context menu – Editor /title/ Context
  • When control menu appears properly;

  • Command defines what to do when a menu is clicked;

The idea is that writeFileSync generates files and writes to preconfigured templates based on different commands

And then look at the implementation

const vscode = require("vscode");
const fs = require("fs");
const path = require("path");
const files_1 = require("./files");
const { page, components } = files_1.files("index");
const fileTypes = ["js"."wxss"."wxml"."json"];
function wxCommandHander(type, e) {
    const stat = fs.statSync(e.fsPath);
    const dir = path.normalize(e.fsPath);
    if (stat.isDirectory()) {
        try {
            fileTypes.map((i) = > __awaiter(this.void 0.void 0.function* () {
                const data = new Uint8Array(Buffer.from(type === "page" ? page[i] : components[i]));
                fs.writeFileSync(`${dir}/index.${i}`, data);
            }));
            vscode.window.showInformationMessage(`create ${type}success! `);
        }
        catch (error) {
            vscode.window.showErrorMessage("create page files failed"); }}else {
        vscode.window.showErrorMessage("please choose a folder"); }}function activate(context) {
    console.log('Congratulations, your extension "wx" is now active! ');
    let disposable = vscode.commands.registerCommand("extension.wxPage".(e) = > __awaiter(this.void 0.void 0.function* () {
        wxCommandHander("page", e);
    }));
    context.subscriptions.push(disposable);
    disposable = vscode.commands.registerCommand("extension.wxComponents".(e) = > {
        wxCommandHander("components", e);
    });
    context.subscriptions.push(disposable);
}
exports.activate = activate;
function deactivate() {}exports.deactivate = deactivate;

Copy the code

File.js contains the configuration template

"use strict";
Object.defineProperty(exports."__esModule", { value: true });
/ * * * *@param name file name
 */ exports.files = function (name) {
    const page = {
        js: ` / * * *${name}.js * / Page ({/ * * * * / data Page of the initial data: {}, function / * * * life cycle - listening Page load * / onLoad: Function (options) {}, /** * lifecycle functions -- listen on page first render */ onReady: function () {}, /** * lifecycle functions -- listen on page display */ onShow: OnHide: function () {}, /** * onHide: function () {}, /** * Function () {}, / onPullDownRefresh: Function () {}, /** * onReachBottom: function () {}, /** * onShareAppMessage: function () { } })`.wxss: ` / * *${name}.wxss**/`.json: ` / * * *${name}.json
 * */
{
"usingComponents": {}
}`.wxml: ` <! --${name}.wxml-->
<text>${name}</text>`
    };
    return {
        page,
        components
    };
};
//# sourceMappingURL=files.js.map
Copy the code

Execution effect, debugging, in a folder directory right – click execution

4. Automatic completion

const vscode = require('vscode');
const util = require('./util');
const snippetsList = require('./utilList.js')
/** * Automatic prompt implementation, this is a very simple operation ** automatically bring package.json dependencies out when you type this.dependencies@param {*} document 
 * @param {*} position 
 * @param {*} token 
 * @param {*} context 
 */
function provideCompletionItems(document, position, token, context) {
    const line = document.lineAt(position);
    const projectPath = util.getProjectPath(document);
    const localDependencies = snippetsList.util
    // Only up to the cursor position to prevent some special cases
    const lineText = line.text.substring(0, position.character);
    // Simple match. Any string before the current cursor is' this.dependencies. 'automatically adds all dependencies
    if (/util\.$/g.test(lineText)) {
        let atest = ['test']
        return localDependencies.map(dep= > {
            return newvscode.CompletionItem(dep.name, vscode.CompletionItemKind.Field); }}})/** * Action is triggered when the cursor selects the current autocomplete item. In general, no action is required@param {*} item 
 * @param {*} token 
 */
function resolveCompletionItem(item, token) {
    return null;
}

module.exports = function (context) {
    // Registration code suggested prompt, only when pressed ". When the trigger
    context.subscriptions.push(vscode.languages.registerCompletionItemProvider('javascript', {
        provideCompletionItems,
        resolveCompletionItem
    }, '. '));
};
Copy the code

The vscode. Languages. RegisterCompletionItemProvider for the new API, accepts three parameters

  • Type of file to execute
  • A function that provides hints
  • Trigger word

5. Code hints

The code hint is actually a new vue.json file that uses code to change the way vscode uses custom snippets

{
  The "print using the console.": {
    "prefix": "colo"."body": [
      "console.log($0)"]."description": "The console print"
  },
  "The console. To print 2": {
    "prefix": "ajax"."body": [
      "$.ajax({"." url: '$1',"." method: '${2:POST}',"." datatype: 'json',"." success: data => {"."$3;"."},"." error: err => {"."$4;"."}"."})"]."description": "Ajax modules"
  },
  "Regional": {
    "prefix": "adress-s"."body": [
      "
      
       "
      ."
      
       "
      ."
      "."
      "." "."</el-form-item>"]."description": "Regional"}}Copy the code

Where prefix is the trigger word body

"contributes": {
     "snippets": [{"language": "vue"."path": "./snippets/vue.json"}],},Copy the code

Work after plug-in development is completed

Plug-ins need to be packaged and shared once they are developed

Once developed, we have three ways to use it

Method 1: directly send the folder to others, let others find vscode plug-in directory and put it in, and then restart VScode, generally not recommended; Method 2: Package it as a Vsix plug-in and send it to someone else to install. If your plug-in is confidential and not easy to release to the app market, try this method. Method 3: Register a developer account and publish to the official website app market, which does not need to be reviewed like NPM.Copy the code

Introduce the second type, locally packaged as a Vsix package, when others use directly to send them. The recipient then installs it in the plugin

Installation method

You need to install the packaging plug-in during packaging

npm i vsce -g 
Copy the code

Packaging orders

vsce package
Copy the code

The publisher configuration in the Packagejson we talked about earlier needs to be used, which needs to be registered. Here’s the registration process

Registration logic

To publish to the app market, you must have an App Publisher account. To have a publishing account, you have to have an Azure DevOps organization; Before you can create an organization, you need to create an Azure account. To create an Azure account, you must have a Microsoft account. A Single Microsoft account can create multiple Azure organizations. An organization can create multiple Publisher accounts; At the same time, an organization can create multiple Personal Access tokens (PAT).Copy the code

Login.live.com/, sign up for Microsof…

The second url aka. Ms /SignupAzure… Enter the Microsoft account we registered just now and follow the steps to register

Personal keys are generated after successful registration

Make sure to select Full Access and set your own name time

After the token is generated, please save it. Once you exit, the website will not save it.

Now we have the account and the token under our project directory

Vsce create-Publisher Your name (whatever)Copy the code

Write your token last

You can view the publishers that have been added through VSCE ls-Publishers

Then add publisher writer to the project’s Packagejson

To perform

vsce package
Copy the code

The plug-in with the suffix vsix can be generated in the project directory.