diff --git a/lerna.json b/lerna.json index c893e4b402..18c131fe56 100644 --- a/lerna.json +++ b/lerna.json @@ -1,6 +1,6 @@ { "$schema": "node_modules/lerna/schemas/lerna-schema.json", - "version": "3.4.6", + "version": "3.4.7", "npmClient": "yarn", "concurrency": 20, "command": { diff --git a/packages/builder/package.json b/packages/builder/package.json index 0fa4687242..a70d19209e 100644 --- a/packages/builder/package.json +++ b/packages/builder/package.json @@ -53,7 +53,7 @@ "@budibase/shared-core": "*", "@budibase/string-templates": "*", "@budibase/types": "*", - "@codemirror/autocomplete": "^6.7.1", + "@codemirror/autocomplete": "6.9.0", "@codemirror/commands": "^6.2.4", "@codemirror/lang-javascript": "^6.1.8", "@codemirror/language": "^6.6.0", diff --git a/packages/builder/src/components/common/CodeEditor/CodeEditor.svelte b/packages/builder/src/components/common/CodeEditor/CodeEditor.svelte index bc88f0f981..2acde47539 100644 --- a/packages/builder/src/components/common/CodeEditor/CodeEditor.svelte +++ b/packages/builder/src/components/common/CodeEditor/CodeEditor.svelte @@ -45,10 +45,11 @@ import { EditorModes } from "./" import { themeStore } from "@/stores/portal" import type { EditorMode } from "@budibase/types" + import type { BindingCompletion } from "@/types" export let label: string | undefined = undefined // TODO: work out what best type fits this - export let completions: any[] = [] + export let completions: BindingCompletion[] = [] export let mode: EditorMode = EditorModes.Handlebars export let value: string | null = "" export let placeholder: string | null = null diff --git a/packages/builder/src/components/common/CodeEditor/index.ts b/packages/builder/src/components/common/CodeEditor/index.ts index 0c974e0bf4..5529484665 100644 --- a/packages/builder/src/components/common/CodeEditor/index.ts +++ b/packages/builder/src/components/common/CodeEditor/index.ts @@ -1,13 +1,10 @@ import { getManifest } from "@budibase/string-templates" import sanitizeHtml from "sanitize-html" import { groupBy } from "lodash" -import { - BindingCompletion, - EditorModesMap, - Helper, - Snippet, -} from "@budibase/types" +import { EditorModesMap, Helper, Snippet } from "@budibase/types" import { CompletionContext } from "@codemirror/autocomplete" +import { EditorView } from "@codemirror/view" +import { BindingCompletion, BindingCompletionOption } from "@/types" export const EditorModes: EditorModesMap = { JS: { @@ -25,15 +22,7 @@ export const EditorModes: EditorModesMap = { }, } -export const SECTIONS = { - HB_HELPER: { - name: "Helper", - type: "helper", - icon: "Code", - }, -} - -export const buildHelperInfoNode = (completion: any, helper: Helper) => { +const buildHelperInfoNode = (helper: Helper) => { const ele = document.createElement("div") ele.classList.add("info-bubble") @@ -65,7 +54,7 @@ const toSpectrumIcon = (name: string) => { ` } -export const buildSectionHeader = ( +const buildSectionHeader = ( type: string, sectionName: string, icon: string, @@ -84,30 +73,27 @@ export const buildSectionHeader = ( } } -export const helpersToCompletion = ( +const helpersToCompletion = ( helpers: Record, mode: { name: "javascript" | "handlebars" } -) => { - const { type, name: sectionName, icon } = SECTIONS.HB_HELPER - const helperSection = buildSectionHeader(type, sectionName, icon, 99) +): BindingCompletionOption[] => { + const helperSection = buildSectionHeader("helper", "Helpers", "Code", 99) return Object.keys(helpers).flatMap(helperName => { - let helper = helpers[helperName] + const helper = helpers[helperName] return { label: helperName, - info: (completion: BindingCompletion) => { - return buildHelperInfoNode(completion, helper) - }, + info: () => buildHelperInfoNode(helper), type: "helper", section: helperSection, detail: "Function", apply: ( - view: any, - completion: BindingCompletion, + view: EditorView, + _completion: BindingCompletionOption, from: number, to: number ) => { - insertBinding(view, from, to, helperName, mode) + insertBinding(view, from, to, helperName, mode, AutocompleteType.HELPER) }, } }) @@ -115,7 +101,7 @@ export const helpersToCompletion = ( export const getHelperCompletions = (mode: { name: "javascript" | "handlebars" -}) => { +}): BindingCompletionOption[] => { // TODO: manifest needs to be properly typed const manifest: any = getManifest() return Object.keys(manifest).flatMap(key => { @@ -123,49 +109,33 @@ export const getHelperCompletions = (mode: { }) } -export const snippetAutoComplete = (snippets: Snippet[]) => { - return function myCompletions(context: CompletionContext) { - if (!snippets?.length) { - return null - } - const word = context.matchBefore(/\w*/) - if (!word || (word.from == word.to && !context.explicit)) { - return null - } - return { - from: word.from, - options: snippets.map(snippet => ({ - label: `snippets.${snippet.name}`, - type: "text", - simple: true, - apply: ( - view: any, - completion: BindingCompletion, - from: number, - to: number - ) => { - insertSnippet(view, from, to, completion.label) - }, - })), - } - } +export const snippetAutoComplete = (snippets: Snippet[]): BindingCompletion => { + return setAutocomplete( + snippets.map(snippet => ({ + section: buildSectionHeader("snippets", "Snippets", "Code", 100), + label: `snippets.${snippet.name}`, + displayLabel: snippet.name, + })) + ) } -const bindingFilter = (options: BindingCompletion[], query: string) => { +const bindingFilter = (options: BindingCompletionOption[], query: string) => { return options.filter(completion => { - const section_parsed = completion.section.name.toLowerCase() + const section_parsed = completion.section?.toString().toLowerCase() const label_parsed = completion.label.toLowerCase() const query_parsed = query.toLowerCase() return ( - section_parsed.includes(query_parsed) || + section_parsed?.includes(query_parsed) || label_parsed.includes(query_parsed) ) }) } -export const hbAutocomplete = (baseCompletions: BindingCompletion[]) => { - async function coreCompletion(context: CompletionContext) { +export const hbAutocomplete = ( + baseCompletions: BindingCompletionOption[] +): BindingCompletion => { + function coreCompletion(context: CompletionContext) { let bindingStart = context.matchBefore(EditorModes.Handlebars.match) let options = baseCompletions || [] @@ -191,9 +161,15 @@ export const hbAutocomplete = (baseCompletions: BindingCompletion[]) => { return coreCompletion } -export const jsAutocomplete = (baseCompletions: BindingCompletion[]) => { - async function coreCompletion(context: CompletionContext) { - let jsBinding = context.matchBefore(/\$\("[\s\w]*/) +function wrappedAutocompleteMatch(context: CompletionContext) { + return context.matchBefore(/\$\("[\s\w]*/) +} + +export const jsAutocomplete = ( + baseCompletions: BindingCompletionOption[] +): BindingCompletion => { + function coreCompletion(context: CompletionContext) { + let jsBinding = wrappedAutocompleteMatch(context) let options = baseCompletions || [] if (jsBinding) { @@ -217,10 +193,42 @@ export const jsAutocomplete = (baseCompletions: BindingCompletion[]) => { return coreCompletion } -export const buildBindingInfoNode = ( - completion: BindingCompletion, - binding: any -) => { +export const jsHelperAutocomplete = ( + baseCompletions: BindingCompletionOption[] +): BindingCompletion => { + return setAutocomplete( + baseCompletions.map(helper => ({ + ...helper, + displayLabel: helper.label, + label: `helpers.${helper.label}()`, + })) + ) +} + +function setAutocomplete( + options: BindingCompletionOption[] +): BindingCompletion { + return function (context: CompletionContext) { + if (wrappedAutocompleteMatch(context)) { + return null + } + + const word = context.matchBefore(/\b\w*(\.\w*)?/) + if (!word || (word.from == word.to && !context.explicit)) { + return null + } + + return { + from: word.from, + options, + } + } +} + +const buildBindingInfoNode = (binding: { + valueHTML: string + value: string | null +}) => { if (!binding.valueHTML || binding.value == null) { return null } @@ -278,18 +286,28 @@ export function jsInsert( return parsedInsert } +const enum AutocompleteType { + BINDING, + HELPER, + TEXT, +} + // Autocomplete apply behaviour -export const insertBinding = ( - view: any, +const insertBinding = ( + view: EditorView, from: number, to: number, text: string, - mode: { name: "javascript" | "handlebars" } + mode: { name: "javascript" | "handlebars" }, + type: AutocompleteType ) => { let parsedInsert if (mode.name == "javascript") { - parsedInsert = jsInsert(view.state.doc?.toString(), from, to, text) + parsedInsert = jsInsert(view.state.doc?.toString(), from, to, text, { + helper: type === AutocompleteType.HELPER, + disableWrapping: type === AutocompleteType.TEXT, + }) } else if (mode.name == "handlebars") { parsedInsert = hbInsert(view.state.doc?.toString(), from, to, text) } else { @@ -319,30 +337,11 @@ export const insertBinding = ( }) } -export const insertSnippet = ( - view: any, - from: number, - to: number, - text: string -) => { - let cursorPos = from + text.length - view.dispatch({ - changes: { - from, - to, - insert: text, - }, - selection: { - anchor: cursorPos, - }, - }) -} - // TODO: typing in this function isn't great export const bindingsToCompletions = ( bindings: any, mode: { name: "javascript" | "handlebars" } -) => { +): BindingCompletionOption[] => { const bindingByCategory = groupBy(bindings, "category") const categoryMeta = bindings?.reduce((acc: any, ele: any) => { acc[ele.category] = acc[ele.category] || {} @@ -356,46 +355,54 @@ export const bindingsToCompletions = ( return acc }, {}) - const completions = Object.keys(bindingByCategory).reduce( - (comps: any, catKey: string) => { - const { icon, rank } = categoryMeta[catKey] || {} + const completions = Object.keys(bindingByCategory).reduce< + BindingCompletionOption[] + >((comps, catKey) => { + const { icon, rank } = categoryMeta[catKey] || {} - const bindingSectionHeader = buildSectionHeader( - // @ts-ignore something wrong with this - logically this should be dictionary - bindingByCategory.type, - catKey, - icon || "", - typeof rank == "number" ? rank : 1 - ) + const bindingSectionHeader = buildSectionHeader( + // @ts-ignore something wrong with this - logically this should be dictionary + bindingByCategory.type, + catKey, + icon || "", + typeof rank == "number" ? rank : 1 + ) - return [ - ...comps, - ...bindingByCategory[catKey].reduce((acc, binding) => { + comps.push( + ...bindingByCategory[catKey].reduce( + (acc, binding) => { let displayType = binding.fieldSchema?.type || binding.display?.type acc.push({ label: binding.display?.name || binding.readableBinding || "NO NAME", - info: (completion: BindingCompletion) => { - return buildBindingInfoNode(completion, binding) - }, + info: () => buildBindingInfoNode(binding), type: "binding", detail: displayType, section: bindingSectionHeader, apply: ( - view: any, - completion: BindingCompletion, + view: EditorView, + _completion: BindingCompletionOption, from: number, to: number ) => { - insertBinding(view, from, to, binding.readableBinding, mode) + insertBinding( + view, + from, + to, + binding.readableBinding, + mode, + AutocompleteType.BINDING + ) }, }) return acc - }, []), - ] - }, - [] - ) + }, + [] + ) + ) + + return comps + }, []) return completions } diff --git a/packages/builder/src/components/common/bindings/BindingPanel.svelte b/packages/builder/src/components/common/bindings/BindingPanel.svelte index ffb477012c..4bd37bf72c 100644 --- a/packages/builder/src/components/common/bindings/BindingPanel.svelte +++ b/packages/builder/src/components/common/bindings/BindingPanel.svelte @@ -23,6 +23,7 @@ snippetAutoComplete, EditorModes, bindingsToCompletions, + jsHelperAutocomplete, } from "../CodeEditor" import BindingSidePanel from "./BindingSidePanel.svelte" import EvaluationSidePanel from "./EvaluationSidePanel.svelte" @@ -34,7 +35,6 @@ import { BindingMode, SidePanel } from "@budibase/types" import type { EnrichedBinding, - BindingCompletion, Snippet, Helper, CaretPositionFn, @@ -42,7 +42,7 @@ JSONValue, } from "@budibase/types" import type { Log } from "@budibase/string-templates" - import type { CompletionContext } from "@codemirror/autocomplete" + import type { BindingCompletion, BindingCompletionOption } from "@/types" const dispatch = createEventDispatcher() @@ -91,7 +91,10 @@ $: bindingCompletions = bindingsToCompletions(enrichedBindings, editorMode) $: bindingHelpers = new BindingHelpers(getCaretPosition, insertAtPos) $: hbsCompletions = getHBSCompletions(bindingCompletions) - $: jsCompletions = getJSCompletions(bindingCompletions, snippets, useSnippets) + $: jsCompletions = getJSCompletions(bindingCompletions, snippets, { + useHelpers: allowHelpers, + useSnippets, + }) $: { // Ensure a valid side panel option is always selected if (sidePanel && !sidePanelOptions.includes(sidePanel)) { @@ -99,7 +102,7 @@ } } - const getHBSCompletions = (bindingCompletions: BindingCompletion[]) => { + const getHBSCompletions = (bindingCompletions: BindingCompletionOption[]) => { return [ hbAutocomplete([ ...bindingCompletions, @@ -109,17 +112,23 @@ } const getJSCompletions = ( - bindingCompletions: BindingCompletion[], + bindingCompletions: BindingCompletionOption[], snippets: Snippet[] | null, - useSnippets?: boolean + config: { + useHelpers: boolean + useSnippets: boolean + } ) => { - const completions: ((_: CompletionContext) => any)[] = [ - jsAutocomplete([ - ...bindingCompletions, - ...getHelperCompletions(EditorModes.JS), - ]), - ] - if (useSnippets && snippets) { + const completions: BindingCompletion[] = [] + if (bindingCompletions.length) { + completions.push(jsAutocomplete([...bindingCompletions])) + } + if (config.useHelpers) { + completions.push( + jsHelperAutocomplete([...getHelperCompletions(EditorModes.JS)]) + ) + } + if (config.useSnippets && snippets) { completions.push(snippetAutoComplete(snippets)) } return completions @@ -381,7 +390,7 @@ autofocus={autofocusEditor} placeholder={placeholder || "Add bindings by typing $ or use the menu on the right"} - jsBindingWrapping + jsBindingWrapping={bindingCompletions.length > 0} /> {/key} {/if} diff --git a/packages/builder/src/components/common/bindings/SnippetDrawer.svelte b/packages/builder/src/components/common/bindings/SnippetDrawer.svelte index f10c44f81f..4862217b13 100644 --- a/packages/builder/src/components/common/bindings/SnippetDrawer.svelte +++ b/packages/builder/src/components/common/bindings/SnippetDrawer.svelte @@ -118,6 +118,7 @@ allowHBS={false} allowJS allowSnippets={false} + allowHelpers={false} showTabBar={false} placeholder="return function(input) ❴ ... ❵" value={code} diff --git a/packages/builder/src/pages/builder/app/[application]/design/[screenId]/[componentId]/new/_components/NewComponentPanel.svelte b/packages/builder/src/pages/builder/app/[application]/design/[screenId]/[componentId]/new/_components/NewComponentPanel.svelte index aa0b26f6b7..d13d72b89f 100644 --- a/packages/builder/src/pages/builder/app/[application]/design/[screenId]/[componentId]/new/_components/NewComponentPanel.svelte +++ b/packages/builder/src/pages/builder/app/[application]/design/[screenId]/[componentId]/new/_components/NewComponentPanel.svelte @@ -13,6 +13,11 @@ import { fly } from "svelte/transition" import { findComponentPath } from "@/helpers/components" + // Smallest possible 1x1 transparent GIF + const ghost = new Image(1, 1) + ghost.src = + "data:image/gif;base64,R0lGODlhAQABAIAAAP///wAAACH5BAEAAAAALAAAAAABAAEAAAICRAEAOw==" + let searchString let searchRef let selectedIndex @@ -217,7 +222,8 @@ } }) - const onDragStart = component => { + const onDragStart = (e, component) => { + e.dataTransfer.setDragImage(ghost, 0, 0) previewStore.startDrag(component) } @@ -250,13 +256,12 @@ {#each category.children as component}
onDragStart(component.component)} + on:dragstart={e => onDragStart(e, component.component)} on:dragend={onDragEnd} class="component" class:selected={selectedIndex === orderMap[component.component]} on:click={() => addComponent(component.component)} - on:mouseover={() => (selectedIndex = null)} - on:focus + on:mouseenter={() => (selectedIndex = null)} > {component.name} @@ -308,7 +313,6 @@ } .component:hover { background: var(--spectrum-global-color-gray-300); - cursor: pointer; } .component :global(.spectrum-Body) { line-height: 1.2 !important; diff --git a/packages/builder/src/pages/builder/app/[application]/design/[screenId]/_components/AppPreview.svelte b/packages/builder/src/pages/builder/app/[application]/design/[screenId]/_components/AppPreview.svelte index ba600c8eef..59548ada01 100644 --- a/packages/builder/src/pages/builder/app/[application]/design/[screenId]/_components/AppPreview.svelte +++ b/packages/builder/src/pages/builder/app/[application]/design/[screenId]/_components/AppPreview.svelte @@ -189,8 +189,8 @@ } else if (type === "reload-plugin") { await componentStore.refreshDefinitions() } else if (type === "drop-new-component") { - const { component, parent, index } = data - await componentStore.create(component, null, parent, index) + const { component, parent, index, props } = data + await componentStore.create(component, props, parent, index) } else if (type === "add-parent-component") { const { componentId, parentType } = data await componentStore.addParent(componentId, parentType) diff --git a/packages/builder/src/stores/builder/app.ts b/packages/builder/src/stores/builder/app.ts index 3c8ed4afc1..abebb5d9f1 100644 --- a/packages/builder/src/stores/builder/app.ts +++ b/packages/builder/src/stores/builder/app.ts @@ -39,7 +39,7 @@ interface AppMetaState { appInstance: { _id: string } | null initialised: boolean hasAppPackage: boolean - usedPlugins: Plugin[] | null + usedPlugins: Plugin[] automations: AutomationSettings routes: { [key: string]: any } version?: string @@ -76,7 +76,7 @@ export const INITIAL_APP_META_STATE: AppMetaState = { appInstance: null, initialised: false, hasAppPackage: false, - usedPlugins: null, + usedPlugins: [], automations: {}, routes: {}, } @@ -109,7 +109,7 @@ export class AppMetaStore extends BudiStore { appInstance: app.instance, revertableVersion: app.revertableVersion, upgradableVersion: app.upgradableVersion, - usedPlugins: app.usedPlugins || null, + usedPlugins: app.usedPlugins || [], icon: app.icon, features: { ...INITIAL_APP_META_STATE.features, diff --git a/packages/builder/src/stores/builder/components.ts b/packages/builder/src/stores/builder/components.ts index b1198ca7b4..b3e897fa3c 100644 --- a/packages/builder/src/stores/builder/components.ts +++ b/packages/builder/src/stores/builder/components.ts @@ -11,6 +11,7 @@ import { findComponentParent, findAllMatchingComponents, makeComponentUnique, + findComponentType, } from "@/helpers/components" import { getComponentFieldOptions } from "@/helpers/formFields" import { selectedScreen } from "./screens" @@ -139,10 +140,6 @@ export class ComponentStore extends BudiStore { /** * Retrieve the component definition object - * @param {string} componentType - * @example - * '@budibase/standard-components/container' - * @returns {object} */ getDefinition(componentType: string) { if (!componentType) { @@ -151,10 +148,6 @@ export class ComponentStore extends BudiStore { return get(this.store).components[componentType] } - /** - * - * @returns {object} - */ getDefaultDatasource() { // Ignore users table const validTables = get(tables).list.filter(x => x._id !== "ta_users") @@ -188,8 +181,6 @@ export class ComponentStore extends BudiStore { /** * Takes an enriched component instance and applies any required migration * logic - * @param {object} enrichedComponent - * @returns {object} migrated Component */ migrateSettings(enrichedComponent: Component) { const componentPrefix = "@budibase/standard-components" @@ -230,22 +221,15 @@ export class ComponentStore extends BudiStore { for (let setting of filterableTypes || []) { const isLegacy = Array.isArray(enrichedComponent[setting.key]) if (isLegacy) { - const processedSetting = utils.processSearchFilters( + enrichedComponent[setting.key] = utils.processSearchFilters( enrichedComponent[setting.key] ) - enrichedComponent[setting.key] = processedSetting migrated = true } } return migrated } - /** - * - * @param {object} component - * @param {object} opts - * @returns - */ enrichEmptySettings( component: Component, opts: { screen?: Screen; parent?: Component; useDefaultValues?: boolean } @@ -280,14 +264,25 @@ export class ComponentStore extends BudiStore { type: "table", } } else if (setting.type === "dataProvider") { - // Pick closest data provider where required + let providerId + + // Pick closest parent data provider if one exists const path = findComponentPath(screen.props, treeId) const providers = path.filter((component: Component) => component._component?.endsWith("/dataprovider") ) - if (providers.length) { - const id = providers[providers.length - 1]?._id - component[setting.key] = `{{ literal ${safe(id)} }}` + providerId = providers[providers.length - 1]?._id + + // If none in our direct path, select the first one the screen + if (!providerId) { + providerId = findComponentType( + screen.props, + "@budibase/standard-components/dataprovider" + )?._id + } + + if (providerId) { + component[setting.key] = `{{ literal ${safe(providerId)} }}` } } else if (setting.type.startsWith("field/")) { // Autofill form field names @@ -316,6 +311,8 @@ export class ComponentStore extends BudiStore { component[setting.key] = fieldOptions[0] component.label = fieldOptions[0] } + } else if (setting.type === "icon") { + component[setting.key] = "ri-star-fill" } else if (useDefaultValues && setting.defaultValue !== undefined) { // Use default value where required component[setting.key] = setting.defaultValue @@ -427,17 +424,10 @@ export class ComponentStore extends BudiStore { } } - /** - * - * @param {string} componentName - * @param {object} presetProps - * @param {object} parent - * @returns - */ createInstance( componentType: string, - presetProps: any, - parent: any + presetProps?: Record, + parent?: Component ): Component | null { const screen = get(selectedScreen) if (!screen) { @@ -463,7 +453,7 @@ export class ComponentStore extends BudiStore { _id: Helpers.uuid(), _component: definition.component, _styles: { - normal: {}, + normal: { ...presetProps?._styles?.normal }, hover: {}, active: {}, }, @@ -512,19 +502,11 @@ export class ComponentStore extends BudiStore { } } - /** - * - * @param {string} componentName - * @param {object} presetProps - * @param {object} parent - * @param {number} index - * @returns - */ async create( componentType: string, - presetProps: any, - parent: Component, - index: number + presetProps?: Record, + parent?: Component, + index?: number ) { const state = get(this.store) const componentInstance = this.createInstance( @@ -611,13 +593,6 @@ export class ComponentStore extends BudiStore { return componentInstance } - /** - * - * @param {function} patchFn - * @param {string} componentId - * @param {string} screenId - * @returns - */ async patch( patchFn: (component: Component, screen: Screen) => any, componentId?: string, @@ -652,11 +627,6 @@ export class ComponentStore extends BudiStore { await screenStore.patch(patchScreen, screenId) } - /** - * - * @param {object} component - * @returns - */ async delete(component: Component) { if (!component) { return @@ -737,13 +707,6 @@ export class ComponentStore extends BudiStore { }) } - /** - * - * @param {object} targetComponent - * @param {string} mode - * @param {object} targetScreen - * @returns - */ async paste( targetComponent: Component, mode: string, @@ -1101,6 +1064,7 @@ export class ComponentStore extends BudiStore { async updateStyles(styles: Record, id: string) { const patchFn = (component: Component) => { + delete component._placeholder component._styles.normal = { ...component._styles.normal, ...styles, @@ -1231,7 +1195,7 @@ export class ComponentStore extends BudiStore { } // Create new parent instance - const newParentDefinition = this.createInstance(parentType, null, parent) + const newParentDefinition = this.createInstance(parentType) if (!newParentDefinition) { return } @@ -1267,10 +1231,6 @@ export class ComponentStore extends BudiStore { /** * Check if the components settings have been cached - * @param {string} componentType - * @example - * '@budibase/standard-components/container' - * @returns {boolean} */ isCached(componentType: string) { const settings = get(this.store).settingsCache @@ -1279,11 +1239,6 @@ export class ComponentStore extends BudiStore { /** * Cache component settings - * @param {string} componentType - * @param {object} definition - * @example - * '@budibase/standard-components/container' - * @returns {array} the settings */ cacheSettings(componentType: string, definition: ComponentDefinition | null) { let settings: ComponentSetting[] = [] @@ -1313,12 +1268,7 @@ export class ComponentStore extends BudiStore { /** * Retrieve an array of the component settings. * These settings are cached because they cannot change at run time. - * * Searches a component's definition for a setting matching a certain predicate. - * @param {string} componentType - * @example - * '@budibase/standard-components/container' - * @returns {Array} */ getComponentSettings(componentType: string) { if (!componentType) { diff --git a/packages/builder/src/stores/builder/navigation.ts b/packages/builder/src/stores/builder/navigation.ts index 1574efee2a..1ef019a11c 100644 --- a/packages/builder/src/stores/builder/navigation.ts +++ b/packages/builder/src/stores/builder/navigation.ts @@ -4,15 +4,13 @@ import { appStore } from "@/stores/builder" import { BudiStore } from "../BudiStore" import { AppNavigation, AppNavigationLink, UIObject } from "@budibase/types" -interface BuilderNavigationStore extends AppNavigation {} - export const INITIAL_NAVIGATION_STATE = { navigation: "Top", links: [], textAlign: "Left", } -export class NavigationStore extends BudiStore { +export class NavigationStore extends BudiStore { constructor() { super(INITIAL_NAVIGATION_STATE) } diff --git a/packages/builder/src/stores/builder/preview.ts b/packages/builder/src/stores/builder/preview.ts index 87b2b9355e..a382eeefb0 100644 --- a/packages/builder/src/stores/builder/preview.ts +++ b/packages/builder/src/stores/builder/preview.ts @@ -54,7 +54,7 @@ export class PreviewStore extends BudiStore { })) } - startDrag(component: any) { + async startDrag(component: string) { this.sendEvent("dragging-new-component", { dragging: true, component, diff --git a/packages/builder/src/types/bindings.ts b/packages/builder/src/types/bindings.ts new file mode 100644 index 0000000000..00571f1d8b --- /dev/null +++ b/packages/builder/src/types/bindings.ts @@ -0,0 +1,8 @@ +import { CompletionContext, Completion } from "@codemirror/autocomplete" + +export type BindingCompletion = (context: CompletionContext) => { + from: number + options: Completion[] +} | null + +export type BindingCompletionOption = Completion diff --git a/packages/builder/src/types/index.ts b/packages/builder/src/types/index.ts new file mode 100644 index 0000000000..f280d975b4 --- /dev/null +++ b/packages/builder/src/types/index.ts @@ -0,0 +1 @@ +export * from "./bindings" diff --git a/packages/client/package.json b/packages/client/package.json index 2ae049f6d0..72be403698 100644 --- a/packages/client/package.json +++ b/packages/client/package.json @@ -5,7 +5,7 @@ "module": "dist/budibase-client.js", "main": "dist/budibase-client.js", "type": "module", - "svelte": "src/index.js", + "svelte": "src/index.ts", "exports": { ".": { "import": "./dist/budibase-client.js", diff --git a/packages/client/src/api/api.ts b/packages/client/src/api/api.ts index b944f7bd7c..564f401164 100644 --- a/packages/client/src/api/api.ts +++ b/packages/client/src/api/api.ts @@ -1,10 +1,6 @@ import { createAPIClient } from "@budibase/frontend-core" import { authStore } from "../stores/auth" -import { - notificationStore, - devToolsEnabled, - devToolsStore, -} from "../stores/index" +import { notificationStore, devToolsEnabled, devToolsStore } from "../stores" import { get } from "svelte/store" export const API = createAPIClient({ diff --git a/packages/client/src/components/Block.svelte b/packages/client/src/components/Block.svelte index 48c11f152a..5f39f7eef1 100644 --- a/packages/client/src/components/Block.svelte +++ b/packages/client/src/components/Block.svelte @@ -1,7 +1,7 @@ diff --git a/packages/client/src/components/context/RowSelectionProvider.svelte b/packages/client/src/components/context/RowSelectionProvider.svelte index 2c87a5fa00..da731e6f05 100644 --- a/packages/client/src/components/context/RowSelectionProvider.svelte +++ b/packages/client/src/components/context/RowSelectionProvider.svelte @@ -1,6 +1,6 @@ diff --git a/packages/client/src/components/context/SnippetsProvider.svelte b/packages/client/src/components/context/SnippetsProvider.svelte index 53fa1e8b7f..104147ecf7 100644 --- a/packages/client/src/components/context/SnippetsProvider.svelte +++ b/packages/client/src/components/context/SnippetsProvider.svelte @@ -1,6 +1,6 @@ diff --git a/packages/client/src/components/context/StateBindingsProvider.svelte b/packages/client/src/components/context/StateBindingsProvider.svelte index a1166594a8..4ef99228c1 100644 --- a/packages/client/src/components/context/StateBindingsProvider.svelte +++ b/packages/client/src/components/context/StateBindingsProvider.svelte @@ -1,6 +1,6 @@ diff --git a/packages/client/src/components/context/UserBindingsProvider.svelte b/packages/client/src/components/context/UserBindingsProvider.svelte index 98769cf76a..02293e2f50 100644 --- a/packages/client/src/components/context/UserBindingsProvider.svelte +++ b/packages/client/src/components/context/UserBindingsProvider.svelte @@ -1,7 +1,7 @@ diff --git a/packages/client/src/components/devtools/DevToolsComponentContextTab.svelte b/packages/client/src/components/devtools/DevToolsComponentContextTab.svelte index 3b4c426851..02032aa0a5 100644 --- a/packages/client/src/components/devtools/DevToolsComponentContextTab.svelte +++ b/packages/client/src/components/devtools/DevToolsComponentContextTab.svelte @@ -1,6 +1,6 @@ diff --git a/packages/client/src/components/overlay/ConfirmationDisplay.svelte b/packages/client/src/components/overlay/ConfirmationDisplay.svelte index b96af502df..823c1c1ab2 100644 --- a/packages/client/src/components/overlay/ConfirmationDisplay.svelte +++ b/packages/client/src/components/overlay/ConfirmationDisplay.svelte @@ -1,5 +1,5 @@ diff --git a/packages/client/src/components/overlay/NotificationDisplay.svelte b/packages/client/src/components/overlay/NotificationDisplay.svelte index 46b3a2a6a1..28f4b33433 100644 --- a/packages/client/src/components/overlay/NotificationDisplay.svelte +++ b/packages/client/src/components/overlay/NotificationDisplay.svelte @@ -1,5 +1,5 @@ diff --git a/packages/client/src/components/overlay/PeekScreenDisplay.svelte b/packages/client/src/components/overlay/PeekScreenDisplay.svelte index 6e0fa81b43..17a92797d5 100644 --- a/packages/client/src/components/overlay/PeekScreenDisplay.svelte +++ b/packages/client/src/components/overlay/PeekScreenDisplay.svelte @@ -5,7 +5,7 @@ notificationStore, routeStore, stateStore, - } from "stores" + } from "@/stores" import { Modal, ModalContent, ActionButton } from "@budibase/bbui" import { onDestroy } from "svelte" diff --git a/packages/client/src/components/preview/DNDHandler.svelte b/packages/client/src/components/preview/DNDHandler.svelte index bdd538748b..15177a90c4 100644 --- a/packages/client/src/components/preview/DNDHandler.svelte +++ b/packages/client/src/components/preview/DNDHandler.svelte @@ -1,19 +1,22 @@ - - - - -{#if $dndIsDragging} - -{/if} diff --git a/packages/client/src/components/preview/DNDPlaceholderOverlay.svelte b/packages/client/src/components/preview/DNDPlaceholderOverlay.svelte deleted file mode 100644 index 61cecc885b..0000000000 --- a/packages/client/src/components/preview/DNDPlaceholderOverlay.svelte +++ /dev/null @@ -1,51 +0,0 @@ - - -{#if left != null && top != null && width && height} -
-{/if} - - diff --git a/packages/client/src/components/preview/DNDSelectionIndicators.svelte b/packages/client/src/components/preview/DNDSelectionIndicators.svelte new file mode 100644 index 0000000000..cd7eb8302d --- /dev/null +++ b/packages/client/src/components/preview/DNDSelectionIndicators.svelte @@ -0,0 +1,40 @@ + + +{#if $dndIsDragging} + {#if !$isGridScreen && $dndParent} + + {/if} + + {#if !waitingForGrid} + + {/if} +{/if} diff --git a/packages/client/src/components/preview/GridDNDHandler.svelte b/packages/client/src/components/preview/GridDNDHandler.svelte index f173dfd960..e5297e9208 100644 --- a/packages/client/src/components/preview/GridDNDHandler.svelte +++ b/packages/client/src/components/preview/GridDNDHandler.svelte @@ -1,15 +1,50 @@ - diff --git a/packages/client/src/components/preview/GridStylesButton.svelte b/packages/client/src/components/preview/GridStylesButton.svelte index 430a0659ec..059971b0da 100644 --- a/packages/client/src/components/preview/GridStylesButton.svelte +++ b/packages/client/src/components/preview/GridStylesButton.svelte @@ -1,6 +1,6 @@ - +{#if !$dndIsDragging && componentId} + +{/if}} diff --git a/packages/client/src/components/preview/Indicator.svelte b/packages/client/src/components/preview/Indicator.svelte index dce7945b29..800bc0423b 100644 --- a/packages/client/src/components/preview/Indicator.svelte +++ b/packages/client/src/components/preview/Indicator.svelte @@ -1,19 +1,21 @@ - - +{#if !$dndIsDragging && $builderStore.selectedComponentId} + +{/if} diff --git a/packages/client/src/components/preview/SettingsBar.svelte b/packages/client/src/components/preview/SettingsBar.svelte index 9dae1dcb22..32d2e8e62e 100644 --- a/packages/client/src/components/preview/SettingsBar.svelte +++ b/packages/client/src/components/preview/SettingsBar.svelte @@ -4,9 +4,9 @@ import GridStylesButton from "./GridStylesButton.svelte" import SettingsColorPicker from "./SettingsColorPicker.svelte" import SettingsPicker from "./SettingsPicker.svelte" - import { builderStore, componentStore, dndIsDragging } from "stores" + import { builderStore, componentStore, dndIsDragging } from "@/stores" import { Utils, shouldDisplaySetting } from "@budibase/frontend-core" - import { getGridVar, GridParams, Devices } from "utils/grid" + import { getGridVar, GridParams, Devices } from "@/utils/grid" const context = getContext("context") const verticalOffset = 36 diff --git a/packages/client/src/components/preview/SettingsButton.svelte b/packages/client/src/components/preview/SettingsButton.svelte index 16a4fe23d0..01e5964917 100644 --- a/packages/client/src/components/preview/SettingsButton.svelte +++ b/packages/client/src/components/preview/SettingsButton.svelte @@ -1,6 +1,6 @@ diff --git a/packages/server/svelte.config.js b/packages/server/svelte.config.js deleted file mode 100644 index 77aeada229..0000000000 --- a/packages/server/svelte.config.js +++ /dev/null @@ -1,5 +0,0 @@ -const { vitePreprocess } = require("@sveltejs/vite-plugin-svelte") - -module.exports = { - preprocess: vitePreprocess(), -} diff --git a/packages/string-templates/package.json b/packages/string-templates/package.json index acd0ea4fa8..a80c2ec15c 100644 --- a/packages/string-templates/package.json +++ b/packages/string-templates/package.json @@ -33,6 +33,7 @@ "@rollup/plugin-json": "^4.1.0", "@rollup/plugin-node-resolve": "^15.2.3", "@rollup/plugin-typescript": "8.3.0", + "@types/doctrine": "^0.0.9", "doctrine": "^3.0.0", "jest": "29.7.0", "marked": "^4.0.10", diff --git a/packages/string-templates/scripts/gen-collection-info.ts b/packages/string-templates/scripts/gen-collection-info.ts index 8b3825bf5c..f7df88ee85 100644 --- a/packages/string-templates/scripts/gen-collection-info.ts +++ b/packages/string-templates/scripts/gen-collection-info.ts @@ -7,18 +7,30 @@ import { marked } from "marked" import { join, dirname } from "path" const helpers = require("@budibase/handlebars-helpers") -const doctrine = require("doctrine") +import doctrine, { Annotation } from "doctrine" -type HelperInfo = { +type BudibaseAnnotation = Annotation & { + example?: string acceptsInline?: boolean acceptsBlock?: boolean +} + +type Helper = { + args: string[] + numArgs: number example?: string description: string - tags?: any[] + requiresBlock?: boolean +} + +type Manifest = { + [category: string]: { + [helper: string]: Helper + } } const FILENAME = join(__dirname, "..", "src", "manifest.json") -const outputJSON: any = {} +const outputJSON: Manifest = {} const ADDED_HELPERS = { date: { date: { @@ -38,11 +50,10 @@ const ADDED_HELPERS = { }, } -function fixSpecialCases(name: string, obj: any) { - const args = obj.args +function fixSpecialCases(name: string, obj: Helper) { if (name === "ifNth") { - args[0] = "a" - args[1] = "b" + obj.args = ["a", "b", "options"] + obj.numArgs = 3 } if (name === "eachIndex") { obj.description = "Iterates the array, listing an item and the index of it." @@ -66,10 +77,10 @@ function lookForward(lines: string[], funcLines: string[], idx: number) { return true } -function getCommentInfo(file: string, func: string): HelperInfo { +function getCommentInfo(file: string, func: string): BudibaseAnnotation { const lines = file.split("\n") const funcLines = func.split("\n") - let comment = null + let comment: string | null = null for (let idx = 0; idx < lines.length; ++idx) { // from here work back until we have the comment if (lookForward(lines, funcLines, idx)) { @@ -91,15 +102,9 @@ function getCommentInfo(file: string, func: string): HelperInfo { } } if (comment == null) { - return { description: "" } + return { description: "", tags: [] } } - const docs: { - acceptsInline?: boolean - acceptsBlock?: boolean - example: string - description: string - tags: any[] - } = doctrine.parse(comment, { unwrap: true }) + const docs: BudibaseAnnotation = doctrine.parse(comment, { unwrap: true }) // some hacky fixes docs.description = docs.description.replace(/\n/g, " ") docs.description = docs.description.replace(/[ ]{2,}/g, " ") @@ -135,7 +140,7 @@ function run() { )}/lib/${collection}.js`, "utf8" ) - const collectionInfo: any = {} + const collectionInfo: { [name: string]: Helper } = {} // collect information about helper let hbsHelperInfo = helpers[collection]() for (let entry of Object.entries(hbsHelperInfo)) { @@ -154,11 +159,8 @@ function run() { const jsDocInfo = getCommentInfo(collectionFile, fnc) let args = jsDocInfo.tags .filter(tag => tag.title === "param") - .map( - tag => - tag.description && - tag.description.replace(/`/g, "").split(" ")[0].trim() - ) + .filter(tag => tag.description) + .map(tag => tag.description!.replace(/`/g, "").split(" ")[0].trim()) collectionInfo[name] = fixSpecialCases(name, { args, numArgs: args.length, diff --git a/packages/types/src/ui/bindings/binding.ts b/packages/types/src/ui/bindings/binding.ts index a770a25a3e..fdeb4a6c13 100644 --- a/packages/types/src/ui/bindings/binding.ts +++ b/packages/types/src/ui/bindings/binding.ts @@ -1,10 +1,3 @@ -export interface BindingCompletion { - section: { - name: string - } - label: string -} - export interface EnrichedBinding { runtimeBinding: string readableBinding: string diff --git a/packages/types/src/ui/components/index.ts b/packages/types/src/ui/components/index.ts index 37b43ea203..728731baa5 100644 --- a/packages/types/src/ui/components/index.ts +++ b/packages/types/src/ui/components/index.ts @@ -2,6 +2,16 @@ export * from "./sidepanel" export * from "./codeEditor" export * from "./errors" +export interface CustomComponent { + Component: any + schema: { + type: "component" + metadata: Record + schema: ComponentDefinition + } + version: string +} + export interface ComponentDefinition { component: string name: string @@ -13,6 +23,11 @@ export interface ComponentDefinition { legalDirectChildren: string[] requiredAncestors?: string[] illegalChildren: string[] + icon?: string + size?: { + width: number + height: number + } } export type DependsOnComponentSetting = diff --git a/packages/worker/package.json b/packages/worker/package.json index ff21d88ac0..c5e32d11a0 100644 --- a/packages/worker/package.json +++ b/packages/worker/package.json @@ -58,7 +58,7 @@ "joi": "17.6.0", "jsonwebtoken": "9.0.2", "knex": "2.4.2", - "koa": "2.13.4", + "koa": "2.15.4", "koa-body": "4.2.0", "koa-compress": "4.0.1", "koa-passport": "4.1.4", diff --git a/yarn.lock b/yarn.lock index b2ca6a0568..efbac62306 100644 --- a/yarn.lock +++ b/yarn.lock @@ -2834,16 +2834,26 @@ dependencies: "@bull-board/api" "5.10.2" -"@codemirror/autocomplete@^6.0.0", "@codemirror/autocomplete@^6.7.1": - version "6.7.1" - resolved "https://registry.yarnpkg.com/@codemirror/autocomplete/-/autocomplete-6.7.1.tgz#3364799b78dff70fb8f81615536c52ea53ce40b2" - integrity sha512-hSxf9S0uB+GV+gBsjY1FZNo53e1FFdzPceRfCfD1gWOnV6o21GfB5J5Wg9G/4h76XZMPrF0A6OCK/Rz5+V1egg== +"@codemirror/autocomplete@6.9.0": + version "6.9.0" + resolved "https://registry.yarnpkg.com/@codemirror/autocomplete/-/autocomplete-6.9.0.tgz#1a1e63122288b8f8e1e9d7aff2eb39a83e04d8a9" + integrity sha512-Fbwm0V/Wn3BkEJZRhr0hi5BhCo5a7eBL6LYaliPjOSwCyfOpnjXY59HruSxOUNV+1OYer0Tgx1zRNQttjXyDog== dependencies: "@codemirror/language" "^6.0.0" "@codemirror/state" "^6.0.0" "@codemirror/view" "^6.6.0" "@lezer/common" "^1.0.0" +"@codemirror/autocomplete@^6.0.0": + version "6.18.4" + resolved "https://registry.yarnpkg.com/@codemirror/autocomplete/-/autocomplete-6.18.4.tgz#4394f55d6771727179f2e28a871ef46bbbeb11b1" + integrity sha512-sFAphGQIqyQZfP2ZBsSHV7xQvo9Py0rV0dW7W3IMRdS+zDuNb2l3no78CvUaWKGfzFjI4FTrLdUSj86IGb2hRA== + dependencies: + "@codemirror/language" "^6.0.0" + "@codemirror/state" "^6.0.0" + "@codemirror/view" "^6.17.0" + "@lezer/common" "^1.0.0" + "@codemirror/commands@^6.2.4": version "6.2.4" resolved "https://registry.yarnpkg.com/@codemirror/commands/-/commands-6.2.4.tgz#b8a0e5ce72448c092ba4c4b1d902e6f183948aec" @@ -2893,6 +2903,13 @@ resolved "https://registry.yarnpkg.com/@codemirror/state/-/state-6.2.0.tgz#a0fb08403ced8c2a68d1d0acee926bd20be922f2" integrity sha512-69QXtcrsc3RYtOtd+GsvczJ319udtBf1PTrr2KbLWM/e2CXUPnh0Nz9AUo8WfhSQ7GeL8dPVNUmhQVgpmuaNGA== +"@codemirror/state@^6.5.0": + version "6.5.2" + resolved "https://registry.yarnpkg.com/@codemirror/state/-/state-6.5.2.tgz#8eca3a64212a83367dc85475b7d78d5c9b7076c6" + integrity sha512-FVqsPqtPWKVVL3dPSxy8wEF/ymIEuVzF1PK3VbUgrxXpJUSHQWWZz4JMToquRxnkw+36LTamCZG2iua2Ptq0fA== + dependencies: + "@marijn/find-cluster-break" "^1.0.0" + "@codemirror/theme-one-dark@^6.1.2": version "6.1.2" resolved "https://registry.yarnpkg.com/@codemirror/theme-one-dark/-/theme-one-dark-6.1.2.tgz#fcef9f9cfc17a07836cb7da17c9f6d7231064df8" @@ -2912,6 +2929,15 @@ style-mod "^4.0.0" w3c-keyname "^2.2.4" +"@codemirror/view@^6.17.0": + version "6.36.2" + resolved "https://registry.yarnpkg.com/@codemirror/view/-/view-6.36.2.tgz#aeb644e161440734ac5a153bf6e5b4a4355047be" + integrity sha512-DZ6ONbs8qdJK0fdN7AB82CgI6tYXf4HWk1wSVa0+9bhVznCuuvhQtX8bFBoy3dv8rZSQqUd8GvhVAcielcidrA== + dependencies: + "@codemirror/state" "^6.5.0" + style-mod "^4.1.0" + w3c-keyname "^2.2.4" + "@colors/colors@1.6.0", "@colors/colors@^1.6.0": version "1.6.0" resolved "https://registry.yarnpkg.com/@colors/colors/-/colors-1.6.0.tgz#ec6cd237440700bc23ca23087f513c75508958b0" @@ -4133,6 +4159,11 @@ semver "^7.3.5" tar "^6.1.11" +"@marijn/find-cluster-break@^1.0.0": + version "1.0.2" + resolved "https://registry.yarnpkg.com/@marijn/find-cluster-break/-/find-cluster-break-1.0.2.tgz#775374306116d51c0c500b8c4face0f9a04752d8" + integrity sha512-l0h88YhZFyKdXIFNfSWpyjStDjGHwZ/U7iobcK1cQQD8sejsONdQtTVU+1wVN1PBw40PiiHB1vA5S7VTfQiP9g== + "@mongodb-js/saslprep@^1.1.5": version "1.1.7" resolved "https://registry.yarnpkg.com/@mongodb-js/saslprep/-/saslprep-1.1.7.tgz#d1700facfd6916c50c2c88fd6d48d363a56c702f" @@ -6456,6 +6487,11 @@ "@types/node" "*" "@types/ssh2" "*" +"@types/doctrine@^0.0.9": + version "0.0.9" + resolved "https://registry.yarnpkg.com/@types/doctrine/-/doctrine-0.0.9.tgz#d86a5f452a15e3e3113b99e39616a9baa0f9863f" + integrity sha512-eOIHzCUSH7SMfonMG1LsC2f8vxBFtho6NGBznK41R84YzPuvSBzrhEps33IsQiOW9+VL6NQ9DbjQJznk/S4uRA== + "@types/estree@*", "@types/estree@1.0.5", "@types/estree@^1.0.0", "@types/estree@^1.0.1": version "1.0.5" resolved "https://registry.yarnpkg.com/@types/estree/-/estree-1.0.5.tgz#a6ce3e556e00fd9895dd872dd172ad0d4bd687f4" @@ -9385,7 +9421,7 @@ cookiejar@^2.1.4: resolved "https://registry.yarnpkg.com/cookiejar/-/cookiejar-2.1.4.tgz#ee669c1fea2cf42dc31585469d193fef0d65771b" integrity sha512-LDx6oHrK+PhzLKJU9j5S7/Y3jM/mUHvD/DeI1WQmJn652iPC5Y4TBzC9l+5OMOXlyTTA+SmVUPm0HQUwpD5Jqw== -cookies@0.8.0, cookies@~0.8.0: +cookies@0.8.0: version "0.8.0" resolved "https://registry.yarnpkg.com/cookies/-/cookies-0.8.0.tgz#1293ce4b391740a8406e3c9870e828c4b54f3f90" integrity sha512-8aPsApQfebXnuI+537McwYsDtjVxGm8gTIzQI3FDW6t5t/DAhERxtnbEPN/8RX+uZthoz4eCOgloXaE5cYyNow== @@ -9393,6 +9429,14 @@ cookies@0.8.0, cookies@~0.8.0: depd "~2.0.0" keygrip "~1.1.0" +cookies@~0.9.0: + version "0.9.1" + resolved "https://registry.yarnpkg.com/cookies/-/cookies-0.9.1.tgz#3ffed6f60bb4fb5f146feeedba50acc418af67e3" + integrity sha512-TG2hpqe4ELx54QER/S3HQ9SRVnQnGBtKUz5bLQWtYAQ+o6GpgMs6sYUvaiJjVxb+UXwhRhAEP3m7LbsIZ77Hmw== + dependencies: + depd "~2.0.0" + keygrip "~1.1.0" + copyfiles@2.4.1: version "2.4.1" resolved "https://registry.yarnpkg.com/copyfiles/-/copyfiles-2.4.1.tgz#d2dcff60aaad1015f09d0b66e7f0f1c5cd3c5da5" @@ -9784,10 +9828,10 @@ dd-trace@5.26.0: shell-quote "^1.8.1" tlhunter-sorted-set "^0.1.0" -debug@4, debug@^4.0.0, debug@^4.0.1, debug@^4.1.0, debug@^4.1.1, debug@^4.3.1, debug@^4.3.2, debug@^4.3.3, debug@^4.3.4, debug@~4.3.1, debug@~4.3.2, debug@~4.3.4: - version "4.3.7" - resolved "https://registry.yarnpkg.com/debug/-/debug-4.3.7.tgz#87945b4151a011d76d95a198d7111c865c360a52" - integrity sha512-Er2nc/H7RrMXZBFCEim6TCmMk02Z8vLC2Rbi1KEBggpo0fS6l0S1nnapwmIi3yW/+GOJap1Krg4w0Hg80oCqgQ== +debug@4, debug@^4.0.0, debug@^4.0.1, debug@^4.1.0, debug@^4.1.1, debug@^4.3.1, debug@^4.3.2, debug@^4.3.3, debug@^4.3.4, debug@^4.3.5: + version "4.4.0" + resolved "https://registry.yarnpkg.com/debug/-/debug-4.4.0.tgz#2b3f2aea2ffeb776477460267377dc8710faba8a" + integrity sha512-6WTZ/IxCY/T6BALoZHaE4ctp9xm+Z5kY/pzYaCHRFeyVhojxlrm+46y68HA6hr0TcwEssoxNiDEUJQjfPZ/RYA== dependencies: ms "^2.1.3" @@ -9805,10 +9849,10 @@ debug@^3.1.0, debug@^3.2.7: dependencies: ms "^2.1.1" -debug@^4.3.5: - version "4.4.0" - resolved "https://registry.yarnpkg.com/debug/-/debug-4.4.0.tgz#2b3f2aea2ffeb776477460267377dc8710faba8a" - integrity sha512-6WTZ/IxCY/T6BALoZHaE4ctp9xm+Z5kY/pzYaCHRFeyVhojxlrm+46y68HA6hr0TcwEssoxNiDEUJQjfPZ/RYA== +debug@~4.3.1, debug@~4.3.2, debug@~4.3.4: + version "4.3.7" + resolved "https://registry.yarnpkg.com/debug/-/debug-4.3.7.tgz#87945b4151a011d76d95a198d7111c865c360a52" + integrity sha512-Er2nc/H7RrMXZBFCEim6TCmMk02Z8vLC2Rbi1KEBggpo0fS6l0S1nnapwmIi3yW/+GOJap1Krg4w0Hg80oCqgQ== dependencies: ms "^2.1.3" @@ -13739,11 +13783,6 @@ jake@^10.8.5: filelist "^1.0.1" minimatch "^3.0.4" -jest-chain-transform@^0.0.8: - version "0.0.8" - resolved "https://registry.yarnpkg.com/jest-chain-transform/-/jest-chain-transform-0.0.8.tgz#cbb4d3aef8d02678b1852968a9b0c861f75eef5a" - integrity sha512-AELTTzYJ34WrmQKAbxUGT+xqnAHu0/XJZhahYNGvBVUhnAayjm1QmT45DQjwEbQPQp7gn6CXzu6rZA03riwBuw== - jest-changed-files@^29.7.0: version "29.7.0" resolved "https://registry.yarnpkg.com/jest-changed-files/-/jest-changed-files-29.7.0.tgz#1c06d07e77c78e1585d020424dedc10d6e17ac3a" @@ -14701,45 +14740,16 @@ koa2-ratelimit@1.1.1: resolved "https://registry.yarnpkg.com/koa2-ratelimit/-/koa2-ratelimit-1.1.1.tgz#9c1d8257770e4a0a08063ba2ddcaf690fd457d23" integrity sha512-IpxGMdZqEhMykW0yYKGVB4vDEacPvSBH4hNpDL38ABj3W2KHNLujAljGEDg7eEjXvrRbXRSWXzANhV3c9v7nyg== -koa@2.13.4: - version "2.13.4" - resolved "https://registry.yarnpkg.com/koa/-/koa-2.13.4.tgz#ee5b0cb39e0b8069c38d115139c774833d32462e" - integrity sha512-43zkIKubNbnrULWlHdN5h1g3SEKXOEzoAlRsHOTFpnlDu8JlAOZSMJBLULusuXRequboiwJcj5vtYXKB3k7+2g== +koa@2.15.4, koa@^2.13.1, koa@^2.13.4: + version "2.15.4" + resolved "https://registry.yarnpkg.com/koa/-/koa-2.15.4.tgz#7000b3d8354558671adb1ba1b1c09bedb5f8da75" + integrity sha512-7fNBIdrU2PEgLljXoPWoyY4r1e+ToWCmzS/wwMPbUNs7X+5MMET1ObhJBlUkF5uZG9B6QhM2zS1TsH6adegkiQ== dependencies: accepts "^1.3.5" cache-content-type "^1.0.0" content-disposition "~0.5.2" content-type "^1.0.4" - cookies "~0.8.0" - debug "^4.3.2" - delegates "^1.0.0" - depd "^2.0.0" - destroy "^1.0.4" - encodeurl "^1.0.2" - escape-html "^1.0.3" - fresh "~0.5.2" - http-assert "^1.3.0" - http-errors "^1.6.3" - is-generator-function "^1.0.7" - koa-compose "^4.1.0" - koa-convert "^2.0.0" - on-finished "^2.3.0" - only "~0.0.2" - parseurl "^1.3.2" - statuses "^1.5.0" - type-is "^1.6.16" - vary "^1.1.2" - -koa@^2.13.1, koa@^2.13.4: - version "2.14.1" - resolved "https://registry.yarnpkg.com/koa/-/koa-2.14.1.tgz#defb9589297d8eb1859936e777f3feecfc26925c" - integrity sha512-USJFyZgi2l0wDgqkfD27gL4YGno7TfUkcmOe6UOLFOVuN+J7FwnNu4Dydl4CUQzraM1lBAiGed0M9OVJoT0Kqw== - dependencies: - accepts "^1.3.5" - cache-content-type "^1.0.0" - content-disposition "~0.5.2" - content-type "^1.0.4" - cookies "~0.8.0" + cookies "~0.9.0" debug "^4.3.2" delegates "^1.0.0" depd "^2.0.0" @@ -19961,6 +19971,11 @@ style-mod@^4.0.0: resolved "https://registry.yarnpkg.com/style-mod/-/style-mod-4.0.3.tgz#136c4abc905f82a866a18b39df4dc08ec762b1ad" integrity sha512-78Jv8kYJdjbvRwwijtCevYADfsI0lGzYJe4mMFdceO8l75DFFDoqBhR1jVDicDRRaX4//g1u9wKeo+ztc2h1Rw== +style-mod@^4.1.0: + version "4.1.2" + resolved "https://registry.yarnpkg.com/style-mod/-/style-mod-4.1.2.tgz#ca238a1ad4786520f7515a8539d5a63691d7bf67" + integrity sha512-wnD1HyVqpJUI2+eKZ+eo1UwghftP6yuFheBqqe+bWCotBjC2K1YnteJILRMs3SM4V/0dLEW1SC27MWP5y+mwmw== + stylus-lookup@^3.0.1: version "3.0.2" resolved "https://registry.yarnpkg.com/stylus-lookup/-/stylus-lookup-3.0.2.tgz#c9eca3ff799691020f30b382260a67355fefdddd"