Line 0: Parsing error: Cannot read property 'map' of undefined" - TypeScript Custom Hook
Line 0: Parsing error: Cannot read property 'map' of undefined" - TypeScript Custom Hook
我有一个错误“./src/hooks/usePagination.tsx Line 0: Parsing error: Cannot read 属性 'map' of undefined” 你知道是什么原因吗?我花了半个晚上在 stackoferflow 等上寻找答案,但多次尝试都没有成功。
首先我想到了我的数据格式,因为现在是
[
{"id":1,"firstName":"Cori","lastName":"Wescott","email":"cwescott0@etsy.com","gender":"Male","ip_address":"236.58.118.85"},
{"id":2,"firstName":"Teena","lastName":"Kedge","email":"tkedge1@ameblo.jp","gender":"Female","ip_address":"74.32.179.20"},
{"id":3,"firstName":"Englebert","lastName":"Menlove","email":"emenlove2@cmu.edu","gender":"Male","ip_address":"91.249.51.126"},
]
我更改了数据而不是 json,但没有帮助。后来我找了一个错误的标记、字母、字符等等——没有结果。最后,我的研究促使我阅读有关 npm 或其他包版本太旧的信息。呃我放弃了..
也许有人会发现问题。
function App() {
const [paginationState, paginationActions] = usePagination(dataEntries, 2);
return (
<div className="App">
<h2>Users</h2>
{ !paginationState.isBusy && <PaginatedTable dataEntries={paginationState.entries}/> }
<Pagination state={paginationState} actions={paginationActions}/>
</div>
);
}
export default App;
d.ts file
export interface User {
id: number
firstName: string
lastName: string
}
export interface PaginationState<T> {
lastPageIdx: number
actualPageIdx: number
entries: T[]
isBusy: boolean
}
export interface PaginationActions {
goToFirstPage: () => void
goToPrevPage: () => void
goToNextPage: () => void
goToLastPage: () => void
goToPage: (number: number) => void
}
自定义挂钩
function usePagination<T>(dataEntries: T[], elementsOnPage: number): [PaginationState<T>, PaginationActions] {
const [actualPageIdx, setActualPageIdx] = useState(1)
const lastPageIdx = Math.ceil(dataEntries.length / elementsOnPage)
const [isBusy, setIsBusy] = useState(false)
useEffect(() => {
setIsBusy(true)
let timer = setTimeout(() => {
setIsBusy(false)
clearTimeout(timer)
}, 333)
return () => {
clearTimeout(timer)
}
}, [actualPageIdx])
const entriesOnSelectedPage = () => {
const firstEntry = (actualPageIdx - 1) * elementsOnPage
const lastEntry = firstEntry + elementsOnPage
return dataEntries.slice(firstEntry, lastEntry)
}
const entries = entriesOnSelectedPage()
const goToFirstPage = () => {
setActualPageIdx(1)
}
const goToLastPage = () => {
setActualPageIdx(lastPageIdx)
}
const goToPage = (page: number) => {
setActualPageIdx(page)
}
const goToPrevPage = () => {
setActualPageIdx((actualPageIdx) => (actualPageIdx === 1 ? actualPageIdx : actualPageIdx - 1))
}
const goToNextPage = () => {
setActualPageIdx((actualPageIdx) =>
actualPageIdx === lastPageIdx ? actualPageIdx : actualPageIdx + 1
)
}
return [
{
actualPageIdx,
lastPageIdx,
entries,
isBusy
},
{
goToFirstPage,
goToPrevPage,
goToPage,
goToNextPage,
goToLastPage,
},
]
}
分页
interface PaginationProps {
state: PaginationState<User>
actions: PaginationActions
}
const Pagination: FC<PaginationProps> = ({ state, actions }) => {
const pageNumbers = []
for (let i = 1; i <= state.lastPageIdx; i++) {
pageNumbers.push(i)
}
const renderPagination = pageNumbers.map((number) => (
<button
key={number}
onClick={() => actions.goToPage(number)}
className={
state.actualPageIdx === number ? styles.actualIdxStyle : styles.paginationStyle
}
>
{number}
</button>
))
return (
<div className={styles.paginationContainer}>
<button onClick={actions.goToFirstPage}>GO TO FIRST</button>
<button onClick={actions.goToPrevPage} data-testid="goToPrevPage">
<i className="fas fa-chevron-left"></i>
</button>
<div data-testid="goToPageButtons">{renderPagination}</div>
<button onClick={actions.goToNextPage} data-testid="goToNextPage">
<i className="fas fa-chevron-right"></i>
</button>
<button onClick={actions.goToLastPage}>GO TO LAST</button>
</div>
)
}
分页表
interface PaginatedTableProps {
dataEntries: User[]
}
const PaginatedTable: FC<PaginatedTableProps> = ({ dataEntries }) => {
const tableEntry = dataEntries && dataEntries.map(({ id, firstName, lastName }) => (
<div key={id} className={styles.tableStyle}>
<p>
{id}{'. '}
</p>
<p>
{firstName} {lastName}
</p>
</div>
))
return (
<div>
<div className={`${styles.tableStyle} ${styles.headStyle}`}>
<p>No.</p>
<p>Name</p>
</div>
<div data-testid="users">{tableEntry}</div>
</div>
)
}
可以确认@radicand 在上面的评论中提到的内容。
以下软件包需要降级到这些版本:
"@typescript-eslint/eslint-plugin": "3.9.1",
"@typescript-eslint/parser": "3.9.1",
"typescript": "3.9.2"
Typescript 4.x 和 eslint 4.x 包在 3.4.3 中无法与 react-scripts 一起使用。
我有一个错误“./src/hooks/usePagination.tsx Line 0: Parsing error: Cannot read 属性 'map' of undefined” 你知道是什么原因吗?我花了半个晚上在 stackoferflow 等上寻找答案,但多次尝试都没有成功。
首先我想到了我的数据格式,因为现在是
[
{"id":1,"firstName":"Cori","lastName":"Wescott","email":"cwescott0@etsy.com","gender":"Male","ip_address":"236.58.118.85"},
{"id":2,"firstName":"Teena","lastName":"Kedge","email":"tkedge1@ameblo.jp","gender":"Female","ip_address":"74.32.179.20"},
{"id":3,"firstName":"Englebert","lastName":"Menlove","email":"emenlove2@cmu.edu","gender":"Male","ip_address":"91.249.51.126"},
]
我更改了数据而不是 json,但没有帮助。后来我找了一个错误的标记、字母、字符等等——没有结果。最后,我的研究促使我阅读有关 npm 或其他包版本太旧的信息。呃我放弃了..
也许有人会发现问题。
function App() {
const [paginationState, paginationActions] = usePagination(dataEntries, 2);
return (
<div className="App">
<h2>Users</h2>
{ !paginationState.isBusy && <PaginatedTable dataEntries={paginationState.entries}/> }
<Pagination state={paginationState} actions={paginationActions}/>
</div>
);
}
export default App;
d.ts file
export interface User {
id: number
firstName: string
lastName: string
}
export interface PaginationState<T> {
lastPageIdx: number
actualPageIdx: number
entries: T[]
isBusy: boolean
}
export interface PaginationActions {
goToFirstPage: () => void
goToPrevPage: () => void
goToNextPage: () => void
goToLastPage: () => void
goToPage: (number: number) => void
}
自定义挂钩
function usePagination<T>(dataEntries: T[], elementsOnPage: number): [PaginationState<T>, PaginationActions] {
const [actualPageIdx, setActualPageIdx] = useState(1)
const lastPageIdx = Math.ceil(dataEntries.length / elementsOnPage)
const [isBusy, setIsBusy] = useState(false)
useEffect(() => {
setIsBusy(true)
let timer = setTimeout(() => {
setIsBusy(false)
clearTimeout(timer)
}, 333)
return () => {
clearTimeout(timer)
}
}, [actualPageIdx])
const entriesOnSelectedPage = () => {
const firstEntry = (actualPageIdx - 1) * elementsOnPage
const lastEntry = firstEntry + elementsOnPage
return dataEntries.slice(firstEntry, lastEntry)
}
const entries = entriesOnSelectedPage()
const goToFirstPage = () => {
setActualPageIdx(1)
}
const goToLastPage = () => {
setActualPageIdx(lastPageIdx)
}
const goToPage = (page: number) => {
setActualPageIdx(page)
}
const goToPrevPage = () => {
setActualPageIdx((actualPageIdx) => (actualPageIdx === 1 ? actualPageIdx : actualPageIdx - 1))
}
const goToNextPage = () => {
setActualPageIdx((actualPageIdx) =>
actualPageIdx === lastPageIdx ? actualPageIdx : actualPageIdx + 1
)
}
return [
{
actualPageIdx,
lastPageIdx,
entries,
isBusy
},
{
goToFirstPage,
goToPrevPage,
goToPage,
goToNextPage,
goToLastPage,
},
]
}
分页
interface PaginationProps {
state: PaginationState<User>
actions: PaginationActions
}
const Pagination: FC<PaginationProps> = ({ state, actions }) => {
const pageNumbers = []
for (let i = 1; i <= state.lastPageIdx; i++) {
pageNumbers.push(i)
}
const renderPagination = pageNumbers.map((number) => (
<button
key={number}
onClick={() => actions.goToPage(number)}
className={
state.actualPageIdx === number ? styles.actualIdxStyle : styles.paginationStyle
}
>
{number}
</button>
))
return (
<div className={styles.paginationContainer}>
<button onClick={actions.goToFirstPage}>GO TO FIRST</button>
<button onClick={actions.goToPrevPage} data-testid="goToPrevPage">
<i className="fas fa-chevron-left"></i>
</button>
<div data-testid="goToPageButtons">{renderPagination}</div>
<button onClick={actions.goToNextPage} data-testid="goToNextPage">
<i className="fas fa-chevron-right"></i>
</button>
<button onClick={actions.goToLastPage}>GO TO LAST</button>
</div>
)
}
分页表
interface PaginatedTableProps {
dataEntries: User[]
}
const PaginatedTable: FC<PaginatedTableProps> = ({ dataEntries }) => {
const tableEntry = dataEntries && dataEntries.map(({ id, firstName, lastName }) => (
<div key={id} className={styles.tableStyle}>
<p>
{id}{'. '}
</p>
<p>
{firstName} {lastName}
</p>
</div>
))
return (
<div>
<div className={`${styles.tableStyle} ${styles.headStyle}`}>
<p>No.</p>
<p>Name</p>
</div>
<div data-testid="users">{tableEntry}</div>
</div>
)
}
可以确认@radicand 在上面的评论中提到的内容。 以下软件包需要降级到这些版本:
"@typescript-eslint/eslint-plugin": "3.9.1",
"@typescript-eslint/parser": "3.9.1",
"typescript": "3.9.2"
Typescript 4.x 和 eslint 4.x 包在 3.4.3 中无法与 react-scripts 一起使用。