Skip to content

Commit

Permalink
Bind XSD, DTD with CodeLens
Browse files Browse the repository at this point in the history
Fixes redhat-developer#395

Signed-off-by: azerr <[email protected]>
  • Loading branch information
angelozerr committed Jun 10, 2021
1 parent 2eb21e2 commit e4c2a32
Show file tree
Hide file tree
Showing 3 changed files with 91 additions and 4 deletions.
3 changes: 2 additions & 1 deletion src/client/xmlClient.ts
Original file line number Diff line number Diff line change
Expand Up @@ -123,7 +123,8 @@ function getLanguageClientOptions(logfile: string, externalXmlSettings: External
codeLens: {
codeLensKind: {
valueSet: [
'references'
'references',
'association'
]
}
},
Expand Down
9 changes: 8 additions & 1 deletion src/commands/commandConstants.ts
Original file line number Diff line number Diff line change
Expand Up @@ -52,11 +52,18 @@ export namespace CommandConstants {
export const OPEN_DOCS_HOME = "xml.open.docs.home";

/**
* VSCode client command to executes an LSP command on the XML Language Server
* VSCode client commands to revalidate files with an LSP command on the XML Language Server
*/
export const EXECUTE_WORKSPACE_COMMAND = "xml.workspace.executeCommand";

export const VALIDATE_CURRENT_FILE = "xml.validation.current.file";

export const VALIDATE_ALL_FILES = "xml.validation.all.files";

/**
* VSCode client commands to associate a XML file with a grammar to select
*/
export const SELECT_FILE = "xml.select.file";

export const ASSOCIATE_GRAMMAR_INSERT = "xml.associate.grammar.insert";
}
83 changes: 81 additions & 2 deletions src/commands/registerCommands.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import * as path from 'path';
import { commands, ExtensionContext, Position, Uri, window, workspace } from "vscode";
import { CancellationToken, ExecuteCommandParams, ExecuteCommandRequest, ReferencesRequest, TextDocumentIdentifier } from "vscode-languageclient";
import { commands, ExtensionContext, OpenDialogOptions, Position, Uri, window, workspace, WorkspaceEdit } from "vscode";
import { CancellationToken, ExecuteCommandParams, ExecuteCommandRequest, ReferencesRequest, TextDocumentIdentifier, TextDocumentEdit } from "vscode-languageclient";
import { LanguageClient } from 'vscode-languageclient/node';
import { markdownPreviewProvider } from "../markdownPreviewProvider";
import { CommandConstants } from "./commandConstants";
Expand All @@ -15,6 +15,7 @@ export async function registerCommands(context: ExtensionContext, languageClient
registerDocsCommands(context);
registerCodeLensCommands(context, languageClient);
registerValidationCommands(context);
registerAssociateGrammarCommands(context, languageClient);

// Register client command to execute custom XML Language Server command
context.subscriptions.push(commands.registerCommand(CommandConstants.EXECUTE_WORKSPACE_COMMAND, (command, ...rest) => {
Expand Down Expand Up @@ -108,4 +109,82 @@ async function registerValidationCommands(context: ExtensionContext): Promise<vo
window.showErrorMessage('Error during XML validation: ' + error.message);
});
}));
}

/**
* Register commands used for associating grammar file (XSD,DTD) to a given XML file
*
* @param context the extension context
*/
async function registerAssociateGrammarCommands(context: ExtensionContext, languageClient: LanguageClient): Promise<void> {
context.subscriptions.push(commands.registerCommand(CommandConstants.SELECT_FILE, (uriString: string, bindingType: string) => {

// A click on Bind with... has been processed in the XMLdocument which is not bound to a grammar
const documentURI = Uri.parse(uriString);
workspace.openTextDocument(documentURI).then(document => {

// Open a dialog to select the XSD,DTD to bind.
const options = createDialogOptions(bindingType);
window.showOpenDialog(options).then(fileUri => {
if (fileUri && fileUri[0]) {

// The XSD, DTD has been selected, get the proper syntax for binding this grammar file in the XML document.
const identifier = TextDocumentIdentifier.create(documentURI.toString());
const grammarURI = fileUri[0];
commands.executeCommand(CommandConstants.EXECUTE_WORKSPACE_COMMAND, CommandConstants.ASSOCIATE_GRAMMAR_INSERT, identifier, grammarURI.toString(), bindingType).
then((result) => {
// Insert the proper syntax for binding
const lspTextDocumentEdit = <TextDocumentEdit>result;
const workEdits = new WorkspaceEdit();
for (const edit of lspTextDocumentEdit.edits) {
workEdits.replace(documentURI, languageClient.protocol2CodeConverter.asRange(edit.range), edit.newText);
}
workspace.applyEdit(workEdits); // apply the edits
}, error => {
window.showErrorMessage('Error during grammar binding: ' + error.message);
});
}
});

})
}));

function createDialogOptions(bindingType : string) : OpenDialogOptions {
switch(bindingType) {
case "xsd": {
const options: OpenDialogOptions = {
canSelectMany: false,
openLabel: 'Select XSD file',
filters: {
'XSD files': ['xsd'],
}
};
return options;
}

case "dtd": {
const options: OpenDialogOptions = {
canSelectMany: false,
openLabel: 'Select DTD file',
filters: {
'DTD files': ['dtd']
}
};
return options;
}

case "xml-model": {
const options: OpenDialogOptions = {
canSelectMany: false,
openLabel: 'Select XSD or DTD file',
filters: {
'XSD files': ['xsd'],
'DTD files': ['dtd']
}
};
return options;
}
}

}
}

0 comments on commit e4c2a32

Please sign in to comment.