snow-flow 3.5.14 ā 3.5.16
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.
|
@@ -31,6 +31,8 @@ export interface LocalFile {
|
|
|
31
31
|
currentContent?: string;
|
|
32
32
|
isModified: boolean;
|
|
33
33
|
fieldMapping?: FieldMapping;
|
|
34
|
+
existedBefore?: boolean;
|
|
35
|
+
previousContent?: string;
|
|
34
36
|
}
|
|
35
37
|
export declare class ArtifactLocalSync {
|
|
36
38
|
private baseDir;
|
|
@@ -84,9 +86,15 @@ export declare class ArtifactLocalSync {
|
|
|
84
86
|
*/
|
|
85
87
|
private validateES5;
|
|
86
88
|
/**
|
|
87
|
-
*
|
|
89
|
+
* AGGRESSIVE STRIP FUNCTION: Remove ALL possible Snow-Flow wrapper variations
|
|
90
|
+
* FIXED: Handles multiple/nested wrappers and all patterns
|
|
88
91
|
*/
|
|
89
92
|
private stripAddedWrappers;
|
|
93
|
+
/**
|
|
94
|
+
* CONSERVATIVE WRAPPER DETECTION: Only add wrappers if content is truly minimal
|
|
95
|
+
* FIXED: Now properly detects ALL types of existing wrappers/comments
|
|
96
|
+
*/
|
|
97
|
+
private needsWrappers;
|
|
90
98
|
/**
|
|
91
99
|
* Sanitize filename for filesystem
|
|
92
100
|
*/
|
|
@@ -127,6 +127,8 @@ class ArtifactLocalSync {
|
|
|
127
127
|
throw new Error(`Unsupported artifact type: ${tableName}. Supported types: ${Object.keys(artifact_registry_1.ARTIFACT_REGISTRY).join(', ')}`);
|
|
128
128
|
}
|
|
129
129
|
console.log(`\nš Pulling ${config.displayName} (${sys_id}) to local files...`);
|
|
130
|
+
console.log(`š Snow-Flow v3.5.16 - ULTRA-CONSERVATIVE Wrapper System (No More Duplicates!)`);
|
|
131
|
+
console.log(`ā ļø CRITICAL FIX: Aggressive strip & minimal wrapper addition only`);
|
|
130
132
|
// Get timeout configuration
|
|
131
133
|
const timeoutConfig = (0, mcp_timeout_config_js_1.getMCPTimeoutConfig)();
|
|
132
134
|
// Use smart fetcher for known types, otherwise direct query
|
|
@@ -186,9 +188,22 @@ class ArtifactLocalSync {
|
|
|
186
188
|
.replace('{name}', sanitizedName)
|
|
187
189
|
.replace('{api_name}', artifactData.api_name || sanitizedName)
|
|
188
190
|
.replace('{short_description}', artifactData.short_description || sanitizedName);
|
|
189
|
-
//
|
|
190
|
-
|
|
191
|
-
|
|
191
|
+
// ULTRA-CONSERVATIVE WRAPPER SYSTEM: When in doubt, don't add wrappers
|
|
192
|
+
let header = '';
|
|
193
|
+
let footer = '';
|
|
194
|
+
// FAILSAFE: Only add wrappers if we're absolutely certain it's safe
|
|
195
|
+
if (mapping.wrapperHeader && mapping.wrapperFooter) {
|
|
196
|
+
const shouldAddWrappers = this.needsWrappers(processedContent, mapping);
|
|
197
|
+
if (shouldAddWrappers && processedContent.trim().length < 50) {
|
|
198
|
+
// EXTRA SAFETY: Only for very short content
|
|
199
|
+
header = this.replacePlaceholders(mapping.wrapperHeader, artifactData);
|
|
200
|
+
footer = this.replacePlaceholders(mapping.wrapperFooter, artifactData);
|
|
201
|
+
console.log(` š§ Adding wrappers for ${filename} (content is minimal: ${processedContent.trim().length} chars)`);
|
|
202
|
+
}
|
|
203
|
+
else {
|
|
204
|
+
console.log(` ā
Skipping wrappers for ${filename} (conservative approach)`);
|
|
205
|
+
}
|
|
206
|
+
}
|
|
192
207
|
const file = this.createLocalFile(artifactPath, `${filename}.${mapping.fileExtension}`, processedContent, mapping.serviceNowField, mapping.fileExtension, header, footer);
|
|
193
208
|
file.fieldMapping = mapping;
|
|
194
209
|
files.push(file);
|
|
@@ -370,6 +385,31 @@ class ArtifactLocalSync {
|
|
|
370
385
|
createLocalFile(dirPath, filename, content, field, type, header = '', footer = '') {
|
|
371
386
|
const filePath = path.join(dirPath, filename);
|
|
372
387
|
const fullContent = header + content + footer;
|
|
388
|
+
// CRITICAL FIX: Check if file exists and handle overwrites intelligently
|
|
389
|
+
let fileExists = false;
|
|
390
|
+
let existingContent = '';
|
|
391
|
+
if (fs.existsSync(filePath)) {
|
|
392
|
+
fileExists = true;
|
|
393
|
+
existingContent = fs.readFileSync(filePath, 'utf8');
|
|
394
|
+
// Check if existing content is the same (avoid unnecessary writes)
|
|
395
|
+
if (existingContent === fullContent) {
|
|
396
|
+
console.log(` š Unchanged: ${filename} (identical content, skipping write)`);
|
|
397
|
+
return {
|
|
398
|
+
filename,
|
|
399
|
+
path: filePath,
|
|
400
|
+
field,
|
|
401
|
+
type: type,
|
|
402
|
+
originalContent: content,
|
|
403
|
+
isModified: false
|
|
404
|
+
};
|
|
405
|
+
}
|
|
406
|
+
console.log(` š Overwriting: ${filename}`);
|
|
407
|
+
console.log(` ā¹ļø File size: ${existingContent.length} ā ${fullContent.length} chars`);
|
|
408
|
+
}
|
|
409
|
+
else {
|
|
410
|
+
console.log(` š Creating: ${filename}`);
|
|
411
|
+
}
|
|
412
|
+
// Write the file
|
|
373
413
|
fs.writeFileSync(filePath, fullContent, 'utf8');
|
|
374
414
|
return {
|
|
375
415
|
filename,
|
|
@@ -377,7 +417,9 @@ class ArtifactLocalSync {
|
|
|
377
417
|
field,
|
|
378
418
|
type: type,
|
|
379
419
|
originalContent: content,
|
|
380
|
-
isModified:
|
|
420
|
+
isModified: fileExists, // Mark as modified if we overwrote existing file
|
|
421
|
+
existedBefore: fileExists,
|
|
422
|
+
previousContent: existingContent
|
|
381
423
|
};
|
|
382
424
|
}
|
|
383
425
|
/**
|
|
@@ -544,28 +586,97 @@ snow-flow sync status ${widget.sys_id}
|
|
|
544
586
|
return issues;
|
|
545
587
|
}
|
|
546
588
|
/**
|
|
547
|
-
*
|
|
589
|
+
* AGGRESSIVE STRIP FUNCTION: Remove ALL possible Snow-Flow wrapper variations
|
|
590
|
+
* FIXED: Handles multiple/nested wrappers and all patterns
|
|
548
591
|
*/
|
|
549
592
|
stripAddedWrappers(content, type, fieldMapping) {
|
|
550
|
-
// Remove our added comments and wrappers
|
|
551
593
|
let cleaned = content;
|
|
594
|
+
// STEP 1: Remove ALL HTML comment variations (multiple times if needed)
|
|
595
|
+
if (type === 'html') {
|
|
596
|
+
let previousLength;
|
|
597
|
+
do {
|
|
598
|
+
previousLength = cleaned.length;
|
|
599
|
+
// Remove ServiceNow Widget Template comments (all variations)
|
|
600
|
+
cleaned = cleaned.replace(/^\s*<!--\s*ServiceNow\s+Widget\s+Template[\s\S]*?-->\s*\n?/gmi, '');
|
|
601
|
+
// Remove Angular bindings comments
|
|
602
|
+
cleaned = cleaned.replace(/^\s*<!--\s*Angular\s+bindings[\s\S]*?-->\s*\n?/gmi, '');
|
|
603
|
+
// Remove any other HTML comments at start
|
|
604
|
+
cleaned = cleaned.replace(/^\s*<!--[\s\S]*?-->\s*\n?/gm, '');
|
|
605
|
+
} while (cleaned.length !== previousLength); // Keep going until no more changes
|
|
606
|
+
}
|
|
607
|
+
// STEP 2: Remove ALL JS comment variations (multiple times if needed)
|
|
552
608
|
if (type === 'js') {
|
|
553
|
-
|
|
554
|
-
|
|
555
|
-
|
|
556
|
-
|
|
557
|
-
|
|
558
|
-
|
|
609
|
+
let previousLength;
|
|
610
|
+
do {
|
|
611
|
+
previousLength = cleaned.length;
|
|
612
|
+
// Remove Server/Client script comment blocks
|
|
613
|
+
cleaned = cleaned.replace(/^\s*\/\*\*[\s\S]*?\*\/\s*\n?/gm, '');
|
|
614
|
+
// Remove function wrappers
|
|
615
|
+
cleaned = cleaned.replace(/^\s*\(function\s*\(\s*\)\s*\{\s*\n?/gm, '');
|
|
616
|
+
cleaned = cleaned.replace(/\s*\n?\s*\}\s*\)\s*\(\s*\)\s*;?\s*$/gm, '');
|
|
617
|
+
// Remove function( wrappers for client scripts
|
|
618
|
+
cleaned = cleaned.replace(/^\s*function\s*\(\s*$/gm, '');
|
|
619
|
+
cleaned = cleaned.replace(/^\s*\)\s*$/gm, '');
|
|
620
|
+
} while (cleaned.length !== previousLength);
|
|
621
|
+
}
|
|
622
|
+
// STEP 3: Remove ALL CSS comment variations
|
|
623
|
+
if (type === 'css') {
|
|
624
|
+
let previousLength;
|
|
625
|
+
do {
|
|
626
|
+
previousLength = cleaned.length;
|
|
627
|
+
// Remove widget style comments
|
|
628
|
+
cleaned = cleaned.replace(/^\s*\/\*[\s\S]*?\*\/\s*\n?/gm, '');
|
|
629
|
+
} while (cleaned.length !== previousLength);
|
|
630
|
+
}
|
|
631
|
+
// STEP 4: Clean up excessive whitespace
|
|
632
|
+
cleaned = cleaned.replace(/^\s*\n+/gm, ''); // Remove empty lines at start
|
|
633
|
+
cleaned = cleaned.replace(/\n\s*$/gm, ''); // Remove trailing whitespace
|
|
634
|
+
return cleaned.trim();
|
|
635
|
+
}
|
|
636
|
+
/**
|
|
637
|
+
* CONSERVATIVE WRAPPER DETECTION: Only add wrappers if content is truly minimal
|
|
638
|
+
* FIXED: Now properly detects ALL types of existing wrappers/comments
|
|
639
|
+
*/
|
|
640
|
+
needsWrappers(content, mapping) {
|
|
641
|
+
if (!content || !content.trim()) {
|
|
642
|
+
return false; // Empty content doesn't need wrappers
|
|
643
|
+
}
|
|
644
|
+
const trimmed = content.trim();
|
|
645
|
+
// CONSERVATIVE APPROACH: If content has ANY of these indicators, skip wrappers
|
|
646
|
+
// 1. Already has HTML comments (ANY HTML comments)
|
|
647
|
+
if (trimmed.includes('<!--')) {
|
|
648
|
+
console.log(` š Detected existing HTML comments - skipping wrappers`);
|
|
649
|
+
return false;
|
|
559
650
|
}
|
|
560
|
-
|
|
561
|
-
|
|
562
|
-
|
|
651
|
+
// 2. Already has JS comments (ANY block comments)
|
|
652
|
+
if (trimmed.includes('/**') || trimmed.includes('/*')) {
|
|
653
|
+
console.log(` š Detected existing JS comments - skipping wrappers`);
|
|
654
|
+
return false;
|
|
563
655
|
}
|
|
564
|
-
|
|
565
|
-
|
|
566
|
-
|
|
656
|
+
// 3. Already has function wrappers (ANY function patterns)
|
|
657
|
+
if (trimmed.includes('(function') || trimmed.match(/^function\s*\(/)) {
|
|
658
|
+
console.log(` š Detected existing function patterns - skipping wrappers`);
|
|
659
|
+
return false;
|
|
567
660
|
}
|
|
568
|
-
|
|
661
|
+
// 4. Content is substantial (more than just basic code)
|
|
662
|
+
if (trimmed.length > 200) {
|
|
663
|
+
console.log(` š Content is substantial (${trimmed.length} chars) - skipping wrappers`);
|
|
664
|
+
return false;
|
|
665
|
+
}
|
|
666
|
+
// 5. Contains ServiceNow-specific patterns
|
|
667
|
+
const serviceNowPatterns = [
|
|
668
|
+
'data.', 'input.', 'options.', '$scope.', 'c.server', 'gs.', '$sp.',
|
|
669
|
+
'ng-', 'angular', 'spModal', 'spUtil', '{{', 'glide'
|
|
670
|
+
];
|
|
671
|
+
for (const pattern of serviceNowPatterns) {
|
|
672
|
+
if (trimmed.toLowerCase().includes(pattern.toLowerCase())) {
|
|
673
|
+
console.log(` š Detected ServiceNow pattern '${pattern}' - skipping wrappers`);
|
|
674
|
+
return false;
|
|
675
|
+
}
|
|
676
|
+
}
|
|
677
|
+
// ONLY add wrappers for truly minimal/empty content
|
|
678
|
+
console.log(` ⨠Content is minimal and clean - adding wrappers`);
|
|
679
|
+
return true;
|
|
569
680
|
}
|
|
570
681
|
/**
|
|
571
682
|
* Sanitize filename for filesystem
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "snow-flow",
|
|
3
|
-
"version": "3.5.
|
|
4
|
-
"description": "ServiceNow development framework with
|
|
3
|
+
"version": "3.5.16",
|
|
4
|
+
"description": "ServiceNow development framework with EMERGENCY FIX for wrapper multiplication bug. v3.5.16 FIXES the triple/quadruple wrapper problem in v3.5.15. Features ULTRA-CONSERVATIVE wrapper system that aggressively strips ALL wrapper variations and only adds wrappers for truly minimal content (<50 chars). No more duplicate HTML comments or function wrappers. Enhanced 'snow-flow init' creates optimized settings.json with 18 MCP servers, extensive development permissions, intelligent hooks, and ServiceNow-specific commands. Features intelligent timeout configuration and comprehensive ServiceNow development workflow.",
|
|
5
5
|
"main": "dist/index.js",
|
|
6
6
|
"type": "commonjs",
|
|
7
7
|
"bin": {
|