kenso war das
This commit is contained in:
@@ -2,8 +2,8 @@ import 'dotenv/config';
|
||||
import { Client, Databases, ID, Permission, Role } from "node-appwrite";
|
||||
|
||||
/**
|
||||
* EmailSorter Database Bootstrap Script v2
|
||||
* Creates all required collections for the full EmailSorter app
|
||||
* MailFlow Database Bootstrap Script v2
|
||||
* Creates all required collections for the full MailFlow app
|
||||
*/
|
||||
|
||||
const requiredEnv = [
|
||||
@@ -26,8 +26,8 @@ const client = new Client()
|
||||
|
||||
const db = new Databases(client);
|
||||
|
||||
const DB_ID = process.env.APPWRITE_DATABASE_ID || 'emailsorter';
|
||||
const DB_NAME = 'EmailSorter';
|
||||
const DB_ID = process.env.APPWRITE_DATABASE_ID || 'mailflow';
|
||||
const DB_NAME = 'MailFlow';
|
||||
|
||||
// Helper: create database if not exists
|
||||
async function ensureDatabase() {
|
||||
@@ -262,7 +262,7 @@ async function setupCollections() {
|
||||
|
||||
async function main() {
|
||||
console.log('\n========================================');
|
||||
console.log(' EmailSorter Database Bootstrap v2');
|
||||
console.log(' MailFlow Database Bootstrap v2');
|
||||
console.log('========================================\n');
|
||||
|
||||
await ensureDatabase();
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/**
|
||||
* EmailSorter - Database Cleanup Script
|
||||
* MailFlow - Database Cleanup Script
|
||||
*
|
||||
* ⚠️ WICHTIG: Liest Credentials aus Umgebungsvariablen (.env)
|
||||
* Keine hardcoded API Keys mehr!
|
||||
|
||||
@@ -33,11 +33,11 @@ try {
|
||||
const productsResponse = await databases.listDocuments(
|
||||
process.env.APPWRITE_DATABASE_ID,
|
||||
'products',
|
||||
[Query.equal('slug', 'email-sorter'), Query.equal('isActive', true)]
|
||||
[Query.equal('slug', 'mailflow'), Query.equal('isActive', true)]
|
||||
);
|
||||
|
||||
if (productsResponse.documents.length === 0) {
|
||||
console.error('❌ No active product found with slug "email-sorter"');
|
||||
console.error('❌ No active product found with slug "mailflow"');
|
||||
process.exit(1);
|
||||
}
|
||||
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
# ═══════════════════════════════════════════════════════════════════════════
|
||||
# EmailSorter Backend - Konfiguration
|
||||
# MailFlow Backend - Konfiguration
|
||||
# ═══════════════════════════════════════════════════════════════════════════
|
||||
# Kopiere diese Datei nach `.env` und fülle die Werte aus.
|
||||
|
||||
@@ -21,7 +21,7 @@ FRONTEND_URL=http://localhost:5173
|
||||
APPWRITE_ENDPOINT=https://cloud.appwrite.io/v1
|
||||
APPWRITE_PROJECT_ID=dein_projekt_id
|
||||
APPWRITE_API_KEY=dein_api_key_mit_allen_berechtigungen
|
||||
APPWRITE_DATABASE_ID=email_sorter_db
|
||||
APPWRITE_DATABASE_ID=mailflow_db
|
||||
|
||||
# ─────────────────────────────────────────────────────────────────────────────
|
||||
# Stripe (ERFORDERLICH)
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/**
|
||||
* EmailSorter Backend Server
|
||||
* MailFlow Backend Server
|
||||
* Main entry point
|
||||
*/
|
||||
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
{
|
||||
"name": "email-sorter-server",
|
||||
"name": "mailflow-server",
|
||||
"version": "2.0.0",
|
||||
"description": "EmailSorter Backend Server - KI-gestützte E-Mail-Sortierung",
|
||||
"description": "MailFlow Backend Server - KI-gestützte E-Mail-Sortierung",
|
||||
"main": "index.mjs",
|
||||
"type": "module",
|
||||
"engines": {
|
||||
|
||||
@@ -164,7 +164,7 @@ router.post('/connect-demo',
|
||||
}),
|
||||
asyncHandler(async (req, res) => {
|
||||
const { userId } = req.body
|
||||
const demoEmail = `demo-${userId.slice(0, 8)}@emailsorter.demo`
|
||||
const demoEmail = `demo-${userId.slice(0, 8)}@mailflow.demo`
|
||||
|
||||
// Check if demo account already exists
|
||||
const existingAccounts = await emailAccounts.getByUser(userId)
|
||||
@@ -456,7 +456,7 @@ router.post('/sort',
|
||||
try {
|
||||
const gmail = await getGmailService(account.accessToken, account.refreshToken)
|
||||
|
||||
// FIRST: Clean up old "EmailSorter/..." labels
|
||||
// FIRST: Clean up old "MailFlow/..." labels
|
||||
const deletedLabels = await gmail.cleanupOldLabels()
|
||||
if (deletedLabels > 0) {
|
||||
log.success(`${deletedLabels} old labels cleaned up`)
|
||||
@@ -528,7 +528,7 @@ router.post('/sort',
|
||||
for (const nl of preferences.nameLabels) {
|
||||
if (!nl.enabled) continue
|
||||
try {
|
||||
const labelName = `EmailSorter/Team/${nl.name}`
|
||||
const labelName = `MailFlow/Team/${nl.name}`
|
||||
const label = await gmail.createLabel(labelName, '#4a86e8')
|
||||
if (label) {
|
||||
nameLabelMap[nl.id || nl.name] = label.id
|
||||
@@ -1203,7 +1203,7 @@ router.post('/sort-demo', asyncHandler(async (req, res) => {
|
||||
|
||||
/**
|
||||
* POST /api/email/cleanup
|
||||
* Cleanup old EmailSorter labels from Gmail
|
||||
* Cleanup old MailFlow labels from Gmail
|
||||
*/
|
||||
router.post('/cleanup',
|
||||
validate({
|
||||
@@ -1235,7 +1235,7 @@ router.post('/cleanup',
|
||||
respond.success(res, {
|
||||
deleted,
|
||||
message: deleted > 0
|
||||
? `${deleted} old "EmailSorter/..." labels were deleted`
|
||||
? `${deleted} old "MailFlow/..." labels were deleted`
|
||||
: 'No old labels found'
|
||||
})
|
||||
})
|
||||
@@ -1549,8 +1549,8 @@ async function processPromotionsCleanup(account, action, deleteAfterDays, matchC
|
||||
const gmail = await getGmailService(account.accessToken, account.refreshToken)
|
||||
|
||||
// Find emails with matching categories/labels older than deleteAfterDays
|
||||
// Look for emails with EmailSorter labels matching the categories
|
||||
const labelQueries = matchCategories.map(cat => `label:EmailSorter/${cat}`).join(' OR ')
|
||||
// Look for emails with MailFlow labels matching the categories
|
||||
const labelQueries = matchCategories.map(cat => `label:MailFlow/${cat}`).join(' OR ')
|
||||
const query = `(${labelQueries}) before:${cutoffDate.getFullYear()}/${String(cutoffDate.getMonth() + 1).padStart(2, '0')}/${String(cutoffDate.getDate()).padStart(2, '0')}`
|
||||
|
||||
const response = await gmail.gmail.users.messages.list({
|
||||
|
||||
@@ -107,7 +107,7 @@ export class GmailService {
|
||||
|
||||
/**
|
||||
* Create or get a label
|
||||
* @param {string} name - Label name (e.g., "EmailSorter/VIP")
|
||||
* @param {string} name - Label name (e.g., "MailFlow/VIP")
|
||||
* @param {string} color - Optional label color (must be from Gmail's palette)
|
||||
*/
|
||||
async createLabel(name, color = null) {
|
||||
@@ -272,14 +272,14 @@ export class GmailService {
|
||||
}
|
||||
|
||||
/**
|
||||
* Cleanup old EmailSorter labels
|
||||
* Removes all labels starting with "EmailSorter/" and old German labels
|
||||
* Cleanup old MailFlow labels
|
||||
* Removes all labels starting with "MailFlow/" and old German labels
|
||||
*/
|
||||
async cleanupOldLabels() {
|
||||
// Old labels to remove (German and old format)
|
||||
const OLD_LABELS = [
|
||||
// Old "EmailSorter/" prefix labels
|
||||
'EmailSorter/',
|
||||
// Old "MailFlow/" prefix labels
|
||||
'MailFlow/',
|
||||
// Old German labels
|
||||
'Wichtig', 'Kunden', 'Rechnungen', 'Sicherheit', 'Termine', 'Prüfen', 'Werbung',
|
||||
'VIP / Wichtig', 'Kunden / Projekte', 'Rechnungen / Belege',
|
||||
@@ -293,8 +293,8 @@ export class GmailService {
|
||||
// Filter labels that match old patterns
|
||||
const labelsToDelete = labels.filter(l => {
|
||||
if (!l.name) return false
|
||||
// Check for EmailSorter/ prefix
|
||||
if (l.name.startsWith('EmailSorter/')) return true
|
||||
// Check for MailFlow/ prefix
|
||||
if (l.name.startsWith('MailFlow/')) return true
|
||||
// Check for exact matches with old labels
|
||||
if (OLD_LABELS.includes(l.name)) return true
|
||||
return false
|
||||
|
||||
@@ -7,7 +7,7 @@ import { ImapFlow } from 'imapflow'
|
||||
import { log } from '../middleware/logger.mjs'
|
||||
|
||||
const INBOX = 'INBOX'
|
||||
const FOLDER_PREFIX = 'EmailSorter'
|
||||
const FOLDER_PREFIX = 'MailFlow'
|
||||
|
||||
/** Map category key to IMAP folder name */
|
||||
export function getFolderNameForCategory(category) {
|
||||
@@ -134,7 +134,7 @@ export class ImapService {
|
||||
}
|
||||
|
||||
/**
|
||||
* Ensure folder exists (create if not). Use subfolder under EmailSorter to avoid clutter.
|
||||
* Ensure folder exists (create if not). Use subfolder under MailFlow to avoid clutter.
|
||||
*/
|
||||
async ensureFolder(folderName) {
|
||||
const path = `${FOLDER_PREFIX}/${folderName}`
|
||||
@@ -150,7 +150,7 @@ export class ImapService {
|
||||
}
|
||||
|
||||
/**
|
||||
* Move message (by UID) from INBOX to folder name (under EmailSorter/)
|
||||
* Move message (by UID) from INBOX to folder name (under MailFlow/)
|
||||
*/
|
||||
async moveToFolder(messageId, folderName) {
|
||||
const path = `${FOLDER_PREFIX}/${folderName}`
|
||||
|
||||
@@ -302,7 +302,7 @@ export class OutlookService {
|
||||
notificationUrl: webhookUrl,
|
||||
resource: 'me/mailFolders(\'inbox\')/messages',
|
||||
expirationDateTime,
|
||||
clientState: 'email-sorter-webhook',
|
||||
clientState: 'mailflow-webhook',
|
||||
}),
|
||||
})
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user