fix: corrige mascara telefone/CPF/CEP na pre-matricula publica e atualiza CHECK constraint para aceitar tipos file e banner
Build and Deploy (Gitea) / build-and-deploy (push) Successful in 2m12s
Details
Build and Deploy (Gitea) / build-and-deploy (push) Successful in 2m12s
Details
This commit is contained in:
parent
b34b5bf523
commit
dd57662d4f
|
|
@ -0,0 +1,97 @@
|
|||
const pg = require('pg');
|
||||
const { S3Client, ListBucketsCommand, ListObjectsV2Command } = require('@aws-sdk/client-s3');
|
||||
|
||||
const pool = new pg.Pool({
|
||||
connectionString: 'postgresql://edumanager:EduManager2026!Seguro@150.230.87.131:5432/edumanager'
|
||||
});
|
||||
|
||||
const s3Client = new S3Client({
|
||||
endpoint: 'http://150.230.87.131:9000',
|
||||
region: 'us-east-1',
|
||||
credentials: {
|
||||
accessKeyId: 'minioadmin',
|
||||
secretAccessKey: 'MiniO2026!Seguro',
|
||||
},
|
||||
forcePathStyle: true,
|
||||
});
|
||||
|
||||
async function main() {
|
||||
try {
|
||||
console.log('--- 1. BUSCANDO TODAS AS TABELAS E DADOS DO POSTGRESQL ---');
|
||||
const { rows: tables } = await pool.query("SELECT table_name FROM information_schema.tables WHERE table_schema = 'public'");
|
||||
console.log(`Encontradas ${tables.length} tabelas no banco de dados.`);
|
||||
|
||||
let dbContentDump = '';
|
||||
for (const t of tables) {
|
||||
const tableName = t.table_name;
|
||||
try {
|
||||
const { rows } = await pool.query(`SELECT * FROM "${tableName}"`);
|
||||
dbContentDump += JSON.stringify(rows) + ' ';
|
||||
} catch (err) {
|
||||
console.warn(`Aviso: não foi possível ler a tabela ${tableName}:`, err.message);
|
||||
}
|
||||
}
|
||||
console.log(`Dumping de referências concluído (${(dbContentDump.length / 1024 / 1024).toFixed(2)} MB).`);
|
||||
|
||||
console.log('\n--- 2. LISTANDO ARQUIVOS NO STORAGE MINIO ---');
|
||||
const bucketsData = await s3Client.send(new ListBucketsCommand({}));
|
||||
const buckets = bucketsData.Buckets || [];
|
||||
console.log(`Encontrados ${buckets.length} buckets no MinIO.`);
|
||||
|
||||
const allFiles = [];
|
||||
let totalStorageSize = 0;
|
||||
|
||||
for (const bucket of buckets) {
|
||||
try {
|
||||
const objects = await s3Client.send(new ListObjectsV2Command({ Bucket: bucket.Name }));
|
||||
const contents = objects.Contents || [];
|
||||
console.log(`Bucket [${bucket.Name}]: ${contents.length} arquivos encontrados.`);
|
||||
for (const obj of contents) {
|
||||
totalStorageSize += obj.Size || 0;
|
||||
allFiles.push({
|
||||
bucket: bucket.Name,
|
||||
key: obj.Key,
|
||||
size: obj.Size || 0,
|
||||
url: `/storage/${bucket.Name}/${obj.Key}`
|
||||
});
|
||||
}
|
||||
} catch (err) {
|
||||
console.warn(`Não foi possível listar objetos do bucket ${bucket.Name}:`, err.message);
|
||||
}
|
||||
}
|
||||
console.log(`Total geral no MinIO: ${(totalStorageSize / 1024 / 1024).toFixed(2)} MB (${allFiles.length} arquivos).`);
|
||||
|
||||
console.log('\n--- 3. FILTRANDO ARQUIVOS NÃO UTILIZADOS ---');
|
||||
const unusedFiles = [];
|
||||
const usedFiles = [];
|
||||
|
||||
for (const file of allFiles) {
|
||||
const hasReference = dbContentDump.includes(file.key) || dbContentDump.includes(file.url);
|
||||
if (hasReference) {
|
||||
usedFiles.push(file);
|
||||
} else {
|
||||
unusedFiles.push(file);
|
||||
}
|
||||
}
|
||||
|
||||
const totalUnusedSize = unusedFiles.reduce((acc, curr) => acc + curr.size, 0);
|
||||
console.log(`\nRESULTADOS:`);
|
||||
console.log(`- Arquivos em Uso: ${usedFiles.length}`);
|
||||
console.log(`- Arquivos Órfãos (NÃO usados): ${unusedFiles.length}`);
|
||||
console.log(`- Espaço sendo desperdiçado: ${(totalUnusedSize / 1024 / 1024).toFixed(2)} MB`);
|
||||
|
||||
if (unusedFiles.length > 0) {
|
||||
console.log('\n--- LISTA DE ARQUIVOS NÃO UTILIZADOS ---');
|
||||
unusedFiles.forEach((file, index) => {
|
||||
console.log(`${index + 1}. Bucket: [${file.bucket}] | Arquivo: ${file.key} | Tamanho: ${(file.size / 1024).toFixed(2)} KB`);
|
||||
});
|
||||
} else {
|
||||
console.log('\nExcelente! Todos os arquivos armazenados no MinIO estão sendo referenciados no banco de dados!');
|
||||
}
|
||||
} catch (error) {
|
||||
console.error('Erro na execução:', error);
|
||||
} finally {
|
||||
await pool.end();
|
||||
}
|
||||
}
|
||||
main();
|
||||
|
|
@ -0,0 +1,101 @@
|
|||
const pg = require('pg');
|
||||
const { S3Client, ListBucketsCommand, ListObjectsV2Command } = require('@aws-sdk/client-s3');
|
||||
|
||||
const DATABASE_URL = process.env.DATABASE_URL || 'postgresql://edumanager:EduManager2026!Seguro@postgres:5432/edumanager';
|
||||
const pool = new pg.Pool({ connectionString: DATABASE_URL });
|
||||
|
||||
const MINIO_ENDPOINT = process.env.MINIO_ENDPOINT || 'minio';
|
||||
const MINIO_PORT = process.env.MINIO_PORT || '9000';
|
||||
const MINIO_ACCESS_KEY = process.env.MINIO_ACCESS_KEY || 'minioadmin';
|
||||
const MINIO_SECRET_KEY = process.env.MINIO_SECRET_KEY || 'MiniO2026!Seguro';
|
||||
|
||||
const s3Client = new S3Client({
|
||||
endpoint: `http://${MINIO_ENDPOINT}:${MINIO_PORT}`,
|
||||
region: 'us-east-1',
|
||||
credentials: {
|
||||
accessKeyId: MINIO_ACCESS_KEY,
|
||||
secretAccessKey: MINIO_SECRET_KEY,
|
||||
},
|
||||
forcePathStyle: true,
|
||||
});
|
||||
|
||||
async function main() {
|
||||
try {
|
||||
console.log('--- 1. BUSCANDO TODAS AS TABELAS E DADOS DO POSTGRESQL ---');
|
||||
const { rows: tables } = await pool.query("SELECT table_name FROM information_schema.tables WHERE table_schema = 'public'");
|
||||
console.log(`Encontradas ${tables.length} tabelas no banco de dados.`);
|
||||
|
||||
let dbContentDump = '';
|
||||
for (const t of tables) {
|
||||
const tableName = t.table_name;
|
||||
try {
|
||||
const { rows } = await pool.query(`SELECT * FROM "${tableName}"`);
|
||||
dbContentDump += JSON.stringify(rows) + ' ';
|
||||
} catch (err) {
|
||||
console.warn(`Aviso: não foi possível ler a tabela ${tableName}:`, err.message);
|
||||
}
|
||||
}
|
||||
console.log(`Dumping de referências concluído (${(dbContentDump.length / 1024 / 1024).toFixed(2)} MB).`);
|
||||
|
||||
console.log('\n--- 2. LISTANDO ARQUIVOS NO STORAGE MINIO ---');
|
||||
const bucketsData = await s3Client.send(new ListBucketsCommand({}));
|
||||
const buckets = bucketsData.Buckets || [];
|
||||
console.log(`Encontrados ${buckets.length} buckets no MinIO.`);
|
||||
|
||||
const allFiles = [];
|
||||
let totalStorageSize = 0;
|
||||
|
||||
for (const bucket of buckets) {
|
||||
try {
|
||||
const objects = await s3Client.send(new ListObjectsV2Command({ Bucket: bucket.Name }));
|
||||
const contents = objects.Contents || [];
|
||||
console.log(`Bucket [${bucket.Name}]: ${contents.length} arquivos encontrados.`);
|
||||
for (const obj of contents) {
|
||||
totalStorageSize += obj.Size || 0;
|
||||
allFiles.push({
|
||||
bucket: bucket.Name,
|
||||
key: obj.Key,
|
||||
size: obj.Size || 0,
|
||||
url: `/storage/${bucket.Name}/${obj.Key}`
|
||||
});
|
||||
}
|
||||
} catch (err) {
|
||||
console.warn(`Não foi possível listar objetos do bucket ${bucket.Name}:`, err.message);
|
||||
}
|
||||
}
|
||||
console.log(`Total geral no MinIO: ${(totalStorageSize / 1024 / 1024).toFixed(2)} MB (${allFiles.length} arquivos).`);
|
||||
|
||||
console.log('\n--- 3. FILTRANDO ARQUIVOS NÃO UTILIZADOS ---');
|
||||
const unusedFiles = [];
|
||||
const usedFiles = [];
|
||||
|
||||
for (const file of allFiles) {
|
||||
const hasReference = dbContentDump.includes(file.key) || dbContentDump.includes(file.url);
|
||||
if (hasReference) {
|
||||
usedFiles.push(file);
|
||||
} else {
|
||||
unusedFiles.push(file);
|
||||
}
|
||||
}
|
||||
|
||||
const totalUnusedSize = unusedFiles.reduce((acc, curr) => acc + curr.size, 0);
|
||||
console.log(`\nRESULTADOS:`);
|
||||
console.log(`- Arquivos em Uso: ${usedFiles.length}`);
|
||||
console.log(`- Arquivos Órfãos (NÃO usados): ${unusedFiles.length}`);
|
||||
console.log(`- Espaço sendo desperdiçado: ${(totalUnusedSize / 1024 / 1024).toFixed(2)} MB`);
|
||||
|
||||
if (unusedFiles.length > 0) {
|
||||
console.log('\n--- LISTA DE ARQUIVOS NÃO UTILIZADOS ---');
|
||||
unusedFiles.forEach((file, index) => {
|
||||
console.log(`${index + 1}. Bucket: [${file.bucket}] | Arquivo: ${file.key} | Tamanho: ${(file.size / 1024).toFixed(2)} KB`);
|
||||
});
|
||||
} else {
|
||||
console.log('\nExcelente! Todos os arquivos armazenados no MinIO estão sendo referenciados no banco de dados!');
|
||||
}
|
||||
} catch (error) {
|
||||
console.error('Erro na execução:', error);
|
||||
} finally {
|
||||
await pool.end();
|
||||
}
|
||||
}
|
||||
main();
|
||||
|
|
@ -0,0 +1,27 @@
|
|||
const pg = require('pg');
|
||||
|
||||
const pool = new pg.Pool({
|
||||
connectionString: 'postgresql://edumanager:EduManager2026!Seguro@150.230.87.131:5432/edumanager'
|
||||
});
|
||||
|
||||
async function run() {
|
||||
try {
|
||||
console.log('Removendo CHECK constraint antigo...');
|
||||
await pool.query('ALTER TABLE prematricula_campos DROP CONSTRAINT prematricula_campos_tipo_check');
|
||||
|
||||
console.log('Adicionando CHECK constraint atualizado com file e banner...');
|
||||
await pool.query(`
|
||||
ALTER TABLE prematricula_campos
|
||||
ADD CONSTRAINT prematricula_campos_tipo_check
|
||||
CHECK (tipo = ANY (ARRAY['text', 'email', 'phone', 'cpf', 'date', 'select', 'textarea', 'number', 'file', 'banner']))
|
||||
`);
|
||||
|
||||
console.log('✅ Constraint atualizado com sucesso! Tipos file e banner agora são aceitos.');
|
||||
} catch (err) {
|
||||
console.error('Erro:', err.message);
|
||||
} finally {
|
||||
await pool.end();
|
||||
}
|
||||
}
|
||||
|
||||
run();
|
||||
|
|
@ -111,7 +111,7 @@ const app=document.getElementById('app');
|
|||
|
||||
function maskPhone(v){
|
||||
if(!v)return "";
|
||||
v=v.replace(/\D/g,"");
|
||||
v=v.replace(/[^0-9]/g,"");
|
||||
if(v.length>11) v=v.substring(0,11);
|
||||
if(v.length>10){
|
||||
return '(' + v.substring(0,2) + ') ' + v.substring(2,7) + '-' + v.substring(7);
|
||||
|
|
@ -125,7 +125,7 @@ function maskPhone(v){
|
|||
|
||||
function maskCPF(v){
|
||||
if(!v)return "";
|
||||
v=v.replace(/\D/g,"");
|
||||
v=v.replace(/[^0-9]/g,"");
|
||||
if(v.length>11) v=v.substring(0,11);
|
||||
if(v.length>9){
|
||||
return v.substring(0,3) + '.' + v.substring(3,6) + '.' + v.substring(6,9) + '-' + v.substring(9);
|
||||
|
|
@ -139,7 +139,7 @@ function maskCPF(v){
|
|||
|
||||
function maskCEP(v){
|
||||
if(!v)return "";
|
||||
v=v.replace(/\D/g,"");
|
||||
v=v.replace(/[^0-9]/g,"");
|
||||
if(v.length>8) v=v.substring(0,8);
|
||||
if(v.length>5){
|
||||
return v.substring(0,5) + '-' + v.substring(5);
|
||||
|
|
@ -147,25 +147,30 @@ function maskCEP(v){
|
|||
return v;
|
||||
}
|
||||
|
||||
// Global fallback event listener
|
||||
// Global single-scope event listener (Rule 50 - anti-double-bind)
|
||||
var _maskingActive = false;
|
||||
document.addEventListener('input',function(e){
|
||||
if(_maskingActive) return;
|
||||
if(!e.target)return;
|
||||
const dt=e.target.getAttribute('data-type');
|
||||
var dt=e.target.getAttribute('data-type');
|
||||
if(dt==='phone' || dt==='cpf' || dt==='cep'){
|
||||
const originalVal = e.target.value;
|
||||
let newVal = originalVal;
|
||||
if(dt==='phone') newVal = maskPhone(originalVal);
|
||||
else if(dt==='cpf') newVal = maskCPF(originalVal);
|
||||
else if(dt==='cep') newVal = maskCEP(originalVal);
|
||||
_maskingActive = true;
|
||||
var raw = e.target.value;
|
||||
var masked = raw;
|
||||
if(dt==='phone') masked = maskPhone(raw);
|
||||
else if(dt==='cpf') masked = maskCPF(raw);
|
||||
else if(dt==='cep') masked = maskCEP(raw);
|
||||
|
||||
if (newVal !== originalVal) {
|
||||
const start = e.target.selectionStart;
|
||||
e.target.value = newVal;
|
||||
if (masked !== raw) {
|
||||
var cursorPos = e.target.selectionStart || 0;
|
||||
var diff = masked.length - raw.length;
|
||||
e.target.value = masked;
|
||||
try {
|
||||
const diff = newVal.length - originalVal.length;
|
||||
e.target.setSelectionRange(start + diff, start + diff);
|
||||
var newPos = Math.max(0, cursorPos + diff);
|
||||
e.target.setSelectionRange(newPos, newPos);
|
||||
} catch(err) {}
|
||||
}
|
||||
_maskingActive = false;
|
||||
}
|
||||
});
|
||||
|
||||
|
|
|
|||
Loading…
Reference in New Issue