AI Engineer Summit 2023

Pydantic is all you need

Jason Liu17:55

Read the talk

Structured LLM Outputs With Pydantic: From Fragile JSON to Programmable Systems

Selected presentation frame from Pydantic is all you need: Jason Liu at 354 seconds
Structured LLM Outputs With Pydantic: From Fragile JSON to Programmable Systems

Jason Liu explains how Pydantic models, OpenAI function calling, Instructor, and explicit validation turn language-model outputs into typed objects that existing software can inspect, execute, and maintain.

From a talk by Jason Liu

At a glance

Ideas worth remembering

  • Use Pydantic models to express the output contract in typed, reviewable code and generate the JSON schema needed for OpenAI function calling. 3:04

  • Treat Instructor as the model-to-object integration layer described in the talk, while recognizing its stated limitation to OpenAI function calling and Liu’s suggestion of Marvin for broader model support. 4:59

  • Keep field descriptions, docstrings, validation rules, and object behavior together so the prompt and application contract evolve as one reviewable unit. 5:57

  • Handle invalid or uncertain outputs with explicit validators, bounded retries, optional results, and structured errors instead of relying on sentinel phrases or unverified prompt compliance. 7:51

  • Represent retrieval requests and query plans as executable data structures so conventional code can select backends, apply filters, schedule parallel work, and resolve dependencies. 11:41

  • Ground generated answers by requiring supporting excerpts to exist in the source text, while recognizing that substring verification confirms textual presence rather than complete interpretive correctness. 14:36

The real integration problem is not chat—it is structured data

Selected presentation frame from Pydantic is all you need: Jason Liu at 174 seconds
The real integration problem is not chat—it is structured data

Jason Liu frames the central production problem as connecting language models to software that already expects specific schemas, APIs, and data structures. Although many developers encountered these models through chat interfaces, the systems they build often need to process inputs and produce structured outputs compatible with interfaces they cannot change. In that setting, asking a model for JSON and hoping the result can be parsed is not a reliable programming model. 0:14

Even when an answer resembles valid JSON, subtle contract violations can remain invisible until downstream code fails: one response might use a user field while another uses username, or the model might surround its payload with conversational text. Liu argues that these errors should surface through explicit contracts rather than relying on logs, regular expressions, and careful inspection of strings. 2:07

OpenAI function calling improves the situation by allowing developers to specify an output JSON schema and receive structured arguments in a more predictable location. However, Liu emphasizes that parsing JSON into dictionaries still leaves applications exposed to missing keys, incorrect types, spelling differences, and additional handwritten checks. A better interface needs to validate the data and give application code an object it can use directly. 2:07

Suggest correction

This note stays in this page until you copy or download it. Nothing is submitted; reloading clears the draft.

0:14 · section reference included

Make the Pydantic model the application contract

Selected presentation frame from Pydantic is all you need: Jason Liu at 346 seconds
Make the Pydantic model the application contract

Liu presents Pydantic as the missing layer between language-model responses and conventional Python systems. Its type hints define data models, its field and model validation enforce expectations, and its JSON schema output provides a format that can be passed into OpenAI function calling. In his delivery example, a timestamp supplied as a string and dimensions supplied as a list of strings can be parsed into the declared datetime and tuple-of-integers representations. 3:04

The benefits extend beyond successful parsing. Once timestamp and dimensions are declared fields, an IDE can expose their types, offer autocomplete, and catch naming mistakes. The prompt also becomes more reviewable: instead of burying the desired structure inside a long text instruction or manually maintained JSON example, developers express the output contract in code they can inspect and evolve. 3:58

Liu describes Instructor as a library he built to connect this contract to OpenAI function calling. In the workflow he presents, developers patch the completion API, declare a Pydantic object as the response model, and receive an instance of that model instead of manually extracting an untyped dictionary. He notes that patching the completion API is a debatable design choice and that this implementation only works with OpenAI function calling; he identifies Marvin as an alternative framework offering access to more language models and additional capabilities. 4:59

Suggest correction

This note stays in this page until you copy or download it. Nothing is submitted; reloading clears the draft.

3:04 · section reference included

Unify prompting, validation, and recovery inside the model

Selected presentation frame from Pydantic is all you need: Jason Liu at 491 seconds
Unify prompting, validation, and recovery inside the model

A Pydantic model can represent more than a flat response: it can contain nested references, lists of related objects, reusable classes, and methods that define behavior. Liu illustrates this with user details, addresses, best friends, and collections of friends. Because class docstrings and field descriptions become part of the JSON schema sent to the model, documentation influences both how the model interprets its task and how developers understand the resulting objects. 5:57

This produces a single review surface for prompt quality, data quality, and code quality. Good variable names, descriptive fields, and accurate documentation become operational parts of the model interaction rather than separate artifacts that can drift apart. Liu’s argument is not simply that structured generation produces cleaner JSON; it is that the model should capture the prompt, the data, and the behavior together. 5:57

Validation adds an explicit boundary around model output. Standard validators can normalize or reject values and return errors that application code can catch, while an LLM-backed validator can assess a qualitative condition such as whether a statement is objectionable. Instructor can then use a configured retry limit to send validation failures back to the language model and request a corrected response. 6:50

Liu distinguishes this retry loop from broader prompting frameworks: the mechanism is validation, error handling, and re-asking implemented as separate, manageable pieces of software. Rules can include a maximum character count or an external check that a name exists in a database. The tradeoff is that developers must define the relevant constraints and recovery behavior explicitly, rather than assuming the initial prompt will enforce every business rule. 7:51

How it fits togetherValidation and correction loop

Generate a candidate structured object.

Validation failures become corrective feedback for another bounded generation attempt.

Suggest correction

This note stays in this page until you copy or download it. Nothing is submitted; reloading clears the draft.

5:57 · section reference included

Model uncertainty and reusable structures explicitly

Selected presentation frame from Pydantic is all you need: Jason Liu at 651 seconds
Model uncertainty and reusable structures explicitly

Structured outputs can express uncertainty without depending on a model to reproduce a specific sentinel phrase. Liu proposes a wrapper that contains an optional extracted user, an error, and an error message, while individual fields such as a role can also be optional. This escape hatch makes an absent result a first-class application state that downstream code can branch on, instead of a fragile string comparison against a phrase meaning that the model does not know. 8:47

Reusable components also make prompt behavior more modular. Liu defines work time and leisure time using the same time-range structure, with start and end fields shared across both. If extraction is unreliable, he suggests adding a chain-of-thought field within that component and comparing configurations with and without it to understand latency and performance tradeoffs between testing and production. 9:49

For open-ended extraction, a list of key-value properties can represent arbitrary attributes without abandoning structure. Consistent property keys can be encouraged through instructions, checked through validators, and repaired through retries; an explicit index can help constrain the list to a desired number of properties. Similarly, users with identifiers and lists of friend identifiers can represent a network that ordinary graph-processing code can traverse. 9:49

Suggest correction

This note stays in this page until you copy or download it. Nothing is submitted; reloading clears the draft.

8:47 · section reference included

Turn retrieval, planning, and citations into executable data

Selected presentation frame from Pydantic is all you need: Jason Liu at 932 seconds
Turn retrieval, planning, and citations into executable data

Liu applies the same modeling approach to retrieval-augmented generation. Rather than assuming every question maps to a single vector search, he describes structured search requests containing a search type, title, query, and date filter. A method can dispatch video searches and email searches to different backends, while a model-generated list of searches can be processed asynchronously using conventional application code. 11:41

Planning can also be represented as a graph. Liu describes a query plan whose nodes contain an identifier, a question, and dependencies, allowing independent lookups to run in parallel before later nodes combine their results. His example contrasts this single model-generated plan with repeatedly asking an agent what to do next; after the plan is produced, execution becomes an ordinary dependency-management and retrieval problem. 12:37

For knowledge-graph extraction, Liu recommends shaping the generated structure to match the graph visualization API as closely as possible. By aligning model output with the downstream consumer, the code needed to create and render a graph becomes simpler. He presents a description of quantum mechanics as an example input that can be transformed into a visualization through a compact implementation. 13:40

The most stringent example concerns grounded question answering. Liu models an answer as a list of facts, each associated with one or more substring excerpts from the source text. Validators discard facts whose excerpts cannot be found in the original chunk, and a second validation layer retains only facts with at least one verified excerpt. This proves that cited text exists in the supplied material; the mechanism described checks substring presence and does not, by itself, establish that every interpretation or paraphrase is correct. 14:36

How it fits togetherDependency-aware retrieval execution

Generate nodes with identifiers, questions, and dependencies.

One generated query plan exposes parallel lookups followed by dependency-based merging.

Suggest correction

This note stays in this page until you copy or download it. Nothing is submitted; reloading clears the draft.

11:41 · section reference included

Treat future capabilities as domain-modeling opportunities

Selected presentation frame from Pydantic is all you need: Jason Liu at 858 seconds
Treat future capabilities as domain-modeling opportunities

Liu’s broader claim is that structured prompting shifts the work from improvising better instructions toward domain modeling. Objects can carry per-object instructions, nested or recursive structures, and behavior that allows generated data to integrate with established software. Once a model produces a graph, workflow, or plan, ordinary code can traverse it or dispatch it to a system such as Airflow instead of relying on an unconstrained loop. 10:50

He also identifies structured evaluation as an area of ongoing experimentation: one interface might assess whether a response is mean while another examines the distribution of numerical attributes and evaluates them against explicit expectations. The presentation characterizes this as open work rather than a completed or universally solved evaluation system. 16:35

Finally, Liu offers multimodal and generative interfaces as prospective applications rather than established results. He imagines extracting image bounding boxes alongside product-search queries, then rendering an interface element for each region, and extends the idea to generated interfaces over images or audio. These examples reinforce the central thesis: the useful unit is not merely a fluent response, but a structured object that existing software can inspect and act on. 16:35

Suggest correction

This note stays in this page until you copy or download it. Nothing is submitted; reloading clears the draft.

10:50 · section reference included

Read the complete timestamped transcript
  1. 0:00

    [upbeat music] Hey, guys.

  2. 0:15

    So I didn't know I was gonna be one of the keynote speakers, so this is probably gonna be the most reduced scope talk of today. [laughing] I'm talking about type hints. [laughing]

  3. 0:24

    And in, in particular, I'm talking about how Pydantic might be all you need to build with language models. In particular, I wanna talk about structured prompting, which is the idea that we can use objects to define what we want back out rather than kind of praying to the LLM gods that the comma is in the right place

  4. 0:39

    and the bracket was closed. So everyone here basically kinda knows or at least agrees that large language models are kind of eating software. But what this really means in production is ninety percent of the applications you build are just ones where you're asking the language model to output JSON or some structured output that you're parsing with a

  5. 0:58

    regular expression and, and that experience is pretty terrible. And the reason this is the case is because we really want language models to be backwards compatible with the existing software that we have.

  6. 1:08

    You know, codegen works, but a lot of the systems we have today are systems that we can't change.

  7. 1:14

    And so, yeah, the idea is that although language models were introduced to us through ChatGPT, most of us are actually building systems and not chatbots. We wanna process input data, integrate with existing systems via APIs or schemas that we might not have control over.

  8. 1:29

    And so the goal for today is effectively introduce OpenAI function calling, introduce Pydantic, then introduce Instructor and Marvin as a library to make u- using Pydantic to prompt language models much easier.

  9. 1:41

    And what this gets us is, uh, you know, better validation, makes your code a little bit cleaner, and then afterwards I'll talk over some design patterns that I've uncovered and some of the applications that we have.

  10. 1:53

    Um, this is basically almost everyone's experience here, right? Like, you know, Riley Goodside had a tweet about asking to get JSON out of Bard, and the only way you could do it was to threaten to take a human life, and that's not code I really wanna commit into my repos. [laughing]

  11. 2:07

    And then when you do ask for JSON, you know, maybe it works today, but maybe tomorrow instead of getting JSON you're gonna get like, "Okay, here you go. Here's some JSON."

  12. 2:15

    And then again, you kind of pray that the JSON's parsed correctly. And I don't know if you noticed, but here user is a key for one query and username is a key for another, and you would not really notice this unless you had, like, good logging in place.

  13. 2:27

    But really, this should not happen to begin with, right? Like, you shouldn't have to, like, read the logs to figure out that the passwords didn't match when you're signing up for an account.

  14. 2:36

    And so what this means is our prompts and our schemas and our outputs are all strings. We're kind of writing code in TextEdit rather than an IDE where you could, you know, get linting or type checking or syntax highlighting.

  15. 2:50

    And so OpenAI function calls somewhat fix this, right? We get to define a JSON Schema of the output that we want, and OpenAI will do a better job in placing the JSON somewhere that you can reliably parse out.

  16. 3:04

    So instead of going from string to string to string, you get string to dict to string, and then you still have to call json.loads, and again, you're kind of praying that everything is in there.

  17. 3:13

    And a lot of this is kind of praying to the LLM gods. Um, on top of that, like, if this code was committed to any repo I was managing, like, I would be pissed, [chuckles] right?

  18. 3:24

    Complex data structures are already difficult to define, and now you're working with the dictionary of json.loads, and that also feels very unsafe 'cause you get missing keys, missing values, and you get hallucinations, then maybe the keys are spelled wrong and you're, you're missing an underscore, and you get all these issues.

  19. 3:40

    And then you end up writing code like this. And this works for, like, name and age and email, then you're checking if something is a bool by parsing a string.

  20. 3:48

    It gets really messy and, and what H- Python has done to solve this is use Pydantic.

  21. 3:54

    Pydantic is a library that do data model validation very similar to dataclasses. It is powered by type hints. It is, has really great model and field validation. It has seventy million downloads a month, which means it's a library that everyone can trust and use and know that it's gonna be maintained for a long period of time.

  22. 4:11

    And more importantly, it outputs JSON Schema, which is how you communicate with OpenAI function calling. And so the general idea is that we can define an object like delivery, say that the timestamp is a datetime and the dimensions is a tuple of ints.

  23. 4:25

    And even if you pass in a string as a timestamp and a list of strings as tuples, everything is parsed out correctly. This is all the code we don't wanna write.

  24. 4:33

    This is why there's seventy million downloads. More interestingly, timestamp and dimensions are now things that your IDE is a-aware of. They know the type of that. You get autocomplete and spell checking.

  25. 4:43

    Again, just more bug-free code. And so this really wa- brings me to the idea of structured prompting, 'cause now your prompt isn't a, you know, triple quoted string. Your prompt is actual code that you can look at, you can review.

  26. 4:59

    And everyone has written a function that returns a data structure, right? Everyone knows how to manage code like this instead of doing the migration of JSON schemas in the one-shot examples.

  27. 5:08

    You know, I've done database migrations. I know how some of these things work. And more importantly, we can program this way. And so that's why I built a library called Instructor a while ago, and the idea here is just, just to make OpenAI function calling super useful.

  28. 5:21

    So the idea is you import instructor, you patch the completion API. Uh, debatable if this is the best idea. But ultimately, you define your Pydantic object, you set that as the response model of that create call, and now you're guaranteed that that response model is the type of the en-entity that you extract.

  29. 5:40

    So again, you get nice autocomplete, you get type safety. Really great.

  30. 5:46

    I would also wanna mention that this only works for OpenAI function calling. If you wanna use a more, uh, comprehensive framework to do some of this Pydantic work, I think Marvin is a really great, uh, library to try out.

  31. 5:57

    Uh, they, they give you access to more, uh, language models and more capabilities above this, uh, response.

  32. 6:04

    But the general idea here isn't that this is gonna make your JSON come out better, right? The idea is that when you define objects, you can define nested references, you can define methods of the behavior of that object, you can return instances of that object instead of dictionaries.

  33. 6:18

    And you're gonna write cl- cleaner code and code that's gonna be easier to maintain as they're passed through different systems.

  34. 6:25

    And so here you have, for example, a BaseModel, but you can add a method if you want to. You could define the same class but with an address key.

  35. 6:32

    You can then define new classes like best friend and friends, which is a list of user details. Like, if I was to write this in JSON Schema to make a POST request, it would be very unmanageable, but this makes it a lot easier.

  36. 6:43

    On top of that, when you have docstrings, the docstrings are now a part of that JSON Schema that is sent to OpenAI.

  37. 6:50

    And this is because the model now represents both the prompt, the data, and the behavior all in one, right? You want good docstrings, you good want f- you good-- You want good field descriptors, and it's all part of the JSON Schema that you send.

  38. 7:03

    And now your code quality, your prompt quality, your data quality are all in sync. There's just one thing you wanna manage and one thing you wanna review. And what that really means is that you need to have good variable names, good descriptions, and good documentation.

  39. 7:15

    And this is something we should have anyways.

  40. 7:20

    You can also do some really cool things with Pydantic without language models. For example, you can define a validator. Here I define a function that takes in a value.

  41. 7:27

    I check that there is a string in that value, and if it's not, I return a lowercase version of that 'cause that just might be how I wanna parse, parse my data.

  42. 7:35

    And when you construct this object, you get an error back out, right? We're not gonna fix it, but we get a validation error, something where we can catch reliably and understand.

  43. 7:43

    But then if you introduce language models, you can just import the LLMValidator, and now you can have something that says like, "Don't say mean things." And then when you construct an object that has something that says that the meaning of life is to be evil and steal things, you're gonna get a validation error and an error message.

  44. 8:00

    And this error message, "The statement is objectionable," is actually coming out of a language model API call. It's using Instructor under the hood to define that.

  45. 8:08

    But, you know, it, it's not enough to actually just point out these errors. You also wanna fix that. And so the easy way of doing that in Instructor is to just add max_retries,

  46. 8:17

    right? Now what we do is we'll append the err- the message that you had before, but then we can also capture all the validations in one shot, send it back to a language model, and try again, right?

  47. 8:27

    But the idea here that this isn't like prompt chain, this isn't, this isn't constitutional AI. Here we just have validation, error handling, and then re-asking, and these are just separate systems in code that we can manage.

  48. 8:39

    If you want something to be less than ten characters, there's a character count validator. If you wanna make sure that a name is in a database, you can just add a POST request if you want to.

  49. 8:47

    But this is just classical code again. This is the backwards compatibility of language models.

  50. 8:52

    But we can also do a lot more, right? Uh, structured prompts get you structured outputs. But ideally, the structure actually helps you structure your thoughts. So here's another example.

  51. 9:02

    Uh, it's really important for us to give language models the ability to have an escape hatch and say that it doesn't know something or can't find something. And right now, most people will say something like, "Return I don't know in all caps.

  52. 9:14

    Check if I don't know all caps in string." Right? Uh, sometimes it doesn't say that. It's very difficult to manage. But here you see that I've defined user details with an optional role that could be None.

  53. 9:26

    But the entity I wanna extract is just maybe a user. It has a result that's maybe a user and then an error and an error message. And so I can write code that looks like this.

  54. 9:36

    I get this object back out. It's a little bit more complicated, but now I can kind of program with language models in a way that feels more like programming and less like chaining, for example.

  55. 9:47

    Right? Um, we can also define reusable components. Here I've defined a work time and a leisure time as both a time range, and the time range has a start time and an end time.

  56. 9:59

    If I find that this is not being parsed correctly, what I could do is actually add chain of thought directly in the t- the time range component. And now I have modularity in how, some, in some of how, uh, in some of these features.

  57. 10:12

    And you can imagine having a system where in production you, uh, disable that chain of thought field and then in put, in, in testing you add that to figure out what's the latency or performance trade-offs.

  58. 10:24

    You could also extract arbitrary values, right? Here I define a property called key and value, and then I wanna extract a list of properties, right? You might wanna add a prompt that says, "Make sure the keys are consistent over those properties."

  59. 10:35

    We can also add validators to make sure that's the case and then re-ask when that's not the case. If I want, you know, only five properties, I could add an index to the property key and just say, "Well, now count them out.

  60. 10:45

    And when you count to five, stop." And you're gonna get much more reliable outputs.

  61. 10:50

    Uh, some of the things that I find really interesting with this kind of method is prompting data structures. Here I have user details, age, name as before, but now I define an ID and a friends array, which is a list of IDs.

  62. 11:02

    And if you prompt that well enough, you can basically extract like a network out of this data str- out of your data.

  63. 11:08

    So, you know, we've seen that structured prompting kinda gives you really useful components that you can reuse and make modular. Um, and the idea again here is that we wanna model both the prompt, the data, and the behavior.

  64. 11:19

    Here I haven't mentioned too many methods that you could act on this object, but the idea is almost like, you know, when we go from C to C++, the thing we get is object-oriented programming, and that makes a lot of things easier.

  65. 11:29

    And we've learned our lessons with object-oriented programming. And so if we do the right track, uh, I think we're gonna get a lot more productive development out of these language models.

  66. 11:37

    And the second thing is that these language models now can output data structures, right? That you can like pull up your old like LeetCode textbooks or whatever and, and actually figure out, like, traverse these graphs, for example, process this data in a useful way.

  67. 11:49

    And so now they can represent, you know, knowledge, workflows, and even plans that you can just dispatch to a classical computer, uh, computer system, right? You can create the data that you wanna send to Airflow rather than doing this for loop hoping it terminates.

  68. 12:04

    And so now I think I have about six minutes, so I'll go over some advanced applications. Um, these are actually fairly simple. I have some more documentation if you wanna see that later on, but, um, let's, let's go over some of these examples.

  69. 12:14

    So the first one is RAG. I think-

  70. 12:17

    When we first started out, a lot of these systems end up being systems where we embed the user query, make a vector database search, return the result, and then hope that those are good enough.

  71. 12:25

    But in, in practice, you might have multiple backends to search from. Maybe you want to rewrite the user query. Maybe you want to decompose that user query, right? If you want to ask something like what, what was something that was recent, you need to have time filters.

  72. 12:37

    And so you could define that as a data structure, right? The search type is email or video. Search has a title, a query, a before date, and a type.

  73. 12:46

    And then you can just implement the execute method that says, you know, if type is video, do this. If email, do that. Really simple. And then what you want to extract back out is multiple searches.

  74. 12:55

    Like, give me a list of search queries. And then you can write some, like, asyncio to map across these things.

  75. 13:02

    And now, because all the prompting is embedded in the data structure, your prompt that you send to OpenAI is very simple. You're a helpful assistant, segment the search queries.

  76. 13:11

    And then what you get back out is this ability to just have an object that you can program with in a way that you've managed sort of, like, all your life, right?

  77. 13:19

    Something very s- straightforward. But you can also do something more interesting. You can then plan, right? Before we talked about, like, extracting a social network, but you can actually just produce the entire DAG.

  78. 13:30

    Here, I had the same graph structure. All right? It's an ID, a question, and a list of dependencies where I have a lot of information in the description here, and that's basically the prompt.

  79. 13:40

    And what I want back out is a query plan.

  80. 13:43

    So now, if you send it to a query planner that says, like, you're a helpful query planner, like, build out this query. You can ask something like, what is the difference in populations of Canada and Jason's home country?

  81. 13:52

    And then what you can see is, you know what, like,

  82. 13:55

    if I'm good at LeetCode, I could query the first two in parallel because there are no dependencies, and then wait for dependency th-three to merge, and then wait for four to merge those two.

  83. 14:05

    But this requires one language model call, and now it's just traditional RAG. And if you have an IR system, you get to skip this for loop of agent queries.

  84. 14:15

    You know, an example that was really popular on Twitter recently was extracting knowledge graphs. You know, same thing here. Here, what I've done is I've made sure that the data structure I model is as close as possible to the Graphviz, uh, visualization API.

  85. 14:29

    What that gets me is really, really simple code that does basically the creation and visualization of a graph. I've just defined things one-to-one to the API, and now what I can do is if I ask for something that's very simple, like, you know, give me the description of quantum mechanics, you can get a graph out, right?

  86. 14:47

    That- that's basically in, like, 40 lines of code because what you've done is you've modeled the data structure Graphviz needs to make the visualization. And we're, we're kinda trying to couple that a lot more.

  87. 14:59

    This is a more advanced example, so don't feel bad if you can't follow this one. But here what I've done is I've done a QuestionAnswer. It's a question and an answer, and the answer is a list of facts.

  88. 15:09

    And what a fact is, is it's a fact as a statement and a substring quote from the original text. I want multiple quotes as a substring of the original text.

  89. 15:18

    And then what my validators do is it says, you know what? For every quote you give me, validate that it exists in the text chunk. If it's not there, throw out the fact.

  90. 15:28

    And then the validator for QuestionAnswer says, only show me facts that have at least one substring quote from the original document. So now I'm trying to encapsulate some of the business logic of not hallucinating, not by asking it to not hallucinate, but actually trying to figure out, like, what is the, like, para- like, the paraphrasing detection

  91. 15:46

    algorithms to, to identify the, what the quotes were. And what this means is instead of being able to say that the answer was in page seven, you can say the answer was this sentence, that sentence, and something else, and I know they exist in the text chunks.

  92. 16:01

    And so I think what we end up finding is that, uh, as language models get more interesting and more capable, we're only gonna be limited in, in the creativity that we can have to actually prompt these things, right?

  93. 16:13

    Like, you can have instructions, uh, per object. You can have, like, recursive structures, right? It, it, it goes into domain modeling more than it goes to prompt engineering. And again, now we can use the code that we've always used.

  94. 16:28

    If you want more examples, I have a bunch of examples here on different kinds of applications that I've had with some of my consulting clients. Um, yeah, I think these are some really useful ones.

  95. 16:37

    And I'll go to the next slide, which is... [gasps]

  96. 16:40

    This doesn't have the P-- uh, the QR code. That's fine. [laughs]

  97. 16:45

    The updated slide has a QR code, but instead you can just visit jxnl.github.io/instructor. I also wanna call out that, uh, we're also experimenting with a lot of different UIs to do this structured evaluation, right?

  98. 16:57

    Where, um, you might wanna figure out whether or not one response was mean, but you also want to figure out what the a- distribution of floats was for a different attribute and be able to write evals against that.

  99. 17:08

    And I think there's a lot of really interesting open work to be done, right? Like, right now we're doing very simple things around extracting graphs out of documents. You can imagine a world where we have multimodal, in which case you could be extracting bounding boxes, right?

  100. 17:21

    Like, one application I'm really excited about is being able to say, given an image, draw the bounding box for every image and the search query I would need to go on Amazon to buy this product.

  101. 17:30

    And then you can really instantly build a UI that just says, you know, for every bounding box, render a modal, right? You can have, like, generative UI over images, over audio.

  102. 17:39

    I think in general it's gonna be a, a very exciting space to play more with, uh, structured outputs. Thank you. [audience applauding] [upbeat music]