add politician

This commit is contained in:
MuslemRahimi 2024-09-02 11:00:29 +02:00
parent 7cc6f32c58
commit f8049d2495

View File

@ -1,10 +1,7 @@
import { formatDistanceToNow } from "date-fns";
import { formatDistanceToNow } from 'date-fns';
let pbCloudImage = import.meta.env.VITE_IMAGE_POCKETBASE_URL; // Set a default API URL let pbCloudImage = import.meta.env.VITE_IMAGE_POCKETBASE_URL; // Set a default API URL
import { clsx, type ClassValue } from "clsx"; import { clsx, type ClassValue } from "clsx";
import { twMerge } from "tailwind-merge"; import { twMerge } from "tailwind-merge";
import { cubicOut } from "svelte/easing"; import { cubicOut } from "svelte/easing";
@ -14,7 +11,6 @@ export function cn(...inputs: ClassValue[]) {
return twMerge(clsx(inputs)); return twMerge(clsx(inputs));
} }
type FlyAndScaleParams = { type FlyAndScaleParams = {
y?: number; y?: number;
x?: number; x?: number;
@ -77,7 +73,6 @@ export const flyAndScale = (
}; };
}; };
export const formatDateRange = (lastDateStr) => { export const formatDateRange = (lastDateStr) => {
// Convert lastDateStr to Date object // Convert lastDateStr to Date object
const lastDate = new Date(lastDateStr); const lastDate = new Date(lastDateStr);
@ -86,12 +81,21 @@ export const formatDateRange = (lastDateStr) => {
const firstDate = new Date(lastDate.getFullYear(), lastDate.getMonth(), 1); const firstDate = new Date(lastDate.getFullYear(), lastDate.getMonth(), 1);
// Format first and last dates // Format first and last dates
const firstDateFormatted = firstDate.toLocaleString('en-US', { month: 'short', day: 'numeric', year: 'numeric', day: '2-digit' }); const firstDateFormatted = firstDate.toLocaleString("en-US", {
const lastDateFormatted = lastDate.toLocaleString('en-US', { month: 'short', day: 'numeric', year: 'numeric', day: '2-digit' }); month: "short",
day: "numeric",
year: "numeric",
day: "2-digit",
});
const lastDateFormatted = lastDate.toLocaleString("en-US", {
month: "short",
day: "numeric",
year: "numeric",
day: "2-digit",
});
// Construct and return the formatted date range string // Construct and return the formatted date range string
return `${firstDateFormatted} - ${lastDateFormatted}`; return `${firstDateFormatted} - ${lastDateFormatted}`;
} };
export const serializeNonPOJOs = (obj) => { export const serializeNonPOJOs = (obj) => {
return structuredClone(obj); return structuredClone(obj);
@ -99,41 +103,36 @@ export const serializeNonPOJOs = (obj) => {
export const generateUsername = (name) => { export const generateUsername = (name) => {
const randomHex = Math.floor(Math.random() * 65536).toString(16); const randomHex = Math.floor(Math.random() * 65536).toString(16);
const id = randomHex.padStart(4, '0'); const id = randomHex.padStart(4, "0");
return `${name.slice(0, 5)}${id}`; return `${name.slice(0, 5)}${id}`;
}; };
export const getImageURL = (collectionId, recordId, fileName, size = "0x0") => {
export const getImageURL = (collectionId, recordId, fileName, size = '0x0') => {
//For development or local storage or S3 bucket without CDN Cloudfront //For development or local storage or S3 bucket without CDN Cloudfront
if(pbCloudImage === 'http://localhost:8090') if (pbCloudImage === "http://localhost:8090") {
{
return `${pbCloudImage}/api/files/${collectionId}/${recordId}/${fileName}?thumb=${size}`; return `${pbCloudImage}/api/files/${collectionId}/${recordId}/${fileName}?thumb=${size}`;
} }
return `${pbCloudImage}/${collectionId}/${recordId}/${fileName}?thumb=${size}`; return `${pbCloudImage}/${collectionId}/${recordId}/${fileName}?thumb=${size}`;
}; };
export const validateData = async (formData, schema) => { export const validateData = async (formData, schema) => {
const body = Object.fromEntries(formData) const body = Object.fromEntries(formData);
try { try {
const data = schema.parse(body); const data = schema.parse(body);
return { return {
formData: data, formData: data,
errors: null errors: null,
} };
} catch (err) { } catch (err) {
console.log('Error: ', err) console.log("Error: ", err);
const errors = err.flatten() const errors = err.flatten();
return { return {
formData: body, formData: body,
errors errors,
};
} }
} };
}
export function sumQuarterlyResultsByYear(quarterlyResults, namingList) { export function sumQuarterlyResultsByYear(quarterlyResults, namingList) {
const yearlySummaries = {}; const yearlySummaries = {};
@ -143,21 +142,31 @@ export function sumQuarterlyResultsByYear(quarterlyResults, namingList) {
// Define a Set of keys to exclude from summing // Define a Set of keys to exclude from summing
// FMP sucks since these keys are up to date for every quarter hence no summation required // FMP sucks since these keys are up to date for every quarter hence no summation required
const excludeKeys = new Set(['totalDebt','priceToEarnings', 'weightedAverageShsOut', 'weightedAverageShsOutDil']); const excludeKeys = new Set([
"totalDebt",
"priceToEarnings",
"weightedAverageShsOut",
"weightedAverageShsOutDil",
]);
// Function to get the quarter number from the period string // Function to get the quarter number from the period string
function getQuarterNumber(period) { function getQuarterNumber(period) {
switch (period) { switch (period) {
case 'Q1': return 1; case "Q1":
case 'Q2': return 2; return 1;
case 'Q3': return 3; case "Q2":
case 'Q4': return 4; return 2;
default: return 0; case "Q3":
return 3;
case "Q4":
return 4;
default:
return 0;
} }
} }
// Iterate over each quarterly result // Iterate over each quarterly result
quarterlyResults?.forEach(quarter => { quarterlyResults?.forEach((quarter) => {
// Extract year and quarter from the data // Extract year and quarter from the data
const year = quarter?.calendarYear; const year = quarter?.calendarYear;
const quarterNum = getQuarterNumber(quarter?.period); const quarterNum = getQuarterNumber(quarter?.period);
@ -167,7 +176,7 @@ export function sumQuarterlyResultsByYear(quarterlyResults, namingList) {
yearlySummaries[year] = { yearlySummaries[year] = {
calendarYear: `${year}`, // Use end of the year date calendarYear: `${year}`, // Use end of the year date
lastQuarterProcessed: 0, // Keep track of the last quarter processed lastQuarterProcessed: 0, // Keep track of the last quarter processed
date: quarter?.date // Copy the 'date' field unchanged date: quarter?.date, // Copy the 'date' field unchanged
}; };
quarterCounts[year] = 0; quarterCounts[year] = 0;
} }
@ -183,9 +192,14 @@ export function sumQuarterlyResultsByYear(quarterlyResults, namingList) {
} }
// Sum up the numeric fields for the year, excluding specific keys // Sum up the numeric fields for the year, excluding specific keys
Object?.keys(quarter)?.forEach(key => { Object?.keys(quarter)?.forEach((key) => {
if (typeof quarter[key] === 'number' && !excludeKeys?.has(key) && !lastQuarterKeys.has(key)) { if (
yearlySummaries[year][key] = (yearlySummaries[year][key] || 0) + quarter[key]; typeof quarter[key] === "number" &&
!excludeKeys?.has(key) &&
!lastQuarterKeys.has(key)
) {
yearlySummaries[year][key] =
(yearlySummaries[year][key] || 0) + quarter[key];
} else if (excludeKeys.has(key)) { } else if (excludeKeys.has(key)) {
// Directly copy the last quarter value for these keys // Directly copy the last quarter value for these keys
yearlySummaries[year][key] = quarter[key]; yearlySummaries[year][key] = quarter[key];
@ -197,8 +211,10 @@ export function sumQuarterlyResultsByYear(quarterlyResults, namingList) {
}); });
// Filter out years with less than 4 quarters // Filter out years with less than 4 quarters
const validYears = Object?.keys(quarterCounts)?.filter(year => quarterCounts[year] === 4); const validYears = Object?.keys(quarterCounts)?.filter(
const annualResults = validYears?.map(year => yearlySummaries[year]); (year) => quarterCounts[year] === 4
);
const annualResults = validYears?.map((year) => yearlySummaries[year]);
// Sort the results by year in descending order // Sort the results by year in descending order
annualResults.sort((a, b) => b?.calendarYear?.localeCompare(a?.calendarYear)); annualResults.sort((a, b) => b?.calendarYear?.localeCompare(a?.calendarYear));
@ -206,38 +222,66 @@ export function sumQuarterlyResultsByYear(quarterlyResults, namingList) {
return annualResults; return annualResults;
} }
export const sortPostsByDate = (posts) => { export const sortPostsByDate = (posts) => {
return posts.sort(function (a, b) { return posts.sort(function (a, b) {
return new Date(b.created) - new Date(a.created); return new Date(b.created) - new Date(a.created);
}); });
} };
export function capitalizeFirstLetter(string) { export function capitalizeFirstLetter(string) {
return string.charAt(0).toUpperCase() + string.slice(1); return string.charAt(0).toUpperCase() + string.slice(1);
} }
export function formatString(inputString) { export function formatString(inputString) {
// Split the input string into words using space as a delimiter // Split the input string into words using space as a delimiter
const words = inputString?.split(' '); const words = inputString?.split(" ");
// Capitalize the first letter of each word and convert the rest to lowercase // Capitalize the first letter of each word and convert the rest to lowercase
const formattedWords = words?.map((word, index) => { const formattedWords = words?.map((word, index) => {
if (word.length > 0) { if (word.length > 0) {
// Check if the word is "LTG" or "LLC" and keep them uppercase // Check if the word is "LTG" or "LLC" and keep them uppercase
const excludedList = ['n/a','CEO','U.S.','NGL','ETF','SPDR','S&P','USD','US','JPMORGAN','SRS','AQR','XN','TIG','HAP','AB','AKRE','LTG', 'LLC','JVL', 'NJ', 'FMR', 'LP', 'NNS','BPS','BNP','PCG','CTC','IMC', 'PLC','WIT']; const excludedList = [
"n/a",
"CEO",
"U.S.",
"NGL",
"ETF",
"SPDR",
"S&P",
"USD",
"US",
"JPMORGAN",
"SRS",
"AQR",
"XN",
"TIG",
"HAP",
"AB",
"AKRE",
"LTG",
"LLC",
"JVL",
"NJ",
"FMR",
"LP",
"NNS",
"BPS",
"BNP",
"PCG",
"CTC",
"IMC",
"PLC",
"WIT",
];
// Check if the word is "black-rock" and format it accordingly // Check if the word is "black-rock" and format it accordingly
if (index < words?.length - 1 && word?.toLowerCase() === 'black' && words[index + 1]?.toLowerCase() === 'rock') { if (
return 'Black Rock'; index < words?.length - 1 &&
} word?.toLowerCase() === "black" &&
else if (excludedList?.includes(word)) { words[index + 1]?.toLowerCase() === "rock"
) {
return "Black Rock";
} else if (excludedList?.includes(word)) {
return word; return word;
} else { } else {
return word?.charAt(0)?.toUpperCase() + word?.slice(1)?.toLowerCase(); return word?.charAt(0)?.toUpperCase() + word?.slice(1)?.toLowerCase();
@ -247,20 +291,23 @@ export function capitalizeFirstLetter(string) {
}); });
// Join the formatted words back together with spaces // Join the formatted words back together with spaces
const formattedString = formattedWords?.join(' '); const formattedString = formattedWords?.join(" ");
return formattedString; return formattedString;
} }
export function abbreviateNumber(number, addDollarSign = false) { export function abbreviateNumber(number, addDollarSign = false) {
const negative = number < 0; const negative = number < 0;
// Handle special case for exactly 1000 // Handle special case for exactly 1000
if (Math.abs(number) === 1000) { if (Math.abs(number) === 1000) {
return addDollarSign ? (negative ? '-$1K' : '$1K') : (negative ? '-1K' : '1K'); return addDollarSign
? negative
? "-$1K"
: "$1K"
: negative
? "-1K"
: "1K";
} }
if (Math.abs(number) !== 0 && Math.abs(number) > 1000) { if (Math.abs(number) !== 0 && Math.abs(number) > 1000) {
@ -276,81 +323,89 @@ export function capitalizeFirstLetter(string) {
abbreviation = abbreviation.toFixed(2); abbreviation = abbreviation.toFixed(2);
} }
abbreviation = abbreviation.toLocaleString('en-US', { maximumFractionDigits: 2, minimumFractionDigits: 2 }); abbreviation = abbreviation.toLocaleString("en-US", {
maximumFractionDigits: 2,
minimumFractionDigits: 2,
});
if (Math.abs(number) % 1000 === 0) { if (Math.abs(number) % 1000 === 0) {
abbreviation = abbreviation.replace('-', ''); abbreviation = abbreviation.replace("-", "");
} }
if (abbreviation?.slice(-3) === '.00') { if (abbreviation?.slice(-3) === ".00") {
abbreviation = abbreviation.slice(0, -3); abbreviation = abbreviation.slice(0, -3);
} }
const formattedNumber = abbreviation + suffixes[index]; const formattedNumber = abbreviation + suffixes[index];
if (addDollarSign) { if (addDollarSign) {
return (negative ? '-$' : '$') + formattedNumber; return (negative ? "-$" : "$") + formattedNumber;
} else { } else {
return negative ? '-' + formattedNumber : formattedNumber; return negative ? "-" + formattedNumber : formattedNumber;
} }
} } else if (Math.abs(number) >= 0 && Math.abs(number) < 1000) {
else if (Math.abs(number) >= 0 && Math.abs(number) < 1000) {
if (addDollarSign) { if (addDollarSign) {
return (negative ? '-$' : '$') + number; return (negative ? "-$" : "$") + number;
} else { } else {
return number; return number;
} }
} } else {
return addDollarSign ? "$0" : "0";
else {
return addDollarSign ? '$0' : '0';
} }
} }
export const formatDate = (dateString) => { export const formatDate = (dateString) => {
const date = new Date(dateString) const date = new Date(dateString);
return formatDistanceToNow(date, { addSuffix: false, includeSeconds: false })?.replace(/about /i, '') return formatDistanceToNow(date, {
} addSuffix: false,
includeSeconds: false,
})?.replace(/about /i, "");
};
export const formatRuleValue = (rule) => { export const formatRuleValue = (rule) => {
if (['interestIncome', 'interestExpenses'].includes(rule.name)) { if (["interestIncome", "interestExpenses"].includes(rule.name)) {
return `$${rule.value === 1000 ? `${rule.value / 1000} Bn` : `${rule.value} Mio`}`; return `$${rule.value === 1000 ? `${rule.value / 1000} Bn` : `${rule.value} Mio`}`;
} else if (['revenue', 'costOfRevenue', 'costAndExpenses', 'netIncome', 'grossProfit', 'researchAndDevelopmentExpenses', 'marketCap', 'operatingExpenses', 'operatingIncome', 'ebitda'].includes(rule.name)) { } else if (
[
"revenue",
"costOfRevenue",
"costAndExpenses",
"netIncome",
"grossProfit",
"researchAndDevelopmentExpenses",
"marketCap",
"operatingExpenses",
"operatingIncome",
"ebitda",
].includes(rule.name)
) {
return `${rule.condition} $${rule.value} Bn`; return `${rule.condition} $${rule.value} Bn`;
} else if (rule.name === 'aiSignal') { } else if (rule.name === "aiSignal") {
return `${rule.value === '2' ? 'Buy' : rule.value === '1' ? 'Hold' : rule.value === '0' ? 'Sell' : 'n/a'} Signal`; return `${rule.value === "2" ? "Buy" : rule.value === "1" ? "Hold" : rule.value === "0" ? "Sell" : "n/a"} Signal`;
} } else if (["avgVolume"].includes(rule.name)) {
else if (['avgVolume'].includes(rule.name)) {
return `${rule.condition} ${rule.value} Mio`; return `${rule.condition} ${rule.value} Mio`;
} } else if (["var"].includes(rule.name)) {
else if (['var'].includes(rule.name)) {
return `${rule.condition} ${rule.value}%`; return `${rule.condition} ${rule.value}%`;
} } else if (["ratingRecommendation"].includes(rule.name)) {
else if (['ratingRecommendation'].includes(rule.name)) { return rule.value === 2 ? "Buy" : rule.value === 1 ? "Hold" : "Sell";
return rule.value === 2 ? 'Buy' : rule.value === 1 ? 'Hold' : 'Sell'; } else if (["trendAnalysis", "fundamentalAnalysis"].includes(rule.name)) {
}
else if (['trendAnalysis','fundamentalAnalysis'].includes(rule.name)) {
return `${rule.condition} ${rule.value}% Accuracy`; return `${rule.condition} ${rule.value}% Accuracy`;
} else {
return `${rule.condition} ${rule.value}${rule.name.includes("Growth") ? " %" : ""}`;
} }
else { };
return `${rule.condition} ${rule.value}${rule.name.includes('Growth') ? ' %' : ''}`;
}
}
export function formatETFName(inputString) { export function formatETFName(inputString) {
// Define special cases // Define special cases
const specialCases = { const specialCases = {
"etf-mg": "ETFMG", "etf-mg": "ETFMG",
"ark": "ARK", ark: "ARK",
"index-iq": "IndexIQ", "index-iq": "IndexIQ",
"bny-mellon": "BNY Mellon", "bny-mellon": "BNY Mellon",
"ssc": "SS&C", ssc: "SS&C",
"pgim": "PGIM", pgim: "PGIM",
"jpmorgan-chase": "JPMorgan Chase", "jpmorgan-chase": "JPMorgan Chase",
"us-global-investors": "US Global Investors" "us-global-investors": "US Global Investors",
// Add more special cases as needed // Add more special cases as needed
}; };
@ -361,18 +416,19 @@ export function formatETFName(inputString) {
} }
// Split the input string into an array of words // Split the input string into an array of words
const words = inputString?.split('-'); const words = inputString?.split("-");
// Capitalize the first letter of each word // Capitalize the first letter of each word
const capitalizedWords = words?.map(word => word.charAt(0)?.toUpperCase() + word?.slice(1)); const capitalizedWords = words?.map(
(word) => word.charAt(0)?.toUpperCase() + word?.slice(1)
);
// Join the words back together with a space between them // Join the words back together with a space between them
const formattedString = capitalizedWords?.join(' '); const formattedString = capitalizedWords?.join(" ");
return formattedString; return formattedString;
} }
// Function to add days to a given date // Function to add days to a given date
export function addDays(data, days, state) { export function addDays(data, days, state) {
let result; let result;
@ -381,19 +437,20 @@ export function addDays(data, days, state) {
result = new Date(createdDate); result = new Date(createdDate);
result.setDate(result.getDate() + days); result.setDate(result.getDate() + days);
if(state === 'date') { if (state === "date") {
return result; return result;
} else { } else {
const differenceInTime = result - createdDate; const differenceInTime = result - createdDate;
const differenceInDays = Math.round(differenceInTime / (1000 * 60 * 60 * 24)); const differenceInDays = Math.round(
differenceInTime / (1000 * 60 * 60 * 24)
);
return Math.abs(differenceInDays); return Math.abs(differenceInDays);
} }
} }
export function pageTransitionIn(node, { duration, screenWidth }) { export function pageTransitionIn(node, { duration, screenWidth }) {
if (screenWidth >= 640) if (screenWidth >= 640) {
{ return;
return
} }
return { return {
duration, duration,
@ -408,7 +465,7 @@ export function pageTransitionIn(node, { duration, screenWidth }) {
z-index: 9999; z-index: 9999;
transition: transform ${duration}ms ease-out; transition: transform ${duration}ms ease-out;
`; `;
} },
}; };
} }
@ -430,7 +487,6 @@ export function pageTransitionOut(node, { duration }) {
}; };
} }
/* /*
function convertNYTimeToLocalTime(nyTimeString) { function convertNYTimeToLocalTime(nyTimeString) {
// New York Time Zone // New York Time Zone
@ -714,7 +770,7 @@ export function getPartyForPoliticians(name) {
"Buddy Carter": "Republican", "Buddy Carter": "Republican",
"John Fetterman": "Democratic", "John Fetterman": "Democratic",
"Sharice Davids": "Democratic", "Sharice Davids": "Democratic",
"Jake Auchincloss": "Democratic",
}; };
// Combine first and last name to form the key // Combine first and last name to form the key
@ -723,8 +779,6 @@ export function getPartyForPoliticians(name) {
return senatorPartyMap[nameKey] || "Other"; return senatorPartyMap[nameKey] || "Other";
} }
export const listOfCountries = [ export const listOfCountries = [
"Afghanistan", "Afghanistan",
"Albania", "Albania",
@ -921,5 +975,5 @@ export const listOfCountries = [
"Vietnam", "Vietnam",
"Yemen", "Yemen",
"Zambia", "Zambia",
"Zimbabwe" "Zimbabwe",
]; ];