- Updated API documentation to reflect changes in article data structure. - Improved ArticlePhoto component to support dynamic sizing and object fit options. - Added performance logging for image upload in ArticlePhotosDialog and ArticlePhotoTile components. - Enhanced ArticleTile to conditionally render photos and adjusted styling for better layout. - Optimized image preparation process with configurable AVIF encoding speed.
84 lines
2.3 KiB
JavaScript
84 lines
2.3 KiB
JavaScript
#!/usr/bin/env node
|
|
/**
|
|
* Export pic.fullbinary by hash using dashback/.env MSSQL credentials.
|
|
* Usage: node scripts/export-pic-by-hash.mjs <fullHash> [outPath]
|
|
*/
|
|
import { createRequire } from 'node:module';
|
|
import { mkdir, writeFile } from 'node:fs/promises';
|
|
import { dirname, resolve } from 'node:path';
|
|
import { fileURLToPath } from 'node:url';
|
|
|
|
const require = createRequire(import.meta.url);
|
|
const dotenv = require('../../dashback/node_modules/dotenv');
|
|
const sql = require('../../dashback/node_modules/mssql');
|
|
|
|
const __dirname = dirname(fileURLToPath(import.meta.url));
|
|
const dashfrontRoot = resolve(__dirname, '..');
|
|
const dashbackEnv = resolve(dashfrontRoot, '../dashback/.env');
|
|
|
|
dotenv.config({ path: dashbackEnv, quiet: true });
|
|
|
|
const FULL_HASH_RE = /^[a-fA-F0-9]{64}$/;
|
|
const hash = process.argv[2]?.trim();
|
|
const outPath = resolve(
|
|
process.argv[3] ?? resolve(dashfrontRoot, 'tmp/bench-source.avif'),
|
|
);
|
|
|
|
if (!hash || !FULL_HASH_RE.test(hash)) {
|
|
console.error('Usage: node scripts/export-pic-by-hash.mjs <64-char-hex-fullHash> [outPath]');
|
|
process.exit(1);
|
|
}
|
|
|
|
const config = {
|
|
server: process.env.MSSQL_SERVER,
|
|
database: process.env.MSSQL_DATABASE,
|
|
user: process.env.MSSQL_USER,
|
|
password: process.env.MSSQL_PASSWORD,
|
|
port: Number(process.env.MSSQL_PORT) || 1433,
|
|
options: {
|
|
encrypt: process.env.MSSQL_ENCRYPT === 'true',
|
|
trustServerCertificate: process.env.MSSQL_TRUST_SERVER_CERTIFICATE !== 'false',
|
|
},
|
|
};
|
|
|
|
if (!config.server || !config.database || !config.user || !config.password) {
|
|
console.error('Missing MSSQL_* in dashback/.env');
|
|
process.exit(1);
|
|
}
|
|
|
|
const pool = await sql.connect(config);
|
|
try {
|
|
const result = await pool
|
|
.request()
|
|
.input('hash', sql.VarChar(64), hash.toLowerCase())
|
|
.query(`
|
|
SELECT w, h, size, fullbinary
|
|
FROM pic
|
|
WHERE hash = @hash
|
|
`);
|
|
|
|
const row = result.recordset[0];
|
|
if (!row?.fullbinary) {
|
|
console.error(`No pic found for hash ${hash}`);
|
|
process.exit(1);
|
|
}
|
|
|
|
const buffer = Buffer.isBuffer(row.fullbinary)
|
|
? row.fullbinary
|
|
: Buffer.from(row.fullbinary);
|
|
|
|
await mkdir(dirname(outPath), { recursive: true });
|
|
await writeFile(outPath, buffer);
|
|
|
|
console.log(JSON.stringify({
|
|
outPath,
|
|
hash: hash.toLowerCase(),
|
|
w: row.w,
|
|
h: row.h,
|
|
size: row.size,
|
|
bytes: buffer.length,
|
|
}, null, 2));
|
|
} finally {
|
|
await pool.close();
|
|
}
|