mirror of
https://github.com/langgenius/dify.git
synced 2026-07-25 13:38:31 +08:00
chore(web): improve web accessibility semantics (#39505)
This commit is contained in:
parent
e1495c0bae
commit
7bb09ce039
@ -1,7 +1,7 @@
|
||||
import type { RenderOptions } from '@testing-library/react'
|
||||
import type { ReactElement } from 'react'
|
||||
import type { UsagePlanInfo, UsageResetInfo } from '@/app/components/billing/type'
|
||||
import { screen } from '@testing-library/react'
|
||||
import { screen, within } from '@testing-library/react'
|
||||
import userEvent from '@testing-library/user-event'
|
||||
import * as React from 'react'
|
||||
import AnnotationFull from '@/app/components/billing/annotation-full'
|
||||
@ -200,20 +200,22 @@ describe('Billing Page + Plan Integration', () => {
|
||||
expect(screen.getByText(/plansCommon\.apiRateLimit/i)).toBeInTheDocument()
|
||||
})
|
||||
|
||||
it('should display usage values as "usage / total" format', () => {
|
||||
it('should expose each quota card and its value through stable semantics', () => {
|
||||
setupProviderContext({
|
||||
type: Plan.sandbox,
|
||||
usage: { buildApps: 3, teamMembers: 1 },
|
||||
total: { buildApps: 5, teamMembers: 1 },
|
||||
usage: { teamMembers: 3 },
|
||||
total: { teamMembers: 5 },
|
||||
})
|
||||
|
||||
render(<PlanComp loc="test" />)
|
||||
|
||||
// Check that the buildApps usage fraction "3 / 5" is rendered
|
||||
const usageContainers = screen.getAllByText('3')
|
||||
expect(usageContainers.length).toBeGreaterThan(0)
|
||||
const totalContainers = screen.getAllByText('5')
|
||||
expect(totalContainers.length).toBeGreaterThan(0)
|
||||
const quotaCard = screen.getByRole('group', { name: /usagePage\.teamMembers/i })
|
||||
const quotaLabel = within(quotaCard).getByText(/usagePage\.teamMembers/i)
|
||||
const quotaValue = within(quotaCard).getByTestId('billing-quota-value')
|
||||
|
||||
expect(quotaLabel.tagName).toBe('DT')
|
||||
expect(quotaValue.tagName).toBe('DD')
|
||||
expect(quotaValue).toHaveTextContent(/3\s*\/\s*5/)
|
||||
})
|
||||
|
||||
it('should show "unlimited" for infinite quotas (professional API rate limit)', () => {
|
||||
|
||||
@ -169,6 +169,9 @@ describe('Pricing Modal Flow', () => {
|
||||
it('should show plan range switcher (annual billing toggle) by default for cloud', () => {
|
||||
render(<Pricing onCancel={onCancel} />)
|
||||
|
||||
expect(
|
||||
screen.getByRole('switch', { name: 'billing.plansCommon.yearlyBilling' }),
|
||||
).toBeInTheDocument()
|
||||
expect(screen.getByText(/plansCommon\.annualBilling/i)).toBeInTheDocument()
|
||||
})
|
||||
|
||||
@ -284,7 +287,9 @@ describe('Pricing Modal Flow', () => {
|
||||
const user = userEvent.setup()
|
||||
render(<Pricing onCancel={onCancel} />)
|
||||
|
||||
expect(screen.getByRole('switch')).toBeChecked()
|
||||
expect(
|
||||
screen.getByRole('switch', { name: 'billing.plansCommon.yearlyBilling' }),
|
||||
).toBeChecked()
|
||||
|
||||
await user.click(screen.getByRole('button', { name: 'education.useEducationDiscount' }))
|
||||
|
||||
|
||||
@ -1,5 +1,4 @@
|
||||
'use client'
|
||||
import type { FC } from 'react'
|
||||
import { Switch } from '@langgenius/dify-ui/switch'
|
||||
import * as React from 'react'
|
||||
import { useTranslation } from 'react-i18next'
|
||||
@ -14,12 +13,13 @@ type PlanRangeSwitcherProps = {
|
||||
onChange: (value: PlanRange) => void
|
||||
}
|
||||
|
||||
const PlanRangeSwitcher: FC<PlanRangeSwitcherProps> = ({ value, onChange }) => {
|
||||
function PlanRangeSwitcher({ value, onChange }: PlanRangeSwitcherProps) {
|
||||
const { t } = useTranslation()
|
||||
|
||||
return (
|
||||
<div className="flex items-center justify-end gap-x-3 pr-5">
|
||||
<Switch
|
||||
aria-label={t(($) => $['plansCommon.yearlyBilling'], { ns: 'billing' })}
|
||||
size="lg"
|
||||
checked={value === PlanRange.yearly}
|
||||
onCheckedChange={(v) => {
|
||||
|
||||
@ -154,20 +154,29 @@ const UsageInfo: FC<Props> = ({
|
||||
}
|
||||
|
||||
return (
|
||||
<div className={cn('flex flex-col gap-2 rounded-xl bg-components-panel-bg p-4', className)}>
|
||||
<div
|
||||
role="group"
|
||||
aria-label={name}
|
||||
className={cn('flex flex-col gap-2 rounded-xl bg-components-panel-bg p-4', className)}
|
||||
>
|
||||
{!hideIcon && Icon && <Icon className="size-4 text-text-tertiary" />}
|
||||
<div className="flex items-center gap-1">
|
||||
<div className="system-xs-medium text-text-tertiary">{name}</div>
|
||||
{tooltip && (
|
||||
<Infotip aria-label={tooltip} popupClassName="w-[180px] max-w-[180px]">
|
||||
{tooltip}
|
||||
</Infotip>
|
||||
)}
|
||||
</div>
|
||||
<div className="flex items-center gap-1 system-md-semibold text-text-primary">
|
||||
{wrapWithStorageTooltip(usageDisplay)}
|
||||
{rightInfo}
|
||||
</div>
|
||||
<dl className="flex flex-col gap-2">
|
||||
<dt className="flex items-center gap-1 system-xs-medium text-text-tertiary">
|
||||
{name}
|
||||
{tooltip && (
|
||||
<Infotip aria-label={tooltip} popupClassName="w-[180px] max-w-[180px]">
|
||||
{tooltip}
|
||||
</Infotip>
|
||||
)}
|
||||
</dt>
|
||||
<dd
|
||||
data-testid="billing-quota-value"
|
||||
className="flex items-center gap-1 system-md-semibold text-text-primary"
|
||||
>
|
||||
{wrapWithStorageTooltip(usageDisplay)}
|
||||
{rightInfo}
|
||||
</dd>
|
||||
</dl>
|
||||
{wrapWithStorageTooltip(bar)}
|
||||
</div>
|
||||
)
|
||||
|
||||
@ -27,7 +27,8 @@ const createMockBanner = (overrides: Partial<Banner> = {}): Banner =>
|
||||
const renderBannerItem = (
|
||||
banner: Banner = createMockBanner(),
|
||||
props: Partial<ComponentProps<typeof BannerItem>> = {},
|
||||
) => render(<BannerItem banner={banner} sort={1} language="en-US" {...props} />)
|
||||
) =>
|
||||
render(<BannerItem banner={banner} sort={1} language="en-US" titleId="banner-title" {...props} />)
|
||||
|
||||
describe('BannerItem', () => {
|
||||
afterEach(() => {
|
||||
|
||||
@ -130,11 +130,13 @@ vi.mock('../banner-item', () => ({
|
||||
sort,
|
||||
language,
|
||||
accountId,
|
||||
titleId,
|
||||
}: {
|
||||
banner: BannerType
|
||||
sort: number
|
||||
language: string
|
||||
accountId?: string
|
||||
titleId?: string
|
||||
}) => (
|
||||
<article
|
||||
data-testid="banner-item"
|
||||
@ -143,7 +145,7 @@ vi.mock('../banner-item', () => ({
|
||||
data-language={language}
|
||||
data-account-id={accountId}
|
||||
>
|
||||
{banner.content.title}
|
||||
<p id={titleId}>{banner.content.title}</p>
|
||||
</article>
|
||||
),
|
||||
}))
|
||||
@ -220,6 +222,17 @@ describe('Banner', () => {
|
||||
expect(secondSlide).toHaveAttribute('inert')
|
||||
})
|
||||
|
||||
it('names each slide with its visible title', () => {
|
||||
render(<Banner banners={[createMockBanner('1', 'enabled', 'First banner')]} />)
|
||||
|
||||
const slide = screen.getByRole('group', { name: 'First banner' })
|
||||
const title = document.getElementById(slide.getAttribute('aria-labelledby')!)
|
||||
|
||||
expect(slide).not.toHaveAttribute('aria-label')
|
||||
expect(title).toHaveTextContent('First banner')
|
||||
expect(slide).toContainElement(title)
|
||||
})
|
||||
|
||||
it('keeps one shared control set mounted while selecting a banner', () => {
|
||||
render(
|
||||
<Banner
|
||||
|
||||
@ -1,5 +1,4 @@
|
||||
import type { Banner } from '@/models/app'
|
||||
import { useId } from 'react'
|
||||
import { trackEvent } from '@/app/components/base/amplitude'
|
||||
|
||||
type BannerItemProps = {
|
||||
@ -7,10 +6,10 @@ type BannerItemProps = {
|
||||
sort: number
|
||||
language: string
|
||||
accountId?: string
|
||||
titleId: string
|
||||
}
|
||||
|
||||
export function BannerItem({ banner, sort, language, accountId }: BannerItemProps) {
|
||||
const titleId = useId()
|
||||
export function BannerItem({ banner, sort, language, accountId, titleId }: BannerItemProps) {
|
||||
const { category, title, description, 'img-src': imgSrc } = banner.content
|
||||
|
||||
const handleBannerClick = () => {
|
||||
|
||||
@ -1,7 +1,7 @@
|
||||
import type { ComponentProps, FocusEvent } from 'react'
|
||||
import type { Banner as BannerType } from '@/models/app'
|
||||
import { useAtomValue } from 'jotai'
|
||||
import { useEffect, useRef, useState } from 'react'
|
||||
import { useEffect, useId, useRef, useState } from 'react'
|
||||
import { useTranslation } from 'react-i18next'
|
||||
import { trackEvent } from '@/app/components/base/amplitude'
|
||||
import { Carousel, useCarousel } from '@/app/components/base/carousel'
|
||||
@ -23,6 +23,35 @@ type BannerCarouselContentProps = {
|
||||
language: string
|
||||
}
|
||||
|
||||
type BannerSlideProps = {
|
||||
banner: BannerType
|
||||
index: number
|
||||
isActive: boolean
|
||||
accountId?: string
|
||||
language: string
|
||||
}
|
||||
|
||||
function BannerSlide({ banner, index, isActive, accountId, language }: BannerSlideProps) {
|
||||
const titleId = useId()
|
||||
|
||||
return (
|
||||
<Carousel.Item
|
||||
data-banner-id={banner.id}
|
||||
aria-labelledby={titleId}
|
||||
aria-hidden={!isActive}
|
||||
inert={!isActive}
|
||||
>
|
||||
<BannerItem
|
||||
banner={banner}
|
||||
sort={index + 1}
|
||||
language={language}
|
||||
accountId={accountId}
|
||||
titleId={titleId}
|
||||
/>
|
||||
</Carousel.Item>
|
||||
)
|
||||
}
|
||||
|
||||
function BannerCarouselContent({ banners, accountId, language }: BannerCarouselContentProps) {
|
||||
const { t } = useTranslation()
|
||||
const { api, selectedIndex } = useCarousel()
|
||||
@ -120,26 +149,16 @@ function BannerCarouselContent({ banners, accountId, language }: BannerCarouselC
|
||||
return (
|
||||
<>
|
||||
<Carousel.Content aria-live={isPlaying ? 'off' : 'polite'}>
|
||||
{banners.map((banner, index) => {
|
||||
const isActive = index === selectedIndex
|
||||
|
||||
return (
|
||||
<Carousel.Item
|
||||
key={banner.id}
|
||||
data-banner-id={banner.id}
|
||||
aria-label={banner.content.title}
|
||||
aria-hidden={!isActive}
|
||||
inert={!isActive}
|
||||
>
|
||||
<BannerItem
|
||||
banner={banner}
|
||||
sort={index + 1}
|
||||
language={language}
|
||||
accountId={accountId}
|
||||
/>
|
||||
</Carousel.Item>
|
||||
)
|
||||
})}
|
||||
{banners.map((banner, index) => (
|
||||
<BannerSlide
|
||||
key={banner.id}
|
||||
banner={banner}
|
||||
index={index}
|
||||
isActive={index === selectedIndex}
|
||||
accountId={accountId}
|
||||
language={language}
|
||||
/>
|
||||
))}
|
||||
</Carousel.Content>
|
||||
|
||||
{hasFooter ? (
|
||||
|
||||
@ -1,3 +1,4 @@
|
||||
import { screen, within } from '@testing-library/react'
|
||||
import { renderWorkflowComponent } from '../../__tests__/workflow-test-env'
|
||||
import EditingTitle from '../editing-title'
|
||||
|
||||
@ -24,7 +25,7 @@ describe('EditingTitle', () => {
|
||||
})
|
||||
|
||||
it('should render autosave, published time, and syncing status when the draft has metadata', () => {
|
||||
const { container } = renderWorkflowComponent(<EditingTitle />, {
|
||||
renderWorkflowComponent(<EditingTitle />, {
|
||||
initialStoreState: {
|
||||
draftUpdatedAt: 1_710_000_000_000,
|
||||
publishedAt: 1_710_003_600_000,
|
||||
@ -34,26 +35,44 @@ describe('EditingTitle', () => {
|
||||
|
||||
expect(mockFormatTime).toHaveBeenCalledWith(1_710_000_000, 'HH:mm:ss')
|
||||
expect(mockFormatTimeFromNow).toHaveBeenCalledWith(1_710_003_600_000)
|
||||
expect(container).toHaveTextContent('workflow.common.autoSaved')
|
||||
expect(container).toHaveTextContent('08:00:00')
|
||||
expect(container).toHaveTextContent('workflow.common.published')
|
||||
expect(container).toHaveTextContent('2 hours ago')
|
||||
expect(container).toHaveTextContent('workflow.common.syncingData')
|
||||
const saveStatus = screen.getByRole('status', {
|
||||
name: 'workflow.common.workflowSaveStatus',
|
||||
})
|
||||
const statusContent = within(saveStatus)
|
||||
|
||||
expect(statusContent.getByText('workflow.common.autoSaved')).toBeInTheDocument()
|
||||
expect(statusContent.getByText('workflow.common.published')).toBeInTheDocument()
|
||||
expect(statusContent.getByText('workflow.common.syncingData')).toBeInTheDocument()
|
||||
|
||||
const draftUpdatedTime = statusContent.getByText('08:00:00')
|
||||
const publishedTime = statusContent.getByText('2 hours ago')
|
||||
expect(draftUpdatedTime.tagName).toBe('TIME')
|
||||
expect(draftUpdatedTime).toHaveTextContent('08:00:00')
|
||||
expect(draftUpdatedTime).toHaveAttribute('datetime', '2024-03-09T16:00:00.000Z')
|
||||
expect(publishedTime.tagName).toBe('TIME')
|
||||
expect(publishedTime).toHaveTextContent('2 hours ago')
|
||||
expect(publishedTime).toHaveAttribute('datetime', '2024-03-09T17:00:00.000Z')
|
||||
})
|
||||
|
||||
it('should render unpublished status without autosave metadata when the workflow has not been published', () => {
|
||||
const { container } = renderWorkflowComponent(<EditingTitle />, {
|
||||
it('should expose autosave time separately from the unpublished status', () => {
|
||||
renderWorkflowComponent(<EditingTitle />, {
|
||||
initialStoreState: {
|
||||
draftUpdatedAt: 0,
|
||||
draftUpdatedAt: 1_710_000_000_000,
|
||||
publishedAt: 0,
|
||||
isSyncingWorkflowDraft: false,
|
||||
},
|
||||
})
|
||||
|
||||
expect(mockFormatTime).not.toHaveBeenCalled()
|
||||
expect(mockFormatTime).toHaveBeenCalledWith(1_710_000_000, 'HH:mm:ss')
|
||||
expect(mockFormatTimeFromNow).not.toHaveBeenCalled()
|
||||
expect(container).toHaveTextContent('workflow.common.unpublished')
|
||||
expect(container).not.toHaveTextContent('workflow.common.autoSaved')
|
||||
expect(container).not.toHaveTextContent('workflow.common.syncingData')
|
||||
const saveStatus = screen.getByRole('status', {
|
||||
name: 'workflow.common.workflowSaveStatus',
|
||||
})
|
||||
const statusContent = within(saveStatus)
|
||||
|
||||
expect(statusContent.getByText('workflow.common.autoSaved')).toBeInTheDocument()
|
||||
expect(statusContent.getByText('workflow.common.unpublished')).toBeInTheDocument()
|
||||
expect(statusContent.queryByText('workflow.common.syncingData')).not.toBeInTheDocument()
|
||||
expect(statusContent.getByText('08:00:00').tagName).toBe('TIME')
|
||||
})
|
||||
})
|
||||
|
||||
@ -4,7 +4,7 @@ import { useStore } from '@/app/components/workflow/store'
|
||||
import { useFormatTimeFromNow } from '@/hooks/use-format-time-from-now'
|
||||
import useTimestamp from '@/hooks/use-timestamp'
|
||||
|
||||
const EditingTitle = () => {
|
||||
function EditingTitle() {
|
||||
const { t } = useTranslation()
|
||||
const { formatTime } = useTimestamp()
|
||||
const { formatTimeFromNow } = useFormatTimeFromNow()
|
||||
@ -13,21 +13,38 @@ const EditingTitle = () => {
|
||||
const isSyncingWorkflowDraft = useStore((s) => s.isSyncingWorkflowDraft)
|
||||
|
||||
return (
|
||||
<div className="flex h-[18px] min-w-[300px] items-center system-xs-regular whitespace-nowrap text-text-tertiary">
|
||||
<div
|
||||
role="status"
|
||||
aria-label={t(($) => $['common.workflowSaveStatus'], { ns: 'workflow' })}
|
||||
className="flex h-[18px] min-w-[300px] items-center system-xs-regular whitespace-nowrap text-text-tertiary"
|
||||
>
|
||||
{!!draftUpdatedAt && (
|
||||
<>
|
||||
{t(($) => $['common.autoSaved'], { ns: 'workflow' })}{' '}
|
||||
{formatTime(draftUpdatedAt / 1000, 'HH:mm:ss')}
|
||||
</>
|
||||
<span className="flex items-center gap-1">
|
||||
<span>{t(($) => $['common.autoSaved'], { ns: 'workflow' })}</span>
|
||||
<time dateTime={new Date(draftUpdatedAt).toISOString()}>
|
||||
{formatTime(draftUpdatedAt / 1000, 'HH:mm:ss')}
|
||||
</time>
|
||||
</span>
|
||||
)}
|
||||
<span aria-hidden="true" className="mx-1 flex items-center">
|
||||
·
|
||||
</span>
|
||||
{publishedAt ? (
|
||||
<span className="flex items-center gap-1">
|
||||
<span>{t(($) => $['common.published'], { ns: 'workflow' })}</span>
|
||||
<time dateTime={new Date(publishedAt).toISOString()}>
|
||||
{formatTimeFromNow(publishedAt)}
|
||||
</time>
|
||||
</span>
|
||||
) : (
|
||||
<span>{t(($) => $['common.unpublished'], { ns: 'workflow' })}</span>
|
||||
)}
|
||||
<span className="mx-1 flex items-center">·</span>
|
||||
{publishedAt
|
||||
? `${t(($) => $['common.published'], { ns: 'workflow' })} ${formatTimeFromNow(publishedAt)}`
|
||||
: t(($) => $['common.unpublished'], { ns: 'workflow' })}
|
||||
{isSyncingWorkflowDraft && (
|
||||
<>
|
||||
<span className="mx-1 flex items-center">·</span>
|
||||
{t(($) => $['common.syncingData'], { ns: 'workflow' })}
|
||||
<span aria-hidden="true" className="mx-1 flex items-center">
|
||||
·
|
||||
</span>
|
||||
<span>{t(($) => $['common.syncingData'], { ns: 'workflow' })}</span>
|
||||
</>
|
||||
)}
|
||||
</div>
|
||||
|
||||
@ -151,6 +151,7 @@
|
||||
"plansCommon.workflowExecution.standard": "تنفيذ سير عمل قياسي",
|
||||
"plansCommon.workflowExecution.tooltip": "أولوية وسرعة قائمة انتظار تنفيذ سير العمل.",
|
||||
"plansCommon.year": "سنة",
|
||||
"plansCommon.yearlyBilling": "الفوترة السنوية",
|
||||
"plansCommon.yearlyTip": "ادفع لمدة 10 أشهر، واستمتع بسنة كاملة!",
|
||||
"teamMembers": "أعضاء الفريق",
|
||||
"triggerLimitModal.description": "لقد وصلت إلى الحد الأقصى لمشغلات أحداث سير العمل لهذه الخطة.",
|
||||
|
||||
@ -280,6 +280,7 @@
|
||||
"common.workflowProcessPaused": "تم إيقاف عملية سير العمل مؤقتًا",
|
||||
"common.workflowProcessRunning": "عملية سير العمل قيد التشغيل",
|
||||
"common.workflowProcessSucceeded": "نجحت عملية سير العمل",
|
||||
"common.workflowSaveStatus": "حالة حفظ سير العمل",
|
||||
"customWebhook": "ويب هوك مخصص",
|
||||
"debug.copyLastRun": "نسخ آخر تشغيل",
|
||||
"debug.copyLastRunError": "فشل نسخ مدخلات آخر تشغيل",
|
||||
|
||||
@ -151,6 +151,7 @@
|
||||
"plansCommon.workflowExecution.standard": "Standard-Workflow-Ausführung",
|
||||
"plansCommon.workflowExecution.tooltip": "Priorität und Geschwindigkeit der Arbeitsablauf-Ausführungswarteschlange.",
|
||||
"plansCommon.year": "Jahr",
|
||||
"plansCommon.yearlyBilling": "Jährliche Abrechnung",
|
||||
"plansCommon.yearlyTip": "Erhalten Sie 2 Monate kostenlos durch jährliches Abonnieren!",
|
||||
"teamMembers": "Teammitglieder",
|
||||
"triggerLimitModal.description": "Sie haben das Limit der Workflow-Ereignisauslöser für diesen Plan erreicht.",
|
||||
|
||||
@ -280,6 +280,7 @@
|
||||
"common.workflowProcessPaused": "Arbeitsablauf pausiert",
|
||||
"common.workflowProcessRunning": "Arbeitsablauf wird ausgeführt",
|
||||
"common.workflowProcessSucceeded": "Arbeitsablauf erfolgreich",
|
||||
"common.workflowSaveStatus": "Speicherstatus des Workflows",
|
||||
"customWebhook": "Benutzerdefinierter Webhook",
|
||||
"debug.copyLastRun": "Letzte Ausführung kopieren",
|
||||
"debug.copyLastRunError": "Fehler beim Kopieren der letzten Lauf-Eingaben",
|
||||
|
||||
@ -151,6 +151,7 @@
|
||||
"plansCommon.workflowExecution.standard": "Standard Workflow Execution",
|
||||
"plansCommon.workflowExecution.tooltip": "Workflow execution queue priority and speed.",
|
||||
"plansCommon.year": "year",
|
||||
"plansCommon.yearlyBilling": "Yearly billing",
|
||||
"plansCommon.yearlyTip": "Pay for 10 months, enjoy 1 Year!",
|
||||
"teamMembers": "Team Members",
|
||||
"triggerLimitModal.description": "You've reached the limit of workflow event triggers for this plan.",
|
||||
|
||||
@ -280,6 +280,7 @@
|
||||
"common.workflowProcessPaused": "Workflow Process paused",
|
||||
"common.workflowProcessRunning": "Workflow Process running",
|
||||
"common.workflowProcessSucceeded": "Workflow Process succeeded",
|
||||
"common.workflowSaveStatus": "Workflow save status",
|
||||
"customWebhook": "Custom Webhook",
|
||||
"debug.copyLastRun": "Copy Last Run",
|
||||
"debug.copyLastRunError": "Failed to copy last run inputs",
|
||||
|
||||
@ -151,6 +151,7 @@
|
||||
"plansCommon.workflowExecution.standard": "Ejecución estándar del flujo de trabajo",
|
||||
"plansCommon.workflowExecution.tooltip": "Prioridad y velocidad de la cola de ejecución de flujos de trabajo.",
|
||||
"plansCommon.year": "año",
|
||||
"plansCommon.yearlyBilling": "Facturación anual",
|
||||
"plansCommon.yearlyTip": "¡Obtén 2 meses gratis al suscribirte anualmente!",
|
||||
"teamMembers": "Miembros del equipo",
|
||||
"triggerLimitModal.description": "Has alcanzado el límite de activadores de eventos de flujo de trabajo para este plan.",
|
||||
|
||||
@ -280,6 +280,7 @@
|
||||
"common.workflowProcessPaused": "Proceso de flujo de trabajo pausado",
|
||||
"common.workflowProcessRunning": "Proceso de flujo de trabajo en ejecución",
|
||||
"common.workflowProcessSucceeded": "Proceso de flujo de trabajo completado correctamente",
|
||||
"common.workflowSaveStatus": "Estado de guardado del flujo de trabajo",
|
||||
"customWebhook": "Webhook personalizado",
|
||||
"debug.copyLastRun": "Copiar última ejecución",
|
||||
"debug.copyLastRunError": "No se pudo copiar las entradas de la última ejecución",
|
||||
|
||||
@ -151,6 +151,7 @@
|
||||
"plansCommon.workflowExecution.standard": "اجرای جریان کاری استاندارد",
|
||||
"plansCommon.workflowExecution.tooltip": "اولویت و سرعت صف اجرای گردش کار.",
|
||||
"plansCommon.year": "سال",
|
||||
"plansCommon.yearlyBilling": "صورتحساب سالانه",
|
||||
"plansCommon.yearlyTip": "با اشتراک سالانه 2 ماه رایگان دریافت کنید!",
|
||||
"teamMembers": "اعضای تیم",
|
||||
"triggerLimitModal.description": "شما به حد مجاز تریگرهای رویداد گردش کار برای این طرح رسیدهاید.",
|
||||
|
||||
@ -280,6 +280,7 @@
|
||||
"common.workflowProcessPaused": "فرآیند گردش کار متوقف شده است",
|
||||
"common.workflowProcessRunning": "فرآیند گردش کار در حال اجراست",
|
||||
"common.workflowProcessSucceeded": "فرآیند گردش کار با موفقیت انجام شد",
|
||||
"common.workflowSaveStatus": "وضعیت ذخیرهسازی گردش کار",
|
||||
"customWebhook": "وبهوک سفارشی",
|
||||
"debug.copyLastRun": "کپی آخرین اجرا",
|
||||
"debug.copyLastRunError": "کپی ورودیهای آخرین اجرا ناموفق بود",
|
||||
|
||||
@ -151,6 +151,7 @@
|
||||
"plansCommon.workflowExecution.standard": "Exécution du flux de travail standard",
|
||||
"plansCommon.workflowExecution.tooltip": "Priorité et vitesse de la file d'exécution des flux de travail.",
|
||||
"plansCommon.year": "année",
|
||||
"plansCommon.yearlyBilling": "Facturation annuelle",
|
||||
"plansCommon.yearlyTip": "Obtenez 2 mois gratuitement en vous abonnant annuellement !",
|
||||
"teamMembers": "Membres de l'équipe",
|
||||
"triggerLimitModal.description": "Vous avez atteint la limite des déclencheurs d'événements de flux de travail pour ce plan.",
|
||||
|
||||
@ -280,6 +280,7 @@
|
||||
"common.workflowProcessPaused": "Processus de flux de travail en pause",
|
||||
"common.workflowProcessRunning": "Processus de flux de travail en cours d'exécution",
|
||||
"common.workflowProcessSucceeded": "Processus de flux de travail réussi",
|
||||
"common.workflowSaveStatus": "État d’enregistrement du workflow",
|
||||
"customWebhook": "Webhook personnalisé",
|
||||
"debug.copyLastRun": "Copier la dernière exécution",
|
||||
"debug.copyLastRunError": "Échec de la copie des entrées de la dernière exécution",
|
||||
|
||||
@ -151,6 +151,7 @@
|
||||
"plansCommon.workflowExecution.standard": "मानक कार्यप्रवाह निष्पादन",
|
||||
"plansCommon.workflowExecution.tooltip": "वर्कफ़्लो निष्पादन कतार की प्राथमिकता और गति।",
|
||||
"plansCommon.year": "साल",
|
||||
"plansCommon.yearlyBilling": "वार्षिक बिलिंग",
|
||||
"plansCommon.yearlyTip": "वार्षिक सब्सक्राइब करने पर 2 महीने मुफ्त पाएं!",
|
||||
"teamMembers": "टीम के सदस्य",
|
||||
"triggerLimitModal.description": "आप इस योजना के लिए वर्कफ़्लो इवेंट ट्रिगर्स की सीमा तक पहुँच चुके हैं।",
|
||||
|
||||
@ -280,6 +280,7 @@
|
||||
"common.workflowProcessPaused": "कार्यप्रवाह प्रक्रिया रुकी हुई है",
|
||||
"common.workflowProcessRunning": "कार्यप्रवाह प्रक्रिया चल रही है",
|
||||
"common.workflowProcessSucceeded": "कार्यप्रवाह प्रक्रिया सफल रही",
|
||||
"common.workflowSaveStatus": "वर्कफ़्लो सहेजने की स्थिति",
|
||||
"customWebhook": "कस्टम वेबहुक",
|
||||
"debug.copyLastRun": "अंतिम रन कॉपी करें",
|
||||
"debug.copyLastRunError": "अंतिम रन इनपुट को कॉपी करने में विफल",
|
||||
|
||||
@ -151,6 +151,7 @@
|
||||
"plansCommon.workflowExecution.standard": "Eksekusi Alur Kerja Standar",
|
||||
"plansCommon.workflowExecution.tooltip": "Prioritas dan kecepatan antrian eksekusi alur kerja.",
|
||||
"plansCommon.year": "tahun",
|
||||
"plansCommon.yearlyBilling": "Penagihan tahunan",
|
||||
"plansCommon.yearlyTip": "Bayar selama 10 bulan, nikmati 1 tahun!",
|
||||
"teamMembers": "Anggota Tim",
|
||||
"triggerLimitModal.description": "Anda telah mencapai batas pemicu acara alur kerja untuk paket ini.",
|
||||
|
||||
@ -280,6 +280,7 @@
|
||||
"common.workflowProcessPaused": "Proses Alur Kerja dijeda",
|
||||
"common.workflowProcessRunning": "Proses Alur Kerja sedang berjalan",
|
||||
"common.workflowProcessSucceeded": "Proses Alur Kerja berhasil",
|
||||
"common.workflowSaveStatus": "Status penyimpanan alur kerja",
|
||||
"customWebhook": "Webhook Kustom",
|
||||
"debug.copyLastRun": "Salin Eksekusi Terakhir",
|
||||
"debug.copyLastRunError": "Gagal menyalin input eksekusi terakhir",
|
||||
|
||||
@ -151,6 +151,7 @@
|
||||
"plansCommon.workflowExecution.standard": "Esecuzione del flusso di lavoro standard",
|
||||
"plansCommon.workflowExecution.tooltip": "Priorità e velocità della coda di esecuzione del flusso di lavoro.",
|
||||
"plansCommon.year": "anno",
|
||||
"plansCommon.yearlyBilling": "Fatturazione annuale",
|
||||
"plansCommon.yearlyTip": "Ottieni 2 mesi gratis abbonandoti annualmente!",
|
||||
"teamMembers": "Membri del team",
|
||||
"triggerLimitModal.description": "Hai raggiunto il limite degli eventi di attivazione del flusso di lavoro per questo piano.",
|
||||
|
||||
@ -280,6 +280,7 @@
|
||||
"common.workflowProcessPaused": "Processo di flusso di lavoro in pausa",
|
||||
"common.workflowProcessRunning": "Processo di flusso di lavoro in esecuzione",
|
||||
"common.workflowProcessSucceeded": "Processo di flusso di lavoro riuscito",
|
||||
"common.workflowSaveStatus": "Stato di salvataggio del flusso di lavoro",
|
||||
"customWebhook": "Webhook personalizzato",
|
||||
"debug.copyLastRun": "Copia ultimo eseguito",
|
||||
"debug.copyLastRunError": "Impossibile copiare gli input dell'ultima esecuzione",
|
||||
|
||||
@ -151,6 +151,7 @@
|
||||
"plansCommon.workflowExecution.standard": "標準ワークフロー実行キュー",
|
||||
"plansCommon.workflowExecution.tooltip": "ワークフローの実行キューの優先度と実行速度。",
|
||||
"plansCommon.year": "年",
|
||||
"plansCommon.yearlyBilling": "年間請求",
|
||||
"plansCommon.yearlyTip": "10 ヶ月分支払って、1 年間楽しもう!",
|
||||
"teamMembers": "チームメンバー",
|
||||
"triggerLimitModal.description": "このプランでは、ワークフローのトリガーイベント数の上限に達しています。",
|
||||
|
||||
@ -280,6 +280,7 @@
|
||||
"common.workflowProcessPaused": "ワークフロー処理は一時停止中です",
|
||||
"common.workflowProcessRunning": "ワークフロー処理を実行中です",
|
||||
"common.workflowProcessSucceeded": "ワークフロー処理が成功しました",
|
||||
"common.workflowSaveStatus": "ワークフローの保存状態",
|
||||
"customWebhook": "カスタムWebhook",
|
||||
"debug.copyLastRun": "最後の実行をコピー",
|
||||
"debug.copyLastRunError": "最後の実行の入力をコピーできませんでした",
|
||||
|
||||
@ -151,6 +151,7 @@
|
||||
"plansCommon.workflowExecution.standard": "표준 워크플로 실행",
|
||||
"plansCommon.workflowExecution.tooltip": "워크플로 실행 대기열 우선순위 및 속도.",
|
||||
"plansCommon.year": "년",
|
||||
"plansCommon.yearlyBilling": "연간 결제",
|
||||
"plansCommon.yearlyTip": "연간 구독 시 2개월 무료!",
|
||||
"teamMembers": "팀원들",
|
||||
"triggerLimitModal.description": "이 요금제의 워크플로 이벤트 트리거 한도에 도달했습니다.",
|
||||
|
||||
@ -280,6 +280,7 @@
|
||||
"common.workflowProcessPaused": "워크플로우 과정 일시 중지됨",
|
||||
"common.workflowProcessRunning": "워크플로우 과정 실행 중",
|
||||
"common.workflowProcessSucceeded": "워크플로우 과정 성공",
|
||||
"common.workflowSaveStatus": "워크플로우 저장 상태",
|
||||
"customWebhook": "맞춤 웹훅",
|
||||
"debug.copyLastRun": "마지막 실행 복사",
|
||||
"debug.copyLastRunError": "마지막 실행 입력을 복사하는 데 실패했습니다.",
|
||||
|
||||
@ -151,6 +151,7 @@
|
||||
"plansCommon.workflowExecution.standard": "Standard Workflow Execution",
|
||||
"plansCommon.workflowExecution.tooltip": "Workflow execution queue priority and speed.",
|
||||
"plansCommon.year": "year",
|
||||
"plansCommon.yearlyBilling": "Jaarlijkse facturering",
|
||||
"plansCommon.yearlyTip": "Pay for 10 months, enjoy 1 Year!",
|
||||
"teamMembers": "Team Members",
|
||||
"triggerLimitModal.description": "You've reached the limit of workflow event triggers for this plan.",
|
||||
|
||||
@ -280,6 +280,7 @@
|
||||
"common.workflowProcessPaused": "Workflowproces gepauzeerd",
|
||||
"common.workflowProcessRunning": "Workflowproces wordt uitgevoerd",
|
||||
"common.workflowProcessSucceeded": "Workflowproces geslaagd",
|
||||
"common.workflowSaveStatus": "Opslagstatus van workflow",
|
||||
"customWebhook": "Custom Webhook",
|
||||
"debug.copyLastRun": "Copy Last Run",
|
||||
"debug.copyLastRunError": "Failed to copy last run inputs",
|
||||
|
||||
@ -151,6 +151,7 @@
|
||||
"plansCommon.workflowExecution.standard": "Standardowe wykonywanie przepływu pracy",
|
||||
"plansCommon.workflowExecution.tooltip": "Priorytet i szybkość wykonywania kolejki przepływu pracy.",
|
||||
"plansCommon.year": "rok",
|
||||
"plansCommon.yearlyBilling": "Rozliczenie roczne",
|
||||
"plansCommon.yearlyTip": "Otrzymaj 2 miesiące za darmo, subskrybując rocznie!",
|
||||
"teamMembers": "Członkowie zespołu",
|
||||
"triggerLimitModal.description": "Osiągnąłeś limit wyzwalaczy zdarzeń przepływu pracy dla tego planu.",
|
||||
|
||||
@ -280,6 +280,7 @@
|
||||
"common.workflowProcessPaused": "Proces przepływu pracy wstrzymany",
|
||||
"common.workflowProcessRunning": "Proces przepływu pracy w toku",
|
||||
"common.workflowProcessSucceeded": "Proces przepływu pracy zakończony powodzeniem",
|
||||
"common.workflowSaveStatus": "Stan zapisu przepływu pracy",
|
||||
"customWebhook": "Niestandardowy webhook",
|
||||
"debug.copyLastRun": "Kopiuj ostatnie uruchomienie",
|
||||
"debug.copyLastRunError": "Nie udało się skopiować danych wejściowych z ostatniego uruchomienia",
|
||||
|
||||
@ -151,6 +151,7 @@
|
||||
"plansCommon.workflowExecution.standard": "Execução Padrão de Fluxo de Trabalho",
|
||||
"plansCommon.workflowExecution.tooltip": "Prioridade e velocidade da fila de execução de fluxo de trabalho.",
|
||||
"plansCommon.year": "ano",
|
||||
"plansCommon.yearlyBilling": "Cobrança anual",
|
||||
"plansCommon.yearlyTip": "Receba 2 meses grátis assinando anualmente!",
|
||||
"teamMembers": "Membros da equipe",
|
||||
"triggerLimitModal.description": "Você atingiu o limite de eventos de gatilho de fluxo de trabalho para este plano.",
|
||||
|
||||
@ -280,6 +280,7 @@
|
||||
"common.workflowProcessPaused": "Processo de fluxo de trabalho pausado",
|
||||
"common.workflowProcessRunning": "Processo de fluxo de trabalho em execução",
|
||||
"common.workflowProcessSucceeded": "Processo de fluxo de trabalho bem-sucedido",
|
||||
"common.workflowSaveStatus": "Status de salvamento do fluxo de trabalho",
|
||||
"customWebhook": "Webhook Personalizado",
|
||||
"debug.copyLastRun": "Copiar Última Execução",
|
||||
"debug.copyLastRunError": "Falha ao copiar as entradas da última execução",
|
||||
|
||||
@ -151,6 +151,7 @@
|
||||
"plansCommon.workflowExecution.standard": "Executarea fluxului de lucru standard",
|
||||
"plansCommon.workflowExecution.tooltip": "Prioritatea și viteza cozii de execuție a fluxului de lucru.",
|
||||
"plansCommon.year": "an",
|
||||
"plansCommon.yearlyBilling": "Facturare anuală",
|
||||
"plansCommon.yearlyTip": "Obțineți 2 luni gratuite prin abonarea anuală!",
|
||||
"teamMembers": "Membrii echipei",
|
||||
"triggerLimitModal.description": "Ai atins limita de evenimente declanșatoare de flux de lucru pentru acest plan.",
|
||||
|
||||
@ -280,6 +280,7 @@
|
||||
"common.workflowProcessPaused": "Procesul de flux de lucru este întrerupt",
|
||||
"common.workflowProcessRunning": "Procesul de flux de lucru rulează",
|
||||
"common.workflowProcessSucceeded": "Procesul de flux de lucru a reușit",
|
||||
"common.workflowSaveStatus": "Starea salvării fluxului de lucru",
|
||||
"customWebhook": "Webhook personalizat",
|
||||
"debug.copyLastRun": "Copiază ultima execuție",
|
||||
"debug.copyLastRunError": "Nu s-au putut copia ultimele intrări de rulare",
|
||||
|
||||
@ -151,6 +151,7 @@
|
||||
"plansCommon.workflowExecution.standard": "Стандартное выполнение рабочего процесса",
|
||||
"plansCommon.workflowExecution.tooltip": "Приоритет и скорость выполнения очереди рабочих процессов.",
|
||||
"plansCommon.year": "год",
|
||||
"plansCommon.yearlyBilling": "Ежегодная оплата",
|
||||
"plansCommon.yearlyTip": "Получите 2 месяца бесплатно, подписавшись на год!",
|
||||
"teamMembers": "Члены команды",
|
||||
"triggerLimitModal.description": "Вы достигли предела триггеров событий рабочего процесса для этого плана.",
|
||||
|
||||
@ -280,6 +280,7 @@
|
||||
"common.workflowProcessPaused": "Процесс рабочего процесса приостановлен",
|
||||
"common.workflowProcessRunning": "Процесс рабочего процесса выполняется",
|
||||
"common.workflowProcessSucceeded": "Процесс рабочего процесса выполнен успешно",
|
||||
"common.workflowSaveStatus": "Статус сохранения рабочего процесса",
|
||||
"customWebhook": "Пользовательский вебхук",
|
||||
"debug.copyLastRun": "Копировать последний запуск",
|
||||
"debug.copyLastRunError": "Не удалось скопировать последние входные данные выполнения",
|
||||
|
||||
@ -151,6 +151,7 @@
|
||||
"plansCommon.workflowExecution.standard": "Izvajanje standardnega delovnega procesa",
|
||||
"plansCommon.workflowExecution.tooltip": "Prednostna vrstni red in hitrost izvajanja delovnega toka.",
|
||||
"plansCommon.year": "leto",
|
||||
"plansCommon.yearlyBilling": "Letno obračunavanje",
|
||||
"plansCommon.yearlyTip": "Z letno naročnino pridobite 2 meseca brezplačno!",
|
||||
"teamMembers": "Člani ekipe",
|
||||
"triggerLimitModal.description": "Dosegli ste omejitev sprožilcev dogodkov delovnega toka za ta načrt.",
|
||||
|
||||
@ -280,6 +280,7 @@
|
||||
"common.workflowProcessPaused": "Delovni postopek je začasno ustavljen",
|
||||
"common.workflowProcessRunning": "Delovni postopek se izvaja",
|
||||
"common.workflowProcessSucceeded": "Delovni postopek je uspel",
|
||||
"common.workflowSaveStatus": "Stanje shranjevanja delovnega toka",
|
||||
"customWebhook": "Prilagojeni spletni kavelj",
|
||||
"debug.copyLastRun": "Kopiraj zadnji zagon",
|
||||
"debug.copyLastRunError": "Kopiranje vhodov zadnjega zagona ni uspelo",
|
||||
|
||||
@ -151,6 +151,7 @@
|
||||
"plansCommon.workflowExecution.standard": "การดำเนินงานเวิร์กโฟลว์มาตรฐาน",
|
||||
"plansCommon.workflowExecution.tooltip": "ลำดับความสำคัญและความเร็วของคิวการดำเนินงานของเวิร์กโฟลว์",
|
||||
"plansCommon.year": "ปี",
|
||||
"plansCommon.yearlyBilling": "การเรียกเก็บเงินรายปี",
|
||||
"plansCommon.yearlyTip": "รับฟรี 2 เดือนโดยสมัครสมาชิกรายปี!",
|
||||
"teamMembers": "สมาชิกในทีม",
|
||||
"triggerLimitModal.description": "คุณได้ถึงขีดจำกัดของทริกเกอร์เหตุการณ์เวิร์กโฟลว์สำหรับแผนนี้แล้ว",
|
||||
|
||||
@ -280,6 +280,7 @@
|
||||
"common.workflowProcessPaused": "กระบวนการเวิร์กโฟลว์หยุดชั่วคราว",
|
||||
"common.workflowProcessRunning": "กระบวนการเวิร์กโฟลว์กำลังทำงาน",
|
||||
"common.workflowProcessSucceeded": "กระบวนการเวิร์กโฟลว์สำเร็จ",
|
||||
"common.workflowSaveStatus": "สถานะการบันทึกเวิร์กโฟลว์",
|
||||
"customWebhook": "เว็บฮุกที่กำหนดเอง",
|
||||
"debug.copyLastRun": "คัดลอกการทำงานล่าสุด",
|
||||
"debug.copyLastRunError": "ไม่สามารถคัดลอกข้อมูลการทำงานครั้งสุดท้ายได้",
|
||||
|
||||
@ -151,6 +151,7 @@
|
||||
"plansCommon.workflowExecution.standard": "Standart İş Akışı Yürütme",
|
||||
"plansCommon.workflowExecution.tooltip": "İş akışı yürütme kuyruğu önceliği ve hızı.",
|
||||
"plansCommon.year": "yıl",
|
||||
"plansCommon.yearlyBilling": "Yıllık faturalandırma",
|
||||
"plansCommon.yearlyTip": "Yıllık abonelikle 2 ay ücretsiz!",
|
||||
"teamMembers": "Ekip Üyeleri",
|
||||
"triggerLimitModal.description": "Bu plan için iş akışı etkinliği tetikleyici sınırına ulaştınız.",
|
||||
|
||||
@ -280,6 +280,7 @@
|
||||
"common.workflowProcessPaused": "İş Akışı Süreci duraklatıldı",
|
||||
"common.workflowProcessRunning": "İş Akışı Süreci çalışıyor",
|
||||
"common.workflowProcessSucceeded": "İş Akışı Süreci başarılı oldu",
|
||||
"common.workflowSaveStatus": "İş akışı kaydetme durumu",
|
||||
"customWebhook": "Özel Webhook",
|
||||
"debug.copyLastRun": "Son Çalışmayı Kopyala",
|
||||
"debug.copyLastRunError": "Son çalışma girdilerini kopyalamak başarısız oldu.",
|
||||
|
||||
@ -151,6 +151,7 @@
|
||||
"plansCommon.workflowExecution.standard": "Виконання стандартного робочого процесу",
|
||||
"plansCommon.workflowExecution.tooltip": "Пріоритет і швидкість виконання черги робочого процесу.",
|
||||
"plansCommon.year": "рік",
|
||||
"plansCommon.yearlyBilling": "Щорічна оплата",
|
||||
"plansCommon.yearlyTip": "Отримайте 2 місяці безкоштовно, оформивши річну підписку!",
|
||||
"teamMembers": "Члени команди",
|
||||
"triggerLimitModal.description": "Ви досягли ліміту тригерів подій робочого процесу для цього плану.",
|
||||
|
||||
@ -280,6 +280,7 @@
|
||||
"common.workflowProcessPaused": "Процес робочого потоку призупинено",
|
||||
"common.workflowProcessRunning": "Процес робочого потоку виконується",
|
||||
"common.workflowProcessSucceeded": "Процес робочого потоку успішно завершено",
|
||||
"common.workflowSaveStatus": "Стан збереження робочого процесу",
|
||||
"customWebhook": "Користувацький вебхук",
|
||||
"debug.copyLastRun": "Копіювати останній запуск",
|
||||
"debug.copyLastRunError": "Не вдалося скопіювати вхідні дані останнього виконання",
|
||||
|
||||
@ -151,6 +151,7 @@
|
||||
"plansCommon.workflowExecution.standard": "Thực thi Quy trình Làm việc Chuẩn",
|
||||
"plansCommon.workflowExecution.tooltip": "Ưu tiên và tốc độ hàng đợi thực thi quy trình làm việc.",
|
||||
"plansCommon.year": "năm",
|
||||
"plansCommon.yearlyBilling": "Thanh toán hằng năm",
|
||||
"plansCommon.yearlyTip": "Nhận 2 tháng miễn phí khi đăng ký hàng năm!",
|
||||
"teamMembers": "Các thành viên trong nhóm",
|
||||
"triggerLimitModal.description": "Bạn đã đạt đến giới hạn kích hoạt sự kiện quy trình cho gói này.",
|
||||
|
||||
@ -280,6 +280,7 @@
|
||||
"common.workflowProcessPaused": "Quy trình làm việc đã tạm dừng",
|
||||
"common.workflowProcessRunning": "Quy trình làm việc đang chạy",
|
||||
"common.workflowProcessSucceeded": "Quy trình làm việc thành công",
|
||||
"common.workflowSaveStatus": "Trạng thái lưu quy trình làm việc",
|
||||
"customWebhook": "Webhook Tùy Chỉnh",
|
||||
"debug.copyLastRun": "Sao chép lần chạy cuối",
|
||||
"debug.copyLastRunError": "Không thể sao chép đầu vào của lần chạy trước",
|
||||
|
||||
@ -151,6 +151,7 @@
|
||||
"plansCommon.workflowExecution.standard": "标准工作流执行队列",
|
||||
"plansCommon.workflowExecution.tooltip": "工作流的执行队列优先级与运行速度。",
|
||||
"plansCommon.year": "年",
|
||||
"plansCommon.yearlyBilling": "按年计费",
|
||||
"plansCommon.yearlyTip": "支付 10 个月,享受 1 年!",
|
||||
"teamMembers": "团队成员",
|
||||
"triggerLimitModal.description": "您已达到此计划上工作流的触发器事件数限制。",
|
||||
|
||||
@ -280,6 +280,7 @@
|
||||
"common.workflowProcessPaused": "工作流运行已暂停",
|
||||
"common.workflowProcessRunning": "工作流运行中",
|
||||
"common.workflowProcessSucceeded": "工作流运行成功",
|
||||
"common.workflowSaveStatus": "工作流保存状态",
|
||||
"customWebhook": "自定义 Webhook",
|
||||
"debug.copyLastRun": "复制上次运行值",
|
||||
"debug.copyLastRunError": "复制上次运行输入失败",
|
||||
|
||||
@ -151,6 +151,7 @@
|
||||
"plansCommon.workflowExecution.standard": "標準工作流程執行",
|
||||
"plansCommon.workflowExecution.tooltip": "工作流程執行隊列的優先順序與速度。",
|
||||
"plansCommon.year": "年",
|
||||
"plansCommon.yearlyBilling": "按年計費",
|
||||
"plansCommon.yearlyTip": "訂閱年度計劃可免費獲得 2 個月!",
|
||||
"teamMembers": "團隊成員",
|
||||
"triggerLimitModal.description": "您已達到此方案的工作流程事件觸發上限。",
|
||||
|
||||
@ -280,6 +280,7 @@
|
||||
"common.workflowProcessPaused": "工作流運行已暫停",
|
||||
"common.workflowProcessRunning": "工作流運行中",
|
||||
"common.workflowProcessSucceeded": "工作流運行成功",
|
||||
"common.workflowSaveStatus": "工作流程儲存狀態",
|
||||
"customWebhook": "自訂 Webhook",
|
||||
"debug.copyLastRun": "複製上一次運行",
|
||||
"debug.copyLastRunError": "未能複製上一次運行的輸入",
|
||||
|
||||
Loading…
Reference in New Issue
Block a user