Repository: truera/trulens
Issue: [BUG] import error after clean install
Root cause: External Dependency Breakage

**Bug Description**
What happened?

I get an import error with a truelens clean install trying to run the quickstart in the documentation. 


**To Reproduce**
Which steps should someone take to run into the same error? A small, reproducible code example is useful here.

I''ve created a new venv.:
```
python3 -m venv rag_venv
source rag_venv/bin/activate
pip install trulens_eval chromadb openai
```

and simply run the quick start documentation here: https://www.trulens.org/trulens_eval/getting_started/quickstarts/quickstart/

```
university_info = """
The University of Washington, founded in 1861 in Seattle, is a public research university
with over 45,000 students across three campuses in Seattle, Tacoma, and Bothell.
As the flagship institution of the six public universities in Washington state,
UW encompasses over 500 buildings and 20 million square feet of space,
including one of the largest library systems in the world.
"""

import os
from openai import OpenAI
oai_client = OpenAI()

oai_client.embeddings.create(
        model="text-embedding-ada-002",
        input=university_info
    )

import chromadb
from chromadb.utils.embedding_functions import OpenAIEmbeddingFunction

embedding_function = OpenAIEmbeddingFunction(api_key=os.environ.get('OPENAI_API_KEY'),
                                             model_name="text-embedding-ada-002")


chroma_client = chromadb.Client()
vector_store = chroma_client.get_or_create_collection(name="Universities",
                                                      embedding_function=embedding_function)

vector_store.add("uni_info", documents=university_info)


from trulens_eval import Tru
from trulens_eval.tru_custom_app import instrument
tru = Tru()


class RAG_from_scratch:
    @instrument
    def retrieve(self, query: str) -> list:
        """
        Retrieve relevant text from vector store.
        """
        results = vector_store.query(
        query_texts=query,
        n_results=2
    )
        return results['documents'][0]

    @instrument
    def generate_completion(self, query: str, context_str: list) -> str:
        """
        Generate answer from context.
        """
        completion = oai_client.chat.completions.create(
        model="gpt-3.5-turbo",
        temperature=0,
        messages=
        [
            {"role": "user",
            "content": 
            f"We have provided context information below. \n"
            f"---------------------\n"
            f"{context_str}"
            f"\n---------------------\n"
            f"Given this information, please answer the question: {query}"
            }
        ]
        ).choices[0].message.content
        return completion

    @instrument
    def query(self, query: str) -> str:
        context_str = self.retrieve(query)
        completion = self.generate_completion(query, context_str)
        return completion

rag = RAG_from_scratch()


from trulens_eval import Feedback, Select
from trulens_eval.feedback import Groundedness
from trulens_eval.feedback.provider.openai import OpenAI

import numpy as np

provider = OpenAI()

grounded = Groundedness(groundedness_provider=provider)

# Define a groundedness feedback function
f_groundedness = (
    Feedback(grounded.groundedness_measure_with_cot_reasons, name = "Groundedness")
    .on(Select.RecordCalls.retrieve.rets.collect())
    .on_output()
    .aggregate(grounded.grounded_statements_aggregator)
)

# Question/answer relevance between overall question and answer.
f_answer_relevance = (
    Feedback(provider.relevance_with_cot_reasons, name = "Answer Relevance")
    .on(Select.RecordCalls.retrieve.args.query)
    .on_output()
)

# Question/statement relevance between question and each context chunk.
f_context_relevance = (
    Feedback(provider.context_relevance_with_cot_reasons, name = "Context Relevance")
    .on(Select.RecordCalls.retrieve.args.query)
    .on(Select.RecordCalls.retrieve.rets.collect())
    .aggregate(np.mean)
)


from trulens_eval import TruCustomApp
tru_rag = TruCustomApp(rag,
    app_id = 'RAG v1',
    feedbacks = [f_groundedness])

with tru_rag as recording:
    rag.query("When was the University of Washington founded?")


tru.get_leaderboard(app_ids=["RAG v1"])

tru.run_dashboard()
```


**Expected behavior**
A clear and concise description of what you expected to happen.

**Relevant Logs/Tracebacks**
Please copy and paste any relevant log output. This will be automatically formatted into code, so no need for backticks. If the issue is related to the TruLens dashboard, please also include a screenshot.

```
python quickstart.py
🦑 Tru initialized with db url sqlite:///default.sqlite .
🛑 Secret keys may be written to the database. See the `database_redact_keys` option of Tru` to prevent this.
[nltk_data] Downloading package punkt to
[nltk_data]     /Users/Petros.Syntelis/nltk_data...
[nltk_data]   Package punkt is already up-to-date!
✅ In Groundedness, input source will be set to __record__.app.retrieve.rets.collect() .
✅ In Groundedness, input statement will be set to __record__.main_output or `Select.RecordOutput` .
✅ In Answer Relevance, input prompt will be set to __record__.app.retrieve.args.query .
✅ In Answer Relevance, input response will be set to __record__.main_output or `Select.RecordOutput` .
✅ In Context Relevance, input question will be set to __record__.app.retrieve.args.query .
✅ In Context Relevance, input context will be set to __record__.app.retrieve.rets.collect() .
Traceback (most recent call last):
  File "quickstart.py", line 115, in <module>
    tru_rag = TruCustomApp(rag,
  File "/Users/*****/test_truelens/rag_venv/lib/python3.8/site-packages/trulens_eval/tru_custom_app.py", line 394, in __init__
    super().__init__(**kwargs)
  File "/Users/*****/test_truelens/rag_venv/lib/python3.8/site-packages/trulens_eval/app.py", line 548, in __init__
    super().__init__(**kwargs)
  File "/Users/*****/test_truelens/rag_venv/lib/python3.8/site-packages/trulens_eval/schema.py", line 919, in __init__
    super().__init__(**kwargs)
  File "/Users/*****/test_truelens/rag_venv/lib/python3.8/site-packages/trulens_eval/utils/pyschema.py", line 686, in __init__
    super().__init__(*args, **kwargs)
  File "/Users/*****/test_truelens/rag_venv/lib/python3.8/site-packages/pydantic/main.py", line 171, in __init__
    self.__pydantic_validator__.validate_python(data, self_instance=self)
pydantic_core._pydantic_core.ValidationError: 1 validation error for TruCustomApp
records_with_pending_feedback_results
  Input should be an instance of Queue [type=is_instance_of, input_value=<queue.Queue object at 0x16b4af940>, input_type=Queue]
    For further information visit https://errors.pydantic.dev/2.6/v/is_instance_of
```

**Environment:**
 - OS: MacOS
 - Python Version: 3.8.13
 - TruLens version: 0.27.2
 - Versions of other relevant installed libraries

**Additional context**
Add any other context about the problem here.


<!-- Answer -->
Based on the error message you provided, it seems like the `TruCustomApp` class is expecting an instance of `Queue` for the `records_with_pending_feedback_results` parameter, but it's receiving something else. This is causing the `pydantic_core._pydantic_core.ValidationError`.

The `TruCustomApp` class is part of the TruLens library and is used for instrumenting any custom Python class. It uses the Pydantic library for data validation and settings management, which is where the `ValidationError` is coming from. Pydantic uses Python type annotations to validate the data passed to it and will raise a `ValidationError` if the data does not conform to the expected format or types.

Unfortunately, without the exact line of code causing the error, it's hard to pinpoint the exact issue. However, here are a few things you could try:

1. **Check the Data Passed to `TruCustomApp`**: Make sure that the data you're passing to `TruCustomApp` matches the expected types and structures. In particular, check the `records_with_pending_feedback_results` parameter. It should be an instance of `Queue`.

2. **Update Your Packages**: Ensure that you have the latest versions of `trulens_eval`, `chromadb`, `openai`, and `pydantic`. You can update them using pip:

   ```bash
   pip install --upgrade trulens_eval chromadb openai pydantic
   ```

3. **Install `llama-index`**: Based on a similar issue found in the TruLens repository, installing the `llama-index` package might help. You can install it using pip:

   ```bash
   pip install llama-index==0.9.21
   ```

If none of these suggestions work, could you provide the exact line of code causing the error? This would help in diagnosing the issue further.

## Sources
- [[BUG] pydantic_core._pydantic_core.ValidationError: 1 validation error for TruCustomApp](https://github.com/truera/trulens/issues/998)
- [Example google collab cell has a error when running](https://github.com/truera/trulens/issues/707)
- [trulens_eval/examples/quickstart/existing_data_quickstart.ipynb](https://github.com/truera/trulens/blob/main/trulens_eval/examples/quickstart/existing_data_quickstart.ipynb)
- [trulens_eval/trulens_eval/tru_custom_app.py](https://github.com/truera/trulens/blob/main/trulens_eval/trulens_eval/tru_custom_app.py)

<!-- Dosu Comment Footer -->
<details>
<summary>

#### About Dosu
</summary>

This response is meant to be useful and save you time. It is **not meant to be a precise solution**, but rather a starting point for your own research.

Help me be more useful! Please leave a 👍 if this is helpful and 👎 if it is irrelevant.

If you want to continue the conversation, start your reply with @dosu-bot.
</details>


Hey! I spent a bit more time on this. It seems to be related to the python version. I didn't get this error for python 3.9.17.

Thanks for the update @psyntelis ! We'll take a closer look at this on python 3.8

Hi @psyntelis,

This issue specifically impacts Python versions earlier than 3.9. 
The fix for this will be included in the next release.

Hey @psyntelis - fix for this is released in 0.28.0!

Please upgrade your trulens-eval version `pip install -U trulens-eval`