Skip to content

Instantly share code, notes, and snippets.

@daemondevin
Created November 23, 2025 02:30
Show Gist options
  • Select an option

  • Save daemondevin/4f80aad29e774d0a49b259c2715591f1 to your computer and use it in GitHub Desktop.

Select an option

Save daemondevin/4f80aad29e774d0a49b259c2715591f1 to your computer and use it in GitHub Desktop.
ActiveXObject Polyfill
/**
* ActiveXObject Polyfill
* Provides fallback implementations for common ActiveX objects
* Note: This only works for specific objects and has limited functionality
*/
(function() {
'use strict';
// Skip if ActiveXObject already exists (IE)
if (typeof ActiveXObject !== 'undefined') {
return;
}
// Map of ProgIDs to modern equivalents
const activeXMap = {
// XMLHttpRequest variants
'Microsoft.XMLHTTP': function() { return new XMLHttpRequest(); },
'Msxml2.XMLHTTP': function() { return new XMLHttpRequest(); },
'Msxml2.XMLHTTP.3.0': function() { return new XMLHttpRequest(); },
'Msxml2.XMLHTTP.6.0': function() { return new XMLHttpRequest(); },
// XML DOM variants
'Microsoft.XMLDOM': function() {
return new DOMParser();
},
'Msxml2.DOMDocument': function() {
return new DOMParser();
},
'Msxml2.DOMDocument.3.0': function() {
return new DOMParser();
},
'Msxml2.DOMDocument.6.0': function() {
return new DOMParser();
},
// Scripting objects (limited functionality)
'Scripting.FileSystemObject': function() {
return createFileSystemObject();
},
'Scripting.Dictionary': function() {
return createDictionaryObject();
},
'WScript.Shell': function() {
return createWScriptShellObject();
},
'ADODB.Stream': function() {
return createStreamObject();
}
};
// FileSystemObject polyfill (limited web compatibility)
function createFileSystemObject() {
return {
FileExists: function(path) {
console.warn('FileSystemObject.FileExists not available in browser');
return false;
},
FolderExists: function(path) {
console.warn('FileSystemObject.FolderExists not available in browser');
return false;
},
GetFile: function(path) {
throw new Error('FileSystemObject.GetFile not available in browser');
},
OpenTextFile: function(path, mode, create) {
throw new Error('FileSystemObject.OpenTextFile not available in browser');
},
CreateTextFile: function(path) {
throw new Error('FileSystemObject.CreateTextFile not available in browser');
}
};
}
// Dictionary polyfill using Map
function createDictionaryObject() {
const map = new Map();
return {
Add: function(key, value) {
map.set(key, value);
},
Exists: function(key) {
return map.has(key);
},
Item: function(key) {
return map.get(key);
},
Remove: function(key) {
map.delete(key);
},
RemoveAll: function() {
map.clear();
},
get Count() {
return map.size;
},
Keys: function() {
return Array.from(map.keys());
},
Items: function() {
return Array.from(map.values());
}
};
}
// WScript.Shell polyfill (very limited)
function createWScriptShellObject() {
return {
Run: function(cmd, windowStyle, waitOnReturn) {
console.warn('WScript.Shell.Run not available in browser');
throw new Error('Cannot execute system commands in browser');
},
Exec: function(cmd) {
console.warn('WScript.Shell.Exec not available in browser');
throw new Error('Cannot execute system commands in browser');
},
ExpandEnvironmentStrings: function(str) {
console.warn('WScript.Shell.ExpandEnvironmentStrings not available in browser');
return str;
},
RegRead: function(key) {
throw new Error('Registry access not available in browser');
}
};
}
// ADODB.Stream polyfill (limited)
function createStreamObject() {
let data = '';
let position = 0;
return {
Type: 2, // adTypeText
Charset: 'utf-8',
Open: function() {
data = '';
position = 0;
},
WriteText: function(text) {
data += text;
},
ReadText: function(numChars) {
if (numChars === -1 || numChars === undefined) {
return data;
}
return data.substring(position, position + numChars);
},
SaveToFile: function(filename, options) {
console.warn('ADODB.Stream.SaveToFile not fully supported in browser');
// Could use Blob and download in modern browsers
const blob = new Blob([data], { type: 'text/plain' });
const url = URL.createObjectURL(blob);
const a = document.createElement('a');
a.href = url;
a.download = filename;
a.click();
URL.revokeObjectURL(url);
},
LoadFromFile: function(filename) {
throw new Error('ADODB.Stream.LoadFromFile not available in browser');
},
Close: function() {
data = '';
position = 0;
}
};
}
// Main ActiveXObject constructor
window.ActiveXObject = function(progID) {
if (!progID) {
throw new Error('Automation server cannot create object');
}
const factory = activeXMap[progID];
if (factory) {
return factory();
}
// Unknown ProgID
console.error('ActiveXObject polyfill: Unknown ProgID "' + progID + '"');
throw new Error('Automation server cannot create object');
};
// Add some compatibility properties
window.ActiveXObject.prototype = {};
console.info('ActiveXObject polyfill loaded');
})();
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment