File size: 6,110 Bytes
cc9a95f
d934e05
cc9a95f
88be29a
 
d934e05
7c479ac
59df961
cc9a95f
 
 
88be29a
 
 
 
 
 
 
 
 
57b94ca
88be29a
 
 
 
57b94ca
88be29a
57b94ca
 
 
 
 
88be29a
57b94ca
7c479ac
 
57b94ca
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
88be29a
 
cc9a95f
 
88be29a
cc9a95f
 
 
 
 
 
 
 
 
 
 
 
 
 
2db4636
06b78a1
cc46ec6
cc9a95f
 
 
 
 
 
 
 
 
 
 
 
 
7c479ac
 
 
 
cc9a95f
 
 
 
 
7c479ac
 
cc9a95f
 
 
 
1262b99
cc9a95f
aff284c
cc9a95f
 
 
 
 
 
 
d934e05
 
326698c
cc9a95f
 
 
 
 
 
 
 
 
 
 
 
 
88be29a
 
cc9a95f
 
 
88be29a
 
cc9a95f
 
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
import pandas as pd
import streamlit as st

from time import time

from src.st_helpers import st_setup
from src.data_synthesis.test_question_generator import generate_question
from src.common import img_dir, escape_dollars, generate_group_tag
from src.architectures import *


def show_side_by_side() -> None:
    """
    Streamlit render a prompt and the boxes to show each architecture
    :return:
    """
    # Build the layout structure
    st.divider()
    header_container = st.container()
    arch_outer_container = st.container()


    # Build header
    with header_container:
        st.write("### Side by side comparison of architectures")
        st.write('Enter a question below to have it sent to the selected architectures to compare timing and response.')

        options = [a.name for a in Architecture.architectures]
        selected_archs = st.multiselect("Select architectures to use", options=options, default=options)

        if len(selected_archs) == 0:
            st.write("To get started select some architectures to compare")
        else:
            prompt = st.chat_input("Ask a question")
            if st.button("Or press to ask a random question"):
                prompt = generate_question()
            if prompt:
                st.write(f"**Question:** {prompt}")

    # Now build the columns
    if len(selected_archs) > 0:
        with arch_outer_container:
            arch_cols = st.columns(len(selected_archs))
            if prompt:
                # Build columns per architecture
                for i, a in enumerate(selected_archs):
                    with arch_cols[i]:
                        st.write(f'#### {a}')

                # Now dispatch the messages per architecture
                group_tag = generate_group_tag()
                for i, a in enumerate(selected_archs):
                    request = ArchitectureRequest(query=prompt)
                    arch = Architecture.get_architecture(a)
                    with arch_cols[i]:
                        with st.spinner('Architecture processing request'):
                            start = time()
                            arch(request, trace_tags=["UI", "SideBySideCompare", group_tag])
                            elapsed_in_s = (int((time() - start) * 10))/10  # round to 1dp in seconds
                            st.write('##### Timing')
                            st.write(f'Request took **{elapsed_in_s}s**')
                            st.write('##### Response')
                            st.write(request.response)
            else:
                # Build columns per architecture for display only
                for i, a in enumerate(selected_archs):
                    with arch_cols[i]:
                        st.write(f'#### {a}')


def show_architecture(architecture: str) -> None:
    """
    Streamlit render an architecture details and the
    ability to interact with the architecture
    :param architecture: the name of the architecture to output
    """
    arch = Architecture.get_architecture(architecture)

    # Segment into two containers for organisation
    arch_container = st.container()
    chat_container = st.container()

    with arch_container:
        st.divider()
        st.write(f'### {arch.name}')
        st.write('#### Architecture description')
        st.write(arch.description)
        if arch.img is not None:
            img = os.path.join(img_dir, arch.img)
            st.image(img, caption=f'{arch.name} As Built', width=1000)
        table_data = []
        for j, s in enumerate(arch.steps, start=1):
            table_data.append(
                [j, s.__class__.__name__, s.description, s.config_description()]
            )
        table_cols = ['Step', 'Name', 'Description', 'Config details']
        st.write('#### Architecture pipeline steps')
        st.table(pd.DataFrame(table_data, columns=table_cols))

    with chat_container:
        st.write(f"### Chat with {arch.name}")
        st.write("Note this is a simple single query through the relevant architecture. This is just a sample so you can interact with it and does not manage a chat session history.")

        prompt = st.chat_input("Ask a question")
        if st.button("Or press to ask a random question"):
            prompt = generate_question()

        chat_col, trace_col, request_col = st.columns([3, 2, 2])

        with chat_col:
            with st.chat_message("assistant"):
                st.write("Chat with me in the box below")

        if prompt:
            with chat_col:
                with st.chat_message("user"):
                    st.write(prompt)
                request = ArchitectureRequest(query=prompt)
                trace = arch(request, trace_tags=["UI", "SingleArchTest"])
                with st.chat_message("assistant"):
                    st.write(escape_dollars(request.response))
                with trace_col:
                    st.write("#### Architecture Trace")
                    st.markdown(trace.as_markdown())
                with request_col:
                    st.write("#### Full Request/Response")
                    st.markdown(request.as_markdown())


if st_setup('LLM Arch'):
    st.write("# LLM Architectures")
    Architecture.load_architectures()

    # Display the available architectures
    arch_count = len(Architecture.architectures)
    if arch_count == 1:
        st.write('### 1 Architecture available')
    else:
        st.write(f'### {arch_count} Architectures available')

    if st.button("Force reload of architecture configs"):
        Architecture.load_architectures(force_reload=True)

    arch_names = [a.name for a in Architecture.architectures]
    compare = 'Side by side comparison'
    arch_names.append(compare)
    selected_arch = st.radio(label="Available architectures", label_visibility="hidden", options=arch_names, index=None)
    if selected_arch is None:
        st.info('Select an architecture from above to see details and interact with it')
    elif selected_arch == compare:
        show_side_by_side()
    else:
        show_architecture(selected_arch)