我刚刚开始使用Airflow来协调我们的ETL管道。
运行dag时遇到管道错误。
我已经看到了关于堆栈溢出的一般讨论here。
我的情况更多是在气流方面。根据该帖子中的讨论,可能的根本原因是:
如果您的请求被阻止或 花费的时间太长,在请求方超时后,它将关闭 连接,然后当响应端(服务器)尝试写入 套接字,它将引发管道损坏错误。
在我的情况下,这可能是真正的原因,我有一个pythonoperator将在Airflow之外启动另一项工作,而该工作可能会非常漫长(即10个小时以上),我想知道其中的机制是什么我可以利用它来防止这种错误的气流。
有人可以帮忙吗?
UPDATE1 20190303-1:
感谢@ y2k-shubham的SSHOperator,我能够使用它成功建立SSH连接,并且能够在远程站点上运行一些简单的命令(实际上,默认的ssh连接必须设置为localhost)因为该作业位于本地主机上),并且能够看到hostname
,pwd
的正确结果。
但是,当我尝试运行实际作业时,我再次收到相同的错误,该错误是来自jpipeline ob而不是Airflow dag / task。
UPDATE2:20190303-2
我成功运行了一次(气流测试),没有错误,然后又进行了另一个失败运行(调度程序),但管道出现了同样的错误。
答案 0 :(得分:0)
虽然我建议您继续寻找一种优美的方式来尝试实现自己想要的目标,但我还是根据要求提供了
首先,您必须创建一个SSHHook
。这可以通过两种方式完成
从实例化挂钩的客户端代码提供所有必需设置(如主机,用户,密码(如果需要)等)的常规方法。我在此引用test_ssh_hook.py
的示例,但您必须彻底检查SSHHook
及其测试,以了解所有可能的用法
ssh_hook = SSHHook(remote_host="remote_host", port="port", username="username", timeout=10, key_file="fake.file")
在Airflow
way中,您将所有连接详细信息放在Connection
对象中,该对象可以从UI进行管理,并且仅传递conn_id
来实例化钩子
ssh_hook = SSHHook(ssh_conn_id="my_ssh_conn_id")
当然,如果您依靠SSHOperator
,则可以直接将ssh_conn_id
传递给运算符。
ssh_operator = SSHOperator(ssh_conn_id="my_ssh_conn_id")
现在,如果您打算要有一个专用任务来在SSH
上运行命令,则可以使用SSHOperator
。再次引用test_ssh_operator.py
中的示例,但请仔细阅读源代码以获得更好的图片。
task = SSHOperator(task_id="test", command="echo -n airflow", dag=self.dag, timeout=10, ssh_conn_id="ssh_default")
但是随后,您可能希望通过SSH运行命令,这是您的更大任务的一部分。在这种情况下,您不希望使用SSHOperator
,您仍然可以只使用SSHHook
。 SSHHook
的{{3}}方法为您提供get_conn()
的实例。这样,您可以使用paramiko
SSHClient
调用来运行命令
my_command = "echo airflow" stdin, stdout, stderr = ssh_client.exec_command( command=my_command, get_pty=my_command.startswith("sudo"), timeout=10)
如果您查看SSHOperator
的{{3}}方法,它是一段相当复杂(但功能强大)的代码,试图实现非常简单的事情。对于我自己的用途,我创建了一些exec_command()
,您可能想看看
SSHHook
使用SSHOperator
,请查看ssh_utils.py
execute()
实现相同的操作),请参见MultiCmdSSHOperator