Είμαι αρκετά εθισμένος στη σειρά Last Of Us.Συγγνώμη για την κάλυψη.
Οι MCP είναι παντού και για καλό λόγο.Είναι το επόμενο βήμα στην εξέλιξη των εφαρμογών.
Να είστε σε θέση να χρησιμοποιήσετε τα πάντα από μια ενιαία συνομιλία χωρίς πρόσβαση σε οποιαδήποτε εφαρμογή.Ταχυδρόμοςνα προγραμματίσετε όλες τις κοινωνικές σας δημοσιεύσεις από τη συνομιλία! Έτσι, άρχισα να σκάβω στον κώδικα Postiz και να προσθέσω σε αυτό!
Το αποθετήριο MCP είναι λίγο περίεργο
Κάθε MCP έχει μια μεταφορά, η οποία είναι η μέθοδος που χρησιμοποιούν οι LLMs για να μιλήσουν στο σύστημά μας.
There are two primary methods at the momentStdio, η οποία είναι βασικά μια γραμμή εντολών, και SSE.
Δεν καταλαβαίνω πραγματικά γιατί επέλεξαν το SSE - είναι βασικά ένα μακρύ αίτημα που δεν τελειώνει ποτέ και μεταδίδει γεγονότα στον πελάτη.
Το πρόβλημα με αυτή τη μέθοδο είναι ότι για να στείλετε πληροφορίες πίσω στον διακομιστή, πρέπει να στείλετε ένα άλλο αίτημα αλληλογραφίας (καθώς το SSE είναι μια μονόδρομη επικοινωνία), πράγμα που σημαίνει ότι πρέπει να κρατήσετε την κατάσταση.
Στο παράδειγμά τους, κρατούν την κατάσταση στη μνήμη της εφαρμογής και μαντέψτε τι; Πολλοί παραπονιούνται για διαρροές μνήμης επειδή η κατάσταση δεν διαγράφεται όταν ο χρήστης αποσυνδέεται.
Θα χρησιμοποιούσα WebSockets. Έχουν ενσωματωμένη λειτουργία ύπνου και δεν χρειάζεται να διατηρήσετε μια κατάσταση γι 'αυτό.
ΣΚΟΥΠΙΔΑ ΣΤΗΝ
Έχω σκάψει στο SDK ανθρωποειδούς γραμματοσειράς και δεν ήμουν έκπληκτος. Αισθάνεται σκανδαλώδης. Πολλά πράγματα δεν χρησιμοποιούνται στην παραγωγή, όπως "Προϋπολογισμοί". Ο τρόπος που απαιτούν από εσάς να κρατήσετε τα πάντα παγκοσμίως στη μνήμη είναι μια καταστροφή που περιμένει να συμβεί.
Επίσης, είναι δύσκολο να εφαρμόσουμε την επαλήθευση ταυτότητας και να βγάλουμε τον χρήστη από το πλαίσιο, ώστε να μπορέσουμε να πάρουμε τις λεπτομέρειες του.
Το Postiz είναι χτισμένο με το NestJS, οπότε όταν χρησιμοποιείτε μια διαδρομή SSE, κλείνει το παρατηρήσιμο μόλις αποσυνδεθεί, επιτρέποντάς σας να αφαιρέσετε τα πάντα από τη μνήμη.
import EventEmitter from 'events';
import { finalize, fromEvent, startWith } from 'rxjs';
@Injectable()
export class McpService {
static event = new EventEmitter();
constructor(
private _mainMcp: MainMcp
) {
}
async runServer(apiKey: string, organization: string) {
const server = McpSettings.load(organization, this._mainMcp).server();
const transport = new McpTransport(organization);
const observer = fromEvent(
McpService.event,
`organization-${organization}`
).pipe(
startWith({
type: 'endpoint',
data: process.env.NEXT_PUBLIC_BACKEND_URL + '/mcp/' + apiKey + '/messages',
}),
finalize(() => {
transport.close();
})
);
console.log('MCP transport started');
await server.connect(transport);
return observer;
}
async processPostBody(organization: string, body: object) {
const server = McpSettings.load(organization, this._mainMcp).server();
const message = JSONRPCMessageSchema.parse(body);
const transport = new McpTransport(organization);
await server.connect(transport);
transport.handlePostMessage(message);
return {};
}
}
Ετικέτες ΔΗΜΟΣΙΟΓΡΑΦΟΣ ️
Αυτό είναι για εσάς αν είστε μεγάλος οπαδός των frameworks OOP όπως το NestJS/Laravel/Spring.
@McpTool({ toolName: 'POSTIZ_GET_CONFIG_ID' })
async preRun() {
return [
{
type: 'text',
text: `id: ${makeId(10)} Today date is ${dayjs.utc().format()}`,
},
];
}
@McpTool({ toolName: 'POSTIZ_PROVIDERS_LIST' })
async listOfProviders(organization: string) {
const list = (
await this._integrationService.getIntegrationsList(organization)
).map((org) => ({
id: org.id,
name: org.name,
identifier: org.providerIdentifier,
picture: org.picture,
disabled: org.disabled,
profile: org.profile,
customer: org.customer
? {
id: org.customer.id,
name: org.customer.name,
}
: undefined,
}));
return [{ type: 'text', text: JSON.stringify(list) }];
}
@McpTool({
toolName: 'POSTIZ_SCHEDULE_POST',
zod: {
type: eenum(['draft', 'scheduled']),
configId: string(),
generatePictures: boolean(),
date: string().describe('UTC TIME'),
providerId: string().describe('Use POSTIZ_PROVIDERS_LIST to get the id'),
posts: array(object({ text: string(), images: array(string()) })),
},
})
async schedulePost(
organization: string,
obj: {
type: 'draft' | 'schedule';
generatePictures: boolean;
date: string;
providerId: string;
posts: { text: string }[];
}
) {
const create = await this._postsService.createPost(organization, {
date: obj.date,
type: obj.type,
tags: [],
posts: [
{
group: makeId(10),
value: await Promise.all(
obj.posts.map(async (post) => ({
content: post.text,
id: makeId(10),
image: !obj.generatePictures
? []
: [
{
id: makeId(10),
path: await this._openAiService.generateImage(
post.text,
true
),
},
],
}))
),
// @ts-ignore
settings: {},
integration: {
id: obj.providerId,
},
},
],
});
return [
{
type: 'text',
text: `Post created successfully, check it here: ${process.env.FRONTEND_URL}/p/${create[0].postId}`,
},
];
}
Ολόκληρος ο κώδικας μπορεί να βρεθεί στο Postiz εδώ:https://github.com/gitroomhq/postiz-app/tree/main/libraries/nestjs-libraries/src/mcp
Και εδώ :https://github.com/gitroomhq/postiz-app/tree/main/apps/backend/src/mcp
Πρέπει να βάλουμε τα πράγματα στα χέρια μας 🙏🏻
Θα ήταν ωραίο να έχουμε μια ενσωματωμένη επιλογή για να αναγκάσουμε το LLM να κάνει διαφορετικά πράγματα πριν αποκτήσει πρόσβαση στα πράγματα μας.
Κάθε φορά που είπα στον Cursor να προγραμματίσει μια θέση για μένα, προσπάθησε να το προγραμματίσει για το 2024.
Έπρεπε να περάσω μερικές λεπτομέρειες διαμόρφωσης, γι 'αυτό δημιούργησα τοPOSTIZ_CONFIGURATION_PRERUN
Ελπίζουμε, το LLM θα το καλέσει πάντα πριν κάνετε πράγματα.
Αλλά το αγνόησε πολλές φορές (τυπικό), οπότε έπρεπε να είμαι δημιουργικός.POSTIZ_SCHEDULE_POST
, προσθέσαμε μια νέα ιδιοκτησία που ονομάζεταιconfigId
και να αλλάξετε το όνομα του εργαλείου config σεPOSTIZ_GET_CONFIG_ID.
Το αποτέλεσμα του config είναι:id: ${makeId(10)} Today date is ${dayjs.utc().format()}
Αναγκάστηκε το LLM να το καλεί πάντα πριν, και η ημερομηνία ήταν σταθερή! :)
Ήταν ακόμα καλύτερο για μένα επειδή ήξερα ότι θα μου στέλνει ημερομηνίες UTC από τώρα και στο εξής.
ΧΡΗΣΙΜΟΠΟΙΗΣΕΙΣ
Νομίζω ότι λειτουργεί καλύτερα όταν συνδυάζεται με πολλαπλά σύνολα εργαλείων, για παράδειγμα:
- Συνδέστε το στο Cursor και ζητήστε του να προγραμματίσει μια θέση για την εργασία σας σήμερα.
- Συνδέστε το στο Notion και ζητήστε να προγραμματίσετε όλες τις τελευταίες εργασίες της ομάδας στα κοινωνικά δίκτυα - ελέγξτε τα Composio MCPs.
- Συνδέστε το σε οποιοδήποτε SaaS που έχει το CopilotKit και προγραμματίστε δημοσιεύσεις με βάση την εφαρμογή.
Ετικέτες MCP
Ταχυδρόμοςείναι το πιο ισχυρό εργαλείο προγραμματισμού κοινωνικών μέσων ανοιχτού κώδικα - και τώρα ο μόνος προγραμματιστής που προσφέρει MCP (φυσικά, όχι με Zapier ή κάτι τέτοιο)
Με το νέο MCP, μπορείτε να προγραμματίσετε όλες τις δημοσιεύσεις σας από τους πελάτες Cursor / Windsurf και Anthropic.
Όλα είναι 100% δωρεάν :)
Αν σας αρέσει, μην ξεχάσετε να μας σταρ ⭐️https://github.com/gitroomhq/postz-app