如何使用状态为ReactJS

时间:2019-06-20 04:41:12

标签: javascript reactjs

我想知道如何在状态下使用对象创建新的空白数组,以及如何使用setState在其中添加元素。

我想要数组:

newhosts: [
      {
      activityState : "",
      platform: "",
      pushDate: "",
      name: "",
      ip: "",
      software: [{
        vulnerability: {
          link: "",
          desc: "",
          cvss: "",
          cve: ""
        },
        vulnerable: '',
        cpe: "",
        version: "",
        vendor: "",
        name: ""

      }]
      }
    ] 

可以吗,所以要在状态中声明数组? 我如何添加以后的描述项目(例如,主机的描述,然后是其上所有软件元素的描述)。以及如何将两个软件添加到同一主机?

 const namearray= this.state.filteredhosts.map(host=> {
        return (
           host.software.map((sub, subindex) => { 

          if(selectedOption==="name" || selectedOption==="vendor") {
            if(sub[selectedOption]=== writtenOption){


            newState.push(host.meta.name)
            newState.push(host.meta.ip)
            newState.push(sub.name) 
            newState.push(sub.vendor)
          }

         }
          else { 
            if(sub.vulnerable===true){
            newState.push(sub.vulnerability[selectedOption])}
            newState.push(host.meta.name)
            newState.push(host.meta.ip)  
          }
        })
        )
      })

在这里,我必须用您的函数替换此“ newState.push”,以将数据保存到状态。

2 个答案:

答案 0 :(得分:2)

我认为您有此数据

state = {
   newhosts : [{hostdata1}, {hostdata2}]
}

添加主机描述

function addHostDescription = (selectHostIp) => {
    const copyState = [...this.state.newhosts];
    const hostIndex = copyState.findIndex(host => host.ip === selectHostIp);
    copyState[hostIndex] = {...copyState[hostIndex], description : 'description content'};
    this.setState({
        newhosts : copyState
    })
}

添加新软件

function addNewSoftware = (selectHostIp, newSoftware) => {
    const copyState = [...this.state.newhosts];
    const hostIndex = copyState.findIndex(host => host.ip === selectHostIp);
    copyState[hostIndex].software.push(newSoftware);
    this.setState({
        newhosts : copyState
    })
}

添加新主机

function addNewHost = (newHost) => {
    const copyState = [...this.state.newhosts];
    copyState.push(newHost);
    this.setState({
        newhosts : copyState
    })
}

答案 1 :(得分:0)

将数组作为状态值是完全有效的。考虑一下我为您制作的沙箱:https://codesandbox.io/s/deeply-nested-inputs-mf70m

您的问题给了我一些启发,写出来的内容实际上教会了我很多有关处理嵌套输入以及如何更新它们的信息。

此代码将向您展示如何:

  • 创建一个新的host对象以及相应的输入 用户填写。
  • 更新单个主机对象,它是第一层,例如字段activityStateplatform, 等
  • 更新主机内部的单个software对象,包括内部 vulnerability对象和外域,例如vulnerablecpe等。
  • 向主机添加新的software对象。然后更新 这些软件对象。

使用hostssoftware的任意组合填写表格,完成后,按Click to Log Hosts按钮以打印完成的state

代码:

import React from "react";
class App extends React.Component {
  state = {
    newhosts: [
      {
        activityState: "",
        platform: "",
        pushDate: "",
        name: "",
        ip: "",
        software: [
          {
            vulnerability: {
              link: "",
              desc: "",
              cvss: "",
              cve: ""
            },
            vulnerable: "",
            cpe: "",
            version: "",
            vendor: "",
            name: ""
          }
        ]
      }
    ]
  };

  handleOnChange = (event, hostindex, layer, softwareIndex) => {
    const { newhosts } = this.state;
    const copiedHosts = [...newhosts];
    const updatedHosts = copiedHosts.map((host, index) => {
      //find mathcing index to update that item
      if (hostindex === index) {
        //determine what layer of data we need to update
        if (layer === 1) {
          //we need to update activityState, platform etc...
          return {
            ...host,
            [event.target.name]: event.target.value
          };
        } else if (layer === 2) {
          //now we need to find the matching software item to update
          let updatedSoftware = copiedHosts[hostindex].software.map(
            (software, sIndex) => {
              if (softwareIndex === sIndex) {
                return {
                  ...software,
                  [event.target.name]: event.target.value
                };
              } else {
                return {
                  ...software
                };
              }
            }
          );
          return {
            ...host,
            software: updatedSoftware
          };
        } else if (layer === 3) {
          //now we need to find the matching software item to update
          let updatedSoftware = copiedHosts[hostindex].software.map(
            (software, sIndex) => {
              if (softwareIndex === sIndex) {
                return {
                  ...software,
                  vulnerability: {
                    ...software.vulnerability,
                    [event.target.name]: event.target.value
                  }
                };
              } else {
                return {
                  ...software
                };
              }
            }
          );
          return {
            ...host,
            software: updatedSoftware
          };
        }
      } else {
        //return all other hosts
        return host;
      }
    });
    this.setState({
      newhosts: updatedHosts
    });
  };

  createNewHostsForm = () => {
    const { newhosts } = this.state;

    return newhosts.map((host, hostIndex) => {
      return (
        <div>
          <h4>{`Host ${hostIndex + 1}`}</h4>
          {Object.entries(host).map(([key, value], lvl1Index) => {
            if (Array.isArray(value)) {
              const secondLayerInputs = [...value];
              return (
                <div>
                  <strong>software:</strong>
                  {secondLayerInputs.map((input, softwareIndex) => {
                    return Object.entries(input).map(([lvl2Key, lvl2Value]) => {
                      if (typeof lvl2Value === "string") {
                        return (
                          <div>
                            <label>{lvl2Key}</label>{" "}
                            <input
                              value={lvl2Value}
                              name={lvl2Key}
                              onChange={e =>
                                this.handleOnChange(
                                  e,
                                  hostIndex,
                                  2,
                                  softwareIndex
                                )
                              }
                            />
                          </div>
                        );
                      } else {
                        const thirdLayerInputs = { ...lvl2Value };
                        return Object.entries(thirdLayerInputs).map(
                          ([lvl3Key, lvl3Value]) => {
                            return (
                              <div>
                                <label>{lvl3Key}</label>{" "}
                                <input
                                  name={lvl3Key}
                                  value={lvl3Value}
                                  onChange={e =>
                                    this.handleOnChange(
                                      e,
                                      hostIndex,
                                      3,
                                      softwareIndex
                                    )
                                  }
                                />
                              </div>
                            );
                          }
                        );
                      }
                    });
                  })}
                  <button onClick={() => this.addSoftwareToHost(hostIndex)}>
                    Add Software
                  </button>
                </div>
              );
            } else {
              return (
                <div>
                  <label>{key}</label>{" "}
                  <input
                    value={value}
                    onChange={e => this.handleOnChange(e, hostIndex, 1)}
                    name={key}
                  />
                </div>
              );
            }
          })}
        </div>
      );
    });
  };

  addNewHost = () => {
    const newHostObj = {
      activityState: "",
      platform: "",
      pushDate: "",
      name: "",
      ip: "",
      software: [
        {
          vulnerability: {
            link: "",
            desc: "",
            cvss: "",
            cve: ""
          },
          vulnerable: "",
          cpe: "",
          version: "",
          vendor: "",
          name: ""
        }
      ]
    };
    this.setState({
      newhosts: [...this.state.newhosts, newHostObj]
    });
  };

  addSoftwareToHost = hostIndex => {
    const { newhosts } = this.state;
    const copiedHosts = [...newhosts];
    const newSoftwareObj = {
      vulnerability: {
        link: "",
        desc: "",
        cvss: "",
        cve: ""
      },
      vulnerable: "",
      cpe: "",
      version: "",
      vendor: "",
      name: ""
    };

    const updatedHosts = copiedHosts.map((host, index) => {
      if (hostIndex === index) {
        return {
          ...host,
          software: [...host.software, newSoftwareObj]
        };
      } else {
        return {
          ...host
        };
      }
    });

    this.setState({
      newhosts: updatedHosts
    });
  };

  handleSubmit = () => {
    console.log(this.state.newhosts);
  };

  render() {
    return (
      <div>
        {this.createNewHostsForm()}
        <div style={{ margin: "25px 0px" }}>
          {" "}
          <button onClick={this.addNewHost}>Add Host</button>
        </div>
        <button onClick={this.handleSubmit}>Click to Log Hosts</button>
      </div>
    );
  }
}