Skip to content

Commit

Permalink
Allow inline usage of st.chat_input (streamlit#7896)
Browse files Browse the repository at this point in the history
* Add initial version of inline chat input

* Adapt python test

* Fix tests

* Fix tests

* Fix tests

* Fix tests

* Remove unused import

* Remove e2e tests

* Fix test id names

* Improve playwright conftest

* Format conftest

* Update tests

* Fix unembedded iframe

* Update snapshots

* Add e2e test script

* Add e2e tests

* Add updated snapshots

* Finalize test

* Revert toast change

* Fixes and improvements

* Add missing snapshots

* Update snapshots

* Fix observer effect

* Fix flickering effects

* Fix typo

* Fix comments

* Fix test

* Remove position parameter from API

* Update example

* Fix unit tests
  • Loading branch information
lukasmasuch authored Jan 22, 2024
1 parent de8dae4 commit fd38b18
Show file tree
Hide file tree
Showing 78 changed files with 614 additions and 427 deletions.
17 changes: 0 additions & 17 deletions e2e/scripts/embedded_chat_input_app.py

This file was deleted.

17 changes: 0 additions & 17 deletions e2e/scripts/st_chat_input.py

This file was deleted.

43 changes: 0 additions & 43 deletions e2e/specs/embedded_chat_input_app.js

This file was deleted.

76 changes: 0 additions & 76 deletions e2e/specs/st_chat_input.spec.js

This file was deleted.

4 changes: 2 additions & 2 deletions e2e/specs/st_toast.spec.js
Original file line number Diff line number Diff line change
Expand Up @@ -69,7 +69,7 @@ describe("st.toast", () => {
});

it(`overlays toasts with st.chat_input - ${theme}`, () => {
cy.get(".stChatFloatingInputContainer").matchImageSnapshot(`toast+chatInput-${theme}`)
cy.get("[data-testid='stBottomBlockContainer']").matchImageSnapshot(`toast+chatInput-${theme}`)
});
})
});
});
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
22 changes: 16 additions & 6 deletions e2e_playwright/conftest.py
Original file line number Diff line number Diff line change
Expand Up @@ -212,18 +212,28 @@ def wait_for_app_run(page: Page, wait_delay: int = 100):
page.wait_for_timeout(wait_delay)


def wait_for_app_loaded(page: Page):
def wait_for_app_loaded(page: Page, embedded: bool = False):
"""Wait for the app to fully load."""
# Wait for the app view container to appear:
page.wait_for_selector(
"[data-testid='stAppViewContainer']", timeout=30000, state="attached"
)
# Wait for the main app container to appear:
page.wait_for_selector(
"[data-testid='block-container']", timeout=20000, state="attached"
)

# Wait for the main menu to appear:
page.wait_for_selector("#MainMenu", timeout=20000, state="attached")
if not embedded:
page.wait_for_selector(
"[data-testid='stMainMenu']", timeout=20000, state="attached"
)

wait_for_app_run(page)


def rerun_app(page: Page):
"""Triggers an app rerun and waits for the run to be finished."""
# Click somewhere to clear the focus from elements:
page.get_by_test_id("stApp").click(position={"x": 0, "y": 0})
# Press "r" to rerun the app:
page.keyboard.press("r")
wait_for_app_run(page)


Expand Down
37 changes: 37 additions & 0 deletions e2e_playwright/st_chat_input.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,37 @@
# Copyright (c) Streamlit Inc. (2018-2022) Snowflake Inc. (2022-2024)
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.

import streamlit as st
from streamlit import runtime

v1 = st.container().chat_input("Chat input 1 (inline)")
st.write("Chat input 1 (inline) - value:", v1)

col1, _ = st.columns(2)

v2 = col1.chat_input("Chat input 2 (in column, disabled)", disabled=True)
st.write("Chat input 2 (in column, disabled) - value:", v2)

if runtime.exists():

def on_submit():
st.text("chat input submitted")

st.container().chat_input(
"Chat input 3 (callback)", key="chat_input_3", on_submit=on_submit
)
st.write("Chat input 3 (callback) - value:", st.session_state.get("chat_input_3"))

v4 = st.chat_input("Chat input 4 (bottom, max_chars)", max_chars=200)
st.write("Chat input 4 (bottom, max_chars) - value:", v4)
4 changes: 2 additions & 2 deletions e2e_playwright/st_chat_input_file_uploader_regression_test.py
Original file line number Diff line number Diff line change
Expand Up @@ -19,8 +19,8 @@

def test_regression_with_file_uploader_and_chat_input(app: Page):
"""Test issue described in https://github.com/streamlit/streamlit/issues/7556."""
chat_input_element = app.get_by_test_id("stChatInput").first
chat_input_element.fill("Hello world!")
chat_input_element = app.get_by_test_id("stChatInputTextArea").first
chat_input_element.type("Hello world!")
chat_input_element.press("Enter")
wait_for_app_run(app)
last_chat_message = app.get_by_test_id("stChatMessageContent").last
Expand Down
Loading

0 comments on commit fd38b18

Please sign in to comment.