javascript - Restaurando console.log()
google-chrome prototypejs (7)
Como la consola original está en el objeto window.console, intente restaurar window.console
desde iframe
:
var i = document.createElement(''iframe'');
i.style.display = ''none'';
document.body.appendChild(i);
window.console = i.contentWindow.console;
i.parentNode.removeChild(i);
Funciona para mí en Chrome 14.
Por alguna razón, el marco prototipo (u otro código JavaScript) que se incluye con Magento está reemplazando las funciones de la consola estándar, por lo que no puedo depurar nada. Escribiendo en la consola de console
JavaScript obtengo el siguiente resultado:
> console
Object
assert: function () {}
count: function () {}
debug: function () {}
dir: function () {}
dirxml: function () {}
error: function () {}
group: function () {}
groupEnd: function () {}
info: function () {}
log: function () {}
profile: function () {}
profileEnd: function () {}
time: function () {}
timeEnd: function () {}
trace: function () {}
warn: function () {}
Estoy usando la Google Chrome version 13.0.782.112
en Linux.
Prototype JavaScript framework, version 1.6.0.3
¿Hay una manera rápida de resolver esto?
Guarde una referencia a la console
original en una variable al comienzo del script y luego use esta referencia o redefina la console
para que apunte al valor capturado.
Ejemplo:
var c = window.console;
window.console = {
log :function(str) {
alert(str);
}
}
// alerts hello
console.log("hello");
// logs to the console
c.log("hello");
Las soluciones proporcionadas en esta pregunta ya no resuelven este problema correctamente en los nuevos navegadores. El único que (en cierto modo) funciona es agarrar la consola desde un <iframe>
tal como lo indica @Xaerxess.
Escribí un script de usuario que protege a la consola de que no se sobrescriba. No rompe ninguna herramienta que anule la consola; llama a los métodos original y anulado. Por supuesto, también se puede incluir en la página web.
// ==UserScript==
// @name Protect console
// @namespace util
// @description Protect console methods from being overriden
// @include *
// @version 1
// @grant none
// @run-at document-start
// ==/UserScript==
{
/**
* This object contains new methods assigned to console.
* @type {{[x:string]:Function}} **/
const consoleOverridenValues = {};
/**
* This object contains original methods copied from the console object
* @type {{[x:string]:Function}} **/
const originalConsole = {};
window.originalConsole = originalConsole;
// This is the original console object taken from window object
const originalConsoleObject = console;
/**
*
* @param {string} name
*/
function protectConsoleEntry(name) {
const protectorSetter = function (newValue) {
originalConsole.warn("Someone tried to change console." + name + " to ", newValue);
consoleOverridenValues[name] = function () {
/// call original console first
originalConsole[name].apply(originalConsoleObject, arguments);
if (typeof newValue == "function") {
/// call inherited console
newValue.apply(window.console, arguments);
}
}
}
const getter = function () {
if (consoleOverridenValues[name])
return consoleOverridenValues[name];
else
return originalConsole[name];
}
Object.defineProperty(console, name, {
enumerable: true,
configurable: false,
get: getter,
set: protectorSetter
});
}
/*
*** This section contains window.console protection
*** It mirrors any properties of newly assigned values
*** to the overridenConsoleValues
*** so that they can be used properly
*/
/**
* This is any new object assigned to window.console
* @type {Object} **/
var consoleOverridenObject = null;
/// Separate boolean is used instead
/// of checking consoleOverridenObject == null
/// This allows null and undefined to be assigned with
/// expected result
var consoleIsOverriden = false;
for (var i in console) {
originalConsole[i] = console[i];
protectConsoleEntry(i);
}
Object.defineProperty(window, "console", {
/// always returns the original console object
/// get: function () { return consoleIsOverriden ? consoleOverridenObject : originalConsoleObject; },
get: function () { return originalConsoleObject; },
set: function (val) {
originalConsole.log("Somebody tried to override window.console. I blocked this attempt."
+ " However the emulation is not perfect in this case because: /n"
+ " window.console = myObject;/n"
+ " window.console == myObject/n"
+ "returns false."
)
consoleIsOverriden = true;
consoleOverridenObject = val;
for (let propertyName in val) {
consoleOverridenValues[propertyName] = val[propertyName];
}
return console;
},
});
}
Magento tiene el siguiente código en /js/varien/js.js
- /js/varien/js.js
y funcionará.
if (!("console" in window) || !("firebug" in console))
{
var names = ["log", "debug", "info", "warn", "error", "assert", "dir", "dirxml",
"group", "groupEnd", "time", "timeEnd", "count", "trace", "profile", "profileEnd"];
window.console = {};
for (var i = 0; i < names.length; ++i)
window.console[names[i]] = function() {}
}
Por ejemplo,
delete console.log
También restauraría console.log
:
console.log = null;
console.log; // null
delete console.log;
console.log; // function log() { [native code] }
delete window.console
restaura el objeto de console
original en Firefox y Chrome.
¿Como funciona esto? window
es un objeto alojado y, por lo general, se implementa con un prototipo común entre todas las instancias (tiene muchas pestañas en el navegador).
Algunos desarrolladores tontos de bibliotecas / marcos externos (o Firebug , etc.) anulan la propiedad de la consola de la instancia de window
, pero no corrompe window.prototype
. Por el operador de delete
, estamos de vuelta enviando desde la console.*
Métodos para prototipo de código.
function restoreConsole() {
var iframe = document.createElement(''iframe'');
iframe.style.display = ''none'';
document.body.appendChild(iframe);
console = iframe.contentWindow.console;
window.console = console;
// Don''t remove iframe or console will lost
}
Probado en Chrome 71 y Firefox 65