Next.js應(yīng)用轉(zhuǎn)換為TypeScript方法demo
引言
如果你不確定TypeScript是什么,它基本上是一種建立在JavaScript之上的類型化語言。所有的JavaScript都是有效的TypeScript,但反之亦然。你可以在這里閱讀更多關(guān)于它的信息,以及它如何與React/Next.js一起工作。你可以在你的項(xiàng)目中輕松地設(shè)置TypeScript,只需幾個(gè)命令和一些小的重構(gòu),在這篇文章中,我將告訴你如何做!
添加TypeScript
最初添加TypeScript到你的Next.js項(xiàng)目很簡(jiǎn)單。只需通過運(yùn)行以下命令來安裝TypeScript。
npm install --save-dev typescript @types/react @types/node
然后,在你的項(xiàng)目根部創(chuàng)建一個(gè)空的 tsconfig.json文件,然后在你的項(xiàng)目的根部創(chuàng)建一個(gè)空的你可以手動(dòng)完成,或者在你的項(xiàng)目根部運(yùn)行以下命令。
touch tsconfig.json
然后使用 "npm run dev "啟動(dòng)你的項(xiàng)目,你應(yīng)該在控制臺(tái)中看到以下一行。
Next.js會(huì)在你的 tsconfig.json文件中加入一些預(yù)選的選項(xiàng)。我推薦的一個(gè)選項(xiàng)是在第11行將strict設(shè)置為true,以啟用TypeScript的一些更嚴(yán)格的打字選項(xiàng),但并不是必須的。
重構(gòu)
你會(huì)發(fā)現(xiàn)你的項(xiàng)目仍然運(yùn)行良好,這是因?yàn)槟闼械?js或.jsx文件仍然是JavaScript。要將它們切換到TypeScript,只需將文件擴(kuò)展名改為.ts或.tsx。
你現(xiàn)在可能又會(huì)遇到一些錯(cuò)誤,所以我將討論一些常見的錯(cuò)誤。這里有一個(gè)JavaScript組件的例子,它使用API調(diào)用檢索一些有趣的事實(shí),并使用SSR渲染它們。這個(gè)組件使用的是TailwindCSS的樣式,我強(qiáng)烈建議你看一下它。
import React, { useState } from 'react'; import axios from 'axios'; function fetchFact() { //Just a simple get request which gets back a fact in a JSON object return axios .get('https://uselessfacts.jsph.pl//random.json?language=en') .then((res) => { return res.data; }); } //TS7031: Binding element 'facts' implicitly has an 'any' type. export default function SSRExample({ facts }) { return ( <div className="flex h-screen w-screen flex-col items-center justify-center bg-white text-3xl text-white"> <p className="mb-10 rounded bg-neutral-800 p-10"> Heres some fun facts! </p> <ul className="flex max-w-2xl flex-col gap-5 rounded bg-neutral-800 p-10 shadow"> { //TS7031: Binding element 'id' implicitly has an 'any' type. //TS7031: Binding element 'text' implicitly has an 'any' type. facts.map(({ id, text }) => ( <li key={id}>{text}</li> )) } </ul> </div> ); } //TS7031: Binding element 'query' implicitly has an 'any' type. export async function getServerSideProps({ query }) { const { count } = query; const promises = [...new Array(Number(count))].map(() => fetchFact()); const facts = await Promise.all(promises); return { props: { facts, }, }; }
輸入道具
我在這個(gè)組件中得到的第一個(gè)錯(cuò)誤是,TypeScript不知道我的道具是什么類型。這在嚴(yán)格模式下會(huì)導(dǎo)致一個(gè)錯(cuò)誤,因?yàn)槲覀儾辉试S使用任何道具。為了解決這個(gè)問題,我只需要為我的道具添加一個(gè)類型。
type Fact = { id: string; text: string; }; type SSRExampleProps = { facts: Fact[]; }; //TS7031: Binding element 'facts' implicitly has an 'any' type. export default function SSRExample({ facts }: SSRExampleProps) { ... }
現(xiàn)在,來自初始道具的錯(cuò)誤,以及試圖映射事實(shí)數(shù)組的錯(cuò)誤都消失了。
需要注意的一件事是,我們?cè)谶@里使用了對(duì)象重構(gòu),這可能會(huì)掩蓋props是一個(gè)函數(shù)參數(shù)的事實(shí)。你的props將永遠(yuǎn)是一個(gè)包含你提供的任何props的對(duì)象,而不是直接參數(shù)。
export default function SSRExample({ facts }: { facts: { id: string; text: string }[]}) export default function SSRExample(facts: { id: string; text: string }[])
GetXProps
這段代碼中的另一個(gè)問題是,我們的"getServerSideProps()"函數(shù)不知道它的參數(shù)是什么。如果你對(duì)這個(gè)函數(shù)不熟悉,請(qǐng)查看我們這里的文章,了解服務(wù)器端渲染的介紹。如果你使用getStaticProps或getStaticPaths,情況也會(huì)一樣。
為了解決這個(gè)問題,Next.js為每一種和它們的參數(shù)提供了類型。需要注意的一點(diǎn)是,這些類型是針對(duì)箭頭函數(shù)的,所以如果你使用的是正常的函數(shù)體,你就必須重構(gòu)你的函數(shù)。
下面是我們更新的 getServerSideProps():
export const getServerSideProps: GetServerSideProps = async ({ query }) => { const { count } = query; const promises = [...new Array(Number(count))].map(() => fetchFact()); const facts = await Promise.all(promises); return { props: { facts, }, }; };
還有一個(gè)小細(xì)節(jié)是,我們的 ***fetchFact()***函數(shù)沒有一個(gè)類型。在Next.js函數(shù)的交互方式下,這并沒有造成任何問題,但如果我希望在其他地方使用該函數(shù),就會(huì)遇到問題。由于我們已經(jīng)為這個(gè)事實(shí)做了類型,重構(gòu)這個(gè)事實(shí)很簡(jiǎn)單。
function fetchFact(): Promise<Fact> { //Just a simple get request which gets back a fact in a JSON object return axios .get('https://uselessfacts.jsph.pl//random.json?language=en') .then((res) => { return res.data; }); }
狀態(tài)
將類型添加到一個(gè) ***useState()***鉤子添加類型可以通過向函數(shù)提供一個(gè)類型參數(shù)來完成。我對(duì)前面的例子進(jìn)行了重構(gòu),只允許點(diǎn)擊一個(gè)按鈕來獲取一個(gè)額外的事實(shí),并將這些額外的事實(shí)存儲(chǔ)在狀態(tài)中。
export default function SSRExample({ facts }: SSRExampleProps) { const [extraFacts, setExtraFacts] = useState<Fact[]>([]); const getAnotherFact = () => { fetchFact().then((fact) => { setExtraFacts((oldValue) => [...oldValue, fact]); }); }; return ( <div className="flex h-screen w-screen flex-col items-center justify-center bg-white text-3xl text-white"> <p className="mb-10 rounded bg-neutral-800 p-10"> Heres some fun facts! </p> <ul className="flex max-w-2xl flex-col gap-5 rounded bg-neutral-800 p-10 shadow"> { //TS7031: Binding element 'id' implicitly has an 'any' type. //TS7031: Binding element 'text' implicitly has an 'any' type. [...facts, ...extraFacts].map(({ id, text }) => ( <li key={id}>{text}</li> )) } <li> <button className="rounded bg-neutral-900 p-5 shadow" onClick={() => getAnotherFact()}> More </button> </li> </ul> </div> ); }
TypeScript會(huì)盡力從你的狀態(tài)初始值中推斷出類型,但對(duì)于像這個(gè)事實(shí)數(shù)組這樣更復(fù)雜的例子,我們必須包括類型參數(shù)。
希望這些例子足以幫助你在Next.js項(xiàng)目中開始使用TypeScript。TypeScript是一種非常有用的語言,可以幫助你寫出更干凈、更正確的代碼,更多關(guān)于Next.js轉(zhuǎn)換為TypeScript的資料請(qǐng)關(guān)注腳本之家其它相關(guān)文章!
相關(guān)文章
查詢綁定數(shù)據(jù)島的表格中的文本并修改顯示方式的js代碼
查詢綁定數(shù)據(jù)島的表格中的文本并修改顯示方式的js代碼2009-12-12Three.js實(shí)現(xiàn)3D機(jī)房效果
這篇文章主要為大家詳細(xì)介紹了Three.js實(shí)現(xiàn)3D機(jī)房效果,具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2018-12-12深入理解JavaScript系列(10) JavaScript核心(晉級(jí)高手必讀篇)
本篇是ECMA-262-3 in detail系列的一個(gè)概述(本人后續(xù)會(huì)翻譯整理這些文章到本系列(第11-19章)。每個(gè)章節(jié)都有一個(gè)更詳細(xì)的內(nèi)容鏈接,你可以繼續(xù)讀一下每個(gè)章節(jié)對(duì)應(yīng)的詳細(xì)內(nèi)容鏈接進(jìn)行更深入的了解2012-01-01JavaScript中不可忽略的Symbol的盤點(diǎn)
Symbol類型的出現(xiàn),為每個(gè)屬性賦予了獨(dú)一無二的標(biāo)識(shí)符,無論項(xiàng)目多么復(fù)雜,Symbol都能確保屬性鍵的絕對(duì)唯一性,下面我們就來看看JavaScript中那些不可忽略的Symbol吧2024-12-12js addDqmForPP給標(biāo)簽內(nèi)屬性值加上雙引號(hào)的函數(shù)
這篇文章主要介紹了js addDqmForPP給標(biāo)簽內(nèi)屬性值加上雙引號(hào)的函數(shù),需要的朋友可以參考下2016-12-12JS+HTML5本地存儲(chǔ)Localstorage實(shí)現(xiàn)注冊(cè)登錄及驗(yàn)證功能示例
這篇文章主要介紹了JS+HTML5本地存儲(chǔ)Localstorage實(shí)現(xiàn)注冊(cè)登錄及驗(yàn)證功能,結(jié)合實(shí)例形式分析了基于JS+HTML5本地存儲(chǔ)Localstorage實(shí)現(xiàn)注冊(cè)登錄及驗(yàn)證相關(guān)操作技巧,需要的朋友可以參考下2020-02-02JavaScript通如何過RGraph實(shí)現(xiàn)動(dòng)態(tài)儀表盤
這篇文章主要介紹了JavaScript通如何過RGraph實(shí)現(xiàn)動(dòng)態(tài)儀表盤,文中通過示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友可以參考下2020-10-10