量化交易之vnpy篇 - 报表自动化 - private api part部分

# --- auto report api of private part ---
    @classmethod
    def __create_source_data_excel(cls, settlement_jsonfile):
        """
        Create dataframe about source data
        """
        TQZAutoReportFilePath.ensure_sourceDataFold_is_exist()

        account_models = cls.__sourceData_to_modelList(settlement_jsonfile=settlement_jsonfile)

        accounts_name = []
        accounts_id = []
        accounts_balance = []
        accounts_risk_percent = []
        accounts_deposit = []  # 当日入金
        accounts_transfer = []  # 当日出金
        accounts_bonus = []  # 当日分红 (盈利分红 不动份额)

        for account_model in account_models:
            accounts_name.append(account_model.account_name)
            accounts_id.append(account_model.account_id)
            accounts_balance.append(account_model.balance)
            accounts_risk_percent.append(str(account_model.risk_percent) + "%")
            accounts_deposit.append(0)
            accounts_transfer.append(0)
            accounts_bonus.append(0)

        source_dataframe = pandas.DataFrame({
            TQZAutoReportSourceDataColumnType.ACCOUNT_NAME.value: accounts_name,
            TQZAutoReportSourceDataColumnType.ACCOUNT_ID.value: accounts_id,
            TQZAutoReportSourceDataColumnType.ACCOUNT_BALANCE.value: accounts_balance,
            TQZAutoReportSourceDataColumnType.ACCOUNT_RISK_PERCENT.value: accounts_risk_percent,
            TQZAutoReportSourceDataColumnType.ACCOUNT_DEPOSIT.value: accounts_deposit,
            TQZAutoReportSourceDataColumnType.ACCOUNT_TRANSFER.value: accounts_transfer,
            TQZAutoReportSourceDataColumnType.ACCOUNT_BONUS.value: accounts_bonus
        })

        cls.__to_excel(
            dataframe=source_dataframe,
            excel_path=TQZAutoReportFilePath.theory_source_data_excel_path(),
            sheet_name=TQZAutoReportSheetType.SOURCE_DATA.value,
            empty_others=True
        )

    @classmethod
    def __update_per_account_data_excel(cls):
        """
        Update excel data of per account after source data excel was update
        """
        if cls.__per_account_data_updateable() is False:
            return

        # source data excel
        source_dataframe_path = TQZAutoReportFilePath.theory_source_data_excel_path()
        source_dataframe = pandas.read_excel(
            io=source_dataframe_path,
            sheet_name=TQZAutoReportSheetType.SOURCE_DATA.value
        )

        # get current running accounts_id_list
        accounts_id_list = source_dataframe[TQZAutoReportSourceDataColumnType.ACCOUNT_ID.value].values.tolist()

        # 根据 account_id 拿 账户权益
        source_dataframe.set_index(TQZAutoReportSourceDataColumnType.ACCOUNT_ID.value, inplace=True)
        for account_id in accounts_id_list:

            per_account_filename = account_id + '.xlsx'
            per_account_all_path = TQZAutoReportFilePath.per_account_data_fold() + f'/{per_account_filename}'
            if per_account_filename not in os.listdir(TQZAutoReportFilePath.per_account_data_fold()):

                cls.__create_per_account_data_excel(
                    account_all_path=per_account_all_path,
                    account_balance=source_dataframe.loc[account_id][TQZAutoReportSourceDataColumnType.ACCOUNT_BALANCE.value],
                    account_deposit=source_dataframe.loc[account_id][TQZAutoReportSourceDataColumnType.ACCOUNT_DEPOSIT.value],
                    account_transfer=source_dataframe.loc[account_id][TQZAutoReportSourceDataColumnType.ACCOUNT_TRANSFER.value],
                    account_bonus=source_dataframe.loc[account_id][TQZAutoReportSourceDataColumnType.ACCOUNT_BONUS.value]
                )
            else:
                per_account_dataframe = pandas.read_excel(io=per_account_all_path, sheet_name=TQZAutoReportSheetType.PER_ACCOUNT_DATA.value)

                per_account_dataframe = cls.__per_account_dataframe_update_last_line(
                    per_account_dataframe=per_account_dataframe,
                    account_balance=source_dataframe.loc[account_id][TQZAutoReportSourceDataColumnType.ACCOUNT_BALANCE.value],
                    account_deposit=source_dataframe.loc[account_id][TQZAutoReportSourceDataColumnType.ACCOUNT_DEPOSIT.value],
                    account_transfer=source_dataframe.loc[account_id][TQZAutoReportSourceDataColumnType.ACCOUNT_TRANSFER.value],
                    account_bonus=source_dataframe.loc[account_id][TQZAutoReportSourceDataColumnType.ACCOUNT_BONUS.value]
                )

                cls.__to_excel(
                    dataframe=per_account_dataframe,
                    excel_path=per_account_all_path,
                    sheet_name=TQZAutoReportSheetType.PER_ACCOUNT_DATA.value,
                    empty_others=False
                )

    @classmethod
    def __update_today_images(cls):
        """
        Update today images of current running accounts.
        """

        for file_name in os.listdir(TQZAutoReportFilePath.today_images_fold()):
            os.remove(path=TQZAutoReportFilePath.today_images_fold() + f'/{file_name}')

        current_running_account_list = cls.__current_source_data_dataframe()[TQZAutoReportSourceDataColumnType.ACCOUNT_ID.value].values.tolist()

        for file_name in os.listdir(TQZAutoReportFilePath.per_account_data_fold()):
            all_path = TQZAutoReportFilePath.per_account_data_fold() + f'/{file_name}'

            per_account_dataframe = pandas.read_excel(io=all_path, sheet_name=TQZAutoReportSheetType.PER_ACCOUNT_DATA.value)

            account_id = file_name.split(".")[0]

            if account_id not in current_running_account_list:
                print(f'{account_id} not in current_running_account_list')
                continue

            font_type_daily = 'Microsoft YaHei'

            plt.rcParams['font.sans-serif'] = [font_type_daily]  # 用来正常显示中文标签
            plt.rcParams['axes.unicode_minus'] = False  # 用来正常显示负号
            plt.style.use('seaborn-darkgrid')
            my_dpi = 96
            plt.figure(figsize=(8, 8), dpi=my_dpi)
            grid = plt.GridSpec(7, 6, wspace=2, hspace=2)
            ax1 = plt.subplot(grid[3:7, 0:10], frameon=True)
            plt.grid(axis='x')

            if len(per_account_dataframe) <= 8:
                plt.ylim(0.80, 1.2)
                ax1.xaxis.set_major_formatter(mdate.DateFormatter('%Y-%m-%d'))

                plt.xticks(pandas.date_range(per_account_dataframe.loc[1, TQZAutoReportPerAccountDataColumnType.DATE.value], per_account_dataframe.loc[len(per_account_dataframe)-1, TQZAutoReportPerAccountDataColumnType.DATE.value], freq='D'))

            plt.subplots_adjust(left=0.05, bottom=0.0, right=0.95, top=1, hspace=0.1, wspace=0.1)

            plt.plot(per_account_dataframe[TQZAutoReportPerAccountDataColumnType.DATE.value], per_account_dataframe[TQZAutoReportPerAccountDataColumnType.NET_VALUE.value], marker='', color="red", linewidth=2.5, alpha=0.6)
            for tick in ax1.get_xticklabels():
                tick.set_rotation(30)

            ax2 = plt.subplot(grid[0:3, 0:10], frameon=False)
            ax2.grid(False)
            plt.subplots_adjust(left=0.05, bottom=0.1, right=0.95, top=1, hspace=0.1, wspace=0.1)
            plt.gca().get_xaxis().set_visible(False)
            plt.gca().get_yaxis().set_visible(False)

            font_title = fm.FontProperties(family=font_type_daily, size=18, stretch=0, weight='black')
            font_data = fm.FontProperties(family=font_type_daily, size=25, stretch=0, )
            font_dataNote = fm.FontProperties(family=font_type_daily, size=10, stretch=0, weight='black')
            font_netValue = fm.FontProperties(family=font_type_daily, size=40, stretch=1, weight='medium')
            font_introduce = fm.FontProperties(family=font_type_daily, size=10, stretch=0, weight='black')

            plt.rcParams['axes.unicode_minus'] = False  # 用来正常显示负号

            balance = per_account_dataframe.loc[len(per_account_dataframe)-1, TQZAutoReportPerAccountDataColumnType.BALANCE.value]
            profit_and_loss = round(per_account_dataframe.loc[len(per_account_dataframe)-1, TQZAutoReportPerAccountDataColumnType.RESULT_PROFIT_AND_LOSS.value], 2)

            source_data_dataframe = cls.__current_source_data_dataframe().set_index(TQZAutoReportSourceDataColumnType.ACCOUNT_ID.value)
            risk_percent = source_data_dataframe.loc[account_id][TQZAutoReportSourceDataColumnType.ACCOUNT_RISK_PERCENT.value]

            max_dropDown_singleDay = round(per_account_dataframe[TQZAutoReportPerAccountDataColumnType.NET_VALUE_FLUCTUATION_SINGLE_DAY.value].min() * 100, 3)
            sharpe_ratio = round(per_account_dataframe.loc[len(per_account_dataframe)-1, TQZAutoReportPerAccountDataColumnType.SHARPE_RATIO.value], 2)
            max_dropDown_top = round(per_account_dataframe[TQZAutoReportPerAccountDataColumnType.MAX_DRAWDOWN.value].max() * (-1) * 100, 2)
            net_value = per_account_dataframe.loc[len(per_account_dataframe)-1, TQZAutoReportPerAccountDataColumnType.NET_VALUE.value]
            yield_rate_annualized = per_account_dataframe.loc[len(per_account_dataframe)-1, TQZAutoReportPerAccountDataColumnType.YIELD_RATE_ANNUALIZED.value]
            share = per_account_dataframe.loc[len(per_account_dataframe)-1, TQZAutoReportPerAccountDataColumnType.SHARE.value]

            ax2.text(0, 0.8, f'{cls.__get_account_image_title(account_id=account_id)} - CTA全天候', fontproperties=font_title, bbox={'facecolor': 'red', 'alpha': 0.1}, verticalalignment='bottom', horizontalalignment='left')
            ax2.text(0.11, 0.45, f'{format(int(balance), ",")}', fontproperties=font_data, bbox={'facecolor': 'yellow', 'alpha': 0.0}, verticalalignment='center', horizontalalignment='center')
            ax2.text(0.11, 0.35, r'账户权益', fontproperties=font_dataNote, bbox={'facecolor': 'yellow', 'alpha': 0.0}, verticalalignment='center', horizontalalignment='center')
            ax2.text(0.11, 0.00, f'{format(int(profit_and_loss), ",")}', fontproperties=font_data, bbox={'facecolor': 'yellow', 'alpha': 0.0}, verticalalignment='center', horizontalalignment='center')
            ax2.text(0.11, -0.10, r'累计盈利', fontproperties=font_dataNote, bbox={'facecolor': 'yellow', 'alpha': 0.0}, verticalalignment='center', horizontalalignment='center')

            ax2.text(0.35, 0.45, f'{risk_percent}', fontproperties=font_data, bbox={'facecolor': 'yellow', 'alpha': 0.0}, verticalalignment='center', horizontalalignment='center')
            ax2.text(0.35, 0.35, r'风险度', fontproperties=font_dataNote, bbox={'facecolor': 'yellow', 'alpha': 0.0}, verticalalignment='center', horizontalalignment='center')
            ax2.text(0.35, 0.00, f'{max_dropDown_singleDay}%', fontproperties=font_data, bbox={'facecolor': 'yellow', 'alpha': 0.0}, verticalalignment='center', horizontalalignment='center')
            ax2.text(0.35, -0.10, r'最大单日回撤', fontproperties=font_dataNote, bbox={'facecolor': 'yellow', 'alpha': 0.0}, verticalalignment='center', horizontalalignment='center')

            ax2.text(0.55, 0.45, f'{sharpe_ratio}', fontproperties=font_data, bbox={'facecolor': 'yellow', 'alpha': 0.0}, verticalalignment='center', horizontalalignment='center')
            ax2.text(0.55, 0.35, r'夏普比率', fontproperties=font_dataNote, bbox={'facecolor': 'yellow', 'alpha': 0.0}, verticalalignment='center', horizontalalignment='center')
            ax2.text(0.57, 0.00, f'{max_dropDown_top}%', fontproperties=font_data, bbox={'facecolor': 'yellow', 'alpha': 0.0}, verticalalignment='center', horizontalalignment='center')
            ax2.text(0.57, -0.10, r'最大高点回撤', fontproperties=font_dataNote, bbox={'facecolor': 'yellow', 'alpha': 0.0}, verticalalignment='center', horizontalalignment='center')

            ax2.text(0.80, 0.80, f'{round(net_value, 4)}', fontproperties=font_netValue, bbox={'facecolor': 'yellow', 'alpha': 0.0}, verticalalignment='center', horizontalalignment='center')
            ax2.text(0.80, 0.68, r'累计净值', fontproperties=font_dataNote, bbox={'facecolor': 'yellow', 'alpha': 0.0}, verticalalignment='center', horizontalalignment='center')

            ax2.text(0.81, 0.55, f'{round(yield_rate_annualized * 100, 3)}%', fontproperties=font_data, bbox={'facecolor': 'yellow', 'alpha': 0.0}, verticalalignment='center', horizontalalignment='center')
            ax2.text(0.81, 0.45, r'年化收益率', fontproperties=font_dataNote, bbox={'facecolor': 'yellow', 'alpha': 0.0}, verticalalignment='center', horizontalalignment='center')

            ax2.text(0.73, 0.35, r'*产品说明', fontproperties=font_introduce, bbox={'facecolor': 'yellow', 'alpha': 0.0}, verticalalignment='center', horizontalalignment='center')
            ax2.text(0.74, 0.27, r'投资范围:', fontproperties=font_introduce, bbox={'facecolor': 'yellow', 'alpha': 0.0}, verticalalignment='center', horizontalalignment='center')
            ax2.text(0.80, 0.27, r'股指、国债、商品期货', fontproperties=font_introduce, bbox={'facecolor': 'yellow', 'alpha': 0.0}, verticalalignment='center', horizontalalignment='left')
            ax2.text(0.74, 0.19, r'起始日期:', fontproperties=font_introduce, bbox={'facecolor': 'yellow', 'alpha': 0.0}, verticalalignment='center', horizontalalignment='center')

            start_day = per_account_dataframe.loc[0, TQZAutoReportPerAccountDataColumnType.DATE.value].to_pydatetime()
            ax2.text(0.80, 0.19, f'{start_day.year}-{start_day.month}-{start_day.day}', fontproperties=font_introduce, bbox={'facecolor': 'yellow', 'alpha': 0.0}, verticalalignment='center', horizontalalignment='left')
            ax2.text(0.74, 0.11, r'产品份额:', fontproperties=font_introduce, bbox={'facecolor': 'yellow', 'alpha': 0.0}, verticalalignment='center', horizontalalignment='center')

            ax2.text(0.80, 0.11, f'{int(share)}', fontproperties=font_introduce, bbox={'facecolor': 'yellow', 'alpha': 0.0}, verticalalignment='center', horizontalalignment='left')

            end_day = per_account_dataframe.loc[len(per_account_dataframe) - 1, TQZAutoReportPerAccountDataColumnType.DATE.value].to_pydatetime()
            ax2.text(0.00, 0.73, f'{end_day.year}-{end_day.month}-{end_day.day}', fontproperties=font_introduce, bbox={'facecolor': 'yellow', 'alpha': 0.0}, verticalalignment='center', horizontalalignment='left')
            ax2.text(0.12, 0.73, f'{str(account_id)}', fontproperties=font_introduce, bbox={'facecolor': 'yellow', 'alpha': 0.0}, verticalalignment='center', horizontalalignment='left')

            plt.savefig(f"{TQZAutoReportFilePath.today_images_fold()}/{account_id}.png")
            plt.close("all")

    @classmethod
    def __update_total_data_excel(cls):
        """
        Update total data excel
        """

        # source data of all accounts
        account_id_account_dataframe_dictionary = cls.__init_account_id_account_dataframe_dictionary()

        # create new total_balance_following dataframe | balance_fluctuation_singleDay_dataframe | profit_and_loss_total_dataframe
        total_balance_following_dataframe = cls.__init_total_balance_following_dataframe(account_id_account_dataframe_dictionary=account_id_account_dataframe_dictionary)
        balance_fluctuation_singleDay_dataframe = cls.__init_balance_fluctuation_singleDay_dataframe(account_id_account_dataframe_dictionary=account_id_account_dataframe_dictionary)
        profit_and_loss_total_dataframe = cls.__init_profit_and_loss_total_dataframe(account_id_account_dataframe_dictionary=account_id_account_dataframe_dictionary)

        # all accounts by sort in date
        ACCOUNT_ABBR = "账户缩写"
        date_sort_dataframe = pandas.DataFrame(columns=[TQZAutoReportPerAccountDataColumnType.DATE.value, TQZAutoReportSourceDataColumnType.ACCOUNT_ID.value, ACCOUNT_ABBR])
        for account_id, per_account_dataframe in account_id_account_dataframe_dictionary.items():
            new_column = len(date_sort_dataframe)
            date_sort_dataframe.loc[new_column, TQZAutoReportPerAccountDataColumnType.DATE.value] = per_account_dataframe.iloc[0][TQZAutoReportPerAccountDataColumnType.DATE.value]
            date_sort_dataframe.loc[new_column, TQZAutoReportSourceDataColumnType.ACCOUNT_ID.value] = account_id
            date_sort_dataframe.loc[new_column, ACCOUNT_ABBR] = cls.__get_account_image_title(account_id=account_id)

        date_sort_dataframe.sort_values(TQZAutoReportPerAccountDataColumnType.DATE.value, inplace=True)
        account_id_list = date_sort_dataframe[TQZAutoReportSourceDataColumnType.ACCOUNT_ID.value].values.tolist()
        account_name_list = date_sort_dataframe[ACCOUNT_ABBR].values.tolist()

        # add new account_name columns to total_balance_following_dataframe
        for account_id in account_id_list:
            per_account_dataframe = account_id_account_dataframe_dictionary[account_id]
            per_account_dataframe.set_index(TQZAutoReportPerAccountDataColumnType.DATE.value, inplace=True)

            balance_fluctuation_singleDay_dataframe = pandas.merge(
                left=balance_fluctuation_singleDay_dataframe,
                right=per_account_dataframe[TQZAutoReportPerAccountDataColumnType.BALANCE_FLUCTUATION_SINGLE_DAY.value],
                left_index=True,
                right_index=True,
                how='left'
            )

            profit_and_loss_total_dataframe = pandas.merge(
                left=profit_and_loss_total_dataframe,
                right=per_account_dataframe[TQZAutoReportPerAccountDataColumnType.RESULT_PROFIT_AND_LOSS.value],
                left_index=True,
                right_index=True,
                how='left'
            )

            total_balance_following_dataframe.loc[:, cls.__get_account_image_title(account_id=account_id)] = per_account_dataframe[TQZAutoReportPerAccountDataColumnType.BALANCE.value]


        # add TOTAL_BALANCE | PRIFIT_AND_LOSS_TODAY | PROFIT_AND_LOSS_TODAY_PERCENT | PROFIT_AND_LOSS_TOTAL | PROFIT_AND_LOSS_TOTAL_HISTORY to total_balance_following_dataframe
        total_balance_following_dataframe[TQZAutoReportTotalBalanceFollowingColumnType.TOTAL_BALANCE.value] = round(total_balance_following_dataframe[account_name_list].sum(axis=1), 0)

        total_balance_following_dataframe[TQZAutoReportTotalBalanceFollowingColumnType.PROFIT_AND_LOSS_TODAY.value] = round(balance_fluctuation_singleDay_dataframe[:].sum(axis=1), 0)

        total_balance_following_dataframe[TQZAutoReportTotalBalanceFollowingColumnType.PROFIT_AND_LOSS_TODAY_PERCENT.value] = round((total_balance_following_dataframe[TQZAutoReportTotalBalanceFollowingColumnType.PROFIT_AND_LOSS_TODAY.value] / total_balance_following_dataframe[TQZAutoReportTotalBalanceFollowingColumnType.TOTAL_BALANCE.value]) * 100, 3)
        total_balance_following_dataframe[TQZAutoReportTotalBalanceFollowingColumnType.PROFIT_AND_LOSS_TODAY_PERCENT.value] = total_balance_following_dataframe[TQZAutoReportTotalBalanceFollowingColumnType.PROFIT_AND_LOSS_TODAY_PERCENT.value].astype(str) + "%"

        total_balance_following_dataframe[TQZAutoReportTotalBalanceFollowingColumnType.PROFIT_AND_LOSS_TOTAL.value] = round(profit_and_loss_total_dataframe[:].sum(axis=1), 0)

        profit_and_loss_total_dataframe.fillna(method="ffill", inplace=True)  # 缺失值的数据由上一行的数据来补齐
        total_balance_following_dataframe[TQZAutoReportTotalBalanceFollowingColumnType.PROFIT_AND_LOSS_TOTAL_HISTORY.value] = round(profit_and_loss_total_dataframe[:].sum(axis=1), 0)

        # delete hour|minute|second when write to excel
        total_balance_following_dataframe[TQZAutoReportTotalBalanceFollowingColumnType.DATE_ACCOUNT.value] = total_balance_following_dataframe[TQZAutoReportTotalBalanceFollowingColumnType.DATE_ACCOUNT.value].dt.date
        cls.__to_excel(
            dataframe=total_balance_following_dataframe,
            excel_path=TQZAutoReportFilePath.total_data_fold() + f'/total_data({TQZAutoReportFilePath.today_string()}).xlsx',
            sheet_name=TQZAutoReportSheetType.BALANCE_TOTLE_FOLLOWING.value,
            freeze_panes=(1, 1),
            empty_others=True
        )

    @classmethod
    def __update_weekly_pdfs(cls, begin_weekday):
        """
        Update weekly pdfs of current running accounts.
        """

        for file_name in os.listdir(TQZAutoReportFilePath.weekly_pdfs_fold()):
            os.remove(path=TQZAutoReportFilePath.weekly_pdfs_fold() + f'/{file_name}')

        current_running_account_list = cls.__current_source_data_dataframe()[
            TQZAutoReportSourceDataColumnType.ACCOUNT_ID.value
        ].values.tolist()

        for file_name in os.listdir(TQZAutoReportFilePath.per_account_data_fold()):
            all_path = TQZAutoReportFilePath.per_account_data_fold() + f'/{file_name}'

            per_account_dataframe = pandas.read_excel(
                io=all_path,
                sheet_name=TQZAutoReportSheetType.PER_ACCOUNT_DATA.value
            )

            per_account_dataframe = per_account_dataframe.loc[per_account_dataframe[TQZAutoReportPerAccountDataColumnType.DATE.value].dt.dayofweek == begin_weekday, :]
            per_account_dataframe.reset_index(inplace=True)

            if len(per_account_dataframe) < 2:
                continue

            account_id = file_name.split(".")[0]

            if account_id not in current_running_account_list:
                print(f'{account_id} not in current_running_account_list')
                continue

            font_type_pdf_weekly = 'KaiTi'

            plt.rcParams['font.sans-serif'] = [font_type_pdf_weekly]  # 用来正常显示中文标签
            plt.rcParams['axes.unicode_minus'] = False  # 用来正常显示负号
            plt.style.use('seaborn-darkgrid')
            my_dpi = 96
            plt.figure(figsize=(8, 8), dpi=my_dpi)
            grid = plt.GridSpec(7, 6, wspace=2, hspace=2)
            ax1 = plt.subplot(grid[3:7, 0:10], frameon=True)
            plt.grid(axis='x')

            if len(per_account_dataframe) <= 8:
                plt.ylim(0.80, 1.2)
                ax1.xaxis.set_major_formatter(mdate.DateFormatter('%Y-%m-%d'))

                plt.xticks(pandas.date_range(per_account_dataframe.loc[0, TQZAutoReportPerAccountDataColumnType.DATE.value], per_account_dataframe.loc[len(per_account_dataframe) - 1, TQZAutoReportPerAccountDataColumnType.DATE.value], freq='W-FRI'))
                continue

            plt.subplots_adjust(left=0.05, bottom=0.0, right=0.95, top=1, hspace=0.1, wspace=0.1)

            plt.plot(
                per_account_dataframe[TQZAutoReportPerAccountDataColumnType.DATE.value],
                per_account_dataframe[TQZAutoReportPerAccountDataColumnType.NET_VALUE.value],
                marker='',
                color="red",
                linewidth=2.5,
                alpha=0.6
            )

            for tick in ax1.get_xticklabels():
                tick.set_rotation(30)

            ax2 = plt.subplot(grid[0:3, 0:10], frameon=False)
            ax2.grid(False)
            plt.subplots_adjust(left=0.05, bottom=0.1, right=0.95, top=1, hspace=0.1, wspace=0.1)
            plt.gca().get_xaxis().set_visible(False)
            plt.gca().get_yaxis().set_visible(False)

            font_title = fm.FontProperties(family=font_type_pdf_weekly, size=18, stretch=0, weight='black')
            font_data = fm.FontProperties(family=font_type_pdf_weekly, size=25, stretch=0)
            font_dataNote = fm.FontProperties(family=font_type_pdf_weekly, size=10, stretch=0, weight='black')
            font_netValue = fm.FontProperties(family=font_type_pdf_weekly, size=40, stretch=1, weight='medium')
            font_introduce = fm.FontProperties(family=font_type_pdf_weekly, size=10, stretch=0, weight='black')

            plt.rcParams['axes.unicode_minus'] = False  # 用来正常显示负号

            max_dropDown_singleDay = round(
                per_account_dataframe[TQZAutoReportPerAccountDataColumnType.NET_VALUE_FLUCTUATION_SINGLE_DAY.value].min() * 100,
                3
            )
            sharpe_ratio = round(
                per_account_dataframe.loc[len(per_account_dataframe) - 1, TQZAutoReportPerAccountDataColumnType.SHARPE_RATIO.value],
                2
            )
            max_dropDown_top = round(
                per_account_dataframe[TQZAutoReportPerAccountDataColumnType.MAX_DRAWDOWN.value].max() * (-1) * 100,
                2
            )
            net_value = per_account_dataframe.loc[
                len(per_account_dataframe) - 1, TQZAutoReportPerAccountDataColumnType.NET_VALUE.value
            ]
            yield_rate_annualized = round(per_account_dataframe.loc[
                len(per_account_dataframe) - 1,
                TQZAutoReportPerAccountDataColumnType.YIELD_RATE_ANNUALIZED.value
            ] * 100, 3)
            share = per_account_dataframe.loc[
                len(per_account_dataframe) - 1,
                TQZAutoReportPerAccountDataColumnType.SHARE.value
            ]

            ax2.text(0, 0.8, f'翡熙CTA组合净值报告(周度)',
                     fontproperties=font_title, bbox={'facecolor': 'red', 'alpha': 0.1}, verticalalignment='bottom',
                     horizontalalignment='left')
            ax2.text(0.11, 0.45, f'{round(per_account_dataframe[TQZAutoReportPerAccountDataColumnType.NET_VALUE.value].max(), 4)}', fontproperties=font_data,
                     bbox={'facecolor': 'yellow', 'alpha': 0.0}, verticalalignment='center',
                     horizontalalignment='center')

            ax2.text(0.11, 0.35, r'净值峰值 (周度)', fontproperties=font_dataNote, bbox={'facecolor': 'yellow', 'alpha': 0.0},
                     verticalalignment='center', horizontalalignment='center')
            ax2.text(0.11, 0.00, f'{max_dropDown_top}%', fontproperties=font_data, bbox={'facecolor': 'yellow', 'alpha': 0.0}, verticalalignment='center', horizontalalignment='center')
            ax2.text(0.11, -0.10, r'最大高点回撤', fontproperties=font_dataNote, bbox={'facecolor': 'yellow', 'alpha': 0.0}, verticalalignment='center', horizontalalignment='center')

            ax2.text(0.35, 0.45, f'8%-15%', fontproperties=font_data, bbox={'facecolor': 'yellow', 'alpha': 0.0}, verticalalignment='center', horizontalalignment='center')
            ax2.text(0.35, 0.35, r'保证金利用率', fontproperties=font_dataNote, bbox={'facecolor': 'yellow', 'alpha': 0.0},
                     verticalalignment='center', horizontalalignment='center')
            ax2.text(0.35, 0.00, f'{max_dropDown_singleDay}%', fontproperties=font_data,
                     bbox={'facecolor': 'yellow', 'alpha': 0.0}, verticalalignment='center',
                     horizontalalignment='center')
            ax2.text(0.35, -0.10, r'最大单周回撤', fontproperties=font_dataNote, bbox={'facecolor': 'yellow', 'alpha': 0.0},
                     verticalalignment='center', horizontalalignment='center')

            ax2.text(0.55, 0.45, f'{sharpe_ratio}', fontproperties=font_data,
                     bbox={'facecolor': 'yellow', 'alpha': 0.0}, verticalalignment='center',
                     horizontalalignment='center')
            ax2.text(0.55, 0.35, r'夏普比率', fontproperties=font_dataNote, bbox={'facecolor': 'yellow', 'alpha': 0.0},
                     verticalalignment='center', horizontalalignment='center')
            ax2.text(0.57, 0.00, f'{round(yield_rate_annualized/abs(max_dropDown_top), 2)}', fontproperties=font_data,
                     bbox={'facecolor': 'yellow', 'alpha': 0.0}, verticalalignment='center',
                     horizontalalignment='center')
            ax2.text(0.57, -0.10, r'收益风险比', fontproperties=font_dataNote, bbox={'facecolor': 'yellow', 'alpha': 0.0},
                     verticalalignment='center', horizontalalignment='center')

            ax2.text(0.80, 0.80, f'{round(net_value, 4)}', fontproperties=font_netValue,
                     bbox={'facecolor': 'yellow', 'alpha': 0.0}, verticalalignment='center',
                     horizontalalignment='center')
            ax2.text(0.81, 0.68, r'当前净值 (周度)', fontproperties=font_dataNote, bbox={'facecolor': 'yellow', 'alpha': 0.0},
                     verticalalignment='center', horizontalalignment='center')

            ax2.text(0.81, 0.55, f'{yield_rate_annualized}%', fontproperties=font_data,
                     bbox={'facecolor': 'yellow', 'alpha': 0.0}, verticalalignment='center',
                     horizontalalignment='center')
            ax2.text(0.81, 0.45, r'年化收益率', fontproperties=font_dataNote, bbox={'facecolor': 'yellow', 'alpha': 0.0},
                     verticalalignment='center', horizontalalignment='center')

            ax2.text(0.73, 0.35, r'*产品说明', fontproperties=font_introduce, bbox={'facecolor': 'yellow', 'alpha': 0.0},
                     verticalalignment='center', horizontalalignment='center')
            ax2.text(0.74, 0.27, r'投资范围:', fontproperties=font_introduce, bbox={'facecolor': 'yellow', 'alpha': 0.0},
                     verticalalignment='center', horizontalalignment='center')
            ax2.text(0.80, 0.27, r'股指、国债、商品期货', fontproperties=font_introduce,
                     bbox={'facecolor': 'yellow', 'alpha': 0.0}, verticalalignment='center', horizontalalignment='left')
            ax2.text(0.74, 0.19, r'起始日期:', fontproperties=font_introduce, bbox={'facecolor': 'yellow', 'alpha': 0.0},
                     verticalalignment='center', horizontalalignment='center')

            start_day = per_account_dataframe.loc[0, TQZAutoReportPerAccountDataColumnType.DATE.value].to_pydatetime()
            ax2.text(0.80, 0.19, f'{start_day.year}-{start_day.month}-{start_day.day}', fontproperties=font_introduce,
                     bbox={'facecolor': 'yellow', 'alpha': 0.0}, verticalalignment='center', horizontalalignment='left')
            ax2.text(0.74, 0.11, r'产品份额:', fontproperties=font_introduce, bbox={'facecolor': 'yellow', 'alpha': 0.0},
                     verticalalignment='center', horizontalalignment='center')

            ax2.text(0.80, 0.11, f'{int(share)}', fontproperties=font_introduce,
                     bbox={'facecolor': 'yellow', 'alpha': 0.0}, verticalalignment='center', horizontalalignment='left')

            end_day = per_account_dataframe.loc[
                len(per_account_dataframe) - 1, TQZAutoReportPerAccountDataColumnType.DATE.value
            ].to_pydatetime()
            ax2.text(0.00, 0.73, f'{end_day.year}-{end_day.month}-{end_day.day}', fontproperties=font_introduce, bbox={'facecolor': 'yellow', 'alpha': 0.0}, verticalalignment='center', horizontalalignment='left')
            ax2.text(0.12, 0.73, f'{str(account_id)}', fontproperties=font_introduce, bbox={'facecolor': 'yellow', 'alpha': 0.0}, verticalalignment='center', horizontalalignment='left')

            plt.savefig(f'{TQZAutoReportFilePath.weekly_pdfs_fold()}/翡熙CTA周净值报告_{TQZAutoReportFilePath.today_string()}({cls.__get_account_image_title(account_id=account_id)}).pdf')
            plt.close("all")

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值