Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -37,7 +37,7 @@ import {
import { Kind, parse, print } from 'graphql';
import { getAutocompleteSuggestions } from './getAutocompleteSuggestions';
import { getHoverInformation } from './getHoverInformation';
import { validateQuery, getRange, SEVERITY } from './getDiagnostics';
import { validateQuery, getRange, DIAGNOSTIC_SEVERITY } from './getDiagnostics';
import {
getDefinitionQueryResultForFragmentSpread,
getDefinitionQueryResultForDefinitionNode,
Expand Down Expand Up @@ -155,7 +155,7 @@ export class GraphQLLanguageService {
const range = getRange(error.locations[0], query);
return [
{
severity: SEVERITY.ERROR,
severity: DIAGNOSTIC_SEVERITY.Error,
message: error.message,
source: 'GraphQL: Syntax',
range,
Expand All @@ -175,7 +175,7 @@ export class GraphQLLanguageService {
);

const dependenciesSource = fragmentDependencies.reduce(
(prev, cur) => `${prev} ${print(cur.definition)}`,
(prev: any, cur: any) => `${prev} ${print(cur.definition)}`,
'',
);

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@ import {
GraphQLType,
GraphQLCompositeType,
GraphQLEnumValue,
Kind,
} from 'graphql';

import {
Expand Down Expand Up @@ -52,6 +53,34 @@ import {
objectValues,
} from './autocompleteUtils';

// TODO@acao,rebornix
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

ah i see, yes i dont think we need to take step into account, as this context isn't needed in this case

// Convert AST token kind to Monaco CompletionItemKind
// Should we take `step` into account similar to how we resolve completion items?
function toCompletionItemKind(
kind: string,
): monaco.languages.CompletionItemKind {
const mItemKind = monaco.languages.CompletionItemKind;

switch (kind) {
case 'Document':
case 'SelectionSet':
case 'Field':
case 'AliasedField':
case 'Arguments':
case 'ObjectValue':
case 'ObjectField':
case 'EnumValue':
case 'ListValue':
case 'ListType':
case 'TypeCondition':
case 'NamedType':
case 'FragmentSpread':
case 'VariableDefinition':
case 'Directive':
return mItemKind.Method;
}
}

/**
* Given GraphQLSchema, queryText, and context of the current position within
* the source text, provide a list of typeahead entries.
Expand Down Expand Up @@ -79,17 +108,17 @@ export function getAutocompleteSuggestions(
// Definition kinds
if (kind === 'Document') {
return hintList(token, [
{ label: 'query' },
{ label: 'mutation' },
{ label: 'subscription' },
{ label: 'fragment' },
{ label: '{' },
{ label: 'query', kind: toCompletionItemKind(kind) },
{ label: 'mutation', kind: toCompletionItemKind(kind) },
{ label: 'subscription', kind: toCompletionItemKind(kind) },
{ label: 'fragment', kind: toCompletionItemKind(kind) },
{ label: '{', kind: toCompletionItemKind(kind) },
]);
}

// Field names
if (kind === 'SelectionSet' || kind === 'Field' || kind === 'AliasedField') {
return getSuggestionsForFieldNames(token, typeInfo, schema);
return getSuggestionsForFieldNames(token, typeInfo, schema, kind);
}

// Argument names
Expand All @@ -102,6 +131,7 @@ export function getAutocompleteSuggestions(
label: argDef.name,
detail: String(argDef.type),
documentation: argDef.description,
kind: toCompletionItemKind(kind),
})),
);
}
Expand All @@ -117,6 +147,7 @@ export function getAutocompleteSuggestions(
label: field.name,
detail: String(field.type),
documentation: field.description,
kind: toCompletionItemKind(kind),
})),
);
}
Expand All @@ -129,7 +160,7 @@ export function getAutocompleteSuggestions(
(kind === 'ObjectField' && step === 2) ||
(kind === 'Argument' && step === 2)
) {
return getSuggestionsForInputValues(token, typeInfo);
return getSuggestionsForInputValues(token, typeInfo, kind);
}

// Fragment type conditions
Expand All @@ -139,12 +170,23 @@ export function getAutocompleteSuggestions(
state.prevState != null &&
state.prevState.kind === 'TypeCondition')
) {
return getSuggestionsForFragmentTypeConditions(token, typeInfo, schema);
return getSuggestionsForFragmentTypeConditions(
token,
typeInfo,
schema,
kind,
);
}

// Fragment spread names
if (kind === 'FragmentSpread' && step === 1) {
return getSuggestionsForFragmentSpread(token, typeInfo, schema, queryText);
return getSuggestionsForFragmentSpread(
token,
typeInfo,
schema,
queryText,
kind,
);
}

// Variable definition types
Expand All @@ -156,12 +198,12 @@ export function getAutocompleteSuggestions(
(state.prevState.kind === 'VariableDefinition' ||
state.prevState.kind === 'ListType'))
) {
return getSuggestionsForVariableDefinition(token, schema);
return getSuggestionsForVariableDefinition(token, schema, kind);
}

// Directive names
if (kind === 'Directive') {
return getSuggestionsForDirective(token, state, schema);
return getSuggestionsForDirective(token, state, schema, kind);
}

return [];
Expand All @@ -172,6 +214,7 @@ function getSuggestionsForFieldNames(
token: ContextToken,
typeInfo: AllTypeInfo,
schema: GraphQLSchema,
kind: string,
): Array<CompletionItem> {
if (typeInfo.parentType) {
const parentType = typeInfo.parentType;
Expand All @@ -194,6 +237,7 @@ function getSuggestionsForFieldNames(
deprecated: field.isDeprecated,
isDeprecated: field.isDeprecated,
deprecationReason: field.deprecationReason,
kind: toCompletionItemKind(kind),
})),
);
}
Expand All @@ -203,6 +247,7 @@ function getSuggestionsForFieldNames(
function getSuggestionsForInputValues(
token: ContextToken,
typeInfo: AllTypeInfo,
kind: string,
): CompletionItem[] {
const namedInputType = getNamedType(typeInfo.inputType as GraphQLType);
if (namedInputType instanceof GraphQLEnumType) {
Expand All @@ -217,6 +262,7 @@ function getSuggestionsForInputValues(
deprecated: value.isDeprecated,
isDeprecated: value.isDeprecated,
deprecationReason: value.deprecationReason,
kind: toCompletionItemKind(kind),
}),
),
);
Expand All @@ -226,12 +272,14 @@ function getSuggestionsForInputValues(
label: 'true',
detail: String(GraphQLBoolean),
documentation: 'Not false.',
kind: toCompletionItemKind(kind),
},

{
label: 'false',
detail: String(GraphQLBoolean),
documentation: 'Not true.',
kind: toCompletionItemKind(kind),
},
]);
}
Expand All @@ -243,6 +291,7 @@ function getSuggestionsForFragmentTypeConditions(
token: ContextToken,
typeInfo: AllTypeInfo,
schema: GraphQLSchema,
kind: string,
): Array<CompletionItem> {
let possibleTypes: GraphQLType[];
if (typeInfo.parentType) {
Expand Down Expand Up @@ -274,6 +323,7 @@ function getSuggestionsForFragmentTypeConditions(
return {
label: String(type),
documentation: (namedType && namedType.description) || '',
kind: toCompletionItemKind(kind),
};
}),
);
Expand All @@ -284,6 +334,7 @@ function getSuggestionsForFragmentSpread(
typeInfo: AllTypeInfo,
schema: GraphQLSchema,
queryText: string,
kind: string,
): Array<CompletionItem> {
const typeMap = schema.getTypeMap();
const defState = getDefinitionState(token.state);
Expand Down Expand Up @@ -316,6 +367,7 @@ function getSuggestionsForFragmentSpread(
label: frag.name.value,
detail: String(typeMap[frag.typeCondition.name.value]),
documentation: `fragment ${frag.name.value} on ${frag.typeCondition.name.value}`,
kind: toCompletionItemKind(kind),
})),
);
}
Expand Down Expand Up @@ -355,6 +407,7 @@ function getFragmentDefinitions(
function getSuggestionsForVariableDefinition(
token: ContextToken,
schema: GraphQLSchema,
kind: string,
): Array<CompletionItem> {
const inputTypeMap = schema.getTypeMap();
const inputTypes = objectValues(inputTypeMap).filter(isInputType);
Expand All @@ -364,6 +417,7 @@ function getSuggestionsForVariableDefinition(
inputTypes.map((type: any) => ({
label: type.name,
documentation: type.description,
kind: toCompletionItemKind(kind),
})),
);
}
Expand All @@ -372,6 +426,7 @@ function getSuggestionsForDirective(
token: ContextToken,
state: State,
schema: GraphQLSchema,
kind: string,
): Array<CompletionItem> {
if (state.prevState && state.prevState.kind) {
const directives = schema
Expand All @@ -382,6 +437,7 @@ function getSuggestionsForDirective(
directives.map(directive => ({
label: directive.name,
documentation: directive.description || '',
kind: toCompletionItemKind(kind),
})),
);
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -31,10 +31,10 @@ import {
import { DiagnosticSeverity, Diagnostic } from 'vscode-languageserver-types';

export const DIAGNOSTIC_SEVERITY = {
ERROR: 1 as DiagnosticSeverity,
WARNING: 2 as DiagnosticSeverity,
INFORMATION: 3 as DiagnosticSeverity,
HINT: 4 as DiagnosticSeverity,
Error: 1 as DiagnosticSeverity,
Warning: 2 as DiagnosticSeverity,
Information: 3 as DiagnosticSeverity,
Hint: 4 as DiagnosticSeverity,
};

export function getDiagnostics(
Expand All @@ -50,7 +50,7 @@ export function getDiagnostics(
const range = getRange(error.locations[0], query);
return [
{
severity: DIAGNOSTIC_SEVERITY.ERROR as DiagnosticSeverity,
severity: DIAGNOSTIC_SEVERITY.Error as DiagnosticSeverity,
message: error.message,
source: 'GraphQL: Syntax',
range,
Expand All @@ -74,15 +74,15 @@ export function validateQuery(

const validationErrorAnnotations = mapCat(
validateWithCustomRules(schema, ast, customRules, isRelayCompatMode),
error => annotations(error, DIAGNOSTIC_SEVERITY.ERROR, 'Validation'),
error => annotations(error, DIAGNOSTIC_SEVERITY.Error, 'Validation'),
);

// Note: findDeprecatedUsages was added in [email protected], but we want to
// support older versions of graphql-js.
const deprecationWarningAnnotations = !findDeprecatedUsages
? []
: mapCat(findDeprecatedUsages(schema, ast), error =>
annotations(error, DIAGNOSTIC_SEVERITY.WARNING, 'Deprecation'),
annotations(error, DIAGNOSTIC_SEVERITY.Warning, 'Deprecation'),
);

return validationErrorAnnotations.concat(deprecationWarningAnnotations);
Expand Down
6 changes: 5 additions & 1 deletion packages/graphql-language-service-interface/src/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,11 @@ export {
getDefinitionQueryResultForDefinitionNode,
} from './getDefinition';

export { getDiagnostics, validateQuery } from './getDiagnostics';
export {
getDiagnostics,
validateQuery,
DIAGNOSTIC_SEVERITY as DiagnosticSeverity,
} from './getDiagnostics';
export { getOutline } from './getOutline';
export { getHoverInformation } from './getHoverInformation';

Expand Down
5 changes: 3 additions & 2 deletions packages/monaco-graphql/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,9 @@
"name": "@graphql/monaco-graphql",
"version": "0.0.1",
"dependencies": {
"monaco-editor": "0.20.0",
"monaco-editor-core": "0.20.0",
"graphql-language-service-interface": "2.4.0-alpha.1"
},
"devDependencies": {
"monaco-editor-core": "0.20.0"
}
}
39 changes: 1 addition & 38 deletions packages/monaco-graphql/src/graphqlMode.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import * as monaco from 'monaco-editor';
import * as monaco from 'monaco-editor-core';

import IRichLanguageConfiguration = monaco.languages.LanguageConfiguration;

Expand Down Expand Up @@ -28,22 +28,6 @@ export function setupMode(defaults: LanguageServiceDefaultsImpl): IDisposable {

disposeAll(providers);

if (modeConfiguration.documentFormattingEdits) {
providers.push(
monaco.languages.registerDocumentFormattingEditProvider(
languageId,
new languageFeatures.DocumentFormattingEditProvider(worker),
),
);
}
if (modeConfiguration.documentRangeFormattingEdits) {
providers.push(
monaco.languages.registerDocumentRangeFormattingEditProvider(
languageId,
new languageFeatures.DocumentRangeFormattingEditProvider(worker),
),
);
}
if (modeConfiguration.completionItems) {
providers.push(
monaco.languages.registerCompletionItemProvider(
Expand All @@ -52,27 +36,6 @@ export function setupMode(defaults: LanguageServiceDefaultsImpl): IDisposable {
),
);
}
if (modeConfiguration.hovers) {
providers.push(
monaco.languages.registerHoverProvider(
languageId,
new languageFeatures.HoverAdapter(worker),
),
);
}
if (modeConfiguration.documentSymbols) {
providers.push(
monaco.languages.registerDocumentSymbolProvider(
languageId,
new languageFeatures.DocumentSymbolAdapter(worker),
),
);
}
if (modeConfiguration.diagnostics) {
providers.push(
new languageFeatures.DiagnosticsAdapter(languageId, worker, defaults),
);
}
}

registerProviders();
Expand Down
Loading