Javascriptの、ローカルでnode実行するプログラムの開発をしています。
参考サイトのサンプル(回答1つ目、Maciej Caputaさんのもの)を参考に、Firestoreにjsonデータを登録するプログラムです。※参考というより、ロジック部はまるっと借用させて頂いてます
これを、固有箇所を私の情報・ファイル内容に置き換えて実行しているのですが、uploadという更新functionにて、エラー分岐(Could not write document~)に入ってしまっており、問題解決のラチが開かない感があるので、お助けを希望しています。
以下、ここまでに確認できていることの、具体的内容になります。
※記載情報に不足等あれば、その旨ご教示ください。
テスト実行における、インプットは以下です。
※問題箇所は、固有箇所の置き換えではない可能性が高い、と認識しています。
別参考サイトにて、同一指定情報で更新できている(こちらはCSVのみ対応、サブコレクション非対応)ため。
fakedb.json
json
1{ 2 "users" : { 3 "user1" : { 4 "field1" : "foo", 5 "field2" : "bar" 6 }, 7 "user2" : { 8 "field1" : "fog", 9 "field2" : "buzz", 10 "sub": { 11 "subUser1": { 12 "field3" : "foo", 13 "field4" : 4 14 }, 15 "subUser2": { 16 "field3" : "foobar", 17 "field4" : 5 18 } 19 } 20 } 21 } 22} 23
上記をInputにした場合の、結果console出力
node
1Could not write document users/user1. 2Could not write document users/user2/sub/subUser1. 3Could not write document users/user2. 4Could not write document users/user2/sub/subUser2. 5```→サブコレクションが含まれている場合に対応したimportツールのため、コレクション・サブコレクションの数分、繰り返し処理が発生します。当該繰り返し処理については、上記の内容で正しい理解です。 6 7### デバッグで確認できていること 8return await admin.firestore() の行にポインタを置いてデバッグすると、1周目だと、 9「path」という変数には、 (2) ['users', 'user1'] という配列、 10 →これは、ルートノードからのパス構成を配列を持っている理解です。 11「data」という変数には、{field1: 'foo', field2: 'bar'} というobjectが入っています。 12 →これが、登録したいデータの理解です。 13 14inputの(変数)データは、これで正しい理解なのですが、await ~ then catch における、catchのエラーの方に処理が流れてしまっております。 15 16### Firestore画面 17![イメージ説明](abefeedd17be60e88012bac2dd47dea2.png) 18…当該データにUpdateなりInsertなりが走ってほしいのです。 19 20### 参考コード(そのまま貼り付け) 21```ここに言語を入力 22const admin = require('../functions/node_modules/firebase-admin'); 23const serviceAccount = require("./service-key.json"); 24 25admin.initializeApp({ 26 credential: admin.credential.cert(serviceAccount), 27 databaseURL: "https://<your-database-name>.firebaseio.com" 28}); 29 30const data = require("./fakedb.json"); 31 32/** 33 * Data is a collection if 34 * - it has a odd depth 35 * - contains only objects or contains no objects. 36 */ 37function isCollection(data, path, depth) { 38 if ( 39 typeof data != 'object' || 40 data == null || 41 data.length === 0 || 42 isEmpty(data) 43 ) { 44 return false; 45 } 46 47 for (const key in data) { 48 if (typeof data[key] != 'object' || data[key] == null) { 49 // If there is at least one non-object item in the data then it cannot be collection. 50 return false; 51 } 52 } 53 54 return true; 55} 56 57// Checks if object is empty. 58function isEmpty(obj) { 59 for(const key in obj) { 60 if(obj.hasOwnProperty(key)) { 61 return false; 62 } 63 } 64 return true; 65} 66 67async function upload(data, path) { 68 return await admin.firestore() 69 .doc(path.join('/')) 70 .set(data) 71 .then(() => console.log(`Document ${path.join('/')} uploaded.`)) 72 .catch(() => console.error(`Could not write document ${path.join('/')}.`)); 73} 74 75/** 76 * 77 */ 78async function resolve(data, path = []) { 79 if (path.length > 0 && path.length % 2 == 0) { 80 // Document's length of path is always even, however, one of keys can actually be a collection. 81 82 // Copy an object. 83 const documentData = Object.assign({}, data); 84 85 for (const key in data) { 86 // Resolve each collection and remove it from document data. 87 if (isCollection(data[key], [...path, key])) { 88 // Remove a collection from the document data. 89 delete documentData[key]; 90 // Resolve a colleciton. 91 resolve(data[key], [...path, key]); 92 } 93 } 94 95 // If document is empty then it means it only consisted of collections. 96 if (!isEmpty(documentData)) { 97 // Upload a document free of collections. 98 await upload(documentData, path); 99 } 100 } else { 101 // Collection's length of is always odd. 102 for (const key in data) { 103 // Resolve each collection. 104 await resolve(data[key], [...path, key]); 105 } 106 } 107} 108resolve(data);
以上、ヒントになりうることのご教示だけでも大変ありがたい現状です。
何卒よろしくお願いいたします。
あなたの回答
tips
プレビュー