diff --git a/web-network/client/src/sections/network/components/export-data.js b/web-network/client/src/sections/network/components/export-data.js
new file mode 100644
index 0000000..f055387
--- /dev/null
+++ b/web-network/client/src/sections/network/components/export-data.js
@@ -0,0 +1,560 @@
+
+'use strict';
+import React, { useState, useEffect } from 'react';
+import PropTypes from 'prop-types';
+import { Button, message } from "antd";
+import moment from 'moment';
+import XLSX from 'xlsx';
+import { fromJS } from 'immutable';
+import { Request } from '@peace/utils';
+import FileSaver from 'file-saver';
+import { DownOutlined } from '@ant-design/icons';
+
+//通用前端导出组件  使用方法查看底部propTypes
+const ExportData = ({...props}) => {
+    //const [form] = Form.useForm();
+    const [exportLoading, setExportLoading] = useState(false);
+    const { customRender, title, exportType, style, showIcon } = props;
+   
+
+    const loop = (data, keypath, values) => { // deal with array
+        let dkey = keypath.slice(0, 1)[0];
+        if (dkey) {
+            let dvalue = data[dkey];
+            let otherKeypath = keypath.slice(1);
+            if (Array.isArray(dvalue)) {
+                if (otherKeypath.length) {
+                    let immutableData = fromJS(data);
+                    for (let index = 0; index < dvalue.length; index++) {
+                        let tmp = immutableData.getIn([dkey, index]).toJS();
+                        loop(tmp, otherKeypath, values);
+                    }
+                }
+            } else {
+                values.push(dvalue);
+            }
+        }
+        return values;
+    };
+    const getColumnData = (opts) => {
+        const { data, keypath, render, spliter, rawdata, valueEnum } = opts;
+        let v = null;
+        let outer = data[keypath[0]];
+
+        if (Array.isArray(outer)) {
+            let values = loop(data, keypath, []);
+            v = rawdata ? values : values.join(spliter || ',');
+        } else {
+            v = fromJS(data).getIn(keypath);
+        }
+        //处理proTable 枚举
+        if(valueEnum && valueEnum[v]?.text){
+           v =  valueEnum[v]?.text;
+        }
+        //处理render
+        // if (render && typeof render === 'function') {
+        //     v = render(outer, data);
+        // }
+        
+        return v;
+    };
+    const getDataSource = (attrs, filterData) => {
+     
+        let dataSource = filterData.map(item => {
+            let record = {};
+            attrs.forEach(attr => {
+                const { key, dataIndex, render, child, valueEnum } = attr;
+                
+                if (child) {
+                 
+                    record[key] = getDataSource(child, item[key] || []);
+                } else {
+                  
+                    let v = getColumnData({
+                        data: item,
+                        keypath: Array.isArray(dataIndex) ? dataIndex : [dataIndex],
+                        render: render || null,
+                        valueEnum: valueEnum
+                    });
+                    record[key] = v;
+                }
+
+
+            });
+
+            return record;
+        });
+       
+        return dataSource;
+        
+        
+    };
+
+    const getNewColumns = (attrs) => {
+        return attrs.filter(f=> f.dataIndex).map(v=>{
+           const { dataIndex } = v;
+           return {
+               ...v,
+               key: Array.isArray(dataIndex) ? dataIndex.reduce((p,c)=>{
+                    p = `${p}${c.trim().replace(c[0], c[0].toUpperCase())}`;
+                    return p
+               },'') : dataIndex
+           }
+        })
+    }
+    //暂时只处理两层 
+    const getFlatData = (attrs, filterData, dataToAoa, deep = 0) => {
+
+        filterData.map(item => {
+            let cur = dataToAoa[deep]
+            if (!cur) {
+                cur = dataToAoa[deep] = []
+            }
+            attrs.map((attr, index) => {
+                const { key, child } = attr;
+                if (child) {
+                    if (Array.isArray(item[key])) {
+                        //getFlatData(child,item[key],dataToAoa,deep)
+
+                        item[key].map((s, i) => {
+                            if (i == 0) {
+                                child.map(c => {
+                                    cur.push(s[c.key]);
+                                })
+                            } else {
+                                deep++
+                                let childCur = dataToAoa[deep] = []
+                                pushNull(childCur, index);
+                                child.map(c => {
+                                    childCur.push(s[c.key]);
+                                });
+                            }
+
+                        })
+
+                    }
+                } else {
+                    cur.push(item[key]);
+                }
+
+            });
+            deep++
+        });
+
+
+    };
+
+    const getHeader = (headers, excelHeader, deep, perOffset) => {
+        let offset = 0
+        let cur = excelHeader[deep]
+        if (!cur) {
+            cur = excelHeader[deep] = []
+        }
+        pushNull(cur, perOffset - cur.length)
+        for (let i = 0; i < headers.length; i++) {
+            let head = headers[i]
+            cur.push(head.name)
+            if (head.hasOwnProperty('child') && Array.isArray(head.child) && head.child.length > 0) {
+                let childOffset = getHeader(head.child, excelHeader, deep + 1, cur.length - 1)
+                pushNull(cur, childOffset - 1)
+                offset += childOffset
+            } else {
+                offset++
+            }
+        }
+        return offset;
+    }
+
+    const pushNull = (arr, count) => {
+        for (let i = 0; i < count; i++) {
+            arr.push(null)
+        }
+    }
+    const fillNull = (arr) => {
+        let max = Math.max(...(arr.map(a => a.length)))
+        arr.filter(e => e.length < max).forEach(e => pushNull(e, max - e.length))
+    }
+    const doMerges = (arr) => {
+        // 要么横向合并 要么纵向合并
+        let deep = arr.length;
+        let merges = [];
+        for (let y = 0; y < deep; y++) {
+            // 先处理横向合并
+            let row = arr[y];
+            let colSpan = 0
+            for (let x = 0; x < row.length; x++) {
+                if (row[x] === null) {
+                    colSpan++
+                    if (((x + 1) === row.length) && (colSpan > 0 && x > colSpan)) {
+                        merges.push({ s: { r: y, c: x - colSpan }, e: { r: y, c: x } })
+                    }
+                } else if (colSpan > 0 && x > colSpan) {
+                    merges.push({ s: { r: y, c: x - colSpan - 1 }, e: { r: y, c: x - 1 } })
+                    colSpan = 0
+                } else {
+                    colSpan = 0
+                }
+            }
+        }
+        // 再处理纵向合并
+        let colLength = arr[0].length
+        for (let x = 0; x < colLength; x++) {
+            let rowSpan = 0
+            for (let y = 0; y < deep; y++) {
+                if (arr[y][x] != null) {
+                    rowSpan = 0
+                } else {
+                    rowSpan++;
+                }
+            }
+            if (rowSpan > 0) {
+                merges.push({ s: { r: deep - rowSpan - 1, c: x }, e: { r: deep - 1, c: x } })
+            }
+        }
+        return merges;
+    }
+    
+    //内容暂只出了纵向合并
+    const doContetMerges = (arr, headerLength) => {
+        let deep = arr.length;
+        let merges = [];
+        //处理纵向合并
+        let colLength = arr[0].length
+        for (let x = 0; x < colLength; x++) {
+            let rowSpan = 0;
+            let mergY = 0;
+            for (let y = 0; y < deep; y++) {
+                if (rowSpan > 0) {
+                    //如果还有null 继续加
+                    if (arr[y][x] === null) {
+                        rowSpan = rowSpan + 1
+                    } else {
+                        //不为null 增加merge
+                        merges.push({ s: { r: headerLength + (y - rowSpan - 1), c: x }, e: { r: headerLength + y - 1, c: x } });
+                        rowSpan = 0;
+                    }
+                } else {
+                    if (arr[y][x] === null) {
+                        rowSpan = rowSpan + 1
+                    }
+                }
+
+            }
+            if (rowSpan > 0) {
+                merges.push({ s: { r: headerLength + (deep - rowSpan - 1), c: x }, e: { r: headerLength + deep - 1, c: x } })
+                rowSpan = 0;
+            }
+        }
+        return merges;
+    }
+
+    //导出可以纵向合并单元格的数据 不建议使用
+    const exportMergeExcel = async () => {
+        setExportLoading(true)
+        const { columns, data, fileName, exportUrl, exportQuery, exportBody, requestType, header, showYearMouth } = props || {};
+
+        let resultData = [];
+        if (exportUrl) {
+
+            resultData = requestType == 'post' ? await Request.post(exportUrl, exportBody || {}, exportQuery || {}).then(data => {
+                //数据接口返回的结果 如果是对象 必须把返回数组放入rows
+                if (typeof data === 'object' && data.rows) {
+
+                    return data.rows
+
+                } else {
+                    return data;
+                }
+            }, err => {
+                message.error('获取数据失败,导出失败!');
+            }) : await Request.get(exportUrl, exportQuery || {}).then(data => {
+                if (typeof data === 'object' && data.rows) {
+
+                    return data.rows
+
+                } else {
+                    return data;
+                }
+            }, err => {
+                message.error('获取数据失败,导出失败!');
+            });
+            if (!resultData) {
+                return;
+            }
+
+        } else {
+            resultData = data
+        }
+        let excelHeader = [];
+        const newColumns = getNewColumns(columns);
+        getHeader(newColumns, excelHeader, 0, 0);
+        fillNull(excelHeader);
+
+        //console.log(excelHeader);
+
+        let loopData = getDataSource(newColumns, resultData);
+        //console.log(loopData)
+
+        let dataToAoa = [];
+        getFlatData(newColumns, loopData, dataToAoa, 0);
+        fillNull(dataToAoa);
+        //console.log(dataToAoa);
+
+        let aoa = [].concat(excelHeader, dataToAoa);
+        //console.log(aoa)
+
+        let headerMerges = doMerges(excelHeader);
+        let contentMerages = doContetMerges(dataToAoa, excelHeader.length);
+        let merges = [].concat(headerMerges, contentMerages);
+        // console.log(contentMerages)
+
+        // let opts = {
+        //     defaultCellStyle: {
+        //         font: { name: "宋体", sz: 11, color: { auto: 1 } },
+        //         border: {
+        //             color: { auto: 1 }
+        //         },
+        //         alignment: {
+        //             /// 自动换行
+        //             wrapText: 1,
+        //             // 居中
+        //             horizontal: "center",
+        //             vertical: "center",
+        //             indent: 0
+        //         }
+        //    }
+        // }
+        let sheet = XLSX.utils.aoa_to_sheet(aoa);
+        // let newSheet = {}; 
+        // for (let [key, value] of Object.entries(sheet)) {
+        //     if(key == '!ref'){
+        //         newSheet[key] = value
+        //     }else if(typeof value === 'object'){
+        //         newSheet[key] = {
+        //             ...value,
+        //             s: opts.defaultCellStyle
+        //         }
+        //     }
+        // }
+        const wpx = columns.map(c => {
+            return {
+                wpx: Number.parseInt(c.wpx) ? Number.parseInt(c.wpx) : 100
+            }
+        })
+        sheet['!cols'] = wpx;
+        sheet['!merges'] = merges;
+
+        // 构建 workbook 对象
+        const workbook = XLSX.utils.book_new();
+
+        const time = moment().format('YYYY-MM-DD');
+
+
+        XLSX.utils.book_append_sheet(workbook, sheet, 'mySheet');
+        // 导出 Excel
+        XLSX.writeFile(workbook, fileName ? `${fileName}-${time}.xlsx` : `导出数据-${time}.xlsx`);
+        setExportLoading(false);
+        message.success(`成功导出了 ${loopData.length || 0} 条数据`);
+    }
+    //FileSaver 方式导出可以自定义样式 columns可定义 headStyle, rowStyle
+    const exportFileSaver = async () => {
+        setExportLoading(true)
+        const { columns, data, fileName, exportUrl, exportQuery, exportBody, requestType } = props || {};
+        let resultData = [];
+        if (exportUrl) {
+            resultData = requestType == 'post' ? await Request.post(exportUrl, exportBody || {}, exportQuery || {}).then(data => {
+                //数据接口返回的结果 如果是对象 必须把返回数组放入rows
+                if (typeof data === 'object') {
+                    return data.data ? data.data : data.rows
+                } else {
+                    return data;
+                }
+            }, err => {
+                message.error('获取数据失败,导出失败!');
+            }) : await Request.get(exportUrl, exportQuery || {}).then(data => {
+             
+                if (typeof data === 'object' && data.rows) {
+                    return data.rows
+                } else {
+                    return data;
+                }
+            }, err => {
+                message.error('获取数据失败,导出失败!');
+            });
+            if (!resultData) {
+                return;
+            }
+
+        } else {
+            resultData = data
+        }
+        const newColumns = getNewColumns(columns);
+
+        const loopData = getDataSource(newColumns, resultData);
+
+        let content = '';
+        let header = '
';
+        //header += `序号  | `;
+        newColumns.map(colum => {
+            header += `${colum.title}  | `
+        });
+        header += '
';
+        loopData.map(data => {
+                content += ``;
+                newColumns.map(c => {
+                    if (c.style) {
+                        content += `${data[c.key] || ''}  | `
+                    } else {
+                        content += `${data[c.key] || ''}  | `
+                    }
+                });
+                content += `
`;
+            })
+
+        let exportTable = `\uFEFF
+                
+                    ${header}
+                    ${content}
+                
+            `;
+        const time = moment().format('YYYY-MM-DD');
+        let tempStrs = new Blob([exportTable], { type: 'text/xls' })
+        FileSaver.saveAs(tempStrs, fileName ? `${fileName}-${time}.xls` : `导出数据-${time}.xlsx`);
+        setExportLoading(false);
+        message.success(`成功导出了 ${loopData.length || 0} 条数据`);
+    }
+
+    //普通XLSX导出
+    const exportExcel = async () => {
+        setExportLoading(true)
+        const { columns, data, fileName, exportUrl, exportQuery, exportBody, requestType } = props || {};
+
+        const newColumns = getNewColumns(columns);
+       
+        const _headers = newColumns
+            .map((item, i) => Object.assign({}, { key: item.key, title: item.title, position: String.fromCharCode(65 + i) + 1 }))
+            .reduce((prev, next) => Object.assign({}, prev, { [next.position]: { key: next.key, v: next.title } }), {});
+        let resultData = [];
+        if (exportUrl) {
+            resultData = requestType == 'post' ? await Request.post(exportUrl, exportBody || {}, exportQuery || {}).then(data => {
+                //数据接口返回的结果 如果是对象 必须把返回数组放入rows
+                
+                if (typeof data === 'object' && (data.rows || data.data)) { 
+                    return data.data ? data.data : data.rows
+                } else {
+                    return data;
+                }
+            }, err => {
+                message.error('获取数据失败,导出失败!');
+            }) : await Request.get(exportUrl, exportQuery || {}).then(data => {
+                if (typeof data === 'object' && data.rows) {
+                    return data.rows
+
+                } else {
+                    return data;
+                }
+            }, err => {
+                message.error('获取数据失败,导出失败!');
+            });
+            if (!resultData) {
+                return;
+            }
+
+        } else {
+            resultData = data
+        }
+      
+        const loopData = getDataSource(newColumns, resultData);
+     
+
+        const wpx = newColumns.map(c => {
+            return {
+                wpx: Number.parseInt(c.wpx) ? Number.parseInt(c.wpx) : 100
+            }
+        })
+        if (!(loopData.length > 0)) {
+            setExportLoading(false);
+            return;
+        }
+        const _data = loopData
+            .map((item, i) => newColumns.map((key, j) => Object.assign({}, { content: item[key.key], position: String.fromCharCode(65 + j) + (i + 2) })))
+            // 对刚才的结果进行降维处理(二维数组变成一维数组)
+            .reduce((prev, next) => prev.concat(next))
+            // 转换成 worksheet 需要的结构
+            .reduce((prev, next) => Object.assign({}, prev, { [next.position]: { v: next.content } }), {});
+
+        // 合并 columns 和 data
+        const output = Object.assign({}, _headers, _data);
+        // 获取所有单元格的位置
+        const outputPos = Object.keys(output);
+        // 计算出范围 ,["A1",..., "H2"]
+        const ref = `${outputPos[0]}:${outputPos[outputPos.length - 1]}`;
+
+        // 构建 workbook 对象
+        const workbook = {
+            SheetNames: ['mySheet'],
+            Sheets: {
+                mySheet: Object.assign(
+                    {},
+                    output,
+                    {
+                        '!ref': ref,
+                        '!cols': wpx,
+                    },
+                ),
+            },
+        };
+        const time = moment().format('YYYY-MM-DD');
+        // 导出 Excel
+        XLSX.writeFile(workbook, fileName ? `${fileName}-${time}.xlsx` : `导出数据-${time}.xlsx`);
+        setExportLoading(false);
+        message.success(`成功导出了 ${loopData.length || 0} 条数据`);
+    }
+
+  
+    const handleExport = async () => {
+       switch (exportType) {
+           case 'fileSaver':
+               await exportFileSaver();
+           break;
+           case 'xlsx':
+               await exportExcel();
+           break;
+           case 'merge':
+               await exportMergeExcel();
+           break;
+           default:
+               await exportExcel();
+           break;
+       }
+    }
+   
+    return (
+           customRender ? 
+           
+               {customRender}
+            :
+
+                
+    )
+}
+
+ExportData.propTypes = {
+    fileName: PropTypes.string, //导出文件名称前缀
+    showIcon: PropTypes.bool, //导出按钮是否显示icon,默认不显示
+    customRender: PropTypes.element, //自定义导出组件渲染 不传默认按钮样式
+    style: PropTypes.object,//透传style
+    title: PropTypes.string, //导出按钮文字
+    columns: PropTypes.array.isRequired, //导出显示的header数组 兼容antd columns 可直接拿table或者protable的columns使用  注:columns每列的属性wpx设置导出的execl每列的宽度值 默认 100
+    data: PropTypes.array.isRequired,   //导出的数据 兼容antd table 数组嵌套处理,如果传入exportUrl 则从接口获取数据导出,此参数无效
+    exportUrl: PropTypes.string,  //导出数据从接口获取的url地址   返回的数据1、数组必须支持columns的设置 ,2、如果是对象,数组需放在rows属性上
+    exportBody: PropTypes.object, //导出数据接口body参数
+    exportQuery: PropTypes.object,  //导出数据从接口获取的url地址上的参数
+    requestType: PropTypes.string, //请求类型 get,post,默认get
+    exportType: PropTypes.string, //导出执行类型函数 'fileSaver','xlsx','merge'纵向单元格合并
+};
+
+export default ExportData;
diff --git a/web-network/client/src/sections/network/containers/device-monitor.js b/web-network/client/src/sections/network/containers/device-monitor.js
index 1b7bf18..879153f 100644
--- a/web-network/client/src/sections/network/containers/device-monitor.js
+++ b/web-network/client/src/sections/network/containers/device-monitor.js
@@ -14,7 +14,7 @@ import { DeviceTypes } from '../constant';
 import qs from "qs";
 
 import '../style.less';
-// import  TableShow from './tableShow'
+import  TableShow from './tableShow'
 function DeviceMonitor ({ ...props }) {
    const {
       dispatch, actions, user, clientWidth, clientHeight, loading,
@@ -199,8 +199,7 @@ console.log(3213,actions);
                         />
                      ) : 
                   : (
-                     
-                     //   
+                       
                   )
             }
          
diff --git a/web-network/client/src/sections/network/containers/tableShow.js b/web-network/client/src/sections/network/containers/tableShow.js
new file mode 100644
index 0000000..6b0eb61
--- /dev/null
+++ b/web-network/client/src/sections/network/containers/tableShow.js
@@ -0,0 +1,332 @@
+import React, { useEffect, useState, useRef, useMemo } from 'react'
+import { connect } from 'react-redux'
+import { Spin, Card, CardGroup, Form,Select ,Input, Button, Table, Pagination, Tooltip } from 'antd'
+import ExportData from '../components/export-data'
+import moment from 'moment'
+
+const Network = props => {
+  const { dispatch, actions, user, clientHeight, thingId, deviceListAlarms, devicesCardStatusList, project } = props
+  const { analysis } = actions
+  const form = useRef() //表单
+  const [deployData, setDeployData] = useState([])
+  const [deviceData, setDeviceData] = useState([])
+  const [deviceMetasDeployed, setDeviceMetasDeployed] = useState([])
+  const [sensorId, setSensorId] = useState([])
+  const [sensorsDataItems, setSensorsDataItems] = useState({})
+  const [tableData, setTableData] = useState([]) //最新一次的数据
+  const [lastData, setLastData] = useState([]) //最终数据
+  const [lastDataCopy, setLastDataCopy] = useState([]) //最终数据
+  const [searchType, setSearchType] = useState('')
+  const [searchName, setSearchName] = useState('')
+  const [typeList, setTypeList] = useState([])
+  const [query, setQuery] = useState({ limit: 10, page: 0 }) //页码信息
+
+  const DeviceTypes = {
+    'DTU': 'DTU',
+    'gateway': '网关',
+    'sensor': '传感器',
+    'acqUnit': '采集单元',
+    'dau.gateway': '分布式智能云采集网关',
+    'dau.node': '分布式智能云采集节点',
+    'tcp.dtu': '工作站',
+  }
+
+  useEffect(() => {
+    setLastData([])
+    setLastDataCopy([])
+  }, [project])
+
+  useEffect(() => {
+    if (thingId) {
+      let dataList = []
+      dispatch(analysis.getThingsDeploy(thingId)).then(rs => {
+        if (rs.success) {
+          setDeployData(rs.payload.data)
+          dataList = rs.payload.data
+          //列表渲染数据
+          let da = []
+          if (dataList.instances) {
+            Object.keys(dataList.instances).forEach(i => {
+              if (dataList.instances[i].type == 's.d') {
+                da.push({
+                  sensorId: i,
+                  sensorName: dataList.instances[i]?.name,
+                  deviceType: dataList?.instances[i]?.instance?.properties?.deviceType,
+                  collectTime: '--',
+                  data: '--',
+                  iotCardStatus: '--',
+                  status: '--',
+                  option: '--',
+                })
+              }
+            })
+          }
+
+          dispatch(analysis.findDeviceMetaDeployed(thingId)).then(res => {
+            if (res.success) {
+              setDeviceMetasDeployed(res.payload.data)
+              const deviceMetaDeployed = res.payload.data
+              if (deviceMetaDeployed && dataList && deviceMetaDeployed.devices) {
+                const sensorsId = []
+                let alarmSensorId = [] //所有设备的id
+                const sensorsDataItems = {}
+                for (const id in dataList.instances) {
+                  alarmSensorId.push(id)
+                  const instances = dataList.instances[id]
+
+                  if (instances.type == 's.d' && instances.instance.properties.deviceType == 'sensor') {
+                    const meta = deviceMetaDeployed.devices.find(m => m.id == instances.instance.deviceMetaId)
+                    sensorsDataItems[id] = {
+                      items: {},
+                      deviceName: instances.name,
+                    }
+                    if (meta) {
+                      sensorsDataItems[id].items = meta.capabilities[0].properties.reduce((p, n) => {
+                        if (n.category == 'Output') {
+                          p[n.name] = { name: n.showName, unit: n.unit }
+                        }
+                        return p
+                      }, {})
+                    }
+                    sensorsId.push(id)
+                  }
+                }
+                dispatch(analysis.getDevicesAlarms({ deviceIds: alarmSensorId }, { limit: 5 }))
+                dispatch(analysis.findDevicesCardStatus({ deviceIds: alarmSensorId }))
+                setSensorsDataItems(sensorsDataItems)
+                setSensorId(sensorsId)
+                setDeviceData(da)
+              }
+            }
+          })
+        }
+      })
+    }
+  }, [thingId])
+  useEffect(async () => {
+    if (sensorId && sensorId.length && sensorsDataItems) {
+      const rs = await dispatch(analysis.findSensorLastData(sensorId))
+      const tableData = []
+      if (rs.success) {
+        rs.payload.data.forEach(sd => {
+          if (Object.keys(sensorsDataItems).length) {
+            let sensorDataItem = sensorsDataItems[sd.sensorId]
+            let sensorName = sensorDataItem && sensorDataItem.deviceName ? sensorDataItem.deviceName : ''
+            let msg = sd.data.length
+              ? sd.data[0]
+              : {
+                  collectTime: null,
+                  sensorName: sensorName,
+                  data: { noData: '暂无数据' },
+                }
+            let dataStr = ''
+            let dataKeys = Object.keys(msg.data)
+            dataKeys.forEach(k => {
+              let item = sensorDataItem && sensorDataItem.items ? sensorDataItem.items[k] : null
+              if (item) {
+                dataStr += `${item.name}:${msg.data[k]}(${item.unit}); `
+              } else if (k == 'noData') {
+                dataStr += msg.data[k]
+              } else {
+                dataStr += `${k}:${msg.data[k]};`
+              }
+            })
+            let collectTime = msg.collectTime ? moment(msg.collectTime).format('YYYY-MM-DD HH:mm:ss') : '--'
+            tableData.push({
+              sensorId: sd.sensorId,
+              sensorName: sensorName,
+              collectTime: collectTime,
+              data: dataStr,
+              deviceType: 'sensor', //传感器
+              iotCardStatus: '--',
+              status: '--',
+              option: '--',
+            })
+          }
+        })
+      }
+      setTableData(tableData)
+    }
+  }, [sensorId])
+  useEffect(() => {
+    if (deviceData && deviceData.length ) {
+      const dataD = deviceData?.map(p => {
+        const objRslt = tableData?.find(q => q.sensorId == p.sensorId)
+        return {
+          sensorId: objRslt ? objRslt.sensorId : p.sensorId,
+          sensorName: objRslt ? objRslt.sensorName : p.sensorName,
+          collectTime: objRslt ? objRslt.collectTime : p.collectTime,
+          data: objRslt ? objRslt.data : p.data,
+          deviceType: DeviceTypes[objRslt ? objRslt.deviceType : p.deviceType],
+          iotCardStatus:
+            devicesCardStatusList && devicesCardStatusList.length
+              ? devicesCardStatusList.find(v => v.deviceId == p.sensorId).status === 0
+                ? '正常'
+                : devicesCardStatusList.find(v => v.deviceId == p.sensorId).status === 1
+                ? '未激活'
+                : '停机'
+              : '--',
+          status:
+            deviceListAlarms && deviceListAlarms.length
+              ? deviceListAlarms?.find(v => v.deviceId == p.sensorId)
+                ? '异常'
+                : '正常'
+              : '--',
+          option: objRslt ? objRslt.option : p.option,
+        }
+      })
+      const typeList = dataD.reduce((p, c) => {
+        let isExist = p.some(q => q.label === c.deviceType)
+        if (!isExist) {
+          p.push({ label: c.deviceType, value: c.sensorId })
+        }
+        return p
+      }, [])
+      setTypeList(typeList)
+      setLastData(dataD)
+      setLastDataCopy(dataD)
+    }
+  }, [deviceData])
+  //   const lastDataCopy=useMemo(()=>{
+  //       return lastData
+  //   },[thingId])
+  const scroll = useMemo(() => ({ y:clientHeight-600+175+175 }), [])
+  //名称回调事件
+  const inputChange = e => {
+    setSearchName(e.target.value)
+  }
+  //选择设备类型下拉框回调
+  const selectChange = e => {
+    let rslt=typeList.find(f => f.value == e)
+    setSearchType(rslt?rslt.label:undefined)
+  }
+
+  //查询事件回调
+  const searchHandler = () => {
+    setLastData(
+      lastDataCopy.filter(f => 
+        (!searchName || f.sensorName.includes(searchName)) &&
+        (!searchType|| f.deviceType===searchType)
+      )
+    )
+  }
+
+  const columns = [
+    {
+      title: '设备名称',
+      dataIndex: 'sensorName',
+      width: '20%',
+      key: 'sensorName',
+      render: (_, r) => {
+        return (
+          <>
+            
+              {r.sensorName.length > 7 ? `${r.sensorName.substr(0, 7)}...` : r.sensorName}
+            
+          >
+        )
+      },
+    },
+    {
+      title: '设备类型',
+      dataIndex: 'deviceType',
+      width:  '15%',
+      key: 'deviceType',
+    },
+    {
+      title: '最后采集时间',
+      dataIndex: 'collectTime',
+      width:  '15%',
+      key: 'collectTime',
+    },
+    {
+      title: '数据',
+      dataIndex: 'data',
+      width: '20%',
+      key: 'data',
+      render: (_, r) => {
+        return (
+          <>
+            
+              {r.data.length > 6 ? `${r.data.substr(0, 6)}...` : r.data}
+            
+          >
+        )
+      },
+    },
+    {
+      title: '物联网卡状态',
+      width: '15%',
+      dataIndex: 'iotCardStatus',
+      key: 'iotCardStatus',
+    },
+    {
+      title: '状态',
+      width:  '10%',
+      dataIndex: 'status',
+      key: 'status',
+    },
+    {
+      title: '操作',
+      width: '10%',
+      dataIndex: 'option',
+      key: 'option',
+    },
+  ]
+  return (
+    <>
+      
+        
+            }
+              label='名称' 
+              placeholder='请输入设备名称'
+              pure
+              allowClear
+              style={{ width: 260, marginRight: 12 }}
+              onChange={inputChange}/>
+              
+            
+        
+        
+          {' '}
+          {lastData.length ? (
+            
+          ) : (
+            ''
+          )}
+        
+      
 
+      
+    >
+  )
+}
+
+function mapStateToProps(state) {
+  const { auth, global, members, webSocket, deviceListAlarms, devicesCardStatus } = state
+  return {
+    user: auth.user,
+    actions: global.actions,
+    clientHeight: global.clientHeight,
+    deviceListAlarms: deviceListAlarms?.data || [],
+    devicesCardStatusList: devicesCardStatus?.data || [],
+  }
+}
+
+export default connect(mapStateToProps)(Network)