-----------------------------------AI类-----------------------------------------------
AI工作流用过哪些
AI辅助编程Cursor
AI对话搜索(DeepSeek、ChatGPT)
用过哪些AI,分别有什么使用技巧
DeepSeek:擅长长上下文推理和复杂逻辑分析,技巧是提供完整背景和格式要求(如"请用表格对比")。
ChatGPT:对话逻辑强,技巧是用"角色扮演+分步指令"(如"你是一个资深架构师,分三步帮我设计...")
AI知识库有哪些
本质是RAG(检索增强生成)技术。工具层面有:Dify、FastGPT、AnythingLLM;个人常用的是:Obsidian + Copilot、Notion AI。
你认为 AI 协作开发在岗位中的价值是什么?它如何提升效率?
价值:将开发者从"怎么写"的低效细节中解放出来,更专注于"做什么"和"为什么这么做"的架构决策。
提效:能快速生成样板代码、解释遗留系统逻辑、辅助调试错误、补充单元测试。
在你看来,AI 协作开发的⻛险有哪些?如何避免?
风险:生成代码有安全隐患(SQL注入)、引入过时依赖、造成开发者过度信任而丧失审查能力。
规避:采用"AI建议,人脑决策"原则,对生成代码进行安全审查;开启联网搜索获取最新信息;对核心逻辑手动编写测试。
在AI Coding中踩坑和经验
上下文过长导致"遗忘"早期需求。解法:关键约束条件要反复强调,或单独维护一份需求文档喂给AI。
-----------------------------------后端-----------------------------------------------
API网关,即API Gateway
网关的作用分别为:
1.网关层对外部和内部进行了隔离,保障了后台服务的安全性。
2.对外访问控制有网络层面转换成运维层面,减少变更的流程和错误成本
3,减少客户端和服务的耦合,服务可以独立运行,并通过网关层做映射
4.通过网关层聚合,减少外部访问的频次,提升访问效率
5.节约后端服务开发成本,减少上线风险
6.为服务熔断,灰度发布,线上测试提供简单方案
7.便于进行应用层面的扩展
其实也就是将服务于客户端隔离,避免客户端直接调用,为了客户端提供统一入口 保证服务安全性
这里我们采用Ocelot ,Ocelot是一个用.NET Core实现并且开源的API网关,它功能强大,包括了:路由、请求聚合、服务发现、认证、鉴权、限流熔断、并内置了负载均衡器与Service Fabric、Butterfly Tracing集成
配置简单,功能强大:大部分核心功能(如路由、限流、服务发现等)都可通过简单的 JSON 配置完成,无需编写大量代码,降低了使用门槛和开发工作量。
扩展性强,灵活定制:提供了中间件机制,开发者可以根据特定业务需求编写自定义中间件来扩展其功能,满足复杂的定制化场景。
轻量级,性能良好:基于 .NET Core 构建,启动快、内存占用低,在常规的微服务场景中能提供出色的性能表现。
什么是微服务
微服务强调的是将单一应用程序划分为一组小型的、独立的服务。每个服务都运行在自己的进程中,并通过轻量级通信机制(如HTTP/gRPC)协作。
服务拆分:通常基于业务边界(如订单服务、用户服务、库存服务)。每个服务可以是一个独立的ASP.NET Core应用。
独立部署:每个服务有自己的Dockerfile,独立部署在Kubernetes(K8s)的Pod中。
技术栈:.NET 6/8/9 非常适合构建微服务,因为它启动快、内存占用相对较低,且支持跨平台(Linux容器)。
关键组件:在.NET微服务体系中,通常需要引入服务发现(如Consul或K8s自带)、API网关(如Ocelot、YARP)、分布式事务(如CAP理论下的最终一致性,常用DotNetCore.CAP库)以及熔断降级(如Polly)。
什么是分布式
当一个系统由多个通过网络互联的计算机(节点)组成,共同完成任务时,它就是分布式系统。微服务架构一定是分布式的,但分布式系统不一定是微服务(例如传统的SOA架构或分布式单体)。
通信模式:
同步:gRPC(在.NET中性能优于HTTP/REST,常用于服务间高效通信)。
异步:消息队列(RabbitMQ、Azure Service Bus、Kafka)。.NET提供了完善的客户端库支持。
数据一致性:在分布式系统中,无法像单体应用那样依赖SQL Server的本地事务(ACID)。.NET开发者常利用事件驱动架构或Saga模式(如使用MassTransit、NServiceBus等框架)来保证最终一致性。
状态管理:分布式系统通常要求服务是"无状态"的,以便水平扩展。若有状态,则需借助分布式缓存(如Redis,.NET中有StackExchange.Redis)或分布式数据库(如TiDB,或Azure Cosmos DB)。
ORM框架用过哪些,优缺点是啥EF Core、Dapper
EF Core:重量级,优点是开发快、自动管理SQL、有LINQ和变更追踪;缺点是复杂查询性能差、SQL难控制。
Dapper:轻量级,优点是手写SQL性能高、精细控制;缺点是手动写CRUD、没有自动映射关联。
什么是WebService
指通过Web标准(如HTTP、XML、SOAP)提供的服务。与WebAPI不同,WebService更强调跨平台和契约(WSDL),比较重;而现在流行的WebAPI(RESTful或GraphQL)更轻量。
什么是反射
程序在运行时动态获取类型信息(方法、属性)并创建实例或调用方法的能力。常用于依赖注入框架、ORM映射、插件系统等。注意反射有性能开销和安全风险。
ORM中的延迟加载与直接加载有什么异同
延迟加载:访问导航属性时才去查数据库。优点是减少不必要数据加载;缺点是可能产生N+1查询问题。
直接加载(Eager Loading):主查询时用Include()一次性把关联数据带回来。优点是减少查询次数;缺点是可能加载很多用不上的数据。
什么是堆和栈
栈是内存中一块用于存储 局部变量 和 函数调用信息 的区域。它的工作方式遵循 后进先出 (LIFO) 原则,特点极快,空间有限
堆是用于存储 大型对象 或 生命周期不确定 的数据的内存区域。,特点速度慢,有GC垃圾回收器管理,空间大
指针是一个变量,它的值是 另一个变量的内存地址
什么是线程和进程
每个程序至少有一个进程(操作系统分配资源的基本单位),每个进程至少有一个线程(CPU 执行的基本单位),同一进程里,多线程的数据是共享的,共享全局变量、静态变量和打开的文件句柄。多线程通常是为了解决高并发、并行任务以及快速响应的问题
什么是IOC控制反转
IOC是控制反转:通过依赖注入的方式,把获取其他类的控制权,其优点是解耦更灵活
dotNet的服务是怎么打包的,以什么方式在服务器运行
打包:dotnet publish 生成dll或exe(独立部署时)。
运行:可跨平台,用dotnet MyApp.dll运行;或部署到IIS、Docker;Linux上也可用systemd/nohup守护进程。
什么是面向对象
以"事物"为中心,思考"谁在做什么"。将问题拆解成不同的对象,每个对象有自己的属性和行为,通过对象之间的交互来解决问题。
三大特性:继承、封装、多态
什么是面向过程
以"事件"为中心,思考"发生了什么"。将问题拆解成一系列步骤,用函数(方法)一步步执行。
特点:
自顶向下:把大问题拆成小问题,每个小问题写成一个函数。
数据与操作分离:数据是数据,函数是函数。函数处理数据。
关注"怎么做":关注执行任务的顺序和逻辑。
.net core与.net formwork有啥区别
1.跨平台能力
.NET Framework:仅支持 Windows。虽然 Mono 项目可移植到 Linux/macOS,但官方运行时是 Windows 绑定。
.NET Core:原生支持 Windows、Linux、macOS。可以在 Docker、K8s、各种云环境中无缝运行。
2.应用程序模型
.NET Framework:支持 WinForms、WPF、ASP.NET WebForms、MVC 5、Web API 2、WCF 等。这些技术高度依赖 Windows 底层(如 GDI+、DirectX、IIS)。
.NET Core:
早期(Core 3.1)支持 WinForms 和 WPF,但仅限于 Windows。
全新应用模型:ASP.NET Core(MVC/Web API/Razor Pages)、Blazor(Server/WebAssembly)、MAUI(跨平台桌面+移动,.NET 8 成熟)。
不再支持 WebForms、WCF Server(有社区移植版,但非官方)。
3.部署方式
.NET Framework:通常依赖 系统全局安装 的运行时,应用与运行时版本紧耦合。不同应用可能因系统级运行时升级而出现兼容性问题("DLL Hell")。
.NET Core:支持 独立部署(self-contained,运行时和应用打包在一起)和 框架依赖部署(依赖目标机器上安装的共享运行时)。可做到应用级依赖隔离,互不干扰。
4.性能与底层优化
.NET Framework:经过十几年打磨,但设计上受限于早期硬件和 Windows 特性。JIT 和 GC 相对保守。
.NET Core:从头开始设计,大量采用 服务器场景优化(如 RyuJIT、分层编译、GC 工作模式可配置)。.NET Core 3.0 后性能已明显超过 .NET Framework,到 .NET 8 更是大幅领先(特别是 HTTP 处理、JSON 序列化、内存分配)。
5.API 覆盖范围
.NET Framework:包含大量 Windows 专用的 API(如注册表、EventLog、PerformanceCounter、WMI、AppDomain 高级操作等)。还有一些过时的技术(Remoting、Enterprise Services)。
.NET Core:最初是 .NET Framework 的一个子集,但从 2.0 开始逐渐补全,到 3.0 已经涵盖大部分常用 API。缺失的部分通常是 Windows 强耦合或非跨平台特性。对于必须访问注册表等需求,提供 Microsoft.Win32.Registry 包作为 Windows 专用扩展。
6.开源与社区
.NET Framework:闭源(部分代码可参考 Reference Source),只有 Microsoft 内部团队维护。
.NET Core:完全开源(MIT 协议),代码托管在 GitHub,接受社区贡献。开发节奏非常快,每年 11 月发布新版本。
7.版本演进与未来
.NET Framework:最后一个大版本是 4.8.1(2022 年),微软已宣布不再计划增加新功能,只提供安全更新和可靠性修复。
.NET Core:从 5.0 开始更名为 .NET 5(去掉 "Core"),之后每年一个大版本(.NET 6 LTS、7、8 LTS、9 预览)。所有新特性、新性能优化都只会出现在现代 .NET 上。
.net core3.1与.net 8 有啥区别
生命周期与支持
.NET Core 3.1 已于 2022 年 12 月结束支持(EOL),而 .NET 8 是 LTS(长期支持)版本,支持到 2026 年 11 月,适合企业级新项目。
性能
.NET 8 在 JIT、GC、线程池、JSON 序列化等方面有大幅优化。比如 PGO(配置文件引导优化) 默认启用,动态调整热点代码;Struct 内联、AVX-512 指令集 支持等。相同业务下,.NET 8 的吞吐量通常比 3.1 高 20%~50% 以上。
原生 AOT(提前编译)
.NET 8 支持真正的 Native AOT,可以将应用直接编译为单文件、无依赖、启动极快的原生二进制(类似 Go 或 Rust)。而 .NET Core 3.1 只能依赖 JIT 或早期的 CoreRT(不成熟),无法用于生产级 AOT。
最小 API(Minimal APIs)
.NET 6 引入,.NET 8 进一步完善。仅需几行代码即可创建 HTTP 服务,大幅减少样板代码(不需要 Startup.cs 和显式 Controller)。而 .NET Core 3.1 必须使用 MVC 或 WebApi 的传统模式。
内置的 JSON 处理
.NET Core 3.1 开始引入 System.>.Json,但功能相对基础(缺少多态、引用循环处理、中文转义等)。.NET 8 中 System.>.Json 已经非常成熟,新增了 可自定义的契约模型、JsonSerializerOptions.Web 默认驼峰命名、JsonNode 可变 DOM、以及更快的序列化性能,基本可以替代 Newtonsoft.Json。
Blazor 统一模型
.NET Core 3.1 只有 Blazor Server 模式,且处于早期阶段。.NET 8 推出了 Blazor United(现在叫 Blazor Web App),同一组件可同时支持服务端渲染、客户端 WebAssembly 以及流式交互,极大简化全栈 Web 开发。
C# 语言版本
.NET Core 3.1 默认 C# 8.0(可手动开启 9.0,但不完全适配)。.NET 8 默认 C# 12,带来了主构造函数、集合表达式、默认 lambda 参数、ref readonly 参数等大量语法糖,开发效率更高。
其他改进
原生支持 DateOnly / TimeOnly(3.1 需要手写库)。
TimeProvider 抽象(方便测试时间相关逻辑)。
更好的容器支持(默认非 root 用户、更小的镜像大小、原生调试体验)。
EF Core 8:对 SQLite 的向量搜索、JSON 列映射、改进的批量更新等。
日志与指标:内置 OpenTelemetry 支持,更完善的分布式追踪。
CTS、CLS、CLR分别代表什么?对应的作用是什么?
CTS(通用类型系统):确保不同语言(C#/VB.NET)的类型能互操作,比如都继承自System.Object。
CLS(公共语言规范):CTS的子集,规定语言必须支持的规则,保证跨语言调用。
CLR(公共语言运行时):执行.NET程序的虚拟机,负责JIT编译、GC、异常处理等。
dotNet数据库迁移使用过哪些
EF Core的Migrations最常用,此外还有FluentMigrator、DbUp。EF Core迁移的要点是:设计Model → Add-Migration 生成迁移文件 → Update-Database 应用。
说说常用的锁,lock是一种什么样的锁?
lock(Monitor):最常用的进程内互斥锁。
Mutex:可跨进程的互斥锁。
Semaphore / SemaphoreSlim:限制并发数量。
ReaderWriterLockSlim:读多写少场景,提升并发。
SpinLock:极短等待时用的自旋锁。
lock 是一种什么样的锁?
它是 互斥锁,同一时刻只允许一个线程进入临界区。
可重入,同一个线程可以多次进入,不会死锁。
本质是 C# 语法糖,底层是 Monitor.Enter / Exit。
基于对象的 同步块索引 实现,锁对象必须是引用类型。
性能比 Mutex 高很多,因为不用进内核态,适合进程内线程同步。
使用时注意:锁对象要私有、只读,临界区代码要短,避免死锁。
线程池的优点有哪些?又有哪些不足
降低资源开销:复用线程,避免频繁创建和销毁带来的性能损耗。
提升响应速度:任务到达时无需等待线程创建,直接分配空闲线程执行。
统一管理:限制并发线程数,防止系统因线程过多导致内存耗尽或 CPU 过载。
简化开发:开发者只需关注业务逻辑,不用自己维护线程生命周期。
不足之处:
不适合长时间阻塞任务:如果任务长时间阻塞(比如 I/O 或等待锁),会占满线程池线程,导致后续任务饥饿。
无法控制优先级:线程池中的线程都是默认优先级,无法针对关键任务提高优先级。
调试困难:任务执行异常时的堆栈和上下文不如显式创建的线程清晰。
可能引发死锁:例如任务内部又等待另一个被提交到线程池的任务完成,容易形成依赖死锁。
任务无优先级:所有任务 FIFO 执行,不支持优先级调度(需要自己实现)。
SQL优化的方法有哪些;
索引优化
在 WHERE、JOIN、ORDER BY、GROUP BY 的字段上建索引。
避免索引失效:不在索引列上用函数、隐式类型转换、LIKE '%xx' 前置模糊匹配。
查询语句优化
只查需要的列,不用 SELECT *。
尽量用 EXISTS 代替 IN(当子查询结果集大时)。
多表 JOIN 时用小结果集驱动大结果集。
避免重复查询,用 CTE 或临时表。
分页优化
深分页时不用 OFFSET 大偏移量,改用"游标查询"或"基于索引的排序后取 id 再关联"。
减少数据库操作
批量插入/更新,避免循环执行单条 SQL。
合理使用存储过程减少网络交互。
使用执行计划分析
EXPLAIN 查看扫描行数、访问类型(ALL 全表扫描要避免)、是否用到文件排序或临时表。
数据库设计优化
字段类型尽量小、简单(如 INT 优于 VARCHAR)。
适当反范式化,减少 JOIN。
大表考虑分区或分表。
事务与锁优化
控制事务大小,及时提交,避免长事务造成锁等待。
如果一个表10个字段,其中7个字段有索引咋处理
主库:只保留写操作必须的3个索引(比如主键、唯一约束、一个用于事务隔离的索引)。
从库:保留全部7个索引,甚至额外再加一些。
高频热数据(比如用户频繁查询的首页列表数据):直接放 Redis,不查数据库。
冷数据:保留完整索引,供偶尔的导出或报表查询使用。
分段:按时间分区,每天/每周一个分区。写操作先入消息队列,攒批写入当前分区;读操作根据查询条件路由到对应的分区。
docker的中间件有哪些
常用中间件镜像:Redis、MySQL、MongoDB、RabbitMQ、Nginx。
k8s在代码项目里使用的什么语言,怎么使用管理的
k8s通过YAML声明式配置管理,代码项目中常用Helm Chart打包,调用k8s API(Go/Java/.NET客户端)实现弹性伸缩或CI/CD集成。
redis有哪些数据类型
数据类型:String、Hash、List、Set、Sorted Set、BitMap、HyperLogLog、GEO等。
redis配置与调优
调优:内存(maxmemory + LRU淘汰)、持久化(RDB + AOF)、网络(tcp-backlog、timeout)、禁用危险命令(keys、flushall)。
MongoDB使用过哪些方法
find()(查询)、aggregate()(聚合)、updateMany()(批量更新)、createIndex()(建索引)、bulkWrite()(批量写入)
什么是git,有做过git托管仓库的开发吗
使用层面:我日常工作中广泛使用 Git,代码托管在 GitHub、GitLab 以及公司内部的 Gitea 上。包括创建仓库、分支策略(如 Git Flow、GitHub Flow)、PR/MR 评审、打标签、钩子配置等都很熟悉。
nginx是请求服务的方式有哪些,怎么做重定向
Nginx:主要做反向代理、负载均衡、静态服务器。重定向用return 301或rewrite指令。
liunx常用命令有哪些
ls、cd、grep、ps、top、netstat、chmod、tar、systemctl、docker、kubectl。
-----------------------------------前端--------------------------------------------------
Vue2和Vue3有什么区别
响应式原理
Vue2 用 Object.defineProperty,只能劫持对象已有属性,数组需要特殊处理。
Vue3 用 Proxy,可以代理整个对象,包括动态新增属性、删除属性、数组索引和 length 变化都直接监听。
API 风格
Vue2 以 Options API 为主(data、methods、computed 等)。
Vue3 引入 Composition API,逻辑可以按功能组织复用,代码更清晰,尤其适合复杂组件。
性能优化
Vue3 打包体积更小(支持 tree-shaking),编译时优化(静态提升、事件缓存、Block Tree 减少 diff 开销)。
同样的应用,Vue3 性能比 Vue2 提升明显。
TypeScript 支持
Vue3 源码用 TS 编写,对 TS 的集成更友好。
Vue2 对 TS 支持较弱,需要额外的装饰器或类组件库。
组件根节点
Vue2 组件必须有唯一根节点。
Vue3 支持多根节点(Fragment),减少无意义的包裹元素。
新内置组件
Vue3 提供了 Teleport(传送门,比如模态框挂载到 body)、Suspense(异步组件等待状态)。
生命周期
名字有变化:beforeDestroy 改为 beforeUnmount,destroyed 改为 unmounted。
Composition API 中对应钩子名称带 on 前缀。
其他细节
Vue3 移除了 on、on、on、off、$once 实例方法(事件总线不再内置,推荐 mitt 或 vue3 全局 API)。
移除了 filters,推荐用 computed 或方法替代。
v-for 和 v-if 优先级变化:Vue2 中 v-for 高于 v-if;Vue3 中 v-if 高于 v-for。
介绍前端的首屏加载、运行时渲染效率、构建产物优化的三个优化核心维度
一、首屏加载优化(让用户尽快看到内容)
核心目标是缩短白屏时间和可交互时间。
路由懒加载:按需加载页面组件,不一次性加载所有 JS。
CDN 加速:将静态资源部署到 CDN,减少网络往返时间。
压缩与 Gzip:JS/CSS/HTML 压缩,服务端开启 Gzip 或 Brotli。
图片优化:WebP 格式、懒加载、响应式图片(srcset)。
骨架屏 / 预渲染:先展示占位 UI,提升感知体验。
关键 CSS 内联:提取首屏所需的 CSS 内联到 HTML,非关键 CSS 异步加载。
预加载与预连接: 提前加载关键资源,preconnect 提前建立连接。
SSR 或 SSG:服务端渲染或静态站点生成,直接输出 HTML,减少客户端渲染工作量。
二、运行时渲染效率优化(让页面交互流畅)
核心是减少不必要的重绘重排,降低 CPU 和内存消耗。
虚拟 DOM 优化:合理设置组件 key,避免使用 index 作为 key;减少组件层级和 props 传递。
响应式粒度控制:Vue 中用 computed 缓存,避免模板中调用方法;shallowRef/shallowReactive 处理大对象。
列表虚拟滚动:对长列表只渲染可视区域(如 vue-virtual-scroller)。
防抖与节流:高频事件(滚动、输入、resize)使用防抖节流。
异步组件与 Suspense:非关键组件异步加载,减少初始渲染负担。
避免不必要的组件重渲染:合理使用 v-once、v-memo(Vue3),或者手动控制更新时机。
Web Worker:将计算密集型任务移到 Worker 线程,避免阻塞主线程。
三、构建产物优化(让最终生成的代码更小更合理)
核心是减小包体积,拆分模块,提高缓存命中率。
代码分割:动态 import 实现按路由或按需分割,避免单文件过大。
Tree Shaking:删除未使用的代码,注意副作用(sideEffects)配置。
资源压缩:Terser 压缩 JS,CSS 压缩,HTML 压缩;图片使用 imagemin 压缩。
依赖优化:替换大型库为轻量替代(如 day.js 替代 moment),按需引入(如 lodash-es)。
Bundle 分析:使用 webpack-bundle-analyzer 或 Vite 内置分析工具,定位大模块。
缓存策略:文件名加哈希(contenthash),实现长期缓存;分离第三方库到单独的 vendor chunk。
现代语法降级:通过 browserslist 和 babel 按目标环境编译,减少 polyfill 体积;对现代浏览器可直接输出 ES6+ 代码。
使用 Vite 等更快的构建工具:开发时利用原生 ESM,生产打包用 Rollup,产物优化更彻底。
Vite和Webpack在性能优化配置上有什么不同?
开发服务器启动与热更新
Webpack:需要打包整个应用,启动慢;热更新(HMR)也需要重新编译修改的模块及其依赖,大项目时会有明显延迟。
Vite:利用原生 ES 模块,启动时只做预构建(用 esbuild 将 CommonJS 转为 ESM),不打包,所以启动极快。热更新基于 ESM 的精确失效替换,只更新修改的模块,速度非常快。
生产构建优化
Webpack:使用 TerserPlugin 压缩 JS,CSS 提取用 MiniCssExtractPlugin,代码分割需要手动配置 splitChunks,Tree Shaking 依赖 sideEffects 和 usedExports。配置比较复杂,但控制力强。
Vite:底层用 Rollup 打包,优化配置更简洁。比如压缩直接用 build.minify(默认 esbuild,比 Terser 快很多),CSS 自动提取和压缩。代码分割通过 build.rollupOptions.output.manualChunks 配置,但默认已经做了合理的 vendor 拆分。
预加载与依赖优化
Webpack:需要手动配置 preload/prefetch 插件,或者用 webpackPreload 魔法注释。
Vite:提供 vite-plugin-preload 或内置 build.modulePreload 选项,自动生成预加载指令。
缓存策略
Webpack:通过 cache.type: 'filesystem' 开启持久化缓存,能极大提升二次构建速度,但需要显式配置。
Vite:默认开启 cacheDir(node_modules/.vite),依赖预构建缓存和文件系统缓存,几乎零配置。
静态资源处理
Webpack:需要配置 file-loader、url-loader、asset-module 等。
Vite:内置静态资源处理,import 图片等直接返回 URL,可以通过 ?url、?raw 等查询参数改变处理方式,更简洁。
环境变量与模式
Webpack:用 DefinePlugin 或 dotenv + 自定义。
Vite:内置 import.meta.env,支持 .env 文件,自动根据 mode 加载,更方便
在不使用浏览缓存的情况下,怎么在客户端本地存储用户数据
使用内存存储(变量)
将敏感数据保存在 JavaScript 运行时内存中(如全局变量、闭包、Map 对象)。页面关闭或刷新后数据即消失,且开发者虽然可以打断点看到,但相比持久化存储更难被长期窃取。适用于生命周期短的临时数据。
WebAssembly 内存
将数据保存在 Wasm 的线性内存中,JS 层无法直接读取,需要导出的函数才能访问。这比普通 JS 变量更隐蔽。
Service Worker + CacheStorage 并加密
CacheStorage 不是明文直接暴露在 Application 面板的 Storage 区域,但仍可被读取。配合加密同样可做到不可读。
不本地存储,改用短时效的 token + 后端会话
客户端只保存一个随机生成的、后端签名的短时效令牌(比如 JWT 但内容不存敏感信息),真正的用户数据全部保存在服务端。令牌即便被看到也毫无价值,且可随时失效。
Electron通信使用的什么
ipc与webContents通信
渲染进程 → preload → ipcRenderer → 主进程 → ipcMain → 底层API
底层API → ipcMain → 主进程 → ipcRenderer → preload → 渲染进程
Electron的一般项目结构是啥
electron有一个mian主进程和多个渲染进程(渲染进程至少有一个)
其中主进程与渲染进程需要preload进行通信。
preload是渲染进程与主进程进行通信的桥梁
主进程:控制应用生命周期,负责创建渲染进程,仅有一个。
渲染进程:每个窗口对应一个独立进程,支持Node.js和DOM API,数量可动态扩展。
js事件循环、闭包、原型链、继承
1.事件循环
JS 是单线程的,事件循环用来协调同步任务和异步任务。
同步任务直接在主线程执行栈中运行。
异步任务(如定时器、网络请求、Promise)会被挂起,完成后将回调放入任务队列。
事件循环不断检查:执行栈空时,从任务队列中取出回调放入执行栈执行。
任务队列分宏任务(setTimeout、I/O)和微任务(Promise.then、MutationObserver)。微任务优先级高于宏任务,每次宏任务结束后会清空所有微任务。
2.闭包
闭包是指函数能够记住并访问它的词法作用域,即使该函数在词法作用域之外执行。
形成条件:函数嵌套函数,内部函数引用了外部函数的变量。
作用:实现私有变量、模块化、缓存数据等。
注意:闭包会延长变量的生命周期,使用不当可能导致内存泄漏。
3.原型链
每个 JS 对象都有一个内部属性 [[Prototype]](通过 proto 或 Object.getPrototypeOf 访问),指向其原型对象。
当访问对象属性时,如果自身不存在,就会沿着原型链向上查找,直到找到或到达 null。
函数都有一个 prototype 属性,用于实例化对象时设置实例的原型。
原型链的顶端是 Object.prototype,再往上就是 null。
4.继承
在 JS 中,继承通过原型链实现。
原型链继承:子类的原型指向父类的实例。缺点:所有子类实例共享父类引用属性。
构造函数继承:在子类构造函数中调用父类构造函数(Parent.call(this))。解决引用共享,但无法继承父类原型上的方法。
组合继承:上述两者结合,最常用。
寄生组合继承:优化组合继承,避免两次调用父类构造函数。
ES6 class 继承:class Child extends Parent,底层仍是寄生组合继承,语法更清晰
虚拟DOM的理解
虚拟 dom 就是 vue 通过 js 对象渲染虚拟 dom 的,虚拟 dom 的 js 对象包含节点的类型、属性、子节点等信息,这些虚拟 dom 节点会构成一棵树形结构,用来表示整个页面的结构。
当 vue 组件更新时,会通过 diff 算法进行计算,diff 算法是先比较记录再批量更新操作。
diff 算法流程分别有(新 dom 树会和缓存的旧 dom 树进行比较)
根节点比较、逐层比较:从树的根节点开始,确定根节点是否相同、找出节点直接的差异(如果节点类型不同则会停止对子级节点比较,但只是节点属性、内容不同则会记录,并继续对子级的比较记录)。这只是 diff 算法的第一步,用于记录确定哪些部分需要更新。
同级比较:在同一级的节点直接进行比较、找出增删改的节点。
叶子节点比较:对叶子节点进行比较
key比较:如果节点有唯一标识符 key,则 diff 算法会使用这些表示来更精确的比较节点
https为什么比http更安全
加密传输:HTTP明文传输,HTTPS在HTTP下加了一层SSL/TLS,混合使用非对称加密(交换密钥)和对称加密(传输数据)。
身份验证:HTTPS通过CA证书验证服务器身份,防中间人攻击。
完整性保护:防止数据在传输过程中被篡改。
axios封装过没
通常封装成request.js,统一配置:baseURL、超时、拦截器(请求加token、响应统一错误处理)。还可以针对不同模块创建不同的axios实例。
微前端
将前端应用拆分为独立的小应用,组合成一个整体。核心要解决:子应用加载(动态script标签)、隔离(JS沙箱、CSS作用域)、通信(自定义事件或全局状态)。主流框架有qiankun、Module Federation、wujie。