Add first version of package browsing experience

Adds a new command that lists all azure-sdk-for-node packages from npm
and user can filter the list and select a particular package. Hitting
Enter after selection adds a dependency to the selected package in the
project's package.json and adds a require statement in the active
document, if one is open.
This commit is contained in:
Balaji Krishnan 2017-03-09 17:32:24 -08:00
Родитель c0ccbaa7aa
Коммит 63b1016567
5 изменённых файлов: 102 добавлений и 4 удалений

Просмотреть файл

@ -45,12 +45,18 @@
"command": "Azure-Node.template-deploy",
"title": "Generate code for template deployment",
"category": "Azure-Node"
},
{
"command": "Azure-Node.browse-packages",
"title": "Browse Azure-SDK packages",
"category": "Azure-Node"
}
]
},
"scripts": {},
"dependencies": {
"npm": "*",
"npm-user-packages": "^2.0.0",
"escodegen": "^1.8.1",
"esprima": "^3.1.3"
},

Просмотреть файл

@ -0,0 +1,5 @@
var codegenerator = require('./codegen');
exports.generateRequireStatements = function generateRequireStatements(document, modules) {
return codegenerator.generateRequireStatements(document, modules);
};

Просмотреть файл

@ -0,0 +1,60 @@
var fs = require('fs');
var vscode = require('vscode');
var npmUserPackages = require('npm-user-packages');
var jsonEditor = require('../codegen/jsoneditor');
var utils = require('../utils');
var codegen = require('../codegen/codegen.browse-packages');
exports.createCommand = function createCommand() {
vscode.commands.registerCommand('Azure-Node.browse-packages', function () {
npmUserPackages('windowsazure').then(data => {
var pkgs = [];
data.forEach(function (item) {
pkgs.push({ "label": item.name, "description": item.version, "detail": item.description });
});
vscode.window.showQuickPick(pkgs).then((selectedItem) => {
updatePackageJson(selectedItem.label);
if (!vscode.window.activeTextEditor) {
return;
}
return generateCodeInEditor(selectedItem.label);
});
});
});
};
function updatePackageJson(packageToAdd) {
var filePath = utils.getPackageJsonPath();
if (filePath && fs.existsSync(filePath)) {
var packages = [packageToAdd];
jsonEditor.addDependenciesIfRequired(filePath, packages);
}
};
function generateCodeInEditor(moduleName) {
// generate code to be inserted.
const document = vscode.window.activeTextEditor.document;
var importsAndLineNumber = codegen.generateRequireStatements(document, [moduleName]);
vscode.window.activeTextEditor.edit((builder) => {
// insert import statements.
// Insertion point is the line where import group ends.
if (importsAndLineNumber) {
var importPos = new vscode.Position(importsAndLineNumber.line, 0);
var imports = importsAndLineNumber.code;
for (var importStatement of imports) {
builder.insert(importPos, importStatement);
}
}
});
// format the entire document.
// the code we inserted was generated as well-formatted but indenting is relative to the existing text
// in the document. Since we didn't examine existing text and are unaware of the indent depth where
// generated code will be inserted, we have to reformat the whole document. If this leads to performance issues, we'll revisit this logic.
return vscode.commands.executeCommand("editor.action.formatDocument");
};

Просмотреть файл

@ -1,8 +1,8 @@
var fs = require('fs');
var path = require('path');
var vscode = require('vscode');
var codegen = require('../codegen/codgen.template-deploy');
var jsonEditor = require('../codegen/jsoneditor');
var utils = require('../utils');
exports.createCommand = function createCommand() {
vscode.commands.registerCommand('Azure-Node.template-deploy', function () {
@ -21,10 +21,9 @@ exports.createCommand = function createCommand() {
};
function updatePackageJson() {
// TODO: search rootDir\package.json
var filePath = path.join(vscode.workspace.rootPath, 'package.json');
var filePath = utils.getPackageJsonPath();
if (fs.existsSync(filePath)) {
if (filePath && fs.existsSync(filePath)) {
var packages = codegen.getPackageDependencies();
jsonEditor.addDependenciesIfRequired(filePath, packages);
}

Просмотреть файл

@ -1,3 +1,6 @@
var fs = require('fs');
var path = require('path');
var vscode = require('vscode');
let exec = require('child_process').exec;
// checks if there exists a valid installation of NodeJs on this machine
@ -82,3 +85,28 @@ exports.npmInstall = function npmInstall(packages, opts) {
});
});
};
exports.getPackageJsonPath = function getPackageJsonPath(){
var dirAboveRoot = path.join(vscode.workspace.rootPath, '..');
var srcPath = getSourceLocation();
var packageJsonPath;
while (srcPath !== dirAboveRoot) {
packageJsonPath = path.join(srcPath, 'package.json');
if(fs.existsSync(packageJsonPath)){
return packageJsonPath;
}
else{
srcPath = path.join(srcPath, '..');
}
}
};
function getSourceLocation() {
var files = vscode.workspace.textDocuments.filter(item => item.isUntitled === false);
if (files) {
var sourceFile = files[0].fileName;
return sourceFile.slice(0, sourceFile.lastIndexOf('\\') + 1);
}
}