Skip to main content

MarkoWizard

A modern Python library for Markowitz portfolio optimization and analysis.

PyPI Python 3.10+ License: MIT

Previously known as Diversificador. The original portfolio-analysis web app built with Dash is no longer maintained, but it is preserved on the dash-deprecated branch for reference.

Features

  • Markowitz Mean-Variance Optimization — Compute the efficient frontier using scipy.optimize
  • Capital Allocation Line — Mix risky portfolios with risk-free assets
  • Visualization — Plotly-based charts for efficient frontier, allocation pie, CAL, correlation heatmaps, and price timelines
  • Data Fetching — Built-in helpers for downloading market data via yfinance
  • Web Application — FastAPI backend with a dark-themed interactive frontend

Installation

pip install markowizard

That's everything the library needs: optimization (scipy), market-data fetching (yfinance), and visualization (plotly). No optional extras.

Quick Start (Library)

from markowizard import MarkowitzOptimizer, CapitalAllocator
from markowizard.data import fetch_prices, compute_monthly_returns
from markowizard.visualization import efficiency_frontier_plot

# Fetch prices and compute monthly returns (decimal form, e.g. 0.01 = 1%)...
prices = fetch_prices(["AAPL", "MSFT", "GOOGL", "SPY"], period="5y")
returns = compute_monthly_returns(prices)
# ...or bring your own returns DataFrame (assets as columns).

# Optimize
optimizer = MarkowitzOptimizer(returns)
portfolios = optimizer.optimize()

# Compute Sharpe ratios (provide monthly risk-free rate)
risk_free_rate = 0.005  # 0.5% per month
portfolios = optimizer.compute_sharpe(risk_free_rate)

# Plot the efficient frontier
fig = efficiency_frontier_plot(portfolios, highlight_portfolio=50)
fig.show()

# Best portfolio (maximum Sharpe ratio)
best = optimizer.max_sharpe_portfolio()
print(best)

# Capital allocation line
allocator = CapitalAllocator(best, risk_free_rate)
cal_points = allocator.capital_allocation_line(steps=21)

Web Application

An interactive web UI (FastAPI + a dark-themed frontend) lives in backend/ and frontend/. It is not part of the PyPI package — run it from the container image or a clone.

Using Docker

docker run -p 8000:8000 ghcr.io/outliersanalytics/markowizard:latest

From a clone

git clone https://github.com/OutliersAnalytics/MarkoWizard
cd MarkoWizard
uv run --with-requirements backend/requirements.txt uvicorn backend.main:app --port 8000

Open http://localhost:8000 — the app auto-submits with default tickers on load.

It exposes a single endpoint, POST /api/analyze:

{
  "tickers": ["AAPL", "MSFT", "GOOGL", "SPY"],
  "period": "5y",
  "risk_free_rate": 0.005
}

which returns the efficient frontier, max-Sharpe portfolio, capital-allocation-line points, and correlation matrix as JSON. The frontend renders the charts.

API Reference

markowizard (top-level)

Export Description
MarkowitzOptimizer Efficient frontier optimization (from core)
CapitalAllocator Risk-free asset allocation (from allocation)
__version__ Package version string

markowizard.core

MarkowitzOptimizer

class MarkowitzOptimizer:
    def __init__(self, returns: pd.DataFrame) -> None
    def optimize(self) -> pd.DataFrame
    def compute_sharpe(self, risk_free_rate: float) -> pd.DataFrame
    def max_sharpe_portfolio(self) -> pd.Series

Constants: COL_RETURN = "Expected Return", COL_RISK = "Risk", COL_SHARPE = "Sharpe", COL_RISK_FREE = "Risk-Free"

Parameters:

  • returns: DataFrame where each column is an asset and each row is a time period. Values must be in decimal form (e.g., 0.01 = 1%).

optimize() computes the efficient frontier by solving 100 quadratic programming problems with varying risk-aversion parameters. Uses warm-starting: each iteration's solution seeds the next.

compute_sharpe(risk_free_rate) adds a Sharpe column. risk_free_rate must match the period of returns (e.g., monthly).

max_sharpe_portfolio() returns the tangency portfolio row.

MarkowitzOptimizer.portfolios DataFrame columns

Column Description
(ticker columns) Asset weights (sum to 1, all >= 0)
Expected Return Expected portfolio return
Risk Portfolio standard deviation (risk)
Sharpe Sharpe ratio (after compute_sharpe())

markowizard.allocation

CapitalAllocator

class CapitalAllocator:
    def __init__(self, portfolio: pd.Series | Mapping, risk_free_rate: float) -> None
    @staticmethod
    def weigh_risk_free(value: float, risk_free_value: float, p: float) -> float
    def capital_allocation_line(self, steps: int = 21) -> list[dict]
    def final_allocation(self, p: float) -> dict[str, float]
    def expected_returns(self, p: float) -> tuple[float, float]

capital_allocation_line() returns points along the CAL, each with keys p, expected_return, risk, and label.

final_allocation(p) returns asset weights including Risk-Free (risk-free portion).

markowizard.visualization

Function Returns Description
efficiency_frontier_plot(portfolios, highlight_portfolio=0) Figure Scatter plot of expected return vs risk
allocation_pie(portfolio) Figure Pie chart of asset weights
capital_allocation_line_plot(cal_points, highlight_point=0) Figure CAL risk-return trade-off
correlation_timeline(prices, ticker_a, ticker_b=None) Figure Price history (single or normalized dual)
correlation_heatmap(corr_matrix) Figure Correlation matrix heatmap

All visualization functions return Plotly Figure objects — call .show() to display.

markowizard.data

Function Returns Description
fetch_prices(tickers, period="5y", auto_adjust=True) pd.DataFrame Historical close prices from Yahoo Finance
compute_monthly_returns(prices) pd.DataFrame Monthly returns from daily close prices

Modules

Module Description
core MarkowitzOptimizer — efficient frontier optimization
allocation CapitalAllocator — risk-free asset allocation
visualization Plotly chart functions (efficient frontier, pie, CAL, correlation)
data Market-data fetching and monthly-return helpers (yfinance)

The web application (backend/, frontend/) is kept in the repo but is not part of the installable package — see Web Application.

Development

See CONTRIBUTING.md for setup instructions and contribution guidelines.

License

MIT

Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

markowizard-0.2.0.tar.gz (17.0 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

markowizard-0.2.0-py3-none-any.whl (13.4 kB view details)

Uploaded Python 3

File details

Details for the file markowizard-0.2.0.tar.gz.

File metadata

  • Download URL: markowizard-0.2.0.tar.gz
  • Upload date:
  • Size: 17.0 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/7.0.0 CPython/3.13.14

File hashes

Hashes for markowizard-0.2.0.tar.gz
Algorithm Hash digest
SHA256 bbf1cd28135f9e6d3ca2f9a9b9d6cb2257055e89f1c27ced181529bab5b91184
MD5 80fe285fd55a759cf5ff21a603c6d499
BLAKE2b-256 485f45e116c15f7fad8156e5ff24a63fa3ba6d5662ae7138b954c25d70ec4227

See more details on using hashes here.

Provenance

The following attestation bundles were made for markowizard-0.2.0.tar.gz:

Publisher: python-publish.yml on OutliersAnalytics/MarkoWizard

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file markowizard-0.2.0-py3-none-any.whl.

File metadata

  • Download URL: markowizard-0.2.0-py3-none-any.whl
  • Upload date:
  • Size: 13.4 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/7.0.0 CPython/3.13.14

File hashes

Hashes for markowizard-0.2.0-py3-none-any.whl
Algorithm Hash digest
SHA256 1771a633bd617107a4a9024458629d71553a3f233f11c799155241bd62b753b7
MD5 676302e5ccce6b6141b48919c2df9db9
BLAKE2b-256 9511a56f268c619db7b457a35e3b04de392fbd975fdf1d3d40878174af33e7d6

See more details on using hashes here.

Provenance

The following attestation bundles were made for markowizard-0.2.0-py3-none-any.whl:

Publisher: python-publish.yml on OutliersAnalytics/MarkoWizard

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

Release history Release notifications | RSS feed

This release

0.2.0 This release

2 files

0.1.0

2 files

Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page