DolphinScheduler二次开发

【Dolphinscheduler3.1.1】二次开发本地启动项目(前端+后端) Dolphinscheduler二次开发本地启动项目步骤 阅读详情

官方网站:https://dolphinscheduler.apache.org/zh-cn

改动的功能:

1、新增一个task类型

  1. 找到TaskType.java文件,新增一个任务类型
    /*
     * 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.
     */
    package com.grgbanking.ds.datazone.common.enums;
    
    import com.baomidou.mybatisplus.annotation.EnumValue;
    
    /**
     * task node type
     */
    public enum TaskType {
        /**
         * 0 SHELL
         * 1 SQL
         * 2 SUB_PROCESS
         * 3 PROCEDURE
         * 4 MR
         * 5 SPARK
         * 6 PYTHON
         * 7 DEPENDENT
         * 8 FLINK
         * 9 HTTP
         * 10 DATAX
         * 11 CONDITIONS
         * 12 SQOOP
         * 13 SYNC(新增的)
         */
        SHELL(0, "shell"),
        SQL(1, "sql"),
        SUB_PROCESS(2, "sub_process"),
        PROCEDURE(3, "procedure"),
        MR(4, "mr"),
        SPARK(5, "spark"),
        PYTHON(6, "python"),
        DEPENDENT(7, "dependent"),
        FLINK(8, "flink"),
        HTTP(9, "http"),
        DATAX(10, "datax"),
        CONDITIONS(11, "conditions"),
        SQOOP(12, "sqoop"),
        SYNC(13, "sync");
    
        TaskType(int code, String descp){
            this.code = code;
            this.descp = descp;
        }
    
        @EnumValue
        private final int code;
        private final String descp;
    
        public static boolean typeIsNormalTask(String typeName) {
            TaskType taskType = TaskType.valueOf(typeName);
            return !(taskType == TaskType.SUB_PROCESS || taskType == TaskType.DEPENDENT);
        }
    
        public int getCode() {
            return code;
        }
    
        public String getDescp() {
            return descp;
        }
    }
    
  2. 定义你的参数类,用于json解析参数
    /*
     * 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.
     */
    package com.grgbanking.ds.datazone.common.task.sync;
    
    
    import com.grgbanking.ds.datazone.common.process.ResourceInfo;
    import com.grgbanking.ds.datazone.common.task.AbstractParameters;
    
    import java.util.ArrayList;
    import java.util.List;
    import java.util.Map;
    
    /**
     * 数据同步参数
     */
    @Data
    public class SyncParameters extends AbstractParameters {
    
        /**
         * 源数据host
         */
        private String sourceHost;
    
        /**
         * 源数据port
         */
        private String sourcePort;
    
        /**
         * 源数据类型
         */
        private String sourceType;
    
        /**
         * 源数据库
         */
        private String sourceDatabase;
    
        /**
         * 源数据schema
         */
        private String sourceSchema;
    
        /**
         * 源数据用户
         */
        private String sourceUser;
    
        /**
         * 源数据密码
         */
        private String sourcePassword;
    
        /**
         * 源数据信息id
         */
        private int sourceId;
    
        /**
         * 目标数据host
         */
        private String targetHost;
    
    
        /**
         * 目标数据port
         */
        private String targetPort;
    
        /**
         * 目标数据类型
         */
        private String targetType;
    
        /**
         * 目标数据库
         */
        private String targetDatabase;
    
        /**
         * 目标数据schema
         */
        private String targetSchema;
    
        /**
         * 目标数据用户
         */
        private String targetUser;
    
        /**
         * 目标数据密码
         */
        private String targetPassword;
    
        /**
         * 目标数据信息id
         */
        private int targetId;
        /**
         * 同步列表
         */
        private List<Map<String, String>> syncList;
    
    
        @Override
        public boolean checkParameters() {
            return syncList != null && !syncList.isEmpty();
        }
    
        @Override
        public List<ResourceInfo> getResourceFilesList() {
            return new ArrayList<>();
        }
    }
    

  3.  在 AbstractTask.java下新增类型
  4. 在worker文件夹下,找到task目录,新增sync文件夹,然后新建SyncTask.java
  5.  SyncTask.java如下,可作为参考
package com.grgbanking.ds.datazone.server.worker.task.sync;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import com.grgbanking.ds.datazone.common.Constants;
import com.grgbanking.ds.datazone.common.task.AbstractParameters;
import com.grgbanking.ds.datazone.common.task.sync.SyncParameters;
import com.grgbanking.ds.datazone.common.utils.JSONUtils;
import com.grgbanking.ds.datazone.server.entity.TaskExecutionContext;
import com.grgbanking.ds.datazone.server.worker.config.WorkerConfig;
import com.grgbanking.ds.datazone.server.worker.task.AbstractTask;
import com.grgbanking.ds.datazone.service.bean.SpringApplicationContext;
import org.apache.commons.lang.StringUtils;
import org.slf4j.Logger;
import org.springframework.http.HttpHeaders;
import org.springframework.http.MediaType;
import org.springframework.http.ResponseEntity;
import org.springframework.web.client.HttpClientErrorException;
import org.springframework.web.client.ResourceAccessException;
import org.springframework.web.client.RestTemplate;


public class SyncTask extends AbstractTask {

    /**
     * 数据同步参数
     */
    private SyncParameters syncParameters;

    /**
     * taskExecutionContext
     */
    private TaskExecutionContext taskExecutionContext;

    /**
     *  worker config
     */
    private final WorkerConfig workerConfig;

    /**
     * constructor
     *
     * @param taskExecutionContext taskExecutionContext
     * @param logger               logger
     */
    protected SyncTask(TaskExecutionContext taskExecutionContext, Logger logger) {
        super(taskExecutionContext, logger);

        this.taskExecutionContext = taskExecutionContext;
        this.workerConfig = SpringApplicationContext.getBean(WorkerConfig.class);
    }


    @Override
    public void init() {

        logger.info("sync task params {}", taskExecutionContext.getTaskParams());
        this.syncParameters = JSONUtils.parseObject(taskExecutionContext.getTaskParams(), SyncParameters.class);

        if (!syncParameters.checkParameters()) {
            throw new RuntimeException("sync task params is not valid");
        }
    }

    @Override
    public void handle() throws Exception {

        String threadLoggerInfoName = String.format(Constants.TASK_LOG_INFO_FORMAT, taskExecutionContext.getTaskAppId());
        Thread.currentThread().setName(threadLoggerInfoName);

        try{
            RestTemplate restTemplate = new RestTemplate();
            //创建请求头
            HttpHeaders headers = new HttpHeaders();
            headers.setContentType(MediaType.APPLICATION_JSON);
            headers.add("API_KEY", workerConfig.getApiKey());
            headers.add("API_SECRET", workerConfig.getApiSecret());
            int migrateTaskId = createTask(restTemplate);
            if(migrateTaskId == -1){
                setExitStatusCode(-1);
                throw new Exception("与数据同步服务器通讯失败");
            }

            long startTime = System.currentTimeMillis();
            while(true){

                int taskStatus = queryTask(restTemplate, migrateTaskId);
                //假设2为完成状态
                if(taskStatus == 2){
                    break;
                }
                if(System.currentTimeMillis() - startTime >= 3 * 60 * 1000){
                    exitStatusCode = -1;
                    throw new Exception("查询任务状态信息超时");
                }
                Thread.sleep(3000);
            }
            JSONObject logResult = queryLogMsg(restTemplate, migrateTaskId);
            setExitStatusCode(Constants.EXIT_CODE_SUCCESS);
            //处理日志信息
            //...
        } catch (Exception e){
            exitStatusCode = -1;
            throw e;
        }
    }

    @Override
    public AbstractParameters getParameters() {
        return syncParameters;
    }

    private int createTask(RestTemplate restTemplate){
        //返回创建的任务ID,用于查询任务状态信息
        JSONObject json=new JSONObject();
        json.put("destDetails",syncParameters.getTargetUrl());
        json.put("sourceDetails",syncParameters.getSourceUrl());
        try {
            String requestUrl = workerConfig.getApiUrl() + "/MigrateTask";
            ResponseEntity<String> responseEntity = restTemplate.postForEntity(requestUrl, json, String.class);
            String resultStr = responseEntity.getBody();
            JSONObject result = JSON.parseObject(resultStr, JSONObject.class);
            if(result.getBoolean("success")!=true){
                logger.error("服务通讯反馈的信息:{}", resultStr);
            }
            return result.getInteger("data");

        } catch (ResourceAccessException e) {
            logger.error(e.getMessage(), e);
            return -1;
        } catch (HttpClientErrorException e) {
            logger.error("调用异常", e);
            if (StringUtils.contains(e.getMessage(), "404")) {
                return -1;
            }
            return -1;
        } catch (Exception e) {
            logger.error(e.getMessage());
            return -1;
        }
    }

    private int queryTask(RestTemplate restTemplate, int migrateTaskId){
        try {
            String requestUrl = workerConfig.getApiUrl() + "/MigrateTask/" + migrateTaskId;
            ResponseEntity<String> responseEntity = restTemplate.getForEntity(requestUrl, String.class);
            String resultStr = responseEntity.getBody();
            JSONObject result = JSON.parseObject(resultStr, JSONObject.class);
            if(result.getBoolean("success")!=true){
                logger.error("服务通讯反馈的信息:{}", resultStr);
            }
//            return result.getInteger("data");
            return 2;

        } catch (ResourceAccessException e) {
            logger.error(e.getMessage(), e);
            return -1;
        } catch (HttpClientErrorException e) {
            logger.error("调用异常", e);
            if (StringUtils.contains(e.getMessage(), "404")) {
                return -1;
            }
            return -1;
        } catch (Exception e) {
            logger.error(e.getMessage());
            return -1;
        }
    }

    private JSONObject queryLogMsg(RestTemplate restTemplate, int migrateTaskId){
        try {
            String requestUrl = workerConfig.getApiUrl() + "/MigrateTask/log/" + migrateTaskId;
            ResponseEntity<String> responseEntity = restTemplate.getForEntity(requestUrl, String.class);
            String resultStr = responseEntity.getBody();
            JSONObject result = JSON.parseObject(resultStr, JSONObject.class);
            if(result.getBoolean("success")!=true){
                logger.error("服务通讯反馈的信息:{}", resultStr);
            }
//            return result.getInteger("data");
            return result;

        } catch (ResourceAccessException e) {
            logger.error(e.getMessage(), e);
            throw e;
        } catch (HttpClientErrorException e) {
            logger.error("调用异常", e);
            if (StringUtils.contains(e.getMessage(), "404")) {
                throw new RuntimeException("404");
            }
            throw e;
        } catch (Exception e) {
            logger.error(e.getMessage());
            throw e;
        }
    }
}

 6. 找到TaskManager.java,在里面新增任务类型

2、登录授权修改,整合第三方认证中心

3、API整合nacos实现声明式服务调用

4、集成Python3 Python DataX的基础镜像

DockerFile:

FROM openjdk:8-jre-slim-buster

# 1. install command/library/software
# If install slowly, you can replcae debian's mirror with new mirror, Example:
RUN { \
 echo "deb http://mirrors.tuna.tsinghua.edu.cn/debian/ buster main contrib non-free"; \
 echo "deb http://mirrors.tuna.tsinghua.edu.cn/debian/ buster-updates main contrib non-free"; \
 echo "deb http://mirrors.tuna.tsinghua.edu.cn/debian/ buster-backports main contrib non-free"; \
 echo "deb http://mirrors.tuna.tsinghua.edu.cn/debian-security buster/updates main contrib non-free"; \
} > /etc/apt/sources.list

RUN apt-get update && \
    apt-get install -y --no-install-recommends tzdata dos2unix python3 python supervisor procps psmisc netcat sudo tini curl iputils-ping wget && \
    echo "Asia/Shanghai" > /etc/timezone && \
    rm -f /etc/localtime && \
    dpkg-reconfigure tzdata && \
    rm -rf /var/lib/apt/lists/* /tmp/* && \
    wget http://datax-opensource.oss-cn-hangzhou.aliyuncs.com/datax.tar.gz && \
    mkdir /opt/soft && \
    tar -zxvf datax.tar.gz -C /opt/soft && \
    rm -rf datax.tar.gz && \
    rm -rf /opt/soft/datax/plugin/writer/._* && \
    rm -rf /opt/soft/datax/plugin/reader/._*

制作完这个基础镜像,然后原先的openjdk:8-jre-slim-buster基础镜像改成你自定义的镜像。

5、统一数据源中心,新建嵌入Feign远程调用数据源中心保持强一致性,定时同步实现最终一致性。

遇到的坑:

1、master 读取配置文件失败导致启动失败

2、集成DataX遇到的坑

datax执行自测脚本异常:

2022-02-18 09:04:50.468 [main] WARN  ConfigParser - 插件[streamreader,streamwriter]加载失败,1s后重试... Exception:Code:[Common-00], Describe:[您提供的配置文件存在错误信息,请检查您的作业配置 .] - 配置信息错误,您提供的配置文件[/Users/chenweifeng/Downloads/datax/plugin/reader/.DS_Store/plugin.json]不存在. 请检查您的配置文件. 
2022-02-18 09:04:51.486 [main] ERROR Engine - 

经DataX智能分析,该任务最可能的错误原因是:
com.alibaba.datax.common.exception.DataXException: Code:[Common-00], Describe:[您提供的配置文件存在错误信息,请检查您的作业配置 .] - 配置信息错误,您提供的配置文件[/Users/chenweifeng/Downloads/datax/plugin/reader/.DS_Store/plugin.json]不存在. 请检查您的配置文件.
	at com.alibaba.datax.common.exception.DataXException.asDataXException(DataXException.java:26)
	at com.alibaba.datax.common.util.Configuration.from(Configuration.java:95)
	at com.alibaba.datax.core.util.ConfigParser.parseOnePluginConfig(ConfigParser.java:153)
	at com.alibaba.datax.core.util.ConfigParser.parsePluginConfig(ConfigParser.java:125)
	at com.alibaba.datax.core.util.ConfigParser.parse(ConfigParser.java:63)
	at com.alibaba.datax.core.Engine.entry(Engine.java:137)
	at com.alibaba.datax.core.Engine.main(Engine.java:204)

网上查了之后的说法是

然后我就按照操作:

rm -rf ./plugin/reader/._*

rm -rf ./plugin/writer/._*

然后就成功了

3、K8s环境下部署,滚动部署时,master、worker采用k8s域名注册失败;

数据质量的实践参考博客:https://huaweicloud.youkuaiyun.com/63356f17d3efff3090b56c6f.html?spm=1001.2101.3001.6661.1&utm_medium=distribute.pc_relevant_t0.none-task-blog-2~default~CTRLIST~activity-1-119951778-blog-127520960.235^v35^pc_relevant_increate_t0_download_v2&depth_1-utm_source=distribute.pc_relevant_t0.none-task-blog-2~default~CTRLIST~activity-1-119951778-blog-127520960.235^v35^pc_relevant_increate_t0_download_v2&utm_relevant_index=1

数仓工具——DolphinScheduler任务调度工具 数仓学习——DolphinScheduler任务调度工具前言一、DolphinScheduler简介1.DolphinScheduler概述2.DolphinScheduler组件3.DolphinScheduler核心架构二、DolphinScheduler部署说明1.软硬件环境要求1.1 操作系统版本要求1.2 服务器硬件要求2.部署模式2.1单机模式2.2 伪集群模式2.3 集群模式三、DolphinScheduler集群模式部署1.集群规划2.前置准备工作3.解压DolphinScheduler安装 阅读详情

相关推荐

dolphinscheduler节点二次开发需要改动的部分

修改文件给TASK_TYPES_MAP增加新节点的映射信息,如下修改完成之后,新节点的名字就会在dolphin组件的侧边栏显示出来啦。修改文件.draggable.icon-修改完成之后,新节点的logo就会在dolphin组件的侧边栏显示出来啦。在目录下新增节点字段的ts文件如下所示:期间需要新增国际化文件中的字段信息。在目录下新增节点字段的ts文件ps: 这里存在不容易察觉到的细节,尤其注意。这个地方一定要跟着改,不然页面上显示的字段,还是之前复制的那个节点的字段。修改文件。

weixin_41249051的博客 2275

dolphinscheduler 二次开发 问题记录

Apache DolphinScheduler 是一个分布式易扩展的可视化DAG工作流任务调度开源系统。适用于企业级场景,提供了一个可视化操作任务、工作流和全生命周期数据处理过程的解决方案。Apache DolphinScheduler 旨在解决复杂的大数据任务依赖关系,并为应用程序提供数据和各种 OPS 编排中的关系。解决数据研发ETL依赖错综复杂,无法监控任务健康状态的问题。

huangweicheng123的博客 3692

DolphinScheduler3.1.9二次开发环境配置

为了避免版本冲突,打开 dolphinscheduler-ui 模块的 package.json 文件,去除所有 ^ 符号。

qq_42838399的博客 1507

DolphinScheduler分布式调度系统二开 - 编译、打包、部署

初始化脚步路径: ./dolphinscheduler/dolphinscheduler-dao/src/main/resources/sql。数据库链接后增加 useSSL=false。提示MySQL链接不上。

qq_28036249的博客 6068

DolphinScheduler 二次开发实战:从环境搭建到核心问题规避

本文详细介绍了DolphinScheduler二次开发的全流程,从环境搭建、源码获取与初始化、配置文件调整到项目启动与调试技巧,再到打包避坑指南和核心问题解决。特别针对dolphinscheduler二次开发中的常见问题提供了实用解决方案,帮助开发者高效完成定制开发任务。

weixin_28730131的博客 362

DolphinScheduler3.1.9二次开发环境配置实战指南

本文详细介绍了DolphinScheduler3.1.9二次开发环境配置的完整流程,包括JDK、Maven、Node.js等必备软件的版本选择与安装,项目初始化与配置,数据库设置,核心服务配置以及前后端工程的启动技巧。通过实战指南帮助开发者快速搭建开发环境,避免常见问题,提升开发效率。

weixin_33701251的博客 319

Dolphinscheduler二次开发支持DataX的自定义参数传递实现数据UPSET

dolphinscheduler二次开发适配DataX的自定义参数传递

weixin_42890062的博客 2638

二次开发必看!DolphinScheduler 3.1.9 开发环境搭建指南

本文结合真实案例,详细介绍 DolphinScheduler 3.1.9 的二次开发环境配置流程,希望为有定制化开发需求的用户提供实用、可靠的参考。

Apache DolphinScheduler开源社区 986

【Dolphinscheduler3.1.1】从零搭建二次开发环境:前后端联调实战指南

本文详细介绍了如何从零搭建Dolphinscheduler3.1.1的二次开发环境,包括前后端联调的实战指南。内容涵盖环境准备、源码获取、数据库配置、前后端联调全流程及常见问题排查,帮助开发者快速掌握本地启动和二次开发技巧。

weixin_30825581的博客 403

DolphinScheduler3.1.9二次开发环境搭建避坑指南:从JDK到ZooKeeper的完整配置流程

本文详细介绍了DolphinScheduler 3.1.9二次开发环境搭建的全流程,从JDK、Maven、Node.js等基础环境配置到ZooKeeper、MySQL等关键组件的安装与调试,提供了完整的避坑指南。特别针对版本兼容性、IDE配置、服务启动顺序等常见问题给出解决方案,帮助开发者快速搭建稳定的开发环境。

weixin_28837817的博客 237

如何用IntelliJ IDEA高效调试DolphinScheduler3.1.9二次开发?MySQL与PostgreSQL配置全解析

本文详细解析了如何使用IntelliJ IDEA高效调试DolphinScheduler3.1.9的二次开发环境,包括MySQL与PostgreSQL的配置全流程。从工具链版本锁定、数据库选型到分布式组件调试技巧,提供了一系列实战解决方案,帮助开发者快速搭建和优化开发环境,提升二次开发效率。

weixin_42635064的博客 353

【Meetup回顾】Apache DolphinScheduler在联通的实践和二次开发经验分享

在由 openLooKeng 社区主办,Apahce DolphinScheduler社区、Apache Pulsar 社区、示说网协办的联合 Meetup 上,来自联通数字科技的王兴杰老...

Apache DolphinScheduler开源社区 2072

C#教程

C# 教程 C# 是一个简单的、现代的、通用的、面向对象的编程语言,它是由微软(Microsoft)开发的。 本教程将告诉您基础的 C# 编程,同时将向您讲解 C# 编程语言相关的各种先进理念。 现在开始学习 C#! C# 在线工具 谁适合阅读本教程? 本教程有助于初学者理解基础的 C# 编程。在学习完本教程后,您将到达一个中级的 C# 编程水平。

zm1_1zm 1万+

最佳实践 | 联通数科基于 DolphinScheduler 的二次开发

点击上方蓝字关注我们✎编 者 按 数据时代下,井喷的数据量为电信行业带来新的挑战。面对每日数百 TB 的新增数据,稳定可靠的调度系统必不可少。中国联通旗下的联通数字科技有限公司(以下...

Apache DolphinScheduler开源社区 2144

《机器人学一(Robotics(1))》_台大林沛群 第 3 周 【机械手臂 顺运动学】Quiz 3

的方向,旋转方向与四指弯曲方向相反,为负, α为 -90。的方向,旋转方向与四指弯曲方向相反,为负, α为 -90。bug 的图 要求解的 i 位置有误 两套 题目?B. 第2个 坐标系 的原点位置 不便于 计算;上面的正确,后两题 有误, 不知道问题在哪里。标准部分, 前面的更常用,这种仅作为 了解。还是计算过程中保留两位有效数字 不符合。2、确定 旋转角 α 正负的右手定则。1、确定坐标系方向的右手定则。可相交,距离为 0。A: 右手拇指指向。小数点后两位,不符合。

weixin_46034116的博客 1243

数学建模 种群竞争模型 学习笔记

模型背景 应用场景 种群竞争模型 例如 s1=0.5,则表示对于供养甲的资源来讲,单位数量的乙的消耗为单位数量的甲的0.5倍,即表示乙对于该资源的占有能力是甲的0.5倍(即竞争力弱) 仿真结果及分析 (1)设置自然增长率 r1=r2=1 (2)改变自然增长率 r1=r2=0.3 (3)修改甲和乙的最大容量 n1=10000, n2=100 (4)修改甲和乙的初始数量 x1=10, x...

Test_tju的博客 2028

dolphinscheduler核心流程

概况 ​ 因为最近公司,要计划做数据中台,而我们要负责做一个 数据开发这一部分,主要功能是将数据加工,因为产品要加入一些业务上定制化的东西,所以目前是将dolphinscheduler进行一个二次开发。下面我会分享dolphinscheduler的整体架构,和一个核心流程。 下面主要会分为三部分: 1 主要架构 2 代码结构 3 任务执行过程的核心流程 版本: Dolphinscheduler-1.3.8-release 主要架构 上图是从官网直接copy过来,是ds的架构图,ds的架构我觉得主要的

weixin_39639119的博客 1105

【mip-NeRF】使用一组二维图像渲染3D场景视频(mip-NeRF论文复现)

本文对mip-NeRF模型的pytorch实现进行了复现

Ryan2k的博客 1848

跨境电商背景下,DolphinScheduler 在 SHEIN 的二开实践

分享嘉宾:董文彬编辑整理:低代码无代码平台Treelab 张德通SHEIN是一家中国跨境电商巨头公司,也是一家估值千亿的美金独角兽企业。本次分享由SHEIN架构部资深后端开发工程师董文彬介绍海豚调度器 Apache DolphinScheduler(以下简称DS)在SHEIN的使用和二次开发实践。“本次分享将介绍以下四部分内容:SHEIN选择DS的背景和使用DS的实际效果...

Apache DolphinScheduler开源社区 2207

IAR调试CC1310的错误:Fatal error:Failed to connect to the XDS emlulator (Error -241 @ 0x0:)

从simplelink_cc13x0_sdk_2_10_00_36导入collector工程后,rebuild后进行debug,出现了如图错误:Fatal error:Failed to connect to the XDS emlulator (connect ICEPick)...(Error -241 @ 0x0)A router subpath could not be accessed....

qq_40417648的博客 6228

02.1 知识图谱工具 Protege的下载安装与使用

Protege的下载安装与使用 本文是王昊奋老师《知识图谱》系列笔记第2.1篇。 文章目录Protege的下载安装与使用0 相关介绍0.0 Protege相关介绍0.1 Protégé的特点0.2 Protégé的用途1 Protege的下载1.1 准备工作:安装配置JAVA环境1.2 官网下载2 Protege的安装2.1 直接解压缩2.2 双击运行3 Protege的使用实例-创建类...

和而不流 7万+
上一篇: 《面试题》2、Java基础框架
下一篇: Docker基于Centos7.4创建python2、python3、jdk1.8环境并保存镜像,运行容器
CarsonBigData
博客等级 码龄9年 8316粉丝 166原创
评论 21
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值