mirror of
https://gitee.com/nocobase/nocobase.git
synced 2025-05-05 05:29:26 +08:00
Merge branch 'main' into next
This commit is contained in:
commit
42a9d5a6cb
@ -821,6 +821,7 @@
|
||||
"File size should not exceed {{size}}.": "文件大小不能超过 {{size}}",
|
||||
"File size exceeds the limit": "文件大小超过限制",
|
||||
"File type is not allowed": "文件类型不允许",
|
||||
"Uploading": "上传中",
|
||||
"Incomplete uploading files need to be resolved": "未完成上传的文件需要处理",
|
||||
"Default title for each record": "用作数据的默认标题",
|
||||
"If collection inherits, choose inherited collections as templates": "当前表有继承关系时,可选择继承链路上的表作为模板来源",
|
||||
|
@ -42,6 +42,8 @@ function InputInner(props: NocoBaseInputProps) {
|
||||
return <AntdInput {...others} onChange={handleChange} />;
|
||||
}
|
||||
|
||||
InputInner.Password = AntdInput.Password;
|
||||
|
||||
export const Input: ComposedInput = Object.assign(
|
||||
connect(
|
||||
InputInner,
|
||||
|
@ -799,7 +799,7 @@ export function useDesignable() {
|
||||
return component;
|
||||
}
|
||||
const c = get(components, component);
|
||||
return c[LAZY_COMPONENT_KEY] ?? c;
|
||||
return c?.[LAZY_COMPONENT_KEY] ?? c;
|
||||
},
|
||||
[get],
|
||||
),
|
||||
|
@ -15,3 +15,4 @@ export * from './datetime-interface';
|
||||
export * from './datetime-no-tz-interface';
|
||||
export * from './boolean-interface';
|
||||
export * from './date-interface';
|
||||
export * from './time-interface';
|
||||
|
26
packages/core/database/src/interfaces/time-interface.ts
Normal file
26
packages/core/database/src/interfaces/time-interface.ts
Normal file
@ -0,0 +1,26 @@
|
||||
/**
|
||||
* This file is part of the NocoBase (R) project.
|
||||
* Copyright (c) 2020-2024 NocoBase Co., Ltd.
|
||||
* Authors: NocoBase Team.
|
||||
*
|
||||
* This project is dual-licensed under AGPL-3.0 and NocoBase Commercial License.
|
||||
* For more information, please refer to: https://www.nocobase.com/agreement.
|
||||
*/
|
||||
|
||||
import dayjs from 'dayjs';
|
||||
import { BaseInterface } from './base-interface';
|
||||
|
||||
export class TimeInterface extends BaseInterface {
|
||||
toValue(value: any, ctx?: any) {
|
||||
if (this.validate(value)) {
|
||||
const result = dayjs.utc(value).format('HH:mm:ss');
|
||||
return result;
|
||||
}
|
||||
return value;
|
||||
}
|
||||
|
||||
validate(value) {
|
||||
const result = dayjs(value).isValid();
|
||||
return result;
|
||||
}
|
||||
}
|
@ -16,6 +16,7 @@ import {
|
||||
MultipleSelectInterface,
|
||||
PercentInterface,
|
||||
SelectInterface,
|
||||
TimeInterface,
|
||||
} from './index';
|
||||
import { ManyToOneInterface } from './many-to-one-interface';
|
||||
import { ManyToManyInterface } from './many-to-many-interface';
|
||||
@ -50,6 +51,7 @@ const interfaces = {
|
||||
o2m: OneToManyInterface,
|
||||
m2o: ManyToOneInterface,
|
||||
m2m: ManyToManyInterface,
|
||||
time: TimeInterface,
|
||||
};
|
||||
|
||||
export function registerInterfaces(db: Database) {
|
||||
|
@ -2155,4 +2155,53 @@ describe('xlsx importer', () => {
|
||||
|
||||
expect(await Post.repository.count()).toBe(1);
|
||||
});
|
||||
|
||||
it('should import time field successfully', async () => {
|
||||
const TimeCollection = app.db.collection({
|
||||
name: 'time_tests',
|
||||
fields: [
|
||||
{
|
||||
type: 'time',
|
||||
name: 'brithtime',
|
||||
},
|
||||
],
|
||||
});
|
||||
|
||||
await app.db.sync();
|
||||
const templateCreator = new TemplateCreator({
|
||||
collection: TimeCollection,
|
||||
explain: 'test',
|
||||
columns: [
|
||||
{
|
||||
dataIndex: ['birthtime'],
|
||||
defaultTitle: '出生时间',
|
||||
},
|
||||
],
|
||||
});
|
||||
|
||||
const template = (await templateCreator.run({ returnXLSXWorkbook: true })) as XLSX.WorkBook;
|
||||
|
||||
const worksheet = template.Sheets[template.SheetNames[0]];
|
||||
|
||||
XLSX.utils.sheet_add_aoa(worksheet, [['12:12:12']], {
|
||||
origin: 'A3',
|
||||
});
|
||||
|
||||
const importer = new XlsxImporter({
|
||||
collectionManager: app.mainDataSource.collectionManager,
|
||||
collection: TimeCollection,
|
||||
explain: 'test',
|
||||
columns: [
|
||||
{
|
||||
dataIndex: ['brithtime'],
|
||||
defaultTitle: '出生时间',
|
||||
},
|
||||
],
|
||||
workbook: template,
|
||||
});
|
||||
|
||||
await importer.run();
|
||||
const count = await TimeCollection.repository.count();
|
||||
expect(count).toBe(1);
|
||||
});
|
||||
});
|
||||
|
@ -36,6 +36,7 @@ async function importXlsxAction(ctx: Context, next: Next) {
|
||||
const workbook = XLSX.read(ctx.file.buffer, {
|
||||
type: 'buffer',
|
||||
sheetRows: readLimit,
|
||||
cellDates: true,
|
||||
});
|
||||
|
||||
const repository = ctx.getCurrentRepository() as Repository;
|
||||
|
@ -8,6 +8,7 @@
|
||||
*/
|
||||
|
||||
import React, { createContext, useCallback, useContext, useEffect, useState } from 'react';
|
||||
import { useNavigate, useParams } from 'react-router-dom';
|
||||
import { useField, useFieldSchema, useForm } from '@formily/react';
|
||||
import { FormLayout } from '@formily/antd-v5';
|
||||
import { Button, Card, ConfigProvider, Descriptions, Space, Spin, Tag } from 'antd';
|
||||
@ -47,7 +48,6 @@ import WorkflowPlugin, {
|
||||
useAvailableUpstreams,
|
||||
useFlowContext,
|
||||
EXECUTION_STATUS,
|
||||
JOB_STATUS,
|
||||
WorkflowTitle,
|
||||
TASK_STATUS,
|
||||
usePopupRecordContext,
|
||||
@ -56,8 +56,7 @@ import WorkflowPlugin, {
|
||||
import { NAMESPACE, useLang } from '../locale';
|
||||
import { FormBlockProvider } from './instruction/FormBlockProvider';
|
||||
import { ManualFormType, manualFormTypes } from './instruction/SchemaConfig';
|
||||
import { TaskStatusOptionsMap } from '../common/constants';
|
||||
import { useNavigate, useParams } from 'react-router-dom';
|
||||
import { TaskStatusOptionsMap, TASK_STATUS } from '../common/constants';
|
||||
|
||||
function TaskStatusColumn(props) {
|
||||
const recordData = useCollectionRecordData();
|
||||
@ -654,11 +653,11 @@ function TaskItem() {
|
||||
|
||||
const StatusFilterMap = {
|
||||
pending: {
|
||||
status: JOB_STATUS.PENDING,
|
||||
status: TASK_STATUS.PENDING,
|
||||
'execution.status': EXECUTION_STATUS.STARTED,
|
||||
},
|
||||
completed: {
|
||||
status: JOB_STATUS.RESOLVED,
|
||||
status: [TASK_STATUS.RESOLVED, TASK_STATUS.REJECTED],
|
||||
},
|
||||
};
|
||||
|
||||
|
@ -14,7 +14,7 @@ export const MANUAL_TASK_TYPE = 'manual';
|
||||
export const TASK_STATUS = {
|
||||
PENDING: 0,
|
||||
RESOLVED: 1,
|
||||
REJECTED: -1,
|
||||
REJECTED: -5,
|
||||
};
|
||||
|
||||
export const TaskStatusOptions = [
|
||||
|
Loading…
x
Reference in New Issue
Block a user