一、实验环境
Hadoop分布式集群环境
Spark 3
IDEA
二、实验内容
实验中使用Socket来模拟用户浏览商品产生实时数据,数据包括用户当前浏览的商品以及浏览商品的次数和停留时间和是否收藏该商品。使用Spark Streaming构建实时数据处理系统,来计算当前电商平台最受人们关注的商品是哪些。实验可分为以下几个步骤:
1.Socket模拟用户浏览商品产生实时数据
package org.apache.spark;
import java.io.IOException;
import java.io.OutputStream;
import java.io.PrintWriter;
import java.net.ServerSocket;
import java.net.Socket;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.Random;
public class SimulatorSocket {
public static void main(String[] args) throws Exception {
new Thread(new SimulatorSocketLog()).start();
}
}
class SimulatorSocketLog implements Runnable{
//假设一共有100个商品
private int GOODSID = 100;
//随机发送消息的条数
private int MSG_NUM = 30;
//假设用户浏览该商品的次数
private int BROWSE_NUM = 5;
//假设用户浏览商品停留的时间
private int STAY_TIME = 10;
int[] COLLECTION = new int[]{-1,0,1};
private int[] BUY_NUM = new int[]{0,1,0,2,0,0,0,1,0};
public void run() {
// TODO Auto-generated method stub
Random r = new Random();
try {
ServerSocket sScoket = new ServerSocket(9999);
System.out.println("successfully start stimulator data block,run Streaming!");
while(true){
int msgNum = r.nextInt(MSG_NUM)+1;
Socket socket = sScoket.accept();
OutputStream os = socket.getOutputStream();
PrintWriter pw = new PrintWriter(os);
for (int i = 0; i < msgNum; i++) {
StringBuffer sb = new StringBuffer();
sb.append("goodsID-"+(r.nextInt(GOODSID)+1));
sb.append("::");
sb.append(r.nextInt(BROWSE_NUM)+1);
sb.append("::");
sb.append(r.nextInt(STAY_TIME)+r.nextFloat());
sb.append("::");
sb.append(COLLECTION[r.nextInt(2)]);
sb.append("::");
sb.append(BUY_NUM[r.nextInt(9)]);
sb.append("::");
// SimpleDateFormat df = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
// sb.append(df.format(new Date()));
System.out.println(sb.toString());
pw.write(sb.toString()+"\n");
}
pw.flush();
pw.close();
try {
Thread.sleep(5000);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
System.out.println("thread sleep failed");
}
}
} catch (IOException e) {
// TODO Auto-generated catch block
System.out.println("port used");
}
}
}
注:此处代码非原创,来源于网络
2.使用Spark Streaming构建实时数据处理系统
• 数据处理:商品关注度怎么计算呢,浏览次数和浏览时间以及购买力度和是否收藏该商品都有一个权重,可能不同的公司觉得不同的选项权重不一样,可能你觉得浏览时间更重要,另一人觉得浏览次数更重要,所以应该事先约定好这个计算公式。我们约定浏览次数的权重为0.8,浏览时间权重为0.6,是否收藏和购买力度都为1。
• 更新关注度值:由于是流式数据,数据每分每秒都在产生,那么计算的关注值也在变化,那么就需要更新这个状态值。结果输出,并将里面的商品进行关注度排序,降序排序。
#!/usr/bin/env python3
from __future__ import print_function
from pyspark import SparkConf, SparkContext
from pyspark.streaming import StreamingContext
conf = SparkConf().setMaster("local[2]").setAppName("NetworkWordCount")
sc = SparkContext(conf=conf)
ssc = StreamingContext(sc, 5)
lines = ssc.socketTextStream("localhost", 9999)
counts = lines.map(lambda line: line.split("::")) \
.map(lambda word: (word[0], float(word[1])*0.8+float(word[2])*0.6+float(word[3])+float(word[4]))) \
.reduceByKey(lambda a, b: a+b) \
.transform(lambda line: line.map(lambda x: (x[1], x[0])).sortByKey(False).map(lambda x: (x[1], x[0])))
# counts.saveAsTextFiles("file:///mycode/output") #存储到虚拟机本地
counts.transform(lambda lines: lines.saveAsTextFile("hdfs://192.168.126.100:8020/spgzd")) #存储到HDFS
counts.pprint()
ssc.start()
ssc.awaitTermination()
需要注意的地方:由于Dstream没有sortByKey操作,所以排序用transform自定义函数实现。
3.商品关注度分析实现过程
(1)将idea的jar包和py文件导入Linux终端中
(2)启动HDFS以及spark
#启动spark
/export/servers/spark-2.2.0/sbin/start-all.sh
#启动hadoop
start-yarn.sh
start-dfs.sh
使用jps查看节点是否启动成功:
(3)启动Socket服务器端产生数据源
/export/servers/spark-2.2.0/bin/spark-submit --master spark://192.168.126.100:7077 untitled.jar
(4)启动客户端进行数据处理
/export/servers/spark-2.2.0/bin/spark-submit GoodsFX.py localhost 9999
客户端从Socket服务器端接收数据后,执行对商品关注度的计算,然后输出如下所示:
(5)数据展示
在hdfs端生成了商品关注度的数据,查看生成文件如下图所示