挑战项目 --- 微服务编程测评系统(在线OJ系统)
一、前言
1.为什么要做项目
面试官要问项目,考察你到底是理论派还是实战派?
1.希望从你的项目中看到你的真实能力和对知识的灵活运用。
2.展示你在面对问题和需求时的思考方式及解决问题的能力。
3.面试官会就你项目提出一些问题,或扩展需求。以此来评估你如何有效应对和设计解决方案。
2.常见问题
1.你这里的处理可能会引发 XXXbug,那么你想要怎么处理。有时候答不上来面试官也会做一些引导,看你是否有一些自己的想法。
2.我现在有个 XXX 需求,在你的项目中你要怎么满足我的需求?
3.你的 XX 表结构如何设计的,你的缓存如何设计的,为什么要这么设计,这么设计的话,如果需求发生 XX 变化你要怎么处理?
4.针对你使用的某个组件,问一些问题,例如:你是怎么使用redis的,为什么要用它,缓存一致是怎么保证的,内存维护使用怎样的方案.....
3.误区
有些同学可能认为在项目中使用技术越多,面试成功率越高。
然而在有限的时间内,无法深入学习和理解所有的技术,也无法实现所有想到的功能。当面试官问到你没有涉及过的技术或功能时,你如果之前知识一味的追求学习的数量,此时你一定很难回答出来。
面试官更关心你的思考和解决问题的能力,如果你能运用所学知识,清晰地解释应对一个你从未接触过的领域,即使不是业界最优解,你也能得到面试官的认可。
不断思考、探索和创新、以提升自己的总和素质和竞争力。
4.总结
项目的作用在于全面展现你的实战能力,问题处理及思考能力,确保面试官对你完成交付任务的能力充满信心。即使遇到挑战,你也能积极应对,推动项目向前发展。
二、 项目展示及核心技术介绍
用到的技术及组件

在线OJ(online-judge)系统,在线判题系统,类似于LeetCode这样的刷题网站。
1.题库(题目列表)

2.竞赛(竞赛列表)

上述两个功能支持游客登录,因此未登录就可以进行查看。
但是如果要答题、要报名比赛需要登录才可以。
3.手机号验证码进行登录

4.答题(判断通过还是未通过)

5.对题目标题和题目内容及难度的搜索

6.报名/开始答题的按钮提示
7. 答题倒计时(完成竞赛/提交代码按钮)

8. 上一题下一题按钮

9.历史竞赛
查看排名

10.个人中心

11.我的比赛/我的消息


12.退出登录

13.后台管理系统

用户管理

题目管理

竞赛管理

14. 第三方组件xxl-job管理

三、开发环境

四、安装nodejs
Node.js — Run JavaScript Everywhere
五、安装 VS Code
Visual Studio Code - Code Editing. Redefined
六、 项目开发步骤
• 立项阶段:项目定义、需求收集与分析、可行性分析、风险评估与规划、项目团队组建、制定项目计划、获取批准与支持。
• 需求评审与分析:
◦ 项目团队(包括产品经理、开发人员、测试人员等)共同参与,明确项目的目标、功能需求、 用户体验等。
◦ 产出物为《需求规格说明书》或《产品需求文档》。(产品经理最终交付)
• 技术选型与架构设计
◦ 根据项目需求,设计系统的整体架构,选择合适的技术栈。
◦ 架构师或技术负责⼈进行主导。
•接口定义与文档编写:
◦后端开发人员定义API接口,包括接口地址、请求方法、请求参数、响应数据、错误码等。
◦编写接口文档,供前端开发人员使用,确保前后端对接口有统一的理解。(一般会组织简短会议讨论,后端主导)
◦ 所有接口风格统一,促进效率。
• 后端开发、前端开发:
◦ 前端和后端开发⼈员分别根据接口文档和技术选型,进行开发。
◦ 这个过程理想情况,前后端是互不干扰独立开发的所以接口文档一定要保证高质量,但是遇到 问题一定是随时沟通。
• 前后端联调:
◦ 后端同学开发完一部分接⼝后,可将接口部署到开发环境。和前端同学配合联调 ◦
联调工作一般由前端同学主导,后端同学配合调整和修改。
◦ 联调过程中,后端同学可分出一部分精力完成其它工作。但要确保提供联调接⼝的可靠性。
◦ 前后端开发人员配合进行接口联调,确保前后端数据交互无误。
• 测试
◦ 前后端同学分别将前后端系统部署到测试环境。
◦ 测试团队进行功能测试、性能测试、兼容性测试等,确保系统的质量和稳定性。
• 问题修复与优化:
◦ 根据测试结果,修复发现的问题,优化系统性能和用户体验。
◦ 可能涉及前后端代码的修改和调整。
• 部署与上线:
◦ 将项目部署到⽣产环境,配置服务器、数据库等。
◦ 进行上线前的最终测试,确保系统能够稳定运行。
• 维护与迭代:
◦ 项目上线后,进行日常的维护和监控,确保系统的安全和稳定运行。
◦ 根据用户反馈和市场需求,进行功能迭代和优化。
总结:
这就是软件开发的基本步骤,实际生产开发中有时也会做出调整。在整个开发过程中,前后端开 发⼈员需要保持密切的沟通与协作,确保项目的顺利进行。同时,项目团队也需要定期召开会议,同步项目进度、问题和需求变更,确保项目能够按时交付。
七、需求收集与分析
需求分类
•业务需求:指反映企业或组织对系统的⽬标要求,通常来⾃与企业内部。
•用户需求:描述软件系统的⽤⼾期望和需求,如⽤⼾界⾯、操作⽅式、数据展⽰等
•系统需求:从系统⻆度来说明软件的需求,包括功能需求(系统必须实现的功能)、⾮功能需求(⽐如软件的质量,可维护性,效率等等)和设计约束(交付时的⼀些限制条件,⽐如必须采⽤国有⾃主知识产权的数据库,必须运⾏在某个操作系统下)等等。
需求获取
需求获取的⽅式主要有以下⼏种:
•访谈与调研:直接与⽤⼾或者相关⼈员进⾏交流,然后整理出需求。
•问卷调查:由于对⽤⼾进⾏逐⼀访谈⽐较耗时且⽤⼾时间不⼀定允许及时参与访谈,所以可以预先准备问卷调查表让⽤⼾填写,再根据结果进⾏⼩范围访谈,可以看做是对⽤⼾访谈的⼀种优化。
•查阅⽂档与资料:研究⾏业报告、市场分析报告等,了解⾏业趋势、市场需求和竞争态势。
•原型与概念验证:制作简单的原型或概念模型,向⽤⼾展⽰可能的系统界⾯、操作流程和功能点,收集他们的反馈和建议
• 竞品分析:分析竞争对⼿的产品或服务,了解他们的功能、优缺点以及⽤⼾反馈,从⽽发现⾃⾝产 品的潜在需求和改进点。
• 等等
在获取需求的过程中,需要注意以下⼏点:
◦ 保持沟通:与⽤⼾和利益相关者保持持续的沟通,确保及时获取反馈和澄清疑问。
◦ 记录与整理:详细记录获取到的需求信息,并进⾏整理和分析,确保信息的准确性和⼀致性。
◦ 验证与确认:对获取到的需求进⾏验证和确认,确保它们真正反映了⽤⼾的期望和业务需求。
需求种类 需求内容 (在线OJ系统)
业务需求 题⽬列表、刷题、竞赛的列表、竞赛用户排名、
比赛、自动判题、题⽬管理、 竞赛管理。
用户需求 我的竞赛、我的消息、获取⽐赛结果、查看历史竞赛排名
系统需求 用户登录、注册、用户管理
安全防护(身份认证、防sql注入、防xss攻击)SEO优化......
需求确定:




八、系统架构(BS与CS架构)
C/S架构

常见案例:QQ、微信、网易云音乐、王者荣耀等等

C/S架构优缺点

B/S架构
B/S架构全称是浏览器 / 服务器(Browser/Server)架构,
分为Web浏览器、服务器程序、数据库(也可以是第三方组件服务)服务三部分

常见案例: 比如常见的大型网站站都属于此类。比如:平时使用的学校的官网、CSDN的官网等等
B/S架构优缺点

如何选择

十、系统架构-微服务划分01
为什么使用微服务架构


微服务架构带来的挑战

如何划分微服务
微服务划分原则

划分在线OJ系统的服务
按业务划分

按照技术划分

按照实际情况划分



最终的服务架构如下

总结

十一、系统架构---技术选型
后端技术选型

前端技术选型
选择易于上手的Vue3作为前端框架。Vue3作为当前主流的前端框架,备受大型公司如华为、腾讯等的青睐。值得注意的是,Vue2 已在2023年12月31日停止维护,而Vue3在性能、自定义渲染API和组件等方面相较Vue2有了显著的提 升,能够为用户提供更优质的开发体验。因此,我们的项目决定采用最前沿的Vue3作为前端核心框架。
十二、VUE 基础简介
创建vue项目
前置条件
1.熟悉命令行
2.已经安装18.3或更高版本的Node.js
安装并执行create-vue
npm create vue@latest
npm create vue@latest
这⼀指令将会安装并执⾏create-vue,它是Vue官⽅的项⽬脚⼿架⼯具。你将会看到⼀些诸 如TypeScript和测试⽀持之类的可选功能提⽰(我们暂时都选否):

根据提示执行这三个命令
cd vue-project npm install npm run dev
执行结果如下

验证成功:第三个命令执⾏成功后,我们可以看到⼀个可访问地址:http://localhost:5173/在浏 览器访问。看到如下页面则说明前端项⽬创建并启动成功。

用VS Code打开刚刚创建的项目
安装vue-official插件,
使.vue文件中的代码拥有高亮颜色。便于我们开发
十三、vue基础-目录结构
项目结构
核心目录
• node_modules:⽀持项⽬运⾏的依赖文件。(后期开发中我们会引⼊多个依赖包)
• public:存放静态资源和公共资源,如favicon.ico网站图标。
• src:项⽬开发主要⽂件夹。
• index.html:⼊⼝的html⽂件。
• package.json:项⽬的描述⽂件。
• vite.config.js:项⽬的配置⽂件。
十四、单文件组件

模板<template>
![]()
脚本<script>

<script setup>

样式<style>
• 通常使⽤CSS或CSS预处理器编写样式。定义了组件的样式和布局,⽤于控制组件的外观和样式。
• 每个*.vue⽂件可以包含多个<style>标签
十五、 vue基础-选项式API&组合式API
API风格
Vue的组件可以按两种不同的风格书写:选项式 API 和组合式 API。
选项式API
选项式API是传统的组件开发⽅式。在这种⽅式下,组件的选项(如data、methods、 computed、watch等)被组织在单个对象中,每个选项负责不同的功能。这种⽅式使得组件的结构清 晰,但随着组件的复杂度增加,可能会出现代码难以管理和维护的问题。
• data: 定义组件的响应式数据。
• methods: 定义组件的⽅法,它们可以访问组件的data和其他methods。
• computed: ⽤于定义依赖于其他响应式数据的计算值。
• watch: ⽤于观察响应式数据的变化,并执⾏异步或者代价较⼤的操作。
......
官方示例:
<script>
export default {// data() 返回的属性将会成为响应式的状态// 并且暴露在 `this` 上data() {return {count: 0}},// methods 是一些用来更改状态与触发更新的函数// 它们可以在模板中作为事件处理器绑定methods: {increment() {this.count++}},// 生命周期钩子会在组件生命周期的各个不同阶段被调用// 例如这个函数就会在组件挂载完成后被调用mounted() {console.log(`The initial count is ${this.count}.`)}
}
</script><template><button @click="increment">Count is: {{ count }}</button>
</template>
组合式API
通过组合式API,我们可以使⽤导⼊的 API 函数来描述组件逻辑。在单⽂件组件中,组合式 API 通常会 与<script setup>搭配使⽤。这个 setup attribute是⼀个标识,告诉 Vue 需要在编译时进⾏⼀些处 理,让我们可以更简洁地使⽤组合式API。
总结:组合式API可以使我们更清晰地组织和编写组件的逻辑,这种⻛格使得代码更加易于阅读、测试 和维护,尤其适⽤于⼤型、复杂的Vue应⽤程序。
官⽅⽰例:
<script setup>
import { ref, onMounted } from 'vue'// 响应式状态
const count = ref(0)// 用来修改状态、触发更新的函数
function increment() {count.value++
}// 生命周期钩子
onMounted(() => {console.log(`The initial count is ${count.value}.`)
})
</script><template><button @click="increment">Count is: {{ count }}</button>
</template>
<script setup>
如何选择?
两种 API ⻛格都能够覆盖⼤部分的应⽤场景。它们只是同⼀个底层系统所提供的两套不同的接⼝。实际上,选项式 API 是在组合式 API 的基础上实现的!关于 Vue 的基础概念和知识在它们之间都 是通⽤的。
选项式api结构清晰,初学者友好。组合式api更加灵活、⾃由、⾼效、更好的复⽤。
综上: 我们的项⽬中将选择使⽤组合式API。

相关文章:
挑战项目 --- 微服务编程测评系统(在线OJ系统)
一、前言 1.为什么要做项目 面试官要问项目,考察你到底是理论派还是实战派? 1.希望从你的项目中看到你的真实能力和对知识的灵活运用。 2.展示你在面对问题和需求时的思考方式及解决问题的能力。 3.面试官会就你项目提出一些问题,或扩展需求…...
基于springboot的体质测试数据分析及可视化设计
作者:学姐 开发技术:SpringBoot、SSM、Vue、MySQL、JSP、ElementUI、Python、小程序等 文末获取“源码数据库万字文档PPT”,支持远程部署调试、运行安装。 项目包含: 完整源码数据库功能演示视频万字文档PPT 项目编码࿱…...
java-重载与重写
介绍 在 Java 中,重载(Overloading) 和 重写(Overriding) 是两个重要的概念,它们都与方法有关,但它们的应用场景和行为完全不同。 通过理解重载和重写的区别,可以更好地设计类的继承…...
使用C++构建一个优先级队列
1.优先级队列的介绍 优先级队列是一种特殊的队列数据结构,它是队列,但又不完全是,因为它要将装载的数据进行优先级排序,找到一个最大或者最小优先级的元素,下一次出队列的元素就是这个元素,所以说它不完全是…...
linux驱动开发之字符设备与总线设备驱动模型的区别与联系
Linux驱动开发核心概念解析 1. 字符设备(Character Device) 定义与特点: 以字节流形式进行数据交换,适用于顺序访问的设备(如键盘、鼠标、串口)。 用户空间通过设备文件(如/dev/xxx࿰…...
AI deepseek对数据治理的影响
DEEPSEEK作为智能一款助手,在数据治理体系中具有深远的影响。它通过提供智能化、自动化和高效化的解决方案,推动企业在数据治理变革与领域的优化。以下是EPSEEK对数据治理体系影响的多角度分析: 一、战略层面:推动数据治理目标的…...
DeepSeek各版本说明与优缺点分析
DeepSeek各版本说明与优缺点分析 DeepSeek是最近人工智能领域备受瞩目的一个语言模型系列,其在不同版本的发布过程中,逐步加强了对多种任务的处理能力。本文将详细介绍DeepSeek的各版本,从版本的发布时间、特点、优势以及不足之处࿰…...
iOS 老项目适配 #Preview 预览功能
前言 iOS 开发者 最憋屈的就是UI 布局慢,一直以来没有实时预览功能,虽然swiftUI 早就支持了,但是目前主流还是使用UIKit在布局,iOS 17 苹果推出了 #Preview 可以支持UIKit 实时预览,但是仅仅是 iOS 17,老项目怎么办呢?于是就有了这篇 老项目适配 #Preview 预览 的文章,…...
在ubuntu22.04上先部署docker,再编译安装kamailio,附详细操作流程及docker和makailio的版本号
以下是在Ubuntu 22.04上部署Docker并编译安装Kamailio的详细操作流程,包含版本号信息: 一、部署Docker(版本:24.0.7) 更新系统包 sudo apt update && sudo apt upgrade -y安装依赖工具 sudo apt install -y ap…...
蓝桥杯试题:排序
一、问题描述 给定 nn 个正整数 a1,a2,…,ana1,a2,…,an,你可以将它们任意排序。现要将这 nn 个数字连接成一排,即令相邻数字收尾相接,组成一个数。问,这个数最大可以是多少。 输入格式 第一行输入一个正整数 nnÿ…...
C++常用拷贝和替换算法
算法简介: copy // 容器内指定的元素拷贝到另一容器replace // 将容器内指定范围的旧元素改为新元素replace_if // 容器内指定范围满足条件的元素替换为新元素swap //互换两个容器的元素 1. copy 功能描述: 将容器内指定范围的数据拷贝到另一容器中函…...
2024年12月 Scratch 图形化(三级)真题解析 中国电子学会全国青少年软件编程等级考试
202412 Scratch 图形化(三级)真题解析 中国电子学会全国青少年软件编程等级考试 一、选择题(共18题,共50分) 第 1 题 气温和对应的穿衣建议如下表所示,下列选项能正确给出穿衣建议的是?( ) A. …...
C# 中记录(Record)详解
从C#9.0开始,我们有了一个有趣的语法糖:记录(record) 为什么提供记录? 开发过程中,我们往往会创建一些简单的实体,它们仅仅拥有一些简单的属性,可能还有几个简单的方法,比如DTO等等…...
【MQTT协议 03】 抓包分析
一、MQTT测试工具 1、mqtt服务器 emqx 2、mqtt 客户端 mqttx 3、抓包工具 wireshark 搭建参考 【MQTT 协议 01】MQTT 服务器搭建_mqtt服务器搭建-CSDN博客 二、报文测试 2.1、CONNECT (客户端连接) 2.1.1、抓包 2.1.2、解析 #16进制表示 10300…...
深度学习-100-RAG技术之最简单的RAG系统概念和效果优化提升方向
文章目录 1 数据是基础2 Naive RAG(最简单的RAG系统)2.1 RAG周边技术2.2 标准的RAG流程2.3 RAG的潜在问题2.4 如何应对RAG的问题3 优化方向3.1 原始数据创建/准备3.1.1 易于理解的文本3.1.2 提高数据质量3.2 预检索优化3.2.1 分块优化3.2.2 添加元数据3.2.3 选对嵌入模型3.2.4 …...
Redis面试题总结(题目来源JavaGuide)
Redis 基础 问题1:Redis 有什么作用?为什么要用 Redis/为什么要用缓存? Redis 是一个开源的高性能键值对数据库,它的作用主要体现在以下几个方面: 缓存:Redis 常被用作缓存系统,可以将频繁访问的数据存储…...
Django 多数据库
django 支持项目连接多个数据库 DATABASES = {default: {ENGINE: django.db.backends.mysql,NAME: xxx,USER: root,"PASSWORD": xxxxx,HOST: xxxx,PORT: 3306,},bak: {ENGINE: django.db.backends.mysql,NAME: xxx,USER: root,"PASSWORD": xxxx,HOST: xxx…...
为AI聊天工具添加一个知识系统 之87 详细设计之28 Derivation 统一建模元模型 之1
文本要点 要点 Derivation 统一建模元模型 Derivation 统一建模元模型:意识原型的祖传代码,即支撑 程序框架的 符号学中的 自然和逻辑树。 这棵树的雏形中描述了三种建模工件:语用钩子,语法糖和语义胶水。 三种工件对应的三“…...
手机上运行AI大模型(Deepseek等)
最近deepseek的大火,让大家掀起新一波的本地部署运行大模型的热潮,特别是deepseek有蒸馏的小参数量版本,电脑上就相当方便了,直接ollamaopen-webui这种类似的组合就可以轻松地实现,只要硬件,如显存…...
电商项目-分布式事务(四)基于消息队列实现分布式事务
基于消息队列实现分布式事务,实现消息最终一致性 如何基于消息队列实现分布式事务? 通过消息队列实现分布式事务的话,可以保证当前数据的最终一致性。实现思路:将大的分布式事务,进行拆分,拆分成若干个小…...
leetcode_双指针 160.相交链表
160.相交链表 给你两个单链表的头节点 headA 和 headB ,请你找出并返回两个单链表相交的起始节点。如果两个链表不存在相交节点,返回 null 。 思路: 本题中,交点不是数值相等,而是指针相等 双指针遍历两遍后必定相遇,…...
深入理解浮点数:单精度、双精度、半精度和BFloat16详解
文章目录 深入理解浮点数:单精度、双精度、半精度和BFloat16详解 🔢简介 🌟1. 单精度(Single Precision)🎯应用场景 🚀 2. 双精度(Double Precision)💪应用场…...
Verilog基础(三):过程
过程(Procedures) - Always块 – 组合逻辑 (Always blocks – Combinational) 由于数字电路是由电线相连的逻辑门组成的,所以任何电路都可以表示为模块和赋值语句的某种组合. 然而,有时这不是描述电路最方便的方法. 两种always block是十分有用的: 组合逻辑: always @(…...
前端知识速记:POST和GET
前端知识速记:POST和GET请求的区别 一、GET请求概述 GET请求是一种用于获取服务器资源的请求方式。**使用GET请求时,数据通过URL传递,适合用于获取数据而不修改资源。**以下是GET请求的一些基本特征: 数据附在URL后面ÿ…...
【Java】MyBatis动态SQL
在MyBatis中使用动态SQL语句。 动态SQL是指根据参数数据动态组织SQL的技术。 生活中的案例: 在京东上买东西时,用户搜索商品,可以选择筛选条件,比如品牌,价格,材质等,也可以不使用筛选条件。这时…...
java进阶知识点
java回收机制 浅谈java中的反射 依赖注入的简单理解 通过接口的引用和构造方法的表达,将一些事情整好了反过来传给需要用到的地方~ 这样做得好处:做到了单一职责,并且提高了复用性,解耦了之后,任你如何实现…...
Java/Kotlin HashMap 等集合引发 ConcurrentModificationException
在对一些非并发集合同时进行读写的时候,会抛出 ConcurrentModificationException 异常产生示例 示例一(单线程): 遍历集合时候去修改 抛出 ConcurrentModificationException 的主要原因是当你在遍历一个集合(如 Map…...
拍照对比,X70 PRO与X90 PRO+的细节差异
以下是局部截图(上X70P下X90PP) 对比1 这里看不出差异。 对比2 X90PP的字明显更清楚。 对比3 中下的字,X90PP显然更清楚。...
Node.js与嵌入式开发:打破界限的创新结合
文章目录 一、Node.js的本质与核心优势1.1 什么是Node.js?1.2 嵌入式开发的范式转变二、Node.js与嵌入式结合的四大技术路径2.1 硬件交互层2.2 物联网协议栈2.3 边缘计算架构2.4 轻量化运行时方案三、实战案例:智能农业监测系统3.1 硬件配置3.2 软件架构3.3 核心代码片段四、…...
使用java调用deepseek,调用大模型,处理问题。ollama
废话不多,直接上代码 Testpublic void test7171111231233(){// url:放请求地址String url "http://localhost:11434/api/generate";HttpRequest request HttpUtil.createPost(url);Map<String, String> headers new HashMap<>();String a…...








