useStateで値を保持出来ない理由を知りたい
※友人への質問として記述している為、公に書いている訳ではございません。
解決したいこと
新規レビュー作成機能実装中で、useStateに上手く値を保持出来ない。
review_json.
{
review: {
user_id: 1,
company_id: companyInformation.companies.id,
review_category_id: reviewCategoryId,
review_content: content,
},
}
具体的には、
新規レビュー作成(POST_api)を、「投稿する」ボタンをクリックと同時に送っているが、
発生している問題・エラー
Response.
{"status":500,"errors":["Company must exist","Review category must exist","Enrollment must exist"]}
デベロッパーツールのNetworkでは、下記のような500エラーが発生する。
※一番右のEnrollmentに関しては、実装してないので予想通りだが、
CompanyとReview_categoryに関しては、実装していたつもりなので、予想外。
さらに、apiを叩いて、成功している場合はsuccesが呼ばれ、下記のような成功してるっぽい画面も出ている。
console.
{data: {…}, status: 200, statusText: "OK", headers: {…}, config: {…}, …}
config:
Content-Type: "application/json"
adapter: ƒ xhrAdapter(config)
data: "{"review":{"user_id":1,"review_content":"すぎゃの大冒険スペシャル"}}"
headers: {Accept: "application/json, text/plain, */*", Content-Type: "application/json;charset=utf-8"}
maxBodyLength: -1
maxContentLength: -1
method: "post"
timeout: 0
transformRequest: [ƒ]
transformResponse: [ƒ]
url: "http://localhost:3001/api/v1/companies/undefined/review_categories/undefined/reviews"
validateStatus: ƒ validateStatus(status)
xsrfCookieName: "XSRF-TOKEN"
xsrfHeaderName: "X-XSRF-TOKEN"
__proto__: Object
data:
errors: (3) ["Company must exist", "Review category must exist", "Enrollment must exist"]
status: 500
__proto__: Object
headers: {cache-control: "max-age=0, private, must-revalidate", content-type: "application/json; charset=utf-8"}
request: XMLHttpRequest {readyState: 4, timeout: 0, withCredentials: false, upload: XMLHttpRequestUpload, onreadystatechange: ƒ, …}
status: 200
statusText: "OK"
__proto__: Object
該当するソースコード
ReviewsNew.jsx
import React, { useEffect, useState } from 'react'
import axios from 'axios'
import { reviewsNew } from '../../urls/index'
import { SearchCompanies } from '../companies/SearchCompanies'
export const ReviewsNew = () => {
const [searchKeyWord, setSearchKeyWord] = useState('')
// 検索ワードを保持する
const handleChange = (e) => {
setSearchKeyWord(e.target.value)
}
// 検索ワードで企業を探す
const companyInformation = SearchCompanies(searchKeyWord)
// レビューコンテンツ
const [content, setContent] = useState('')
const [content2, setContent2] = useState('')
const [reviewCategoryId, setReviewCategoryID] = useState()
const handleSubmit = () => {
const body = {
review: {
user_id: 1,
company_id: companyInformation.companies.id,
review_category_id: reviewCategoryId,
review_content: content,
},
}
console.log(companyInformation, reviewCategoryId)
const headers = { 'Content-Type': 'application/json' }
axios
.post(
reviewsNew(companyInformation.companies.id, reviewCategoryId),
body,
headers
)
.then((response) => {
console.log('success', response)
alert('レポート投稿が成功しました')
})
.catch((error) => {
console.log('failed', error)
alert('投稿に失敗しました')
})
}
return (
<>
<input type="text" placeholder="医院で検索する" onChange={handleChange} />
<h4>組織体制 / 企業文化</h4>
<form>
<textarea
name="companyCulture"
value={content}
onChange={(event) => setContent(event.target.value)}
/>
<button
onClick={() => setReviewCategoryID(1)}
onClick={handleSubmit}
type="button"
>
この内容で投稿する
</button>
</form>
<h4>入職した理由</h4>
<form>
<textarea
name="JoinReason"
value={content2}
onChange={(event) => setContent2(event.target.value)}
/>
<button onClick={handleSubmit} type="button">
レポートを投稿する
</button>
</form>
</>
)
}
urls/index.js
const DEFAULT_API_LOCALHOST = 'http://localhost:3001/api/v1'
// ユーザー
export const usersNew = `${DEFAULT_API_LOCALHOST}/users`
export const usersLogin = `${DEFAULT_API_LOCALHOST}/login`
export const usersCheckLogin = `${DEFAULT_API_LOCALHOST}/logged_in`
export const usersShow = (id) => `${DEFAULT_API_LOCALHOST}/users/${id}`
export const usersEdit = (id) => `${DEFAULT_API_LOCALHOST}/users/${id}`
// 企業
export const companiesNew = `${DEFAULT_API_LOCALHOST}/companies`
export const companiesShow = (companyId) =>
`${DEFAULT_API_LOCALHOST}/companies/${companyId}`
export const companiesIndex = `${DEFAULT_API_LOCALHOST}/companies`
// 企業検索
export const search = (keyword) =>
`${DEFAULT_API_LOCALHOST}/companies/search?search=${keyword}`
// レビュー
export const reviewsNew = (companyId, reviewCategoryId) =>
`${DEFAULT_API_LOCALHOST}/companies/${companyId}/review_categories/${reviewCategoryId}/reviews`
export const reviewsShow = (companyId, reviewCategoryId, reviewId) =>
`${DEFAULT_API_LOCALHOST}/companies/${companyId}/review_categories/${reviewCategoryId}/reviews/${reviewId}`
export const reviewsIndex = (companyId, reviewCategoryId) =>
`${DEFAULT_API_LOCALHOST}/companies/${companyId}/review_categories/${reviewCategoryId}/reviews`
// レビューカテゴリー
export const reviewCategoriesIndex = (companyId) =>
`${DEFAULT_API_LOCALHOST}/companies/${companyId}/review_categories`
export const reviewCategoriesShow = (companyId, reviewCategoryId) =>
`${DEFAULT_API_LOCALHOST}/companies/${companyId}/review_categories/${reviewCategoryId}`
// 在籍情報
export const enrollmentsNew = `${DEFAULT_API_LOCALHOST}/enrollments`
SearchCompanies.js
import React, { useState, useEffect } from 'react'
import axios from 'axios'
const initialState = {
companies: [
{
id: null,
name: '',
},
],
}
export const SearchCompanies = (keyword) => {
const [companyList, setCompanyList] = useState(initialState)
const fetchCompany = (keyword) =>
axios
.get(`http://localhost:3001/api/v1/companies/search?search=${keyword}`)
.then((res) => {
return res.data
})
.catch((error) => {
console.log(error)
return { companies: [] }
})
useEffect(() => {
fetchCompany(keyword).then(
(data) => setCompanyList(data),
console.log(companyList)
)
}, [keyword])
return companyList
}
自分で試したこと
デバッグしていった結果、ReviewsNew.jsx
において、
reviewCategoryId
とreviewInformation
にstateを保持出来ていない事が分かった。
※console.logで2つとも表示させてようとしたが、undefind
となっていた。
イベントハンドラで発火させる場所が違っているかと思い、色々とstateを更新する箇所を変えてみたが、
変わらず更新出来なかった。
0