@@ -16,7 +16,6 @@ export function activate(context: vscode.ExtensionContext) {
16
16
manageCheckboxStateManually : true ,
17
17
} ) ;
18
18
19
- // Add fileTreeProvider to ensure proper disposal
20
19
context . subscriptions . push ( fileTreeProvider ) ;
21
20
22
21
let history : string [ ] [ ] = [ ] ;
@@ -34,41 +33,32 @@ export function activate(context: vscode.ExtensionContext) {
34
33
return ;
35
34
}
36
35
37
- // Before saving the current selection to history, check if it's the same as the last selection
38
36
const lastSelection = history [ historyPosition ] || [ ] ;
39
37
if ( ! arraysEqual ( checkedFiles , lastSelection ) ) {
40
- // Save the current selection to the history
41
38
if ( historyPosition < history . length - 1 ) {
42
39
history = history . slice ( 0 , historyPosition + 1 ) ;
43
40
}
44
- history . push ( [ ...checkedFiles ] ) ; // Save a copy of the current selection
41
+ history . push ( [ ...checkedFiles ] ) ;
45
42
historyPosition ++ ;
46
43
}
47
44
48
45
const xmlOutput = await generateXmlOutput ( checkedFiles ) ;
49
46
50
- // Include system message if provided
51
47
const config = vscode . workspace . getConfiguration ( "files2prompt" ) ;
52
48
const systemMessage = config . get < string > ( "systemMessage" ) ;
53
49
54
50
let finalOutput = xmlOutput ;
55
51
56
52
if ( systemMessage && systemMessage . trim ( ) !== "" ) {
57
- // Escape any ']]>' sequences in systemMessage
58
- const safeSystemMessage = systemMessage . replace (
59
- / ] ] > / g,
60
- "]]]]><![CDATA[>"
61
- ) ;
62
53
finalOutput =
63
54
`<systemMessage>
64
55
<![CDATA[
65
- ${ safeSystemMessage }
66
- >
56
+ ${ systemMessage }
57
+ ]] >
67
58
</systemMessage>
68
59
` + finalOutput ;
69
60
}
70
61
71
- // Copy to clipboard
72
62
await vscode . env . clipboard . writeText ( finalOutput ) ;
73
63
74
64
vscode . window . showInformationMessage (
@@ -83,11 +73,8 @@ ${safeSystemMessage}
83
73
if ( historyPosition > 0 ) {
84
74
historyPosition -- ;
85
75
const previousSelection = history [ historyPosition ] ;
86
-
87
- // Update the file selections in the FileTreeProvider
88
76
await fileTreeProvider . setCheckedFiles ( previousSelection ) ;
89
77
} else {
90
- // Show warning message
91
78
vscode . window . showWarningMessage (
92
79
"No previous selection to go back to."
93
80
) ;
@@ -97,11 +84,8 @@ ${safeSystemMessage}
97
84
if ( historyPosition < history . length - 1 ) {
98
85
historyPosition ++ ;
99
86
const nextSelection = history [ historyPosition ] ;
100
-
101
- // Update the file selections in the FileTreeProvider
102
87
await fileTreeProvider . setCheckedFiles ( nextSelection ) ;
103
88
} else {
104
- // Show warning message
105
89
vscode . window . showWarningMessage (
106
90
"No next selection to go forward to."
107
91
) ;
@@ -111,69 +95,57 @@ ${safeSystemMessage}
111
95
const clipboardContent = await vscode . env . clipboard . readText ( ) ;
112
96
await processXmlContent ( clipboardContent ) ;
113
97
} ) ,
114
- vscode . commands . registerCommand (
115
- "files2prompt.copyOpenFiles" ,
116
- async ( ) => {
117
- const tabGroups : ReadonlyArray < vscode . TabGroup > =
118
- vscode . window . tabGroups . all ;
119
-
120
- let xmlContent = "" ;
121
-
122
- for ( const group of tabGroups ) {
123
- for ( const tab of group . tabs ) {
124
- if ( tab . input instanceof vscode . TabInputText ) {
125
- const fileUri = tab . input . uri ;
126
- const filePath = fileUri . fsPath ;
127
- if ( fs . existsSync ( filePath ) ) {
128
- const content = fs . readFileSync ( filePath , "utf-8" ) ;
129
- // Escape any ']]>' sequences in content
130
- const safeContent = content . replace (
131
- / ] ] > / g,
132
- "]]]]><![CDATA[>"
133
- ) ;
134
-
135
- const fileName = path . relative (
136
- vscode . workspace . workspaceFolders ! [ 0 ] . uri . fsPath ,
137
- filePath
138
- ) ;
139
-
140
- xmlContent += `<file name="${ fileName } ">
98
+ vscode . commands . registerCommand ( "files2prompt.copyOpenFiles" , async ( ) => {
99
+ const tabGroups : ReadonlyArray < vscode . TabGroup > =
100
+ vscode . window . tabGroups . all ;
101
+
102
+ let xmlContent = "" ;
103
+
104
+ for ( const group of tabGroups ) {
105
+ for ( const tab of group . tabs ) {
106
+ if ( tab . input instanceof vscode . TabInputText ) {
107
+ const fileUri = tab . input . uri ;
108
+ const filePath = fileUri . fsPath ;
109
+ if ( fs . existsSync ( filePath ) ) {
110
+ const content = fs . readFileSync ( filePath , "utf-8" ) ;
111
+
112
+ const fileName = path . relative (
113
+ vscode . workspace . workspaceFolders ! [ 0 ] . uri . fsPath ,
114
+ filePath
115
+ ) ;
116
+
117
+ xmlContent += `<file name="${ fileName } ">
141
118
<![CDATA[
142
- ${ safeContent }
143
- >
119
+ ${ content }
120
+ ]] >
144
121
</file>
145
122
` ;
146
- }
147
123
}
148
124
}
149
125
}
126
+ }
150
127
151
- if ( xmlContent === "" ) {
152
- vscode . window . showWarningMessage ( "No open files to copy." ) ;
153
- return ;
154
- }
128
+ if ( xmlContent === "" ) {
129
+ vscode . window . showWarningMessage ( "No open files to copy." ) ;
130
+ return ;
131
+ }
155
132
156
- const finalOutput = `<files>
133
+ const finalOutput = `<files>
157
134
${ xmlContent } </files>`;
158
135
159
- // Copy to clipboard
160
- await vscode . env . clipboard . writeText ( finalOutput ) ;
161
-
162
- vscode . window . showInformationMessage (
163
- "Open file contents copied to clipboard."
164
- ) ;
165
- }
166
- )
136
+ await vscode . env . clipboard . writeText ( finalOutput ) ;
137
+ vscode . window . showInformationMessage (
138
+ "Open file contents copied to clipboard."
139
+ ) ;
140
+ } )
167
141
) ;
168
142
169
- // Handle checkbox state changes asynchronously
170
143
treeView . onDidChangeCheckboxState ( async ( e ) => {
171
144
for ( const [ item , state ] of e . items ) {
172
145
await fileTreeProvider . updateCheckState ( item , state ) ;
173
146
}
174
147
} ) ;
175
148
176
- // Listen for configuration changes to update behavior dynamically
177
149
context . subscriptions . push (
178
150
vscode . workspace . onDidChangeConfiguration ( ( event ) => {
179
151
if ( event . affectsConfiguration ( "files2prompt.systemMessage" ) ) {
@@ -190,24 +162,20 @@ ${xmlContent}</files>`;
190
162
191
163
export function deactivate ( ) { }
192
164
193
- // Helper function to generate XML output
194
165
async function generateXmlOutput ( filePaths : string [ ] ) : Promise < string > {
195
166
let xmlContent = "" ;
196
167
197
168
for ( const filePath of filePaths ) {
198
169
const content = fs . readFileSync ( filePath , "utf-8" ) ;
199
- // Escape any ']]>' sequences in file content
200
- const safeContent = content . replace ( / ] ] > / g, "]]]]><![CDATA[>" ) ;
201
-
202
170
const fileName = path . relative (
203
171
vscode . workspace . workspaceFolders ! [ 0 ] . uri . fsPath ,
204
172
filePath
205
173
) ;
206
174
207
175
xmlContent += `<file name="${ fileName } ">
208
176
<![CDATA[
209
- ${ safeContent }
210
- >
177
+ ${ content }
178
+ ]] >
211
179
</file>
212
180
` ;
213
181
}
@@ -216,7 +184,6 @@ ${safeContent}
216
184
${ xmlContent } </files>`;
217
185
}
218
186
219
- // Helper function to compare arrays of strings
220
187
function arraysEqual ( a : string [ ] , b : string [ ] ) : boolean {
221
188
if ( a . length !== b . length ) return false ;
222
189
const sortedA = [ ...a ] . sort ( ) ;
@@ -227,28 +194,16 @@ function arraysEqual(a: string[], b: string[]): boolean {
227
194
return true ;
228
195
}
229
196
230
- // Function to process XML content from clipboard
231
197
async function processXmlContent ( xmlContent : string ) {
232
- // Extract only XML content
233
- const xmlOnly = extractXmlContent ( xmlContent ) ;
234
- if ( ! xmlOnly ) {
235
- vscode . window . showErrorMessage ( "No valid XML content found in clipboard." ) ;
236
- return ;
237
- }
238
-
239
198
const parser = new XMLParser ( {
240
199
ignoreAttributes : false ,
241
- allowBooleanAttributes : true ,
242
- parseTagValue : true ,
243
- parseAttributeValue : false ,
244
- trimValues : false ,
245
200
cdataPropName : "__cdata" ,
246
- tagValueProcessor : ( val , tagName ) => val , // Prevent default processing
201
+ trimValues : false
247
202
} ) ;
248
203
249
204
let jsonObj ;
250
205
try {
251
- jsonObj = parser . parse ( xmlOnly ) ;
206
+ jsonObj = parser . parse ( xmlContent ) ;
252
207
} catch ( error ) {
253
208
vscode . window . showErrorMessage ( "Error parsing XML content from clipboard." ) ;
254
209
return ;
@@ -270,7 +225,6 @@ async function processXmlContent(xmlContent: string) {
270
225
if ( fileObj [ "__cdata" ] ) {
271
226
fileContent = fileObj [ "__cdata" ] ;
272
227
} else {
273
- // If no CDATA, get text content
274
228
fileContent = fileObj [ "#text" ] || "" ;
275
229
}
276
230
@@ -285,14 +239,4 @@ async function processXmlContent(xmlContent: string) {
285
239
}
286
240
287
241
vscode . window . showInformationMessage ( "Files have been updated successfully." ) ;
288
- }
289
-
290
- function extractXmlContent ( text : string ) : string | null {
291
- const xmlMatch = text . match ( / < f i l e s > [ \s \S ] * < \/ f i l e s > / ) ;
292
- if ( xmlMatch ) {
293
- return xmlMatch [ 0 ] ;
294
- }
295
-
296
- // If no <files> tag found, return null
297
- return null ;
298
- }
242
+ }
0 commit comments