diff --git a/src/server/routes/adminModels.ts b/src/server/routes/adminModels.ts index ec85461..c8245af 100644 --- a/src/server/routes/adminModels.ts +++ b/src/server/routes/adminModels.ts @@ -242,10 +242,15 @@ router.get('/admin/models/:id/edit', requireAdmin, (req: Request, res: Response) const model = q(`SELECT * FROM models WHERE id = ?`).get(req.params.id) if (!model) { res.redirect('/admin'); return } - const categories = q(`SELECT * FROM categories ORDER BY sort_order, name`).all() - const pdfs = q(`SELECT * FROM model_pdfs WHERE model_id = ? ORDER BY sort_order`).all(model.id) + const categories = q(`SELECT * FROM categories ORDER BY sort_order, name`).all() + const pdfs = q(`SELECT * FROM model_pdfs WHERE model_id = ? ORDER BY sort_order`).all(model.id) + const absModelPath = path.join(UPLOADS_DIR, model.file_path) + const hasGeometry = (model.file_type === 'step' || model.file_type === 'stp') + ? fs.existsSync(geometryOutputPath(absModelPath)) + : true + res.render('admin/edit', { - model, categories, pdfs, error: null, + model, categories, pdfs, error: null, hasGeometry, baseUrl: process.env.BASE_URL ?? `http://localhost:${process.env.PORT ?? 3000}`, }) }) @@ -277,6 +282,44 @@ router.post('/admin/pdfs/:id/delete', requireAdmin, (req: Request, res: Response res.redirect(`/admin/models/${pdf.model_id}/edit`) }) +// ---- Reconvert STEP/STP geometry ----------------------------------------- + +router.post('/admin/models/:id/reconvert', requireAdmin, async (req: Request, res: Response) => { + const model = q(`SELECT * FROM models WHERE id = ?`).get(req.params.id) + if (!model) { res.status(404).json({ error: 'Model not found' }); return } + + if (model.file_type !== 'step' && model.file_type !== 'stp') { + res.status(400).json({ error: 'Only STEP/STP models require geometry conversion' }); return + } + + const absModelPath = path.join(UPLOADS_DIR, model.file_path) + if (!fs.existsSync(absModelPath)) { + res.status(404).json({ error: 'Source model file not found on disk' }); return + } + + const geoOutPath = geometryOutputPath(absModelPath) + + try { + await convertStepFile(absModelPath, geoOutPath) + } catch (err) { + res.status(500).json({ error: `Conversion failed: ${(err as Error).message}` }); return + } + + // Regenerate thumbnail from new geometry (non-fatal) + try { + const geo = JSON.parse(fs.readFileSync(geoOutPath, 'utf8')) as GeometryFile + const tris = geometryToTriangles(geo) + const thumbPath = thumbnailOutputPath(UPLOADS_DIR, model.id) + await renderThumbnail(tris, thumbPath) + const thumbRel = path.relative(UPLOADS_DIR, thumbPath).replace(/\\/g, '/') + db.prepare(`UPDATE models SET thumbnail_path = ? WHERE id = ?`).run(thumbRel, model.id) + } catch (thumbErr) { + console.error('[thumbnail] reconvert thumbnail failed:', (thumbErr as Error).message) + } + + res.json({ ok: true }) +}) + // ---- JSON list ----------------------------------------------------------- router.get('/api/admin/models', requireAdmin, (_req: Request, res: Response) => { diff --git a/src/server/services/stepConverter.ts b/src/server/services/stepConverter.ts index 969cbfe..40347fc 100644 --- a/src/server/services/stepConverter.ts +++ b/src/server/services/stepConverter.ts @@ -22,7 +22,11 @@ let _init: Promise>> | null = null async function getOcct() { if (_occt) return _occt - if (!_init) _init = occtimport().then(m => { _occt = m; return m }) + if (!_init) { + _init = occtimport().then(m => { _occt = m; return m }) + // Reset on failure so the next upload attempt retries rather than replaying a cached rejection + _init.catch(() => { _init = null }) + } return _init } diff --git a/views/admin/edit.ejs b/views/admin/edit.ejs index f98f02c..32b0773 100644 --- a/views/admin/edit.ejs +++ b/views/admin/edit.ejs @@ -61,6 +61,31 @@ + + <% if (model.file_type === 'step' || model.file_type === 'stp') { %> +
+

3D Geometry Processing

+ <% if (hasGeometry) { %> +
+ + Geometry processed successfully +
+ <% } else { %> +
+
+ + Geometry processing failed — model cannot be viewed +
+ +
+ + <% } %> +
+ <% } %> +

Shop Diagrams / PDFs

@@ -115,5 +140,34 @@
+