📊

Hugging Face Spacesで、購買データ分析アプリをつくる(前編)

2024/06/02に公開

目的

さらに、Hugging Face Spacesで別のStreamlitアプリを構築したいと思います。

【前々回】https://zenn.dev/paxdare_labo/articles/0ae79951afed45
【前回】https://zenn.dev/paxdare_labo/articles/48626a0f26d5b1

構築するもの

これまでのStreamlitアプリは、裏でAIモデルを動かすことを重視していましたが、今回はグラフを出力するようにしたいと思います。

さらに、購買データ分析 の内容を踏まえて、購買データを読み込み・分析・グラフ化するアプリケーションをStreamlitで作ってみます。

Hugging Face Spacesの使い方は、上記記事を御覧ください

アウトプットイメージ

今回構築したのは、次のようなアプリケーションです。

初期画面

ここで、左のメニューから分析条件を選択します。例えば、「時系列分析」を選び、国は「United KingdomとAutralia」、日付は初期値の通り「2010/1/1〜2010/12/31」とします。

すると、次のようなグラフが出力されます。
時系列分析のグラフ

ちなみに、データは2010/12/1〜のみの存在のため、それ以前のグラフは出力されません。
さらに、画面をスクロールすると、実際のデータを確認することができます。
また、「Press to Download」でCSV形式でファイルをダウンロードすることも可能です。

時系列分析のテーブル

利用するデータ

データは、購買データ分析 と同様に、Kaggleコンペの「Retail Sales Dataset」のデータを用いています。

メニューコード

次のコードは「app.py」という名称で作成しています。

まずはライブラリをインポートします。
そして、上記のKaggleデータをPandas形式で読み込ませています。

import streamlit as st
import pandas as pd
import datetime

# Kaggleのデータを読み込み
df = pd.read_csv("data/online_retail.csv")

# データ型整備:ID項目のSTRING化など
df = df.astype({'CustomerID': 'object'})
df = df[df["UnitPrice"] * df["Quantity"] > 0]

country_list = df["Country"].unique()

st.set_page_config(
    page_title="購買データ分析App", 
    layout="wide", 
)

左側のメニュー部分は、Streamlitの機能を使うことで、非常に簡単につくることができます。
次のようなコードでメニューを構築しています。

with st.sidebar.form(key="my_form"):
    analysis_menu = st.selectbox("分析メニュー", ["ABC分析", "バスケット分析","時系列分析"])

    country = st.multiselect("国を選択してください。", country_list)
    if len(country) != 0:
        country = "','".join(country)
        country = f"Country in ('{country}')"
    else:
        country = "True"

    st.write("2010年の日付を入れてください。")
    start_date = st.date_input("開始日", datetime.date(2010, 1, 1))
    end_date = st.date_input("終了日", datetime.date(2010, 12, 31))

    submit_button = st.form_submit_button(label = "分析開始")
  • selectboxは、シングルセレクトの選択メニューです。ここにメニュー名と、選択値のリスト値を渡すことで、

  • multiselectは、マルチセレクトの選択メニューです。country_listは、最初のコードでPandas DataframeからCountryの一覧を抽出したリストです。
     このcountryが1件以上選択された場合に、"Country in ('{country}')"といったSTRING型を返します。これは、後ほどの分析SQLで用いるので、ここまでは、このままご理解ください。

  • date_inputでは、日付を入れています。「st.date_input("開始日", datetime.date(2010, 1, 1))」とすることで、初期日付を「2010-01-01」になるようにしています。(データの都合上、かなり過去日になっています)

  • 最後に、form_submit_buttonで、分析実行をするためのボタンを「submit_button」という名前で配置しています。

この「submit_button」が押下されたときの処理を、次のプログラムで定義しています。
ここは「with st.sidebar.form」の外なので、左のメニューではなく、右側のメインウインドウに表示されます。

if submit_button:
    import create_object as co
    import duckdb

     # 処理を実行
    sql = co.create_sql(analysis_menu, country, start_date, end_date)
    df_output = duckdb.query(sql).to_df()

    try:
        fig = co.create_graph(analysis_menu, df_output)
        st.plotly_chart(fig)
    except:
        print("グラフ無し")

    st.table(df_output.head(100))
    st.write("上位100行まで、全体を見たい場合はCSVでダウンロードしてください。")

    st.download_button(
    "Press to Download",
    df_output.to_csv(index=False).encode('utf-8'),
    "file.csv",
    "text/csv",
    key='download-csv'
    )

ここでいきなり、create_objectという独自ライブラリを呼び出しています。
このライブラリについては、次回説明します。

また、duckdbというライブラリも使っています。
これは、こちら の記事でも挙げていますが、Pandas Dataframeを元データとしてSQLを実行できる便利ライブラリです。

今回の分析は、SQLで実装しているため、こちらのライブラリを用いています。

分析した結果が「df_output」というデータで出力されますが、これをst.tableで出力しています。

さらに、st.download_buttonを用いることで、「df_output」の内容をCSV形式でダウンロードできるようにしています。

ここまでのまとめ

ここまでで、アプリとしての枠の部分は作成できています。
このあと、「create_object.py」というファイルに、SQLでの分析や、グラフ出力を実装しています。

そちらについては、次回ご説明していきます。

Discussion