Search code examples
python-3.xapache-sparkpysparkspark-structured-streaming

Convert streaming JSON to DataFrame


Question: How can I convert a JSON string to DataFrame and also selecting only the keys I want?

I just started using Spark last week and I'm still learning so please bear with me.

I'm using Spark(2.4) Structured Streaming. The spark app get data (via socket) from a twitter streaming and data sent is full tweet JSON string. Below is a one of the DataFrames. Each row is the full JSON tweet.

+--------------------+
|               value|
+--------------------+
|{"created_at":"Tu...|
|{"created_at":"Tu...|
|{"created_at":"Tu...|
+--------------------+

As Venkata suggested, I did this, translated to python (full codes below)

schema = StructType().add('created_at', StringType(), False).add('id_str', StringType(), False)
df = lines.selectExpr('CAST(value AS STRING)').select(from_json('value', schema).alias('temp')).select('temp.*')

This is the return value

+------------------------------+-------------------+
|created_at                    |id_str             |
+------------------------------+-------------------+
|Wed Feb 20 04:51:18 +0000 2019|1098082646511443968|
|Wed Feb 20 04:51:18 +0000 2019|1098082646285082630|
|Wed Feb 20 04:51:18 +0000 2019|1098082646444441600|
|Wed Feb 20 04:51:18 +0000 2019|1098082646557642752|
|Wed Feb 20 04:51:18 +0000 2019|1098082646494797824|
|Wed Feb 20 04:51:19 +0000 2019|1098082646817681408|
+------------------------------+-------------------+

As can be seen, only the 2 keys that I wanted was included in the DataFrame.

Hope this would help any newbie.

Full codes

from pyspark.sql import SparkSession
from pyspark.sql.functions import from_json
from pyspark.sql.types import StructType, StringType


spark = SparkSession.builder.appName("StructuredNetworkWordCount").getOrCreate()
sc = spark.sparkContext

lines = spark.readStream.format('socket').option('host', '127.0.0.1').option('port', 9999).load()

schema = StructType().add('created_at', StringType(), False).add('id_str', StringType(), False)
df = lines.selectExpr('CAST(value AS STRING)').select(from_json('value', schema).alias('temp')).select('temp.*')

query = df.writeStream.format('console').option('truncate', 'False').start()

# this part is only used to print out the query when running as an app. Not needed if using jupyter
import time
time.sleep(10)
lines.stop()

Solution

  • Here's a sample code snippet you can use to convert from json to DataFrame.

    val schema = new StructType().add("id", StringType).add("pin",StringType)
    
    val dataFrame= data.
    selectExpr("CAST(value AS STRING)").as[String].
    select(from_json($"value",schema).
    alias("tmp")).
    select("tmp.*")