【问题标题】:Insert data into mysql using dataflow使用数据流将数据插入mysql
【发布时间】:2020-03-02 09:03:00
【问题描述】:

以下代码构建管道并生成 DAG。 RuntimeError: NotImplementedError [while running 'generatedPtransform-438'] 请告诉我在 python 中是否有任何直接连接 mysql 的连接器。

from apache_beam.options.pipeline_options import PipelineOptions
from google.cloud import pubsub_v1
from google.cloud import bigquery
import  mysql.connector
import apache_beam as beam
import logging
import argparse
import sys
import re


PROJECT="12344"
TOPIC = "projects/12344/topics/mytopic"    

class insertfn(beam.Dofn):
def insertdata(self,data):
db_conn=mysql.connector.connect(host="localhost",user="abc",passwd="root",database="new")
db_cursor=db_conn.cursor()
emp_sql = " INSERT INTO emp(ename,eid,dept) VALUES (%s,%s,%s)"
db_cusror.executemany(emp_sql,(data[0],data[1],data[2]))
db_conn.commit()
print(db_cursor.rowcount,"record inserted")
class Split(beam.DoFn):
def process(self, data):
data = data.split(",")               
return [{ 
'ename': data[0],
'eid': data[1],
'dept': data[2]         
}]

def main(argv=None):

parser = argparse.ArgumentParser()
parser.add_argument("--input_topic")
parser.add_argument("--output")
known_args = parser.parse_known_args(argv)


p = beam.Pipeline(options=PipelineOptions())

(p
| 'ReadData' >> beam.io.ReadFromPubSub(topic=TOPIC).with_output_types(bytes)
| "Decode" >> beam.Map(lambda x: x.decode('utf-8'))
| 'ParseCSV' >> beam.ParDo(Split())
| 'WriteToMySQL' >> beam.ParDo(insertfn())
)
result = p.run()
result.wait_until_finish()

【问题讨论】:

  • 您收到的错误信息是什么?
  • 我正在检查您的代码。由于您是 Apache Beam 编程的新手,我建议您查看这个由 Google 创建的 Python DataFlow 代码存储库,link。另一件事,您是否以与 insertfn() 相同的方式定义您的 Split() 过程?
  • 您能告诉我您正在使用的 Apache Beam 版本吗?另外,你提到上面的代码运行,你的意思是你的 MySQL 是在 prem 上的吗?你能告诉我你用来运行管道的命令吗?
  • @AlexandreMoraes 我使用 apache beam 2.19.0。运行管道的命令是 python -m npipe --input_topic "projects/myprojectid1/topics/mytopic" --streaming 我不在 prem mysql 上使用,我编写了单独的 python 文件只是为了将一些随机硬编码值插入云 mysql 并且它工作,所以我怀疑问题是管道代码连接到 mysql 实例的位置。请让我知道你的想法
  • 在发布问题时添加其他信息。

标签: python mysql google-cloud-platform google-cloud-dataflow apache-beam


【解决方案1】:

在我们在评论部分进行讨论后,我注意到您没有使用正确的命令来执行 DataFlow 管道。

根据documentation,必须定义强制标志才能在Dataflow Managed Service 中运行管道。这些标志描述如下:

  • job_name -正在执行的 Dataflow 作业的名称。

  • 项目 - 您的 Google Cloud 项目的 ID。 runner - 管道

  • runner - 将解析您的程序并构建您的管道。为了 云执行,这一定是DataflowRunner。

  • staging_location - 用于 Dataflow 的 Cloud Storage 路径,用于暂存执行作业的工作人员所需的代码包。

  • temp_location - 用于 Dataflow 的 Cloud Storage 路径,用于暂存管道执行期间创建的临时作业文件。

除了这些标志之外,您还可以使用其他标志,因为您使用的是 PubSub 主题:

  • --input_topic:设置要从中读取消息的输入 Pub/Sub 主题。

因此,运行 Dataflow 管道的示例如下:

  python RunPipelineDataflow.py \
  --job_name=jobName\ 
  --project=$PROJECT_NAME \
  --runner=DataflowRunner \
  --staging_location=gs://YOUR_BUCKET_NAME/AND_STAGING_DIRECTORY\
  --temp_location=gs://$BUCKET_NAME/temp
  --input_topic=projects/$PROJECT_NAME/topics/$TOPIC_NAME \

我想指出使用DataflowRunner 的重要性,它允许您使用 Cloud Dataflow 托管服务,提供完全托管的服务、自动缩放和动态工作再平衡。但是,也可以使用DirectRunner 在您的机器中执行您的管道,它旨在验证管道。

【讨论】:

  • 感谢您提供的信息,这次我能够执行管道。它一直运行到运行状态,然后失败并显示消息“Caused by: java.lang.RuntimeException: Error received from用于指令 -43 的 SDK 工具:”我使用 beam.io.WriteToBigQuery 编辑了相同的代码以写入 bigquery 而不是 mysql,并且它成功了。我看到最近发布了一个 mysql 梁连接器,但我无法使用它。有什么建议吗? pypi.org/project/beam-mysql-connector
  • @anonymous1,能否使用您当前使用的代码编辑您的问题?所以我可以更深入地研究这个问题。
  • @lexandre Moraes 我已根据您的建议进行了编辑。我们是否必须编写自定义转换才能通过梁连接到 mysql
  • @anonymous1,我刚刚看到您在问题中发布了另一个错误。您的代码中的 generatedPtransform 函数在哪里?
  • 是的,现在代码抛出了这个错误。我的代码没有生成 Ptransform 函数。我的问题是我将值插入 mysql 的方法是否正确?
猜你喜欢
  • 1970-01-01
  • 2014-04-17
  • 2015-08-23
  • 1970-01-01
  • 1970-01-01
  • 2015-06-20
  • 2019-11-17
  • 2021-12-31
  • 2014-11-03
相关资源
最近更新 更多