此文章適合剛接觸react 項目小白童鞋 項目搭建
create-react-app
# https://www.html.cn/create-react-app/docs/adding-typescript/ 官檔
Trap
typescript 安裝依賴需要安裝對應ts 版本
建議先提取webpack.config.js 文件
引入 less 需要修改對應配置
目錄
1、安裝 create-react-app my-app --typescript
2、安裝less
3
搞起
create-react-app my-app --typescript
提取 webpack 配置 yarn eject >>> 文件夾會多出一個config文件夾
安裝 處理 less ----------------------------
npm install less less-loader -dev
默認自帶 module.css module.sass 引入方式
安裝less依賴後 可能出問題會有兩點原因
1、 版本過高
調整到 yarn add [email protected]
2、typescript 下引用[fileName].module.less 提示引用不到資源
原因:未在全局暴露less 接口
處理方式: react-app-env.d.ts >>>> 添加
declare module '*.module.less' {
const classes: { readonly [key: string]: string };
export default classes;
}
reacrt+js 做完這下面操作就行
引入後需修改 webpack.config.js
添加這兩段
const lessRegex = /\.less$/;
const lessModuleRegex = /\.module\.less$/;
{
test: lessRegex,
exclude: lessModuleRegex,
use: getStyleLoaders(
{
importLoaders: 1,
sourceMap: isEnvProduction && shouldUseSourceMap,
},
'less-loader'
),
sideEffects: true,
},
{
test: lessModuleRegex,
use: getStyleLoaders(
{
importLoaders: 1,
sourceMap: isEnvProduction && shouldUseSourceMap,
modules: {
getLocalIdent: getCSSModuleLocalIdent,
},
},
'less-loader'
),
},
引入redux 狀態管理
ts 版本 npm install @types/react-redux
在根 index.tsx 頁面引入
import { Provider } from "react-redux"
// Proveider 將App包裹 保證全局都能調用到
<Provider store={store}>
<React.StrictMode>
<App />
</React.StrictMode>
</Provider>,
創建 reducers
新建文件夾 reducers
reducers >>> index.tsx
根store 創建
/** index.tsx */
/**創建唯一store
* combineReducers 把一個由多個不同 reducer 函數作爲 value 的 object,合併成一個最終的 reducer
* 函數,然後就可以對這個 reducer 調用 createStore。
*/
import { configureStore, combineReducers, Reducer } from '@reduxjs/toolkit';
import rootReducer, { staticReducers } from './rootReducer'
/**
* rootReducer 全局保存用戶信息 配置信息
* staticReducers
*/
// configureStore()在你的react項目裏,只能出現一次,
const store = configureStore({ //單一原則
reducer: rootReducer,
devTools: process.env.NODE_ENV !== 'production',
})
/**
* @param 一些說明:
* 1. 當前的項目架構使用的是單個 store + 初始化時會生成的 rootReducer(這個reducer裏只有公用的reducer)
* 1.1 如果需要使用 - 路由懶加載代碼分割 - 的模式,那麼會導致動態加載的業務模塊對應的 reducer 不存在,所以會需要將當前 store 進行合併且重新注入,讓業務模塊的reducer 可以存在
*
* 2. 還有一種設計模式可以參考:項目中分爲多個 store , webpack 的 entry 是動態的, 在 build 時使用 npm run build --moduleName
* 2.1 那麼此時每個業務模塊的 rootReducer 也就是被 Provider 提供的 store 始終都是會包含當前業務模塊的 reducer ,就不會出現以上第一種的情況,也就不需要這個 injectReducer 這個操作
*
* - 不傾向某一種 redux 的設計,按照業務來決定即可
*
*/
declare interface LooseObject {
[key: string]: any;
}
const asyncReducers: LooseObject = {};
export function injectReducer<State>(key: string, reducer: Reducer<State>) {
asyncReducers[key] = reducer;
const newRootReducer = combineReducers({
...staticReducers,
...asyncReducers,
});
store.replaceReducer(newRootReducer)
}
/**
*replaceReducer
*如果您的應用程序實現了代碼拆分,並且您想要
*動態加載一些減速器。 如果您可能還需要此
*爲Redux實現熱重載機制。
*/
// 普通 dispatch
// 獲取一個變量的類型時
// 獲取 store.dispatch 的類型 並定義爲 AppDispatch
export type AppDispath = typeof store.dispatch;
// 如果沒有導出ReturnType 而需要獲取ReturnType返回類型的值 // 獲取rootReducer 類型
export type RootState = ReturnType<typeof rootReducer>;
export default store;
基礎版
https://blog.csdn.net/qq_42359718/article/details/105956421
代碼分割後 需要動態注入
局部reducer 創建後 用 上文定義的 injectReducer 引用 (沒有案例難理解, 晚點再分解一張)
injectReducer('supplierData', reducer);
路由
npm install @types/react-router-dom
import { BrowserRouter } from "react-router-dom";
const render = () => {
// const App = require("./App").default;
ReactDOM.render(
<Provider store={store}>
{/* // 需要用BrowserRouter 包裹App 不然無法在內部使用 Switch Route 等組件構建Router */}
<BrowserRouter>
<React.StrictMode>
<App />
</React.StrictMode>
</BrowserRouter>
</Provider>,
document.getElementById("root")
);
}
render()
路由eg:
import React from 'react';
import { Switch, Route, Redirect } from 'react-router-dom'
import LayOut from '../Layout/index'
import NotFound from '../../NotFound/index'
const Admin = () => {
return (
<>
<Switch>
<Route exact path='/'>
<Redirect to="/Admin" />
</Route>
<Route exact path='/Admin'>
<LayOut />
</Route>
<Route path="/404">
<NotFound />
</Route>
<Redirect to="/404" />
</Switch>
</>
)
}
export default Admin