diff --git a/.github/workflows/ci.yaml b/.github/workflows/ci.yaml index 73181b3..84f3118 100644 --- a/.github/workflows/ci.yaml +++ b/.github/workflows/ci.yaml @@ -9,10 +9,10 @@ jobs: runs-on: ubuntu-latest steps: - uses: actions/checkout@v3 - - name: Set up Python 3.8 + - name: Set up Python 3.11 uses: actions/setup-python@v3 with: - python-version: 3.8 + python-version: 3.11 - name: Install dependencies run: | python -m pip install --upgrade pip diff --git a/README.md b/README.md index fb207ac..0761e71 100644 --- a/README.md +++ b/README.md @@ -1,3 +1,12 @@ # ML pipelines Simple ML pipeline repo for experimenting with CI/CD / DevOps / MLOps. + +## To do + +- Use Python 3.11 in CI github action +- make pipelines functions +- add loggers to stuff +- add db conn / func to save inference cases +- add deployment code... +- add versioning to training... in deployment? diff --git a/ml_pipelines/logic/serve/serve.py b/ml_pipelines/logic/serve/serve.py index 58fe643..2fc798f 100644 --- a/ml_pipelines/logic/serve/serve.py +++ b/ml_pipelines/logic/serve/serve.py @@ -1,5 +1,51 @@ -def validate_sample(sample: dict): - x1_upper_bound = 5 - if sample["X1"] > x1_upper_bound: - return False - return True +import pandas as pd +from fastapi import FastAPI, HTTPException +from pydantic import BaseModel, Field +from sklearn.linear_model import LogisticRegression + +from ml_pipelines.logic.common.feature_eng import ( + FeatureEngineeringParams, + transform_features, +) +from ml_pipelines.logic.common.model import predict + + +class Point(BaseModel): + prediction_id: str + x1: float = Field(..., description="Value of x1, must be smaller than 5", lt=5) + x2: float + + +def create_fastapi_app( + model: LogisticRegression, feature_eng_params: FeatureEngineeringParams +): + app = FastAPI() + + @app.get("/predict/") + async def _(inputs: Point | list[Point]): + """ + Endpoint to predict probabilities for the given list of points. + :param points: List of points (x1, x2) (or single point) + :return: List of probability predictions (or single prediction) + """ + try: + single = False + if isinstance(inputs, Point): + single = True + inputs = [inputs] + # Convert the input points to a numpy array + x_matrix = pd.DataFrame([{"X1": p.x1, "X2": p.x2} for p in inputs]) + x_matrix = transform_features(x_matrix, feature_eng_params) + + # Make predictions using the pre-trained model + predictions = predict(model, x_matrix).tolist() + + if single: + predictions = predictions[0] + + return {"predictions": predictions} + + except Exception: + raise HTTPException(status_code=500, detail="Internal server error") + + return app