Files
startup/web/src/lib/teamFeed.js

154 lines
4.0 KiB
JavaScript
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
const TEAM_MEMBERS = [
{ id: "mazlum", name: "Mazlum", role: "Team Lead", icon: "🎩" },
{ id: "berkecan", name: "Berkecan", role: "Frontend Developer", icon: "💻" },
{ id: "simsar", name: "Simsar", role: "Backend Developer", icon: "⚙️" },
{ id: "aybuke", name: "Aybuke", role: "UI/UX Designer", icon: "🎨" },
{ id: "ive", name: "Ive", role: "iOS Developer", icon: "📱" },
{ id: "irgatov", name: "Irgatov", role: "Trainee", icon: "☕" }
];
function normalizeSpeaker(value) {
return String(value ?? "")
.normalize("NFD")
.replace(/[\u0300-\u036f]/g, "")
.toLowerCase();
}
const memberMap = new Map(TEAM_MEMBERS.map((member) => [normalizeSpeaker(member.name), member]));
function isNoiseLine(line) {
const trimmed = line.trim();
if (!trimmed) {
return true;
}
return [
/^╭|^╰|^│|^─/.test(trimmed),
/^/.test(trimmed),
/^⏵⏵/.test(trimmed),
/^⏺/.test(trimmed),
/^✻|^✽|^✳|^✢|^· /.test(trimmed),
/^Auth conflict:/i.test(trimmed),
/^unset ANTHROPIC_API_KEY/i.test(trimmed),
/^Tips for getting/i.test(trimmed),
/^Recent activity/i.test(trimmed),
/^No recent activity/i.test(trimmed),
/^glm-5/i.test(trimmed),
/^Org$/i.test(trimmed),
/^Press up to edit/i.test(trimmed),
/^Deliberating/i.test(trimmed),
/^Cultivating/i.test(trimmed),
/^Sistem yonlendirmesi:/i.test(trimmed),
/^Hedef kisi:/i.test(trimmed),
/^Yalnizca /i.test(trimmed),
/^Cevap zorunlu/i.test(trimmed),
/^Baska hicbir/i.test(trimmed),
/^Kullanici mesaji:/i.test(trimmed),
/^Takim ici /i.test(trimmed),
/^Her cevap /i.test(trimmed),
/^Etiketsiz cevap /i.test(trimmed),
/^Gecerli ornek:/i.test(trimmed),
/^Kullanici tek bir kisiye/i.test(trimmed),
/^Kullanici tum takima/i.test(trimmed),
/^Her ekip uyesi/i.test(trimmed),
/^Ilk cevap olarak/i.test(trimmed),
/^Bu ilk cevap/i.test(trimmed),
/^\(erkek\)|^\(disi\)/i.test(trimmed)
].some(Boolean);
}
function shouldBreakCurrentEntry(line) {
const trimmed = line.trim();
if (!trimmed) {
return false;
}
return [
isNoiseLine(trimmed),
/^[-=]{4,}$/.test(trimmed),
/^>/.test(trimmed),
/^Kullanici /i.test(trimmed),
/^Mazlum nasilsin\?/i.test(trimmed),
/^[A-Za-zÀ-ÿ]+,/.test(trimmed)
].some(Boolean);
}
function isContinuationLine(line) {
const trimmed = line.trim();
if (!trimmed) {
return true;
}
return [
/^[A-Za-zÀ-ÿ0-9ÇĞİÖŞÜçğıöşü"'`(]/.test(trimmed),
/^[.!?…]/.test(trimmed),
/^💪|^😊|^🚀|^☕|^🎨|^📱/.test(trimmed)
].some(Boolean);
}
function dedupeMessages(messages) {
const seen = new Set();
const result = [];
for (const message of messages) {
const key = `${message.speaker}::${message.text}`;
if (seen.has(key)) {
continue;
}
seen.add(key);
result.push(message);
}
return result;
}
export function parseTeamFeed(chat) {
const entries = [];
let currentEntry = null;
for (const rawLine of String(chat ?? "").split("\n")) {
const line = rawLine.trim();
const speakerMatch = line.match(/^[•*\-⏺]?\s*([A-Za-zÀ-ÿ]+):\s*(.*)$/);
if (speakerMatch) {
const member = memberMap.get(normalizeSpeaker(speakerMatch[1]));
if (!member) {
currentEntry = null;
continue;
}
currentEntry = {
id: `${member.id}_${entries.length}_${Date.now()}`,
speaker: member.name,
text: speakerMatch[2] || ""
};
entries.push(currentEntry);
continue;
}
if (!currentEntry) {
continue;
}
if (shouldBreakCurrentEntry(line)) {
currentEntry = null;
continue;
}
if (!isContinuationLine(line)) {
continue;
}
currentEntry.text = currentEntry.text ? `${currentEntry.text}\n${line}` : line;
}
return TEAM_MEMBERS.map((member) => ({
...member,
messages: dedupeMessages(entries.filter((entry) => entry.speaker === member.name))
}));
}
export { TEAM_MEMBERS };