hPiBot openclaw ve Opencode ilk versiyonu[B
This commit is contained in:
371
backend/src/config/firebase.js
Normal file
371
backend/src/config/firebase.js
Normal file
@@ -0,0 +1,371 @@
|
||||
const admin = require('firebase-admin');
|
||||
|
||||
let firebaseApp = null;
|
||||
|
||||
/**
|
||||
* Firebase Admin SDK'yı başlat
|
||||
*/
|
||||
const initializeFirebase = () => {
|
||||
try {
|
||||
// Eğer zaten başlatılmışsa, mevcut instance'ı döndür
|
||||
if (firebaseApp) {
|
||||
return firebaseApp;
|
||||
}
|
||||
|
||||
// Environment variables'dan Firebase config'i al
|
||||
const firebaseConfig = {
|
||||
type: process.env.FIREBASE_TYPE,
|
||||
project_id: process.env.FIREBASE_PROJECT_ID,
|
||||
private_key_id: process.env.FIREBASE_PRIVATE_KEY_ID,
|
||||
private_key: process.env.FIREBASE_PRIVATE_KEY?.replace(/\\n/g, '\n'),
|
||||
client_email: process.env.FIREBASE_CLIENT_EMAIL,
|
||||
client_id: process.env.FIREBASE_CLIENT_ID,
|
||||
auth_uri: process.env.FIREBASE_AUTH_URI,
|
||||
token_uri: process.env.FIREBASE_TOKEN_URI,
|
||||
auth_provider_x509_cert_url: process.env.FIREBASE_AUTH_PROVIDER_X509_CERT_URL,
|
||||
client_x509_cert_url: process.env.FIREBASE_CLIENT_X509_CERT_URL
|
||||
};
|
||||
|
||||
// Gerekli environment variables'ların varlığını kontrol et
|
||||
const requiredFields = ['project_id', 'private_key', 'client_email'];
|
||||
const missingFields = requiredFields.filter(field => !firebaseConfig[field]);
|
||||
|
||||
if (missingFields.length > 0) {
|
||||
console.warn(`⚠️ Firebase konfigürasyonu eksik: ${missingFields.join(', ')}`);
|
||||
console.warn('Push notification özelliği devre dışı bırakıldı.');
|
||||
return null;
|
||||
}
|
||||
|
||||
// Firebase Admin SDK'yı başlat
|
||||
firebaseApp = admin.initializeApp({
|
||||
credential: admin.credential.cert(firebaseConfig),
|
||||
projectId: firebaseConfig.project_id
|
||||
});
|
||||
|
||||
console.log('✅ Firebase Admin SDK başarıyla başlatıldı');
|
||||
return firebaseApp;
|
||||
|
||||
} catch (error) {
|
||||
console.error('❌ Firebase başlatma hatası:', error.message);
|
||||
console.warn('Push notification özelliği devre dışı bırakıldı.');
|
||||
return null;
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* Firebase Messaging instance'ını al
|
||||
*/
|
||||
const getMessaging = () => {
|
||||
if (!firebaseApp) {
|
||||
console.warn('Firebase başlatılmamış. Push notification gönderilemez.');
|
||||
return null;
|
||||
}
|
||||
|
||||
try {
|
||||
return admin.messaging();
|
||||
} catch (error) {
|
||||
console.error('Firebase Messaging alınamadı:', error);
|
||||
return null;
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* Tek bir cihaza push notification gönder
|
||||
* @param {string} token - Device token
|
||||
* @param {object} notification - Notification objesi
|
||||
* @param {object} data - Ek veri
|
||||
* @returns {Promise<object>} Gönderim sonucu
|
||||
*/
|
||||
const sendToDevice = async (token, notification, data = {}) => {
|
||||
const messaging = getMessaging();
|
||||
if (!messaging) {
|
||||
return { success: false, error: 'Firebase Messaging kullanılamıyor' };
|
||||
}
|
||||
|
||||
try {
|
||||
const message = {
|
||||
token: token,
|
||||
notification: {
|
||||
title: notification.title,
|
||||
body: notification.body,
|
||||
...(notification.imageUrl && { imageUrl: notification.imageUrl })
|
||||
},
|
||||
data: {
|
||||
...data,
|
||||
timestamp: new Date().toISOString()
|
||||
},
|
||||
android: {
|
||||
notification: {
|
||||
icon: 'ic_notification',
|
||||
color: '#FF5722',
|
||||
sound: 'default',
|
||||
priority: 'high'
|
||||
}
|
||||
},
|
||||
apns: {
|
||||
payload: {
|
||||
aps: {
|
||||
sound: 'default',
|
||||
badge: 1
|
||||
}
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
const response = await messaging.send(message);
|
||||
|
||||
return {
|
||||
success: true,
|
||||
messageId: response,
|
||||
token: token
|
||||
};
|
||||
|
||||
} catch (error) {
|
||||
console.error('Push notification gönderme hatası:', error);
|
||||
|
||||
// Token geçersizse, bu bilgiyi döndür
|
||||
if (error.code === 'messaging/registration-token-not-registered' ||
|
||||
error.code === 'messaging/invalid-registration-token') {
|
||||
return {
|
||||
success: false,
|
||||
error: 'Invalid token',
|
||||
invalidToken: true,
|
||||
token: token
|
||||
};
|
||||
}
|
||||
|
||||
return {
|
||||
success: false,
|
||||
error: error.message,
|
||||
token: token
|
||||
};
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* Birden fazla cihaza push notification gönder
|
||||
* @param {string[]} tokens - Device token'ları
|
||||
* @param {object} notification - Notification objesi
|
||||
* @param {object} data - Ek veri
|
||||
* @returns {Promise<object>} Gönderim sonucu
|
||||
*/
|
||||
const sendToMultipleDevices = async (tokens, notification, data = {}) => {
|
||||
const messaging = getMessaging();
|
||||
if (!messaging) {
|
||||
return { success: false, error: 'Firebase Messaging kullanılamıyor' };
|
||||
}
|
||||
|
||||
if (!tokens || tokens.length === 0) {
|
||||
return { success: false, error: 'Token listesi boş' };
|
||||
}
|
||||
|
||||
try {
|
||||
const message = {
|
||||
notification: {
|
||||
title: notification.title,
|
||||
body: notification.body,
|
||||
...(notification.imageUrl && { imageUrl: notification.imageUrl })
|
||||
},
|
||||
data: {
|
||||
...data,
|
||||
timestamp: new Date().toISOString()
|
||||
},
|
||||
android: {
|
||||
notification: {
|
||||
icon: 'ic_notification',
|
||||
color: '#FF5722',
|
||||
sound: 'default',
|
||||
priority: 'high'
|
||||
}
|
||||
},
|
||||
apns: {
|
||||
payload: {
|
||||
aps: {
|
||||
sound: 'default',
|
||||
badge: 1
|
||||
}
|
||||
}
|
||||
},
|
||||
tokens: tokens
|
||||
};
|
||||
|
||||
const response = await messaging.sendMulticast(message);
|
||||
|
||||
// Başarısız token'ları topla
|
||||
const failedTokens = [];
|
||||
const invalidTokens = [];
|
||||
|
||||
response.responses.forEach((resp, idx) => {
|
||||
if (!resp.success) {
|
||||
const token = tokens[idx];
|
||||
failedTokens.push({ token, error: resp.error?.message });
|
||||
|
||||
if (resp.error?.code === 'messaging/registration-token-not-registered' ||
|
||||
resp.error?.code === 'messaging/invalid-registration-token') {
|
||||
invalidTokens.push(token);
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
return {
|
||||
success: response.successCount > 0,
|
||||
successCount: response.successCount,
|
||||
failureCount: response.failureCount,
|
||||
failedTokens: failedTokens,
|
||||
invalidTokens: invalidTokens
|
||||
};
|
||||
|
||||
} catch (error) {
|
||||
console.error('Toplu push notification gönderme hatası:', error);
|
||||
return {
|
||||
success: false,
|
||||
error: error.message
|
||||
};
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* Topic'e push notification gönder
|
||||
* @param {string} topic - Topic adı
|
||||
* @param {object} notification - Notification objesi
|
||||
* @param {object} data - Ek veri
|
||||
* @returns {Promise<object>} Gönderim sonucu
|
||||
*/
|
||||
const sendToTopic = async (topic, notification, data = {}) => {
|
||||
const messaging = getMessaging();
|
||||
if (!messaging) {
|
||||
return { success: false, error: 'Firebase Messaging kullanılamıyor' };
|
||||
}
|
||||
|
||||
try {
|
||||
const message = {
|
||||
topic: topic,
|
||||
notification: {
|
||||
title: notification.title,
|
||||
body: notification.body,
|
||||
...(notification.imageUrl && { imageUrl: notification.imageUrl })
|
||||
},
|
||||
data: {
|
||||
...data,
|
||||
timestamp: new Date().toISOString()
|
||||
},
|
||||
android: {
|
||||
notification: {
|
||||
icon: 'ic_notification',
|
||||
color: '#FF5722',
|
||||
sound: 'default',
|
||||
priority: 'high'
|
||||
}
|
||||
},
|
||||
apns: {
|
||||
payload: {
|
||||
aps: {
|
||||
sound: 'default',
|
||||
badge: 1
|
||||
}
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
const response = await messaging.send(message);
|
||||
|
||||
return {
|
||||
success: true,
|
||||
messageId: response,
|
||||
topic: topic
|
||||
};
|
||||
|
||||
} catch (error) {
|
||||
console.error('Topic push notification gönderme hatası:', error);
|
||||
return {
|
||||
success: false,
|
||||
error: error.message,
|
||||
topic: topic
|
||||
};
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* Cihazı topic'e abone et
|
||||
* @param {string[]} tokens - Device token'ları
|
||||
* @param {string} topic - Topic adı
|
||||
* @returns {Promise<object>} Abonelik sonucu
|
||||
*/
|
||||
const subscribeToTopic = async (tokens, topic) => {
|
||||
const messaging = getMessaging();
|
||||
if (!messaging) {
|
||||
return { success: false, error: 'Firebase Messaging kullanılamıyor' };
|
||||
}
|
||||
|
||||
try {
|
||||
const response = await messaging.subscribeToTopic(tokens, topic);
|
||||
|
||||
return {
|
||||
success: response.successCount > 0,
|
||||
successCount: response.successCount,
|
||||
failureCount: response.failureCount,
|
||||
errors: response.errors
|
||||
};
|
||||
|
||||
} catch (error) {
|
||||
console.error('Topic abonelik hatası:', error);
|
||||
return {
|
||||
success: false,
|
||||
error: error.message
|
||||
};
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* Cihazın topic aboneliğini iptal et
|
||||
* @param {string[]} tokens - Device token'ları
|
||||
* @param {string} topic - Topic adı
|
||||
* @returns {Promise<object>} Abonelik iptal sonucu
|
||||
*/
|
||||
const unsubscribeFromTopic = async (tokens, topic) => {
|
||||
const messaging = getMessaging();
|
||||
if (!messaging) {
|
||||
return { success: false, error: 'Firebase Messaging kullanılamıyor' };
|
||||
}
|
||||
|
||||
try {
|
||||
const response = await messaging.unsubscribeFromTopic(tokens, topic);
|
||||
|
||||
return {
|
||||
success: response.successCount > 0,
|
||||
successCount: response.successCount,
|
||||
failureCount: response.failureCount,
|
||||
errors: response.errors
|
||||
};
|
||||
|
||||
} catch (error) {
|
||||
console.error('Topic abonelik iptal hatası:', error);
|
||||
return {
|
||||
success: false,
|
||||
error: error.message
|
||||
};
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* Firebase durumunu kontrol et
|
||||
* @returns {object} Firebase durum bilgisi
|
||||
*/
|
||||
const getStatus = () => {
|
||||
return {
|
||||
initialized: !!firebaseApp,
|
||||
messaging: !!getMessaging(),
|
||||
projectId: firebaseApp?.options?.projectId || null
|
||||
};
|
||||
};
|
||||
|
||||
module.exports = {
|
||||
initializeFirebase,
|
||||
getMessaging,
|
||||
sendToDevice,
|
||||
sendToMultipleDevices,
|
||||
sendToTopic,
|
||||
subscribeToTopic,
|
||||
unsubscribeFromTopic,
|
||||
getStatus
|
||||
};
|
||||
Reference in New Issue
Block a user