【阿里低代码引擎实战】— 预览&表单回显

1,719 阅读3分钟

【阿里低代码引擎实战】— 预览&表单回显

上一篇使用低代码引擎demo拖拉拽生成自已的页面,通过调接口将不同页面的schema数据保存在 mysql 数据库中,并且根据不同页面路由回显相对应的页面数据,上篇指路:juejin.cn/post/734695…

这篇我们将demo中的预览功能完善,并且在user页面搞一个用户信息的表单,支持用户自由修改个人资料并回显;

本篇代码github地址:github.com/JoeXu727/al…

github.com/JoeXu727/lo…

一. 预览功能

  1. 官方demo里的预览逻辑是从 localstorage 里去获取 schema 的:

    const projectSchema = getProjectSchemaFromLocalStorage(scenarioName);
    
  2. 这里我们需要改成调接口获取,在 mockService 新增 `getFullSchema 方法,并且把之前的 getPageSchema 修改一下:

    mockService.tsexport const getPageSchema = async (
      pageType: number = 1
    ) => {
      const schema = await getFullSchema(pageType);
      return schema.componentsTree[0];
    };
    ​
    export const getFullSchema = async (pageType: number = 1) => {
      let pageSchema;
      let url = `http://127.0.0.1:7001/admin?page_type=${pageType}`;
      pageSchema = await fetchData(url).then((res) => {
        return JSON.parse(res.data.page_schema);
      });
    ​
      if (pageSchema) {
        return pageSchema;
      }
    }
    
  3. 修改预览逻辑:

    preview.tsx
    ​
    ​
    import { getProjectSchemaFromLocalStorage, getPackagesFromLocalStorage, getPreviewLocale, setPreviewLocale, getFullSchema } from './services/mockService';
    ​
    const getPageType = function () {
      if (location.search) {
        let pageName = new URLSearchParams(location.search.slice(1)).get('page') || 'home';
        return pageName === 'home' ? 1 : 2;
      }
      return 1;
    }
    ​
    async function init() {
        const scenarioName = getScenarioName();
        const pageType = getPageType();
        const packages = getPackagesFromLocalStorage(scenarioName);
        const projectSchema = await getFullSchema(pageType);
        const pageSchema = componentsTree[0];
        ...
      }
    
  4. 查看预览效果,已经是我们数据库里存放的schema了:

    image-20240331133431240.png

二. 表单回显

数据库

  1. 如下新建数据库表 userInfo

    image-20240331134622281.png

  1. 表内随意加一条数据:

    image-20240331134722518.png

lowcode-egg-demo

  1. 添加 查询用户信息保存用户信息 在Controller 层的逻辑,新建 user.js :

    controller/user.js
    ​
    const { Controller } = require('egg');
    ​
    class UserController extends Controller {
      // 查询用户信息
      async getUserInfo() {
        const { ctx } = this;
        const result = await ctx.service.user.getUserInfo();
        ctx.body = result;
      }
    ​
      // 保存用户信息
      async saveUserInfo() {
        const { ctx } = this;
        const params = ctx.request.body;
        const result = await ctx.service.user.saveUserInfo(params);
        if (result) {
          ctx.body = {
            status: 200,
            msg: '保存成功',
            data: result,
          };
        } else {
          ctx.body = {
            status: 201,
            msg: '保存失败',
            data: {},
          };
        }
      }
    }
    ​
    module.exports = UserController;
    
  1. 对应添加 service 层逻辑:

    service/user.jsconst Service = require('egg').Service;
    ​
    class UserService extends Service {
        // 查询用户信息
        async getUserInfo() {
            try {
                const result = await this.app.mysql.get('userInfo');
                return result;
            } catch (error) {
                console.log(error);
            }
        }
    ​
        // 保存用户信息
        async saveUserInfo(params) {
            try {
                const row = params;
                const result = await this.app.mysql.update('userInfo', row);
                return result;
            } catch (error) {
                console.log(error);
            }
        }
    }
    ​
    module.exports = UserService;
    
  1. 最后加上对应的路由:

    router.js
    ​
    module.exports = app => {
      const { router, controller } = app;
      router.get('/admin', controller.admin.getSchema);
      router.post('/admin', controller.admin.saveSchema);
      router.get('/user', controller.user.getUserInfo);
      router.post('/user', controller.user.saveUserInfo);
    };
    
  1. 在浏览器用fetch发请求测试下接口:

    image-20240331142613811.png

    image-20240331142649486.png

    image-20240331142709062.png

ali-lowcode-demo

  1. 在demo画布中创建一个用户信息的表单(如下图),给表单容器绑定表单值 this.state.userInfo

143551.png

  1. 给表单中的每个formItem 输入框在右边设置器添加表单标识,一一对应 userName, email, gender, age, signature ,这时表单里面的数据就可以正确回显了;

    143258.png

  1. 首先给表单容器绑定组件自带事件:onChange,然后给提交按钮绑定事件:onClick:

    image-20240331144347873.png

    image-20240331144418506.png

  1. 打开demo左侧的源码面板,对源码进行修改,实现点击 提交 按钮时,用户编辑的表单数据可以保存在数据库中;

    image-20240331144528817.png

    关键代码如下:

    class LowcodeComponent extends Component {
      state = {
        "text": "outer",
        "isShowDialog": false,
        "userInfo": {
          "userName": '',
          "email": '',
          "age": '',
          "gender": ''
        }
      }
      // 提交按钮点击事件
      onClick() {
        const { userInfo } = this.state;
    ​
        fetch('http://localhost:7001/user', {
          method: 'POST',
          mode: 'cors',
          cache: 'no-cache',
          credentials: 'same-origin',
          headers: {
            'Content-Type': 'application/json'
          },
          body: JSON.stringify(userInfo)
        })
      }
      
      // 表单改变事件
      onChange(data){
        Object.assign(this.state.userInfo, data)
      }
    }
    

结果演示

现在就可以在预览页面查看和修改用户信息了:

image-20240331144954948.png

==========================================================
以上为个人工作学习笔记总结,供学习参考交流,未经允许禁止转载或商用。
个人博客地址:joexu727.github.io/