recoder-code 2.3.0 → 2.3.4

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.
@@ -0,0 +1,208 @@
1
+ // Team Collaboration Plugin for Recoder
2
+ // Handle chalk properly
3
+ const chalkModule = require('chalk');
4
+ const chalk = chalkModule.default || chalkModule;
5
+ const fs = require('fs');
6
+ const path = require('path');
7
+
8
+ module.exports = {
9
+ name: 'team-collaboration',
10
+ version: '1.0.0',
11
+ description: 'Enhanced team collaboration features and workflows',
12
+ author: 'Recoder Team',
13
+ enabled: true,
14
+
15
+ async init() {
16
+ console.log(chalk.green('✅ Team collaboration plugin initialized'));
17
+ },
18
+
19
+ async cleanup() {
20
+ console.log('Team collaboration plugin cleaned up');
21
+ },
22
+
23
+ commands: {
24
+ 'team-setup': async (args, context) => {
25
+ const chat = context.chat;
26
+ if (!chat.collaborationManager) {
27
+ return '❌ Collaboration manager not available';
28
+ }
29
+
30
+ let response = '🤝 Team Setup Quick Guide:\n\n';
31
+ response += '1. Create a team workspace:\n /workspace create "My Team" "Project description"\n\n';
32
+ response += '2. Invite team members:\n /team invite alice\n /team invite bob\n\n';
33
+ response += '3. Share your current session:\n /share session\n\n';
34
+ response += '4. Start collaborating:\n /collaborate start\n\n';
35
+ response += 'Team Features:\n';
36
+ response += '• Shared conversations across team members\n';
37
+ response += '• File sharing and collaborative editing\n';
38
+ response += '• Real-time messaging and notifications\n';
39
+ response += '• Workspace-based project organization\n';
40
+ response += '• Session broadcasting and synchronization\n';
41
+
42
+ return response;
43
+ },
44
+
45
+ 'quick-share': async (args, context) => {
46
+ const chat = context.chat;
47
+ if (!chat.collaborationManager) {
48
+ return '❌ Collaboration manager not available';
49
+ }
50
+
51
+ // Quick share current conversation
52
+ const currentConv = chat.getCurrentConversation();
53
+ const quickSessionData = {
54
+ name: currentConv.name,
55
+ model: currentConv.model,
56
+ conversation: {
57
+ ...currentConv,
58
+ created: currentConv.created.toISOString(),
59
+ lastActive: currentConv.lastActive.toISOString()
60
+ },
61
+ timestamp: new Date().toISOString()
62
+ };
63
+
64
+ const sharedId = await chat.collaborationManager.createSharedSession(quickSessionData);
65
+ return `🚀 Quick share created! ID: ${sharedId}\nShare this with your team: /share join ${sharedId}`;
66
+ },
67
+
68
+ 'team-status': async (args, context) => {
69
+ const chat = context.chat;
70
+ if (!chat.collaborationManager) {
71
+ return '❌ Collaboration manager not available';
72
+ }
73
+
74
+ const status = chat.collaborationManager.getCollaborationStatus();
75
+ const workspaces = chat.collaborationManager.listTeamWorkspaces();
76
+ const sharedSessions = chat.collaborationManager.listSharedSessions();
77
+
78
+ let response = '👥 Team Status Dashboard:\n\n';
79
+ response += `Collaboration Mode: ${status.mode}\n`;
80
+ response += `Team Members: ${status.teamMembers.length}\n`;
81
+ response += `Workspaces: ${workspaces.length}\n`;
82
+ response += `Shared Sessions: ${sharedSessions.length}\n`;
83
+
84
+ if (status.collaborationId) {
85
+ response += `\n🤝 Active Collaboration: ${status.collaborationId}\n`;
86
+ response += `Role: ${status.isHost ? 'Host' : 'Participant'}\n`;
87
+ }
88
+
89
+ if (workspaces.length > 0) {
90
+ response += '\n📁 Recent Workspaces:\n';
91
+ workspaces.slice(0, 3).forEach(ws => {
92
+ response += `• ${ws.name} (${ws.members.length} members)\n`;
93
+ });
94
+ }
95
+
96
+ return response;
97
+ },
98
+
99
+ 'sync': async (args, context) => {
100
+ const chat = context.chat;
101
+ if (!chat.collaborationManager) {
102
+ return '❌ Collaboration manager not available';
103
+ }
104
+
105
+ const status = chat.collaborationManager.getCollaborationStatus();
106
+ if (status.mode === 'none') {
107
+ return '⚠️ Not in collaboration mode. Use /collaborate start to begin.';
108
+ }
109
+
110
+ // Simulate syncing with team
111
+ const currentConv = chat.getCurrentConversation();
112
+ await chat.collaborationManager.broadcastMessage(
113
+ `Syncing conversation: ${currentConv.name}`,
114
+ {
115
+ type: 'sync',
116
+ conversationId: chat.currentConversationId,
117
+ messageCount: currentConv.history.length,
118
+ model: currentConv.model
119
+ }
120
+ );
121
+
122
+ return '✅ Conversation synced with team';
123
+ },
124
+
125
+ 'invite-link': async (args, context) => {
126
+ const chat = context.chat;
127
+ if (!chat.collaborationManager) {
128
+ return '❌ Collaboration manager not available';
129
+ }
130
+
131
+ const workspaceId = args[0];
132
+ if (!workspaceId) {
133
+ return '❌ Usage: /invite-link <workspace-id>';
134
+ }
135
+
136
+ // Generate a shareable invitation link (simulated)
137
+ const inviteCode = require('crypto').randomBytes(6).toString('hex');
138
+
139
+ let response = `🔗 Workspace Invitation Generated!\n\n`;
140
+ response += `Workspace ID: ${workspaceId}\n`;
141
+ response += `Invite Code: ${inviteCode}\n\n`;
142
+ response += `Share this with team members:\n`;
143
+ response += `"Join our workspace with: /workspace join ${workspaceId}"\n\n`;
144
+ response += `💡 Tip: Team members can also use /team-setup for guidance`;
145
+
146
+ return response;
147
+ }
148
+ },
149
+
150
+ // Process messages for collaboration suggestions
151
+ onMessage: async (message, context) => {
152
+ const lowerMessage = message.toLowerCase();
153
+
154
+ // Suggest collaboration features
155
+ if (lowerMessage.includes('team') || lowerMessage.includes('collaborate')) {
156
+ return '💡 Tip: Use /team-setup for collaboration quick start';
157
+ }
158
+
159
+ if (lowerMessage.includes('share') || lowerMessage.includes('send to')) {
160
+ return '💡 Tip: Use /quick-share to instantly share current conversation';
161
+ }
162
+
163
+ if (lowerMessage.includes('workspace') || lowerMessage.includes('project')) {
164
+ return '💡 Tip: Use /workspace create to set up team workspace';
165
+ }
166
+
167
+ if (lowerMessage.includes('invite') || lowerMessage.includes('add member')) {
168
+ return '💡 Tip: Use /team invite <username> to add team members';
169
+ }
170
+
171
+ return null;
172
+ },
173
+
174
+ // Hook into conversation events
175
+ onResponse: async (response, context) => {
176
+ const chat = context.chat;
177
+
178
+ // Auto-sync important responses in collaboration mode
179
+ if (chat.collaborationManager?.getCollaborationStatus().mode !== 'none') {
180
+ if (response.includes('```') || response.length > 500) {
181
+ // This is likely code or a significant response
182
+ console.log(chalk.gray('🔄 Auto-syncing significant response with team'));
183
+
184
+ await chat.collaborationManager.broadcastMessage(
185
+ 'Significant AI response generated',
186
+ {
187
+ type: 'ai_response',
188
+ length: response.length,
189
+ hasCode: response.includes('```'),
190
+ conversationId: chat.currentConversationId
191
+ }
192
+ );
193
+ }
194
+ }
195
+ },
196
+
197
+ hooks: {
198
+ beforeResponse: async (data) => {
199
+ // Could add team input processing here
200
+ return data;
201
+ },
202
+
203
+ afterResponse: async (data) => {
204
+ // Could add team notification features here
205
+ return data;
206
+ }
207
+ }
208
+ };
@@ -11,7 +11,7 @@ module.exports = {
11
11
  enabled: true,
12
12
 
13
13
  async init() {
14
- console.log(chalk.green('✅ Voice commands plugin initialized'));
14
+ // console.log(chalk.green('✅ Voice commands plugin initialized'));
15
15
  },
16
16
 
17
17
  async cleanup() {
@@ -0,0 +1,136 @@
1
+ // Voice Commands Plugin for Recoder
2
+ // Handle chalk properly
3
+ const chalkModule = require('chalk');
4
+ const chalk = chalkModule.default || chalkModule;
5
+
6
+ module.exports = {
7
+ name: 'voice-commands',
8
+ version: '1.0.0',
9
+ description: 'Enhanced voice command processing and shortcuts',
10
+ author: 'Recoder Team',
11
+ enabled: true,
12
+
13
+ async init() {
14
+ console.log(chalk.green('✅ Voice commands plugin initialized'));
15
+ },
16
+
17
+ async cleanup() {
18
+ console.log('Voice commands plugin cleaned up');
19
+ },
20
+
21
+ commands: {
22
+ listen: async (args, context) => {
23
+ const chat = context.chat;
24
+ if (!chat.voiceManager) {
25
+ return '❌ Voice manager not available';
26
+ }
27
+
28
+ if (!chat.voiceManager.speechToTextEnabled) {
29
+ return '❌ Speech-to-text not enabled. Use /voice stt on first.';
30
+ }
31
+
32
+ // Start listening mode
33
+ if (chat.voiceManager.isRecording) {
34
+ return '⚠️ Already listening. Use /record to stop.';
35
+ }
36
+
37
+ const started = await chat.voiceManager.startRecording();
38
+ if (started) {
39
+ return '🎤 Voice listening activated. Press Enter to stop and process.';
40
+ } else {
41
+ return '❌ Failed to start voice recording';
42
+ }
43
+ },
44
+
45
+ quiet: async (args, context) => {
46
+ const chat = context.chat;
47
+ if (!chat.voiceManager) {
48
+ return '❌ Voice manager not available';
49
+ }
50
+
51
+ await chat.voiceManager.stopSpeaking();
52
+ return '🔇 Voice output stopped';
53
+ },
54
+
55
+ 'voice-setup': async (args, context) => {
56
+ const chat = context.chat;
57
+ if (!chat.voiceManager) {
58
+ return '❌ Voice manager not available';
59
+ }
60
+
61
+ const status = chat.voiceManager.getStatus();
62
+
63
+ let response = '🎤 Voice Setup Quick Guide:\n\n';
64
+
65
+ if (!status.textToSpeechEnabled) {
66
+ response += '🔊 Enable Text-to-Speech: /voice tts on\n';
67
+ } else {
68
+ response += '✅ Text-to-Speech is enabled\n';
69
+ }
70
+
71
+ if (!status.speechToTextEnabled) {
72
+ response += '🎙️ Enable Speech-to-Text: /voice stt on\n';
73
+ } else {
74
+ response += '✅ Speech-to-Text is enabled\n';
75
+ }
76
+
77
+ response += '\nVoice Commands:\n';
78
+ response += '• /record - Start/stop voice recording\n';
79
+ response += '• /speak <text> - Speak text aloud\n';
80
+ response += '• /listen - Quick voice input\n';
81
+ response += '• /quiet - Stop current speech\n';
82
+ response += '• /voice voices - List available voices\n';
83
+ response += '• /voice set <name> - Change voice\n';
84
+
85
+ return response;
86
+ }
87
+ },
88
+
89
+ // Process messages for voice-related suggestions
90
+ onMessage: async (message, context) => {
91
+ const lowerMessage = message.toLowerCase();
92
+
93
+ // Suggest voice commands for common phrases
94
+ if (lowerMessage.includes('speak') || lowerMessage.includes('say')) {
95
+ return '💡 Tip: Use /speak <text> to hear responses aloud';
96
+ }
97
+
98
+ if (lowerMessage.includes('listen') || lowerMessage.includes('voice input')) {
99
+ return '💡 Tip: Use /record or /listen for voice input';
100
+ }
101
+
102
+ if (lowerMessage.includes('voice') || lowerMessage.includes('audio')) {
103
+ return '💡 Tip: Use /voice to manage voice settings';
104
+ }
105
+
106
+ return null;
107
+ },
108
+
109
+ // Hook into response processing to add voice features
110
+ onResponse: async (response, context) => {
111
+ const chat = context.chat;
112
+
113
+ // Check if response contains code - don't speak code blocks
114
+ if (response.includes('```') && chat.voiceManager?.textToSpeechEnabled) {
115
+ console.log(chalk.gray('🔇 Skipping TTS for code response'));
116
+
117
+ // Stop any current speech and don't speak this response
118
+ await chat.voiceManager.stopSpeaking();
119
+
120
+ // You could override the TTS behavior here
121
+ // by temporarily disabling it for this response
122
+ }
123
+ },
124
+
125
+ hooks: {
126
+ beforeResponse: async (data) => {
127
+ // Could process voice commands before sending to AI
128
+ return data;
129
+ },
130
+
131
+ afterResponse: async (data) => {
132
+ // Could add voice feedback after responses
133
+ return data;
134
+ }
135
+ }
136
+ };
@@ -10,7 +10,7 @@ module.exports = {
10
10
 
11
11
  // Plugin initialization
12
12
  async init() {
13
- console.log('Weather plugin initialized');
13
+ // console.log('Weather plugin initialized');
14
14
  },
15
15
 
16
16
  // Plugin cleanup
@@ -0,0 +1,83 @@
1
+ // Example Weather Plugin for Recoder
2
+ const axios = require('axios');
3
+
4
+ module.exports = {
5
+ name: 'weather',
6
+ version: '1.0.0',
7
+ description: 'Get weather information for any city',
8
+ author: 'Recoder Team',
9
+ enabled: true,
10
+
11
+ // Plugin initialization
12
+ async init() {
13
+ console.log('Weather plugin initialized');
14
+ },
15
+
16
+ // Plugin cleanup
17
+ async cleanup() {
18
+ console.log('Weather plugin cleaned up');
19
+ },
20
+
21
+ // Custom commands
22
+ commands: {
23
+ weather: async (args, context) => {
24
+ if (!args.length) {
25
+ return 'Usage: /weather <city>';
26
+ }
27
+
28
+ const city = args.join(' ');
29
+ try {
30
+ // Using a free weather API (OpenWeatherMap alternative)
31
+ const response = await axios.get(`https://wttr.in/${encodeURIComponent(city)}?format=j1`);
32
+ const data = response.data;
33
+
34
+ if (!data.current_condition) {
35
+ return `Weather data not found for ${city}`;
36
+ }
37
+
38
+ const current = data.current_condition[0];
39
+ const location = data.nearest_area[0];
40
+
41
+ return `🌤️ Weather in ${location.areaName[0].value}, ${location.country[0].value}:
42
+ Temperature: ${current.temp_C}°C (${current.temp_F}°F)
43
+ Condition: ${current.weatherDesc[0].value}
44
+ Humidity: ${current.humidity}%
45
+ Wind: ${current.windspeedKmph} km/h ${current.winddir16Point}
46
+ Feels like: ${current.FeelsLikeC}°C`;
47
+
48
+ } catch (error) {
49
+ return `Failed to fetch weather data: ${error.message}`;
50
+ }
51
+ }
52
+ },
53
+
54
+ // Hook into message processing
55
+ onMessage: async (message, context) => {
56
+ // Auto-detect weather requests
57
+ const weatherKeywords = ['weather', 'temperature', 'forecast', 'climate'];
58
+ const cityPattern = /weather in (\w+)/i;
59
+
60
+ if (weatherKeywords.some(keyword => message.toLowerCase().includes(keyword))) {
61
+ const match = message.match(cityPattern);
62
+ if (match) {
63
+ const city = match[1];
64
+ context.suggestedCommand = `/weather ${city}`;
65
+ return `💡 Suggestion: Use /weather ${city} for current weather`;
66
+ }
67
+ }
68
+ return null;
69
+ },
70
+
71
+ // Hooks for various events
72
+ hooks: {
73
+ beforeResponse: async (data) => {
74
+ // Could modify the response before it's sent
75
+ return data;
76
+ },
77
+
78
+ afterResponse: async (data) => {
79
+ // Could perform actions after response is sent
80
+ return data;
81
+ }
82
+ }
83
+ };