PK creative Spring Festival, I am participating in the “Spring Festival creative submission contest”, please see: Spring Festival creative submission Contest

First, share your work

With the Spring Festival holiday just around the corner, things are getting more hectic. As a person in charge of the front end, in addition to fulfilling business requirements, continuously improving my ability and making new quarterly plans for the front end, I also need to pay attention to the technical growth of team members. So I started to follow my own leader’s example (he is very wise, stable and super capable) and learn his way of dealing with problems. Thanks to my leadership, I can cross the river without feeling for stones.

Although I have a lot of daily things, I can’t help sharing good ideas or features. Because my colleague’s help to me is warm and meticulous. (My angel colleagues, my question must be completely understood, from implementation to principle.)

There is a batch import function in the recent requirement. I checked the project code and found that most of the batch import functions were directly added to the page without modularization treatment. Therefore, I packaged the batch import into a business component based on my understanding of the business and the general forecast of future scalability.

The project is based on the React framework, so the code is written using JSX syntax, component development using hooks function components, and THE UI framework using ANTD.

Inspiration comes from happiness

I changed the business needs of running water into actively looking for development inspiration. Every time there is a new development harvest, I will give myself a little red flower, who will be too much red flower.

2.1 Flow of Multiple Batch import Functions

The flow chart I combed is as follows:

2.2 Component Encapsulation

2.2.1 Thinking about business scenarios

Sometimes the same product is designed to have different interactions for the same function. There are two kinds of batch import in our system, one is the way of popup interactive file import, the other is the page directly display import button group.

1) Popover interaction mode

2) Display the import button group directly on the page

Either way, the file selection function and import confirm function are the same. However, the interaction mode is different, and the front-end layout processing will be different. Therefore, I will communicate the way of interaction in advance when product colleagues review requirements. In addition, for the company’s internal background management system, I personally prefer simple design, and do not recommend a variety of interactive methods for similar functions. So at present, the batch import function in our system only has these two interactive ways. Today we are sharing the componentization of business functions in the form of direct operation upload and import on the page.

2.2.2 Expansibility of functions

The function of batch import is relatively simple. At present, it can be expanded as follows

1) Import buttons can be single or multiple;

2) Download template button can be single or multiple;

3) Support multiple imports only need the existence of a download template button;

2.2.3 Function implementation

1) Select the file function and use the upload component provided by ANTD;

2) Import button uses array object, loop rendering directly through map method;

3) Depending on the requirements of the product, the import and template are separate, so the front-end layout is separate, but the data and import are the same array object.

4) Just as the design of the above flow chart, when there are multiple import buttons on the page, the button operation will be controlled. Each import button is set with an operable switch, and only one button can be operated in an import operation.

CommonMultipleBatchImport.jsx

/ * * *@description Common service component - Batch upload Currently multiple batch upload operations */
import React, { useState, Fragment } from 'react';
import { useHistory } from 'react-router-dom';
import PropTypes from 'prop-types';
import _ from 'lodash';
import axios from 'axios';
import { Button, Row, Col, Upload, Space, message } from 'antd';
import { UploadOutlined } from '@ant-design/icons';
import style from './style';

const CommonMultipleBatchImport = ({ ...props }) = > {
  const { importList, callback } = props;
  const history = useHistory();
  const [fileList, setFileList] = useState([]);
  const [file, setFile] = useState(null);
  const [importListInit, setImportListInit] = useState(_.cloneDeep(importList));

  /** * events before upload *@param {Object} File Indicates the file object to be uploaded@return {void} No * /
  const beforeUpload = file= > {
    setFile(file);
    setFileList([file]);
    return false;
  };

  /** * upload event *@param {Object} Item Upload object * of the current operation@return {void} No * /
  const upload = (item, index) = > {
    if(! file) {return message.error('Please select file');
    }
    message.info('Best wishes uploaded, please hold on');
    let list = _.cloneDeep(importListInit);
    list.map((itm, inx) = > {
      // Upload operation item loading and unclickable processing
      itm.loading = inx === index ? true : false;
      itm.disabled = true;
    });
    setImportListInit(list);
    const formData = new FormData();
    formData.append('file', file);
    axios
      .post(item.httpMethod, formData, { nobody: true })
      .then(() = > {
        message.success('Best wishes to batch import success, your family and friends will soon receive ~');
      })
      .finally(() = > {
        let listFinally = _.cloneDeep(importListInit);
        listFinally.map(itm= > {
          itm.loading = false;
          itm.disabled = false;
        });
        setImportListInit(listFinally);
        setFileList([]);
        setFile(null);
        callback && callback(true);
      });
  };

  /** * File removal event *@param {void} No *@return {void} No * /
  const onRemove = () = > {
    setFile(null);
    setFileList([]);
  };

  /** * Download template *@param {Object} Item Upload object * of the current operation@return {void} No * /
  const downTemplate = item= > {
    location.href = item.downUrl;
  };

  return (
    <Row align='middle' className={style['multiple-datch-import']} >
      <Col className='file-col mr10'>
        <Upload accept='.xlsx,.xls' onRemove={onRemove} fileList={fileList} beforeUpload={beforeUpload}>
          <Button icon={<UploadOutlined />}> Select file</Button>
        </Upload>
      </Col>

      <Col span={6}>
        <Space>Importlistinit. map((item, index) => {return ()<Button key={item.key} type='primary' onClick={()= >upload(item, index)} loading={item.loading} disabled={item.disabled || ! file}> {item.name}</Button>); Importlistinit. map(item => {return (importListinit. map(item => {return (<Fragment key={item.key}>
                {item.downUrl ? (
                  <Button type='primary' onClick={()= > downTemplate(item)}>
                    {item.downName}
                  </Button>
                ) : null}
              </Fragment>
            );
          })}
        </Space>
      </Col>
    </Row>
  );
};

CommonMultipleBatchImport.propTypes = {
  importList: PropTypes.array.isRequired, // An array object to upload content to
  callback: PropTypes.func, // The callback of the operation
};

CommonMultipleBatchImport.defaultProps = {
  importList: [],};export default CommonMultipleBatchImport;
Copy the code

style.less

:local(.multiple-datch-import) {
  margin-bottom: 10px;

  .ant-row {
    margin-bottom: 15px;
  }

  .file-col {
    margin-right: 10px;

    > span {
      display: flex; }}}Copy the code

2.3 Component Usage

2.3.1 Importing Components

Our business components are placed under /bundleComponents, so we will find the corresponding file location when importing them.

list.jsx

// Component import
import { CommonMultipleBatchImport } from '@/bundleComponents';

// page usage
<CommonMultipleBatchImport callback={listQuery} importList={importList} />;
Copy the code

2.3.2 Component Communication

Props and participation

1) Download template: the value can be empty, when its value is empty, the page does not display the download template button;

2) Import interface request address: Our import process is to directly take the file and pass it to the backend through the interface, and then the backend will process the file data. Different companies may have different handling methods. You can rectify the fault based on the actual situation.

list.jsx

 // Import an array object
const importList = [
  {
    key: 'fuqi'.// Import the operation key
    name: 'Batch import blessing'.// Import the operation button name
    downName: 'Download template'.// Download template button name
    downUrl: 'Actual download template link'.// Download the template to open the link
    httpMethod: 'Actual interface request address'.// Import the interface request address
  },
  {
    key: 'zhufu'.name: 'Batch import blessing'.downName: 'Download delete Template'.downUrl: ' '.// Download template open link button with empty value is not displayed
    httpMethod: 'Actual interface request address',},]Copy the code

The callback function

Because the current page needs to be updated after the data import is successful, the callback process is done in the successful import logic, and the list page will be refreshed after the callback.

list.jsx

const listQuery = () = > {
  list.query();
};
Copy the code

Third, summary

Batch import function, not very complex, especially to comb out the operation, each case is simulated clear, in fact, the amount of code is very small.

The important thing is that when you encounter similar business functions, you can design the functions first and then code them. Although the contents of some functions are not the same, but the process and core functions are consistent, so modular encapsulation of functions can be considered. The advantage of this is that it can not only improve the technology in business development, but also improve the efficiency. We have already made components of seemingly complex functions, which can be directly introduced into the page and used in a few lines of code.

Congratulations, I got a little red flower.