Mirror: TypeScript LSP plugin that finds GraphQL documents in your code and provides diagnostics, auto-complete and hover-information.

feat(core): add support for multiple schemas (#303)

+26
.changeset/light-penguins-explain.md
···
···
+
---
+
'@0no-co/graphqlsp': minor
+
---
+
+
Add support for defining multiple indepenent schemas through a new config property called `schemas`, you can
+
pass a config like the following:
+
+
```json
+
{
+
"name": "@0no-co/graphqlsp",
+
"schemas": [
+
{
+
"name": "pokemons",
+
"schema": "./pokemons.graphql",
+
"tadaOutputLocation": "./pokemons-introspection.d.ts"
+
},
+
{
+
"name": "weather",
+
"schema": "./weather.graphql",
+
"tadaOutputLocation": "./weather-introspection.d.ts"
+
}
+
]
+
}
+
```
+
+
The LSP will depending on what `graphql()` template you use figure out what API you are reaching out to.
+6 -11
packages/example-tada/introspection.d.ts
···
* instead save to a .ts instead of a .d.ts file.
*/
export type introspection = {
query: 'Query';
mutation: never;
subscription: never;
types: {
'Attack': { kind: 'OBJECT'; name: 'Attack'; fields: { 'damage': { name: 'damage'; type: { kind: 'SCALAR'; name: 'Int'; ofType: null; } }; 'name': { name: 'name'; type: { kind: 'SCALAR'; name: 'String'; ofType: null; } }; 'type': { name: 'type'; type: { kind: 'ENUM'; name: 'PokemonType'; ofType: null; } }; }; };
-
'Int': unknown;
-
'String': unknown;
'AttacksConnection': { kind: 'OBJECT'; name: 'AttacksConnection'; fields: { 'fast': { name: 'fast'; type: { kind: 'LIST'; name: never; ofType: { kind: 'OBJECT'; name: 'Attack'; ofType: null; }; } }; 'special': { name: 'special'; type: { kind: 'LIST'; name: never; ofType: { kind: 'OBJECT'; name: 'Attack'; ofType: null; }; } }; }; };
'EvolutionRequirement': { kind: 'OBJECT'; name: 'EvolutionRequirement'; fields: { 'amount': { name: 'amount'; type: { kind: 'SCALAR'; name: 'Int'; ofType: null; } }; 'name': { name: 'name'; type: { kind: 'SCALAR'; name: 'String'; ofType: null; } }; }; };
-
'Pokemon': { kind: 'OBJECT'; name: 'Pokemon'; fields: { 'attacks': { name: 'attacks'; type: { kind: 'OBJECT'; name: 'AttacksConnection'; ofType: null; } }; 'classification': { name: 'classification'; type: { kind: 'SCALAR'; name: 'String'; ofType: null; } }; 'evolutionRequirements': { name: 'evolutionRequirements'; type: { kind: 'LIST'; name: never; ofType: { kind: 'OBJECT'; name: 'EvolutionRequirement'; ofType: null; }; } }; 'evolutions': { name: 'evolutions'; type: { kind: 'LIST'; name: never; ofType: { kind: 'OBJECT'; name: 'Pokemon'; ofType: null; }; } }; 'fleeRate': { name: 'fleeRate'; type: { kind: 'SCALAR'; name: 'Float'; ofType: null; } }; 'height': { name: 'height'; type: { kind: 'OBJECT'; name: 'PokemonDimension'; ofType: null; } }; 'id': { name: 'id'; type: { kind: 'NON_NULL'; name: never; ofType: { kind: 'SCALAR'; name: 'ID'; ofType: null; }; } }; 'maxCP': { name: 'maxCP'; type: { kind: 'SCALAR'; name: 'Int'; ofType: null; } }; 'maxHP': { name: 'maxHP'; type: { kind: 'SCALAR'; name: 'Int'; ofType: null; } }; 'name': { name: 'name'; type: { kind: 'NON_NULL'; name: never; ofType: { kind: 'SCALAR'; name: 'String'; ofType: null; }; } }; 'resistant': { name: 'resistant'; type: { kind: 'LIST'; name: never; ofType: { kind: 'ENUM'; name: 'PokemonType'; ofType: null; }; } }; 'types': { name: 'types'; type: { kind: 'LIST'; name: never; ofType: { kind: 'ENUM'; name: 'PokemonType'; ofType: null; }; } }; 'weaknesses': { name: 'weaknesses'; type: { kind: 'LIST'; name: never; ofType: { kind: 'ENUM'; name: 'PokemonType'; ofType: null; }; } }; 'weight': { name: 'weight'; type: { kind: 'OBJECT'; name: 'PokemonDimension'; ofType: null; } }; }; };
'Float': unknown;
'ID': unknown;
'PokemonDimension': { kind: 'OBJECT'; name: 'PokemonDimension'; fields: { 'maximum': { name: 'maximum'; type: { kind: 'SCALAR'; name: 'String'; ofType: null; } }; 'minimum': { name: 'minimum'; type: { kind: 'SCALAR'; name: 'String'; ofType: null; } }; }; };
-
'PokemonType': { kind: 'ENUM'; name: 'PokemonType'; type: 'Bug' | 'Dark' | 'Dragon' | 'Electric' | 'Fairy' | 'Fighting' | 'Fire' | 'Flying' | 'Ghost' | 'Grass' | 'Ground' | 'Ice' | 'Normal' | 'Poison' | 'Psychic' | 'Rock' | 'Steel' | 'Water'; };
'Query': { kind: 'OBJECT'; name: 'Query'; fields: { 'pokemon': { name: 'pokemon'; type: { kind: 'OBJECT'; name: 'Pokemon'; ofType: null; } }; 'pokemons': { name: 'pokemons'; type: { kind: 'LIST'; name: never; ofType: { kind: 'OBJECT'; name: 'Pokemon'; ofType: null; }; } }; }; };
-
'Boolean': unknown;
};
};
import * as gqlTada from 'gql.tada';
-
-
declare module 'gql.tada' {
-
interface setupSchema {
-
introspection: introspection;
-
}
-
}
···
* instead save to a .ts instead of a .d.ts file.
*/
export type introspection = {
+
name: 'pokemons';
query: 'Query';
mutation: never;
subscription: never;
types: {
'Attack': { kind: 'OBJECT'; name: 'Attack'; fields: { 'damage': { name: 'damage'; type: { kind: 'SCALAR'; name: 'Int'; ofType: null; } }; 'name': { name: 'name'; type: { kind: 'SCALAR'; name: 'String'; ofType: null; } }; 'type': { name: 'type'; type: { kind: 'ENUM'; name: 'PokemonType'; ofType: null; } }; }; };
'AttacksConnection': { kind: 'OBJECT'; name: 'AttacksConnection'; fields: { 'fast': { name: 'fast'; type: { kind: 'LIST'; name: never; ofType: { kind: 'OBJECT'; name: 'Attack'; ofType: null; }; } }; 'special': { name: 'special'; type: { kind: 'LIST'; name: never; ofType: { kind: 'OBJECT'; name: 'Attack'; ofType: null; }; } }; }; };
+
'Boolean': unknown;
'EvolutionRequirement': { kind: 'OBJECT'; name: 'EvolutionRequirement'; fields: { 'amount': { name: 'amount'; type: { kind: 'SCALAR'; name: 'Int'; ofType: null; } }; 'name': { name: 'name'; type: { kind: 'SCALAR'; name: 'String'; ofType: null; } }; }; };
'Float': unknown;
'ID': unknown;
+
'Int': unknown;
+
'Pokemon': { kind: 'OBJECT'; name: 'Pokemon'; fields: { 'attacks': { name: 'attacks'; type: { kind: 'OBJECT'; name: 'AttacksConnection'; ofType: null; } }; 'classification': { name: 'classification'; type: { kind: 'SCALAR'; name: 'String'; ofType: null; } }; 'evolutionRequirements': { name: 'evolutionRequirements'; type: { kind: 'LIST'; name: never; ofType: { kind: 'OBJECT'; name: 'EvolutionRequirement'; ofType: null; }; } }; 'evolutions': { name: 'evolutions'; type: { kind: 'LIST'; name: never; ofType: { kind: 'OBJECT'; name: 'Pokemon'; ofType: null; }; } }; 'fleeRate': { name: 'fleeRate'; type: { kind: 'SCALAR'; name: 'Float'; ofType: null; } }; 'height': { name: 'height'; type: { kind: 'OBJECT'; name: 'PokemonDimension'; ofType: null; } }; 'id': { name: 'id'; type: { kind: 'NON_NULL'; name: never; ofType: { kind: 'SCALAR'; name: 'ID'; ofType: null; }; } }; 'maxCP': { name: 'maxCP'; type: { kind: 'SCALAR'; name: 'Int'; ofType: null; } }; 'maxHP': { name: 'maxHP'; type: { kind: 'SCALAR'; name: 'Int'; ofType: null; } }; 'name': { name: 'name'; type: { kind: 'NON_NULL'; name: never; ofType: { kind: 'SCALAR'; name: 'String'; ofType: null; }; } }; 'resistant': { name: 'resistant'; type: { kind: 'LIST'; name: never; ofType: { kind: 'ENUM'; name: 'PokemonType'; ofType: null; }; } }; 'types': { name: 'types'; type: { kind: 'LIST'; name: never; ofType: { kind: 'ENUM'; name: 'PokemonType'; ofType: null; }; } }; 'weaknesses': { name: 'weaknesses'; type: { kind: 'LIST'; name: never; ofType: { kind: 'ENUM'; name: 'PokemonType'; ofType: null; }; } }; 'weight': { name: 'weight'; type: { kind: 'OBJECT'; name: 'PokemonDimension'; ofType: null; } }; }; };
'PokemonDimension': { kind: 'OBJECT'; name: 'PokemonDimension'; fields: { 'maximum': { name: 'maximum'; type: { kind: 'SCALAR'; name: 'String'; ofType: null; } }; 'minimum': { name: 'minimum'; type: { kind: 'SCALAR'; name: 'String'; ofType: null; } }; }; };
+
'PokemonType': { name: 'PokemonType'; enumValues: 'Bug' | 'Dark' | 'Dragon' | 'Electric' | 'Fairy' | 'Fighting' | 'Fire' | 'Flying' | 'Ghost' | 'Grass' | 'Ground' | 'Ice' | 'Normal' | 'Poison' | 'Psychic' | 'Rock' | 'Steel' | 'Water'; };
'Query': { kind: 'OBJECT'; name: 'Query'; fields: { 'pokemon': { name: 'pokemon'; type: { kind: 'OBJECT'; name: 'Pokemon'; ofType: null; } }; 'pokemons': { name: 'pokemons'; type: { kind: 'LIST'; name: never; ofType: { kind: 'OBJECT'; name: 'Pokemon'; ofType: null; }; } }; }; };
+
'String': unknown;
};
};
import * as gqlTada from 'gql.tada';
+1 -1
packages/example-tada/package.json
···
"license": "ISC",
"dependencies": {
"@graphql-typed-document-node/core": "^3.2.0",
-
"gql.tada": "^1.4.0",
"@urql/core": "^3.0.0",
"graphql": "^16.8.1",
"urql": "^4.0.6"
···
"license": "ISC",
"dependencies": {
"@graphql-typed-document-node/core": "^3.2.0",
+
"gql.tada": "1.5.9-canary-8711af177005f46fa3e06d990b6ba28e353e7f9b",
"@urql/core": "^3.0.0",
"graphql": "^16.8.1",
"urql": "^4.0.6"
+7 -2
packages/example-tada/tsconfig.json
···
"plugins": [
{
"name": "@0no-co/graphqlsp",
-
"schema": "./schema.graphql",
-
"tadaOutputLocation": "./introspection.d.ts"
}
],
"jsx": "react-jsx",
···
"plugins": [
{
"name": "@0no-co/graphqlsp",
+
"schemas": [
+
{
+
"name": "pokemons",
+
"schema": "./schema.graphql",
+
"tadaOutputLocation": "./introspection.d.ts"
+
}
+
]
}
],
"jsx": "react-jsx",
+1 -1
packages/graphqlsp/package.json
···
"typescript": "^5.3.3"
},
"dependencies": {
-
"@gql.tada/internal": "^0.1.2",
"graphql": "^16.8.1",
"node-fetch": "^2.0.0"
},
···
"typescript": "^5.3.3"
},
"dependencies": {
+
"@gql.tada/internal": "0.3.0-canary-8711af177005f46fa3e06d990b6ba28e353e7f9b",
"graphql": "^16.8.1",
"node-fetch": "^2.0.0"
},
+47 -8
packages/graphqlsp/src/ast/index.ts
···
return wip;
}
export function findAllCallExpressions(
sourceFile: ts.SourceFile,
info: ts.server.PluginCreateInfo,
shouldSearchFragments: boolean = true
): {
-
nodes: Array<ts.NoSubstitutionTemplateLiteral>;
fragments: Array<FragmentDefinitionNode>;
} {
-
const result: Array<ts.NoSubstitutionTemplateLiteral> = [];
let fragments: Array<FragmentDefinitionNode> = [];
let hasTriedToFindFragments = shouldSearchFragments ? false : true;
function find(node: ts.Node) {
if (ts.isCallExpression(node) && templates.has(node.expression.getText())) {
const [arg, arg2] = node.arguments;
if (!hasTriedToFindFragments && !arg2) {
···
}
if (arg && ts.isNoSubstitutionTemplateLiteral(arg)) {
-
result.push(arg);
}
return;
} else {
···
}
export function findAllPersistedCallExpressions(
-
sourceFile: ts.SourceFile
-
): Array<ts.CallExpression> {
-
const result: Array<ts.CallExpression> = [];
function find(node: ts.Node) {
-
if (ts.isCallExpression(node)) {
// This expression ideally for us looks like <template>.persisted
const expression = node.expression.getText();
const parts = expression.split('.');
···
const [template, method] = parts;
if (!templates.has(template) || method !== 'persisted') return;
-
result.push(node);
} else {
ts.forEachChild(node, find);
}
···
return wip;
}
+
export const getSchemaName = (
+
node: ts.CallExpression,
+
typeChecker?: ts.TypeChecker
+
): string | null => {
+
if (!typeChecker) return null;
+
+
const expression = ts.isPropertyAccessExpression(node.expression)
+
? node.expression.expression
+
: node.expression;
+
const type = typeChecker.getTypeAtLocation(expression);
+
if (type) {
+
const brandTypeSymbol = type.getProperty('__name');
+
if (brandTypeSymbol) {
+
const brand = typeChecker.getTypeOfSymbol(brandTypeSymbol);
+
if (brand.isUnionOrIntersection()) {
+
const found = brand.types.find(x => x.isStringLiteral());
+
return found && found.isStringLiteral() ? found.value : null;
+
} else if (brand.isStringLiteral()) {
+
return brand.value;
+
}
+
}
+
}
+
+
return null;
+
};
+
export function findAllCallExpressions(
sourceFile: ts.SourceFile,
info: ts.server.PluginCreateInfo,
shouldSearchFragments: boolean = true
): {
+
nodes: Array<{
+
node: ts.NoSubstitutionTemplateLiteral;
+
schema: string | null;
+
}>;
fragments: Array<FragmentDefinitionNode>;
} {
+
const typeChecker = info.languageService.getProgram()?.getTypeChecker();
+
const result: Array<{
+
node: ts.NoSubstitutionTemplateLiteral;
+
schema: string | null;
+
}> = [];
let fragments: Array<FragmentDefinitionNode> = [];
let hasTriedToFindFragments = shouldSearchFragments ? false : true;
function find(node: ts.Node) {
if (ts.isCallExpression(node) && templates.has(node.expression.getText())) {
+
const name = getSchemaName(node, typeChecker);
+
const [arg, arg2] = node.arguments;
if (!hasTriedToFindFragments && !arg2) {
···
}
if (arg && ts.isNoSubstitutionTemplateLiteral(arg)) {
+
result.push({ node: arg, schema: name });
}
return;
} else {
···
}
export function findAllPersistedCallExpressions(
+
sourceFile: ts.SourceFile,
+
info: ts.server.PluginCreateInfo
+
): Array<{ node: ts.CallExpression; schema: string | null }> {
+
const result: Array<{ node: ts.CallExpression; schema: string | null }> = [];
+
const typeChecker = info.languageService.getProgram()?.getTypeChecker();
function find(node: ts.Node) {
+
if (node && ts.isCallExpression(node)) {
// This expression ideally for us looks like <template>.persisted
const expression = node.expression.getText();
const parts = expression.split('.');
···
const [template, method] = parts;
if (!templates.has(template) || method !== 'persisted') return;
+
const name = getSchemaName(node, typeChecker);
+
+
result.push({ node, schema: name });
} else {
ts.forEachChild(node, find);
}
+15 -4
packages/graphqlsp/src/autoComplete.ts
···
bubbleUpTemplate,
findNode,
getAllFragments,
getSource,
} from './ast';
import { Cursor } from './ast/cursor';
···
import { getToken } from './ast/token';
import { getSuggestionsForFragmentSpread } from './graphql/getFragmentSpreadSuggestions';
import { templates } from './ast/templates';
export function getGraphQLCompletions(
filename: string,
cursorPosition: number,
-
schema: { current: GraphQLSchema | null },
info: ts.server.PluginCreateInfo
): ts.WithMetadata<ts.CompletionInfo> | undefined {
const isCallExpression = info.config.templateIsCallExpression ?? true;
···
? bubbleUpCallExpression(node)
: bubbleUpTemplate(node);
-
let text, cursor;
if (
ts.isCallExpression(node) &&
isCallExpression &&
···
node.arguments.length > 0 &&
ts.isNoSubstitutionTemplateLiteral(node.arguments[0])
) {
const foundToken = getToken(node.arguments[0], cursorPosition);
-
if (!schema.current || !foundToken) return undefined;
const queryText = node.arguments[0].getText().slice(1, -1);
const fragments = getAllFragments(filename, node, info);
···
text = combinedText;
cursor = new Cursor(foundToken.line, foundToken.start - 1);
} else {
return undefined;
}
const [suggestions, spreadSuggestions] = getSuggestionsInternal(
-
schema.current,
text,
cursor
);
···
bubbleUpTemplate,
findNode,
getAllFragments,
+
getSchemaName,
getSource,
} from './ast';
import { Cursor } from './ast/cursor';
···
import { getToken } from './ast/token';
import { getSuggestionsForFragmentSpread } from './graphql/getFragmentSpreadSuggestions';
import { templates } from './ast/templates';
+
import { SchemaRef } from './graphql/getSchema';
export function getGraphQLCompletions(
filename: string,
cursorPosition: number,
+
schema: SchemaRef,
info: ts.server.PluginCreateInfo
): ts.WithMetadata<ts.CompletionInfo> | undefined {
const isCallExpression = info.config.templateIsCallExpression ?? true;
···
? bubbleUpCallExpression(node)
: bubbleUpTemplate(node);
+
let text, cursor, schemaToUse: GraphQLSchema | undefined;
if (
ts.isCallExpression(node) &&
isCallExpression &&
···
node.arguments.length > 0 &&
ts.isNoSubstitutionTemplateLiteral(node.arguments[0])
) {
+
const typeChecker = info.languageService.getProgram()?.getTypeChecker();
+
const schemaName = getSchemaName(node, typeChecker);
+
+
schemaToUse =
+
schemaName && schema.multi[schemaName]
+
? schema.multi[schemaName]?.schema
+
: schema.current?.schema;
+
const foundToken = getToken(node.arguments[0], cursorPosition);
+
if (!schemaToUse || !foundToken) return undefined;
const queryText = node.arguments[0].getText().slice(1, -1);
const fragments = getAllFragments(filename, node, info);
···
text = combinedText;
cursor = new Cursor(foundToken.line, foundToken.start - 1);
+
schemaToUse = schema.current.schema;
} else {
return undefined;
}
const [suggestions, spreadSuggestions] = getSuggestionsInternal(
+
schemaToUse,
text,
cursor
);
+2 -2
packages/graphqlsp/src/checkImports.ts
···
const exports = typeChecker.getExportsOfModule(symbol);
const exportedNames = exports.map(symb => symb.name);
const nodes = callExpressions.nodes.filter(x => {
-
let parent = x.parent;
while (
parent &&
!ts.isSourceFile(parent) &&
···
});
nodes.forEach(node => {
-
const text = resolveTemplate(node, src.fileName, info).combinedText;
try {
const parsed = parse(text, { noLocation: true });
if (parsed.definitions.every(x => x.kind === Kind.FRAGMENT_DEFINITION)) {
···
const exports = typeChecker.getExportsOfModule(symbol);
const exportedNames = exports.map(symb => symb.name);
const nodes = callExpressions.nodes.filter(x => {
+
let parent = x.node.parent;
while (
parent &&
!ts.isSourceFile(parent) &&
···
});
nodes.forEach(node => {
+
const text = resolveTemplate(node.node, src.fileName, info).combinedText;
try {
const parsed = parse(text, { noLocation: true });
if (parsed.definitions.every(x => x.kind === Kind.FRAGMENT_DEFINITION)) {
+37 -19
packages/graphqlsp/src/diagnostics.ts
···
getDocumentReferenceFromDocumentNode,
getDocumentReferenceFromTypeQuery,
} from './persisted';
const clientDirectives = new Set([
'populate',
···
export function getGraphQLDiagnostics(
filename: string,
-
schema: { current: GraphQLSchema | null; version: number },
info: ts.server.PluginCreateInfo
): ts.Diagnostic[] | undefined {
const isCallExpression = info.config.templateIsCallExpression ?? true;
···
if (!source) return undefined;
let fragments: Array<FragmentDefinitionNode> = [],
-
nodes: (ts.TaggedTemplateExpression | ts.NoSubstitutionTemplateLiteral)[];
if (isCallExpression) {
const result = findAllCallExpressions(source, info);
fragments = result.fragments;
nodes = result.nodes;
} else {
-
nodes = findAllTaggedTemplateNodes(source);
}
-
const texts = nodes.map(node => {
if (
(ts.isNoSubstitutionTemplateLiteral(node) ||
ts.isTemplateExpression(node)) &&
···
let fragmentDiagnostics: ts.Diagnostic[] = [];
if (isCallExpression) {
-
const persistedCalls = findAllPersistedCallExpressions(source);
// We need to check whether the user has correctly inserted a hash,
// by means of providing an argument to the function and that they
// are establishing a reference to the document by means of the generic.
-
//
-
// OPTIONAL: we could also check whether the hash is out of date with the
-
// document but this removes support for self-generating identifiers
const persistedDiagnostics = persistedCalls
-
.map<ts.Diagnostic | null>(callExpression => {
if (!callExpression.typeArguments && !callExpression.arguments[1]) {
return {
category: ts.DiagnosticCategory.Warning,
···
const hash = callExpression.arguments[0].getText().slice(1, -1);
if (hash.startsWith('sha256:')) {
-
const hash = generateHashForDocument(
info,
initializer.arguments[0],
foundFilename
);
-
if (!hash) return null;
-
const upToDateHash = `sha256:${hash}`;
if (upToDateHash !== hash) {
return {
category: ts.DiagnosticCategory.Warning,
···
const moduleSpecifierToFragments = getColocatedFragmentNames(source, info);
const usedFragments = new Set();
-
nodes.forEach(node => {
try {
const parsed = parse(node.getText().slice(1, -1), {
noLocation: true,
···
nodes,
fragments,
}: {
-
nodes: (ts.TaggedTemplateExpression | ts.NoSubstitutionTemplateLiteral)[];
fragments: FragmentDefinitionNode[];
},
-
schema: { current: GraphQLSchema | null; version: number },
info: ts.server.PluginCreateInfo
) => {
const filename = source.fileName;
···
const diagnostics = nodes
.map(originalNode => {
-
let node = originalNode;
if (
!isCallExpression &&
(ts.isNoSubstitutionTemplateLiteral(node) ||
···
} catch (e) {}
}
const graphQLDiagnostics = getDiagnostics(
text,
-
schema.current,
undefined,
undefined,
docFragments
···
message: 'Operation should contain a name.',
start: node.getStart(),
code: MISSING_OPERATION_NAME_CODE,
-
length: originalNode.getText().length,
range: {} as any,
severity: 2,
} as any);
···
const usageDiagnostics =
checkFieldUsageInFile(
source,
-
nodes as ts.NoSubstitutionTemplateLiteral[],
info
) || [];
···
getDocumentReferenceFromDocumentNode,
getDocumentReferenceFromTypeQuery,
} from './persisted';
+
import { SchemaRef } from './graphql/getSchema';
const clientDirectives = new Set([
'populate',
···
export function getGraphQLDiagnostics(
filename: string,
+
schema: SchemaRef,
info: ts.server.PluginCreateInfo
): ts.Diagnostic[] | undefined {
const isCallExpression = info.config.templateIsCallExpression ?? true;
···
if (!source) return undefined;
let fragments: Array<FragmentDefinitionNode> = [],
+
nodes: {
+
node: ts.NoSubstitutionTemplateLiteral | ts.TaggedTemplateExpression;
+
schema: string | null;
+
}[];
if (isCallExpression) {
const result = findAllCallExpressions(source, info);
fragments = result.fragments;
nodes = result.nodes;
} else {
+
nodes = findAllTaggedTemplateNodes(source).map(x => ({
+
node: x,
+
schema: null,
+
}));
}
+
const texts = nodes.map(({ node }) => {
if (
(ts.isNoSubstitutionTemplateLiteral(node) ||
ts.isTemplateExpression(node)) &&
···
let fragmentDiagnostics: ts.Diagnostic[] = [];
if (isCallExpression) {
+
const persistedCalls = findAllPersistedCallExpressions(source, info);
// We need to check whether the user has correctly inserted a hash,
// by means of providing an argument to the function and that they
// are establishing a reference to the document by means of the generic.
const persistedDiagnostics = persistedCalls
+
.map<ts.Diagnostic | null>(found => {
+
const { node: callExpression } = found;
if (!callExpression.typeArguments && !callExpression.arguments[1]) {
return {
category: ts.DiagnosticCategory.Warning,
···
const hash = callExpression.arguments[0].getText().slice(1, -1);
if (hash.startsWith('sha256:')) {
+
const generatedHash = generateHashForDocument(
info,
initializer.arguments[0],
foundFilename
);
+
if (!generatedHash) return null;
+
+
const upToDateHash = `sha256:${generatedHash}`;
if (upToDateHash !== hash) {
return {
category: ts.DiagnosticCategory.Warning,
···
const moduleSpecifierToFragments = getColocatedFragmentNames(source, info);
const usedFragments = new Set();
+
nodes.forEach(({ node }) => {
try {
const parsed = parse(node.getText().slice(1, -1), {
noLocation: true,
···
nodes,
fragments,
}: {
+
nodes: {
+
node: ts.TaggedTemplateExpression | ts.NoSubstitutionTemplateLiteral;
+
schema: string | null;
+
}[];
fragments: FragmentDefinitionNode[];
},
+
schema: SchemaRef,
info: ts.server.PluginCreateInfo
) => {
const filename = source.fileName;
···
const diagnostics = nodes
.map(originalNode => {
+
let node = originalNode.node;
if (
!isCallExpression &&
(ts.isNoSubstitutionTemplateLiteral(node) ||
···
} catch (e) {}
}
+
const schemaToUse =
+
originalNode.schema && schema.multi[originalNode.schema]
+
? schema.multi[originalNode.schema]?.schema
+
: schema.current?.schema;
+
+
if (!schemaToUse) {
+
return undefined;
+
}
+
const graphQLDiagnostics = getDiagnostics(
text,
+
schemaToUse,
undefined,
undefined,
docFragments
···
message: 'Operation should contain a name.',
start: node.getStart(),
code: MISSING_OPERATION_NAME_CODE,
+
length: originalNode.node.getText().length,
range: {} as any,
severity: 2,
} as any);
···
const usageDiagnostics =
checkFieldUsageInFile(
source,
+
nodes.map(x => x.node) as ts.NoSubstitutionTemplateLiteral[],
info
) || [];
+43 -35
packages/graphqlsp/src/graphql/getSchema.ts
···
import fs from 'node:fs/promises';
import path from 'path';
-
import type { GraphQLSchema, IntrospectionQuery } from 'graphql';
import {
-
type SchemaOrigin,
type SchemaLoaderResult,
-
load,
-
resolveTypeScriptRootDir,
minifyIntrospection,
outputIntrospectionFile,
} from '@gql.tada/internal';
import { ts } from '../ts';
···
}
}
-
export interface SchemaRef {
-
current: GraphQLSchema | null;
-
version: number;
-
}
export const loadSchema = (
// TODO: abstract info away
info: ts.server.PluginCreateInfo,
-
origin: SchemaOrigin,
logger: Logger
-
): SchemaRef => {
-
let loaderResult: SchemaLoaderResult | null = null;
-
const ref: SchemaRef = { current: null, version: 0 };
(async () => {
const rootPath =
(await resolveTypeScriptRootDir(info.project.getProjectName())) ||
path.dirname(info.project.getProjectName());
const tadaDisablePreprocessing =
info.config.tadaDisablePreprocessing ?? false;
const tadaOutputLocation =
···
logger('Got root-directory to resolve schema from: ' + rootPath);
logger('Resolving schema from "schema" config: ' + JSON.stringify(origin));
-
const loader = load({ origin, rootPath });
-
try {
-
logger(`Loading schema from "${origin}"`);
-
loaderResult = await loader.load();
} catch (error) {
logger(`Failed to load schema: ${error}`);
}
-
if (loaderResult) {
-
ref.current = loaderResult && loaderResult.schema;
-
ref.version++;
-
if (tadaOutputLocation) {
-
saveTadaIntrospection(
-
loaderResult.introspection,
-
tadaOutputLocation,
-
tadaDisablePreprocessing,
-
logger
-
);
-
}
}
-
loader.notifyOnUpdate(result => {
-
logger(`Got schema for origin "${origin}"`);
-
ref.current = (loaderResult = result).schema;
-
ref.version++;
-
if (tadaOutputLocation) {
saveTadaIntrospection(
-
loaderResult.introspection,
-
tadaOutputLocation,
tadaDisablePreprocessing,
logger
);
···
});
})();
-
return ref;
};
···
import fs from 'node:fs/promises';
import path from 'path';
+
import type { IntrospectionQuery } from 'graphql';
import {
type SchemaLoaderResult,
+
type SchemaRef as _SchemaRef,
+
type GraphQLSPConfig,
+
loadRef,
minifyIntrospection,
outputIntrospectionFile,
+
resolveTypeScriptRootDir,
} from '@gql.tada/internal';
import { ts } from '../ts';
···
}
}
+
export type SchemaRef = _SchemaRef<SchemaLoaderResult | null>;
export const loadSchema = (
// TODO: abstract info away
info: ts.server.PluginCreateInfo,
+
origin: GraphQLSPConfig,
logger: Logger
+
): _SchemaRef<SchemaLoaderResult | null> => {
+
const ref = loadRef(origin);
(async () => {
const rootPath =
(await resolveTypeScriptRootDir(info.project.getProjectName())) ||
path.dirname(info.project.getProjectName());
+
const tadaDisablePreprocessing =
info.config.tadaDisablePreprocessing ?? false;
const tadaOutputLocation =
···
logger('Got root-directory to resolve schema from: ' + rootPath);
logger('Resolving schema from "schema" config: ' + JSON.stringify(origin));
try {
+
logger(`Loading schema...`);
+
await ref.load({ rootPath });
} catch (error) {
logger(`Failed to load schema: ${error}`);
}
+
if (ref.current) {
+
saveTadaIntrospection(
+
ref.current.introspection,
+
tadaOutputLocation,
+
tadaDisablePreprocessing,
+
logger
+
);
+
} else if (ref.multi) {
+
Object.values(ref.multi).forEach(value => {
+
if (!value) return;
+
+
if (value.tadaOutputLocation) {
+
saveTadaIntrospection(
+
value.introspection,
+
path.resolve(rootPath, value.tadaOutputLocation),
+
tadaDisablePreprocessing,
+
logger
+
);
+
}
+
});
}
+
ref.autoupdate({ rootPath }, (schemaRef, value) => {
+
if (!value) return;
+
+
if (value.tadaOutputLocation) {
+
const found = schemaRef.multi
+
? schemaRef.multi[value.name as string]
+
: schemaRef.current;
+
if (!found) return;
saveTadaIntrospection(
+
found.introspection,
+
path.resolve(rootPath, value.tadaOutputLocation),
tadaDisablePreprocessing,
logger
);
···
});
})();
+
return ref as any;
};
+3 -2
packages/graphqlsp/src/index.ts
···
interface Config {
schema: SchemaOrigin;
tadaDisablePreprocessing?: boolean;
templateIsCallExpression?: boolean;
shouldCheckForColocatedFragments?: boolean;
···
const config: Config = info.config;
logger('config: ' + JSON.stringify(config));
-
if (!config.schema) {
logger('Missing "schema" option in configuration.');
throw new Error('Please provide a GraphQL Schema!');
}
···
const proxy = createBasicDecorator(info);
-
const schema = loadSchema(info, config.schema, logger);
proxy.getSemanticDiagnostics = (filename: string): ts.Diagnostic[] => {
const originalDiagnostics =
···
interface Config {
schema: SchemaOrigin;
+
schemas: SchemaOrigin[];
tadaDisablePreprocessing?: boolean;
templateIsCallExpression?: boolean;
shouldCheckForColocatedFragments?: boolean;
···
const config: Config = info.config;
logger('config: ' + JSON.stringify(config));
+
if (!config.schema && !config.schemas) {
logger('Missing "schema" option in configuration.');
throw new Error('Please provide a GraphQL Schema!');
}
···
const proxy = createBasicDecorator(info);
+
const schema = loadSchema(info, config, logger);
proxy.getSemanticDiagnostics = (filename: string): ts.Diagnostic[] => {
const originalDiagnostics =
+1 -1
packages/graphqlsp/src/persisted.ts
···
// is more defined we will need to use the ts.Symbol to support re-exporting
// this function by means of "export const peristed = graphql.persisted".
if (
-
!ts.isCallExpression(callExpression) ||
!isPersistedCall(callExpression.expression) ||
(!callExpression.typeArguments && !callExpression.arguments[1])
)
···
// is more defined we will need to use the ts.Symbol to support re-exporting
// this function by means of "export const peristed = graphql.persisted".
if (
+
(callExpression && !ts.isCallExpression(callExpression)) ||
!isPersistedCall(callExpression.expression) ||
(!callExpression.typeArguments && !callExpression.arguments[1])
)
+15 -4
packages/graphqlsp/src/quickInfo.ts
···
bubbleUpCallExpression,
bubbleUpTemplate,
findNode,
getSource,
} from './ast';
import { resolveTemplate } from './ast/resolve';
import { getToken } from './ast/token';
import { Cursor } from './ast/cursor';
import { templates } from './ast/templates';
export function getGraphQLQuickInfo(
filename: string,
cursorPosition: number,
-
schema: { current: GraphQLSchema | null },
info: ts.server.PluginCreateInfo
): ts.QuickInfo | undefined {
const isCallExpression = info.config.templateIsCallExpression ?? true;
···
? bubbleUpCallExpression(node)
: bubbleUpTemplate(node);
-
let cursor, text;
if (
ts.isCallExpression(node) &&
isCallExpression &&
···
node.arguments.length > 0 &&
ts.isNoSubstitutionTemplateLiteral(node.arguments[0])
) {
const foundToken = getToken(node.arguments[0], cursorPosition);
-
if (!schema.current || !foundToken) return undefined;
text = node.arguments[0].getText();
cursor = new Cursor(foundToken.line, foundToken.start - 1);
···
foundToken.line = foundToken.line + amountOfLines;
text = combinedText;
cursor = new Cursor(foundToken.line, foundToken.start - 1);
} else {
return undefined;
}
-
const hoverInfo = getHoverInformation(schema.current, text, cursor);
return {
kind: ts.ScriptElementKind.label,
···
bubbleUpCallExpression,
bubbleUpTemplate,
findNode,
+
getSchemaName,
getSource,
} from './ast';
import { resolveTemplate } from './ast/resolve';
import { getToken } from './ast/token';
import { Cursor } from './ast/cursor';
import { templates } from './ast/templates';
+
import { SchemaRef } from './graphql/getSchema';
export function getGraphQLQuickInfo(
filename: string,
cursorPosition: number,
+
schema: SchemaRef,
info: ts.server.PluginCreateInfo
): ts.QuickInfo | undefined {
const isCallExpression = info.config.templateIsCallExpression ?? true;
···
? bubbleUpCallExpression(node)
: bubbleUpTemplate(node);
+
let cursor, text, schemaToUse: GraphQLSchema | undefined;
if (
ts.isCallExpression(node) &&
isCallExpression &&
···
node.arguments.length > 0 &&
ts.isNoSubstitutionTemplateLiteral(node.arguments[0])
) {
+
const typeChecker = info.languageService.getProgram()?.getTypeChecker();
+
const schemaName = getSchemaName(node, typeChecker);
+
+
schemaToUse =
+
schemaName && schema.multi[schemaName]
+
? schema.multi[schemaName]?.schema
+
: schema.current?.schema;
+
const foundToken = getToken(node.arguments[0], cursorPosition);
+
if (!schemaToUse || !foundToken) return undefined;
text = node.arguments[0].getText();
cursor = new Cursor(foundToken.line, foundToken.start - 1);
···
foundToken.line = foundToken.line + amountOfLines;
text = combinedText;
cursor = new Cursor(foundToken.line, foundToken.start - 1);
+
schemaToUse = schema.current.schema;
} else {
return undefined;
}
+
const hoverInfo = getHoverInformation(schemaToUse, text, cursor);
return {
kind: ts.ScriptElementKind.label,
+269 -45
pnpm-lock.yaml
···
specifier: ^3.0.0
version: 3.2.2(graphql@16.8.1)
gql.tada:
-
specifier: ^1.4.0
-
version: 1.4.0(graphql@16.8.1)
graphql:
specifier: ^16.8.1
version: 16.8.1
···
packages/graphqlsp:
dependencies:
'@gql.tada/internal':
-
specifier: ^0.1.2
-
version: 0.1.2(graphql@16.8.1)(typescript@5.3.3)
graphql:
specifier: ^16.8.1
version: 16.8.1
···
version: link:../../../packages/graphqlsp
'@urql/core':
specifier: ^4.0.4
-
version: 4.2.2(graphql@16.8.1)
devDependencies:
typescript:
specifier: ^5.3.3
···
dependencies:
graphql: 16.8.1
/@actions/core@1.10.1:
resolution: {integrity: sha512-3lBR9EDAY+iYIpTnTIXmWcNbX3T2kCkAEQGIQx4NVQ0575nk2k3GRZDTPQG+vVtS2izSLmINlxXf0uLtnrTP+g==}
dependencies:
···
dependencies:
'@jridgewell/gen-mapping': 0.3.3
'@jridgewell/trace-mapping': 0.3.21
-
dev: true
/@ardatan/relay-compiler@12.0.0(graphql@16.8.1):
resolution: {integrity: sha512-9anThAaj1dQr6IGmzBMcfzOQKTa5artjuPmw8NYK/fiGEMjADbSguBY2FMDykt+QhilR3wc9VA/3yVju7JHg7Q==}
···
/@babel/helper-string-parser@7.23.4:
resolution: {integrity: sha512-803gmbQdqwdf4olxrX4AJyFBV/RTr3rSmOj0rKwesmzlfhYNDEs+/iOcznzpNWlJlIlTJC2QfPFcHB6DlzdVLQ==}
engines: {node: '>=6.9.0'}
-
dev: true
/@babel/helper-validator-identifier@7.22.20:
resolution: {integrity: sha512-Y4OZ+ytlatR8AI+8KZfKuL5urKp7qey08ha31L8b3BwewJAoJamTzyvxPR/5D+KkdJCGPq/+8TukHBlY10FX9A==}
engines: {node: '>=6.9.0'}
-
dev: true
/@babel/helper-validator-option@7.23.5:
resolution: {integrity: sha512-85ttAOMLsr53VgXkTbkx8oA6YTfT4q7/HzXSLEYmjcSTJPMPQtvq1BD79Byep5xMUYbGRzEpDsjUf3dyp54IKw==}
···
'@babel/types': 7.23.6
dev: true
/@babel/plugin-proposal-class-properties@7.18.6(@babel/core@7.23.7):
resolution: {integrity: sha512-cumfXOF0+nzZrrN8Rf0t7M+tF6sZc7vhQwYQck9q1/5w2OExlD+b4v4RpMJFaV1Z7WcDRgO6FqvxqxGlwo+RHQ==}
engines: {node: '>=6.9.0'}
···
'@babel/helper-string-parser': 7.23.4
'@babel/helper-validator-identifier': 7.22.20
to-fast-properties: 2.0.0
-
dev: true
/@changesets/apply-release-plan@6.1.4:
resolution: {integrity: sha512-FMpKF1fRlJyCZVYHr3CbinpZZ+6MwvOtWUuO8uo+svcATEoc1zRDcj23pAurJ2TZ/uVz1wFHH6K3NlACy0PLew==}
···
engines: {node: '>=14'}
dev: true
-
/@gql.tada/cli-utils@0.3.0:
-
resolution: {integrity: sha512-kDebLVuM5r3/bI1MmlhHr9VKHxXeq8Gxy1wHVTPva4R5ObfbhzxnHsTCvR6MUp8ziy9Pg9MESb8S1YZW8ohM3A==}
dependencies:
-
'@gql.tada/internal': 0.1.0
graphql: 16.8.1
dev: false
-
/@gql.tada/internal@0.1.0:
-
resolution: {integrity: sha512-FTvBVXVvt0xUo8hvRlwFoyeNXpUDqc+e20MzFkF8ozbsa5PoYb/gksmmnHMjUphsIq1H3Hq8o4RGstFN5LKH4w==}
dependencies:
graphql: 16.8.1
typescript: 5.3.3
dev: false
-
/@gql.tada/internal@0.1.2(graphql@16.8.1)(typescript@5.3.3):
-
resolution: {integrity: sha512-8I4Z1zxYYGK66FWdB3yIZBn3cITLPnciEgjChp3K2+Ha1e/AEBGtZv9AUlodraO/RZafDMkpFhoi+tMpluBjeg==}
peerDependencies:
graphql: ^16.8.1
-
typescript: ^5.3.3
dependencies:
'@0no-co/graphql.web': 1.0.6(graphql@16.8.1)
graphql: 16.8.1
···
'@jridgewell/set-array': 1.1.2
'@jridgewell/sourcemap-codec': 1.4.15
'@jridgewell/trace-mapping': 0.3.21
-
dev: true
/@jridgewell/resolve-uri@3.1.1:
resolution: {integrity: sha512-dSYZh7HhCDtCKm4QakX0xFpsRDqjjtZf/kjI/v3T3Nwt5r8/qz/M19F9ySyOqU94SXBmeG9ttTul+YnR4LOxFA==}
engines: {node: '>=6.0.0'}
-
dev: true
/@jridgewell/set-array@1.1.2:
resolution: {integrity: sha512-xnkseuNADM0gt2bs+BvhO0p78Mk762YnZdsuzFV018NoG1Sj1SCQvpSqa7XUaTam5vAGasABV9qXASMKnFMwMw==}
engines: {node: '>=6.0.0'}
-
dev: true
/@jridgewell/source-map@0.3.3:
resolution: {integrity: sha512-b+fsZXeLYi9fEULmfBrhxn4IrPlINf8fiNarzTof004v3lFdntdwa9PF7vFJqm3mg7s+ScJMxXaE3Acp1irZcg==}
···
/@jridgewell/sourcemap-codec@1.4.15:
resolution: {integrity: sha512-eF2rxCRulEKXHTRiDrDy6erMYWqNw4LPdQ8UQA4huuxaQsVeRPFl2oM8oDGxMFhJUWZf9McpLtJasDDZb/Bpeg==}
-
dev: true
/@jridgewell/trace-mapping@0.3.21:
resolution: {integrity: sha512-SRfKmRe1KvYnxjEMtxEr+J4HIeMX5YBg/qhRHpxEIGjhX1rshcHlnFUE9K0GazhVKWM7B+nARSkV8LuvJdJ5/g==}
dependencies:
'@jridgewell/resolve-uri': 3.1.1
'@jridgewell/sourcemap-codec': 1.4.15
-
dev: true
/@jridgewell/trace-mapping@0.3.9:
resolution: {integrity: sha512-3Belt6tdc8bPgAtbcmdtNJlirVoTmEb5e2gC94PnkwEW9jI6CAHUeoG85tjWP5WquqfavoMtMwiG4P926ZKKuQ==}
···
peerDependencies:
rollup: ^2.14.0||^3.0.0||^4.0.0
tslib: '*'
-
typescript: ^5.3.3
peerDependenciesMeta:
rollup:
optional: true
···
/@types/estree@1.0.5:
resolution: {integrity: sha512-/kYRxGDLWzHOB7q+wtSUQlFrtcdUccpfy+X+9iMBpHK8QLLhx2wIPYuS5DYtR9Wa/YlZAbIovy7qVdB1Aq6Lyw==}
-
dev: true
/@types/is-ci@3.0.0:
resolution: {integrity: sha512-Q0Op0hdWbYd1iahB+IFNQcWXFq4O0Q5MwQP7uN0souuQ4rPg1vEYcnIOfr1gY+M+6rc8FGoRaBO1mOOvL29sEQ==}
···
wonka: 6.3.4
dev: false
/@urql/core@4.2.2(graphql@16.8.1):
resolution: {integrity: sha512-TP1kheq9bnrEdnVbJqh0g0ZY/wfdpPeAzjiiDK+Tm+Pbi0O1Xdu6+fUJ/wJo5QpHZzkIyya4/AecG63e6scFqQ==}
dependencies:
-
'@0no-co/graphql.web': 1.0.4(graphql@16.8.1)
wonka: 6.3.4
transitivePeerDependencies:
- graphql
···
pretty-format: 29.7.0
dev: true
/@whatwg-node/events@0.0.3:
resolution: {integrity: sha512-IqnKIDWfXBJkvy/k6tzskWTc2NK3LcqHlb+KHGCrjOCH4jfQckRX0NAiIcC/vIqQkzLYw2r2CTSwAxcrtcD6lA==}
dev: true
···
resolution: {integrity: sha512-nc0Axzp/0FILLEVsm4fNwLCwMttvhEI263QtVPQcbpfZZ3ts0hLsZGOpE6czNlid7CJ9MlyH8reXkpsf3YUY4w==}
engines: {node: '>=0.4.0'}
hasBin: true
-
dev: true
/agent-base@7.1.0:
resolution: {integrity: sha512-o/zjMZRhJxny7OyEF+Op8X+efiELC7k7yOjMzgfzVqOzXqkBkWI79YoTdOtsuWd5BWhAGAuOY/Xa6xpiaWXiNg==}
···
resolution: {integrity: sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q==}
dev: true
/array-buffer-byte-length@1.0.0:
resolution: {integrity: sha512-LPuwb2P+NrQw3XhxGc36+XSvuBPopovXYTR9Ew++Du9Yb/bx5AzBfrIsBoj0EZUifjQU+sHL21sseZ3jerWO/A==}
dependencies:
···
engines: {node: '>= 0.4'}
dev: true
/babel-plugin-syntax-trailing-function-commas@7.0.0-beta.0:
resolution: {integrity: sha512-Xj9XuRuz3nTSbaTXWv3itLOcxyF4oPD8douBBmj7U9BBC6nEBYfyOJYQMf/8PJAFotC62UY5dFfIGEPr7WswzQ==}
dev: true
···
/balanced-match@1.0.2:
resolution: {integrity: sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==}
-
dev: true
/base64-js@1.5.1:
resolution: {integrity: sha512-AKpaYlHn8t4SVbOHCy+b5+KKgvR4vrsD8vbvrbiQJps7fKDTkjkDry6ji0rUJjC0kzbNePLwzxq8iypo41qeWA==}
···
resolution: {integrity: sha512-XnAIvQ8eM+kC6aULx6wuQiwVsnzsi9d3WxzV3FpWTGA19F621kwdbsAcFKXgKUHZWsy+mY6iL1sHTxWEFCytDA==}
dependencies:
balanced-match: 1.0.2
-
dev: true
/braces@3.0.2:
resolution: {integrity: sha512-b8um+L1RzM3WDSzvhm6gIz1yfTbBt6YTlcEKAvsmqCZZFw46z626lVj9j1yEPW33H5H+lBQpZMP1k8l+78Ha0A==}
···
engines: {node: '>=0.8'}
dev: true
/color-convert@1.9.3:
resolution: {integrity: sha512-QfAUtd+vFdAtFQcC8CCyYt1fYWxSqAiK2cSD6zDB8N3cpsEBAvRxp9zOGg6G/SHHJYAT88/az/IuDGALsNVbGg==}
dependencies:
···
resolution: {integrity: sha512-W9pAhw0ja1Edb5GVdIF1mjZw/ASI0AlShXM83UUGe2DVr5TdAPEA1OA8m/g8zWp9x6On7gqufY+FatDbC3MDQg==}
dev: true
/concat-map@0.0.1:
resolution: {integrity: sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg==}
dev: true
···
resolution: {integrity: sha512-kcZ6+W5QzcJ3P1Mt+83OUv/oHFqZHIx8DuxG6eZ5RGMERoLqp4BuGjhHLYGK+Kf5XVkQvqBSmAy/nGWN3qDgEA==}
engines: {node: '>=14'}
peerDependencies:
-
typescript: ^5.3.3
peerDependenciesMeta:
typescript:
optional: true
···
which: 2.0.2
dev: true
/csstype@3.1.3:
resolution: {integrity: sha512-M1uQkMl8rQK/szD0LNhtqxIPLpimGm8sOBwU7lLnCpSbTyY3yeU1Vc7l4KT5zT4s/yOxHH5O7tIuuLOCnLADRw==}
dev: true
···
resolution: {integrity: sha512-8YnDaaf7N3k/q5HnTJVuzSyLETjoZjVmHc4AeKAzOvKHEFQKcn64OKBfzHYtE9zGjctNM7V9I0MfnUVLpi7M5g==}
dev: true
/debounce@1.2.1:
resolution: {integrity: sha512-XRRe6Glud4rd/ZGQfiV1ruXSfbvfJedlV9Y6zOlP+2K04vBYiJEte6stfFkCP03aMnY5tsipamumUjL14fofug==}
dev: true
···
resolution: {integrity: sha512-z2S+W9X73hAUUki+N+9Za2lBlun89zigOyGrsax+KUQ6wKW4ZoWpEYBkGhQjwAjjDCkWxhY0VKEhk8wzY7F5cA==}
engines: {node: '>=0.10.0'}
dev: true
/deep-eql@4.1.3:
resolution: {integrity: sha512-WaEtAOpRA1MQ0eohqZjpGD8zdI0Ovsm8mmFhaDN8dvDZzyoUMcYDnf5Y6iu7HTXxf8JDS23qWa4a+hKCDyOPzw==}
···
/deprecation@2.3.1:
resolution: {integrity: sha512-xmHIy4F3scKVwMsQ4WnVaS8bHOx0DmVwRywosKhaILI0ywMDWPtBSku2HNxRvF7jtwDRsoEwYQSfbxj8b7RlJQ==}
dev: true
/detect-indent@6.1.0:
resolution: {integrity: sha512-reYkTUJAZb9gUuZ2RvVCNhVHdg62RHnJ7WJl8ftMi4diZ6NWlciOzQN88pUhSELEwflJht4oQDv0F0BMlwaYtA==}
···
ansi-colors: 4.1.3
dev: true
/error-ex@1.3.2:
resolution: {integrity: sha512-7dFHNmqeFSEt2ZBsCriorKnn3Z2pj+fd9kmI6QoWw4//DL+icEBfc0U7qJCisqrTsKTjw4fNFy2pW9OqStD84g==}
dependencies:
···
/estree-walker@2.0.2:
resolution: {integrity: sha512-Rfkk/Mp/DL7JVje3u18FxFujQlTNR2q6QfMSMB7AvCBx91NGj/ba3kCfza0f6dVDbw7YlRf/nDrn7pQrCCyQ/w==}
-
dev: true
/eventemitter3@5.0.1:
resolution: {integrity: sha512-GWkBvjiSZK87ELrYOSESUYeVIc9mvLLf/nXalMOS5dYrgZq9o5OVkbZAVM06CVxYsCwH9BDZFPlQTlPA1j4ahA==}
···
- graphql
dev: false
-
/gql.tada@1.4.0(graphql@16.8.1):
-
resolution: {integrity: sha512-/LZJmInJQESn0QafOrDCJRk9ASeI65caU/HmarPtcSNitNWBrH7UfNOsHtISnTTA/CS80eUYqy3M4ogasFZWPQ==}
hasBin: true
dependencies:
-
'@0no-co/graphql.web': 1.0.4(graphql@16.8.1)
-
'@gql.tada/cli-utils': 0.3.0
-
'@gql.tada/internal': 0.1.0
transitivePeerDependencies:
- graphql
dev: false
/graceful-fs@4.2.11:
···
function-bind: 1.1.2
dev: true
/header-case@2.0.4:
resolution: {integrity: sha512-H/vuk5TEEVZwrR0lp2zed9OCo1uAILMlx0JEMgC26rzyJJ3N1v6XkwHHXJQdR2doSjcGPM6OKPYoJgf0plJ11Q==}
dependencies:
···
'@types/estree': 1.0.5
dev: true
/is-regex@1.1.4:
resolution: {integrity: sha512-kvRdxDsxZjhzUX07ZnLydzS1TU/TJlTUHHY4YLL87e37oUA49DfkLqgy+VjFocowy29cKvcSiu+kIv728jTTVg==}
engines: {node: '>= 0.4'}
···
engines: {node: '>=14'}
dev: true
/locate-path@5.0.0:
resolution: {integrity: sha512-t7hw9pI+WvuwNJXwk5zVHpyhIqzg2qTlklJOf0mVxGSbe3Fp2VieZcduNYjaLDoy6p9uGpQEGWG87WpMKlNq8g==}
engines: {node: '>=8'}
···
resolution: {integrity: sha512-7fm3l3NAF9WfN6W3JOmf5drwpVqX78JtoGJ3A6W0a6ZnldM41w2fV5D490psKFTpMds8TJse/eHLFFsNHHjHgg==}
dependencies:
tslib: 2.6.2
-
dev: true
/lru-cache@10.0.1:
resolution: {integrity: sha512-IJ4uwUTi2qCccrioU6g9g/5rvvVl13bsdczUUcqbciD9iLr095yj8DQKdObriEvuNSx325N1rV1O0sJFszx75g==}
···
engines: {node: '>=12'}
dependencies:
'@jridgewell/sourcemap-codec': 1.4.15
-
dev: true
/make-error@1.3.6:
resolution: {integrity: sha512-s8UhlNe7vPKomQhC1qFelMokr/Sc3AgNbso3n74mVPA5LTZwkB9NlXf4XPamLxJE8h0gh73rM94xvwRT2CVInw==}
···
engines: {node: '>=8'}
dev: true
/meow@6.1.1:
resolution: {integrity: sha512-3YffViIt2QWgTy6Pale5QpopX/IvU3LPL03jOTqp6pGj3VjesdO/U8CuHMKpnQr4shCNCM5fd5XFFvIIl6JBHg==}
engines: {node: '>=8'}
···
brace-expansion: 2.0.1
dev: true
/minimist-options@4.1.0:
resolution: {integrity: sha512-Q4r8ghd80yhO/0j1O3B2BjweX3fiHg9cdOwjJd2J76Q135c+NDxGCqdYKQ1SKBuFfgWbAUzBfvYjPUEeNgqN1A==}
engines: {node: '>= 6'}
···
resolution: {integrity: sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==}
dev: true
/mute-stream@0.0.8:
resolution: {integrity: sha512-nnbWWOkoWyUsTjKrhgD0dcz22mdkSnpYqbEjIm2nhwhuxlSkpywJmBo8h0ZqJdkp73mb90SssHkN4rsRaBAfAA==}
dev: true
···
dependencies:
lower-case: 2.0.2
tslib: 2.6.2
-
dev: true
/node-fetch@2.6.7:
resolution: {integrity: sha512-ZjMPFEfVx5j+y2yF35Kzx5sF7kDzxuDj6ziH4FFbOp87zKDZNx8yExJIb05OGF4Nlt9IHFIMBkRl41VdvcNdbQ==}
···
dependencies:
no-case: 3.0.4
tslib: 2.6.2
-
dev: true
/path-case@3.0.4:
resolution: {integrity: sha512-qO4qCFjXqVTrcbPt/hQfhTQ+VhFsqNKOPtytgNKkKxSoEp3XPUQ8ObFuePylOIok5gjn69ry8XiULxCwot3Wfg==}
···
resolution: {integrity: sha512-Dp6zGqpTdETdR63lehJYPeIOqpiNBNtc7BpWSLrOje7UaIsE5aY92r/AunQA7rsXvet3lrJ3JnZX29UPTKXyKQ==}
dev: true
/picocolors@1.0.0:
resolution: {integrity: sha512-1fygroTLlHu66zi26VoTDv8yRgm0Fccecssto+MhsZ0D/DGW2sm8E8AjW7NU5VVTRt5GxbeZ5qBuJr+HyLYkjQ==}
dev: true
···
engines: {node: '>=16'}
peerDependencies:
rollup: ^3.29.4 || ^4
-
typescript: ^5.3.3
dependencies:
magic-string: 0.30.5
rollup: 4.9.5
···
engines: {node: '>=0.10.0'}
dev: true
/source-map-support@0.5.21:
resolution: {integrity: sha512-uBHU3L3czsIyYXKX88fdrGovxdSCoTGDRZ6SYXtSRxLZUzHg5P/66Ht6uoUlHu9EZod+inXhKo3qQgwXUT/y1w==}
dependencies:
···
engines: {node: '>= 0.4'}
dev: true
/swap-case@2.0.2:
resolution: {integrity: sha512-kc6S2YS/2yXbtkSMunBtKdah4VFETZ8Oh6ONSmSd9bRxhqTrtARUCBUiWXH3xVPpvR7tz2CSnkuXVE42EcGnMw==}
dependencies:
···
/to-fast-properties@2.0.0:
resolution: {integrity: sha512-/OaKK0xYrs3DmxRYqL/yDc+FxFUVYhDlXMhRmv3z915w2HF1tnN1omB354j8VUGO/hbRzyD6Y3sA7v7GS/ceog==}
engines: {node: '>=4'}
-
dev: true
/to-regex-range@5.0.1:
resolution: {integrity: sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ==}
···
'@swc/core': '>=1.2.50'
'@swc/wasm': '>=1.2.50'
'@types/node': '*'
-
typescript: ^5.3.3
peerDependenciesMeta:
'@swc/core':
optional: true
···
/tslib@2.6.2:
resolution: {integrity: sha512-AEYxH93jGFPn/a2iVAwW87VuUIkR1FVUKB77NwMF7nBTDkDrrT/Hpt/IrCJ0QXhW27jTBDcf5ZY7w6RiqTMw2Q==}
-
dev: true
/tty-table@4.2.1:
resolution: {integrity: sha512-xz0uKo+KakCQ+Dxj1D/tKn2FSyreSYWzdkL/BYhgN6oMW808g8QRMuh1atAV9fjTPbWBjfbkKQpI/5rEcnAc7g==}
···
resolution: {integrity: sha512-zHhCWatviizPIq9B7Vh9uvrH6x3sK8itC84HkamnBWoDFJtzBf7SWlpLCZUit72b3os45h6RWQNC9xHRDF8dRA==}
dev: true
/wcwidth@1.0.1:
resolution: {integrity: sha512-XHPEwS0q6TaxcvG85+8EYkbiCux2XtWG2mkc47Ng2A77BQu9+DqIOJldST4HgPkuea7dvKSj5VgX3P1d4rW8Tg==}
dependencies:
···
id: file:packages/graphqlsp
name: '@0no-co/graphqlsp'
peerDependencies:
-
typescript: ^5.3.3
dependencies:
-
'@gql.tada/internal': 0.1.2(graphql@16.8.1)(typescript@5.3.3)
graphql: 16.8.1
node-fetch: 2.6.7
typescript: 5.3.3
···
specifier: ^3.0.0
version: 3.2.2(graphql@16.8.1)
gql.tada:
+
specifier: 1.5.9-canary-8711af177005f46fa3e06d990b6ba28e353e7f9b
+
version: 1.5.9-canary-8711af177005f46fa3e06d990b6ba28e353e7f9b(graphql@16.8.1)(svelte@4.2.15)(typescript@5.3.3)
graphql:
specifier: ^16.8.1
version: 16.8.1
···
packages/graphqlsp:
dependencies:
'@gql.tada/internal':
+
specifier: 0.3.0-canary-8711af177005f46fa3e06d990b6ba28e353e7f9b
+
version: 0.3.0-canary-8711af177005f46fa3e06d990b6ba28e353e7f9b(graphql@16.8.1)(typescript@5.3.3)
graphql:
specifier: ^16.8.1
version: 16.8.1
···
version: link:../../../packages/graphqlsp
'@urql/core':
specifier: ^4.0.4
+
version: 4.2.2
devDependencies:
typescript:
specifier: ^5.3.3
···
dependencies:
graphql: 16.8.1
+
/@0no-co/graphqlsp@1.11.0(typescript@5.3.3):
+
resolution: {integrity: sha512-P8DRsT+pRgXXZ+8szO1ISUXLxtaL9ukKddjLqSh+oBvWVCzUDyUM4Une0Co0Y7XC017wI4pdcrR/3hWqw9uuDg==}
+
peerDependencies:
+
typescript: ^5.0.0
+
dependencies:
+
'@gql.tada/internal': 0.1.3(graphql@16.8.1)(typescript@5.3.3)
+
graphql: 16.8.1
+
node-fetch: 2.6.7
+
typescript: 5.3.3
+
transitivePeerDependencies:
+
- encoding
+
dev: false
+
/@actions/core@1.10.1:
resolution: {integrity: sha512-3lBR9EDAY+iYIpTnTIXmWcNbX3T2kCkAEQGIQx4NVQ0575nk2k3GRZDTPQG+vVtS2izSLmINlxXf0uLtnrTP+g==}
dependencies:
···
dependencies:
'@jridgewell/gen-mapping': 0.3.3
'@jridgewell/trace-mapping': 0.3.21
/@ardatan/relay-compiler@12.0.0(graphql@16.8.1):
resolution: {integrity: sha512-9anThAaj1dQr6IGmzBMcfzOQKTa5artjuPmw8NYK/fiGEMjADbSguBY2FMDykt+QhilR3wc9VA/3yVju7JHg7Q==}
···
/@babel/helper-string-parser@7.23.4:
resolution: {integrity: sha512-803gmbQdqwdf4olxrX4AJyFBV/RTr3rSmOj0rKwesmzlfhYNDEs+/iOcznzpNWlJlIlTJC2QfPFcHB6DlzdVLQ==}
engines: {node: '>=6.9.0'}
/@babel/helper-validator-identifier@7.22.20:
resolution: {integrity: sha512-Y4OZ+ytlatR8AI+8KZfKuL5urKp7qey08ha31L8b3BwewJAoJamTzyvxPR/5D+KkdJCGPq/+8TukHBlY10FX9A==}
engines: {node: '>=6.9.0'}
/@babel/helper-validator-option@7.23.5:
resolution: {integrity: sha512-85ttAOMLsr53VgXkTbkx8oA6YTfT4q7/HzXSLEYmjcSTJPMPQtvq1BD79Byep5xMUYbGRzEpDsjUf3dyp54IKw==}
···
'@babel/types': 7.23.6
dev: true
+
/@babel/parser@7.24.4:
+
resolution: {integrity: sha512-zTvEBcghmeBma9QIGunWevvBAp4/Qu9Bdq+2k0Ot4fVMD6v3dsC9WOcRSKk7tRRyBM/53yKMJko9xOatGQAwSg==}
+
engines: {node: '>=6.0.0'}
+
hasBin: true
+
dependencies:
+
'@babel/types': 7.23.6
+
dev: false
+
/@babel/plugin-proposal-class-properties@7.18.6(@babel/core@7.23.7):
resolution: {integrity: sha512-cumfXOF0+nzZrrN8Rf0t7M+tF6sZc7vhQwYQck9q1/5w2OExlD+b4v4RpMJFaV1Z7WcDRgO6FqvxqxGlwo+RHQ==}
engines: {node: '>=6.9.0'}
···
'@babel/helper-string-parser': 7.23.4
'@babel/helper-validator-identifier': 7.22.20
to-fast-properties: 2.0.0
/@changesets/apply-release-plan@6.1.4:
resolution: {integrity: sha512-FMpKF1fRlJyCZVYHr3CbinpZZ+6MwvOtWUuO8uo+svcATEoc1zRDcj23pAurJ2TZ/uVz1wFHH6K3NlACy0PLew==}
···
engines: {node: '>=14'}
dev: true
+
/@gql.tada/cli-utils@1.2.3-canary-8711af177005f46fa3e06d990b6ba28e353e7f9b(svelte@4.2.15)(typescript@5.3.3):
+
resolution: {integrity: sha512-tCKCGD4VmdSrnt7wvvzuJ1dtDf0nB6rBlYkOAvgmwDzDQgkWnwP97Xv6t6i1HAWiE9f9uzMl8y1eAr4IbySPrQ==}
+
peerDependencies:
+
typescript: ^5.0.0
dependencies:
+
'@0no-co/graphqlsp': 1.11.0(typescript@5.3.3)
+
'@gql.tada/internal': 0.3.0-canary-8711af177005f46fa3e06d990b6ba28e353e7f9b(graphql@16.8.1)(typescript@5.3.3)
+
'@vue/compiler-dom': 3.4.25
+
'@vue/language-core': 2.0.14(typescript@5.3.3)
graphql: 16.8.1
+
svelte2tsx: 0.7.7(svelte@4.2.15)(typescript@5.3.3)
+
typescript: 5.3.3
+
transitivePeerDependencies:
+
- encoding
+
- svelte
dev: false
+
/@gql.tada/internal@0.1.3(graphql@16.8.1)(typescript@5.3.3):
+
resolution: {integrity: sha512-wIvykBId7O0gaizmSl5n5AhbQsgJVLTUsFBm3RsfQ9dVfpmT+Fhy2yHX+yNgiVECg2EimXMhs4ltcE4EuZ2WOA==}
+
peerDependencies:
+
graphql: ^16.8.1
+
typescript: ^5.0.0
dependencies:
+
'@0no-co/graphql.web': 1.0.6(graphql@16.8.1)
graphql: 16.8.1
typescript: 5.3.3
dev: false
+
/@gql.tada/internal@0.3.0-canary-8711af177005f46fa3e06d990b6ba28e353e7f9b(graphql@16.8.1)(typescript@5.3.3):
+
resolution: {integrity: sha512-CPx00hSOue+XK1KUZhovuN0sZ3sCcUx99Y/iv9obL8ea2rLJ7HbehJ1uI8zwLVtfPoX/tLz+Cc34TFF1znSR7Q==}
peerDependencies:
graphql: ^16.8.1
+
typescript: ^5.0.0
dependencies:
'@0no-co/graphql.web': 1.0.6(graphql@16.8.1)
graphql: 16.8.1
···
'@jridgewell/set-array': 1.1.2
'@jridgewell/sourcemap-codec': 1.4.15
'@jridgewell/trace-mapping': 0.3.21
/@jridgewell/resolve-uri@3.1.1:
resolution: {integrity: sha512-dSYZh7HhCDtCKm4QakX0xFpsRDqjjtZf/kjI/v3T3Nwt5r8/qz/M19F9ySyOqU94SXBmeG9ttTul+YnR4LOxFA==}
engines: {node: '>=6.0.0'}
/@jridgewell/set-array@1.1.2:
resolution: {integrity: sha512-xnkseuNADM0gt2bs+BvhO0p78Mk762YnZdsuzFV018NoG1Sj1SCQvpSqa7XUaTam5vAGasABV9qXASMKnFMwMw==}
engines: {node: '>=6.0.0'}
/@jridgewell/source-map@0.3.3:
resolution: {integrity: sha512-b+fsZXeLYi9fEULmfBrhxn4IrPlINf8fiNarzTof004v3lFdntdwa9PF7vFJqm3mg7s+ScJMxXaE3Acp1irZcg==}
···
/@jridgewell/sourcemap-codec@1.4.15:
resolution: {integrity: sha512-eF2rxCRulEKXHTRiDrDy6erMYWqNw4LPdQ8UQA4huuxaQsVeRPFl2oM8oDGxMFhJUWZf9McpLtJasDDZb/Bpeg==}
/@jridgewell/trace-mapping@0.3.21:
resolution: {integrity: sha512-SRfKmRe1KvYnxjEMtxEr+J4HIeMX5YBg/qhRHpxEIGjhX1rshcHlnFUE9K0GazhVKWM7B+nARSkV8LuvJdJ5/g==}
dependencies:
'@jridgewell/resolve-uri': 3.1.1
'@jridgewell/sourcemap-codec': 1.4.15
/@jridgewell/trace-mapping@0.3.9:
resolution: {integrity: sha512-3Belt6tdc8bPgAtbcmdtNJlirVoTmEb5e2gC94PnkwEW9jI6CAHUeoG85tjWP5WquqfavoMtMwiG4P926ZKKuQ==}
···
peerDependencies:
rollup: ^2.14.0||^3.0.0||^4.0.0
tslib: '*'
+
typescript: '>=3.7.0'
peerDependenciesMeta:
rollup:
optional: true
···
/@types/estree@1.0.5:
resolution: {integrity: sha512-/kYRxGDLWzHOB7q+wtSUQlFrtcdUccpfy+X+9iMBpHK8QLLhx2wIPYuS5DYtR9Wa/YlZAbIovy7qVdB1Aq6Lyw==}
/@types/is-ci@3.0.0:
resolution: {integrity: sha512-Q0Op0hdWbYd1iahB+IFNQcWXFq4O0Q5MwQP7uN0souuQ4rPg1vEYcnIOfr1gY+M+6rc8FGoRaBO1mOOvL29sEQ==}
···
wonka: 6.3.4
dev: false
+
/@urql/core@4.2.2:
+
resolution: {integrity: sha512-TP1kheq9bnrEdnVbJqh0g0ZY/wfdpPeAzjiiDK+Tm+Pbi0O1Xdu6+fUJ/wJo5QpHZzkIyya4/AecG63e6scFqQ==}
+
dependencies:
+
'@0no-co/graphql.web': 1.0.4(graphql@16.8.1)
+
wonka: 6.3.4
+
transitivePeerDependencies:
+
- graphql
+
dev: false
+
/@urql/core@4.2.2(graphql@16.8.1):
resolution: {integrity: sha512-TP1kheq9bnrEdnVbJqh0g0ZY/wfdpPeAzjiiDK+Tm+Pbi0O1Xdu6+fUJ/wJo5QpHZzkIyya4/AecG63e6scFqQ==}
dependencies:
+
'@0no-co/graphql.web': 1.0.6(graphql@16.8.1)
wonka: 6.3.4
transitivePeerDependencies:
- graphql
···
pretty-format: 29.7.0
dev: true
+
/@volar/language-core@2.2.0-alpha.10:
+
resolution: {integrity: sha512-njVJLtpu0zMvDaEk7K5q4BRpOgbyEUljU++un9TfJoJNhxG0z/hWwpwgTRImO42EKvwIxF3XUzeMk+qatAFy7Q==}
+
dependencies:
+
'@volar/source-map': 2.2.0-alpha.10
+
dev: false
+
+
/@volar/source-map@2.2.0-alpha.10:
+
resolution: {integrity: sha512-nrdWApVkP5cksAnDEyy1JD9rKdwOJsEq1B+seWO4vNXmZNcxQQCx4DULLBvKt7AzRUAQiAuw5aQkb9RBaSqdVA==}
+
dependencies:
+
muggle-string: 0.4.1
+
dev: false
+
+
/@vue/compiler-core@3.4.25:
+
resolution: {integrity: sha512-Y2pLLopaElgWnMNolgG8w3C5nNUVev80L7hdQ5iIKPtMJvhVpG0zhnBG/g3UajJmZdvW0fktyZTotEHD1Srhbg==}
+
dependencies:
+
'@babel/parser': 7.24.4
+
'@vue/shared': 3.4.25
+
entities: 4.5.0
+
estree-walker: 2.0.2
+
source-map-js: 1.2.0
+
dev: false
+
+
/@vue/compiler-dom@3.4.25:
+
resolution: {integrity: sha512-Ugz5DusW57+HjllAugLci19NsDK+VyjGvmbB2TXaTcSlQxwL++2PETHx/+Qv6qFwNLzSt7HKepPe4DcTE3pBWg==}
+
dependencies:
+
'@vue/compiler-core': 3.4.25
+
'@vue/shared': 3.4.25
+
dev: false
+
+
/@vue/language-core@2.0.14(typescript@5.3.3):
+
resolution: {integrity: sha512-3q8mHSNcGTR7sfp2X6jZdcb4yt8AjBXAfKk0qkZIh7GAJxOnoZ10h5HToZglw4ToFvAnq+xu/Z2FFbglh9Icag==}
+
peerDependencies:
+
typescript: '*'
+
peerDependenciesMeta:
+
typescript:
+
optional: true
+
dependencies:
+
'@volar/language-core': 2.2.0-alpha.10
+
'@vue/compiler-dom': 3.4.25
+
'@vue/shared': 3.4.25
+
computeds: 0.0.1
+
minimatch: 9.0.4
+
path-browserify: 1.0.1
+
typescript: 5.3.3
+
vue-template-compiler: 2.7.16
+
dev: false
+
+
/@vue/shared@3.4.25:
+
resolution: {integrity: sha512-k0yappJ77g2+KNrIaF0FFnzwLvUBLUYr8VOwz+/6vLsmItFp51AcxLL7Ey3iPd7BIRyWPOcqUjMnm7OkahXllA==}
+
dev: false
+
/@whatwg-node/events@0.0.3:
resolution: {integrity: sha512-IqnKIDWfXBJkvy/k6tzskWTc2NK3LcqHlb+KHGCrjOCH4jfQckRX0NAiIcC/vIqQkzLYw2r2CTSwAxcrtcD6lA==}
dev: true
···
resolution: {integrity: sha512-nc0Axzp/0FILLEVsm4fNwLCwMttvhEI263QtVPQcbpfZZ3ts0hLsZGOpE6czNlid7CJ9MlyH8reXkpsf3YUY4w==}
engines: {node: '>=0.4.0'}
hasBin: true
/agent-base@7.1.0:
resolution: {integrity: sha512-o/zjMZRhJxny7OyEF+Op8X+efiELC7k7yOjMzgfzVqOzXqkBkWI79YoTdOtsuWd5BWhAGAuOY/Xa6xpiaWXiNg==}
···
resolution: {integrity: sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q==}
dev: true
+
/aria-query@5.3.0:
+
resolution: {integrity: sha512-b0P0sZPKtyu8HkeRAfCq0IfURZK+SuwMjY1UXGBU27wpAiTwQAIlq56IbIO+ytk/JjS1fMR14ee5WBBfKi5J6A==}
+
dependencies:
+
dequal: 2.0.3
+
dev: false
+
/array-buffer-byte-length@1.0.0:
resolution: {integrity: sha512-LPuwb2P+NrQw3XhxGc36+XSvuBPopovXYTR9Ew++Du9Yb/bx5AzBfrIsBoj0EZUifjQU+sHL21sseZ3jerWO/A==}
dependencies:
···
engines: {node: '>= 0.4'}
dev: true
+
/axobject-query@4.0.0:
+
resolution: {integrity: sha512-+60uv1hiVFhHZeO+Lz0RYzsVHy5Wr1ayX0mwda9KPDVLNJgZ1T9Ny7VmFbLDzxsH0D87I86vgj3gFrjTJUYznw==}
+
dependencies:
+
dequal: 2.0.3
+
dev: false
+
/babel-plugin-syntax-trailing-function-commas@7.0.0-beta.0:
resolution: {integrity: sha512-Xj9XuRuz3nTSbaTXWv3itLOcxyF4oPD8douBBmj7U9BBC6nEBYfyOJYQMf/8PJAFotC62UY5dFfIGEPr7WswzQ==}
dev: true
···
/balanced-match@1.0.2:
resolution: {integrity: sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==}
/base64-js@1.5.1:
resolution: {integrity: sha512-AKpaYlHn8t4SVbOHCy+b5+KKgvR4vrsD8vbvrbiQJps7fKDTkjkDry6ji0rUJjC0kzbNePLwzxq8iypo41qeWA==}
···
resolution: {integrity: sha512-XnAIvQ8eM+kC6aULx6wuQiwVsnzsi9d3WxzV3FpWTGA19F621kwdbsAcFKXgKUHZWsy+mY6iL1sHTxWEFCytDA==}
dependencies:
balanced-match: 1.0.2
/braces@3.0.2:
resolution: {integrity: sha512-b8um+L1RzM3WDSzvhm6gIz1yfTbBt6YTlcEKAvsmqCZZFw46z626lVj9j1yEPW33H5H+lBQpZMP1k8l+78Ha0A==}
···
engines: {node: '>=0.8'}
dev: true
+
/code-red@1.0.4:
+
resolution: {integrity: sha512-7qJWqItLA8/VPVlKJlFXU+NBlo/qyfs39aJcuMT/2ere32ZqvF5OSxgdM5xOfJJ7O429gg2HM47y8v9P+9wrNw==}
+
dependencies:
+
'@jridgewell/sourcemap-codec': 1.4.15
+
'@types/estree': 1.0.5
+
acorn: 8.11.2
+
estree-walker: 3.0.3
+
periscopic: 3.1.0
+
dev: false
+
/color-convert@1.9.3:
resolution: {integrity: sha512-QfAUtd+vFdAtFQcC8CCyYt1fYWxSqAiK2cSD6zDB8N3cpsEBAvRxp9zOGg6G/SHHJYAT88/az/IuDGALsNVbGg==}
dependencies:
···
resolution: {integrity: sha512-W9pAhw0ja1Edb5GVdIF1mjZw/ASI0AlShXM83UUGe2DVr5TdAPEA1OA8m/g8zWp9x6On7gqufY+FatDbC3MDQg==}
dev: true
+
/computeds@0.0.1:
+
resolution: {integrity: sha512-7CEBgcMjVmitjYo5q8JTJVra6X5mQ20uTThdK+0kR7UEaDrAWEQcRiBtWJzga4eRpP6afNwwLsX2SET2JhVB1Q==}
+
dev: false
+
/concat-map@0.0.1:
resolution: {integrity: sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg==}
dev: true
···
resolution: {integrity: sha512-kcZ6+W5QzcJ3P1Mt+83OUv/oHFqZHIx8DuxG6eZ5RGMERoLqp4BuGjhHLYGK+Kf5XVkQvqBSmAy/nGWN3qDgEA==}
engines: {node: '>=14'}
peerDependencies:
+
typescript: '>=4.9.5'
peerDependenciesMeta:
typescript:
optional: true
···
which: 2.0.2
dev: true
+
/css-tree@2.3.1:
+
resolution: {integrity: sha512-6Fv1DV/TYw//QF5IzQdqsNDjx/wc8TrMBZsqjL9eW01tWb7R7k/mq+/VXfJCl7SoD5emsJop9cOByJZfs8hYIw==}
+
engines: {node: ^10 || ^12.20.0 || ^14.13.0 || >=15.0.0}
+
dependencies:
+
mdn-data: 2.0.30
+
source-map-js: 1.2.0
+
dev: false
+
/csstype@3.1.3:
resolution: {integrity: sha512-M1uQkMl8rQK/szD0LNhtqxIPLpimGm8sOBwU7lLnCpSbTyY3yeU1Vc7l4KT5zT4s/yOxHH5O7tIuuLOCnLADRw==}
dev: true
···
resolution: {integrity: sha512-8YnDaaf7N3k/q5HnTJVuzSyLETjoZjVmHc4AeKAzOvKHEFQKcn64OKBfzHYtE9zGjctNM7V9I0MfnUVLpi7M5g==}
dev: true
+
/de-indent@1.0.2:
+
resolution: {integrity: sha512-e/1zu3xH5MQryN2zdVaF0OrdNLUbvWxzMbi+iNA6Bky7l1RoP8a2fIbRocyHclXt/arDrrR6lL3TqFD9pMQTsg==}
+
dev: false
+
/debounce@1.2.1:
resolution: {integrity: sha512-XRRe6Glud4rd/ZGQfiV1ruXSfbvfJedlV9Y6zOlP+2K04vBYiJEte6stfFkCP03aMnY5tsipamumUjL14fofug==}
dev: true
···
resolution: {integrity: sha512-z2S+W9X73hAUUki+N+9Za2lBlun89zigOyGrsax+KUQ6wKW4ZoWpEYBkGhQjwAjjDCkWxhY0VKEhk8wzY7F5cA==}
engines: {node: '>=0.10.0'}
dev: true
+
+
/dedent-js@1.0.1:
+
resolution: {integrity: sha512-OUepMozQULMLUmhxS95Vudo0jb0UchLimi3+pQ2plj61Fcy8axbP9hbiD4Sz6DPqn6XG3kfmziVfQ1rSys5AJQ==}
+
dev: false
/deep-eql@4.1.3:
resolution: {integrity: sha512-WaEtAOpRA1MQ0eohqZjpGD8zdI0Ovsm8mmFhaDN8dvDZzyoUMcYDnf5Y6iu7HTXxf8JDS23qWa4a+hKCDyOPzw==}
···
/deprecation@2.3.1:
resolution: {integrity: sha512-xmHIy4F3scKVwMsQ4WnVaS8bHOx0DmVwRywosKhaILI0ywMDWPtBSku2HNxRvF7jtwDRsoEwYQSfbxj8b7RlJQ==}
dev: true
+
+
/dequal@2.0.3:
+
resolution: {integrity: sha512-0je+qPKHEMohvfRTCEo3CrPG6cAzAYgmzKyxRiYSSDkS6eGJdyVJm7WaYA5ECaAD9wLB2T4EEeymA5aFVcYXCA==}
+
engines: {node: '>=6'}
+
dev: false
/detect-indent@6.1.0:
resolution: {integrity: sha512-reYkTUJAZb9gUuZ2RvVCNhVHdg62RHnJ7WJl8ftMi4diZ6NWlciOzQN88pUhSELEwflJht4oQDv0F0BMlwaYtA==}
···
ansi-colors: 4.1.3
dev: true
+
/entities@4.5.0:
+
resolution: {integrity: sha512-V0hjH4dGPh9Ao5p0MoRY6BVqtwCjhz6vI5LT8AJ55H+4g9/4vbHx1I54fS0XuclLhDHArPQCiMjDxjaL8fPxhw==}
+
engines: {node: '>=0.12'}
+
dev: false
+
/error-ex@1.3.2:
resolution: {integrity: sha512-7dFHNmqeFSEt2ZBsCriorKnn3Z2pj+fd9kmI6QoWw4//DL+icEBfc0U7qJCisqrTsKTjw4fNFy2pW9OqStD84g==}
dependencies:
···
/estree-walker@2.0.2:
resolution: {integrity: sha512-Rfkk/Mp/DL7JVje3u18FxFujQlTNR2q6QfMSMB7AvCBx91NGj/ba3kCfza0f6dVDbw7YlRf/nDrn7pQrCCyQ/w==}
+
+
/estree-walker@3.0.3:
+
resolution: {integrity: sha512-7RUKfXgSMMkzt6ZuXmqapOurLGPPfgj6l9uRZ7lRGolvk0y2yocc35LdcxKC5PQZdn2DMqioAQ2NoWcrTKmm6g==}
+
dependencies:
+
'@types/estree': 1.0.5
+
dev: false
/eventemitter3@5.0.1:
resolution: {integrity: sha512-GWkBvjiSZK87ELrYOSESUYeVIc9mvLLf/nXalMOS5dYrgZq9o5OVkbZAVM06CVxYsCwH9BDZFPlQTlPA1j4ahA==}
···
- graphql
dev: false
+
/gql.tada@1.5.9-canary-8711af177005f46fa3e06d990b6ba28e353e7f9b(graphql@16.8.1)(svelte@4.2.15)(typescript@5.3.3):
+
resolution: {integrity: sha512-3tglGLiGY1zyMyZAow2kpy8GBi35xGAGiEDiPAIPXOUyU35B0HpY0lmMZhf5jEs0fv2FTMgWvFXO6Z3378B6FA==}
hasBin: true
+
peerDependencies:
+
typescript: ^5.0.0
dependencies:
+
'@0no-co/graphql.web': 1.0.6(graphql@16.8.1)
+
'@gql.tada/cli-utils': 1.2.3-canary-8711af177005f46fa3e06d990b6ba28e353e7f9b(svelte@4.2.15)(typescript@5.3.3)
+
'@gql.tada/internal': 0.3.0-canary-8711af177005f46fa3e06d990b6ba28e353e7f9b(graphql@16.8.1)(typescript@5.3.3)
+
typescript: 5.3.3
transitivePeerDependencies:
+
- encoding
- graphql
+
- svelte
dev: false
/graceful-fs@4.2.11:
···
function-bind: 1.1.2
dev: true
+
/he@1.2.0:
+
resolution: {integrity: sha512-F/1DnUGPopORZi0ni+CvrCgHQ5FyEAHRLSApuYWMmrbSwoN2Mn/7k+Gl38gJnR7yyDZk6WLXwiGod1JOWNDKGw==}
+
hasBin: true
+
dev: false
+
/header-case@2.0.4:
resolution: {integrity: sha512-H/vuk5TEEVZwrR0lp2zed9OCo1uAILMlx0JEMgC26rzyJJ3N1v6XkwHHXJQdR2doSjcGPM6OKPYoJgf0plJ11Q==}
dependencies:
···
'@types/estree': 1.0.5
dev: true
+
/is-reference@3.0.2:
+
resolution: {integrity: sha512-v3rht/LgVcsdZa3O2Nqs+NMowLOxeOm7Ay9+/ARQ2F+qEoANRcqrjAZKGN0v8ymUetZGgkp26LTnGT7H0Qo9Pg==}
+
dependencies:
+
'@types/estree': 1.0.5
+
dev: false
+
/is-regex@1.1.4:
resolution: {integrity: sha512-kvRdxDsxZjhzUX07ZnLydzS1TU/TJlTUHHY4YLL87e37oUA49DfkLqgy+VjFocowy29cKvcSiu+kIv728jTTVg==}
engines: {node: '>= 0.4'}
···
engines: {node: '>=14'}
dev: true
+
/locate-character@3.0.0:
+
resolution: {integrity: sha512-SW13ws7BjaeJ6p7Q6CO2nchbYEc3X3J6WrmTTDto7yMPqVSZTUyY5Tjbid+Ab8gLnATtygYtiDIJGQRRn2ZOiA==}
+
dev: false
+
/locate-path@5.0.0:
resolution: {integrity: sha512-t7hw9pI+WvuwNJXwk5zVHpyhIqzg2qTlklJOf0mVxGSbe3Fp2VieZcduNYjaLDoy6p9uGpQEGWG87WpMKlNq8g==}
engines: {node: '>=8'}
···
resolution: {integrity: sha512-7fm3l3NAF9WfN6W3JOmf5drwpVqX78JtoGJ3A6W0a6ZnldM41w2fV5D490psKFTpMds8TJse/eHLFFsNHHjHgg==}
dependencies:
tslib: 2.6.2
/lru-cache@10.0.1:
resolution: {integrity: sha512-IJ4uwUTi2qCccrioU6g9g/5rvvVl13bsdczUUcqbciD9iLr095yj8DQKdObriEvuNSx325N1rV1O0sJFszx75g==}
···
engines: {node: '>=12'}
dependencies:
'@jridgewell/sourcemap-codec': 1.4.15
/make-error@1.3.6:
resolution: {integrity: sha512-s8UhlNe7vPKomQhC1qFelMokr/Sc3AgNbso3n74mVPA5LTZwkB9NlXf4XPamLxJE8h0gh73rM94xvwRT2CVInw==}
···
engines: {node: '>=8'}
dev: true
+
/mdn-data@2.0.30:
+
resolution: {integrity: sha512-GaqWWShW4kv/G9IEucWScBx9G1/vsFZZJUO+tD26M8J8z3Kw5RDQjaoZe03YAClgeS/SWPOcb4nkFBTEi5DUEA==}
+
dev: false
+
/meow@6.1.1:
resolution: {integrity: sha512-3YffViIt2QWgTy6Pale5QpopX/IvU3LPL03jOTqp6pGj3VjesdO/U8CuHMKpnQr4shCNCM5fd5XFFvIIl6JBHg==}
engines: {node: '>=8'}
···
brace-expansion: 2.0.1
dev: true
+
/minimatch@9.0.4:
+
resolution: {integrity: sha512-KqWh+VchfxcMNRAJjj2tnsSJdNbHsVgnkBhTNrW7AjVo6OvLtxw8zfT9oLw1JSohlFzJ8jCoTgaoXvJ+kHt6fw==}
+
engines: {node: '>=16 || 14 >=14.17'}
+
dependencies:
+
brace-expansion: 2.0.1
+
dev: false
+
/minimist-options@4.1.0:
resolution: {integrity: sha512-Q4r8ghd80yhO/0j1O3B2BjweX3fiHg9cdOwjJd2J76Q135c+NDxGCqdYKQ1SKBuFfgWbAUzBfvYjPUEeNgqN1A==}
engines: {node: '>= 6'}
···
resolution: {integrity: sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==}
dev: true
+
/muggle-string@0.4.1:
+
resolution: {integrity: sha512-VNTrAak/KhO2i8dqqnqnAHOa3cYBwXEZe9h+D5h/1ZqFSTEFHdM65lR7RoIqq3tBBYavsOXV84NoHXZ0AkPyqQ==}
+
dev: false
+
/mute-stream@0.0.8:
resolution: {integrity: sha512-nnbWWOkoWyUsTjKrhgD0dcz22mdkSnpYqbEjIm2nhwhuxlSkpywJmBo8h0ZqJdkp73mb90SssHkN4rsRaBAfAA==}
dev: true
···
dependencies:
lower-case: 2.0.2
tslib: 2.6.2
/node-fetch@2.6.7:
resolution: {integrity: sha512-ZjMPFEfVx5j+y2yF35Kzx5sF7kDzxuDj6ziH4FFbOp87zKDZNx8yExJIb05OGF4Nlt9IHFIMBkRl41VdvcNdbQ==}
···
dependencies:
no-case: 3.0.4
tslib: 2.6.2
+
+
/path-browserify@1.0.1:
+
resolution: {integrity: sha512-b7uo2UCUOYZcnF/3ID0lulOJi/bafxa1xPe7ZPsammBSpjSWQkjNxlt635YGS2MiR9GjvuXCtz2emr3jbsz98g==}
+
dev: false
/path-case@3.0.4:
resolution: {integrity: sha512-qO4qCFjXqVTrcbPt/hQfhTQ+VhFsqNKOPtytgNKkKxSoEp3XPUQ8ObFuePylOIok5gjn69ry8XiULxCwot3Wfg==}
···
resolution: {integrity: sha512-Dp6zGqpTdETdR63lehJYPeIOqpiNBNtc7BpWSLrOje7UaIsE5aY92r/AunQA7rsXvet3lrJ3JnZX29UPTKXyKQ==}
dev: true
+
/periscopic@3.1.0:
+
resolution: {integrity: sha512-vKiQ8RRtkl9P+r/+oefh25C3fhybptkHKCZSPlcXiJux2tJF55GnEj3BVn4A5gKfq9NWWXXrxkHBwVPUfH0opw==}
+
dependencies:
+
'@types/estree': 1.0.5
+
estree-walker: 3.0.3
+
is-reference: 3.0.2
+
dev: false
+
/picocolors@1.0.0:
resolution: {integrity: sha512-1fygroTLlHu66zi26VoTDv8yRgm0Fccecssto+MhsZ0D/DGW2sm8E8AjW7NU5VVTRt5GxbeZ5qBuJr+HyLYkjQ==}
dev: true
···
engines: {node: '>=16'}
peerDependencies:
rollup: ^3.29.4 || ^4
+
typescript: ^4.5 || ^5.0
dependencies:
magic-string: 0.30.5
rollup: 4.9.5
···
engines: {node: '>=0.10.0'}
dev: true
+
/source-map-js@1.2.0:
+
resolution: {integrity: sha512-itJW8lvSA0TXEphiRoawsCksnlf8SyvmFzIhltqAHluXd88pkCd+cXJVHTDwdCr0IzwptSm035IHQktUu1QUMg==}
+
engines: {node: '>=0.10.0'}
+
dev: false
+
/source-map-support@0.5.21:
resolution: {integrity: sha512-uBHU3L3czsIyYXKX88fdrGovxdSCoTGDRZ6SYXtSRxLZUzHg5P/66Ht6uoUlHu9EZod+inXhKo3qQgwXUT/y1w==}
dependencies:
···
engines: {node: '>= 0.4'}
dev: true
+
/svelte2tsx@0.7.7(svelte@4.2.15)(typescript@5.3.3):
+
resolution: {integrity: sha512-HAIxtk5TUHXvCRKApKfxoh1BGT85S/17lS3DvbfxRKFd+Ghr5YScqBvd+sU+p7vJFw48LNkzdFk+ooNVk3e4kA==}
+
peerDependencies:
+
svelte: ^3.55 || ^4.0.0-next.0 || ^4.0 || ^5.0.0-next.0
+
typescript: ^4.9.4 || ^5.0.0
+
dependencies:
+
dedent-js: 1.0.1
+
pascal-case: 3.1.2
+
svelte: 4.2.15
+
typescript: 5.3.3
+
dev: false
+
+
/svelte@4.2.15:
+
resolution: {integrity: sha512-j9KJSccHgLeRERPlhMKrCXpk2TqL2m5Z+k+OBTQhZOhIdCCd3WfqV+ylPWeipEwq17P/ekiSFWwrVQv93i3bsg==}
+
engines: {node: '>=16'}
+
dependencies:
+
'@ampproject/remapping': 2.2.1
+
'@jridgewell/sourcemap-codec': 1.4.15
+
'@jridgewell/trace-mapping': 0.3.21
+
'@types/estree': 1.0.5
+
acorn: 8.11.2
+
aria-query: 5.3.0
+
axobject-query: 4.0.0
+
code-red: 1.0.4
+
css-tree: 2.3.1
+
estree-walker: 3.0.3
+
is-reference: 3.0.2
+
locate-character: 3.0.0
+
magic-string: 0.30.5
+
periscopic: 3.1.0
+
dev: false
+
/swap-case@2.0.2:
resolution: {integrity: sha512-kc6S2YS/2yXbtkSMunBtKdah4VFETZ8Oh6ONSmSd9bRxhqTrtARUCBUiWXH3xVPpvR7tz2CSnkuXVE42EcGnMw==}
dependencies:
···
/to-fast-properties@2.0.0:
resolution: {integrity: sha512-/OaKK0xYrs3DmxRYqL/yDc+FxFUVYhDlXMhRmv3z915w2HF1tnN1omB354j8VUGO/hbRzyD6Y3sA7v7GS/ceog==}
engines: {node: '>=4'}
/to-regex-range@5.0.1:
resolution: {integrity: sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ==}
···
'@swc/core': '>=1.2.50'
'@swc/wasm': '>=1.2.50'
'@types/node': '*'
+
typescript: '>=2.7'
peerDependenciesMeta:
'@swc/core':
optional: true
···
/tslib@2.6.2:
resolution: {integrity: sha512-AEYxH93jGFPn/a2iVAwW87VuUIkR1FVUKB77NwMF7nBTDkDrrT/Hpt/IrCJ0QXhW27jTBDcf5ZY7w6RiqTMw2Q==}
/tty-table@4.2.1:
resolution: {integrity: sha512-xz0uKo+KakCQ+Dxj1D/tKn2FSyreSYWzdkL/BYhgN6oMW808g8QRMuh1atAV9fjTPbWBjfbkKQpI/5rEcnAc7g==}
···
resolution: {integrity: sha512-zHhCWatviizPIq9B7Vh9uvrH6x3sK8itC84HkamnBWoDFJtzBf7SWlpLCZUit72b3os45h6RWQNC9xHRDF8dRA==}
dev: true
+
/vue-template-compiler@2.7.16:
+
resolution: {integrity: sha512-AYbUWAJHLGGQM7+cNTELw+KsOG9nl2CnSv467WobS5Cv9uk3wFcnr1Etsz2sEIHEZvw1U+o9mRlEO6QbZvUPGQ==}
+
dependencies:
+
de-indent: 1.0.2
+
he: 1.2.0
+
dev: false
+
/wcwidth@1.0.1:
resolution: {integrity: sha512-XHPEwS0q6TaxcvG85+8EYkbiCux2XtWG2mkc47Ng2A77BQu9+DqIOJldST4HgPkuea7dvKSj5VgX3P1d4rW8Tg==}
dependencies:
···
id: file:packages/graphqlsp
name: '@0no-co/graphqlsp'
peerDependencies:
+
typescript: ^5.0.0
dependencies:
+
'@gql.tada/internal': 0.3.0-canary-8711af177005f46fa3e06d990b6ba28e353e7f9b(graphql@16.8.1)(typescript@5.3.3)
graphql: 16.8.1
node-fetch: 2.6.7
typescript: 5.3.3