Allow using lodash functions in transform query

This commit is contained in:
Jos de Jong 2020-09-02 12:14:48 +02:00
parent 023c57f492
commit 45f8881e96
3 changed files with 23 additions and 6 deletions

View File

@ -10,6 +10,8 @@
import { sortArray, sortObjectKeys } from '../../logic/sort.js'
import { sortModalState } from './sortModalState.js'
import { compileJSONPointer } from '../../utils/jsonPointer.js'
import { get } from 'lodash-es'
import { getIn } from '../../utils/immutabilityHelpers.js'
export let id
export let json
@ -22,7 +24,7 @@
$: json
$: jsonIsArray = Array.isArray(json)
$: paths = jsonIsArray ? getNestedPaths(json) : undefined
$: properties = paths?.map(pathToOption)
$: properties = paths ? paths.map(pathToOption) : undefined
const asc = {
value: 1,
@ -34,8 +36,8 @@
}
const directions = [asc, desc]
let selectedProperty = sortModalState[stateId]?.selectedProperty || undefined
let selectedDirection = sortModalState[stateId]?.selectedDirection || asc
let selectedProperty = (sortModalState[stateId] && sortModalState[stateId].selectedProperty) || undefined
let selectedDirection = (sortModalState[stateId] && sortModalState[stateId].selectedDirection) || asc
$: {
// if there is only one option, select it and do not render the select box

View File

@ -5,6 +5,12 @@
.description {
padding-bottom: $padding;
code {
background: $background-gray;
font-family: $font-family-mono;
font-size: $font-size-mono;
}
}
label {

View File

@ -8,6 +8,8 @@
import { transformModalState } from './transformModalState.js'
import { DEBOUNCE_DELAY, MAX_PREVIEW_CHARACTERS } from '../../constants.js'
import { truncate } from '../../utils/stringUtils.js'
import * as _ from 'lodash-es'
import { getIn } from '../../utils/immutabilityHelpers.js'
export let id
export let json
@ -20,14 +22,15 @@
let stateId = `${id}:${compileJSONPointer(rootPath)}`
let query = transformModalState[stateId]?.query || DEFAULT_QUERY
let query = (transformModalState[stateId] && transformModalState[stateId].query) || DEFAULT_QUERY
let previewHasError = false
let preview = ''
function evalTransform(json, query) {
// FIXME: replace unsafe eval with a JS based query language
// FIXME: replace unsafe new Function with a JS based query language
// As long as we don't persist or fetch queries, there is no security risk.
const queryFn = eval(`(${query})`)
// TODO: only import the most relevant subset of lodash instead of the full library?
const queryFn = new Function('_', `'use strict'; return (${query})`)(_)
return queryFn(json)
}
@ -86,6 +89,12 @@
<div class='description'>
Enter a JavaScript function to filter, sort, or transform the data.
</div>
<div class='description'>
You can use <a href='https://lodash.com' target='_blank' rel='noopener noreferrer'>Lodash</a>
functions like <code>_.map</code>, <code>_.filter</code>,
<code>_.orderBy</code>, <code>_.sortBy</code>, <code>_.groupBy</code>,
<code>_.pick</code>, <code>_.uniq</code>, <code>_.get</code>, etcetera.
</div>
<label>Query</label>
<textarea class="query" bind:value={query} />