codeep 1.0.35 → 1.0.37
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/dist/components/Input.js +29 -61
- package/package.json +1 -1
package/dist/components/Input.js
CHANGED
|
@@ -1,7 +1,6 @@
|
|
|
1
1
|
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
2
|
-
import { useState, useMemo, useEffect
|
|
3
|
-
import { Text, Box, useInput } from 'ink';
|
|
4
|
-
import clipboard from 'clipboardy';
|
|
2
|
+
import { useState, useMemo, useEffect } from 'react';
|
|
3
|
+
import { Text, Box, useInput, useStdin } from 'ink';
|
|
5
4
|
const COMMANDS = [
|
|
6
5
|
{ cmd: '/help', desc: 'Show help' },
|
|
7
6
|
{ cmd: '/status', desc: 'Show status' },
|
|
@@ -33,8 +32,7 @@ export const ChatInput = ({ onSubmit, disabled, history = [], clearTrigger = 0 }
|
|
|
33
32
|
const [selectedIndex, setSelectedIndex] = useState(0);
|
|
34
33
|
const [pasteInfo, setPasteInfo] = useState(null);
|
|
35
34
|
const [historyIndex, setHistoryIndex] = useState(-1);
|
|
36
|
-
const
|
|
37
|
-
const inputBuffer = useRef('');
|
|
35
|
+
const { stdin } = useStdin();
|
|
38
36
|
// Clear input when clearTrigger changes
|
|
39
37
|
useEffect(() => {
|
|
40
38
|
if (clearTrigger > 0) {
|
|
@@ -57,37 +55,33 @@ export const ChatInput = ({ onSubmit, disabled, history = [], clearTrigger = 0 }
|
|
|
57
55
|
setSelectedIndex(0);
|
|
58
56
|
}
|
|
59
57
|
}, [suggestions.length]);
|
|
60
|
-
//
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
lastInputTime.current = now;
|
|
80
|
-
return false;
|
|
81
|
-
};
|
|
82
|
-
const handlePastedText = (text) => {
|
|
58
|
+
// Listen for raw stdin data to detect paste (multiple chars at once)
|
|
59
|
+
useEffect(() => {
|
|
60
|
+
if (disabled || !stdin)
|
|
61
|
+
return;
|
|
62
|
+
const handleData = (data) => {
|
|
63
|
+
const str = data.toString();
|
|
64
|
+
// Detect paste: multiple printable characters arriving at once
|
|
65
|
+
// Exclude control sequences (start with ESC)
|
|
66
|
+
if (str.length > 1 && !str.startsWith('\x1b') && !str.startsWith('\x16')) {
|
|
67
|
+
// This is likely a paste - multiple chars at once
|
|
68
|
+
handlePastedText(str, true);
|
|
69
|
+
}
|
|
70
|
+
};
|
|
71
|
+
stdin.on('data', handleData);
|
|
72
|
+
return () => {
|
|
73
|
+
stdin.off('data', handleData);
|
|
74
|
+
};
|
|
75
|
+
}, [disabled, stdin]);
|
|
76
|
+
const handlePastedText = (text, fromCtrlV = false) => {
|
|
83
77
|
const trimmed = text.trim();
|
|
84
78
|
if (!trimmed)
|
|
85
79
|
return;
|
|
86
80
|
const lines = trimmed.split(/\r?\n/);
|
|
87
81
|
const lineCount = lines.length;
|
|
88
82
|
const charCount = trimmed.length;
|
|
89
|
-
// For multi-line
|
|
90
|
-
if (lineCount > 1 || charCount > 100) {
|
|
83
|
+
// For multi-line, long pastes, or explicit Ctrl+V - show indicator
|
|
84
|
+
if (lineCount > 1 || charCount > 100 || (fromCtrlV && charCount > 20)) {
|
|
91
85
|
const firstLine = lines[0].substring(0, 60);
|
|
92
86
|
const preview = firstLine + (lines[0].length > 60 ? '...' : '');
|
|
93
87
|
setPasteInfo({
|
|
@@ -97,7 +91,7 @@ export const ChatInput = ({ onSubmit, disabled, history = [], clearTrigger = 0 }
|
|
|
97
91
|
fullText: trimmed,
|
|
98
92
|
});
|
|
99
93
|
// Show only indicator in input field, NOT the actual pasted text
|
|
100
|
-
const indicator = `📋
|
|
94
|
+
const indicator = `📋 Paste: ${charCount} chars`;
|
|
101
95
|
// Replace entire value with just the indicator (don't append pasted text)
|
|
102
96
|
setValue(indicator);
|
|
103
97
|
setCursorPos(indicator.length);
|
|
@@ -113,22 +107,13 @@ export const ChatInput = ({ onSubmit, disabled, history = [], clearTrigger = 0 }
|
|
|
113
107
|
useInput((input, key) => {
|
|
114
108
|
if (disabled)
|
|
115
109
|
return;
|
|
116
|
-
// Handle Ctrl+V paste
|
|
117
|
-
if (key.ctrl && input === 'v') {
|
|
118
|
-
clipboard.read().then(text => {
|
|
119
|
-
if (text) {
|
|
120
|
-
handlePastedText(text);
|
|
121
|
-
}
|
|
122
|
-
}).catch(() => { });
|
|
123
|
-
return;
|
|
124
|
-
}
|
|
125
110
|
// Handle Enter - submit
|
|
126
111
|
if (key.return) {
|
|
127
112
|
if (value.trim()) {
|
|
128
113
|
let submitValue = value.trim();
|
|
129
114
|
// Replace paste indicator with actual content
|
|
130
|
-
if (pasteInfo && submitValue.includes('📋
|
|
131
|
-
submitValue = submitValue.replace(/📋
|
|
115
|
+
if (pasteInfo && submitValue.includes('📋 Paste:')) {
|
|
116
|
+
submitValue = submitValue.replace(/📋 Paste: \d+ chars/, pasteInfo.fullText);
|
|
132
117
|
}
|
|
133
118
|
onSubmit(submitValue);
|
|
134
119
|
setValue('');
|
|
@@ -142,7 +127,7 @@ export const ChatInput = ({ onSubmit, disabled, history = [], clearTrigger = 0 }
|
|
|
142
127
|
if (key.escape) {
|
|
143
128
|
if (pasteInfo) {
|
|
144
129
|
// Remove paste indicator from value
|
|
145
|
-
setValue(prev => prev.replace(/📋
|
|
130
|
+
setValue(prev => prev.replace(/📋 Paste: \d+ chars/, ''));
|
|
146
131
|
setPasteInfo(null);
|
|
147
132
|
}
|
|
148
133
|
else if (value) {
|
|
@@ -157,7 +142,7 @@ export const ChatInput = ({ onSubmit, disabled, history = [], clearTrigger = 0 }
|
|
|
157
142
|
setValue(prev => prev.slice(0, cursorPos - 1) + prev.slice(cursorPos));
|
|
158
143
|
setCursorPos(prev => prev - 1);
|
|
159
144
|
// Clear paste info if we deleted the indicator
|
|
160
|
-
if (pasteInfo && !value.includes('📋
|
|
145
|
+
if (pasteInfo && !value.includes('📋 Paste:')) {
|
|
161
146
|
setPasteInfo(null);
|
|
162
147
|
}
|
|
163
148
|
}
|
|
@@ -254,23 +239,6 @@ export const ChatInput = ({ onSubmit, disabled, history = [], clearTrigger = 0 }
|
|
|
254
239
|
setCursorPos(prev => prev + input.length);
|
|
255
240
|
}
|
|
256
241
|
}, { isActive: !disabled });
|
|
257
|
-
// Process any remaining buffered input after a delay
|
|
258
|
-
useEffect(() => {
|
|
259
|
-
const timer = setTimeout(() => {
|
|
260
|
-
if (inputBuffer.current.length > 0) {
|
|
261
|
-
const buffered = inputBuffer.current;
|
|
262
|
-
inputBuffer.current = '';
|
|
263
|
-
if (buffered.length > 5) {
|
|
264
|
-
handlePastedText(buffered);
|
|
265
|
-
}
|
|
266
|
-
else {
|
|
267
|
-
setValue(prev => prev + buffered);
|
|
268
|
-
setCursorPos(prev => prev + buffered.length);
|
|
269
|
-
}
|
|
270
|
-
}
|
|
271
|
-
}, 100);
|
|
272
|
-
return () => clearTimeout(timer);
|
|
273
|
-
}, [value]);
|
|
274
242
|
// Render input with cursor
|
|
275
243
|
const renderInput = () => {
|
|
276
244
|
if (!value) {
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "codeep",
|
|
3
|
-
"version": "1.0.
|
|
3
|
+
"version": "1.0.37",
|
|
4
4
|
"description": "AI-powered coding assistant built for the terminal. Multiple LLM providers, project-aware context, and a seamless development workflow.",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"main": "dist/index.js",
|