Fixes for datasource authentication parsing. Mapping UX updates
This commit is contained in:
parent
ac8513bd4c
commit
31b51e1ecf
|
@ -40,5 +40,6 @@
|
|||
on:change={onChange}
|
||||
on:pick
|
||||
on:type
|
||||
on:blur
|
||||
/>
|
||||
</Field>
|
||||
|
|
|
@ -52,7 +52,10 @@
|
|||
{id}
|
||||
type="text"
|
||||
on:focus={() => (focus = true)}
|
||||
on:blur={() => (focus = false)}
|
||||
on:blur={() => {
|
||||
focus = false
|
||||
dispatch("blur")
|
||||
}}
|
||||
on:change={onType}
|
||||
value={value || ""}
|
||||
placeholder={placeholder || ""}
|
||||
|
|
|
@ -54,7 +54,56 @@ export const getBindableProperties = (asset, componentId) => {
|
|||
*/
|
||||
export const getRestBindings = () => {
|
||||
const userBindings = getUserBindings()
|
||||
return [...userBindings]
|
||||
return [...userBindings, ...getAuthBindings()]
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets all rest bindable auth fields
|
||||
*/
|
||||
export const getAuthBindings = () => {
|
||||
let bindings = []
|
||||
const safeUser = makePropSafe("user")
|
||||
const safeOAuth2 = makePropSafe("oauth2")
|
||||
const safeAccessToken = makePropSafe("accessToken")
|
||||
|
||||
const authBindings = [
|
||||
{
|
||||
runtime: `${safeUser}.${safeOAuth2}.${safeAccessToken}`,
|
||||
readable: `Current User.OAuthToken`,
|
||||
key: "accessToken",
|
||||
},
|
||||
]
|
||||
|
||||
bindings = Object.keys(authBindings).map(key => {
|
||||
const fieldBinding = authBindings[key]
|
||||
return {
|
||||
type: "context",
|
||||
runtimeBinding: fieldBinding.runtime,
|
||||
readableBinding: fieldBinding.readable,
|
||||
fieldSchema: { type: "string", name: fieldBinding.key },
|
||||
providerId: "user",
|
||||
}
|
||||
})
|
||||
return bindings
|
||||
}
|
||||
|
||||
/**
|
||||
* Utility - convert a key/value map to an array of custom 'context' bindings
|
||||
* @param {object} valueMap Key/value pairings
|
||||
* @param {string} prefix A contextual string prefix/path for a user readable binding
|
||||
* @return {object[]} An array containing readable/runtime binding objects
|
||||
*/
|
||||
export const toBindingsArray = (valueMap, prefix) => {
|
||||
if (!valueMap) {
|
||||
return []
|
||||
}
|
||||
return Object.keys(valueMap).map(binding => {
|
||||
return {
|
||||
type: "context",
|
||||
runtimeBinding: binding,
|
||||
readableBinding: `${prefix}.${binding}`,
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
|
@ -2,6 +2,8 @@
|
|||
import { onMount } from "svelte"
|
||||
import { ModalContent, Layout, Select, Body, Input } from "@budibase/bbui"
|
||||
import { AUTH_TYPE_LABELS, AUTH_TYPES } from "./authTypes"
|
||||
import DrawerBindableCombobox from "components/common/bindings/DrawerBindableCombobox.svelte"
|
||||
import { getAuthBindings } from "builderStore/dataBinding"
|
||||
|
||||
export let configs
|
||||
export let currentConfig
|
||||
|
@ -203,11 +205,23 @@
|
|||
/>
|
||||
{/if}
|
||||
{#if form.type === AUTH_TYPES.BEARER}
|
||||
<Input
|
||||
<DrawerBindableCombobox
|
||||
label="Token"
|
||||
bind:value={form.bearer.token}
|
||||
on:change={onFieldChange}
|
||||
on:blur={() => (blurred.bearer.token = true)}
|
||||
value={form.bearer.token}
|
||||
bindings={getAuthBindings()}
|
||||
on:change={e => {
|
||||
form.bearer.token = e.detail
|
||||
console.log(e.detail)
|
||||
onFieldChange()
|
||||
}}
|
||||
on:blur={() => {
|
||||
blurred.bearer.token = true
|
||||
onFieldChange()
|
||||
}}
|
||||
allowJS={false}
|
||||
placeholder="Token"
|
||||
appendBindingsAsOptions={true}
|
||||
drawerEnabled={false}
|
||||
error={blurred.bearer.token ? errors.bearer.token : null}
|
||||
/>
|
||||
{/if}
|
||||
|
|
|
@ -18,6 +18,8 @@
|
|||
export let options
|
||||
export let allowJS = true
|
||||
export let appendBindingsAsOptions = true
|
||||
export let drawerEnabled = false
|
||||
export let error
|
||||
|
||||
const dispatch = createEventDispatcher()
|
||||
let bindingDrawer
|
||||
|
@ -59,10 +61,12 @@
|
|||
value={isJS ? "(JavaScript function)" : readableValue}
|
||||
on:type={e => onChange(e.detail, false)}
|
||||
on:pick={e => onChange(e.detail, true)}
|
||||
on:blur={() => dispatch("blur")}
|
||||
{placeholder}
|
||||
options={allOptions}
|
||||
{error}
|
||||
/>
|
||||
{#if !disabled}
|
||||
{#if !disabled && drawerEnabled}
|
||||
<div
|
||||
class="icon"
|
||||
on:click={bindingDrawer.show}
|
||||
|
@ -72,21 +76,23 @@
|
|||
</div>
|
||||
{/if}
|
||||
</div>
|
||||
<Drawer bind:this={bindingDrawer} {title}>
|
||||
<svelte:fragment slot="description">
|
||||
Add the objects on the left to enrich your text.
|
||||
</svelte:fragment>
|
||||
<Button cta slot="buttons" on:click={handleClose}>Save</Button>
|
||||
<svelte:component
|
||||
this={panel}
|
||||
slot="body"
|
||||
value={readableValue}
|
||||
close={handleClose}
|
||||
on:change={event => (tempValue = event.detail)}
|
||||
{bindings}
|
||||
{allowJS}
|
||||
/>
|
||||
</Drawer>
|
||||
{#if !drawerEnabled}
|
||||
<Drawer bind:this={bindingDrawer} {title}>
|
||||
<svelte:fragment slot="description">
|
||||
Add the objects on the left to enrich your text.
|
||||
</svelte:fragment>
|
||||
<Button cta slot="buttons" on:click={handleClose}>Save</Button>
|
||||
<svelte:component
|
||||
this={panel}
|
||||
slot="body"
|
||||
value={readableValue}
|
||||
close={handleClose}
|
||||
on:change={event => (tempValue = event.detail)}
|
||||
{bindings}
|
||||
{allowJS}
|
||||
/>
|
||||
</Drawer>
|
||||
{/if}
|
||||
|
||||
<style>
|
||||
.control {
|
||||
|
|
|
@ -11,6 +11,7 @@
|
|||
} from "@budibase/bbui"
|
||||
import { createEventDispatcher } from "svelte"
|
||||
import { lowercase } from "helpers"
|
||||
import DrawerBindableInput from "components/common/bindings/DrawerBindableInput.svelte"
|
||||
|
||||
let dispatch = createEventDispatcher()
|
||||
|
||||
|
@ -30,6 +31,7 @@
|
|||
export let tooltip
|
||||
export let menuItems
|
||||
export let showMenu = false
|
||||
export let bindings = []
|
||||
|
||||
let fields = Object.entries(object || {}).map(([name, value]) => ({
|
||||
name,
|
||||
|
@ -108,6 +110,16 @@
|
|||
/>
|
||||
{#if options}
|
||||
<Select bind:value={field.value} on:change={changed} {options} />
|
||||
{:else if bindings && bindings.length}
|
||||
<DrawerBindableInput
|
||||
{bindings}
|
||||
placeholder="Value"
|
||||
on:change={e => (field.value = e.detail)}
|
||||
disabled={readOnly}
|
||||
value={field.value}
|
||||
allowJS={false}
|
||||
fillWidth={true}
|
||||
/>
|
||||
{:else}
|
||||
<Input
|
||||
placeholder={valuePlaceholder}
|
||||
|
|
|
@ -42,8 +42,9 @@
|
|||
|
||||
import {
|
||||
getRestBindings,
|
||||
readableToRuntimeBinding,
|
||||
toBindingsArray,
|
||||
runtimeToReadableBinding,
|
||||
readableToRuntimeBinding,
|
||||
runtimeToReadableMap,
|
||||
readableToRuntimeMap,
|
||||
} from "builderStore/dataBinding"
|
||||
|
@ -57,6 +58,25 @@
|
|||
let dynamicVariables, addVariableModal, varBinding
|
||||
let restBindings = getRestBindings()
|
||||
|
||||
$: staticVariables = datasource?.config?.staticVariables || {}
|
||||
$: customRequestBindings = toBindingsArray(requestBindings, "Binding")
|
||||
$: dynamicRequestBindings = toBindingsArray(dynamicVariables, "Dynamic")
|
||||
$: dataSourceStaticBindings = toBindingsArray(
|
||||
staticVariables,
|
||||
"Datasource.Static"
|
||||
)
|
||||
|
||||
$: mergedBindings = [
|
||||
...restBindings,
|
||||
...customRequestBindings,
|
||||
...dynamicRequestBindings,
|
||||
...dataSourceStaticBindings,
|
||||
]
|
||||
|
||||
$: mergedAndCompleteBindings = mergedBindings.filter(binding => {
|
||||
return binding.runtimeBinding && binding.readableBinding
|
||||
})
|
||||
|
||||
$: datasourceType = datasource?.source
|
||||
$: integrationInfo = $integrations[datasourceType]
|
||||
$: queryConfig = integrationInfo?.query
|
||||
|
@ -72,7 +92,10 @@
|
|||
Object.keys(schema || {}).length !== 0 ||
|
||||
Object.keys(query?.schema || {}).length !== 0
|
||||
|
||||
$: runtimeUrlQueries = readableToRuntimeMap(restBindings, breakQs)
|
||||
$: runtimeUrlQueries = readableToRuntimeMap(
|
||||
mergedAndCompleteBindings,
|
||||
breakQs
|
||||
)
|
||||
|
||||
function getSelectedQuery() {
|
||||
const cloneQuery = cloneDeep(
|
||||
|
@ -87,32 +110,18 @@
|
|||
queryVerb: "read",
|
||||
}
|
||||
)
|
||||
|
||||
if (cloneQuery?.fields?.headers) {
|
||||
cloneQuery.fields.headers = runtimeToReadableMap(
|
||||
restBindings,
|
||||
cloneQuery.fields.headers
|
||||
)
|
||||
}
|
||||
|
||||
if (cloneQuery?.fields?.requestBody) {
|
||||
cloneQuery.fields.requestBody =
|
||||
typeof cloneQuery.fields.requestBody === "object"
|
||||
? runtimeToReadableMap(restBindings, cloneQuery.fields.requestBody)
|
||||
? runtimeToReadableMap(
|
||||
mergedAndCompleteBindings,
|
||||
cloneQuery.fields.requestBody
|
||||
)
|
||||
: runtimeToReadableBinding(
|
||||
restBindings,
|
||||
mergedAndCompleteBindings,
|
||||
cloneQuery.fields.requestBody
|
||||
)
|
||||
}
|
||||
|
||||
if (cloneQuery?.parameters) {
|
||||
const flatParams = restUtils.queryParametersToKeyValue(
|
||||
cloneQuery.parameters
|
||||
)
|
||||
const updatedParams = runtimeToReadableMap(restBindings, flatParams)
|
||||
cloneQuery.parameters = restUtils.keyValueToQueryParameters(updatedParams)
|
||||
}
|
||||
|
||||
return cloneQuery
|
||||
}
|
||||
|
||||
|
@ -128,7 +137,7 @@
|
|||
return base
|
||||
}
|
||||
const qs = restUtils.buildQueryString(
|
||||
runtimeToReadableMap(restBindings, qsObj)
|
||||
runtimeToReadableMap(mergedAndCompleteBindings, qsObj)
|
||||
)
|
||||
let newUrl = base
|
||||
if (base.includes("?")) {
|
||||
|
@ -140,14 +149,17 @@
|
|||
function buildQuery() {
|
||||
const newQuery = cloneDeep(query)
|
||||
const queryString = restUtils.buildQueryString(runtimeUrlQueries)
|
||||
newQuery.fields.headers = readableToRuntimeMap(
|
||||
restBindings,
|
||||
newQuery.fields.headers
|
||||
)
|
||||
|
||||
newQuery.fields.requestBody =
|
||||
typeof newQuery.fields.requestBody === "object"
|
||||
? readableToRuntimeMap(restBindings, newQuery.fields.requestBody)
|
||||
: readableToRuntimeBinding(restBindings, newQuery.fields.requestBody)
|
||||
? readableToRuntimeMap(
|
||||
mergedAndCompleteBindings,
|
||||
newQuery.fields.requestBody
|
||||
)
|
||||
: readableToRuntimeBinding(
|
||||
mergedAndCompleteBindings,
|
||||
newQuery.fields.requestBody
|
||||
)
|
||||
|
||||
newQuery.fields.path = url.split("?")[0]
|
||||
newQuery.fields.queryString = queryString
|
||||
|
@ -155,14 +167,6 @@
|
|||
newQuery.fields.disabledHeaders = restUtils.flipHeaderState(enabledHeaders)
|
||||
newQuery.schema = restUtils.fieldsToSchema(schema)
|
||||
|
||||
const parsedRequestBindings = readableToRuntimeMap(
|
||||
restBindings,
|
||||
requestBindings
|
||||
)
|
||||
newQuery.parameters = restUtils.keyValueToQueryParameters(
|
||||
parsedRequestBindings
|
||||
)
|
||||
|
||||
return newQuery
|
||||
}
|
||||
|
||||
|
@ -409,10 +413,20 @@
|
|||
headings
|
||||
keyPlaceholder="Binding name"
|
||||
valuePlaceholder="Default"
|
||||
bindings={[
|
||||
...restBindings,
|
||||
...dynamicRequestBindings,
|
||||
...dataSourceStaticBindings,
|
||||
]}
|
||||
/>
|
||||
</Tab>
|
||||
<Tab title="Params">
|
||||
<KeyValueBuilder bind:object={breakQs} name="param" headings />
|
||||
<KeyValueBuilder
|
||||
bind:object={breakQs}
|
||||
name="param"
|
||||
headings
|
||||
bindings={mergedAndCompleteBindings}
|
||||
/>
|
||||
</Tab>
|
||||
<Tab title="Headers">
|
||||
<KeyValueBuilder
|
||||
|
@ -421,6 +435,7 @@
|
|||
toggle
|
||||
name="header"
|
||||
headings
|
||||
bindings={mergedAndCompleteBindings}
|
||||
/>
|
||||
</Tab>
|
||||
<Tab title="Body">
|
||||
|
|
|
@ -36,6 +36,12 @@ class QueryRunner {
|
|||
if (!Integration) {
|
||||
throw "Integration type does not exist."
|
||||
}
|
||||
|
||||
datasource.config.authConfigs = enrichQueryFields(
|
||||
datasource.config.authConfigs,
|
||||
this.ctx
|
||||
)
|
||||
|
||||
const integration = new Integration(datasource.config)
|
||||
|
||||
// pre-query, make sure datasource variables are added to parameters
|
||||
|
|
Loading…
Reference in New Issue