随手记第二弹

引言

当谈到前端开发时, 无论是初学者还是经验丰富的开发者, 都能够感受到这个领域的迅速发展和变化。前端技术不断演进, 新的框架和工具层出不穷, 这使得我们需要不断学习和掌握新的知识点。然而, 有时候我们会遇到一些零散的小知识点, 它们虽然看似微小, 但却能为我们的工作和学习带来巨大的帮助。

在本专栏中, 我将总结一些我平时 随手 记录小知识点。这些小的知识点有的是平常项目中遇到的, 有的则是看了一些大佬们分享的博客后摘抄、总结的; 尽管它们可能篇幅较小, 但它们的实际应用价值却是不可忽视的。我会选择一些具有代表性的知识点, 并提供简洁明了的解释和示例, 以便大家能够轻松理解和应用。

最后如果, 如果你对本专栏的知识感兴趣, 欢迎👏🏻👏🏻 点击订阅!!! 无论你是新手还是有经验的开发者, 都希望这些小知识点能够对你有所启发和帮助!!!

一、vscode 合并多个窗口

在实际开发过程中, 我们可能得同时开多个项目, 并频繁切换, 这时如果可以将多个 vscode 窗口进行合并, 通过 tabs 进行切换那就炒鸡方便咯

那么上面👆🏻效果要如何配置呢?

  1. 进入配置文件
  1. 搜索 window.native, 并勾选 Native Tabs
  1. 合并所有窗口到一个窗口(以 tabs 形式进行展示)

二、apollo-server-koa 和 @koa/cors 冲突问题

昆仑虚 中, 使用 apollo-server-koa 来为 koa 接入 graphql 同时通过 @koa/cors 来设置跨域问题

@koa/cors 设置过程中, 发现不管怎么设置跨域配置都无法生效, 经过排查发现 apollo-server-koa 默认也开启了 cors 配置, 导致 @koa/cors 的配置被覆盖了

解决办法其实也简单, 只要关闭 apollo-server-koacors 配置即可:

js 复制代码
// 创建服务
const server = new ApolloServer({
  // ...
});

// 启动服务
await server.start();

// 配置中间件
server.applyMiddleware({
  app,
  cors: false, // 不开启 cors 由 src/app/middleware/cross.js 统一控制
});

三、qs 中 url 参数解析错误记录

项目中使用 qs 工具库 来处理 url 参数, 在解析 url 参数过程中出现错误, 经排查发现是 qs 对于解析对象的层级以及数组长度做了限制....

  1. qs 通过 depth 来限制对象的深度, 该值默认为 5 超出部分将会丢失
  2. qs 通过 arrayLimit 来限制数组长度, 当数组长度超出时, 会将数组解析为对象; 就是当个数组长度大于 arrayLimit, 解析出来的会是一个对象, arrayLimit 默认值为 20
js 复制代码
const urlParams = qs.parse(searchStr, {
  depth: 256,
  arrayLimit: Infinity,
})

四、深拷贝方法

简单介绍几个深拷贝方法, 更多可查阅 《八股文: 讲讲什么是浅拷贝、深拷贝?》

  1. 使用工具库 lodashcloneDeep 方法
  2. 使用 JSON 方法:
js 复制代码
JSON.parse(JSON.stringify(obj))

需要注意的是, 该方法对于循环引用的数据将会抛出错误, 并且对于很多 JS 特殊的数据, 将会忽略、或者抛出错误, 因为 JSON 并不是 JS 特有的, 对于特殊数据是不支持的

  1. 使用 structuredClone, 该方法是一个全局的 API 可用于对数据进行 深拷贝, 同时还支持循环引用
js 复制代码
const base = {
  name: '张三',
  age: 18,
}

const obj = { base }

obj.obj = obj

const res = structuredClone(obj) 

注意: 使用 structuredClone 进行拷贝, 如果有个属性值是个函数, 方法会抛出错误

js 复制代码
// DOMException [DataCloneError]: () => {} could not be cloned.
const res = structuredClone({
  add: () => {}
})

有关 structuredClone 更多信息查看 MDN

  1. 手撸, 具体代码参考: 《八股文: 讲讲什么是浅拷贝、深拷贝?》

五、chrome 全面删除 Event.path

参考: chrome 搞事,下个月全面删除 Event.path

  1. 一句话总结就是, chrome 109 也就是(2023-01-10)删除了事件对象 Eventpath 属性
  2. path 属性是啥? 它是事件冒泡经过的节点组成的数组, 其实就是由根节点到触发事件的目标节点的一个完整路径
  1. 其实 Eventpath 属性并不是一个标准的属性, 这里我们可以通过 Event.composedPath() 来获取事件经过的路径, 该方法是一个标准方法, 基本所有浏览器都是支持的!!

  2. 如果你的项目比较老, 使用了 Event.path 或者并不确定是否调用了该属性, 那么又可以怎么处理, 才能尽量避免意外错误出现呢? 其实可以参考下面代码: 针对全局 Event.prototype 设置 path 属性的 getter 方法

js 复制代码
Object.defineProperty(Event.prototype, "path", {
  get() {
    return this.composedPath();
  },
});

六、为什么不推荐 JSX 中使用 &&

参考: React 开发不推荐使用 &&

如下代码: 如果 condition0, 则在 UI 中显示 0

js 复制代码
condition && <ConditionalComponent />

七、监听全屏事件

JS 中可通过 fullscreenchange 来监听页面上全屏切换变更操作, 切换到全屏或者退出全屏都能够被捕获到

js 复制代码
useEffect(() => {
  const onFullScreenChange = () => {
    setIsFullScreen((old) => {
      if (old) {
        onExitScreen()
      } else {
        onFullScreen()
      }
      return !old
    })
  }
  
  document.addEventListener('fullscreenchange', onFullScreenChange)

  return () => document.removeEventListener('fullscreenchange', onFullScreenChange)
}, [onExitScreen, onFullScreen])

八、字符串拆分

有一串字符串, 由多组 数量词 + 名词 组成, 需要将其拆分成一个数组, 数组每个元素都是一组 数量词 + 名词

  • 示例 1:

输入: "1头猪2头驴3头羊"
输出: ["1头猪", "2头驴", "3头羊"]

  • 示例 2:

输入: "10头猪20头驴30头羊"
输出: ["10头猪", "20头驴", "30头羊"]

解答如下: 具体思路看注释

js 复制代码
// 通过 String.prototype.split 直接来拆分字符串, 参数为正则
// 正则 (?=\d) 表示后面存在数字, (?<=[^\d]) 则表示前面存在非数字
// 这里使用了预前(?=) 预后表达式(?<=)
const parse = (str) => {
  return str.split(/(?=\d)(?<=[^\d])/)
}

parse("1头猪2头驴3头羊") // ['1头猪', '2头驴', '3头羊']
parse("10头猪20头驴30头羊") // ['10头猪', '20头驴', '30头羊']

九、require.context 注意事项

  1. require.context 是一个 webpackapi ,通过该函数可以获取到一个特定的上下文, 主要用来实现自动化导入模块, 如下代码可以批量引入项目中所有符合正则的 js 文件
js 复制代码
// 1. 加载所有 *.store.js 文件
const files = require.context('.', true, /\.store\.ts/);

// 2. 收集 reducer、action
export const { reducer, actions } = files.keys().reduce((total, filePath) => {
  // 2.1 加载 *.store.js 文件导出的内容
  const slice = files(filePath).default;

  // 2.2 组装数据
  total.reducer[slice.name] = slice.reducer;
  total.actions[slice.name] = slice.actions;
  return total;
}, { reducer: {}, actions: {} };
  1. 但是在使用 require.context 时, 第三参数(正则)有试用限制的:
  • 不支持 RegExp 只支持字面量形式
  • 必须是静态的, 而不能是一个变量
js 复制代码
// 无效, 因为不支持 `RegExp` 只支持字面量形式
require.context('./locales', true, new RegExp('zh-CN\.yam'))

// 无效, 因为必须是静态的, 而不能是一个变量
const reg = /zh-CN\.yam/
require.context('./locales', true, reg)
  1. 那么我们如果我想要根据不同环境加载不同的内容可以怎么做呢? 这里可以从第一参数如手:
  • 整一个变量, 根据不同环境设置相应的值
  • require.context 第一个参数使用变量, webpack 在编译时就会将对应变量替换为相应的字符串

参考

十、WIFI 接入软路由(openWrt) 个别网站无法打开

前段时间为家里路由器接入了软路由(《树莓派 4B 做软路由🔥》), 在使用过程中发现 react.dev 无法正常访问, 错误代码: DNS_PROBE_FINISHED_NXDOMAIN

经排查发现问题出在 DNS 上, 将 openWrt 接口设置中的 DNS 改为 114.114.114.114 就恢复正常了

本文到此结束, 欢迎👏🏻订阅本栏目, 敬请期待下一弹...

相关推荐
Tiffany_Ho4 分钟前
【TypeScript】知识点梳理(三)
前端·typescript
安冬的码畜日常1 小时前
【D3.js in Action 3 精译_029】3.5 给 D3 条形图加注图表标签(上)
开发语言·前端·javascript·信息可视化·数据可视化·d3.js
太阳花ˉ1 小时前
html+css+js实现step进度条效果
javascript·css·html
小白学习日记2 小时前
【复习】HTML常用标签<table>
前端·html
john_hjy2 小时前
11. 异步编程
运维·服务器·javascript
风清扬_jd2 小时前
Chromium 中JavaScript Fetch API接口c++代码实现(二)
javascript·c++·chrome
丁总学Java2 小时前
微信小程序-npm支持-如何使用npm包
前端·微信小程序·npm·node.js
yanlele3 小时前
前瞻 - 盘点 ES2025 已经定稿的语法规范
前端·javascript·代码规范
It'sMyGo3 小时前
Javascript数组研究09_Array.prototype[Symbol.unscopables]
开发语言·javascript·原型模式