学生提交材料清单
1.Spark 项目运行结果截图
2.Hive数据库查询截图
3.接口测试截图
4.数据可视化网页截图
5.分别导出Spark项目,前后端项目的Zip(压缩包)
注意:
1.所有截图请统一粘贴到一个 Word 文件中,命名为:
提交截图_姓名_班级.docx;2.最终考生提交内容打包为一个总压缩包,命名格式如下:
张三-大数据高23-1班-大数据实训.rar
一、Hive 环境启动
【题目要求】
启动 Hadoop 分布式文件系统HDFS与 YARN;
启动 Hive Metastore 与 HiveServer2 服务。
# 启动 Hadoop 文件系统
start-dfs.sh
start-yarn.sh
# 启动 Hive 服务
hive --service metastore &
hive --service hiveserver2 &
二、Hive 数据库与数据导入
【题目要求】
创建数据库
salesdb;创建表
salesinfo,包含订单信息与分类字段;从本地路径
/opt/exam_spark/sales_data.csv加载数据;查询前 3 行,验证导入是否成功。
DROP DATABASE IF EXISTS salesdb CASCADE;
CREATE DATABASE IF NOT EXISTS salesdb;
USE salesdb;
CREATE TABLE IF NOT EXISTS salesinfo (
order_id STRING,
customer_id STRING,
product_id STRING,
sale_date DATE,
quantity INT,
unit_price INT,
payment_method STRING,
region STRING,
product_name STRING,
category STRING
)
ROW FORMAT DELIMITED
FIELDS TERMINATED BY ','
STORED AS TEXTFILE
TBLPROPERTIES ("skip.header.line.count"="1");
LOAD DATA LOCAL INPATH '/opt/exam_spark/sales_data.csv' INTO TABLE salesinfo;
SELECT * FROM salesinfo LIMIT 3;
三、Spark SQL 销售信息统计
【题目要求】
创建
Spark项目SparkTask,并导入Pom.xml文件;创建 Scala 类
PaymentAnalysis,路径为:src/main/scala/org/example/PaymentAnalysis.scala使用 Spark SQL 对 Hive 表
salesinfo进行如下分析:统计2023年每种支付方式的订单数量和销售额(数量 × 单价);
按总销售额降序排序;
将结果写入 Hive 表
payment_count_result。
package org.example
import org.apache.spark.sql.SparkSession
object PaymentAnalysis {
def main(args: Array[String]): Unit = {
// 设置 Hadoop 用户名,避免权限问题
System.setProperty("HADOOP_USER_NAME", "root")
// 1. 创建 SparkSession,并启用 Hive 支持
val spark = SparkSession.builder()
.appName("PaymentMethodStat")
.master("local[*]")
.enableHiveSupport()
.getOrCreate()
println("1.SparkSession 初始化成功,Hive 支持开启")
// 2. 切换到目标数据库
spark.sql("USE salesdb")
// 3. 执行 SQL 查询:统计 2024 年各支付方式的订单数量和销售总额
println("2.正在统计 2024 年各支付方式的订单数量与销售额...")
val result = spark.sql(
"""
|SELECT
| payment_method,
| COUNT(*) AS order_count,
| ROUND(SUM(quantity * unit_price) / 10000, 2) AS total_sales
|FROM salesinfo
|WHERE payment_method IS NOT NULL AND year(sale_date) = 2024
|GROUP BY payment_method
|HAVING total_sales IS NOT NULL
|ORDER BY total_sales DESC
|""".stripMargin)
// 4. 展示结果
val count = result.count()
println(s"3.查询完成,共获取到 $count 种支付方式的记录:")
result.show(truncate = false)
// 5. 保存统计结果为 Hive 表(覆盖写入)
println("4.正在将统计结果写入 Hive 表:salesdb.payment_count_result ...")
result.write
.mode("overwrite") // 如表已存在则覆盖
.saveAsTable("salesdb.payment_count_result")
println("5.所有数据成功写入目标表,准备关闭 Spark...")
// 6. 关闭 SparkSession,释放资源
spark.stop()
println("6.程序结束,SparkSession 已关闭。")
}
}
四、Spring Boot 接口开发 + Vue 可视化
4.1 后端接口开发
【题目要求】
创建
Spring Boot项目 ,名称为Backend,并导入Pom.xml文件;创建类
PaymentController,路径为:src/main/java/com/example/backend/controller/PaymentController.java使用 Spring Boot 创建接口
/payment-count,请求方式为GET;在接口中通过 JDBC 查询 Hive 表
payment_count_result;查询字段包括:
payment_method,order_count;将查询结果以 JSON 列表形式返回,每条记录包含上述字段键值对。
package com.example.backend.controller;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RestController;
import java.sql.*;
import java.util.*;
@RestController // 声明为 REST 控制器,返回 JSON 格式数据
public class PaymentController {
@GetMapping("/payment-count") // 设置请求路径为 /payment-count
public List<Map<String, Object>> getPaymentCount() {
List<Map<String, Object>> result = new ArrayList<>(); // 存放查询结果
try {
// 1. 加载 Hive JDBC 驱动
Class.forName("org.apache.hive.jdbc.HiveDriver");
// 2. 连接 HiveServer2(指定地址、数据库、用户名密码)
Connection conn = DriverManager.getConnection(
"jdbc:hive2://master:10000/salesdb", "root", "123456");
// 3. 创建 SQL 执行对象
Statement stmt = conn.createStatement();
// 4. 执行 Hive SQL 查询,读取支付方式与订单数量统计结果表
ResultSet rs = stmt.executeQuery(
"SELECT payment_method, order_count FROM payment_count_result");
// 5. 遍历结果集,将每一行转为 map 对象存入列表
while (rs.next()) {
Map<String, Object> map = new HashMap<>();
map.put("payment_method", rs.getString("payment_method")); // 支付方式
map.put("order_count", rs.getInt("order_count")); // 订单数量
result.add(map);
}
// 6. 关闭资源
rs.close();
stmt.close();
conn.close();
} catch (Exception e) {
e.printStackTrace(); // 出错时打印错误日志
}
// 7. 返回结果列表,自动转换为 JSON
return result;
}
}
4.2 Vue + ECharts 可视化
【题目要求】
创建
VUE项目 ,名称为Frontend;创建组件文件
components/PaymentChart.vue和主页面App.vue,配置代理文件vite.config.js;使用 Vue3 + ECharts 创建柱状图组件;
从接口
/api/payment-count获取数据;展示2024年各支付方式(如微信、支付宝、现金等)对应的订单数量,以柱状图形式可视化展示。
【参考代码】
vite.config.js
// 引入 Vite 的配置函数和 Vue 插件
import { defineConfig } from 'vite'
import vue from '@vitejs/plugin-vue'
// 默认导出配置对象
export default defineConfig({
// 注册插件:使用 Vue 插件支持 .vue 文件
plugins: [vue()],
// 本地开发服务器配置
server: {
port: 5173, // 本地开发服务器端口(默认也是 5173,可自定义)
// 配置代理:解决前端开发中跨域请求后端的问题
proxy: {
'/api': {
target: 'http://localhost:8080', // 后端服务器地址(Spring Boot 或其他服务)
changeOrigin: true, // 修改请求头中的 origin 字段,避免跨域
rewrite: path => path.replace(/^\/api/, '')
// 将请求路径中的 `/api` 前缀去掉,例如:
// 前端请求:/api/region-sales → 实际转发为:http://localhost:8080/region-sales
}
}
}
})
App.vue
<!-- 页面结构区域 -->
<template>
<div class="chart-wrapper">
<h1>数据可视化</h1>
<h2>大数据高23-1班 张三</h2>
<!-- 引入的图表组件,用于展示区域销售数据 -->
<PaymentChart />
</div>
</template>
<!-- 脚本逻辑区域 -->
<script setup>
// 引入封装好的区域图表组件
import PaymentChart from './components/PaymentChart.vue'
</script>
<!-- 页面样式区域 -->
<style>
/* 设置整个页面的背景色和默认字体样式 */
body {
background-color: #f0f2f5; /* 浅灰背景色 */
margin: 0; /* 页面贴边显示(去除浏览器默认外边距) */
padding: 20px; /* 页面内部留出 内边距 20px(上下左右)*/
font-family: "Microsoft YaHei", sans-serif;
}
/* 图表容器样式:限制最大宽度、居中显示 */
.chart-wrapper {
max-width: 1400px; /* 设置容器的最大宽度为 1400 像素 */
margin: 40px auto; /* 上下间距 40px,左右自动居中 */
font-family: sans-serif; /* 设置字体为无衬线字体(简洁现代风格) */
}
</style>
components/PaymentChart.vue
<template>
<!-- 图表容器,通过 ref 引用 -->
<div ref="chartRef" class="chart-container"></div>
</template>
<script setup>
import { ref, onMounted } from 'vue'
import * as echarts from 'echarts'
import axios from 'axios'
// 引用图表容器 DOM
const chartRef = ref()
// 渲染图表方法(页面加载后执行)
const renderChart = async () => {
// 1. 请求后端接口,获取 Hive 查询结果
const res = await axios.get('/api/payment-count')
const data = res.data
// 2. 提取横轴(支付方式)和纵轴(订单数量)数据
const xData = data.map(item => item.payment_method) // 如:微信、支付宝
const yData = data.map(item => item.order_count) // 对应的订单数量
// 3. 初始化 ECharts 实例
const chart = echarts.init(chartRef.value)
// 4. 配置并渲染柱状图
chart.setOption({
title: {
text: '2024年各支付方式的订单数量对比', // 主标题
subtext: '单位:件', // 副标题
left: 'center' // 居中显示
},
tooltip: {
trigger: 'axis' // 鼠标悬停显示横轴对齐提示
},
xAxis: {
type: 'category',
data: xData // 横轴:支付方式
},
yAxis: {
type: 'value',
name: '订单数量',
max: Math.ceil(Math.max(...yData) * 1.2) // 动态设置最大值,提高图表空间
},
series: [{
type: 'bar', // 柱状图
name: '订单数',
data: yData, // 数据值
barWidth: '45%', // 柱子宽度
itemStyle: {
color: '#5470C6' // 默认蓝色柱子
},
label: {
show: true,
position: 'top' // 在柱子顶端显示数值
}
}]
})
}
// 5. 页面加载完毕后自动执行图表渲染
onMounted(() => renderChart())
</script>
<style scoped>
.chart-container {
width: 100%; /* 宽度占满父容器 */
height: 400px; /* 固定高度 400px,确保 ECharts 能正确显示 */
min-width: 700px; /* 最小宽度为 700px,防止图表在小屏下过小 */
background: #fff; /* 图表背景白色 */
border: 1px solid #e0e0e0; /* 边框线 */
border-radius: 15px; /* 圆角边框 */
padding: 10px; /* 内边距 */
box-shadow: 0 2px 8px rgba(0, 0, 0, 0.05); /* 轻微阴影 */
}
</style>

