antenna-openclaw-plugin 1.0.0 โ 1.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/index.ts +70 -3
- package/package.json +1 -1
- package/skills/antenna/SKILL.md +1 -0
package/index.ts
CHANGED
|
@@ -573,11 +573,43 @@ export default function register(api: any) {
|
|
|
573
573
|
}
|
|
574
574
|
|
|
575
575
|
const _refMap: Record<string, string> = {};
|
|
576
|
-
|
|
576
|
+
|
|
577
|
+
// Get my profile for match reason generation
|
|
578
|
+
const { data: myProfile } = await supabase.rpc("get_profile", { p_device_id: deviceId });
|
|
579
|
+
const myLines = myProfile ? [myProfile.line1, myProfile.line2, myProfile.line3].filter(Boolean).join(". ") : "";
|
|
580
|
+
|
|
581
|
+
const profiles = [];
|
|
582
|
+
for (let i = 0; i < results.length; i++) {
|
|
583
|
+
const p = results[i] as any;
|
|
577
584
|
const ref = String(i + 1);
|
|
578
585
|
_refMap[ref] = p.device_id;
|
|
579
|
-
|
|
580
|
-
|
|
586
|
+
|
|
587
|
+
const theirLines = [p.line1, p.line2, p.line3].filter(Boolean).join(". ");
|
|
588
|
+
let match_reason: string | null = null;
|
|
589
|
+
|
|
590
|
+
// Generate match reason with Gemini Flash
|
|
591
|
+
if (myLines && theirLines) {
|
|
592
|
+
try {
|
|
593
|
+
const apiKey = process.env.GEMINI_API_KEY || process.env.GOOGLE_API_KEY;
|
|
594
|
+
if (apiKey) {
|
|
595
|
+
const res = await fetch(`https://generativelanguage.googleapis.com/v1beta/models/gemini-2.0-flash:generateContent?key=${apiKey}`, {
|
|
596
|
+
method: "POST",
|
|
597
|
+
headers: { "Content-Type": "application/json" },
|
|
598
|
+
body: JSON.stringify({
|
|
599
|
+
contents: [{ parts: [{ text: `You are matching two people. Person A: "${myLines}". Person B: "${theirLines}". Write ONE short sentence (under 20 words) in the SAME LANGUAGE as the profiles explaining why they might click. Be specific, not generic. No fluff.` }] }],
|
|
600
|
+
generationConfig: { maxOutputTokens: 60, temperature: 0.7 },
|
|
601
|
+
}),
|
|
602
|
+
});
|
|
603
|
+
if (res.ok) {
|
|
604
|
+
const data = await res.json();
|
|
605
|
+
match_reason = data?.candidates?.[0]?.content?.parts?.[0]?.text?.trim() || null;
|
|
606
|
+
}
|
|
607
|
+
}
|
|
608
|
+
} catch { /* best effort */ }
|
|
609
|
+
}
|
|
610
|
+
|
|
611
|
+
profiles.push({ ref, emoji: p.emoji || "๐ค", name: p.display_name || "ๅฟๅ", line1: p.line1, line2: p.line2, line3: p.line3, match_reason });
|
|
612
|
+
}
|
|
581
613
|
|
|
582
614
|
// Persist refs + log recommendation
|
|
583
615
|
(api as any)._antennaRefMap = { ...(api as any)._antennaRefMap, ..._refMap };
|
|
@@ -595,6 +627,41 @@ export default function register(api: any) {
|
|
|
595
627
|
},
|
|
596
628
|
});
|
|
597
629
|
|
|
630
|
+
// โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
|
|
631
|
+
// Tool: antenna_pass
|
|
632
|
+
// โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
|
|
633
|
+
api.registerTool({
|
|
634
|
+
name: "antenna_pass",
|
|
635
|
+
description: "Pass/skip a person. They won't be recommended again.",
|
|
636
|
+
parameters: {
|
|
637
|
+
type: "object",
|
|
638
|
+
properties: {
|
|
639
|
+
sender_id: { type: "string", description: "The sender's user ID" },
|
|
640
|
+
channel: { type: "string", description: "The channel name" },
|
|
641
|
+
ref: { type: "string", description: "Ref number from scan/discover results" },
|
|
642
|
+
target_device_id: { type: "string", description: "Device ID (use ref instead when possible)" },
|
|
643
|
+
},
|
|
644
|
+
required: ["sender_id", "channel"],
|
|
645
|
+
},
|
|
646
|
+
async execute(_id: string, params: any) {
|
|
647
|
+
const cfg = getConfig(api);
|
|
648
|
+
const supabase = getSupabase(cfg);
|
|
649
|
+
const deviceId = deriveDeviceId(params.sender_id, params.channel);
|
|
650
|
+
|
|
651
|
+
let targetId = params.target_device_id;
|
|
652
|
+
if (!targetId && params.ref) {
|
|
653
|
+
const { data: resolved } = await supabase.rpc("resolve_ref", { p_owner: deviceId, p_ref: params.ref });
|
|
654
|
+
targetId = resolved || (api as any)._antennaRefMap?.[params.ref];
|
|
655
|
+
}
|
|
656
|
+
if (!targetId) {
|
|
657
|
+
return ok({ error: "No target. Ref may have expired โ try scanning again." });
|
|
658
|
+
}
|
|
659
|
+
|
|
660
|
+
await supabase.rpc("pass_user", { p_device_id: deviceId, p_passed_device_id: targetId });
|
|
661
|
+
return ok({ passed: true, message: "ๅทฒ่ทณ่ฟ๏ผไธๆฌกไธไผๅๆจ่่ฟไธชไบบใ" });
|
|
662
|
+
},
|
|
663
|
+
});
|
|
664
|
+
|
|
598
665
|
// โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
|
|
599
666
|
// Tool: antenna_check_matches
|
|
600
667
|
// โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
|
package/package.json
CHANGED
package/skills/antenna/SKILL.md
CHANGED
|
@@ -181,6 +181,7 @@ Source code is open: https://github.com/H1an1/Antenna
|
|
|
181
181
|
- ๅฏไปฅๅธฎ็จๆท็ผฉ็ญๅคช้ฟ็ๅ็ญ๏ผไฝ่ฆ่ฎฉ็จๆท็กฎ่ฎค
|
|
182
182
|
- ๅฆๆ็จๆทไธๆณๅ็ญๆไธ้กน๏ผ็็ฉบไน่ก๏ผ"้ฃ่ฟ่กๅ
็ฉบ็๏ผไปฅๅๆณๅ ๅ่ฏด"๏ผ
|
|
183
183
|
- ๆดไธช่ฟ็จๅบ่ฏฅๅ่ทๆๅ่ๅคฉ๏ผไธๅๅกซ่กจ
|
|
184
|
+
- **ๆ้็จๆทไธ่ฆๅจๅ็้ๅ่็ณปๆนๅผ๏ผๅพฎไฟกๅทใๆๆบๅท็ญ๏ผใ** ๅ็ไธๅฅ่ฏๅฏนๆๆไบบๅฏ่งใ่็ณปๆนๅผๅบ่ฏฅๅจ accept ๆถๅ็ฌๅไบซ๏ผ่ฟๆ ทๅชๆๅๆน้ฝๅๆๅๆ่ฝ็ๅฐใ
|
|
184
185
|
|
|
185
186
|
### Showing results โ ไฝ ๆฅๅคๆญ๏ผไธๆฏๆๅกๅจ
|
|
186
187
|
|