小哲记账项目总结

412 阅读2分钟

项目技术栈

基于React/React Router /自定义hooks/webpack实现的极简主义记账应用

开发初衷

因为自身开销比较大,有很多模糊的消费,为了满足自己清晰自己消费情况的需求,我独立开发了一款可以快速记账的应用

通过该项目习得的技术栈

该项目使用我对 Typescript/webpack/Hooks API/SVG ICon 有了更深入的理解

Typescript

因为之前使用ts非常的少,刚开始使用ts开发的感觉很奇妙,我知道ts的编译错误非常让人抓狂,但是使用了后,我像是有了受虐倾向一般,让ts报错来的更猛烈些吧,首先要解决的是函数组件的React.FC,如果有props的情况下React.FC<Props>,请在使用props之前将props的类型整理干净

type Props = {
  noteName: string
} & React.InputHTMLAttributes<HTMLInputElement>

此处的Props后面的&意思是加上了input的所有属性,就不用在一个个很呆的将input的props一个个手敲了
那么在组件中const{...rest}=props接受所有传来的参数,直接使用在组件的input中<input {...rest}> 反正ts一句话,哪里有问题解决哪里,每次要对数据本身进行一个判断,有时候报错可能是因为数据存在多种类型,比如可能为空,然后webStorm会报错,这个时候只需要添加判断条件即可,排除掉可能为空的情况

Partial
const onChange = (obj: Partial<typeof value>) => {
  setValue({
    ...value,
    ...obj
  });
};

Partial<typeof value>此时obj参数就是value类型中的随意一个或者多个

自定义Hooks

项目中有需要集中数据管理,我自行封装了hooks来实现redux,并且向外暴露了增删改查的接口

export const useRecords = () => {
  const [records, setRecords] = useState<RecordItem[]>([]);
  }
  const addRecord = (newRecord: newRecordItem) => {
    if (newRecord.amount === '0') {
      alert('金额不能等于0');
      return false;
    } else if (newRecord.tagIds.length === 0) {
      alert('请选择一个标签');
      return false;
    } else {
      const record = {...newRecord, createdAt: (new Date()).toISOString()};
      setRecords([...records, record]);
      return true;
    }

  };
  useEffect(() => {
    setRecords(JSON.parse(window.localStorage.getItem('records') || '[]'));
  }, []);
  useUpdate(() => {
    window.localStorage.setItem('records', JSON.stringify(records));
  }, records);
  return {records, addRecord};
};

实际都是使用了原生的hooks,例如useState和useEffect

useEffect

此项目中使用useEffect较多的是,第一次渲染时获取默认数据

useEffect(() => {
  setRecords(JSON.parse(window.localStorage.getItem('records') || '[]'));
}, []);

以及当第二个参数变化时,重新渲染

useEffect(() => {
    if (count.current > 1) {
      fn();
    }

  }, [fn, deps]);
};

当[]内的数据发生变化时,那么重新渲染

useRef

通常配合current使用 const valueRef = useRef<InputHTMLElement>() 此项目中我配合ref使用,用valueRef获取HTML元素 或者使用()赋值,来形成一个不会因为地址变更而变更的值

SVG Icon

引入svg symbol 首先在React项目中,运行 yarn eject,生成webpack配置文件
在webpack.config文件里加上,module>rules>one Of

{

  test: /\.svg$/,

  use: [

    {loader: 'svg-sprite-loader', options: {}},

    {loader: 'svgo-loader', options: {}},

  ]

},

并且引用时要用require

styled components

本质是用js语法创建css
俗称css in js

const Title = styled.h1`

  font-size: 1.5em;

  text-align: center;

  color: palevioletred;

`;

const Wrapper = styled.div`

  padding: 4em;

  background: red;

`;

function App() {

  return (

    <Wrapper>

      <Tit>

        Hello World!

      </Tit>

    </Wrapper>

  );

}