From 1a021321a9b55ea42de6447a5e119f71263a4c9e Mon Sep 17 00:00:00 2001 From: Gabriel Luiz Freitas Almeida Date: Fri, 12 Apr 2024 16:39:22 -0300 Subject: [PATCH] Update Dockerfiles, main.py, constants.py, and package versions (#1691) * Update Dockerfiles to include user creation and use --user flag for pip install * Add JavaScriptMIMETypeMiddleware to main.py * Update constants.py and run.py files * Update package versions in poetry.lock and pyproject.toml files * Refactor Dockerfile to optimize image building process * Fix import error in main.py * Update Dockerfiles to use logspace/langflow image --- base.Dockerfile | 6 +- deploy/base.Dockerfile | 92 ------------------- deploy/docker-compose.yml | 11 +-- poetry.lock | 14 +-- pyproject.toml | 2 +- ..._replace_credential_table_with_variable.py | 1 + .../79e675cb6752_change_datetime_type.py | 2 +- src/backend/base/langflow/base/constants.py | 1 + src/backend/base/langflow/interface/run.py | 4 - src/backend/base/langflow/main.py | 12 ++- src/backend/base/poetry.lock | 6 +- src/backend/base/pyproject.toml | 2 +- tests/conftest.py | 1 - 13 files changed, 31 insertions(+), 123 deletions(-) delete mode 100644 deploy/base.Dockerfile diff --git a/base.Dockerfile b/base.Dockerfile index 3946af99d..2325ece79 100644 --- a/base.Dockerfile +++ b/base.Dockerfile @@ -63,8 +63,10 @@ RUN --mount=type=cache,target=/root/.cache \ # copy project requirement files here to ensure they will be cached. WORKDIR $PYSETUP_PATH +# Copy just one file to avoid rebuilding the whole image COPY poetry.lock pyproject.toml ./ -COPY ./src/backend/langflow/main.py ./src/backend/langflow/main.py +COPY ./src/backend/langflow ./src/backend/langflow +COPY ./src/backend/base/pyproject.toml ./src/backend/base/pyproject.toml # Copy README.md to the build context COPY README.md . # install runtime deps - uses $POETRY_VIRTUALENVS_IN_PROJECT internally @@ -84,7 +86,7 @@ COPY --from=builder-base $POETRY_HOME $POETRY_HOME COPY --from=builder-base $PYSETUP_PATH $PYSETUP_PATH # Copy just one file to avoid rebuilding the whole image -COPY ./src/backend/langflow/__init__.py ./src/backend/langflow/__init__.py +COPY ./src/backend/langflow ./src/backend/langflow # quicker install as runtime deps are already installed RUN --mount=type=cache,target=/root/.cache \ poetry install --with=dev --extras deploy diff --git a/deploy/base.Dockerfile b/deploy/base.Dockerfile deleted file mode 100644 index 84b448e2d..000000000 --- a/deploy/base.Dockerfile +++ /dev/null @@ -1,92 +0,0 @@ - - -# syntax=docker/dockerfile:1 -# Keep this syntax directive! It's used to enable Docker BuildKit - -# Based on https://github.com/python-poetry/poetry/discussions/1879?sort=top#discussioncomment-216865 -# but I try to keep it updated (see history) - -################################ -# PYTHON-BASE -# Sets up all our shared environment variables -################################ -FROM python:3.10-slim as python-base - -# python -ENV PYTHONUNBUFFERED=1 \ - # prevents python creating .pyc files - PYTHONDONTWRITEBYTECODE=1 \ - \ - # pip - PIP_DISABLE_PIP_VERSION_CHECK=on \ - PIP_DEFAULT_TIMEOUT=100 \ - \ - # poetry - # https://python-poetry.org/docs/configuration/#using-environment-variables - POETRY_VERSION=1.8.2 \ - # make poetry install to this location - POETRY_HOME="/opt/poetry" \ - # make poetry create the virtual environment in the project's root - # it gets named `.venv` - POETRY_VIRTUALENVS_IN_PROJECT=true \ - # do not ask any interactive question - POETRY_NO_INTERACTION=1 \ - \ - # paths - # this is where our requirements + virtual environment will live - PYSETUP_PATH="/opt/pysetup" \ - VENV_PATH="/opt/pysetup/.venv" - - -# prepend poetry and venv to path -ENV PATH="$POETRY_HOME/bin:$VENV_PATH/bin:$PATH" - - -################################ -# BUILDER-BASE -# Used to build deps + create our virtual environment -################################ -FROM python-base as builder-base -RUN apt-get update \ - && apt-get install --no-install-recommends -y \ - # deps for installing poetry - curl \ - # deps for building python deps - build-essential - -# install poetry - respects $POETRY_VERSION & $POETRY_HOME -# The --mount will mount the buildx cache directory to where -# Poetry and Pip store their cache so that they can reuse it -RUN --mount=type=cache,target=/root/.cache \ - curl -sSL https://install.python-poetry.org | python3 - - -# copy project requirement files here to ensure they will be cached. -WORKDIR $PYSETUP_PATH -COPY ./poetry.lock ./pyproject.toml ./ -# Copy README.md to the build context -COPY ./README.md ./ -# install runtime deps - uses $POETRY_VIRTUALENVS_IN_PROJECT internally -RUN --mount=type=cache,target=/root/.cache \ - poetry install --without dev --extras deploy - - -################################ -# DEVELOPMENT -# Image used during development / testing -################################ -FROM python-base as development -WORKDIR $PYSETUP_PATH - -# copy in our built poetry + venv -COPY --from=builder-base $POETRY_HOME $POETRY_HOME -COPY --from=builder-base $PYSETUP_PATH $PYSETUP_PATH - -# Copy just one file to avoid rebuilding the whole image -COPY ./src/backend/langflow/__init__.py ./src/backend/langflow/__init__.py -# quicker install as runtime deps are already installed -RUN --mount=type=cache,target=/root/.cache \ - poetry install --with=dev --extras deploy - -# copy in our app code -COPY ./src/backend ./src/backend -COPY ./tests ./tests diff --git a/deploy/docker-compose.yml b/deploy/docker-compose.yml index 201f9bc97..c47871bf6 100644 --- a/deploy/docker-compose.yml +++ b/deploy/docker-compose.yml @@ -69,10 +69,7 @@ services: - traefik.http.routers.${STACK_NAME?Variable not set}-proxy-http.middlewares=${STACK_NAME?Variable not set}-www-redirect,${STACK_NAME?Variable not set}-https-redirect backend: &backend - image: "ogabrielluiz/langflow:latest" - build: - context: ../ - dockerfile: base.Dockerfile + image: "logspace/langflow:latest" depends_on: - db - broker @@ -143,9 +140,6 @@ services: <<: *backend env_file: - .env - build: - context: ../ - dockerfile: base.Dockerfile command: celery -A langflow.worker.celery_app worker --loglevel=INFO --concurrency=1 -n lf-worker@%h -P eventlet healthcheck: test: "exit 0" @@ -158,9 +152,6 @@ services: - .env networks: - default - build: - context: ../ - dockerfile: base.Dockerfile environment: - FLOWER_PORT=5555 diff --git a/poetry.lock b/poetry.lock index f2645e589..6f9b0809f 100644 --- a/poetry.lock +++ b/poetry.lock @@ -3866,7 +3866,7 @@ six = "*" [[package]] name = "langflow-base" -version = "0.0.31" +version = "0.0.32" description = "A Python package with a built-in web application" optional = false python-versions = ">=3.10,<3.12" @@ -3943,13 +3943,13 @@ openai = ["openai (>=0.27.8)"] [[package]] name = "langsmith" -version = "0.1.45" +version = "0.1.46" description = "Client library to connect to the LangSmith LLM Tracing and Evaluation Platform." optional = false python-versions = "<4.0,>=3.8.1" files = [ - {file = "langsmith-0.1.45-py3-none-any.whl", hash = "sha256:5a5b7fafe767fa28826c925f175875c09bf5368bfdb141286381a94bf737e6ef"}, - {file = "langsmith-0.1.45.tar.gz", hash = "sha256:713206107df636db1edf30867d64b92495afb1f09d2fee0857a77b7a8ee083d5"}, + {file = "langsmith-0.1.46-py3-none-any.whl", hash = "sha256:459b76b25fe3b86e7bf5521f4dc8c3f796de288ceb3e0d05c99db4d509edaabf"}, + {file = "langsmith-0.1.46.tar.gz", hash = "sha256:a5a96259e411641633561575b567c2139bede997f7104eeedb59cb9511416d1b"}, ] [package.dependencies] @@ -8288,13 +8288,13 @@ transformers = ">=4.32.0,<5.0.0" [[package]] name = "setuptools" -version = "69.3.0" +version = "69.4.0" description = "Easily download, build, install, upgrade, and uninstall Python packages" optional = false python-versions = ">=3.8" files = [ - {file = "setuptools-69.3.0-py3-none-any.whl", hash = "sha256:48c518e350470d98cfa2944a31edbfc897c9a7d8fa4847da66d89f0f5fb64b57"}, - {file = "setuptools-69.3.tar.gz", hash = "sha256:e1fd0ca7ba442e4be8a415dcca867b8018777dd5f95f4492bb4dc7d77dbc8bd8"}, + {file = "setuptools-69.4.0-py3-none-any.whl", hash = "sha256:b6df12d754b505e4ca283c61582d5578db83ae2f56a979b3bc9a8754705ae3bf"}, + {file = "setuptools-69.4.tar.gz", hash = "sha256:659e902e587e77fab8212358f5b03977b5f0d18d4724310d4a093929fee4ca1a"}, ] [package.extras] diff --git a/pyproject.toml b/pyproject.toml index 7faad73ff..7f4147057 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -1,6 +1,6 @@ [tool.poetry] name = "langflow" -version = "1.0.0a19" +version = "1.0.0a20" description = "A Python package with a built-in web application" authors = ["Logspace "] maintainers = [ diff --git a/src/backend/base/langflow/alembic/versions/1a110b568907_replace_credential_table_with_variable.py b/src/backend/base/langflow/alembic/versions/1a110b568907_replace_credential_table_with_variable.py index e27d088d0..48d12ac30 100644 --- a/src/backend/base/langflow/alembic/versions/1a110b568907_replace_credential_table_with_variable.py +++ b/src/backend/base/langflow/alembic/versions/1a110b568907_replace_credential_table_with_variable.py @@ -5,6 +5,7 @@ Revises: 63b9c451fd30 Create Date: 2024-03-25 09:40:02.743453 """ + from typing import Sequence, Union import sqlalchemy as sa diff --git a/src/backend/base/langflow/alembic/versions/79e675cb6752_change_datetime_type.py b/src/backend/base/langflow/alembic/versions/79e675cb6752_change_datetime_type.py index c2fc1c425..c6e4e633f 100644 --- a/src/backend/base/langflow/alembic/versions/79e675cb6752_change_datetime_type.py +++ b/src/backend/base/langflow/alembic/versions/79e675cb6752_change_datetime_type.py @@ -5,7 +5,7 @@ Revises: e3bc869fa272 Create Date: 2024-04-11 19:23:10.697335 """ -from calendar import c + from typing import Sequence, Union import sqlalchemy as sa diff --git a/src/backend/base/langflow/base/constants.py b/src/backend/base/langflow/base/constants.py index c9a41a100..498b46f65 100644 --- a/src/backend/base/langflow/base/constants.py +++ b/src/backend/base/langflow/base/constants.py @@ -6,6 +6,7 @@ Constants: - NODE_FORMAT_ATTRIBUTES: A list of attributes used for formatting nodes. - FIELD_FORMAT_ATTRIBUTES: A list of attributes used for formatting fields. """ + STREAM_INFO_TEXT = "Stream the response from the model. Streaming works only in Chat." NODE_FORMAT_ATTRIBUTES = ["beta", "icon", "display_name", "description"] diff --git a/src/backend/base/langflow/interface/run.py b/src/backend/base/langflow/interface/run.py index 2327b8725..283c752e8 100644 --- a/src/backend/base/langflow/interface/run.py +++ b/src/backend/base/langflow/interface/run.py @@ -1,9 +1,5 @@ -from typing import Dict, Tuple - from loguru import logger -from langflow.graph import Graph - def get_memory_key(langchain_object): """ diff --git a/src/backend/base/langflow/main.py b/src/backend/base/langflow/main.py index e71c2d81e..8893e60b0 100644 --- a/src/backend/base/langflow/main.py +++ b/src/backend/base/langflow/main.py @@ -11,6 +11,7 @@ from fastapi.responses import FileResponse from fastapi.staticfiles import StaticFiles from loguru import logger from rich import print as rprint +from starlette.middleware.base import BaseHTTPMiddleware from langflow.api import router from langflow.initial_setup.setup import create_or_update_starter_projects @@ -20,8 +21,16 @@ from langflow.services.utils import initialize_services, teardown_services from langflow.utils.logger import configure +class JavaScriptMIMETypeMiddleware(BaseHTTPMiddleware): + async def dispatch(self, request: Request, call_next): + response = await call_next(request) + if "files/" not in request.url.path and request.url.path.endswith(".js") and response.status_code == 200: + response.headers["Content-Type"] = "text/javascript" + return response + + def get_lifespan(fix_migration=False, socketio_server=None): - from langflow.version import __version__ + from langflow.version import __version__ # type: ignore @asynccontextmanager async def lifespan(app: FastAPI): @@ -62,6 +71,7 @@ def create_app(): allow_methods=["*"], allow_headers=["*"], ) + app.add_middleware(JavaScriptMIMETypeMiddleware) @app.middleware("http") async def flatten_query_string_lists(request: Request, call_next): diff --git a/src/backend/base/poetry.lock b/src/backend/base/poetry.lock index 6f5cfa785..96852ea9d 100644 --- a/src/backend/base/poetry.lock +++ b/src/backend/base/poetry.lock @@ -1146,13 +1146,13 @@ extended-testing = ["lxml (>=5.1.0,<6.0.0)"] [[package]] name = "langsmith" -version = "0.1.45" +version = "0.1.46" description = "Client library to connect to the LangSmith LLM Tracing and Evaluation Platform." optional = false python-versions = "<4.0,>=3.8.1" files = [ - {file = "langsmith-0.1.45-py3-none-any.whl", hash = "sha256:5a5b7fafe767fa28826c925f175875c09bf5368bfdb141286381a94bf737e6ef"}, - {file = "langsmith-0.1.45.tar.gz", hash = "sha256:713206107df636db1edf30867d64b92495afb1f09d2fee0857a77b7a8ee083d5"}, + {file = "langsmith-0.1.46-py3-none-any.whl", hash = "sha256:459b76b25fe3b86e7bf5521f4dc8c3f796de288ceb3e0d05c99db4d509edaabf"}, + {file = "langsmith-0.1.46.tar.gz", hash = "sha256:a5a96259e411641633561575b567c2139bede997f7104eeedb59cb9511416d1b"}, ] [package.dependencies] diff --git a/src/backend/base/pyproject.toml b/src/backend/base/pyproject.toml index 1a58f1e53..5421914c8 100644 --- a/src/backend/base/pyproject.toml +++ b/src/backend/base/pyproject.toml @@ -1,6 +1,6 @@ [tool.poetry] name = "langflow-base" -version = "0.0.31" +version = "0.0.32" description = "A Python package with a built-in web application" authors = ["Logspace "] maintainers = [ diff --git a/tests/conftest.py b/tests/conftest.py index 03cefb686..e3faa3ba5 100644 --- a/tests/conftest.py +++ b/tests/conftest.py @@ -19,7 +19,6 @@ from langflow.services.database.models.flow.model import Flow, FlowCreate from langflow.services.database.models.user.model import User, UserCreate from langflow.services.database.utils import session_getter from langflow.services.deps import get_db_service -from sqlmodel import Session, SQLModel, create_engine, select from sqlmodel.pool import StaticPool from typer.testing import CliRunner