This is an automated email from the ASF dual-hosted git repository.
dockerzhang pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/inlong.git
The following commit(s) were added to refs/heads/master by this push:
new 2b83000ff [INLONG-7264][Dashboard] Support sink Apache Kudu (#7267)
2b83000ff is described below
commit 2b83000ffe524fa287982f0a8750d48066676480
Author: feat <[email protected]>
AuthorDate: Tue Jan 31 14:15:08 2023 +0800
[INLONG-7264][Dashboard] Support sink Apache Kudu (#7267)
Co-authored-by: healchow <[email protected]>
---
inlong-dashboard/src/locales/cn.json | 11 +
inlong-dashboard/src/locales/en.json | 11 +
inlong-dashboard/src/metas/sinks/defaults/Kudu.ts | 242 +++++++++++++++++++++
inlong-dashboard/src/metas/sinks/defaults/index.ts | 5 +
4 files changed, 269 insertions(+)
diff --git a/inlong-dashboard/src/locales/cn.json
b/inlong-dashboard/src/locales/cn.json
index 5640a53cb..fc5666bec 100644
--- a/inlong-dashboard/src/locales/cn.json
+++ b/inlong-dashboard/src/locales/cn.json
@@ -344,6 +344,17 @@
"meta.Sinks.Redis.DataSeparator.Asterisk": "星号(*)",
"meta.Sinks.Redis.DataSeparator.DoubleQuotes": "双引号(\")",
"meta.Sinks.Redis.FormatDataSeparator": "数据字段分隔符",
+ "meta.Sinks.Kudu.masters": "主节点",
+ "meta.Sinks.Kudu.TableName": "表名",
+ "meta.Sinks.Kudu.ExtListHelper": "Kudu 表的 DDL 属性需添加'ddl.'前缀",
+ "meta.Sinks.Kudu.ExtList": "高级参数",
+ "meta.Sinks.Kudu.DataConsistency": "数据一致性",
+ "meta.Sinks.Kudu.PartitionKeyHelper": "主键字段需以逗号分割",
+ "meta.Sinks.Kudu.PartitionKey": "主键字段",
+ "meta.Sinks.Kudu.FieldName": "字段名",
+ "meta.Sinks.Kudu.FieldNameRule": "以英文字母或下划线开头,只能包含英文字母、数字、下划线",
+ "meta.Sinks.Kudu.FieldType": "类型",
+ "meta.Sinks.Kudu.FieldDescription": "描述",
"meta.Group.InlongGroupId": "数据流组 ID",
"meta.Group.InlongGroupIdRules": "只能包含小写字母、数字、中划线、下划线",
"meta.Group.InlongGroupName": "数据流组名称",
diff --git a/inlong-dashboard/src/locales/en.json
b/inlong-dashboard/src/locales/en.json
index 116fbb94a..8f35eb2a3 100644
--- a/inlong-dashboard/src/locales/en.json
+++ b/inlong-dashboard/src/locales/en.json
@@ -344,6 +344,17 @@
"meta.Sinks.Redis.DataSeparator.Asterisk": "Asterisk(*)",
"meta.Sinks.Redis.DataSeparator.DoubleQuotes": "Double quotes(\")",
"meta.Sinks.Redis.FormatDataSeparator": "Data separator",
+ "meta.Sinks.Kudu.masters": "masters",
+ "meta.Sinks.Kudu.TableName": "Table",
+ "meta.Sinks.Kudu.ExtListHelper": "The DDL attribute of the Kudu table needs
to be prefixed with 'ddl.'",
+ "meta.Sinks.Kudu.ExtList": "Extenstion params",
+ "meta.Sinks.Kudu.DataConsistency": "DataConsistency",
+ "meta.Sinks.Kudu.PartitionKeyHelper": "Primary key fields need to be
separated by commas",
+ "meta.Sinks.Kudu.PartitionKey": "PartitionKey",
+ "meta.Sinks.Kudu.FieldName": "FieldName",
+ "meta.Sinks.Kudu.FieldNameRule": "At the beginning of English letters, only
English letters, numbers, and underscores",
+ "meta.Sinks.Kudu.FieldType": "FieldType",
+ "meta.Sinks.Kudu.FieldDescription": "FieldDescription",
"meta.Group.InlongGroupId": "Inlong Group ID",
"meta.Group.InlongGroupIdRules": "Only lowercase letters, numbers, minus,
and underscores",
"meta.Group.InlongGroupName": "Inlong Group Name",
diff --git a/inlong-dashboard/src/metas/sinks/defaults/Kudu.ts
b/inlong-dashboard/src/metas/sinks/defaults/Kudu.ts
new file mode 100644
index 000000000..3c43c69b4
--- /dev/null
+++ b/inlong-dashboard/src/metas/sinks/defaults/Kudu.ts
@@ -0,0 +1,242 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import { DataWithBackend } from '@/metas/DataWithBackend';
+import { RenderRow } from '@/metas/RenderRow';
+import { RenderList } from '@/metas/RenderList';
+import i18n from '@/i18n';
+import EditableTable from '@/components/EditableTable';
+import { sourceFields } from '../common/sourceFields';
+import { SinkInfo } from '../common/SinkInfo';
+
+const { I18n } = DataWithBackend;
+const { FieldDecorator } = RenderRow;
+const { ColumnDecorator } = RenderList;
+
+const kuduFieldTypes = [
+ 'int',
+ 'long',
+ 'string',
+ 'float',
+ 'double',
+ 'date',
+ 'timestamp',
+ 'time',
+ 'boolean',
+ 'decimal',
+ 'timestamptz',
+ 'binary',
+ 'fixed',
+ 'uuid',
+].map(item => ({
+ label: item,
+ value: item,
+}));
+
+export default class KuduSink extends SinkInfo implements DataWithBackend,
RenderRow, RenderList {
+ @FieldDecorator({
+ type: 'input',
+ initialValue: '127.0.0.1:5071,127.0.0.1:5072',
+ rules: [{ required: true }],
+ props: values => ({
+ disabled: [110, 130].includes(values?.status),
+ placeholder: '127.0.0.1:5071,127.0.0.1:5072',
+ }),
+ })
+ @ColumnDecorator()
+ @I18n('meta.Sinks.Kudu.masters')
+ masters: string;
+
+ @FieldDecorator({
+ type: 'input',
+ rules: [{ required: true }],
+ props: values => ({
+ disabled: [110, 130].includes(values?.status),
+ }),
+ })
+ @ColumnDecorator()
+ @I18n('meta.Sinks.Kudu.TableName')
+ tableName: string;
+
+ @FieldDecorator({
+ type: 'radio',
+ rules: [{ required: true }],
+ initialValue: 1,
+ tooltip: i18n.t('meta.Sinks.EnableCreateResourceHelp'),
+ props: values => ({
+ disabled: [110, 130].includes(values?.status),
+ options: [
+ {
+ label: i18n.t('basic.Yes'),
+ value: 1,
+ },
+ {
+ label: i18n.t('basic.No'),
+ value: 0,
+ },
+ ],
+ }),
+ })
+ @I18n('meta.Sinks.EnableCreateResource')
+ enableCreateResource: number;
+
+ @FieldDecorator({
+ type: EditableTable,
+ rules: [{ required: false }],
+ initialValue: [],
+ tooltip: i18n.t('meta.Sinks.Kudu.ExtListHelper'),
+ props: values => ({
+ size: 'small',
+ columns: [
+ {
+ title: 'Key',
+ dataIndex: 'keyName',
+ props: {
+ disabled: [110, 130].includes(values?.status),
+ },
+ },
+ {
+ title: 'Value',
+ dataIndex: 'keyValue',
+ props: {
+ disabled: [110, 130].includes(values?.status),
+ },
+ },
+ ],
+ }),
+ })
+ @ColumnDecorator()
+ @I18n('meta.Sinks.Kudu.ExtList')
+ extList: string;
+
+ @FieldDecorator({
+ type: 'select',
+ rules: [{ required: true }],
+ initialValue: 'EXACTLY_ONCE',
+ isPro: true,
+ props: values => ({
+ disabled: [110, 130].includes(values?.status),
+ options: [
+ {
+ label: 'EXACTLY_ONCE',
+ value: 'EXACTLY_ONCE',
+ },
+ {
+ label: 'AT_LEAST_ONCE',
+ value: 'AT_LEAST_ONCE',
+ },
+ ],
+ }),
+ })
+ @ColumnDecorator()
+ @I18n('meta.Sinks.Kudu.DataConsistency')
+ dataConsistency: string;
+
+ @FieldDecorator({
+ type: EditableTable,
+ props: values => ({
+ size: 'small',
+ editing: ![110, 130].includes(values?.status),
+ columns: getFieldListColumns(values),
+ }),
+ })
+ sinkFieldList: Record<string, unknown>[];
+
+ @FieldDecorator({
+ type: 'input',
+ tooltip: i18n.t('meta.Sinks.Kudu.PartitionKeyHelper'),
+ rules: [{ required: false }],
+ props: values => ({
+ disabled: [110, 130].includes(values?.status),
+ }),
+ })
+ @ColumnDecorator()
+ @I18n('meta.Sinks.Kudu.PartitionKey')
+ partitionKey: string;
+}
+
+const getFieldListColumns = sinkValues => {
+ return [
+ ...sourceFields,
+ {
+ title: `Kudu ${i18n.t('meta.Sinks.Kudu.FieldName')}`,
+ width: 110,
+ dataIndex: 'fieldName',
+ rules: [
+ { required: true },
+ {
+ pattern: /^[a-zA-Z_][a-zA-Z0-9_]*$/,
+ message: i18n.t('meta.Sinks.Kudu.FieldNameRule'),
+ },
+ ],
+ props: (text, record, idx, isNew) => ({
+ disabled: [110, 130].includes(sinkValues?.status as number) && !isNew,
+ }),
+ },
+ {
+ title: `Kudu ${i18n.t('meta.Sinks.Kudu.FieldType')}`,
+ dataIndex: 'fieldType',
+ width: 130,
+ initialValue: kuduFieldTypes[0].value,
+ type: 'select',
+ rules: [{ required: true }],
+ props: (text, record, idx, isNew) => ({
+ options: kuduFieldTypes,
+ disabled: [110, 130].includes(sinkValues?.status as number) && !isNew,
+ }),
+ },
+ {
+ title: 'Length',
+ dataIndex: 'fieldLength',
+ type: 'inputnumber',
+ props: {
+ min: 0,
+ },
+ initialValue: 1,
+ rules: [{ type: 'number', required: true }],
+ visible: (text, record) => record.fieldType === 'fixed',
+ },
+ {
+ title: 'Precision',
+ dataIndex: 'fieldPrecision',
+ type: 'inputnumber',
+ props: {
+ min: 0,
+ },
+ initialValue: 1,
+ rules: [{ type: 'number', required: true }],
+ visible: (text, record) => record.fieldType === 'decimal',
+ },
+ {
+ title: 'Scale',
+ dataIndex: 'fieldScale',
+ type: 'inputnumber',
+ props: {
+ min: 0,
+ },
+ initialValue: 1,
+ rules: [{ type: 'number', required: true }],
+ visible: (text, record) => record.fieldType === 'decimal',
+ },
+ {
+ title: i18n.t('meta.Sinks.Kudu.FieldDescription'),
+ dataIndex: 'fieldComment',
+ },
+ ];
+};
diff --git a/inlong-dashboard/src/metas/sinks/defaults/index.ts
b/inlong-dashboard/src/metas/sinks/defaults/index.ts
index cb83240d4..fac78d633 100644
--- a/inlong-dashboard/src/metas/sinks/defaults/index.ts
+++ b/inlong-dashboard/src/metas/sinks/defaults/index.ts
@@ -106,4 +106,9 @@ export const allDefaultSinks:
MetaExportWithBackendList<SinkMetaType> = [
value: 'REDIS',
LoadEntity: () => import('./Redis'),
},
+ {
+ label: 'Kudu',
+ value: 'KUDU',
+ LoadEntity: () => import('./Kudu'),
+ },
];