json-summary
Advanced tools
Comparing version 0.2.5 to 1.0.0
@@ -1,409 +0,432 @@ | ||
// https://andrewtburks.dev/json-summary v0.2.5 Copyright 2019 Andrew Burks | ||
// https://andrewtburks.dev/json-summary v1.0.0 Copyright 2019 Andrew Burks | ||
(function (global, factory) { | ||
typeof exports === 'object' && typeof module !== 'undefined' ? module.exports = factory() : | ||
typeof define === 'function' && define.amd ? define(factory) : | ||
(global = global || self, global.jsonSummary = factory()); | ||
}(this, function () { 'use strict'; | ||
typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports) : | ||
typeof define === 'function' && define.amd ? define(['exports'], factory) : | ||
(global = global || self, factory(global.jsonSummary = {})); | ||
}(this, function (exports) { 'use strict'; | ||
const summarizer = (function() { | ||
let defaultOptions = { | ||
arraySampleCount: 10, | ||
indentation: " ", // or "\t" | ||
indentCount: 2, | ||
showExampleValue: true, | ||
startExpanded: false, | ||
theme: "dark" | ||
}; | ||
var defaults = { | ||
arraySampleCount: 10, | ||
indentation: " ", // or "\t" | ||
indentCount: 2, | ||
showExampleValue: true, | ||
startExpanded: false, | ||
theme: "dark" | ||
}; | ||
// summarizer utility class | ||
return function({ | ||
arraySampleCount = 10, | ||
indentation = " ", // or "\t" | ||
indentCount = 2, | ||
showExampleValue = true, | ||
startExpanded = false, | ||
theme = "dark" | ||
} = defaultOptions) { | ||
let defaultSummOpt = { | ||
arraySampleCount: defaults.arraySampleCount | ||
}; | ||
let options = { | ||
arraySampleCount, | ||
indentation, | ||
indentCount, | ||
showExampleValue, | ||
startExpanded, | ||
theme | ||
}; | ||
// utility function to extract overall json structure without printing entire data object | ||
function summarizeJSON(data, { | ||
arraySampleCount = defaultSummOpt.arraySampleCount | ||
} = defaultSummOpt) { | ||
let summary = summarizeItem(data); | ||
// clean up the marking | ||
unmarkObject(data); | ||
return summary; | ||
// utility function to extract overall json structure without printing entire data object | ||
function summarizeJSON(data) { | ||
let summary = summarizeItem(data); | ||
function summarizeItem(item) { | ||
let summarize = { | ||
Array: arr => { | ||
let summarized = { | ||
count: 1, | ||
type: "Array", | ||
length: arr.length | ||
}; | ||
// recurse to items in the array | ||
if (arr.length) { | ||
if (arraySampleCount > 0) { | ||
let numToSample = arraySampleCount === "all" ? arr.length : Math.min(arraySampleCount, arr.length); | ||
let sampledItems = {}; | ||
// summarized.count = numToSample; | ||
// clean up the marking | ||
unmarkObject(data); | ||
while (numToSample > 0) { | ||
let sampleIndex = Math.floor(Math.random() * arr.length); | ||
return summary; | ||
} | ||
function summarizeItem(item) { | ||
let summarize = { | ||
Array: arr => { | ||
let summarized = { | ||
count: 1, | ||
type: "Array", | ||
length: arr.length | ||
}; | ||
// recurse to items in the array | ||
if (arr.length) { | ||
if (arraySampleCount > 0) { | ||
let numToSample = Math.min(arraySampleCount, arr.length); | ||
let sampledItems = {}; | ||
// summarized.count = numToSample; | ||
while (numToSample > 0) { | ||
let sampleIndex = Math.floor(Math.random() * arr.length); | ||
if (!sampledItems.hasOwnProperty(sampleIndex)) { | ||
sampledItems[sampleIndex] = arr[sampleIndex]; | ||
numToSample--; | ||
} | ||
if (!sampledItems.hasOwnProperty(sampleIndex)) { | ||
sampledItems[sampleIndex] = arr[sampleIndex]; | ||
numToSample--; | ||
} | ||
} | ||
let summarizedSamples = []; | ||
let summarizedSamples = []; | ||
for (let [idx, item] of Object.entries(sampledItems)) { | ||
summarizedSamples.push(summarizeItem(item)); | ||
} | ||
for (let pair of Object.entries(sampledItems)) { | ||
let item = pair[1]; | ||
let joinedSample = joinSampledArray(summarizedSamples); | ||
summarized.items = { | ||
0: joinedSample | ||
}; | ||
} else { | ||
// sumamrized.count = 1; | ||
summarized.items = { | ||
0: summarizeItem(arr[0]) | ||
}; | ||
summarizedSamples.push(summarizeItem(item)); | ||
} | ||
let joinedSample = joinSampledArray(summarizedSamples); | ||
summarized.items = { | ||
0: joinedSample | ||
}; | ||
} else { | ||
// sumamrized.count = 1; | ||
summarized.items = { | ||
0: undefined | ||
0: summarizeItem(arr[0]) | ||
}; | ||
} | ||
return summarized; | ||
}, | ||
Object: obj => { | ||
let summarized = { | ||
count: 1, | ||
type: "Object", | ||
keys: Object.keys(obj), | ||
items: {} | ||
} else { | ||
summarized.items = { | ||
0: undefined | ||
}; | ||
} | ||
for (let key of summarized.keys) { | ||
summarized.items[key] = summarizeItem(obj[key]); | ||
} | ||
return summarized; | ||
}, | ||
Other: data => { | ||
let range; | ||
return summarized; | ||
}, | ||
Object: obj => { | ||
let summarized = { | ||
count: 1, | ||
type: "Object", | ||
keys: Object.keys(obj), | ||
items: {} | ||
}; | ||
if (typeof data === "string") { | ||
range = [data.length, data.length]; | ||
} else if (typeof data === "number") { | ||
range = [data, data]; | ||
} | ||
for (let key of summarized.keys) { | ||
summarized.items[key] = summarizeItem(obj[key]); | ||
} | ||
return { | ||
type: typeof data, | ||
example: data, | ||
count: 1, | ||
range | ||
}; | ||
return summarized; | ||
}, | ||
Other: data => { | ||
let range; | ||
if (typeof data === "string") { | ||
range = [data.length, data.length]; | ||
} else if (typeof data === "number") { | ||
range = [data, data]; | ||
} | ||
}; | ||
let type = "Other"; | ||
if (item instanceof Array) { | ||
type = "Array"; | ||
} else if (item instanceof Object) { | ||
type = "Object"; | ||
} | ||
if (item && item["*snippets_mark*"]) { | ||
return { | ||
type: type, | ||
circular: true | ||
type: typeof data, | ||
example: data, | ||
count: 1, | ||
range | ||
}; | ||
} else { | ||
// marked as visited to make sure it doesn't hit a circular structure | ||
if (type !== "Other") { | ||
Object.defineProperty(item, "*snippets_mark*", { | ||
enumerable: false, | ||
writable: true, | ||
configurable: true | ||
}); | ||
item["*snippets_mark*"] = true; | ||
} | ||
return summarize[type](item); | ||
} | ||
}; | ||
let type = "Other"; | ||
if (item instanceof Array) { | ||
type = "Array"; | ||
} else if (item instanceof Object) { | ||
type = "Object"; | ||
} | ||
function joinSampledArray(itemset) { | ||
// let type = itemset.map(d => d.type) | ||
// .reduce((a, type) => { | ||
// a[type] = []; | ||
// return a; | ||
// }, {}); | ||
// for (let item of itemset) { | ||
// type[item.type].push(item); | ||
// } | ||
if (item && item["*snippets_mark*"]) { | ||
return { | ||
type: type, | ||
circular: true | ||
}; | ||
} else { | ||
// marked as visited to make sure it doesn't hit a circular structure | ||
if (type !== "Other") { | ||
Object.defineProperty(item, "*snippets_mark*", { | ||
enumerable: false, | ||
writable: true, | ||
configurable: true | ||
}); | ||
item["*snippets_mark*"] = true; | ||
} | ||
// let joins = {}; | ||
return summarize[type](item); | ||
} | ||
} | ||
// for (let [t, itemset] of Object.entries(type)) { | ||
// joins[t] = joinItems(itemset, t); | ||
// } | ||
function joinSampledArray(itemset) { | ||
// let type = itemset.map(d => d.type) | ||
// .reduce((a, type) => { | ||
// a[type] = []; | ||
// return a; | ||
// }, {}); | ||
// console.log(joins); | ||
// for (let item of itemset) { | ||
// type[item.type].push(item); | ||
// } | ||
// return | ||
// let joins = {}; | ||
// assume theyre all a matching type | ||
// for (let [t, itemset] of Object.entries(type)) { | ||
// joins[t] = joinItems(itemset, t); | ||
// } | ||
let joinableTypes = {Array: true, Object: true, boolean: true, string: true, number: true}; | ||
let items = itemset.filter(i => joinableTypes[i.type]); | ||
// console.log(joins); | ||
if (items.length) { | ||
let type = items[0].type; | ||
return joinItems(items.filter(i => i.type === type), type); | ||
} else { | ||
// idk - no items to join? | ||
return { | ||
count: 0 | ||
}; | ||
} | ||
// return | ||
// assume theyre all a matching type | ||
let joinableTypes = {Array: true, Object: true, boolean: true, string: true, number: true}; | ||
let items = itemset.filter(i => joinableTypes[i.type]); | ||
if (items.length) { | ||
let type = items[0].type; | ||
return joinItems(items.filter(i => i.type === type), type); | ||
} else { | ||
// idk - no items to join? | ||
return { | ||
count: 0 | ||
}; | ||
} | ||
function joinItems(itemArr, type) { | ||
itemArr = itemArr.filter(i => i.type === type); | ||
} | ||
// functions to join items by type | ||
let joiner = { | ||
string: function(items) { | ||
// string length range | ||
let min = items.reduce((acc, item) => { | ||
return Math.min(acc, item.range[0]); | ||
}, Infinity); | ||
function joinItems(itemArr, type) { | ||
itemArr = itemArr.filter(i => i.type === type); | ||
let max = items.reduce((acc, item) => { | ||
return Math.max(acc, item.range[1]); | ||
}, -Infinity); | ||
// functions to join items by type | ||
let joiner = { | ||
string: function(items) { | ||
// string length range | ||
let min = items.reduce((acc, item) => { | ||
return Math.min(acc, item.range[0]); | ||
}, Infinity); | ||
let joinedString = { | ||
type: "string", | ||
example: items[0].example, | ||
range: [min, max], | ||
count: items.reduce((a, i) => a + i.count, 0) | ||
}; | ||
let max = items.reduce((acc, item) => { | ||
return Math.max(acc, item.range[1]); | ||
}, -Infinity); | ||
return joinedString; | ||
}, | ||
number: function(items) { | ||
let min = items.reduce((acc, item) => { | ||
return Math.min(acc, item.range[0]); | ||
}, Infinity); | ||
let joinedString = { | ||
type: "string", | ||
example: items[0].example, | ||
range: [min, max], | ||
count: items.reduce((a, i) => a + i.count, 0) | ||
}; | ||
let max = items.reduce((acc, item) => { | ||
return Math.max(acc, item.range[1]); | ||
}, -Infinity); | ||
return joinedString; | ||
}, | ||
number: function(items) { | ||
let min = items.reduce((acc, item) => { | ||
return Math.min(acc, item.range[0]); | ||
}, Infinity); | ||
let joinedNumber = { | ||
type: "number", | ||
example: items[0].example, | ||
range: [min, max], | ||
count: items.reduce((a, i) => a + i.count, 0) | ||
}; | ||
let max = items.reduce((acc, item) => { | ||
return Math.max(acc, item.range[1]); | ||
}, -Infinity); | ||
return joinedNumber; | ||
}, | ||
boolean: function(items) { | ||
return { | ||
type: "boolean", | ||
example: items[0].example, | ||
count: items.reduce((a, i) => a + i.count, 0) | ||
}; | ||
}, | ||
Object: function(items) { | ||
let masterKeys = {}; | ||
let joinedNumber = { | ||
type: "number", | ||
example: items[0].example, | ||
range: [min, max], | ||
count: items.reduce((a, i) => a + i.count, 0) | ||
}; | ||
for (let obj of items) { | ||
if (!obj.circular) { | ||
for (let key of obj.keys) { | ||
!masterKeys[key] && (masterKeys[key] = []); | ||
return joinedNumber; | ||
}, | ||
boolean: function(items) { | ||
return { | ||
type: "boolean", | ||
example: items[0].example, | ||
count: items.reduce((a, i) => a + i.count, 0) | ||
}; | ||
}, | ||
Object: function(items) { | ||
let masterKeys = {}; | ||
masterKeys[key].push(obj.items[key]); | ||
} | ||
for (let obj of items) { | ||
if (!obj.circular) { | ||
for (let key of obj.keys) { | ||
!masterKeys[key] && (masterKeys[key] = []); | ||
masterKeys[key].push(obj.items[key]); | ||
} | ||
} | ||
} | ||
let joinedObject = { type: "Object", keys: [], items: {}, count: items.length }; | ||
let joinedObject = { type: "Object", keys: [], items: {}, count: items.length }; | ||
for (let key of Object.keys(masterKeys)) { | ||
joinedObject.keys.push(key); | ||
for (let key of Object.keys(masterKeys)) { | ||
joinedObject.keys.push(key); | ||
joinedObject.items[key] = joinSampledArray(masterKeys[key]); | ||
} | ||
joinedObject.items[key] = joinSampledArray(masterKeys[key]); | ||
} | ||
return joinedObject; | ||
}, | ||
Array: function(items) { | ||
let joinedValues = joinSampledArray(items.map(i => i.items[0]).filter(i => i)); | ||
return joinedObject; | ||
}, | ||
Array: function(items) { | ||
let joinedValues = joinSampledArray(items.map(i => i.items[0]).filter(i => i)); | ||
let joinedArray = { | ||
count: items.length, | ||
items: { | ||
0: joinedValues | ||
}, | ||
length: joinedValues.count / items.length, | ||
type: "Array" | ||
}; | ||
let joinedArray = { | ||
count: items.length, | ||
items: { | ||
0: joinedValues | ||
}, | ||
length: joinedValues.count / items.length, | ||
type: "Array" | ||
}; | ||
return joinedArray; | ||
} | ||
}; | ||
return joinedArray; | ||
} | ||
}; | ||
return joiner[type](itemArr); | ||
} | ||
return joiner[type](itemArr); | ||
} | ||
function unmarkObject(obj) { | ||
if (obj && obj["*snippets_mark*"]) { | ||
delete obj["*snippets_mark*"]; | ||
// recurse to the next level | ||
if (obj instanceof Array && obj.length) { | ||
unmarkObject(obj[0]); | ||
} else if (obj instanceof Object) { | ||
for (let key of Object.keys(obj)) { | ||
unmarkObject(obj[key]); | ||
} | ||
function unmarkObject(obj) { | ||
if (obj && obj["*snippets_mark*"]) { | ||
delete obj["*snippets_mark*"]; | ||
// recurse to the next level | ||
if (obj instanceof Array && obj.length) { | ||
unmarkObject(obj[0]); | ||
} else if (obj instanceof Object) { | ||
for (let key of Object.keys(obj)) { | ||
unmarkObject(obj[key]); | ||
} | ||
} | ||
} | ||
} | ||
} | ||
// utility function to stringify the summary output from summarizeJSON | ||
function printSummarizedJSON(summary) { | ||
// start at 0 indentation | ||
return `<div class='json-summary-wrapper ${options.theme}'>` + printSummaryLevel(summary, 0, 1); | ||
} | ||
function printSummaryLevel(data, l, prevCount) { | ||
let string = ""; | ||
if (data.circular) { | ||
string += wrapInHTML("(circular reference)", "circular"); | ||
} else if (data.type === "Object") { | ||
string += "{"; | ||
let keys = data.keys.map(k => `'${k}'`).join(", "); | ||
string += wrapInHTML(keys, "keys"); | ||
let childStrings = data.keys.map(key => { | ||
return printSummaryLevel(data.items[key], l + 1, data.count); | ||
}); | ||
if (childStrings.length) { | ||
let childStringCombined = "\n"; | ||
for (let i = 0; i < data.keys.length; i++) { | ||
childStringCombined += options.indentation.repeat( | ||
(l + 1) * options.indentCount | ||
var summarize = summarizeJSON; | ||
let defaultPrintOpt = { | ||
indentation: defaults.indentation, // or "\t" | ||
indentCount: defaults.indentCount, | ||
showExampleValue: defaults.showExampleValue, | ||
startExpanded: defaults.startExpanded, | ||
theme: defaults.theme | ||
}; | ||
// utility function to stringify the summary output from summarizeJSON | ||
function printSummarizedJSON( | ||
summary, | ||
{ | ||
indentation = defaultPrintOpt.indentation, // or "\t" | ||
indentCount = defaultPrintOpt.indentCount, | ||
showExampleValue = defaultPrintOpt.showExampleValue, | ||
startExpanded = defaultPrintOpt.startExpanded, | ||
theme = defaultPrintOpt.theme | ||
} = defaultPrintOpt | ||
) { | ||
// start at 0 indentation | ||
return ( | ||
`<div class="theme ${theme}"><div class='json-summary-wrapper'>` + | ||
printSummaryLevel(summary, 0) + | ||
`<div></div>` | ||
); | ||
function printSummaryLevel(data, l) { | ||
let string = ""; | ||
if (data.circular) { | ||
string += wrapInHTML("(circular reference)", "circular"); | ||
} else if (data.type === "Object") { | ||
string += "{"; | ||
let keys = data.keys.map(k => `'${k}'`).join(", "); | ||
string += wrapInHTML(keys, "keys"); | ||
let childStrings = data.keys.map(key => { | ||
return printSummaryLevel(data.items[key], l + 1); | ||
}); | ||
if (childStrings.length) { | ||
let childStringCombined = "\n"; | ||
for (let i = 0; i < data.keys.length; i++) { | ||
childStringCombined += indentation.repeat((l + 1) * indentCount); | ||
childStringCombined += wrapInHTML(data.keys[i], "name") + ": "; | ||
if (data.count > 1) { | ||
childStringCombined += htmlPercentageBar( | ||
(data.items[data.keys[i]].count / data.count) * 100 | ||
); | ||
childStringCombined += wrapInHTML(data.keys[i], "name") + ": "; | ||
} | ||
if (data.count > 1) { | ||
childStringCombined += htmlPercentageBar(data.items[data.keys[i]].count / data.count * 100); | ||
} | ||
childStringCombined += childStrings[i]; | ||
if (i < data.keys.length - 1) { | ||
childStringCombined += ","; | ||
} | ||
childStringCombined += "\n"; | ||
childStringCombined += childStrings[i]; | ||
if (i < data.keys.length - 1) { | ||
childStringCombined += ","; | ||
} | ||
childStringCombined += options.indentation.repeat(l * options.indentCount); | ||
string += wrapInHTML(childStringCombined, "child"); | ||
childStringCombined += "\n"; | ||
} | ||
string += "}"; | ||
string = wrapInHTML(string, "layer"); | ||
} else if (data.type === "Array") { | ||
// string += "[]"; | ||
// string += `[ ${data.length ? `(${data.length}×)` : "∅"} `; | ||
string += wrapInHTML(data.count > 1 ? "μ = " + data.length.toFixed(1) : data.length, "length") + ` [`; | ||
if (data.length) { | ||
let needsNewlines = | ||
data.items["0"].type === "Object" || data.items["0"].type === "Array"; | ||
if (needsNewlines) { | ||
string += "\n" + options.indentation.repeat((l + 1) * options.indentCount); | ||
} | ||
string += printSummaryLevel(data.items["0"], l + 1, data.count); | ||
if (needsNewlines) { | ||
string += "\n" + options.indentation.repeat(l * options.indentCount); | ||
} | ||
childStringCombined += indentation.repeat(l * indentCount); | ||
string += wrapInHTML(childStringCombined, "child"); | ||
} | ||
string += "}"; | ||
string = wrapInHTML(string, "layer"); | ||
} else if (data.type === "Array") { | ||
// string += "[]"; | ||
// string += `[ ${data.length ? `(${data.length}×)` : "∅"} `; | ||
string += | ||
wrapInHTML( | ||
data.count > 1 ? "μ = " + data.length.toFixed(1) : data.length, | ||
"length" | ||
) + ` [`; | ||
if (data.length) { | ||
let needsNewlines = | ||
data.items["0"].type === "Object" || data.items["0"].type === "Array"; | ||
if (needsNewlines) { | ||
string += "\n" + indentation.repeat((l + 1) * indentCount); | ||
} | ||
string += "]"; | ||
// string = wrapInHTML(string, "layer"); | ||
} else { | ||
if (data.example == null || data.example == undefined) { | ||
string += wrapInHTML("?", "type"); | ||
} else { | ||
string += wrapInHTML(data.type, "type"); | ||
string += printSummaryLevel(data.items["0"], l + 1, data.count); | ||
if (needsNewlines) { | ||
string += "\n" + indentation.repeat(l * indentCount); | ||
} | ||
if (options.showExampleValue) { | ||
string += wrapInHTML(data.example, "value", data.type); | ||
data.count > 1 && data.range && (string += wrapInHTML(data.range, "range", data.type)); | ||
} | ||
} | ||
return string; | ||
string += "]"; | ||
// string = wrapInHTML(string, "layer"); | ||
} else { | ||
if (data.example == null || data.example == undefined) { | ||
string += wrapInHTML("?", "type"); | ||
} else { | ||
string += wrapInHTML(data.type, "type"); | ||
} | ||
if (showExampleValue) { | ||
string += wrapInHTML(data.example, "value", data.type); | ||
data.count > 1 && | ||
data.range && | ||
(string += wrapInHTML(data.range, "range", data.type)); | ||
} | ||
} | ||
function wrapInHTML(value, role, type) { | ||
let tags = { | ||
type: () => `<span class="json-summary json-summary-type json-summary-type-${value}"><${value}></span>`, | ||
value: () => `<span class="json-summary json-summary-value json-summary-value-${type}">${value}</span>`, | ||
range: () => `<span class="json-summary json-summary-range json-summary-range-${type}">[${value[0]}, ${value[1]}]</span>`, | ||
name: () => `<span class="json-summary json-summary-name">${value}</span>`, | ||
length: () => `<span class="json-summary json-summary-length">(${value})</span>`, | ||
circular: () => `<span class="json-summary json-summary-circular">${value}</span>`, | ||
layer: () => `<span class="json-summary json-summary-checkbox ${ | ||
options.startExpanded ? "checked" : "" | ||
}"> | ||
<input type="checkbox" ${ | ||
options.startExpanded ? "checked" : "" | ||
}> | ||
return string; | ||
} | ||
function wrapInHTML(value, role, type) { | ||
let tags = { | ||
type: () => | ||
`<span class="json-summary json-summary-type json-summary-type-${value}"><${value}></span>`, | ||
value: () => | ||
`<span class="json-summary json-summary-value json-summary-value-${type}">${value}</span>`, | ||
range: () => | ||
`<span class="json-summary json-summary-range json-summary-range-${type}">[${ | ||
value[0] | ||
}, ${value[1]}]</span>`, | ||
name: () => `<span class="json-summary json-summary-name">${value}</span>`, | ||
length: () => | ||
`<span class="json-summary json-summary-length">(${value})</span>`, | ||
circular: () => | ||
`<span class="json-summary json-summary-circular">${value}</span>`, | ||
layer: () => `<span class="json-summary json-summary-checkbox ${ | ||
startExpanded ? "checked" : "" | ||
}"> | ||
<input type="checkbox" ${startExpanded ? "checked" : ""}> | ||
<span class="json-summary-checkboxmarker" onclick="(function(me){ | ||
@@ -413,24 +436,34 @@ me.parentNode.classList.toggle('checked'); | ||
</span><div class="json-summary json-summary-layer">${value}</div>`, | ||
child: () => `<div class="json-summary json-summary-child">${value}</div>`, | ||
keys: () => `<span class="json-summary json-summary-keys">${value}</span>` | ||
}; | ||
child: () => `<div class="json-summary json-summary-child">${value}</div>`, | ||
keys: () => `<span class="json-summary json-summary-keys">${value}</span>` | ||
}; | ||
return tags[role](); | ||
} | ||
return tags[role](); | ||
} | ||
function htmlPercentageBar(percentage) { | ||
return `<div class="json-summary json-summary-bar" title="${percentage.toFixed(2)}%"><div class="json-summary json-summary-percentage" style="width:${percentage}%;"></div></div>` | ||
} | ||
return { | ||
summarize: summarizeJSON, | ||
printSummary: printSummarizedJSON | ||
}; | ||
function htmlPercentageBar(percentage) { | ||
return `<div class="json-summary json-summary-bar" title="${percentage.toFixed( | ||
2 | ||
)}%"><div class="json-summary json-summary-percentage" style="width:${percentage}%;"></div></div>`; | ||
} | ||
}()); | ||
} | ||
var jsonSummary = summarizer; | ||
var printSummary = printSummarizedJSON; | ||
return jsonSummary; | ||
var jsonSummary = { | ||
defaults: defaults, | ||
summarize: summarize, | ||
printSummary: printSummary | ||
}; | ||
var jsonSummary_1 = jsonSummary.defaults; | ||
var jsonSummary_2 = jsonSummary.summarize; | ||
var jsonSummary_3 = jsonSummary.printSummary; | ||
exports.default = jsonSummary; | ||
exports.defaults = jsonSummary_1; | ||
exports.printSummary = jsonSummary_3; | ||
exports.summarize = jsonSummary_2; | ||
Object.defineProperty(exports, '__esModule', { value: true }); | ||
})); |
@@ -1,2 +0,2 @@ | ||
// https://andrewtburks.dev/json-summary v0.2.5 Copyright 2019 Andrew Burks | ||
!function(e,t){"object"==typeof exports&&"undefined"!=typeof module?module.exports=t():"function"==typeof define&&define.amd?define(t):(e=e||self).jsonSummary=t()}(this,function(){"use strict";return function(){let e={arraySampleCount:10,indentation:" ",indentCount:2,showExampleValue:!0,startExpanded:!1,theme:"dark"};return function({arraySampleCount:t=10,indentation:n=" ",indentCount:r=2,showExampleValue:a=!0,startExpanded:s=!1,theme:o="dark"}=e){let u={arraySampleCount:t,indentation:n,indentCount:r,showExampleValue:a,startExpanded:s,theme:o};function l(e){let t={Array:!0,Object:!0,boolean:!0,string:!0,number:!0},n=e.filter(e=>t[e.type]);if(n.length){let e=n[0].type;return function(e,t){return e=e.filter(e=>e.type===t),{string:function(e){let t=e.reduce((e,t)=>Math.min(e,t.range[0]),1/0),n=e.reduce((e,t)=>Math.max(e,t.range[1]),-1/0);return{type:"string",example:e[0].example,range:[t,n],count:e.reduce((e,t)=>e+t.count,0)}},number:function(e){let t=e.reduce((e,t)=>Math.min(e,t.range[0]),1/0),n=e.reduce((e,t)=>Math.max(e,t.range[1]),-1/0);return{type:"number",example:e[0].example,range:[t,n],count:e.reduce((e,t)=>e+t.count,0)}},boolean:function(e){return{type:"boolean",example:e[0].example,count:e.reduce((e,t)=>e+t.count,0)}},Object:function(e){let t={};for(let n of e)if(!n.circular)for(let e of n.keys)!t[e]&&(t[e]=[]),t[e].push(n.items[e]);let n={type:"Object",keys:[],items:{},count:e.length};for(let e of Object.keys(t))n.keys.push(e),n.items[e]=l(t[e]);return n},Array:function(e){let t=l(e.map(e=>e.items[0]).filter(e=>e));return{count:e.length,items:{0:t},length:t.count/e.length,type:"Array"}}}[t](e)}(n.filter(t=>t.type===e),e)}return{count:0}}function i(e,t,n){return{type:()=>`<span class="json-summary json-summary-type json-summary-type-${e}"><${e}></span>`,value:()=>`<span class="json-summary json-summary-value json-summary-value-${n}">${e}</span>`,range:()=>`<span class="json-summary json-summary-range json-summary-range-${n}">[${e[0]}, ${e[1]}]</span>`,name:()=>`<span class="json-summary json-summary-name">${e}</span>`,length:()=>`<span class="json-summary json-summary-length">(${e})</span>`,circular:()=>`<span class="json-summary json-summary-circular">${e}</span>`,layer:()=>`<span class="json-summary json-summary-checkbox ${u.startExpanded?"checked":""}">\n <input type="checkbox" ${u.startExpanded?"checked":""}>\n <span class="json-summary-checkboxmarker" onclick="(function(me){\n me.parentNode.classList.toggle('checked');\n })(this)"></span>\n </span><div class="json-summary json-summary-layer">${e}</div>`,child:()=>`<div class="json-summary json-summary-child">${e}</div>`,keys:()=>`<span class="json-summary json-summary-keys">${e}</span>`}[t]()}return{summarize:function(e){let n=function e(n){let r={Array:n=>{let r={count:1,type:"Array",length:n.length};if(n.length)if(t>0){let a=Math.min(t,n.length),s={};for(;a>0;){let e=Math.floor(Math.random()*n.length);s.hasOwnProperty(e)||(s[e]=n[e],a--)}let o=[];for(let[t,n]of Object.entries(s))o.push(e(n));let u=l(o);r.items={0:u}}else r.items={0:e(n[0])};else r.items={0:void 0};return r},Object:t=>{let n={count:1,type:"Object",keys:Object.keys(t),items:{}};for(let r of n.keys)n.items[r]=e(t[r]);return n},Other:e=>{let t;return"string"==typeof e?t=[e.length,e.length]:"number"==typeof e&&(t=[e,e]),{type:typeof e,example:e,count:1,range:t}}},a="Other";return n instanceof Array?a="Array":n instanceof Object&&(a="Object"),n&&n["*snippets_mark*"]?{type:a,circular:!0}:("Other"!==a&&(Object.defineProperty(n,"*snippets_mark*",{enumerable:!1,writable:!0,configurable:!0}),n["*snippets_mark*"]=!0),r[a](n))}(e);return function e(t){if(t&&t["*snippets_mark*"])if(delete t["*snippets_mark*"],t instanceof Array&&t.length)e(t[0]);else if(t instanceof Object)for(let n of Object.keys(t))e(t[n])}(e),n},printSummary:function(e){return`<div class='json-summary-wrapper ${u.theme}'>`+function e(t,n,r){let a="";if(t.circular)a+=i("(circular reference)","circular");else if("Object"===t.type){a+="{";let r=t.keys.map(e=>`'${e}'`).join(", ");a+=i(r,"keys");let o=t.keys.map(r=>e(t.items[r],n+1,t.count));if(o.length){let e="\n";for(let r=0;r<t.keys.length;r++)e+=u.indentation.repeat((n+1)*u.indentCount),e+=i(t.keys[r],"name")+": ",t.count>1&&(e+=`<div class="json-summary json-summary-bar" title="${(s=t.items[t.keys[r]].count/t.count*100).toFixed(2)}%"><div class="json-summary json-summary-percentage" style="width:${s}%;"></div></div>`),e+=o[r],r<t.keys.length-1&&(e+=","),e+="\n";e+=u.indentation.repeat(n*u.indentCount),a+=i(e,"child")}a=i(a+="}","layer")}else if("Array"===t.type){if(a+=i(t.count>1?"μ = "+t.length.toFixed(1):t.length,"length")+" [",t.length){let r="Object"===t.items[0].type||"Array"===t.items[0].type;r&&(a+="\n"+u.indentation.repeat((n+1)*u.indentCount)),a+=e(t.items[0],n+1,t.count),r&&(a+="\n"+u.indentation.repeat(n*u.indentCount))}a+="]"}else null==t.example||null==t.example?a+=i("?","type"):a+=i(t.type,"type"),u.showExampleValue&&(a+=i(t.example,"value",t.type),t.count>1&&t.range&&(a+=i(t.range,"range",t.type)));var s;return a}(e,0)}}}}()}); | ||
// https://andrewtburks.dev/json-summary v1.0.0 Copyright 2019 Andrew Burks | ||
!function(e,t){"object"==typeof exports&&"undefined"!=typeof module?t(exports):"function"==typeof define&&define.amd?define(["exports"],t):t((e=e||self).jsonSummary={})}(this,function(e){"use strict";var t={arraySampleCount:10,indentation:" ",indentCount:2,showExampleValue:!0,startExpanded:!1,theme:"dark"};let n={arraySampleCount:t.arraySampleCount};let a={indentation:t.indentation,indentCount:t.indentCount,showExampleValue:t.showExampleValue,startExpanded:t.startExpanded,theme:t.theme};var r={defaults:t,summarize:function(e,{arraySampleCount:t=n.arraySampleCount}=n){let a=function e(n){let a={Array:n=>{let a={count:1,type:"Array",length:n.length};if(n.length)if(t>0){let s="all"===t?n.length:Math.min(t,n.length),l={};for(;s>0;){let e=Math.floor(Math.random()*n.length);l.hasOwnProperty(e)||(l[e]=n[e],s--)}let u=[];for(let t of Object.entries(l)){let n=t[1];u.push(e(n))}let m=r(u);a.items={0:m}}else a.items={0:e(n[0])};else a.items={0:void 0};return a},Object:t=>{let n={count:1,type:"Object",keys:Object.keys(t),items:{}};for(let a of n.keys)n.items[a]=e(t[a]);return n},Other:e=>{let t;return"string"==typeof e?t=[e.length,e.length]:"number"==typeof e&&(t=[e,e]),{type:typeof e,example:e,count:1,range:t}}},s="Other";return n instanceof Array?s="Array":n instanceof Object&&(s="Object"),n&&n["*snippets_mark*"]?{type:s,circular:!0}:("Other"!==s&&(Object.defineProperty(n,"*snippets_mark*",{enumerable:!1,writable:!0,configurable:!0}),n["*snippets_mark*"]=!0),a[s](n))}(e);return function e(t){if(t&&t["*snippets_mark*"])if(delete t["*snippets_mark*"],t instanceof Array&&t.length)e(t[0]);else if(t instanceof Object)for(let n of Object.keys(t))e(t[n])}(e),a;function r(e){let t={Array:!0,Object:!0,boolean:!0,string:!0,number:!0},n=e.filter(e=>t[e.type]);if(n.length){let e=n[0].type;return function(e,t){return e=e.filter(e=>e.type===t),{string:function(e){let t=e.reduce((e,t)=>Math.min(e,t.range[0]),1/0),n=e.reduce((e,t)=>Math.max(e,t.range[1]),-1/0);return{type:"string",example:e[0].example,range:[t,n],count:e.reduce((e,t)=>e+t.count,0)}},number:function(e){let t=e.reduce((e,t)=>Math.min(e,t.range[0]),1/0),n=e.reduce((e,t)=>Math.max(e,t.range[1]),-1/0);return{type:"number",example:e[0].example,range:[t,n],count:e.reduce((e,t)=>e+t.count,0)}},boolean:function(e){return{type:"boolean",example:e[0].example,count:e.reduce((e,t)=>e+t.count,0)}},Object:function(e){let t={};for(let n of e)if(!n.circular)for(let e of n.keys)!t[e]&&(t[e]=[]),t[e].push(n.items[e]);let n={type:"Object",keys:[],items:{},count:e.length};for(let e of Object.keys(t))n.keys.push(e),n.items[e]=r(t[e]);return n},Array:function(e){let t=r(e.map(e=>e.items[0]).filter(e=>e));return{count:e.length,items:{0:t},length:t.count/e.length,type:"Array"}}}[t](e)}(n.filter(t=>t.type===e),e)}return{count:0}}},printSummary:function(e,{indentation:t=a.indentation,indentCount:n=a.indentCount,showExampleValue:r=a.showExampleValue,startExpanded:s=a.startExpanded,theme:l=a.theme}=a){return`<div class="theme ${l}"><div class='json-summary-wrapper'>`+function e(a,s){let l="";if(a.circular)l+=u("(circular reference)","circular");else if("Object"===a.type){l+="{";let r=a.keys.map(e=>`'${e}'`).join(", ");l+=u(r,"keys");let o=a.keys.map(t=>e(a.items[t],s+1));if(o.length){let e="\n";for(let r=0;r<a.keys.length;r++)e+=t.repeat((s+1)*n),e+=u(a.keys[r],"name")+": ",a.count>1&&(e+=`<div class="json-summary json-summary-bar" title="${(m=a.items[a.keys[r]].count/a.count*100).toFixed(2)}%"><div class="json-summary json-summary-percentage" style="width:${m}%;"></div></div>`),e+=o[r],r<a.keys.length-1&&(e+=","),e+="\n";e+=t.repeat(s*n),l+=u(e,"child")}l=u(l+="}","layer")}else if("Array"===a.type){if(l+=u(a.count>1?"μ = "+a.length.toFixed(1):a.length,"length")+" [",a.length){let r="Object"===a.items[0].type||"Array"===a.items[0].type;r&&(l+="\n"+t.repeat((s+1)*n)),l+=e(a.items[0],s+1,a.count),r&&(l+="\n"+t.repeat(s*n))}l+="]"}else null==a.example||null==a.example?l+=u("?","type"):l+=u(a.type,"type"),r&&(l+=u(a.example,"value",a.type),a.count>1&&a.range&&(l+=u(a.range,"range",a.type)));var m;return l}(e,0)+"<div></div>";function u(e,t,n){return{type:()=>`<span class="json-summary json-summary-type json-summary-type-${e}"><${e}></span>`,value:()=>`<span class="json-summary json-summary-value json-summary-value-${n}">${e}</span>`,range:()=>`<span class="json-summary json-summary-range json-summary-range-${n}">[${e[0]}, ${e[1]}]</span>`,name:()=>`<span class="json-summary json-summary-name">${e}</span>`,length:()=>`<span class="json-summary json-summary-length">(${e})</span>`,circular:()=>`<span class="json-summary json-summary-circular">${e}</span>`,layer:()=>`<span class="json-summary json-summary-checkbox ${s?"checked":""}">\n <input type="checkbox" ${s?"checked":""}>\n <span class="json-summary-checkboxmarker" onclick="(function(me){\n me.parentNode.classList.toggle('checked');\n })(this)"></span>\n </span><div class="json-summary json-summary-layer">${e}</div>`,child:()=>`<div class="json-summary json-summary-child">${e}</div>`,keys:()=>`<span class="json-summary json-summary-keys">${e}</span>`}[t]()}}},s=r.defaults,l=r.summarize,u=r.printSummary;e.default=r,e.defaults=s,e.printSummary=u,e.summarize=l,Object.defineProperty(e,"__esModule",{value:!0})}); |
429
index.js
@@ -1,424 +0,7 @@ | ||
const summarizer = (function() { | ||
let defaultOptions = { | ||
arraySampleCount: 10, | ||
indentation: " ", // or "\t" | ||
indentCount: 2, | ||
showExampleValue: true, | ||
startExpanded: false, | ||
theme: "dark" | ||
}; | ||
"use strict"; | ||
// summarizer utility class | ||
return function({ | ||
arraySampleCount = 10, | ||
indentation = " ", // or "\t" | ||
indentCount = 2, | ||
showExampleValue = true, | ||
startExpanded = false, | ||
theme = "dark" | ||
} = defaultOptions) { | ||
let options = { | ||
arraySampleCount, | ||
indentation, | ||
indentCount, | ||
showExampleValue, | ||
startExpanded, | ||
theme | ||
}; | ||
// utility function to extract overall json structure without printing entire data object | ||
function summarizeJSON(data) { | ||
let summary = summarizeItem(data); | ||
// clean up the marking | ||
unmarkObject(data); | ||
return summary; | ||
} | ||
function summarizeItem(item) { | ||
let summarize = { | ||
Array: arr => { | ||
let summarized = { | ||
count: 1, | ||
type: "Array", | ||
length: arr.length | ||
}; | ||
// recurse to items in the array | ||
if (arr.length) { | ||
if (arraySampleCount > 0) { | ||
let numToSample = Math.min(arraySampleCount, arr.length); | ||
let sampledItems = {}; | ||
// summarized.count = numToSample; | ||
while (numToSample > 0) { | ||
let sampleIndex = Math.floor(Math.random() * arr.length); | ||
if (!sampledItems.hasOwnProperty(sampleIndex)) { | ||
sampledItems[sampleIndex] = arr[sampleIndex]; | ||
numToSample--; | ||
} | ||
} | ||
let summarizedSamples = []; | ||
for (let [idx, item] of Object.entries(sampledItems)) { | ||
summarizedSamples.push(summarizeItem(item)); | ||
} | ||
let joinedSample = joinSampledArray(summarizedSamples); | ||
summarized.items = { | ||
0: joinedSample | ||
}; | ||
} else { | ||
// sumamrized.count = 1; | ||
summarized.items = { | ||
0: summarizeItem(arr[0]) | ||
}; | ||
} | ||
} else { | ||
summarized.items = { | ||
0: undefined | ||
}; | ||
} | ||
return summarized; | ||
}, | ||
Object: obj => { | ||
let summarized = { | ||
count: 1, | ||
type: "Object", | ||
keys: Object.keys(obj), | ||
items: {} | ||
}; | ||
for (let key of summarized.keys) { | ||
summarized.items[key] = summarizeItem(obj[key]); | ||
} | ||
return summarized; | ||
}, | ||
Other: data => { | ||
let range; | ||
if (typeof data === "string") { | ||
range = [data.length, data.length]; | ||
} else if (typeof data === "number") { | ||
range = [data, data]; | ||
} | ||
return { | ||
type: typeof data, | ||
example: data, | ||
count: 1, | ||
range | ||
}; | ||
} | ||
}; | ||
let type = "Other"; | ||
if (item instanceof Array) { | ||
type = "Array"; | ||
} else if (item instanceof Object) { | ||
type = "Object"; | ||
} | ||
if (item && item["*snippets_mark*"]) { | ||
return { | ||
type: type, | ||
circular: true | ||
}; | ||
} else { | ||
// marked as visited to make sure it doesn't hit a circular structure | ||
if (type !== "Other") { | ||
Object.defineProperty(item, "*snippets_mark*", { | ||
enumerable: false, | ||
writable: true, | ||
configurable: true | ||
}); | ||
item["*snippets_mark*"] = true; | ||
} | ||
return summarize[type](item); | ||
} | ||
} | ||
function joinSampledArray(itemset) { | ||
// let type = itemset.map(d => d.type) | ||
// .reduce((a, type) => { | ||
// a[type] = []; | ||
// return a; | ||
// }, {}); | ||
// for (let item of itemset) { | ||
// type[item.type].push(item); | ||
// } | ||
// let joins = {}; | ||
// for (let [t, itemset] of Object.entries(type)) { | ||
// joins[t] = joinItems(itemset, t); | ||
// } | ||
// console.log(joins); | ||
// return | ||
// assume theyre all a matching type | ||
let joinableTypes = {Array: true, Object: true, boolean: true, string: true, number: true}; | ||
let items = itemset.filter(i => joinableTypes[i.type]); | ||
if (items.length) { | ||
let type = items[0].type; | ||
return joinItems(items.filter(i => i.type === type), type); | ||
} else { | ||
// idk - no items to join? | ||
return { | ||
count: 0 | ||
}; | ||
} | ||
} | ||
function joinItems(itemArr, type) { | ||
itemArr = itemArr.filter(i => i.type === type); | ||
// functions to join items by type | ||
let joiner = { | ||
string: function(items) { | ||
// string length range | ||
let min = items.reduce((acc, item) => { | ||
return Math.min(acc, item.range[0]); | ||
}, Infinity); | ||
let max = items.reduce((acc, item) => { | ||
return Math.max(acc, item.range[1]); | ||
}, -Infinity); | ||
let joinedString = { | ||
type: "string", | ||
example: items[0].example, | ||
range: [min, max], | ||
count: items.reduce((a, i) => a + i.count, 0) | ||
}; | ||
return joinedString; | ||
}, | ||
number: function(items) { | ||
let min = items.reduce((acc, item) => { | ||
return Math.min(acc, item.range[0]); | ||
}, Infinity); | ||
let max = items.reduce((acc, item) => { | ||
return Math.max(acc, item.range[1]); | ||
}, -Infinity); | ||
let joinedNumber = { | ||
type: "number", | ||
example: items[0].example, | ||
range: [min, max], | ||
count: items.reduce((a, i) => a + i.count, 0) | ||
}; | ||
return joinedNumber; | ||
}, | ||
boolean: function(items) { | ||
return { | ||
type: "boolean", | ||
example: items[0].example, | ||
count: items.reduce((a, i) => a + i.count, 0) | ||
}; | ||
}, | ||
Object: function(items) { | ||
let masterKeys = {}; | ||
for (let obj of items) { | ||
if (!obj.circular) { | ||
for (let key of obj.keys) { | ||
!masterKeys[key] && (masterKeys[key] = []); | ||
masterKeys[key].push(obj.items[key]); | ||
} | ||
} | ||
} | ||
let joinedObject = { type: "Object", keys: [], items: {}, count: items.length }; | ||
for (let key of Object.keys(masterKeys)) { | ||
joinedObject.keys.push(key); | ||
joinedObject.items[key] = joinSampledArray(masterKeys[key]); | ||
} | ||
return joinedObject; | ||
}, | ||
Array: function(items) { | ||
let joinedValues = joinSampledArray(items.map(i => i.items[0]).filter(i => i)); | ||
let joinedArray = { | ||
count: items.length, | ||
items: { | ||
0: joinedValues | ||
}, | ||
length: joinedValues.count / items.length, | ||
type: "Array" | ||
}; | ||
return joinedArray; | ||
} | ||
}; | ||
return joiner[type](itemArr); | ||
} | ||
function unmarkObject(obj) { | ||
if (obj && obj["*snippets_mark*"]) { | ||
delete obj["*snippets_mark*"]; | ||
// recurse to the next level | ||
if (obj instanceof Array && obj.length) { | ||
unmarkObject(obj[0]); | ||
} else if (obj instanceof Object) { | ||
for (let key of Object.keys(obj)) { | ||
unmarkObject(obj[key]); | ||
} | ||
} | ||
} | ||
} | ||
// utility function to stringify the summary output from summarizeJSON | ||
function printSummarizedJSON(summary) { | ||
// start at 0 indentation | ||
return `<div class='json-summary-wrapper ${options.theme}'>` + printSummaryLevel(summary, 0, 1); | ||
} | ||
function printSummaryLevel(data, l, prevCount) { | ||
let string = ""; | ||
if (data.circular) { | ||
string += wrapInHTML("(circular reference)", "circular"); | ||
} else if (data.type === "Object") { | ||
string += "{"; | ||
let keys = data.keys.map(k => `'${k}'`).join(", "); | ||
string += wrapInHTML(keys, "keys"); | ||
let childStrings = data.keys.map(key => { | ||
return printSummaryLevel(data.items[key], l + 1, data.count); | ||
}); | ||
if (childStrings.length) { | ||
let childStringCombined = "\n"; | ||
for (let i = 0; i < data.keys.length; i++) { | ||
childStringCombined += options.indentation.repeat( | ||
(l + 1) * options.indentCount | ||
); | ||
childStringCombined += wrapInHTML(data.keys[i], "name") + ": "; | ||
if (data.count > 1) { | ||
childStringCombined += htmlPercentageBar(data.items[data.keys[i]].count / data.count * 100); | ||
} | ||
childStringCombined += childStrings[i]; | ||
if (i < data.keys.length - 1) { | ||
childStringCombined += ","; | ||
} | ||
childStringCombined += "\n"; | ||
} | ||
childStringCombined += options.indentation.repeat(l * options.indentCount); | ||
string += wrapInHTML(childStringCombined, "child"); | ||
} | ||
string += "}"; | ||
string = wrapInHTML(string, "layer"); | ||
} else if (data.type === "Array") { | ||
// string += "[]"; | ||
// string += `[ ${data.length ? `(${data.length}×)` : "∅"} `; | ||
string += wrapInHTML(data.count > 1 ? "μ = " + data.length.toFixed(1) : data.length, "length") + ` [`; | ||
if (data.length) { | ||
let needsNewlines = | ||
data.items["0"].type === "Object" || data.items["0"].type === "Array"; | ||
if (needsNewlines) { | ||
string += "\n" + options.indentation.repeat((l + 1) * options.indentCount); | ||
} | ||
string += printSummaryLevel(data.items["0"], l + 1, data.count); | ||
if (needsNewlines) { | ||
string += "\n" + options.indentation.repeat(l * options.indentCount); | ||
} | ||
} | ||
string += "]"; | ||
// string = wrapInHTML(string, "layer"); | ||
} else { | ||
if (data.example == null || data.example == undefined) { | ||
string += wrapInHTML("?", "type"); | ||
} else { | ||
string += wrapInHTML(data.type, "type"); | ||
} | ||
if (options.showExampleValue) { | ||
string += wrapInHTML(data.example, "value", data.type); | ||
data.count > 1 && data.range && (string += wrapInHTML(data.range, "range", data.type)); | ||
} | ||
} | ||
return string; | ||
} | ||
function wrapInHTML(value, role, type) { | ||
let tags = { | ||
type: () => `<span class="json-summary json-summary-type json-summary-type-${value}"><${value}></span>`, | ||
value: () => `<span class="json-summary json-summary-value json-summary-value-${type}">${value}</span>`, | ||
range: () => `<span class="json-summary json-summary-range json-summary-range-${type}">[${value[0]}, ${value[1]}]</span>`, | ||
name: () => `<span class="json-summary json-summary-name">${value}</span>`, | ||
length: () => `<span class="json-summary json-summary-length">(${value})</span>`, | ||
circular: () => `<span class="json-summary json-summary-circular">${value}</span>`, | ||
layer: () => `<span class="json-summary json-summary-checkbox ${ | ||
options.startExpanded ? "checked" : "" | ||
}"> | ||
<input type="checkbox" ${ | ||
options.startExpanded ? "checked" : "" | ||
}> | ||
<span class="json-summary-checkboxmarker" onclick="(function(me){ | ||
me.parentNode.classList.toggle('checked'); | ||
})(this)"></span> | ||
</span><div class="json-summary json-summary-layer">${value}</div>`, | ||
child: () => `<div class="json-summary json-summary-child">${value}</div>`, | ||
keys: () => `<span class="json-summary json-summary-keys">${value}</span>` | ||
}; | ||
return tags[role](); | ||
} | ||
function htmlPercentageBar(percentage) { | ||
return `<div class="json-summary json-summary-bar" title="${percentage.toFixed(2)}%"><div class="json-summary json-summary-percentage" style="width:${percentage}%;"></div></div>` | ||
} | ||
return { | ||
summarize: summarizeJSON, | ||
printSummary: printSummarizedJSON | ||
}; | ||
} | ||
}()); | ||
module.exports = summarizer; | ||
module.exports = { | ||
defaults: require("./src/defaults"), | ||
summarize: require("./src/summarize"), | ||
printSummary: require("./src/printSummary") | ||
}; |
{ | ||
"name": "json-summary", | ||
"version": "0.2.5", | ||
"version": "1.0.0", | ||
"description": "A simple JSON summarizer to extract the structure from a JSON object", | ||
@@ -12,6 +12,5 @@ "keywords": [ | ||
"main": "index.js", | ||
"module": "dist/json-summary.esm.js", | ||
"browser": "dist/json-summary.js", | ||
"browserMin": "dist/json-summary.min.js", | ||
"files":[ | ||
"files": [ | ||
"/dist", | ||
@@ -24,3 +23,3 @@ "index.js" | ||
"prepublish": "npm run build && npm test", | ||
"build": "rollup -c && cp dist/json-summary.js docs/json-summary.js && cp summarizer.css docs/summarizer.css" | ||
"build": "rollup -c && cp dist/json-summary.js docs/json-summary.js && sass style/main.scss dist/summarizer.css && cp dist/summarizer.css docs/summarizer.css" | ||
}, | ||
@@ -42,2 +41,3 @@ "repository": { | ||
"coveralls": "^3.0.3", | ||
"eslint": "^5.16.0", | ||
"jest": "^24.7.1", | ||
@@ -47,5 +47,7 @@ "rollup": "^1.9.0", | ||
"rollup-plugin-node-resolve": "^4.2.1", | ||
"rollup-plugin-terser": "^4.0.4" | ||
"rollup-plugin-terser": "^4.0.4", | ||
"sass": "^1.18.0" | ||
}, | ||
"dependencies": {} | ||
"dependencies": {}, | ||
"eslintConfig": "./.eslintrc.json" | ||
} |
# json-summary | ||
[![npm version](https://img.shields.io/travis/com/AndrewTBurks/json-summary.svg)](https://www.npmjs.com/package/json-summary) | ||
[![npm downloads](https://img.shields.io/npm/v/json-summary.svg)](https://www.npmjs.com/package/json-summary) | ||
[![npm downloads](https://img.shields.io/npm/dt/json-summary.svg)](https://www.npmjs.com/package/json-summary) | ||
[![Coverage Status](https://coveralls.io/repos/github/AndrewTBurks/json-summary/badge.svg?branch=master)](https://coveralls.io/github/AndrewTBurks/json-summary?branch=master) | ||
[![Travis (.com)](https://img.shields.io/travis/com/AndrewTBurks/json-summary.svg?style=for-the-badge)](https://www.npmjs.com/package/json-summary) | ||
[![npm version](https://img.shields.io/npm/v/json-summary.svg?style=for-the-badge)](https://www.npmjs.com/package/json-summary) | ||
[![npm downloads](https://img.shields.io/npm/dt/json-summary.svg?style=for-the-badge)](https://www.npmjs.com/package/json-summary) | ||
[![npm bundle size](https://img.shields.io/bundlephobia/min/json-summary.svg?style=for-the-badge)](https://www.npmjs.com/package/json-summary) | ||
[![Coveralls github](https://img.shields.io/coveralls/github/AndrewTBurks/json-summary.svg?style=for-the-badge)](https://coveralls.io/github/AndrewTBurks/json-summary?branch=master) | ||
@@ -8,0 +9,0 @@ |
Sorry, the diff of this file is not supported yet
Sorry, the diff of this file is not supported yet
No v1
QualityPackage is not semver >=1. This means it is not stable and does not support ^ ranges.
Found 1 instance in 1 package
1
13
44110
8
1064