使用 react 获取使用全球捐赠 API 的慈善机构

Fetching the charities using the global giving API using react

我正在使用全球捐赠 API 制作慈善查找器应用程序。

我在 CharityFinderPage.js 组件中有两个下拉菜单和一个搜索按钮。现在单击搜索按钮,我想使用 themeId 获取慈善机构。终点是 https://api.globalgiving.org/api/public/projectservice/themes/{themeId}/projects

我知道在 handleClick 上我应该获取慈善机构,但是如何在 CharityFinderPage.js 组件的 handleClick 中获取 themeId 的值。

我想要的是在单击按钮时显示一个新的卡片组件,就像显示一张慈善卡片,上面填充了来自 API 的数据的字段,但首先我需要能够获得来自 API 的数据,然后我可以渲染一个新组件。

代码如下:



CharityFinderPage.js

const CharityFinderPage = () => {

  const handleClick = () => {
    console.log("inside handleclick")
  }

  return (
    <div style={containerStyle}>
      <h1>Charity Finder ❤️</h1>
      <h3>Search for charity</h3>
      <h4>
        Filter charities by personal search conditions. Use the dropdown below
        to see charities matching your criteria.
      </h4>

      <Themes />
      <Regions />
      <button onClick={handleClick}>Search</button>
    </div>
  )
}

export default CharityFinderPage

Themes.js

import React, { useEffect, useState } from "react"
import axios from "axios"
const url = `https://api.globalgiving.org/api/public/projectservice/themes.json?api_key=${process.env.REACT_APP_api_key}`

const Themes = () => {
  const [isLoading, setIsLoading] = useState(false)
  const [selectValue, setSelectValue] = useState("")
  const [themes, setThemes] = useState([])

  useEffect(() => {
    const fetchThemes = async () => {
      try {
        setIsLoading(true)
        const result = await axios.get(url)
        setThemes(result.data.themes.theme)
        setIsLoading(false)
      } catch (err) {
        console.log(err)
      }
    }
    fetchThemes()
  }, [])

  const handleChange = (event) => {
    console.log("inside handleChange", event.target.value)
    setSelectValue(event.target.value)
  }

  return (
    <div>
      {isLoading ? (
        <h4>Loading......</h4>
      ) : (
        <div>
          <label>Select theme: </label>
          <select onChange={handleChange} value={selectValue}>
            {themes.map((theme, id) => {
              return <option key={id}>{theme.name}</option> //{id} is the `themeId`
            })}
          </select>
        </div>
      )}
    </div>
  )
}

export default Themes

Regions 组件与 Themes.

完全相似

你可以做到这一点。

const CharityFinderPage = () => {
  const [themeId, setThemeId] = useState();
  const handleClick = () => {
    console.log("inside handleclick")
    // make call to endpoint with themeId
  }

  return (
    <div style={containerStyle}>
      <h1>Charity Finder ❤️</h1>
      <h3>Search for charity</h3>
      <h4>
        Filter charities by personal search conditions. Use the dropdown below
        to see charities matching your criteria.
      </h4>

      <Themes setThemeId={setThemeId} />
      <Regions />
      <button onClick={handleClick}>Search</button>
    </div>
  )
}

export default CharityFinderPage

然后在Themes.js:

...

const handleChange = (event) => {
  console.log("inside handleChange", event.target.value)
  props.setThemeId(event.target.value);
  setSelectValue(event.target.value)
}

...

所以你在这里需要做的事情叫做提升状态。

您需要将主题组件的状态移动到 CharityFinder 组件

我只提升 selectedValue,因为这就是您所需要的

CharityFinderPage.js

const CharityFinderPage = () => {

  const [selectValue, setSelectValue] = useState("")



  const handleClick = () => {
    console.log(`inside handleclick with ${selectValue}`)
  }

  return (
    <div style={containerStyle}>
      <h1>Charity Finder ❤️</h1>
      <h3>Search for charity</h3>
      <h4>
        Filter charities by personal search conditions. Use the dropdown below
        to see charities matching your criteria.
      </h4>

// you can pass the setSelectValue as prop to Themes component
      <Themes setSelectValue={setSelectValue} selectValue={selectValue} />
      <Regions />
      <button onClick={handleClick}>Search</button>
    </div>
  )
}

export default CharityFinderPage

Theme.js

import React, { useEffect, useState } from "react"
import axios from "axios"
const url = `https://api.globalgiving.org/api/public/projectservice/themes.json?api_key=${process.env.REACT_APP_api_key}`

const Themes = ({ selectValue, setSelectValue }) => {
  const [isLoading, setIsLoading] = useState(false)
  const [themes, setThemes] = useState([])

  useEffect(() => {
    const fetchThemes = async () => {
      try {
        setIsLoading(true)
        const result = await axios.get(url)
        setThemes(result.data.themes.theme)
        setIsLoading(false)
      } catch (err) {
        console.log(err)
      }
    }
    fetchThemes()
  }, [])

  const handleChange = (event) => {
    console.log("inside handleChange", event.target.value)
    setSelectValue(event.target.value)
  }

  return (
    <div>
      {isLoading ? (
        <h4>Loading......</h4>
      ) : (
        <div>
          <label>Select theme: </label>
          <select onChange={handleChange} value={selectValue}>
            {themes.map((theme, id) => {
              return <option key={id}>{theme.name}</option> //{id} is the `themeId`
            })}
          </select>
        </div>
      )}
    </div>
  )
}

export default Themes