Commit 9f0d6893 authored by 郑云峰's avatar 郑云峰

feat: 初始化mobx以及storage

parent 8bec3598
......@@ -62,3 +62,13 @@ buck-out/
# Ruby / CocoaPods
/ios/Pods/
/vendor/bundle/
# IDE - VSCode
.vscode
!.vscode/settings.json
!.vscode/tasks.json
!.vscode/launch.json
!.vscode/extensions.json
# IDEs and editors
/.idea
\ No newline at end of file
{}
\ No newline at end of file
......@@ -14,14 +14,19 @@
"lint": "eslint . --ext .js,.jsx,.ts,.tsx"
},
"dependencies": {
"@react-native-async-storage/async-storage": "^1.17.11",
"@react-navigation/bottom-tabs": "^6.4.0",
"@react-navigation/native": "^6.0.13",
"@react-navigation/native-stack": "^6.9.1",
"@react-navigation/stack": "^6.3.4",
"mobx": "^6.7.0",
"mobx-react": "^7.6.0",
"mobx-react-lite": "^3.4.0",
"react": "18.1.0",
"react-native": "0.70.6",
"react-native-safe-area-context": "^4.4.1",
"react-native-screens": "^3.18.2"
"react-native-screens": "^3.18.2",
"react-native-storage": "^1.0.1"
},
"devDependencies": {
"@babel/core": "^7.12.9",
......
......@@ -27,6 +27,10 @@ import {
ReloadInstructions,
} from 'react-native/Libraries/NewAppScreen';
import RootNavigationContainer from './routers/RootNavigationContainer';
import { storage } from './utils/storage';
//创建全局属性,任意位置都可以调用该实例
global.storage = storage;
const Section: React.FC<
PropsWithChildren<{
......
export * from "./user"
\ No newline at end of file
/**
* 登录存储的用户信息
*/
export const USER_INFO = 'USER_INFO';
/**
* TOKEN 信息
*/
export const TOKEN = 'TOKEN';
\ No newline at end of file
declare global {
var storage: any;
}
export {};
import RootStore from './rootStore';
const rootStore = new RootStore();
/**
* 这里只做根Store的导出
* 预留以后可能会出现 额外的Store
*/
const Store = {
...rootStore,
};
export default Store;
import { makeAutoObservable } from 'mobx';
import UserStore from '../userStore';
import { UserStoreModel } from '../userStore/model';
class RootStore {
userStore: UserStoreModel;
constructor() {
makeAutoObservable(this);
this.userStore = new UserStore(this);
}
}
export default RootStore;
import { UserStoreModel } from '../userStore/model';
export interface RootStoreModel {
userStore: UserStoreModel;
}
import React, { FC, createContext, ReactNode, ReactElement, useContext } from 'react';
import { RootStoreModel } from './rootStore/model';
export const StoreContext = createContext<RootStoreModel>({} as RootStoreModel);
export type StoreComponent = FC<{
store: RootStoreModel;
children: ReactNode;
}>;
// eslint-disable-next-line react/prop-types
export const StoreProvider: StoreComponent = ({ children, store }): ReactElement => (
<StoreContext.Provider value={store}>{children}</StoreContext.Provider>
);
/**
* 组件具体使用mobx的hooks
*/
export const useStores = (): RootStoreModel => useContext(StoreContext);
export default useStores;
import { makeObservable, observable, runInAction } from 'mobx';
import { getAsyncStorage, setAsyncStorage, removeAsyncStorage } from '../../utils/storage';
import { USER_INFO, TOKEN } from '../../constants';
import { RootStoreModel } from '../rootStore/model';
import { UserStoreModel, userInfoType } from './model';
export default class UserStore implements UserStoreModel {
private rootStore: RootStoreModel;
username = 'Bob';
userInfo: userInfoType | null = null;
constructor(rootStore: RootStoreModel) {
makeObservable(this, {
username: observable,
userInfo: observable,
});
this.rootStore = rootStore;
this.fetchUserInfo();
}
setUserName(name: string) {
this.username = name;
}
async fetchUserInfo() {
this.userInfo = await getAsyncStorage(USER_INFO);
}
// 用户登录时,或者修改用户信息的时候更新UserInfo
async setUserInfo(data: userInfoType) {
await setAsyncStorage(USER_INFO, data);
runInAction(() => {
this.userInfo = data;
});
}
async removeUserInfo() {
await removeAsyncStorage(TOKEN);
await removeAsyncStorage(USER_INFO);
// 商品分享口令生成数字
await removeAsyncStorage("SHARE_CODE_NUM");
runInAction(() => {
this.userInfo = null;
});
}
}
export type userInfoType = {
account?: string;
company?: string;
countryCode?: string;
idCardNo?: string;
logo?: string;
mail?: string;
memberId?: number;
memberRoleId?: number;
name: string;
orgName?: string;
phone?: string;
token?: string;
tokenExpireMinutes?: number;
urls?: string[];
userId: number;
memberType?: number;
jobTitle?: string,
roles: {
roleId: number,
roleName: string,
}[]
}
export interface UserStoreModel {
username: string;
setUserName: (name: string) => void;
userInfo: null | userInfoType;
removeUserInfo: () => void;
setUserInfo: (data: any) => void;
}
import AsyncStorage from "@react-native-async-storage/async-storage";
import Storage from "react-native-storage";
//创建库
export const storage = new Storage({
// 最大存储多少条数据
size: 1000,
// 存储引擎,指定后会存储到app中
storageBackend: AsyncStorage, // for web: window.localStorage
// 数据保存时间
defaultExpires: 1000 * 3600 * 24,
// 读取时在内存中缓存数据
enableCache: true,
// 当storage中没有响应数据或已过期,会调用该方法
// 该方法可以通过storage.sync直接修改、require('引入其他文件写好的')
sync: {
// we'll talk about the details later.
}
});
/**
* 根据key存储
* @param key 不能使用下划线, key永远存在, 不受过期时间影响
* @param data
* @param expires 过期时间,如果未设置则使用实例对象中的时间戳, null表示永久保存
*/
export const setAsyncStorage = async <T>(key: string, data: T, expires?: number) => {
await storage.save({
key,
data,
expires
})
}
/**
* 依据key来获取存储的值
* @param key
* @param autoSync autoSync(默认为true),意味着在没有找到数据或数据过期时自动调用相应的sync方法
* @param syncInBackground syncInBackground(默认为true)意味着如果数据过期,在调用sync方法的同时先返回已经过期的数据。设置为false的话,则等待sync方法提供的最新数据(当然会需要更多时间)。
* @param extraFetchOptions 传递给sync方法的参数
* @returns
*/
export const getAsyncStorage = async <T = any, P = any>(key: string, autoSync = false, syncInBackground = true, extraFetchOptions?: P): Promise<T | null> => {
const res = await storage.load({
key,
autoSync,
syncInBackground,
syncParams: {
extraFetchOptions,
someFlag: true,
},
})
if (res) {
return res as T
}
return null
}
/**
* 移除指定key的值
* @param key
*/
export const removeAsyncStorage = async (key: string) => {
await storage.remove({key})
}
/**
* 清除所有设置了key-id的内容
*/
export const clearAsyncStorage = async () => {
await storage.clearMap()
}
import React from 'react';
import { View, Text } from 'react-native';
const Customer = ({ navigation }) => {
interface CustomerProps {
navigation: any
}
const Customer: React.FC<CustomerProps> = ({ navigation }) => {
return (
<View style={{ flex: 1, alignItems: 'center', justifyContent: 'center' }}>
<Text>个人中心</Text>
......
This diff is collapsed.
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment