mirror of
https://github.com/KnugiHK/WhatsApp-Chat-Exporter.git
synced 2026-04-27 00:11:33 +00:00
80 lines
2.8 KiB
Python
80 lines
2.8 KiB
Python
import itertools
|
|
from typing import List, TypedDict
|
|
import vobject
|
|
|
|
class ContactsNamesFromVCards:
|
|
def __init__(self) -> None:
|
|
self.l = []
|
|
|
|
def should_enrich_from_vcards(self):
|
|
return len(self.l) > 0
|
|
|
|
def load_vcf_file(self, vcfFilePath: str, default_country_calling_code: str):
|
|
self.l = readVCardsFile(vcfFilePath, default_country_calling_code)
|
|
|
|
def enrich_names_from_vCards(self, chats):
|
|
for counter, (number, name) in enumerate(self.l):
|
|
# short number must be a bad contact, lets skip it
|
|
if len(number) <= 5:
|
|
continue
|
|
|
|
for counter, chat in enumerate(filter_dict_by_prefix(chats, number).values()):
|
|
if not hasattr(chat, 'name') or (hasattr(chat, 'name') and chat.name is None):
|
|
setattr(chat, 'name', name)
|
|
|
|
|
|
def readVCardsFile(vcfFilePath, default_country_calling_code: str):
|
|
contacts = []
|
|
with open(vcfFilePath, mode="r") as f:
|
|
reader = vobject.readComponents(f)
|
|
for row in reader:
|
|
if not hasattr(row, 'fn'):
|
|
continue
|
|
|
|
if not hasattr(row, 'tel'):
|
|
continue
|
|
|
|
contact: ExportedGoogleContactVCARDRawNumbers = {
|
|
"full_name": row.fn.value,
|
|
"numbers": list(map(lambda tel:tel.value, row.tel_list)),
|
|
}
|
|
|
|
contacts.append(contact)
|
|
|
|
step2 = createNumberToNameDicts(contacts, default_country_calling_code)
|
|
|
|
return step2
|
|
|
|
|
|
def filter_dict_by_prefix(d, prefix: str):
|
|
return {k: v for k, v in d.items() if k.startswith(prefix)}
|
|
|
|
def createNumberToNameDicts(inContacts, default_country_calling_code: str):
|
|
outContacts = list(itertools.chain.from_iterable(
|
|
[[normalize_number(num, default_country_calling_code), f"{contact['full_name']} ({i+1})" if len(contact['numbers']) > 1 else contact['full_name']]
|
|
for i, num in enumerate(contact['numbers'])]
|
|
for contact in inContacts
|
|
))
|
|
|
|
return outContacts
|
|
|
|
class ExportedGoogleContactVCARDRawNumbers(TypedDict):
|
|
full_name: str
|
|
numbers: List[str]
|
|
|
|
def normalize_number(number: str, default_country_calling_code: str):
|
|
afterSomeCleaning = number.replace('(', '').replace(')', '').replace(' ', '').replace('-', '')
|
|
|
|
# A number that starts with a + or 00 means it already have country_calling_code
|
|
if afterSomeCleaning.startswith('+'):
|
|
afterSomeCleaning = afterSomeCleaning.replace('+', '')
|
|
elif afterSomeCleaning.startswith('00'):
|
|
afterSomeCleaning = afterSomeCleaning[2:]
|
|
else:
|
|
# Remove leading zero
|
|
if afterSomeCleaning.startswith('0'):
|
|
afterSomeCleaning = afterSomeCleaning[1:]
|
|
|
|
afterSomeCleaning = default_country_calling_code + afterSomeCleaning
|
|
|
|
return afterSomeCleaning |