質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
87.20%
Firebase

Firebaseは、Googleが提供するBasSサービスの一つ。リアルタイム通知可能、並びにアクセス制御ができるオブジェクトデータベース機能を備えます。さらに認証機能、アプリケーションのログ解析機能などの利用も可能です。

Cloud Firestore

Cloud Firestore は、自動スケーリングと高性能を実現し、アプリケーション開発を簡素化するように構築された NoSQLドキュメントデータベースです。

React.js

Reactは、アプリケーションのインターフェースを構築するためのオープンソースJavaScriptライブラリです。

受付中

[firestore] [react] useCollectionDataでデータを取り出す際docIdがいつの間にかundefiedになっていた

DaisukeMori
DaisukeMori

総合スコア202

Firebase

Firebaseは、Googleが提供するBasSサービスの一つ。リアルタイム通知可能、並びにアクセス制御ができるオブジェクトデータベース機能を備えます。さらに認証機能、アプリケーションのログ解析機能などの利用も可能です。

Cloud Firestore

Cloud Firestore は、自動スケーリングと高性能を実現し、アプリケーション開発を簡素化するように構築された NoSQLドキュメントデータベースです。

React.js

Reactは、アプリケーションのインターフェースを構築するためのオープンソースJavaScriptライブラリです。

0回答

0評価

0クリップ

176閲覧

投稿2022/05/13 17:22

昔実装したReact + Firestoreの登録・削除機能を久しぶりに実装してみたところ登録は以前のようにできたのですが、削除が一向にされないという不具合が発生しました。

その原因を追求したところどうやらuseCollectionDataで呼び出し,
console.log(list.docId);docIdを出そうしたところ何故かundefiedになってしまいます。
docIdundefiedになるがゆえに
<div className="delete" onClick={() => handleDelete(item.docId)}>Delete</div>docIdが渡せず、削除が行われなくなっています。
数年前確実にdocIdが取得できておりもちろん削除も正常に行われていました。
この数年のうちにFirestore側で変更あったのでしょうか?
そしてFirestoreのdocIdを取得する方法を教えていただきたいです。

uploadのコード全文載せておきます。

jsx

import { useState } from 'react'; import firebase, { storage, db } from '../../Firebase'; import { useForm } from 'react-hook-form'; import { useCollectionData } from 'react-firebase-hooks/firestore'; const Upload = () => { // Create const [msg, setMsg] = useState(''); const [pending,setPending] = useState(false); // Upload const [image, setImage] = useState(''); const [imageUrl, setImageUrl] = useState(''); const { handleSubmit } = useForm(); // auth user const user = firebase.auth().currentUser; let authId; let email; let name; let photoURL; if (user != null) { user.providerData.forEach(() => { authId = user.uid; email = user.email; name = user.displayName; photoURL = user.photoURL; }); } // Create const createdAt = firebase.firestore.FieldValue.serverTimestamp(); const OnSubmit = async () => { setMsg(''); setImageUrl(''); setPending(true); try { await firebase .firestore() .collection('posts') .add({ msg, createdAt, imageUrl, // 以下firebase.auth().currentUser情報 authId, email, name, photoURL }); } finally { setPending(false); } } // Render const [ list, loading, error ] = useCollectionData(db.collection('posts').orderBy('createdAt', 'desc'), { idField: 'docId' }); console.log(list.docId); // undefiedになってしまう if (loading) return <div>Loading...</div>; if (error) return <div>Error...</div>; const result = Object.keys(list).length; // Countを数える console.log(result); // Delete const handleDelete = (uid) => { if (window.confirm('削除しますか?')) { db.collection('posts').doc(uid).delete(); } } // File upload const handleImage = e => { const image = e.target.files[0]; setImage(image); } const onSubmit = e => { e.preventDefault(); if (image === '') { console.log('ファイルが選択されていません'); } const uploadTask = storage.ref(`/images/${image.name}`).put(image); uploadTask.on( firebase.storage.TaskEvent.STATE_CHANGED, next, uploadError, complete ); } const next = snapshot => { const percent = (snapshot.bytesTransferred / snapshot.totalBytes) * 100; console.log(percent + '% done'); console.log(snapshot); } const uploadError = error => { console.log(error); } const complete = () => { storage .ref('images') .child(image.name) .getDownloadURL() .then(fireBaseUrl => { setImageUrl(fireBaseUrl); }); } return ( <> <form onSubmit={handleSubmit(OnSubmit)}> <textarea value={ msg } onChange={ e => setMsg(e.target.value) } placeholder="コメント" name="msg" > </textarea> {imageUrl && ( <> <input type="hidden" value={imageUrl} onChange={ e => setImageUrl(e.target.value) } name="image" /> </> )} <button type="submit">投稿</button> { pending && 'Pendeing...' } </form> <form onSubmit={onSubmit}> <input type="file" onChange={handleImage} /> <button>Upload</button> </form> {imageUrl && ( <> <img src={imageUrl} id="imgSample" alt="uploaded" /> </> )} {list.map(item => ( <div key={item.docId + String(new Date())}> {authId === item.authId ? ( <> {item.name ? ( <div>{item.name}</div> ) : ( <div>ゲストユーザー</div> )} <div> <div>{item.msg}</div> {/* docIdがundefiedになるため削除できない */} <div className="delete" onClick={() => handleDelete(item.docId)}>Delete</div> </div> {item.imageUrl && ( <img src={item.imageUrl} alt="イメージ画像" /> )} {item.photoURL ? ( <img src={ item.photoURL } alt="ユーザー画像" /> ) : ( <div>no image</div> )} </> ) : ( <> <div> {item.name ? ( <div>{item.name}</div> ) : ( <div>ゲストユーザー</div> )} <div> <div>{item.msg}</div> </div> {item.imageUrl && ( <img src={item.imageUrl} alt="イメージ画像" /> )} {item.photoURL ? ( <img src={ item.photoURL } alt="ユーザー画像" /> ) : ( <div>no image</div> )} </div> </> )} </div> ))} </> ); } export default Upload;

良い質問の評価を上げる

以下のような質問は評価を上げましょう

  • 質問内容が明確
  • 自分も答えを知りたい
  • 質問者以外のユーザにも役立つ

評価が高い質問は、TOPページの「注目」タブのフィードに表示されやすくなります。

気になる質問をクリップする

クリップした質問は、後からいつでもマイページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

teratailでは下記のような質問を「具体的に困っていることがない質問」、「サイトポリシーに違反する質問」と定義し、推奨していません。

  • プログラミングに関係のない質問
  • やってほしいことだけを記載した丸投げの質問
  • 問題・課題が含まれていない質問
  • 意図的に内容が抹消された質問
  • 過去に投稿した質問と同じ内容の質問
  • 広告と受け取られるような投稿

評価を下げると、トップページの「アクティブ」「注目」タブのフィードに表示されにくくなります。

まだ回答がついていません

会員登録して回答してみよう

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
87.20%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問

同じタグがついた質問を見る

Firebase

Firebaseは、Googleが提供するBasSサービスの一つ。リアルタイム通知可能、並びにアクセス制御ができるオブジェクトデータベース機能を備えます。さらに認証機能、アプリケーションのログ解析機能などの利用も可能です。

Cloud Firestore

Cloud Firestore は、自動スケーリングと高性能を実現し、アプリケーション開発を簡素化するように構築された NoSQLドキュメントデータベースです。

React.js

Reactは、アプリケーションのインターフェースを構築するためのオープンソースJavaScriptライブラリです。