116 lines
3.9 KiB
Python
116 lines
3.9 KiB
Python
import io
|
|
import logging
|
|
import simplejson as json
|
|
import pandas as pd
|
|
import mappings
|
|
import ghostfolio_service
|
|
import datetime
|
|
from correpy.domain.enums import TransactionType
|
|
from correpy.parsers.brokerage_notes.parser_factory import ParserFactory
|
|
from fastapi import UploadFile
|
|
import re
|
|
|
|
account_id = '1590f1bb-b3ee-4dc8-ac46-bd1f15a83e87'
|
|
|
|
logger = logging.getLogger(__name__)
|
|
|
|
|
|
def read_brokerage_pdf(file: UploadFile):
|
|
content = io.BytesIO(file.file.read())
|
|
content.seek(0)
|
|
|
|
logger.info(f'Processing {file.filename} ')
|
|
|
|
try:
|
|
brokerage_notes = ParserFactory(brokerage_note=content, password='052').parse()
|
|
return convert_to_ghostfolio(brokerage_notes, file.filename)
|
|
except Exception as e:
|
|
print(f'Failed to parse {file.filename}: {e}')
|
|
logger.error(f'Failed to parse {file.filename}: {e}')
|
|
return 500
|
|
|
|
|
|
def convert_to_ghostfolio(brokerage_list: list, filename: str):
|
|
activities = {}
|
|
|
|
for brokerage_note in brokerage_list:
|
|
reference_date = brokerage_note.reference_date.isoformat() + 'T00:00:00.000Z'
|
|
fees = (brokerage_note.settlement_fee + brokerage_note.emoluments + brokerage_note.others) / len(
|
|
brokerage_note.transactions)
|
|
|
|
# activities['meta'] = {'date': datetime.datetime.now().isoformat(), 'version': 'v0'}
|
|
activities['activities'] = []
|
|
# activities['updateCashBalance'] = 'false'
|
|
|
|
for transaction in brokerage_note.transactions:
|
|
|
|
# activity['fee'] = (brokerage_note.settlement_fee + brokerage_note.emoluments)
|
|
|
|
transaction_type: str = ''
|
|
|
|
if transaction.transaction_type == TransactionType.BUY:
|
|
transaction_type = 'BUY'
|
|
elif transaction.transaction_type == TransactionType.SELL:
|
|
transaction_type = 'SELL'
|
|
|
|
name = re.sub(r'@|#' , '', transaction.security.name.strip())
|
|
|
|
activity = {'accountId': account_id, 'comment': filename, 'date': reference_date,
|
|
'type': transaction_type,
|
|
'fee': fees, 'unitPrice': transaction.unit_price, 'quantity': transaction.amount,
|
|
'symbol': mappings.name_to_tickers[name.strip()].strip(),
|
|
'currency': 'BRL',
|
|
'dataSource': 'YAHOO'}
|
|
activities['activities'].append(activity)
|
|
|
|
if len(activity['symbol']) < 1:
|
|
logger.info(f'No symbol for {transaction.security.name}')
|
|
|
|
result = ghostfolio_service.import_activities(activities, filename)
|
|
|
|
return result
|
|
|
|
|
|
def read_dividends_xlsx(file: UploadFile):
|
|
dividends_xlsx = file.file
|
|
df = pd.read_excel(dividends_xlsx, engine='openpyxl')
|
|
path = f'./{file.filename}'
|
|
df.to_csv(path, encoding='utf-8')
|
|
df = pd.read_csv(path, encoding='utf-8')
|
|
df = df[df['Produto'].notnull()]
|
|
df = df[df['Tipo de Evento'] != 'PAGAMENTO DE JUROS']
|
|
|
|
return dividends_df_to_ghostfolio(df, file.filename)
|
|
|
|
|
|
def dividends_df_to_ghostfolio(dividends_df: pd.DataFrame, filename: str):
|
|
activities = {"activities": []}
|
|
|
|
for index, row in dividends_df.iterrows():
|
|
payment_date = datetime.datetime.strptime(row['Pagamento'], "%d/%m/%Y").isoformat()
|
|
name = row['Produto'].split('-')[0].strip() + '.SA'
|
|
|
|
if name in mappings.ticker_changes:
|
|
symbol = mappings.ticker_changes[name]
|
|
else:
|
|
symbol = name
|
|
|
|
activity = {
|
|
"accountId": account_id,
|
|
"date": payment_date,
|
|
"comment": filename,
|
|
"currency": "BRL",
|
|
"dataSource": "YAHOO",
|
|
"quantity": row['Quantidade'],
|
|
"type": "DIVIDEND",
|
|
"symbol": symbol,
|
|
"unitPrice": row['Preço unitário'],
|
|
"fee": 0
|
|
}
|
|
|
|
activities["activities"].append(activity)
|
|
|
|
print(activities)
|
|
|
|
return ghostfolio_service.import_activities(activities, filename)
|