Come ispezionare gli oggetti Javascript


100

Come posso ispezionare un oggetto in una casella di avviso? Normalmente l'avviso di un oggetto genera semplicemente il nome del nodo:

alert(document);

Ma voglio ottenere le proprietà e i metodi dell'oggetto nella casella di avviso. Come posso ottenere questa funzionalità, se possibile? O ci sono altri suggerimenti?

In particolare, sto cercando una soluzione per un ambiente di produzione in cui console.log e Firebug non sono disponibili.


9
fare console.logsu Firefox o Chrome
KJYe.Name 葉家仁

1
Non ho capito bene. In un ambiente di produzione, hai utenti reali, giusto? Allora perché dovresti lanciare un avviso con le proprietà dell'oggetto? Forse una soluzione migliore è serializzare l'oggetto e registrarlo in un file o inviare un'e-mail?
Nathan Long

Forse ha bisogno dell'avviso come strumento, ma la funzionalità effettiva per fare qualcos'altro. Potrebbero esserci tutti i tipi di motivi per cui potrebbe volerlo fare, come mostrare statistiche o un errore, o fare entrambe le cose semplicemente passando un oggetto a qualunque cosa stia usando per ispezionare l'oggetto.
Christian


A volte JSON.stringifyè utile.
BrainSlugs83

Risposte:


56

Il for- inesegue un ciclo per ogni proprietà in un oggetto o in un array. È possibile utilizzare questa proprietà per ottenere il valore e modificarlo.

Nota: le proprietà private non sono disponibili per l'ispezione, a meno che non si utilizzi una "spia"; fondamentalmente, sovrascrivi l'oggetto e scrivi del codice che esegue un ciclo for-in all'interno del contesto dell'oggetto.

Perché in assomiglia a:

for (var property in object) loop();

Alcuni esempi di codice:

function xinspect(o,i){
    if(typeof i=='undefined')i='';
    if(i.length>50)return '[MAX ITERATIONS]';
    var r=[];
    for(var p in o){
        var t=typeof o[p];
        r.push(i+'"'+p+'" ('+t+') => '+(t=='object' ? 'object:'+xinspect(o[p],i+'  ') : o[p]+''));
    }
    return r.join(i+'\n');
}

// example of use:
alert(xinspect(document));

Modifica: qualche tempo fa, ho scritto il mio ispettore, se sei interessato, sono felice di condividere.

Modifica 2: beh, ne ho scritto uno comunque.


Dovrebbe essere in qualche modo protetto dalla ricorsione. Hash ( dizionari ) con alcuni ID interni del renderizzatore HTML? Potrebbe essere utile per i noob inserire questo controllo nel codice.
Nakilon

@Nakilon Ho sempre avuto problemi con la ricorsione infinita, specialmente in PHP. Ci sono due modi per risolvere questo problema: usando un parametro di profondità o modificando l'hash e aggiungi la tua proprietà che usi per controllare la ricorsione. Quello di profondità è probabilmente più sicuro.
Christian

Mi piace di più questa versione della linea 7. Assomiglia un po 'di più a ruby ​​e fa dei bei spazi r.push (i +' "'+ p +'" => '+ (t ==' object '?' {\ N '+ xinspect (o [p], i + '') + ('\ n' + i + '},'): o [p] + ''));
BC.

2
Quel pezzo di codice ha completamente distrutto Safari Mobile su iPhone. Sceglierei la soluzione JSON.stringify di seguito per un'alternativa più sicura.
Daniel

1
Questa cosa si è schiantata Safari, Chrome ispezionando un oggetto, non lo consiglierei.
Keno

194

Che ne dici alert(JSON.stringify(object))di un browser moderno?

In caso di TypeError: Converting circular structure to JSON, ecco più opzioni: Come serializzare il nodo DOM in JSON anche se ci sono riferimenti circolari?

La documentazione: JSON.stringify()fornisce informazioni sulla formattazione o sulla modifica dell'output.


+1 Buon suggerimento. Aggiungerei che potrebbe usare jsonview ( jsonviewer.stack.hu ) per vederlo bene.
Christian

2
Se vuoi che sia formattato bene, puoi chiamare:, alert(JSON.stringify(object, null, 4)dove 4è il numero di spazi usati per il rientro.
Jan Molak

Questo mi dà "undefined" come output. Sto cercando di eseguire il debug dei test del karma.
Alex C

1
Ci sono avvertimenti a questo approccio. OP dice che vuole ispezionare i metodi dell'oggetto. stringify non mostrerà metodi: JSON.stringify({f: ()=>{}}) => "{}". Inoltre, se l'oggetto implementa toJSONil metodo si ottiene ciò che metodo restituisce, che è inutile se si vuole esaminare l'oggetto: JSON.stringify({toJSON: () => 'nothin'}) => '"nothin"'.
Morozov

39

Usa console.dir(object)e il plugin Firebug


4
Questo mi ha dato le informazioni più complete e utili per quello che stavo cercando. Grazie.
Shon

2
Non ero a conoscenza della console.dirfunzionalità. Non riuscivo a capire perché non potevo più visualizzare l'intero oggetto in Firebug. Questo ora ha risolto il problema per me. Grazie!
Andrew Newby

Ho bisogno di sapere se ci sono altri vantaggi di questo console.logoltre alla comodità di visualizzazione, per favore
user10089632

17

Esistono pochi metodi:

 1. typeof tells you which one of the 6 javascript types is the object. 
 2. instanceof tells you if the object is an instance of another object.
 3. List properties with for(var k in obj)
 4. Object.getOwnPropertyNames( anObjectToInspect ) 
 5. Object.getPrototypeOf( anObject )
 6. anObject.hasOwnProperty(aProperty) 

In un contesto di console, a volte il .constructor o .prototype può essere utile:

console.log(anObject.constructor ); 
console.log(anObject.prototype ) ; 

17

Usa la tua console:

console.log(object);

Oppure, se stai ispezionando elementi dom html, usa console.dir (object). Esempio:

let element = document.getElementById('alertBoxContainer');
console.dir(element);

O se hai un array di oggetti js puoi usare:

console.table(objectArr);

Se stai emettendo molti console.log (oggetti) puoi anche scrivere

console.log({ objectName1 });
console.log({ objectName2 });

Questo ti aiuterà a etichettare gli oggetti scritti sulla console.


Quei valori visualizzati cambiano dinamicamente, in tempo reale, il che può essere fuorviante ai fini del debug
user10089632

in Chrome utilizza le preferenze della console e fai clic su conserva registro. Ora, anche se lo script ti reindirizza a un'altra pagina, la tua console non viene cancellata.
Richard Torcato

Sembra che questo problema sia correlato a Firefox perché in Chrome a meno che tu non re console.log () i valori visualizzati sono ancora. Potresti suggerire di passare a Chrome, ma a volte stai testando la disponibilità delle funzionalità del browser. Comunque grazie per il suggerimento che può essere utile.
user10089632

Non posso usare consoleperché sto usando lo stile stackoverflow.com/q/7505623/1480391 e non è compatibile
Yves M.

9
var str = "";
for(var k in obj)
    if (obj.hasOwnProperty(k)) //omit this test if you want to see built-in properties
        str += k + " = " + obj[k] + "\n";
alert(str);

Come funziona console.log ()? :)
Christian

usa Firefox o Chrome. Ottieni Firebug per Firefox. un must have
moe

Ero sarcastico. L'OP ha chiesto espressamente il codice JS e, a meno che tu non stia suggerendo di approfondire firebug / fox / chrome, non so dove avrebbe trovato una risposta.
Christian

6

Questa è una palese fregatura dell'eccellente risposta di Christian. L'ho appena reso un po 'più leggibile:

/**
 * objectInspector digs through a Javascript object
 * to display all its properties
 *
 * @param object - a Javascript object to inspect
 * @param result - a string of properties with datatypes
 *
 * @return result - the concatenated description of all object properties
 */
function objectInspector(object, result) {
    if (typeof object != "object")
        return "Invalid object";
    if (typeof result == "undefined")
        result = '';

    if (result.length > 50)
        return "[RECURSION TOO DEEP. ABORTING.]";

    var rows = [];
    for (var property in object) {
        var datatype = typeof object[property];

        var tempDescription = result+'"'+property+'"';
        tempDescription += ' ('+datatype+') => ';
        if (datatype == "object")
            tempDescription += 'object: '+objectInspector(object[property],result+'  ');
        else
            tempDescription += object[property];

        rows.push(tempDescription);
    }//Close for

    return rows.join(result+"\n");
}//End objectInspector

4

Ecco il mio ispettore oggetti che è più leggibile. Poiché il codice impiega troppo tempo per essere scritto qui, puoi scaricarlo all'indirizzo http://etto-aa-js.googlecode.com/svn/trunk/inspector.js

Usa in questo modo:

document.write(inspect(object));

2
Di solito è così (ed è sicuramente la guida ufficiale - non pubblicare collegamenti), OTOH, per qualcosa che ha una versione in questo modo, può essere un po 'carino, poiché sai che guarderai sempre il codice più recente, e non qualcosa di vecchio che è stato pubblicato anni fa e potrebbe non funzionare più ... - Inoltre, quell'enorme blocco di codice sembrerebbe piuttosto orribile incollato in un muro di testo, quindi rispondi ... - Fuori tema: sarebbe bello se ci fosse un modo in SO per avere tag "spoiler" per il codice e per essere in grado di collegarsi a una fonte esterna e aggiornarlo automaticamente (quando possibile),
BrainSlugs83
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.