test run mesh subs
This commit is contained in:
parent
91ce34e260
commit
4f6fba7e71
35
.meshrc.yml
35
.meshrc.yml
@ -8,21 +8,20 @@ sources:
|
|||||||
endpoint: https://directus.andert.me/graphql
|
endpoint: https://directus.andert.me/graphql
|
||||||
source: ./src/schemas/directus.graphql
|
source: ./src/schemas/directus.graphql
|
||||||
operationHeaders:
|
operationHeaders:
|
||||||
Authorization: Bearer {env.DIRECTUS_API}
|
Authorization: "Bearer {env.DIRECTUS_API}"
|
||||||
additionalResolvers:
|
connectionParams:
|
||||||
- ./src/resolvers/subs_directus.js
|
access_token: "Bv5RknRvv5AZouxcYdBJgVOe3ZC493Y3"
|
||||||
|
# - name: Cloudron
|
||||||
# - name: Cloudron
|
# handler:
|
||||||
# handler:
|
# openapi:
|
||||||
# openapi:
|
# endpoint: https://my.andert.me/api/v1
|
||||||
# endpoint: https://my.andert.me/api/v1
|
# source: ./src/schemas/cloudron.json
|
||||||
# source: ./src/schemas/cloudron.json
|
# operationHeaders:
|
||||||
# operationHeaders:
|
# Authorization: Bearer {env.CLOUDRON_API}
|
||||||
# Authorization: Bearer {env.CLOUDRON_API}
|
# - name: Gitea
|
||||||
# - name: Gitea
|
# handler:
|
||||||
# handler:
|
# openapi:
|
||||||
# openapi:
|
# endpoint: https://git.andert.me/api/v1
|
||||||
# endpoint: https://git.andert.me/api/v1
|
# source: ./src/schemas/gitea.yml
|
||||||
# source: ./src/schemas/gitea.yml
|
# operationHeaders:
|
||||||
# operationHeaders:
|
# Authorization: Bearer {env.GITEA_API}
|
||||||
# Authorization: Bearer {env.GITEA_API}
|
|
||||||
|
@ -33,8 +33,10 @@
|
|||||||
"fs": "0.0.1-security",
|
"fs": "0.0.1-security",
|
||||||
"graphql": "^16.7.1",
|
"graphql": "^16.7.1",
|
||||||
"graphql-request": "^6.1.0",
|
"graphql-request": "^6.1.0",
|
||||||
|
"graphql-sse": "^2.2.3",
|
||||||
"graphql-subscriptions": "^2.0.0",
|
"graphql-subscriptions": "^2.0.0",
|
||||||
"graphql-ws": "^5.14.0",
|
"graphql-ws": "^5.14.0",
|
||||||
|
"isomorphic-ws": "^5.0.0",
|
||||||
"next": "13.4.9",
|
"next": "13.4.9",
|
||||||
"node-fetch": "^3.3.2",
|
"node-fetch": "^3.3.2",
|
||||||
"path": "^0.12.7",
|
"path": "^0.12.7",
|
||||||
|
15
pnpm-lock.yaml
generated
15
pnpm-lock.yaml
generated
@ -58,12 +58,18 @@ dependencies:
|
|||||||
graphql-request:
|
graphql-request:
|
||||||
specifier: ^6.1.0
|
specifier: ^6.1.0
|
||||||
version: 6.1.0(graphql@16.7.1)
|
version: 6.1.0(graphql@16.7.1)
|
||||||
|
graphql-sse:
|
||||||
|
specifier: ^2.2.3
|
||||||
|
version: 2.2.3(graphql@16.7.1)
|
||||||
graphql-subscriptions:
|
graphql-subscriptions:
|
||||||
specifier: ^2.0.0
|
specifier: ^2.0.0
|
||||||
version: 2.0.0(graphql@16.7.1)
|
version: 2.0.0(graphql@16.7.1)
|
||||||
graphql-ws:
|
graphql-ws:
|
||||||
specifier: ^5.14.0
|
specifier: ^5.14.0
|
||||||
version: 5.14.0(graphql@16.7.1)
|
version: 5.14.0(graphql@16.7.1)
|
||||||
|
isomorphic-ws:
|
||||||
|
specifier: ^5.0.0
|
||||||
|
version: 5.0.0(ws@8.13.0)
|
||||||
next:
|
next:
|
||||||
specifier: 13.4.9
|
specifier: 13.4.9
|
||||||
version: 13.4.9(@babel/core@7.22.8)(react-dom@18.2.0)(react@18.2.0)
|
version: 13.4.9(@babel/core@7.22.8)(react-dom@18.2.0)(react@18.2.0)
|
||||||
@ -5808,6 +5814,15 @@ packages:
|
|||||||
tslib: 2.6.0
|
tslib: 2.6.0
|
||||||
dev: false
|
dev: false
|
||||||
|
|
||||||
|
/graphql-sse@2.2.3(graphql@16.7.1):
|
||||||
|
resolution: {integrity: sha512-pcSbaPa2IAFm/oT5e7tu4kE0FaaZ32mWMQZa2hh+08bbjhmTlHInCGousYEYohWMUSKOrOFpFifpdWHms51JbA==}
|
||||||
|
engines: {node: '>=12'}
|
||||||
|
peerDependencies:
|
||||||
|
graphql: '>=0.11 <=16'
|
||||||
|
dependencies:
|
||||||
|
graphql: 16.7.1
|
||||||
|
dev: false
|
||||||
|
|
||||||
/graphql-subscriptions@2.0.0(graphql@16.7.1):
|
/graphql-subscriptions@2.0.0(graphql@16.7.1):
|
||||||
resolution: {integrity: sha512-s6k2b8mmt9gF9pEfkxsaO1lTxaySfKoEJzEfmwguBbQ//Oq23hIXCfR1hm4kdh5hnR20RdwB+s3BCb+0duHSZA==}
|
resolution: {integrity: sha512-s6k2b8mmt9gF9pEfkxsaO1lTxaySfKoEJzEfmwguBbQ//Oq23hIXCfR1hm4kdh5hnR20RdwB+s3BCb+0duHSZA==}
|
||||||
peerDependencies:
|
peerDependencies:
|
||||||
|
@ -1,108 +0,0 @@
|
|||||||
const { createClient } = require('graphql-ws');
|
|
||||||
const WebSocket = require('ws');
|
|
||||||
const { PubSub } = require('graphql-subscriptions');
|
|
||||||
const { parse } = require('graphql');
|
|
||||||
|
|
||||||
const pubsub = new PubSub();
|
|
||||||
|
|
||||||
const schema = require('raw-loader!../schemas/directus.graphql').default;
|
|
||||||
|
|
||||||
// Parse the schema
|
|
||||||
const document = parse(schema);
|
|
||||||
|
|
||||||
// Function to find a type definition by name
|
|
||||||
const findTypeDefinition = (typeName) => {
|
|
||||||
return document.definitions.find(
|
|
||||||
def => def.kind === 'ObjectTypeDefinition' && def.name.value === typeName
|
|
||||||
);
|
|
||||||
};
|
|
||||||
|
|
||||||
// Extract the fields excluding the ones ending with '_func', of object type, and specific fields
|
|
||||||
const extractFields = (type, depth = 0) => {
|
|
||||||
return type.fields
|
|
||||||
.filter(field => !field.name.value.endsWith('_func') && !['avatar', 'role'].includes(field.name.value))
|
|
||||||
.map(field => {
|
|
||||||
if (field.type.kind === 'NamedType' && depth < 1) {
|
|
||||||
// If the field is of object type and we are not too deep, recursively extract its fields
|
|
||||||
const nestedType = findTypeDefinition(field.type.name.value);
|
|
||||||
if (nestedType) {
|
|
||||||
return `${field.name.value} {\n${extractFields(nestedType, depth + 1)}\n}`;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return field.name.value;
|
|
||||||
})
|
|
||||||
.join('\n');
|
|
||||||
};
|
|
||||||
|
|
||||||
const client = createClient({
|
|
||||||
url: 'wss://directus.andert.me/graphql',
|
|
||||||
keepAlive: 30000,
|
|
||||||
webSocketImpl: WebSocket,
|
|
||||||
connectionParams: async () => {
|
|
||||||
return { access_token: process.env.DIRECTUS_API };
|
|
||||||
},
|
|
||||||
});
|
|
||||||
|
|
||||||
const generateSubscriptionQuery = (typeName) => {
|
|
||||||
const typeDefinition = findTypeDefinition(typeName);
|
|
||||||
const fields = extractFields(typeDefinition);
|
|
||||||
|
|
||||||
return `
|
|
||||||
subscription {
|
|
||||||
${typeName}_mutated {
|
|
||||||
key
|
|
||||||
event
|
|
||||||
data {
|
|
||||||
${fields}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
`;
|
|
||||||
};
|
|
||||||
|
|
||||||
const handleSubscription = (typeName) => {
|
|
||||||
const MUTATED = `${typeName.toUpperCase()}_MUTATED`;
|
|
||||||
|
|
||||||
const type = findTypeDefinition(typeName);
|
|
||||||
const fields = extractFields(type);
|
|
||||||
|
|
||||||
const query = generateSubscriptionQuery(typeName);
|
|
||||||
|
|
||||||
client.subscribe(
|
|
||||||
{
|
|
||||||
query: query,
|
|
||||||
},
|
|
||||||
{
|
|
||||||
next: data => {
|
|
||||||
if (data && data.data && data.data[`${typeName}_mutated`]) {
|
|
||||||
pubsub.publish(MUTATED, { [`${typeName}_mutated`]: data.data[`${typeName}_mutated`] });
|
|
||||||
}
|
|
||||||
},
|
|
||||||
error: error => console.error('error:', error),
|
|
||||||
}
|
|
||||||
);
|
|
||||||
|
|
||||||
return {
|
|
||||||
[`${typeName}_mutated`]: {
|
|
||||||
subscribe: () => pubsub.asyncIterator([MUTATED]),
|
|
||||||
resolve: payload => payload[`${typeName}_mutated`],
|
|
||||||
},
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
// Find the Subscription type definition
|
|
||||||
const subscriptionType = findTypeDefinition('Subscription');
|
|
||||||
|
|
||||||
// Extract the subscription type names, excluding the ones starting with 'directus_'
|
|
||||||
const subscriptionTypeNames = subscriptionType.fields
|
|
||||||
.map(field => field.name.value.replace('_mutated', ''))
|
|
||||||
.filter(name => !name.startsWith('directus_'));
|
|
||||||
|
|
||||||
// Generate subscriptions for each type
|
|
||||||
const subscriptions = subscriptionTypeNames.reduce((acc, typeName) => {
|
|
||||||
return { ...acc, ...handleSubscription(typeName) };
|
|
||||||
}, {});
|
|
||||||
|
|
||||||
module.exports = {
|
|
||||||
Subscription: subscriptions,
|
|
||||||
};
|
|
Reference in New Issue
Block a user