Skip to content

Commit 2c0e30a

Browse files
authored
Add quarto-stock-report-python content (#59)
* Add quarto-stock-report-python content * Address PR review * Update version for release
1 parent 4dddbe0 commit 2c0e30a

File tree

8 files changed

+242
-0
lines changed

8 files changed

+242
-0
lines changed

.github/workflows/extensions.yml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -31,6 +31,7 @@ jobs:
3131
filters: |
3232
reaper: extensions/reaper/**
3333
integration-session-manager: extensions/integration-session-manager/**
34+
quarto-stock-report-python: extensions/quarto-stock-report-python/**
3435
portfolio-dashboard: extensions/portfolio-dashboard/**
3536
3637
# Runs for each extension that has changed from `simple-extension-changes`
Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
/.quarto/
2+
*.csv
3+
index.html
4+
index_files
5+
index.ipynb
6+
/env/
7+
.output_metadata.json
8+
/email-preview/
9+
/index.quarto_ipynb
Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
# Quarto Stock Report using Python
2+
3+
## About this example
4+
5+
This stock report is generated using Quarto and Python. It is an example
6+
of how you might automate regular updates using a data source. The report
7+
also generates a custom email, sharing the results directly to
8+
stakeholders.
9+
10+
11+
## Learn more
12+
13+
* [Quarto](https://quarto.org)
14+
15+
## Requirements
16+
17+
* Quarto version 1.4 or higher
18+
* Python version 3.9 or higher
Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,2 @@
1+
project:
2+
title: Stock Report
Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
---
2+
title: Quarto Stock Report using Python
3+
categories:
4+
- python
5+
- quarto
6+
---
7+
8+
This stock report is generated using Quarto and Python. It is an example of how you might automate regular updates using a data source. The report also generates a custom email, sharing the results directly to stakeholders.
Lines changed: 137 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,137 @@
1+
---
2+
title: Stock Report
3+
date: today
4+
date-format: long
5+
published-title: produced
6+
jupyter: python3
7+
format: email
8+
attachments:
9+
- data.csv
10+
email-preview: true
11+
---
12+
13+
## Report for TSLA
14+
15+
```{python}
16+
#| echo: true
17+
18+
import pandas as pd
19+
import yfinance as yf
20+
import datetime
21+
22+
tsla = yf.Ticker("TSLA")
23+
hist = tsla.history("5y")
24+
25+
hist['Change'] = hist['Close'] - hist['Open']
26+
27+
latest = hist.last_valid_index()
28+
days_90 = latest - pd.to_timedelta("90d")
29+
30+
prices_1d = hist[latest:]
31+
prices_90d = hist[days_90:]
32+
prices_rolling = hist.asfreq('D').rolling(window=52*7, min_periods=1)
33+
34+
data=[
35+
[
36+
prices_1d['High'].values[0],
37+
prices_1d['Low'].values[0],
38+
prices_1d['Volume'].values[0].round(),
39+
],
40+
[
41+
prices_rolling.max()[latest:]['High'].values[0],
42+
prices_rolling.min()[latest:]['Low'].values[0],
43+
prices_rolling.mean()[latest:]['Volume'].values[0].round(),
44+
]
45+
]
46+
47+
df = pd.DataFrame(
48+
data,
49+
columns=['High', 'Low', 'Avg Volume'],
50+
index=['Most Recent Trading Day', '52-Week'])
51+
df
52+
```
53+
54+
### Price History
55+
56+
```{python}
57+
#| echo: false
58+
#| label: fig-history
59+
#| fig-cap: "TSLA price history"
60+
61+
_ = hist['Close'].plot(grid=True)
62+
```
63+
64+
## Raw Data
65+
66+
```{python}
67+
#| echo: false
68+
69+
hist
70+
```
71+
72+
## Legacy Information
73+
74+
This report also produces a CSV file containing recent price data, which may
75+
be used in other analysis.
76+
77+
```{python}
78+
#| echo: false
79+
#| include: false
80+
81+
prices_90d.to_csv("data.csv")
82+
```
83+
84+
[Link to CSV](data.csv)
85+
86+
## Email
87+
88+
This report also produces an email that is sent to key stakeholders with summary
89+
information.
90+
91+
::: {.email}
92+
93+
::: {.subject}
94+
```{python}
95+
#| echo: false
96+
#| output: asis
97+
98+
closes = prices_90d['Close']
99+
change = closes[-2] - closes[-1]
100+
abschange = abs(change)
101+
updown = "up"
102+
if change < 0:
103+
updown = "down"
104+
print(f"TSLA is {updown} today by ${abschange:.2f}")
105+
```
106+
:::
107+
108+
Hello Team,
109+
110+
```{python}
111+
#| echo: false
112+
#| output: asis
113+
114+
print(f"Here are the latest stock prices for **TSLA** as of {datetime.date.today()}:")
115+
```
116+
117+
```{python}
118+
#| echo: false
119+
120+
prices_90d.head(5)[['Open', 'Close', 'Change', 'Volume']]
121+
```
122+
123+
The historical trend is shown below:
124+
125+
```{python}
126+
#| echo: false
127+
128+
_ = prices_90d['Close'].plot(grid=True)
129+
```
130+
131+
Let me know if you have any questions.
132+
133+
Best,
134+
135+
Team Lead
136+
137+
:::
Lines changed: 56 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,56 @@
1+
{
2+
"version": 1,
3+
"locale": "en_US.UTF-8",
4+
"metadata": {
5+
"appmode": "quarto-static"
6+
},
7+
"extension": {
8+
"name": "quarto-stock-report-python",
9+
"title": "Quarto Stock Report using Python",
10+
"description": "An example of how you might automate regular updates using a data source",
11+
"homepage": "https://github.com/posit-dev/connect-extensions/tree/main/extensions/quarto-stock-report-python",
12+
"version": "1.0.0"
13+
},
14+
"environment": {
15+
"python": {
16+
"requires": ">=3.9, <4"
17+
}
18+
},
19+
"quarto": {
20+
"version": "1.6.42",
21+
"engines": [
22+
"jupyter"
23+
]
24+
},
25+
"python": {
26+
"version": "3.11.7",
27+
"package_manager": {
28+
"name": "pip",
29+
"version": "24.2",
30+
"package_file": "requirements.txt"
31+
}
32+
},
33+
"files": {
34+
"requirements.txt": {
35+
"checksum": "1b9e705f62a822cffaa4dc0e988101b4"
36+
},
37+
".gitignore": {
38+
"checksum": "ae206a13f5875901e752811238e8fdbd"
39+
},
40+
"README.md": {
41+
"checksum": "837f74720c4532629d02fd4bff3df83b"
42+
},
43+
"_quarto.yml": {
44+
"checksum": "35b4c4c58cce875b126683c525ad40f4"
45+
},
46+
"index.qmd": {
47+
"checksum": "6fb0db80d26eab1544afdcbc91df228b"
48+
},
49+
"index.quarto_ipynb": {
50+
"checksum": "04ad8e09510236db1b397038a4c06186"
51+
},
52+
"thumbnail.jpg": {
53+
"checksum": "8db36358d1e9dbab78f8ffef39846eee"
54+
}
55+
}
56+
}
Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
# jupyter
2+
notebook==7.2.2
3+
qtconsole==5.5.1
4+
jupyter-console==6.6.3
5+
nbconvert==7.16.1
6+
ipykernel==6.29.3
7+
ipywidgets==8.1.2
8+
9+
matplotlib==3.8.3
10+
pandas==2.2.1
11+
yfinance==0.2.54

0 commit comments

Comments
 (0)