Merge pull request #15794 from Budibase/BUDI-9127/extract-env-input

Extract env input component
This commit is contained in:
Adria Navarro 2025-03-25 15:26:57 +01:00 committed by GitHub
commit 871d875c68
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
22 changed files with 208 additions and 193 deletions

View File

@ -27,5 +27,6 @@
}, },
"[handlebars]": { "[handlebars]": {
"editor.formatOnSave": false "editor.formatOnSave": false
} },
"eslint.validate": ["javascript", "typescript", "svelte"]
} }

View File

@ -1,25 +1,26 @@
<script> <script lang="ts">
import "@spectrum-css/textfield/dist/index-vars.css" import "@spectrum-css/textfield/dist/index-vars.css"
import { createEventDispatcher, onMount } from "svelte" import { createEventDispatcher, onMount } from "svelte"
import clickOutside from "../../Actions/click_outside" import clickOutside from "../../Actions/click_outside"
import Divider from "../../Divider/Divider.svelte" import Divider from "../../Divider/Divider.svelte"
import type { EnvDropdownType } from "../../types"
export let value = null export let value: string | number | undefined = undefined
export let placeholder = null export let placeholder: string | undefined = undefined
export let type = "text" export let type: EnvDropdownType = "text"
export let disabled = false export let disabled: boolean = false
export let id = null export let id: string | undefined = undefined
export let readonly = false export let readonly: boolean = false
export let updateOnChange = true export let updateOnChange: boolean = true
export let align export let align: string | undefined = undefined
export let autofocus = false export let autofocus: boolean = false
export let variables export let variables
export let showModal export let showModal: () => void
export let environmentVariablesEnabled export let environmentVariablesEnabled
export let handleUpgradePanel export let handleUpgradePanel: () => void
const dispatch = createEventDispatcher() const dispatch = createEventDispatcher()
let field let field: HTMLInputElement
let focus = false let focus = false
let iconFocused = false let iconFocused = false
let open = false let open = false
@ -30,7 +31,7 @@
// Strips the name out of the value which is {{ env.Variable }} resulting in an array like ["Variable"] // Strips the name out of the value which is {{ env.Variable }} resulting in an array like ["Variable"]
$: hbsValue = String(value)?.match(STRIP_NAME_REGEX) || [] $: hbsValue = String(value)?.match(STRIP_NAME_REGEX) || []
const updateValue = newValue => { const updateValue = (newValue: any) => {
if (readonly) { if (readonly) {
return return
} }
@ -48,7 +49,7 @@
focus = true focus = true
} }
const onBlur = event => { const onBlur = (event: any) => {
if (readonly) { if (readonly) {
return return
} }
@ -56,14 +57,14 @@
updateValue(event.target.value) updateValue(event.target.value)
} }
const onInput = event => { const onInput = (event: any) => {
if (readonly || !updateOnChange) { if (readonly || !updateOnChange) {
return return
} }
updateValue(event.target.value) updateValue(event.target.value)
} }
const handleOutsideClick = event => { const handleOutsideClick = (event: Event) => {
if (open) { if (open) {
event.stopPropagation() event.stopPropagation()
open = false open = false
@ -73,7 +74,7 @@
} }
} }
const handleVarSelect = variable => { const handleVarSelect = (variable: string) => {
open = false open = false
focus = false focus = false
iconFocused = false iconFocused = false
@ -121,10 +122,10 @@
<input <input
bind:this={field} bind:this={field}
disabled={hbsValue.length || disabled} disabled={!!hbsValue.length || disabled}
{readonly} {readonly}
{id} {id}
value={hbsValue.length ? `{{ ${hbsValue[0]} }}` : value} value={(hbsValue.length ? `{{ ${hbsValue[0]} }}` : value) ?? ""}
placeholder={placeholder || ""} placeholder={placeholder || ""}
on:click on:click
on:blur on:blur

View File

@ -13,7 +13,7 @@
export let quiet = false export let quiet = false
export let align: "left" | "right" | "center" | undefined = undefined export let align: "left" | "right" | "center" | undefined = undefined
export let autofocus: boolean | null = false export let autofocus: boolean | null = false
export let autocomplete: boolean | undefined export let autocomplete: boolean | string | undefined
const dispatch = createEventDispatcher() const dispatch = createEventDispatcher()

View File

@ -1,26 +1,26 @@
<script> <script lang="ts">
import Field from "./Field.svelte" import Field from "./Field.svelte"
import EnvDropdown from "./Core/EnvDropdown.svelte" import EnvDropdown from "./Core/EnvDropdown.svelte"
import { createEventDispatcher } from "svelte" import { createEventDispatcher } from "svelte"
import type { EnvDropdownType } from "../types"
export let value = null export let value: string | undefined = undefined
export let label = null export let label: string | undefined = undefined
export let labelPosition = "above" export let labelPosition: string = "above"
export let placeholder = null export let placeholder: string | undefined = undefined
export let type = "text" export let type: EnvDropdownType = "text"
export let disabled = false export let disabled = false
export let readonly = false export let readonly = false
export let error = null export let error: string | undefined = undefined
export let updateOnChange = true export let updateOnChange = true
export let quiet = false export let autofocus: boolean = false
export let autofocus export let variables: { name: string }[] = []
export let variables export let showModal: () => void
export let showModal export let helpText: string | undefined = undefined
export let helpText = null export let environmentVariablesEnabled: boolean = false
export let environmentVariablesEnabled export let handleUpgradePanel: () => void = () => {}
export let handleUpgradePanel
const dispatch = createEventDispatcher() const dispatch = createEventDispatcher()
const onChange = e => { const onChange = (e: any) => {
value = e.detail value = e.detail
dispatch("change", e.detail) dispatch("change", e.detail)
} }
@ -29,13 +29,11 @@
<Field {helpText} {label} {labelPosition} {error}> <Field {helpText} {label} {labelPosition} {error}>
<EnvDropdown <EnvDropdown
{updateOnChange} {updateOnChange}
{error}
{disabled} {disabled}
{readonly} {readonly}
{value} {value}
{placeholder} {placeholder}
{type} {type}
{quiet}
{autofocus} {autofocus}
{variables} {variables}
{showModal} {showModal}

View File

@ -14,7 +14,7 @@
export let updateOnChange = true export let updateOnChange = true
export let quiet = false export let quiet = false
export let autofocus: boolean | undefined = undefined export let autofocus: boolean | undefined = undefined
export let autocomplete: boolean | undefined = undefined export let autocomplete: boolean | string | undefined = undefined
export let helpText: string | undefined = undefined export let helpText: string | undefined = undefined
const dispatch = createEventDispatcher() const dispatch = createEventDispatcher()

View File

@ -3,7 +3,7 @@
import Icon from "../Icon/Icon.svelte" import Icon from "../Icon/Icon.svelte"
const dispatch = createEventDispatcher() const dispatch = createEventDispatcher()
const actionMenu = getContext("actionMenu") as { hideAll: () => void } const actionMenu = getContext("actionMenu")
export let icon: string | undefined = undefined export let icon: string | undefined = undefined
export let disabled: boolean | undefined = undefined export let disabled: boolean | undefined = undefined

View File

@ -1,7 +1,9 @@
import { ActionMenu } from "./types" import { ActionMenu } from "./types"
import { ModalContext } from "./types"
declare module "svelte" { declare module "svelte" {
export function getContext(key: "actionMenu"): ActionMenu | undefined export function getContext(key: "actionMenu"): ActionMenu | undefined
export function getContext(key: "bbui-modal"): ModalContext
} }
export const Modal = "bbui-modal" export const Modal = "bbui-modal"

View File

@ -111,3 +111,5 @@ export { banner, BANNER_TYPES } from "./Stores/banner"
// Helpers // Helpers
export * as Helpers from "./helpers" export * as Helpers from "./helpers"
export type * from "./types"

View File

@ -1,3 +1,4 @@
export interface ActionMenu { export interface ActionMenu {
hide: () => void hide: () => void
hideAll: () => void
} }

View File

@ -0,0 +1 @@
export type EnvDropdownType = "text" | "number" | "password" | "port"

View File

@ -0,0 +1,3 @@
export * from "./actionMenu"
export * from "./envDropdown"
export * from "./modalContext"

View File

@ -0,0 +1,3 @@
export interface ModalContext {
hide: () => void
}

View File

@ -1,4 +1,4 @@
<script> <script lang="ts">
import ObjectField from "./fields/Object.svelte" import ObjectField from "./fields/Object.svelte"
import BooleanField from "./fields/Boolean.svelte" import BooleanField from "./fields/Boolean.svelte"
import LongFormField from "./fields/LongForm.svelte" import LongFormField from "./fields/LongForm.svelte"
@ -6,15 +6,22 @@
import StringField from "./fields/String.svelte" import StringField from "./fields/String.svelte"
import SelectField from "./fields/Select.svelte" import SelectField from "./fields/Select.svelte"
export let type type InputType =
export let value | "string"
export let error | "boolean"
export let name | "object"
export let config | "longForm"
export let showModal = () => {} | "fieldGroup"
export let placeholder | "select"
const selectComponent = type => { export let type: InputType
export let value: any
export let error: string | null
export let name: string
export let config: any = undefined
export let placeholder: string | undefined = undefined
const selectComponent = (type: InputType) => {
if (type === "object") { if (type === "object") {
return ObjectField return ObjectField
} else if (type === "boolean") { } else if (type === "boolean") {
@ -40,7 +47,6 @@
{error} {error}
{name} {name}
{config} {config}
{showModal}
{placeholder} {placeholder}
on:blur on:blur
on:change on:change

View File

@ -1,33 +1,23 @@
<script> <script lang="ts">
import { Label, EnvDropdown } from "@budibase/bbui" import { Label } from "@budibase/bbui"
import { environment, licensing } from "@/stores/portal" import EnvVariableInput from "@/components/portal/environment/EnvVariableInput.svelte"
export let type export let type
export let name export let name
export let value export let value
export let error export let error
export let placeholder export let placeholder
export let showModal = () => {}
async function handleUpgradePanel() {
await environment.upgradePanelOpened()
$licensing.goToUpgradePage()
}
</script> </script>
<div class="form-row"> <div class="form-row">
<Label>{name}</Label> <Label>{name}</Label>
<EnvDropdown <EnvVariableInput
on:change on:change
on:blur on:blur
type={type === "port" ? "string" : type} type={type === "port" ? "string" : type}
{value} {value}
{error} {error}
{placeholder} {placeholder}
variables={$environment.variables}
environmentVariablesEnabled={$licensing.environmentVariablesEnabled}
{showModal}
{handleUpgradePanel}
/> />
</div> </div>

View File

@ -1,19 +1,10 @@
<script> <script>
import { import { keepOpen, Body, Layout, ModalContent } from "@budibase/bbui"
keepOpen,
Modal,
notifications,
Body,
Layout,
ModalContent,
} from "@budibase/bbui"
import { processStringSync } from "@budibase/string-templates" import { processStringSync } from "@budibase/string-templates"
import CreateEditVariableModal from "@/components/portal/environment/CreateEditVariableModal.svelte"
import ConfigInput from "./ConfigInput.svelte" import ConfigInput from "./ConfigInput.svelte"
import { createValidatedConfigStore } from "./stores/validatedConfig" import { createValidatedConfigStore } from "./stores/validatedConfig"
import { createValidatedNameStore } from "./stores/validatedName" import { createValidatedNameStore } from "./stores/validatedName"
import { get } from "svelte/store" import { get } from "svelte/store"
import { environment } from "@/stores/portal"
export let integration export let integration
export let config export let config
@ -39,24 +30,6 @@
return keepOpen return keepOpen
} }
let createVariableModal
let configValueSetterCallback = () => {}
const showModal = setter => {
configValueSetterCallback = setter
createVariableModal.show()
}
async function saveVariable(data) {
try {
await environment.createVariable(data)
configValueSetterCallback(`{{ env.${data.name} }}`)
createVariableModal.hide()
} catch (err) {
notifications.error(`Failed to create variable: ${err.message}`)
}
}
</script> </script>
<ModalContent <ModalContent
@ -79,7 +52,6 @@
value={$nameStore.name} value={$nameStore.name}
error={$nameStore.error} error={$nameStore.error}
name="Name" name="Name"
showModal={() => showModal(nameStore.updateValue)}
on:blur={nameStore.markActive} on:blur={nameStore.markActive}
on:change={e => nameStore.updateValue(e.detail)} on:change={e => nameStore.updateValue(e.detail)}
/> />
@ -94,15 +66,9 @@
{name} {name}
{config} {config}
{placeholder} {placeholder}
showModal={() =>
showModal(newValue => configStore.updateFieldValue(key, newValue))}
on:blur={() => configStore.markFieldActive(key)} on:blur={() => configStore.markFieldActive(key)}
on:change={e => configStore.updateFieldValue(key, e.detail)} on:change={e => configStore.updateFieldValue(key, e.detail)}
/> />
{/if} {/if}
{/each} {/each}
</ModalContent> </ModalContent>
<Modal bind:this={createVariableModal}>
<CreateEditVariableModal save={saveVariable} />
</Modal>

View File

@ -9,10 +9,10 @@
export let value = "" export let value = ""
export let bindings = [] export let bindings = []
export let placeholder export let placeholder = undefined
export let label export let label
export let disabled = false export let disabled = false
export let options export let options = undefined
export let appendBindingsAsOptions = true export let appendBindingsAsOptions = true
export let error export let error

View File

@ -1,7 +1,7 @@
<script> <script>
import { beforeUrlChange, goto, params } from "@roxi/routify" import { beforeUrlChange, goto, params } from "@roxi/routify"
import { datasources, flags, integrations, queries } from "@/stores/builder" import { datasources, flags, integrations, queries } from "@/stores/builder"
import { environment } from "@/stores/portal"
import { import {
Banner, Banner,
Body, Body,
@ -407,13 +407,6 @@
notifications.error("Error getting datasources") notifications.error("Error getting datasources")
} }
try {
// load the environment variables
await environment.loadVariables()
} catch (error) {
notifications.error(`Error getting environment variables - ${error}`)
}
datasource = $datasources.list.find(ds => ds._id === query?.datasourceId) datasource = $datasources.list.find(ds => ds._id === query?.datasourceId)
const datasourceUrl = datasource?.config.url const datasourceUrl = datasource?.config.url
const qs = query?.fields.queryString const qs = query?.fields.queryString

View File

@ -1,4 +1,4 @@
<script> <script lang="ts">
import { import {
ModalContent, ModalContent,
Button, Button,
@ -14,23 +14,23 @@
const modalContext = getContext(Context.Modal) const modalContext = getContext(Context.Modal)
export let save export let save: any
export let row export let row: { name: string } | undefined = undefined
let deleteDialog let deleteDialog: ConfirmDialog
let name = row?.name || "" let name = row?.name || ""
let productionValue let productionValue: string
let developmentValue let developmentValue: string
let useProductionValue = true let useProductionValue = true
const HasSpacesRegex = /[\\"\s]/ const HasSpacesRegex = /[\\"\s]/
const deleteVariable = async name => { const deleteVariable = async (name: string) => {
try { try {
await environment.deleteVariable(name) await environment.deleteVariable(name)
modalContext.hide() modalContext.hide()
notifications.success("Environment variable deleted") notifications.success("Environment variable deleted")
} catch (err) { } catch (err: any) {
notifications.error(err.message) notifications.error(err.message)
} }
} }
@ -43,7 +43,7 @@
development: developmentValue, development: developmentValue,
}) })
notifications.success("Environment variable saved") notifications.success("Environment variable saved")
} catch (err) { } catch (err: any) {
notifications.error(`Error saving environment variable - ${err.message}`) notifications.error(`Error saving environment variable - ${err.message}`)
} }
} }
@ -55,10 +55,10 @@
title={!row ? "Add new environment variable" : "Edit environment variable"} title={!row ? "Add new environment variable" : "Edit environment variable"}
> >
<Input <Input
disabled={row} disabled={!!row}
label="Name" label="Name"
bind:value={name} bind:value={name}
error={HasSpacesRegex.test(name) && "Must not include spaces"} error={HasSpacesRegex.test(name) ? "Must not include spaces" : undefined}
/> />
<div> <div>
<Heading size="XS">Production</Heading> <Heading size="XS">Production</Heading>
@ -100,12 +100,12 @@
<ConfirmDialog <ConfirmDialog
bind:this={deleteDialog} bind:this={deleteDialog}
onOk={() => { onOk={() => {
deleteVariable(row.name) deleteVariable(name)
}} }}
okText="Delete Environment Variable" okText="Delete Environment Variable"
title="Confirm Deletion" title="Confirm Deletion"
> >
Are you sure you wish to delete the environment variable Are you sure you wish to delete the environment variable
<i>{row.name}?</i> <i>{name}?</i>
This action cannot be undone. This action cannot be undone.
</ConfirmDialog> </ConfirmDialog>

View File

@ -0,0 +1,58 @@
<script lang="ts">
import {
EnvDropdown,
Modal,
notifications,
type EnvDropdownType,
} from "@budibase/bbui"
import { environment, licensing } from "@/stores/portal"
import CreateEditVariableModal from "./CreateEditVariableModal.svelte"
import type { CreateEnvironmentVariableRequest } from "@budibase/types"
import { onMount } from "svelte"
export let label: string = ""
export let type: EnvDropdownType = "text"
export let value: string | undefined = undefined
export let error: string | undefined = undefined
export let placeholder: string | undefined = undefined
let modal: Modal
async function handleUpgradePanel() {
await environment.upgradePanelOpened()
$licensing.goToUpgradePage()
}
async function saveVariable(data: CreateEnvironmentVariableRequest) {
await environment.createVariable(data)
value = `{{ env.${data.name} }}`
modal.hide()
}
onMount(async () => {
try {
// load the environment variables
await environment.loadVariables()
} catch (error) {
notifications.error(`Error getting environment variables - ${error}`)
}
})
</script>
<EnvDropdown
on:change
on:blur
bind:value
{label}
type={type === "port" ? "text" : type}
{error}
{placeholder}
variables={$environment.variables}
environmentVariablesEnabled={$licensing.environmentVariablesEnabled}
showModal={() => modal.show()}
{handleUpgradePanel}
/>
<Modal bind:this={modal}>
<CreateEditVariableModal save={saveVariable} />
</Modal>

View File

@ -1,4 +1,4 @@
<script> <script lang="ts">
import { onMount } from "svelte" import { onMount } from "svelte"
import { import {
ModalContent, ModalContent,
@ -6,32 +6,52 @@
Select, Select,
Body, Body,
Input, Input,
EnvDropdown,
Modal,
notifications, notifications,
} from "@budibase/bbui" } from "@budibase/bbui"
import { AUTH_TYPE_LABELS, AUTH_TYPES } from "./authTypes" import { AUTH_TYPE_LABELS, AUTH_TYPES } from "./authTypes"
import { BindableCombobox } from "@/components/common/bindings" import { BindableCombobox } from "@/components/common/bindings"
import { getAuthBindings, getEnvironmentBindings } from "@/dataBinding" import { getAuthBindings, getEnvironmentBindings } from "@/dataBinding"
import { environment, licensing, auth } from "@/stores/portal" import { environment, licensing } from "@/stores/portal"
import CreateEditVariableModal from "@/components/portal/environment/CreateEditVariableModal.svelte" import EnvVariableInput from "@/components/portal/environment/EnvVariableInput.svelte"
interface FormData {
name?: string
type?: string
basic: {
username?: string
password?: string
}
bearer: {
token?: string
}
}
export let configs export let configs
export let currentConfig export let currentConfig
export let onConfirm export let onConfirm
export let onRemove export let onRemove
let form = { let form: FormData = {
basic: {}, basic: {},
bearer: {}, bearer: {},
} }
let errors = { let errors: FormData = {
basic: {}, basic: {},
bearer: {}, bearer: {},
} }
let blurred = { let blurred: {
name?: boolean
type?: boolean
basic: {
username?: boolean
password?: boolean
}
bearer: {
token?: boolean
}
} = {
basic: {}, basic: {},
bearer: {}, bearer: {},
} }
@ -39,19 +59,7 @@
let hasErrors = false let hasErrors = false
let hasChanged = false let hasChanged = false
let createVariableModal
let formFieldkey
onMount(async () => { onMount(async () => {
try {
await environment.loadVariables()
if ($auth.user) {
await licensing.init()
}
} catch (err) {
console.error(err)
}
if (currentConfig) { if (currentConfig) {
deconstructConfig() deconstructConfig()
} }
@ -79,7 +87,7 @@
* map the form into a new config to save by type * map the form into a new config to save by type
*/ */
const constructConfig = () => { const constructConfig = () => {
const newConfig = { const newConfig: any = {
name: form.name, name: form.name,
type: form.type, type: form.type,
} }
@ -123,10 +131,10 @@
errors.name = errors.name =
// check for duplicate excluding the current config // check for duplicate excluding the current config
configs.find( configs.find(
c => c.name === form.name && c.name !== currentConfig?.name (c: any) => c.name === form.name && c.name !== currentConfig?.name
) !== undefined ) !== undefined
? "Name must be unique" ? "Name must be unique"
: null : undefined
} }
// Name required // Name required
else { else {
@ -137,17 +145,17 @@
// TYPE // TYPE
const typeError = () => { const typeError = () => {
errors.type = form.type ? null : "Type is required" errors.type = form.type ? undefined : "Type is required"
return !!errors.type return !!errors.type
} }
// BASIC AUTH // BASIC AUTH
const basicAuthErrors = () => { const basicAuthErrors = () => {
errors.basic.username = form.basic.username errors.basic.username = form.basic.username
? null ? undefined
: "Username is required" : "Username is required"
errors.basic.password = form.basic.password errors.basic.password = form.basic.password
? null ? undefined
: "Password is required" : "Password is required"
return !!(errors.basic.username || errors.basic.password || commonError) return !!(errors.basic.username || errors.basic.password || commonError)
@ -155,7 +163,7 @@
// BEARER TOKEN // BEARER TOKEN
const bearerTokenErrors = () => { const bearerTokenErrors = () => {
errors.bearer.token = form.bearer.token ? null : "Token is required" errors.bearer.token = form.bearer.token ? undefined : "Token is required"
return !!(errors.bearer.token || commonError) return !!(errors.bearer.token || commonError)
} }
@ -169,16 +177,6 @@
} }
} }
const save = async data => {
try {
await environment.createVariable(data)
form.basic[formFieldkey] = `{{ env.${data.name} }}`
createVariableModal.hide()
} catch (err) {
notifications.error(`Failed to create variable: ${err.message}`)
}
}
const onFieldChange = () => { const onFieldChange = () => {
checkErrors() checkErrors()
checkChanged() checkChanged()
@ -188,15 +186,13 @@
onConfirm(constructConfig()) onConfirm(constructConfig())
} }
async function handleUpgradePanel() { onMount(async () => {
await environment.upgradePanelOpened() try {
$licensing.goToUpgradePage() await environment.loadVariables()
} } catch (error) {
notifications.error(`Error getting environment variables - ${error}`)
function showModal(key) { }
formFieldkey = key })
createVariableModal.show()
}
</script> </script>
<ModalContent <ModalContent
@ -221,7 +217,7 @@
bind:value={form.name} bind:value={form.name}
on:change={onFieldChange} on:change={onFieldChange}
on:blur={() => (blurred.name = true)} on:blur={() => (blurred.name = true)}
error={blurred.name ? errors.name : null} error={blurred.name ? errors.name : undefined}
/> />
<Select <Select
label="Type" label="Type"
@ -229,31 +225,24 @@
on:change={onFieldChange} on:change={onFieldChange}
options={AUTH_TYPE_LABELS} options={AUTH_TYPE_LABELS}
on:blur={() => (blurred.type = true)} on:blur={() => (blurred.type = true)}
error={blurred.type ? errors.type : null} error={blurred.type ? errors.type : undefined}
/> />
{#if form.type === AUTH_TYPES.BASIC} {#if form.type === AUTH_TYPES.BASIC}
<EnvDropdown <EnvVariableInput
label="Username" label="Username"
bind:value={form.basic.username} bind:value={form.basic.username}
on:change={onFieldChange} on:change={onFieldChange}
on:blur={() => (blurred.basic.username = true)} on:blur={() => (blurred.basic.username = true)}
error={blurred.basic.username ? errors.basic.username : null} error={blurred.basic.username ? errors.basic.username : undefined}
showModal={() => showModal("configKey")}
variables={$environment.variables}
environmentVariablesEnabled={$licensing.environmentVariablesEnabled}
{handleUpgradePanel}
/> />
<EnvDropdown
<EnvVariableInput
label="Password" label="Password"
type="password" type="password"
bind:value={form.basic.password} bind:value={form.basic.password}
on:change={onFieldChange} on:change={onFieldChange}
on:blur={() => (blurred.basic.password = true)} on:blur={() => (blurred.basic.password = true)}
error={blurred.basic.password ? errors.basic.password : null} error={blurred.basic.password ? errors.basic.password : undefined}
showModal={() => showModal("configKey")}
variables={$environment.variables}
environmentVariablesEnabled={$licensing.environmentVariablesEnabled}
{handleUpgradePanel}
/> />
{/if} {/if}
{#if form.type === AUTH_TYPES.BEARER} {#if form.type === AUTH_TYPES.BEARER}
@ -274,16 +263,10 @@
blurred.bearer.token = true blurred.bearer.token = true
onFieldChange() onFieldChange()
}} }}
allowJS={false}
placeholder="Token" placeholder="Token"
appendBindingsAsOptions={true} appendBindingsAsOptions={true}
drawerEnabled={false}
error={blurred.bearer.token ? errors.bearer.token : null} error={blurred.bearer.token ? errors.bearer.token : null}
/> />
{/if} {/if}
</Layout> </Layout>
</ModalContent> </ModalContent>
<Modal bind:this={createVariableModal}>
<CreateEditVariableModal {save} />
</Modal>

View File

@ -1,14 +1,15 @@
<script> <script>
import { Heading, Layout } from "@budibase/bbui" import { Heading, Layout, notifications } from "@budibase/bbui"
import KeyValueBuilder from "@/components/integration/KeyValueBuilder.svelte" import KeyValueBuilder from "@/components/integration/KeyValueBuilder.svelte"
import ViewDynamicVariables from "./ViewDynamicVariables.svelte" import ViewDynamicVariables from "./ViewDynamicVariables.svelte"
import { getEnvironmentBindings } from "@/dataBinding" import { getEnvironmentBindings } from "@/dataBinding"
import { licensing } from "@/stores/portal" import { environment, licensing } from "@/stores/portal"
import { queries } from "@/stores/builder" import { queries } from "@/stores/builder"
import { cloneDeep } from "lodash/fp" import { cloneDeep } from "lodash/fp"
import SaveDatasourceButton from "../SaveDatasourceButton.svelte" import SaveDatasourceButton from "../SaveDatasourceButton.svelte"
import Panel from "../Panel.svelte" import Panel from "../Panel.svelte"
import Tooltip from "../Tooltip.svelte" import Tooltip from "../Tooltip.svelte"
import { onMount } from "svelte"
export let datasource export let datasource
@ -27,6 +28,14 @@
updatedDatasource.config.staticVariables = newStaticVariables updatedDatasource.config.staticVariables = newStaticVariables
} }
onMount(async () => {
try {
await environment.loadVariables()
} catch (error) {
notifications.error(`Error getting environment variables - ${error}`)
}
})
</script> </script>
<Panel> <Panel>

View File

@ -24,7 +24,6 @@
auth, auth,
admin, admin,
licensing, licensing,
environment,
enrichedApps, enrichedApps,
sortBy, sortBy,
} from "@/stores/portal" } from "@/stores/portal"
@ -162,7 +161,6 @@
onMount(async () => { onMount(async () => {
try { try {
await environment.loadVariables()
// If the portal is loaded from an external URL with a template param // If the portal is loaded from an external URL with a template param
const initInfo = await auth.getInitInfo() const initInfo = await auth.getInitInfo()
if (initInfo?.init_template) { if (initInfo?.init_template) {