Browse Source

feat: add api to specify default column order in active view

Signed-off-by: Pranav C <pranavxc@gmail.com>
pull/4504/head
Pranav C 2 years ago
parent
commit
27a19ea7f5
  1. 10
      packages/nc-gui/components/smartsheet/header/Menu.vue
  2. 32
      packages/nocodb-sdk/src/lib/Api.ts
  3. 50
      packages/nocodb/src/lib/meta/api/columnApis.ts
  4. 2
      packages/nocodb/src/lib/models/Column.ts
  5. 6
      packages/nocodb/src/lib/models/GridViewColumn.ts
  6. 42
      packages/nocodb/src/lib/models/View.ts
  7. 61
      scripts/sdk/swagger.json

10
packages/nc-gui/components/smartsheet/header/Menu.vue

@ -132,8 +132,6 @@ const duplicateColumn = async () => {
} }
try { try {
await $api.dbTableColumn.create(meta!.value!.id!, columnCreatePayload)
await getMeta(meta!.value!.id!, true)
const gridViewColumnList = await $api.dbViewColumn.list(view.value?.id as string) const gridViewColumnList = await $api.dbViewColumn.list(view.value?.id as string)
@ -145,9 +143,15 @@ const duplicateColumn = async () => {
let newColumnOrder = (gridViewColumnList[currentColumnIndex].order! + gridViewColumnList[currentColumnIndex + 1]?.order) / 2 let newColumnOrder = (gridViewColumnList[currentColumnIndex].order! + gridViewColumnList[currentColumnIndex + 1]?.order) / 2
await $api.dbViewColumn.update(view.value!.id!, gridViewColumnList[gridViewColumnList.length - 1].id, { await $api.dbTableColumn.create(meta!.value!.id!, {
...columnCreatePayload,
columnOrder: {
order: newColumnOrder, order: newColumnOrder,
viewId: view.value?.id as string,
},
}) })
await getMeta(meta!.value!.id!, true)
eventBus.emit(SmartsheetStoreEvents.FIELD_RELOAD) eventBus.emit(SmartsheetStoreEvents.FIELD_RELOAD)
} catch (e: any) { } catch (e: any) {

32
packages/nocodb-sdk/src/lib/Api.ts

@ -571,8 +571,7 @@ export interface HookLogType {
updated_at?: string; updated_at?: string;
} }
export type ColumnReqType = export interface NormalColumnRequestType {
| {
uidt?: uidt?:
| 'ID' | 'ID'
| 'SingleLineText' | 'SingleLineText'
@ -628,33 +627,52 @@ export type ColumnReqType =
dtxp?: string; dtxp?: string;
dtxs?: string; dtxs?: string;
au?: boolean; au?: boolean;
''?: string;
} }
| {
export interface LinkToAnotherColumnReqType {
uidt: 'LinkToAnotherRecord'; uidt: 'LinkToAnotherRecord';
title: string; title: string;
virtual?: boolean;
parentId: string; parentId: string;
childId: string; childId: string;
type: 'hm' | 'bt' | 'mm'; type: 'hm' | 'bt' | 'mm';
} }
| {
export interface RollupColumnReqType {
uidt?: 'Rollup'; uidt?: 'Rollup';
title?: string; title?: string;
fk_relation_column_id?: string; fk_relation_column_id?: string;
fk_rollup_column_id?: string; fk_rollup_column_id?: string;
rollup_function?: string; rollup_function?: string;
} }
| {
export interface LookupColumnReqType {
uidt?: 'Lookup'; uidt?: 'Lookup';
title?: string; title?: string;
fk_relation_column_id?: string; fk_relation_column_id?: string;
fk_lookup_column_id?: string; fk_lookup_column_id?: string;
} }
| {
export interface FormulaColumnReqType {
uidt?: string; uidt?: string;
formula_raw?: string; formula_raw?: string;
formula?: string; formula?: string;
title?: string; title?: string;
}
export type ColumnReqType = (
| NormalColumnRequestType
| LinkToAnotherColumnReqType
| RollupColumnReqType
| FormulaColumnReqType
| LookupColumnReqType
) & {
column_name?: string;
title?: string;
columnOrder?: {
viewId?: string;
order?: number;
};
}; };
export interface UserInfoType { export interface UserInfoType {

50
packages/nocodb/src/lib/meta/api/columnApis.ts

@ -15,9 +15,13 @@ import {
import { import {
AuditOperationSubTypes, AuditOperationSubTypes,
AuditOperationTypes, AuditOperationTypes,
ColumnReqType,
isVirtualCol, isVirtualCol,
LinkToAnotherColumnReqType,
LinkToAnotherRecordType, LinkToAnotherRecordType,
LookupColumnReqType,
RelationTypes, RelationTypes,
RollupColumnReqType,
substituteColumnAliasWithIdInFormula, substituteColumnAliasWithIdInFormula,
substituteColumnIdWithAliasInFormula, substituteColumnIdWithAliasInFormula,
TableType, TableType,
@ -96,7 +100,10 @@ async function createHmAndBtColumn(
} }
} }
export async function columnAdd(req: Request, res: Response<TableType>) { export async function columnAdd(
req: Request<any, any, ColumnReqType & { uidt: UITypes }>,
res: Response<TableType>
) {
const table = await Model.getWithInfo({ const table = await Model.getWithInfo({
id: req.params.tableId, id: req.params.tableId,
}); });
@ -121,7 +128,7 @@ export async function columnAdd(req: Request, res: Response<TableType>) {
NcError.badRequest('Duplicate column alias'); NcError.badRequest('Duplicate column alias');
} }
let colBody = req.body; let colBody: any = req.body;
switch (colBody.uidt) { switch (colBody.uidt) {
case UITypes.Rollup: case UITypes.Rollup:
{ {
@ -137,7 +144,7 @@ export async function columnAdd(req: Request, res: Response<TableType>) {
const relation = await ( const relation = await (
await Column.get({ await Column.get({
colId: req.body.fk_relation_column_id, colId: (req.body as RollupColumnReqType).fk_relation_column_id,
}) })
).getColOptions<LinkToAnotherRecordType>(); ).getColOptions<LinkToAnotherRecordType>();
@ -163,7 +170,8 @@ export async function columnAdd(req: Request, res: Response<TableType>) {
const relatedTable = await relatedColumn.getModel(); const relatedTable = await relatedColumn.getModel();
if ( if (
!(await relatedTable.getColumns()).find( !(await relatedTable.getColumns()).find(
(c) => c.id === req.body.fk_rollup_column_id (c) =>
c.id === (req.body as RollupColumnReqType).fk_rollup_column_id
) )
) )
throw new Error('Rollup column not found in related table'); throw new Error('Rollup column not found in related table');
@ -183,7 +191,7 @@ export async function columnAdd(req: Request, res: Response<TableType>) {
const relation = await ( const relation = await (
await Column.get({ await Column.get({
colId: req.body.fk_relation_column_id, colId: (req.body as LookupColumnReqType).fk_relation_column_id,
}) })
).getColOptions<LinkToAnotherRecordType>(); ).getColOptions<LinkToAnotherRecordType>();
@ -209,7 +217,8 @@ export async function columnAdd(req: Request, res: Response<TableType>) {
const relatedTable = await relatedColumn.getModel(); const relatedTable = await relatedColumn.getModel();
if ( if (
!(await relatedTable.getColumns()).find( !(await relatedTable.getColumns()).find(
(c) => c.id === req.body.fk_lookup_column_id (c) =>
c.id === (req.body as LookupColumnReqType).fk_lookup_column_id
) )
) )
throw new Error('Lookup column not found in related table'); throw new Error('Lookup column not found in related table');
@ -227,14 +236,21 @@ export async function columnAdd(req: Request, res: Response<TableType>) {
validateParams(['parentId', 'childId', 'type'], req.body); validateParams(['parentId', 'childId', 'type'], req.body);
// get parent and child models // get parent and child models
const parent = await Model.getWithInfo({ id: req.body.parentId }); const parent = await Model.getWithInfo({
const child = await Model.getWithInfo({ id: req.body.childId }); id: (req.body as LinkToAnotherColumnReqType).parentId,
});
const child = await Model.getWithInfo({
id: (req.body as LinkToAnotherColumnReqType).childId,
});
let childColumn: Column; let childColumn: Column;
const sqlMgr = await ProjectMgrv2.getSqlMgr({ const sqlMgr = await ProjectMgrv2.getSqlMgr({
id: base.project_id, id: base.project_id,
}); });
if (req.body.type === 'hm' || req.body.type === 'bt') { if (
(req.body as LinkToAnotherColumnReqType).type === 'hm' ||
(req.body as LinkToAnotherColumnReqType).type === 'bt'
) {
// populate fk column name // populate fk column name
const fkColName = getUniqueColumnName( const fkColName = getUniqueColumnName(
await child.getColumns(), await child.getColumns(),
@ -285,7 +301,7 @@ export async function columnAdd(req: Request, res: Response<TableType>) {
childColumn = await Column.get({ colId: id }); childColumn = await Column.get({ colId: id });
// ignore relation creation if virtual // ignore relation creation if virtual
if (!req.body.virtual) { if (!(req.body as LinkToAnotherColumnReqType).virtual) {
// create relation // create relation
await sqlMgr.sqlOpPlus(base, 'relationCreate', { await sqlMgr.sqlOpPlus(base, 'relationCreate', {
childColumn: fkColName, childColumn: fkColName,
@ -315,11 +331,11 @@ export async function columnAdd(req: Request, res: Response<TableType>) {
child, child,
parent, parent,
childColumn, childColumn,
req.body.type, (req.body as LinkToAnotherColumnReqType).type as RelationTypes,
req.body.title, (req.body as LinkToAnotherColumnReqType).title,
req.body.virtual (req.body as LinkToAnotherColumnReqType).virtual
); );
} else if (req.body.type === 'mm') { } else if ((req.body as LinkToAnotherColumnReqType).type === 'mm') {
const aTn = `${project?.prefix ?? ''}_nc_m2m_${randomID()}`; const aTn = `${project?.prefix ?? ''}_nc_m2m_${randomID()}`;
const aTnAlias = aTn; const aTnAlias = aTn;
@ -378,7 +394,7 @@ export async function columnAdd(req: Request, res: Response<TableType>) {
columns: associateTableCols, columns: associateTableCols,
}); });
if (!req.body.virtual) { if (!(req.body as LinkToAnotherColumnReqType).virtual) {
const rel1Args = { const rel1Args = {
...req.body, ...req.body,
childTable: aTn, childTable: aTn,
@ -412,7 +428,7 @@ export async function columnAdd(req: Request, res: Response<TableType>) {
childCol, childCol,
null, null,
null, null,
req.body.virtual, (req.body as LinkToAnotherColumnReqType).virtual,
true true
); );
await createHmAndBtColumn( await createHmAndBtColumn(
@ -421,7 +437,7 @@ export async function columnAdd(req: Request, res: Response<TableType>) {
parentCol, parentCol,
null, null,
null, null,
req.body.virtual, (req.body as LinkToAnotherColumnReqType).virtual,
true true
); );

2
packages/nocodb/src/lib/models/Column.ts

@ -5,7 +5,7 @@ import RollupColumn from './RollupColumn';
import SelectOption from './SelectOption'; import SelectOption from './SelectOption';
import Model from './Model'; import Model from './Model';
import NocoCache from '../cache/NocoCache'; import NocoCache from '../cache/NocoCache';
import { AllowedColumnTypesForQrCode, ColumnType, UITypes } from 'nocodb-sdk'; import { ColumnReqType, AllowedColumnTypesForQrCode, ColumnType, UITypes } from 'nocodb-sdk';
import { import {
CacheDelDirection, CacheDelDirection,
CacheGetType, CacheGetType,

6
packages/nocodb/src/lib/models/GridViewColumn.ts

@ -70,9 +70,11 @@ export default class GridViewColumn implements GridColumnType {
const insertObj = { const insertObj = {
fk_view_id: column.fk_view_id, fk_view_id: column.fk_view_id,
fk_column_id: column.fk_column_id, fk_column_id: column.fk_column_id,
order: await ncMeta.metaGetNextOrder(MetaTable.GRID_VIEW_COLUMNS, { order:
column?.order ??
(await ncMeta.metaGetNextOrder(MetaTable.GRID_VIEW_COLUMNS, {
fk_view_id: column.fk_view_id, fk_view_id: column.fk_view_id,
}), })),
show: column.show, show: column.show,
project_id: column.project_id, project_id: column.project_id,
base_id: column.base_id, base_id: column.base_id,

42
packages/nocodb/src/lib/models/View.ts

@ -13,7 +13,13 @@ import GalleryView from './GalleryView';
import GridViewColumn from './GridViewColumn'; import GridViewColumn from './GridViewColumn';
import Sort from './Sort'; import Sort from './Sort';
import Filter from './Filter'; import Filter from './Filter';
import { isSystemColumn, UITypes, ViewType, ViewTypes } from 'nocodb-sdk'; import {
ColumnReqType,
isSystemColumn,
UITypes,
ViewType,
ViewTypes,
} from 'nocodb-sdk';
import GalleryViewColumn from './GalleryViewColumn'; import GalleryViewColumn from './GalleryViewColumn';
import FormViewColumn from './FormViewColumn'; import FormViewColumn from './FormViewColumn';
import KanbanViewColumn from './KanbanViewColumn'; import KanbanViewColumn from './KanbanViewColumn';
@ -442,9 +448,9 @@ export default class View implements ViewType {
param: { param: {
fk_column_id: any; fk_column_id: any;
fk_model_id: any; fk_model_id: any;
order; order?: number;
show; show;
}, } & Pick<ColumnReqType, 'columnOrder'>,
ncMeta = Noco.ncMeta ncMeta = Noco.ncMeta
) { ) {
const insertObj = { const insertObj = {
@ -456,33 +462,21 @@ export default class View implements ViewType {
const views = await this.list(param.fk_model_id, ncMeta); const views = await this.list(param.fk_model_id, ncMeta);
for (const view of views) { for (const view of views) {
const modifiedInsertObj = { ...insertObj, fk_view_id: view.id };
if (param.columnOrder?.viewId === view.id) {
modifiedInsertObj.order = param.columnOrder?.order;
}
switch (view.type) { switch (view.type) {
case ViewTypes.GRID: case ViewTypes.GRID:
await GridViewColumn.insert( await GridViewColumn.insert(modifiedInsertObj, ncMeta);
{
...insertObj,
fk_view_id: view.id,
},
ncMeta
);
break; break;
case ViewTypes.GALLERY: case ViewTypes.GALLERY:
await GalleryViewColumn.insert( await GalleryViewColumn.insert(modifiedInsertObj, ncMeta);
{
...insertObj,
fk_view_id: view.id,
},
ncMeta
);
break; break;
case ViewTypes.KANBAN: case ViewTypes.KANBAN:
await KanbanViewColumn.insert( await KanbanViewColumn.insert(modifiedInsertObj, ncMeta);
{
...insertObj,
fk_view_id: view.id,
},
ncMeta
);
break; break;
} }
} }

61
scripts/sdk/swagger.json

@ -8957,9 +8957,7 @@
} }
} }
}, },
"ColumnReq": { "NormalColumnRequest": {
"oneOf": [
{
"properties": { "properties": {
"uidt": { "uidt": {
"type": "string", "type": "string",
@ -9070,13 +9068,10 @@
}, },
"au": { "au": {
"type": "boolean" "type": "boolean"
},
"": {
"type": "string"
} }
} }
}, },
{ "LinkToAnotherColumnReq": {
"properties": { "properties": {
"uidt": { "uidt": {
"type": "string", "type": "string",
@ -9087,6 +9082,9 @@
"title": { "title": {
"type": "string" "type": "string"
}, },
"virtual": {
"type": "boolean"
},
"parentId": { "parentId": {
"type": "string" "type": "string"
}, },
@ -9110,7 +9108,7 @@
"type" "type"
] ]
}, },
{ "RollupColumnReq": {
"properties": { "properties": {
"uidt": { "uidt": {
"type": "string", "type": "string",
@ -9132,7 +9130,7 @@
} }
} }
}, },
{ "LookupColumnReq": {
"properties": { "properties": {
"uidt": { "uidt": {
"type": "string", "type": "string",
@ -9151,7 +9149,7 @@
} }
} }
}, },
{ "FormulaColumnReq": {
"properties": { "properties": {
"uidt": { "uidt": {
"type": "string" "type": "string"
@ -9166,6 +9164,49 @@
"type": "string" "type": "string"
} }
} }
},
"ColumnReq": {
"allOf": [
{
"oneOf": [
{
"$ref": "#/components/schemas/NormalColumnRequest"
},
{
"$ref": "#/components/schemas/LinkToAnotherColumnReq"
},
{
"$ref": "#/components/schemas/RollupColumnReq"
},
{
"$ref": "#/components/schemas/FormulaColumnReq"
},
{
"$ref": "#/components/schemas/LookupColumnReq"
}
]
},
{
"type": "object",
"properties": {
"column_name": {
"type": "string"
},
"title": {
"type": "string"
},
"columnOrder": {
"type": "object",
"properties": {
"viewId": {
"type": "string"
},
"order": {
"type": "integer"
}
}
}
}
} }
], ],
"description": "", "description": "",

Loading…
Cancel
Save