thinkncollab-cli 0.0.21 → 0.0.22
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/bin/index.js +38 -20
- package/package.json +1 -1
package/bin/index.js
CHANGED
|
@@ -198,28 +198,45 @@ async function uploadFileSigned(filePath, folder, roomId, token, email) {
|
|
|
198
198
|
return cloudRes.data.secure_url;
|
|
199
199
|
}
|
|
200
200
|
|
|
201
|
-
async function uploadTree(fileTree, folderHex, roomId, token, email, parentPath = "") {
|
|
201
|
+
async function uploadTree(fileTree, folderHex, roomId, token, email, previousVersions, parentPath = "") {
|
|
202
202
|
const uploaded = [];
|
|
203
203
|
|
|
204
204
|
for (const node of fileTree) {
|
|
205
205
|
const relativePath = path.join(parentPath, node.name).replace(/\\/g, "/");
|
|
206
206
|
|
|
207
207
|
if (node.type === "folder") {
|
|
208
|
-
const children = await uploadTree(node.children, folderHex, roomId, token, email, relativePath);
|
|
208
|
+
const children = await uploadTree(node.children, folderHex, roomId, token, email, previousVersions, relativePath);
|
|
209
209
|
const folderHash = crypto.createHash("sha256").update(relativePath + children.map(c => c.hash || "").join("")).digest("hex");
|
|
210
210
|
uploaded.push({ ...node, children, hash: folderHash });
|
|
211
211
|
} else if (node.changed && node.path) {
|
|
212
|
-
|
|
213
|
-
|
|
214
|
-
|
|
212
|
+
try {
|
|
213
|
+
const url = await uploadFileSigned(node.path, `tnc_uploads/${folderHex}`, roomId, token, email);
|
|
214
|
+
console.log(`📦 Uploaded: ${relativePath} → ${url}`);
|
|
215
|
+
uploaded.push({
|
|
216
|
+
...node,
|
|
217
|
+
url,
|
|
218
|
+
hash: node.hash
|
|
219
|
+
});
|
|
220
|
+
} catch (err) {
|
|
221
|
+
console.error(`❌ Failed to upload ${relativePath}:`, err.message);
|
|
222
|
+
uploaded.push({ ...node, hash: node.hash });
|
|
223
|
+
}
|
|
215
224
|
} else {
|
|
216
|
-
|
|
225
|
+
// Unchanged file - use previous URL
|
|
226
|
+
const prevFile = previousVersions[node.path];
|
|
227
|
+
uploaded.push({
|
|
228
|
+
...node,
|
|
229
|
+
url: prevFile?.url, // ✅ Use stored URL
|
|
230
|
+
hash: node.hash,
|
|
231
|
+
version: prevFile?.version || 1
|
|
232
|
+
});
|
|
217
233
|
}
|
|
218
234
|
}
|
|
219
235
|
|
|
220
236
|
return uploaded;
|
|
221
237
|
}
|
|
222
238
|
|
|
239
|
+
|
|
223
240
|
/** ------------------ PUSH FUNCTION ------------------ **/
|
|
224
241
|
async function push(roomId, targetPath) {
|
|
225
242
|
const { token, email } = readToken();
|
|
@@ -230,10 +247,6 @@ async function push(roomId, targetPath) {
|
|
|
230
247
|
}
|
|
231
248
|
const meta = JSON.parse(fs.readFileSync(tncMetaPath, "utf-8"));
|
|
232
249
|
const projectId = meta.projectId;
|
|
233
|
-
if (!projectId) {
|
|
234
|
-
console.error("❌ Project ID missing in metadata. Run 'tnc init' again.");
|
|
235
|
-
process.exit(1);
|
|
236
|
-
}
|
|
237
250
|
|
|
238
251
|
const stats = fs.statSync(targetPath);
|
|
239
252
|
const rootFolder = stats.isDirectory() ? targetPath : path.dirname(targetPath);
|
|
@@ -267,10 +280,9 @@ async function push(roomId, targetPath) {
|
|
|
267
280
|
const folderHex = crypto.createHash("md5").update(path.basename(targetPath) + Date.now()).digest("hex");
|
|
268
281
|
|
|
269
282
|
console.log("🚀 Uploading to Cloudinary...");
|
|
270
|
-
const uploadedTree = await uploadTree(contentWithChanges, folderHex, roomId, token, email);
|
|
271
|
-
|
|
272
|
-
console.log("🗂️ Sending metadata:", { folderId: folderHex, content: uploadedTree, uploadedBy: email, projectId });
|
|
283
|
+
const uploadedTree = await uploadTree(contentWithChanges, folderHex, roomId, token, email, previousVersions);
|
|
273
284
|
|
|
285
|
+
console.log("🗂️ Sending metadata...");
|
|
274
286
|
await axios.post(
|
|
275
287
|
`${BASE_URL}/${roomId}/upload`,
|
|
276
288
|
{ folderId: folderHex, content: uploadedTree, uploadedBy: email, projectId },
|
|
@@ -279,16 +291,22 @@ async function push(roomId, targetPath) {
|
|
|
279
291
|
|
|
280
292
|
console.log("✅ Upload complete! Metadata stored successfully.");
|
|
281
293
|
|
|
282
|
-
// Save version hashes
|
|
283
|
-
const
|
|
284
|
-
const
|
|
294
|
+
// Save version hashes WITH URLs
|
|
295
|
+
const newVersionMap = {};
|
|
296
|
+
const flattenAndStore = (items) => {
|
|
285
297
|
for (const item of items) {
|
|
286
|
-
|
|
287
|
-
|
|
298
|
+
if (item.type === "file") {
|
|
299
|
+
newVersionMap[item.path] = {
|
|
300
|
+
hash: item.hash,
|
|
301
|
+
url: item.url, // ✅ Store URL locally
|
|
302
|
+
version: item.version || 1
|
|
303
|
+
};
|
|
304
|
+
}
|
|
305
|
+
if (item.children) flattenAndStore(item.children);
|
|
288
306
|
}
|
|
289
307
|
};
|
|
290
|
-
|
|
291
|
-
saveVersions(
|
|
308
|
+
flattenAndStore(uploadedTree);
|
|
309
|
+
saveVersions(newVersionMap);
|
|
292
310
|
|
|
293
311
|
} catch (err) {
|
|
294
312
|
console.error("❌ Upload failed:", err.response?.data || err.message);
|