Compartilhar via


A área dinâmica para dados snapshot formato de ficheiro

Investigar a utilização da memória em aplicações Web pode ser difícil. A ferramenta DevTools Memory permite-lhe explorar todos os objetos que são alocados na memória, através da sua aplicação Web, através de uma área dinâmica para dados snapshot. Estas informações são úteis para investigações de desempenho porque pode descobrir que objetos estão a consumir mais memória.

No entanto, por vezes poderá ter de se concentrar em partes específicas dos dados de memória que a ferramenta Memória não mostra. Neste caso, utilize DevTools para exportar todo o conjunto de dados de memória como um .heapsnapshot ficheiro JSON.

Este artigo descreve a estrutura e o conteúdo dos .heapsnapshot ficheiros JSON para que possa criar as suas próprias ferramentas de visualização e análise.

Registar uma área dinâmica para dados snapshot

Para exportar um .heapsnapshot ficheiro, primeiro tem de registar uma área dinâmica para dados snapshot na ferramenta Memória, da seguinte forma:

  1. No Microsoft Edge, navegue para o site a partir do qual pretende exportar os dados.

  2. Prima Ctrl+Shift+I (Windows, Linux) ou Comando+Opção+I (macOS) para abrir as Devtools.

  3. Abra a ferramenta Memória .

  4. Selecione Área dinâmica para dados snapshot e, em seguida, clique em Tomar snapshot.

Para obter mais informações, veja Record heap snapshots using the Memory tool ("Heap snapshot" profiling type).

Exportar e ver um .heapsnapshot ficheiro

Depois de registar uma área dinâmica para dados snapshot, pode exportá-la.

  1. Na barra lateral esquerda da ferramenta Memória, clique em Guardar junto à área dinâmica para dados snapshot item que acabou de gravar.

  2. Altere a extensão de ficheiro de .heapsnapshot para .json, para facilitar a abertura do ficheiro num editor de texto.

  3. Abra o ficheiro guardado num editor de texto, como Visual Studio Code.

  4. Para facilitar a leitura do JSON, no Visual Studio Code, clique com o botão direito do rato em qualquer parte do código e, em seguida, selecione Formatar documento.

Geralmente, o ficheiro resultante .heapsnapshot é diferente sempre que grava e exporta uma área dinâmica para dados snapshot. Os instantâneos de área dinâmica são gerados de forma dinâmica, com base no conteúdo da aplicação Web que está atualmente a ser inspecionada nas DevTools.

Descrição geral do formato de .heapsnapshot ficheiro

A memória utilizada por uma aplicação Web é organizada como um gráfico por V8, que é o motor JavaScript utilizado pelo Microsoft Edge. Um gráfico é um tipo de dados composto por nós (pontos no gráfico) e arestas (ligações entre os pontos).

Os dados no .heapsnapshot ficheiro representam a memória da aplicação Web que grafa de forma eficiente e facilitam a transferência de grupos de dados entre o processo do browser e as DevTools. O .heapsnapshot ficheiro contém uma representação simplificada das relações entre nós e arestas, como um objeto JSON que contém matrizes de números e cadeias. O ficheiro tem uma .heapsnapshot extensão de nome de ficheiro e contém dados formatados em JSON.

Os dados têm duas partes main:

  • Os metadados, que contêm todas as informações necessárias para analisar as matrizes de dados que representam o gráfico de memória.
  • Os dados das matrizes, que contêm os dados reais necessários para recriar o gráfico.

Atualizar esta documentação de formato de dados

O formato do .heapsnapshot ficheiro, conforme documentado abaixo, pode mudar à medida que v8 e DevTools evoluem. Se encontrar uma discrepância na documentação, forneça feedback no repositório MicrosoftDocs/edge-developer.

Esquema dos .heapsnapshot dados

Estrutura de nível superior

Os .heapsnapshot dados JSON contêm um objeto de raiz que tem as seguintes propriedades:

{
    "snapshot": {},
    "nodes": [],
    "edges": [],
    "trace_function_infos": [],
    "trace_tree": [],
    "samples": [],
    "locations": [],
    "strings": []
}
Propriedade Descrição Formatar
snapshot Contém todas as informações sobre o formato dos dados do gráfico de memória e o respetivo tamanho. Object
nodes Todas as informações necessárias para recriar os nós do gráfico. Para analisar estes dados, utilize snapshot.meta.node_types e snapshot.meta.node_fields. Array
edges Todas as informações necessárias para recriar as margens do gráfico. Para analisar estes dados, utilize snapshot.meta.edge_types e snapshot.meta.edge_fields. Array
trace_function_infos Ainda não documentado Array
trace_tree Ainda não documentado Array
samples Ainda não documentado Array
locations Contém informações sobre a localização do script dos nós. Para analisar estes dados, utilize snapshot.meta.location_fields com a nodes matriz . Array
strings Uma matriz de todas as cadeias que são mantidas na memória. Estas podem ser cadeias de carateres, como cadeias definidas pelo utilizador ou código. Array

Instantâneo

{
    "snapshot": {     
        "meta": {},
        "node_count": 123,
        "edge_count": 456,
        "trace_function_count": 0
    }
    ...
}
Propriedade Descrição Formatar
meta Propriedades que contêm informações sobre a forma e o tamanho de cada objeto contido nos dados do gráfico de memória. Object
node_count O número total de nós no gráfico de memória. Number
edge_count O número total de arestas no gráfico de memória. Number
trace_function_count O número total de funções de rastreio no gráfico de memória. Number

Metadados de instantâneo

{
    "snapshot": {
        "meta": {
            "node_fields": [],
            "node_types": [],
            "edge_fields": [],
            "edge_types": []
        }
    }
    ...
}
Propriedade Descrição Formatar
node_fields A lista de todas as propriedades necessárias para recriar um nó. Array
node_types Os tipos de todas as propriedades necessárias para recriar um nó. O número de tipos é o mesmo que o número de propriedades definidas em node_fields. Array
edge_fields A lista de todas as propriedades necessárias para recriar um edge. Array
edge_types Os tipos de todas as propriedades necessárias para recriar uma aresta. O número de tipos é o mesmo número de propriedades em edge_fields. Array

Segue-se um exemplo de um objeto de metadados:

{
    "snapshot": {
        "meta": {
            "node_fields": [
                "type",
                "name",
                "id",
                "self_size",
                "edge_count",
                "trace_node_id",
                "detachedness"
            ],
            "node_types": [
                [
                    "hidden",
                    "array",
                    "string",
                    "object",
                    "code",
                    "closure",
                    "regexp",
                    "number",
                    "native",
                    "synthetic",
                    "concatenated string",
                    "sliced string",
                    "symbol",
                    "bigint",
                    "object shape"
                ],
                "string",
                "number",
                "number",
                "number",
                "number",
                "number"
            ],
            "edge_fields": [
                "type",
                "name_or_index",
                "to_node"
            ],
            "edge_types": [
                [
                    "context",
                    "element",
                    "property",
                    "internal",
                    "hidden",
                    "shortcut",
                    "weak"
                ],
                "string_or_number",
                "node"
            ]
        }
    }
}

Nós

A nodes matriz, que está no nível superior dos .heapsnapshot dados, contém todas as informações necessárias para recriar os nós do gráfico de memória.

Para analisar esta matriz, são necessárias as seguintes informações:

  • snapshot.node_count, para saber quantos nós existem.
  • snapshot.meta.node_fields, para saber quantos campos cada nó tem.

Cada nó na matriz é representado por uma série de snapshot.meta.node_fields.length números. Assim, o número total de elementos na nodes matriz é snapshot.node_count multiplicado por snapshot.meta.node_fields.length.

Para recriar um nó, leia os números da nodes matriz por grupos de tamanho snapshot.meta.node_fields.length.

O fragmento de código seguinte mostra os node_fields metadados e os dados dos dois primeiros nós no gráfico:

{
    "snapshot": {
        "meta": {
            "node_fields": [
                "type",
                "name",
                "id",
                "self_size",
                "edge_count",
                "trace_node_id",
                "detachedness"
            ]
            ...
        }
        ...
    },
    "nodes": [
        9,1,1,0,10,0,0,
        2,1,79,12,1,0,0,
        ...
    ]
    ...
}
Índice no grupo de nós Nome Descrição
0 type O tipo de nó. Veja Tipos de nós abaixo.
1 name O nome do nó. Este é um número que é o índice na matriz de nível strings superior. Para localizar o nome real, utilize o número do índice para procurar a cadeia na matriz de nível strings superior.
2 id O ID exclusivo do nó.
3 self_size O tamanho do nó em bytes.
4 edge_count O número de arestas ligadas a este nó.
5 trace_node_id O ID do nó de rastreio
6 detachedness Se este nó pode ser alcançado a window partir do objeto global. 0 significa que o nó não está desanexado; o nó pode ser alcançado a window partir do objeto global. 1 significa que o nó está desanexado; não é possível aceder ao nó a window partir do objeto global.

Tipos de nós

O primeiro número no grupo de números de um nó na nodes matriz corresponde ao respetivo tipo. Este número é um índice que pode ser utilizado para procurar o nome do snapshot.meta.node_types[0] tipo na matriz.

Tipo de nó Descrição
Hidden Um elemento interno V8 que não corresponde diretamente a um objeto JavaScript controlável pelo utilizador. Nas DevTools, todas estas são apresentadas sob o nome da categoria (sistema). Embora estes objetos sejam internos, podem ser uma parte importante dos caminhos de retenção.
Objeto Qualquer objeto definido pelo utilizador, como { x: 2 } ou new Foo(4). Os contextos, que aparecem em DevTools como sistema/Contexto, contêm variáveis que tiveram de ser alocadas na área dinâmica para dados porque são utilizadas por uma função aninhada.
Nativo Itens que são alocados pelo motor de composição Blink, em vez de por V8. Trata-se principalmente de itens DOM, como HTMLDivElement ou CSSStyleRule.
Cadeia concatenada O resultado da concatenação de duas cadeias com o + operador . Em vez de criar uma nova cadeia que contém uma cópia de todos os dados das duas cadeias de origem, o V8 cria um ConsString objeto que contém ponteiros para as duas cadeias de origem. Do ponto de vista do JavaScript, funciona como qualquer outra cadeia, mas, do ponto de vista da criação de perfis de memória, é diferente.
Cadeia segmentada O resultado de uma operação de subcadeia, como utilizar String.prototype.substr ou String.prototype.substring. O V8 evita copiar dados de cadeia ao criar, em vez disso, um SlicedString, que aponta para a cadeia original e especifica o índice de início e o comprimento. Do ponto de vista do JavaScript, uma cadeia segmentada age como qualquer outra cadeia, mas, do ponto de vista da criação de perfis de memória, é diferente.
Matriz Várias listas internas, que são apresentadas em DevTools com o nome da categoria (matriz). Tal como Oculto, esta categoria agrupa uma variedade de itens. Muitos dos objetos aqui indicados têm o nome (propriedades do objeto) ou (elementos de objeto), o que indica que contêm as propriedades com chave de cadeia ou chave numérica de um objeto JavaScript.
Código Coisas que crescem proporcionalmente à quantidade de script e/ou ao número de vezes que as funções são executadas.
Sintético Os nós sintéticos não correspondem a nada realmente atribuído na memória. Estes são utilizados para distinguir os diferentes tipos de raízes de libertação da memória (GC).

Arestas

Semelhante à nodes matriz, a edges matriz de nível superior contém todos os elementos necessários para recriar as margens do gráfico de memória.

Também semelhante aos nós, o número total de arestas pode ser calculado multiplicando snapshot.edge_count por snapshot.meta.edge_fields.length. As arestas também são armazenadas como uma sequência de números, que terá de iterar por grupos de tamanho snapshot.meta.edge_fields.length.

No entanto, para ler a edges matriz corretamente, primeiro tem de ler a nodes matriz, uma vez que cada nó sabe quantas arestas tem.

Para recriar uma aresta, precisa de três informações:

  • O tipo de limite.
  • O nome ou índice do edge.
  • O nó ao qual a extremidade está ligada.

Por exemplo, se ler o primeiro nó na matriz e a nodes respetiva edge_count propriedade estiver definida como 4, os primeiros quatro grupos de snapshot.meta.edge_fields.length números na edges matriz correspondem às quatro margens deste nó.

Índice no grupo edge Nome Descrição
0 type O tipo de aresta. Veja Tipos de edge para saber quais são os tipos possíveis.
1 name_or_index Pode ser um número ou uma cadeia. Se for um número, corresponde ao índice na matriz de nível strings superior, onde o nome da margem pode ser encontrado.
2 to_node O índice dentro da nodes matriz à qual esta aresta está ligada.

Tipos de arestas

O primeiro número no grupo de números de uma margem na edges matriz corresponde ao respetivo tipo. Este número é um índice que pode ser utilizado para procurar o nome do snapshot.meta.edge_types[0] tipo na matriz.

Tipo de limite Descrição
Interno As arestas que não correspondem a nomes visíveis para JavaScript, mas que ainda são importantes. Por exemplo, as Instâncias de função têm um "contexto" que representa o estado das variáveis que estavam no âmbito onde a função foi definida. Não há forma de o código JavaScript ler diretamente o "contexto" de uma função, mas estas arestas são necessárias para investigar os retentores.
Fraco As arestas fracas não mantêm o nó ao qual estão ligados vivos e, portanto, são omitidos da vista Retentores. Qualquer objeto com apenas arestas fracas a apontar para o mesmo pode ser eliminado pela libertação da memória (GC).
Hidden Semelhante a Interno, exceto que estas arestas não têm nomes exclusivos e, em vez disso, são numeradas por ordem crescente.
Shortcut Uma representação mais fácil de ler de outro caminho. Este tipo raramente é utilizado. Por exemplo, se utilizar Function.prototype.bind para criar uma função vinculada com alguns argumentos vinculados, v8 cria um JSBoundFunction, que aponta para um (um FixedArray tipo interno), que aponta para cada argumento vinculado. Ao produzir um snapshot, o V8 adiciona um limite de atalho da função vinculada diretamente a cada argumento vinculado, ignorando o FixedArray.
Elemento Propriedades do objeto em que a chave é um número.

locations

A locations matriz, que está no nível superior dos .heapsnapshot dados, contém informações sobre onde alguns dos nós na snapshot foram criados. Esta matriz consiste numa série de números destinados a serem lidos por grupos de tamanho snapshot.meta.location_fields.length. Por conseguinte, iremos snapshot.meta.location_fields saber quantos campos cada localização na locations matriz tem e quais são esses campos. Por exemplo, se location_fields contiver 4 itens, a locations matriz deve ser lida por grupos de 4.

snapshot.meta.location_fields contém as informações para cada localização:

Indexar em location_fields Nome Descrição
0 object_index O índice do nó na snapshot.nodes matriz associada a esta localização.
1 script_id O ID do script que cria o nó associado.
2 line O número de linha onde o nó foi criado, dentro do script que criou o nó.
3 column O número da coluna onde o nó foi criado, dentro do script que criou o nó.

O exemplo de código seguinte mostra como ligar a snapshot.locations matriz à snapshot.nodes matriz:

{
    "snapshot": {
        "meta": {
            "location_fields": [
                "object_index",
                "script_id",
                "line",
                "column"
            ]
            ...
        }
        ...
    },
    "nodes": [
        9,1,1,0,10,0,0,
        2,1,79,12,1,0,0,
        ...
    ],
    "locations":[
        7,9,0,0,
        113792,3,25,21,
        ...
    ],
    ...
}

A primeira localização na locations matriz é 7,9,0,0,. Esta localização está associada ao grupo de informações do nó que começa no índice 7 na nodes matriz. Por conseguinte, o nó contém os seguintes pares chave/valor:

"type": 2,
"name": 1,
"id": 79,
"self_size": 12,
"edge_count": 1,
"trace_node_id": 0,
"detachedness": 0,
"script_id": 9,
"line" 0,
"column": 0,

Confira também

Para saber mais sobre o formato de .heapsnapshot ficheiro, veja o código que gera o ficheiro, que é a HeapSnapshotGenerator classe em heap-snapshot-generator.h.