正如文档中所述,useCallback返回一个memoized回调.
传递内联回调和一组输入.useCallback将返回一个回忆的memoized版本,该版本仅在其中一个输入发生更改时才会更改.这在将回调传递给优化的子组件时非常有用,这些子组件依赖于引用相等性来防止不必要的渲染(例如,shouldComponentUpdate).
const memoizedCallback = useCallback(
() => {
doSomething(a, b);
},
[a, b],
);
Run Code Online (Sandbox Code Playgroud)
但是它如何工作以及在React中最好使用它?
我正在尝试使用新的react useReducer API来获取一些数据,并停留在需要异步获取的阶段。我只是不知道如何:/
如何将数据获取放置在switch语句中,或者这不是应该完成的方式?
import React from 'react'
const ProfileContext = React.createContext()
const initialState = {
data: false
}
let reducer = async (state, action) => {
switch (action.type) {
case 'unload':
return initialState
case 'reload':
return { data: reloadProfile() } //how to do it???
}
}
const reloadProfile = async () => {
try {
let profileData = await fetch('/profile')
profileData = await profileData.json()
return profileData
} catch (error) {
console.log(error)
}
}
function ProfileContextProvider(props) {
let [profile, profileR] …Run Code Online (Sandbox Code Playgroud) 我不明白为什么当我使用setTimeout函数时我的react组件启动到无限的console.log.一切正常,但PC开始落后于地狱.有些人说超时功能会改变我的状态和rerender组件,设置新的计时器等等.现在我需要了解如何清除它是正确的.
export default function Loading() {
// if data fetching is slow, after 1 sec i will show some loading animation
const [showLoading, setShowLoading] = useState(true)
let timer1 = setTimeout(() => setShowLoading(true), 1000)
console.log('this message will render every second')
return 1
}
Run Code Online (Sandbox Code Playgroud)
清除不同版本的代码无助于:
const [showLoading, setShowLoading] = useState(true)
let timer1 = setTimeout(() => setShowLoading(true), 1000)
useEffect(
() => {
return () => {
clearTimeout(timer1)
}
},
[showLoading]
)
Run Code Online (Sandbox Code Playgroud) 大多数时候对我来说,需要动态检查来验证 fetch 响应。我在想,这可以用用户定义的 typeguard 以通用方式完成,用于具有多个 props 和附加检查的任何类型的对象,因此可以使用以下内容:
// ================= shared exported =================
type Writer = {
name: string
age: number
}
type Book = {
id: number
name: string
tags: string[] | null
writers: Writer[]
}
// function to check object with multiple props general shape, to not do it by hand
function ofType<T>(obj: any): obj is T {
if (!obj) return false;
// how to?
return true // or false
}
// ================= used and defined …Run Code Online (Sandbox Code Playgroud) 有没有办法从文字类型中选择(或任何其他解决方案)以连接到主角色界面?
原因是,如果我将来要更改或删除角色中的某些内容,我可以看到需要更改/删除它的位置。
游乐场。
type Roles = 'admin' | 'user' | 'guest'
// no connection to Roles
type ApiRoute = { roles: 'admin' | 'user' }
// how to?
type ApiRouteWithCheck = { roles: Pick<Roles, 'admin' | 'user'> }
Run Code Online (Sandbox Code Playgroud) 我想允许 data!.id
错误:
警告禁止非空断言@typescript-eslint/no-non-null-assertion
当前配置:
module.exports = {
parser: '@typescript-eslint/parser',
extends: [
'eslint:recommended',
'plugin:jsx-a11y/recommended',
'plugin:@typescript-eslint/eslint-recommended',
'plugin:@typescript-eslint/recommended',
'plugin:react/recommended',
'prettier/@typescript-eslint',
'plugin:prettier/recommended'
],
plugins: ['react-hooks'],
parserOptions: {
ecmaVersion: 2020,
sourceType: 'module',
ecmaFeatures: {
jsx: true
}
},
rules: {
'@typescript-eslint/ban-ts-ignore': 0,
'@typescript-eslint/no-explicit-any': 0,
'@typescript-eslint/consistent-type-assertions': ['warn', { assertionStyle: 'as' }],
eqeqeq: 1,
'react/prop-types': 0,
'@typescript-eslint/camelcase': 0,
'react-hooks/rules-of-hooks': 'error',
'react-hooks/exhaustive-deps': 'warn'
},
globals: {
React: 'writable'
}
}
Run Code Online (Sandbox Code Playgroud) 我想禁用未使用的参数警告,但保留“未使用的变量”警告。
对于此代码:
const Query = objectType({
name: 'Query',
definition(t) {
t.field('test', {
type: 'Test',
resolve: (root, args, ctx) => {
const x = 1
return { id: 1, time: new Date().toString() }
},
})
},
})
Run Code Online (Sandbox Code Playgroud)
我收到警告:
26:17 warning 'root' is defined but never used @typescript-eslint/no-unused-vars
26:23 warning 'args' is defined but never used @typescript-eslint/no-unused-vars
26:29 warning 'ctx' is defined but never used @typescript-eslint/no-unused-vars
27:15 warning 'x' is assigned a value but never used @typescript-eslint/no-unused-vars
Run Code Online (Sandbox Code Playgroud)
eslint 配置:
module.exports = { …Run Code Online (Sandbox Code Playgroud) 在我的客户端,我这样做:
useEffect(() => {
socket.emit('login', myLoginCode)
}, [])
Run Code Online (Sandbox Code Playgroud)
在服务器端,我做了这个:
app.get('login', (req, res) => {
const cookieProtected = {
maxAge: 946080000000,
httpOnly: true,
secure: true,
sameSite: true
}
res.cookie('id', login, cookieProtected)
res.cookie('session', encryptSession, cookieProtected)
res.cookie('logged', 'true', {
maxAge: 946080000000,
secure: true,
sameSite: true
})
})
Run Code Online (Sandbox Code Playgroud)
但是我怎么能用套接字做同样的事情呢?
socket.on('login', loginCode => {
// How to to place cookies in user browser from here?
}
Run Code Online (Sandbox Code Playgroud)
也许有一种方法可以使用socket.emit发送标头?
我收到此错误:
无法在已卸载的组件上执行React状态更新。这是空操作,但它表明应用程序中发生内存泄漏。要修复,请取消使用useEffect清理功能中的所有订阅和异步任务。
当开始获取数据并卸载组件时,但是函数试图更新已卸载组件的状态。
解决此问题的最佳方法是什么?
default function Test() {
const [notSeenAmount, setNotSeenAmount] = useState(false)
useEffect(() => {
let timer = setInterval(updateNotSeenAmount, 2000)
return () => clearInterval(timer)
}, [])
async function updateNotSeenAmount() {
let data // here i fetch data
setNotSeenAmount(data) // here is problem. If component was unmounted, i get error.
}
async function anotherFunction() {
updateNotSeenAmount() //it can trigger update too
}
return <button onClick={updateNotSeenAmount}>Push me</button> //update can be triggered manually
}
Run Code Online (Sandbox Code Playgroud) reactjs ×5
react-hooks ×4
typescript ×3
eslint ×2
javascript ×2
express ×1
settimeout ×1
socket.io ×1