> 웹 프론트엔드 > JS 튜토리얼 > Pastate.js 반응형 반응 프레임워크 모듈화

Pastate.js 반응형 반응 프레임워크 모듈화

不言
풀어 주다: 2018-04-10 16:34:45
원래의
1804명이 탐색했습니다.

이 문서의 내용은 Pastate.js 반응형 반응 프레임워크의 모듈화에 관한 것입니다. 이는 특정 참조 가치가 있습니다. 필요한 친구가 참조할 수 있습니다.

이것은 Pastate.js 반응형 반응 상태 관리 프레임워크에 대한 일련의 튜토리얼입니다. . 관심을 갖고 계속 업데이트해 주시기 바랍니다.

Pastate.js Github

모듈형 실무 작업

애플리케이션이 복잡하고, 페이지가 많고, 인터페이스에 구성 요소와 작업이 많으면 애플리케이션을 모듈(모듈)로 나누어 관리해야 합니다.
붙여넣기 응용 프로그램의 모듈식 메커니즘을 소개하기 위해 수업 정보 관리 시스템을 예로 들어 보겠습니다.

실제 경험 : https://birdleescut.github.io/pastate-demo

애플리케이션 소스 코드 : https://github.com/BirdLeeSCUT/pastate-demo

애플리케이션 프로토타입은 다음과 같습니다.

(1) 학생 섹션

  • 학생 정보 가져오기 및 표시

Pastate.js 반응형 반응 프레임워크 모듈화

  • 학생 정보 수정

Pastate.js 반응형 반응 프레임워크 모듈화

(2) 강좌 섹션: 강좌 정보 표시

Pastate.js 반응형 반응 프레임워크 모듈화

이 앱은 비교적 간단합니다. 실제 개발에서는 반드시 모듈화할 필요가 없습니다. 여기서는 파스타를 사용하여 복잡한 애플리케이션을 처리하는 방법을 알려드리기 위해 모듈화할 필요가 없습니다.

모듈 분할

모듈 설계의 첫 번째 단계는 모듈 분할입니다. 먼저 수업 정보 관리 시스템을 모듈로 나누어 보겠습니다.

  1. 탐색 모듈: Navigator

Pastate.js 반응형 반응 프레임워크 모듈화

  1. StudentPanel

Pastate.js 반응형 반응 프레임워크 모듈화

  1. 과정 정보 모듈: ClassPanel

Pastate.js 반응형 반응 프레임워크 모듈화

pastate 모듈 메커니즘은 간단한 플럭스 모드 구현입니다. 모듈은 세 가지 기본 요소로 구성됩니다.

    State: 모듈의 현재 상태를 저장
  • View: 모듈 상태 표시 로직
  • Action: 모듈 작업의 처리 로직
  • 이 세 가지 모듈 요소는 다음과 같습니다. 단방향 데이터 흐름 프로세스:

Pastate.js 반응형 반응 프레임워크 모듈화모듈 구조

폴더를 통해 모듈을 구성하고 "학생 정보 모듈" StudentPanel을 예로 들어 새 StudentPanel 폴더를 만들고 아래에 다음 파일을 만듭니다. 폴더:

    StudentPanel 모듈 폴더
    • StudentPanel 模块文件夹
    • StudentPanel.model.js 模型文件:用于定义应用的 state 和 actions

    • StudentPanel.view.jsx 视图文件:用于定义的视图组件(组件渲染逻辑)

    • StudentPanel.css 样式文件:用于定义用于的样式(可以改用 less 或 sass)

模型文件 *.model.js

(1)设计模块的 state

我们先在模型文件 StudentPanel.model.js 下定义模块的 state 结构:
StudentPanel.model.js

StudentPanel. model.js 모델 파일: 애플리케이션의 상태와 동작을 정의하는 데 사용

StudentPanel.view.jsx 보기 파일: 사용됨 정의된 뷰 구성 요소(구성 요소 렌더링 논리)

Pastate.js 반응형 반응 프레임워크 모듈화StudentPanel.css 스타일 파일: 사용되는 스타일을 정의하는 데 사용됩니다(대신 less 또는 sass를 사용할 수 있음)

모델 파일*.model.js🎜

(1) 디자인 모듈의 상태

🎜먼저 모델 파일 StudentPanel.model.js에서 모듈의 상태 구조를 정의합니다: 🎜 StudentPanel.model.js🎜
const initState = {
    initialized: false, // 初始化状态
    /** @type { "loading" | "ok" | "error" } */
    status: 'loading', // 加载状态
    isEditting: false, // 是否在编辑中
    selected: 0, // 选中的学生
    /** @type {studentType[]} */
    students: [] // 学生数组
}

const studentType = {
    name: '张小明',
    studentNumber: '2018123265323',
    age: 22,
    isBoy: true,
    introduction: '我是简介'
}
...
로그인 후 복사
🎜전과 마찬가지로, 상태 구조의 정의와 jsDoc 주석과 함께 초기 값의 정의. 🎜🎜팁: "열거형 문자열" 유형을 정의하려면 위의 상태 속성을 정의하는 패턴을 사용하는 것이 좋습니다. 이러한 열거형 값을 할당할 때 문자열을 직접 입력하는 대신 intelSence의 "선택" 방법을 사용해 보세요. 개발은 편리함을 제공하고 실수를 줄일 수 있습니다. 할당할 때 등호 뒤의 따옴표 사이에 입력 커서를 놓고 "트리거 프롬프트" 바로가기 키를 누르면 옵션이 표시됩니다. 🎜🎜🎜🎜🎜🎜 🎜🎜상태 모의 영역🎜: 뷰를 개발할 때 상태를 완전히 테스트해야 합니다. 예를 들어 state.status를 "loading" | "error"와 동일하게 만듭니다. 모듈의 렌더링 로직을 완전히 테스트하려면 true | false로 설정해야 합니다. 이때 initState의 값을 직접 변경하지 말고 initState의 하단을 상태 모의 테스트 영역으로 사용하고 상태를 수정하여 모의를 구현해야 합니다.
const initState = {...}
const studentType ={...}

/***** MOCK AREA *****/
// initState.status = 'ok'
// initState.isEditting = true
// initState.students = [studentType, studentType]
로그인 후 복사

你可以根据开发调试需求新建 mock 行,或通过注释控制某个 mock 行是否生效,以此来使应用处于某个中间 state 状态,方便调试。并在模块开发完成时把 mock 区域全部注释即可,这种模式可以有效地管理 mock 过程。

模块的 initState 是对模块的一种 “定义”,它具有“文档属性”,而 mock state 是对应用进行调试时执行的临时动态操作,如果通过直接修改 initState 来进行 mock,我们会破坏模块的定义,然后又尝试凭记忆对定义进行恢复,这个过程容易出错或遗漏,特别是当 state 变得复杂的时候。所以我们推荐采用 MOCK AREA 对 state 进行 mock 调试。

(2)定义模块的 actions

之前我们是把应用的动作逻辑实现为视图组件的成员函数,在应用简单时这种模式会比较直接方便,而当应用复杂且某些操作逻辑需要在不同组件甚至模块间共享时,原理的模式无法实现。因此我们把模块的相关操作逻辑统一放在 actions 中进行管理:

StudentPanel.model.js

const actions = {
    init(){ },
    loadStudents(){ },
    switchEditting(){ },
    /** @param {number} index 学生数组索引号 */
    selectStudent(index){ },
    increaseAge(){ },
    decreaseAge(){ }
}
로그인 후 복사

在初步的 actions 声明阶段,我们只需把 actions 的名字和参数声明出来,在应用开发过程中再逐渐实现其业务逻辑。你可以考虑使用 jsDoc 对 action 的用途和参数进行注释说明。当模块简单的时候,你可以直接在 actions 中直接实现同步更新 state 的操作和异步从后台获取数据等操作,pastate 不对 actions 的实现的内容做限制,不需要像 redux 或 vuex 一样规定一定要把同步和异步逻辑的分开实现,在 pastate 中,当你认为有必要时才那样做就好了。

多级 actions 管理: 当模块的 actions 比较多的时候,我们可以采用多级属性的模式对 actions 进行分类管理, 具体的分类方法和分类级别根据具体需要自行定义即可,如下:

const actions = {
    init(){ },
    handle:{
        handleBtnClick(){ },
        handleXxx1(){ },
        handleXxx2(){ }
    },
    ajax:{
        getStudentsData(){ },
        getXxx(){ },
        postXxx(data){ }
    }
}
로그인 후 복사

mutations 模式: 如果你的模块比较复杂,想遵循 redux 或 vuex 把对 state 同步操作 和 异步动作两类操作分类管理的模式,那么你可以对 state 的同步操作放在 actions.mutations 分类下,pastate 提供特殊中间件对 mutations 提供而外的开发调试支持,详见 规模化 章节。

const actions = {
    init(){ },
    handleBtnClick(){ },
    getStudentsData(){ },
    mutations:{
        increaseAge(){ },
        decreaseAge(){ }
    }
}
로그인 후 복사

Mutations 其实就是一些同步的 state 更新函数,你可以通过其他普通 actions 调用 mutations, 或直接在视图中调用 mutations。比起 redux dispatch actions to reducers 和 vuex commit mutations 通过字符串 mutations 名称发起(dispatch) 的模式,这种函数调用的方式在开发时更加方便且不易出错:

  • 无需为了调用方便,定义 actions / mutation 的常量名称

  • 可以友好的支持 编辑器/ IDE 的智能提示

Pastate.js 반응형 반응 프레임워크 모듈화

如果你选择使用 pastate 的 mutations 机制, 那么每个 mutation 都要使用同步函数,不要在 mutation 中使用 ajax 请求或 setTimeout 或 Promise 等异步操作。这样相关的浏览器 devtools 才能够显示 有准确意义 的信息:

Pastate.js 반응형 반응 프레임워크 모듈화

这种 actions 分类管理的设计体现了 pastate 的精益原则:你能在需要某些高级特性的时候 才去能够 使用这些高级特性。

(3)创建并配置模块的 store

我们可以像之前那样简单地创建 store:
StudentPanel.model.js

import { Pastore } from 'pastate'
const initState = {...}
const actions = {...}
...

const store = new Pastore(initState);
/** @type {initState} */
let state = store.state;

export { initState, actions, store}
로그인 후 복사

Pastate 采用一种 可选的 的 actions 注入模式,你可以自愿决定是否把 actions 注入 store。 把 actions 注入 store 后,可利用 pastate 的中间件机制对 actions 进行统一管理控制,具有较强的可扩展性。例如我们可以使用 logActions 中间件对每次 actions 的调用在控制台进行 log,并使用 dispalyActionNamesInReduxTool 中间件 对把 mutations 名称显示出来,以便于调试:

import { ..., logActions, dispalyActionNamesInReduxTool } from 'pastate'

...
const store = new Pastore(initState);
store.name = 'StudentPanel';
store.actionMiddlewares = [logActions(), dispalyActionNamesInReduxTool(true)]
store.actions = actions;

/** @type {initState} */
let state = store.state;

export { initState, actions, store}
로그인 후 복사

如果你觉得上面的定义方式比较琐碎,你可以直接使用 pastate 提供的工厂函数 createStore 来定义一个完整地 store:

import { ..., createStore, logActions, dispalyActionNamesInReduxTool } from 'pastate'

const store = createStore({
    name: 'StudentPanel',
    initState: initState,
    actions: actions,
    middlewares: [logActions(), dispalyActionNamesInReduxTool(true)]
})
const { state } = store // createStore 具有良好的泛型定义,无需额外的 jsdoc 注释即可获取 state 的结构信息
로그인 후 복사

你也可以进一步把中间件配置为仅在开发环境下生效的模式, 生产环境下无效。Pastate 中间件的详细内容请查看规模化章节。

视图部分

我们创建 StudentPanel.view.jsx 文件来保存我们的模块视图, 视图定义和原来的模式类似:
StudentPanel.view.jsx

import React from 'react'
import { makeContainer, Input, Select} from 'pastate'
import { initState, actions } from './StudentPanel.model'
import './StudentPanel.css'

const isBoyOptions = [{
    value: true,
    tag: '男'
},{
    value: false,
    tag: '女'
}]

class StudentPanel extends React.PureComponent {

    componentDidMount(){
        actions.init()
    }

    render() {
        let state = this.props.state
        return (
            <p className="info-panel">
                {this[&#39;view_&#39; + state.status](state)}
            </p>
        )
    }

    view_loading() {
        return (
            <p className="info-panel-tip-loading">
                加载中...
            </p>
        )
    }

    view_error() {
        return (
            <p className="info-panel-tip-error">
                加载失败, 请刷新重试
            </p>
        )
    }

    /** @param {initState} state */
    view_ok(state) {
        let selectedStudent = state.students[state.selected];
        return (
            <p className="info-panel-ok">
                ...
            </p>
        )
    }
}

export default makeContainer(StudentPanel)
로그인 후 복사

Pastate 模块化需要实现一种多模块可以互相协作的机制。因此我们不再使用 makeOnyContainer 唯一地绑定一个视图组件与对应的 store。首先,我们会用各模块的 store 生成一个全局的 store 树,并使用 makeContainer 把模块的视图封装为引用全局 store 的某些节点的容器。

我们目前只有一个模块,此处简单地调用 makeContainer(StudentPanel) 让 StudentPanel 引用全局的 store 树 的根节点的 state ,我们可以为 makeContainer 指定第二个参数,指明引用 store 树 的哪些子节点,详情会在下一章介绍。

在上面视图组件的代码中,我们引入了 model 中的 actions:

import { store, initState, actions } from &#39;./StudentPanel.model&#39;
로그인 후 복사

这些 actions 可以直接赋值到组件的 onClick 或 onChange 等位置:

<button className="..." onClick={actions.increaseAge} > + </button>
로그인 후 복사

这些 actions 也可以在组件的生命周期函数中调用:

...
componentDidMount(){
    actions.init()
}
...
로그인 후 복사

视图部分还包含样式文件 StudentPanel.css ,在此就不列出了。

如果该模块要需要封装一些当前模块专用的子组件,把子组件定义为独立的文件,并放在与 StudentPanel 模块相同的文件夹下即可。如果需要封装一些多个模块通用的非容器组件,可以考虑把它们放在独立于模块文件夹的其他目录。

导出模块

最后,为了方便调用,我们来为模块做一个封装文件 StudentPanel / index.js,导出模块的元素:

export { default as view } from &#39;./StudentPanel.view&#39;
export { store, actions, initState } from &#39;./StudentPanel.model&#39;
로그인 후 복사

pastate 模块向外导出 view, initState, actions, store 四个元素。

大功告成!这时我们可以尝试在 src / index.js 中引入该模块并渲染出来:

import ReactDOM from &#39;react-dom&#39;;
import { makeApp } from &#39;pastate&#39;;
import * as StudentPanel from &#39;./StudentPanel&#39;;

ReactDOM.render(
    makeApp(<StudentPanel.view />, StudentPanel.store), 
    document.getElementById(&#39;root&#39;)
);
...
로그인 후 복사

我们使用 makeApp 函数创建一个 pastate 应用并渲染出来,makeApp 的第一个参数是 根容器,第二个参数是 store 树, 我们现在只有一个模块,所以应用的 store 树只有 StudentPanel 的 store。

自此,我们的第一个模块 StudentPanel 构建完成。

模块的模板文件

我们可以使用模板文件快速创建模块,一个模块的模板文件非常简单,下面以 TemplateModule 模块为例完整给出:

  • /index.js

export { default as view } from &#39;./TemplateModule.view&#39;
export { initState, actions, store } from &#39;./TemplateModule.model&#39;
로그인 후 복사
  • /TemplateModule.model.js

import { createStore } from &#39;pastate&#39;;

const initState = {

}

const actions = {

}

const store = createStore({
    name: &#39;TemplateModule&#39;,
    initState,
    actions
})
const { state } = store
export { initState, actions, store }
로그인 후 복사
  • /TemplateModule.view.jsx

import React from &#39;react&#39;;
import { makeContainer } from &#39;pastate&#39;;
import { initState, actions } from &#39;./ClassPanel.model&#39;;
import &#39;./TemplateModule.css&#39;

class TemplateModule extends React.PureComponent{
    render(){
        /** @type {initState} */
        const state = this.props.state;
        return (
            <p>
                TemplateModule
            </p>
        )
    }
}

export default makeContainer(TemplateModule, &#39;template&#39;)
로그인 후 복사
  • /.css

// css 样式文件初始为空,你也可以选用 less 或 sass 来定义样式
로그인 후 복사

这个例子的 demo 源码已包含该模板模块 src/TemplateModule, 你只需把它复制到你的 src 目录下,并右键点击模块文件夹,选择 “在文件夹中查找”,然后把 TemplateModule 字符串全部替换为你想要的模块名称即可:

Pastate.js 반응형 반응 프레임워크 모듈화

Pastate.js 반응형 반응 프레임워크 모듈화

点击替换之后保存文件。不过目前还不能自动替换文件名,需要手动替换一下。

Pastate 以后将会实现相关的命令行工具,实现一行命令创建新模块等功能,加速 pastate 应用的开发。

下一章,我们来创建另外的模块,并介绍不同模块之间如何协作。

相关推荐:

Pastate.js 响应式框架之数组渲染与操作

Pastate.js 响应式 react 框架之表单渲染与操作

Pastate.js 响应式框架之多组件应用

위 내용은 Pastate.js 반응형 반응 프레임워크 모듈화의 상세 내용입니다. 자세한 내용은 PHP 중국어 웹사이트의 기타 관련 기사를 참조하세요!

관련 라벨:
원천:php.cn
본 웹사이트의 성명
본 글의 내용은 네티즌들의 자발적인 기여로 작성되었으며, 저작권은 원저작자에게 있습니다. 본 사이트는 이에 상응하는 법적 책임을 지지 않습니다. 표절이나 침해가 의심되는 콘텐츠를 발견한 경우 admin@php.cn으로 문의하세요.
인기 튜토리얼
더>
최신 다운로드
더>
웹 효과
웹사이트 소스 코드
웹사이트 자료
프론트엔드 템플릿