AI Engineer World's Fair 2026
AI Agents for Performance: Ship Faster, Pay Less
Read the talk
AI Agents for Performance: From Production Profiles to Preventing Slow Code
Production profiles can guide coding agents toward costly patterns, while a shared catalog, tests and canaries turn individual fixes into a repeatable performance workflow.
From a talk by Rajat Shah
Before you start: Familiarity with call stacks, CPU profiling, Git revisions and automated testing will help; the code example uses Java and Guava’s ImmutableMap.
Why faster coding creates a performance bottleneck
What happens when generating code becomes easier than checking what it costs to run? Rajat Shah works on large-scale distributed systems for machine-learning model hosting in Netflix’s AI platform organization. His starting problem is performance-engineering throughput: how to keep infrastructure efficient as coding agents help engineers ship more code.
Shah frames the mismatch as code authoring becoming 10× faster, with a deliberately exaggerated suggestion that CPU bills are growing at the same pace. The underlying concern is concrete: agents optimized to produce working code quickly do not necessarily produce the fastest implementation.
Better models help, but they do not automatically know an organization’s internal platform, frameworks or established code patterns. An agent may import a convention from another codebase or invent a way to use an internal framework that its designers never anticipated. Performance depends on local knowledge as well as general coding ability.
Suggest correction
This note stays in this page until you copy or download it. Nothing is submitted; reloading clears the draft.
The manual profiling loop
A performance engineer typically works through a recurring sequence:
- Trigger profiling on one production instance in a service fleet.
- Download the profile, which may contain structured call-stack and CPU data in JSON.
- Open a visualizer and search for expensive paths.
- Find the corresponding packages and methods in the source repositories.
- Diagnose a fix, submit it for code review and merge it.
- Repeat the investigation for the next opportunity.
The visualizer makes the data readable, but interpreting it remains a learned skill. Finding a hot path is only the beginning; the engineer must connect it to code that can actually be improved.
That repetition makes proactive profiling difficult to sustain across many services. It is easy for profiling to become something people reach for during a 2 a.m. CPU incident. Shah estimates that identifying hot paths can take an engineer about 20 minutes. The experiment begins with a narrower question than autonomous optimization: can an LLM read the profile and shorten that search? The team tested the idea on live services.
Suggest correction
This note stays in this page until you copy or download it. Nothing is submitted; reloading clears the draft.
What profilers and coding agents already provide
The first assumption is that profilers expose comparable information across runtimes. A Java, Python or Go profiler can sample a production instance at high frequency and record its call stacks, including self CPU—work attributed to a method itself—and inclusive CPU, which includes work beneath it in the call path. The file formats need not be identical for an agent to reason over this common structure.
The second assumption is that coding agents already recognize common performance patterns from their training:
- Quadratic work: loops whose total work grows as O(N²).
- Loop invariants: computations repeated inside a loop even though their result could be calculated once.
- Repeated allocation: objects recreated on a frequently executed path when their construction could be moved elsewhere.
- Contention and batching: coordination or repeated small operations that could be reorganized to reduce overhead.
Shah makes this capability conditional on the quality of the code in training. The useful starting point is pattern recognition: combine an expensive runtime path with a familiar implementation smell to identify something worth investigating.
Suggest correction
This note stays in this page until you copy or download it. Nothing is submitted; reloading clears the draft.
From a call stack to the deployed source
The first distinctive finding connects two rows in the profile. Rows one and three belong to the same call path: ImmutableMap.copyOf appears inside a tensor-merge method, shown on the slide as TensorSet.merge. Recognizing what the copy operation does lets the agent suspect repeated copying and quadratic accumulation. Shah reports that this initial inference came from the profile’s call stack, before the agent inspected the source. It gives the investigation a target; source inspection then establishes how that target is implemented.
To turn that suspicion into a proposed fix, the agent needs to connect runtime evidence to the correct version of the code:
- Search for the method and identify its owning repository.
- Resolve the production build to its exact Git commit and check out that revision.
- Locate the relevant implementation, avoiding a detour through unrelated internal-library details.
- Trace the full method call path with the source available.
The production commit is part of the evidence. Inspecting a different revision could mean explaining code that did not produce the profile. With this connection in place, the experiment on a couple of services could test whether the agent could go beyond detection and produce a real fix suitable for an engineer to approve.
Suggest correction
This note stays in this page until you copy or download it. Nothing is submitted; reloading clears the draft.
One finding, then a search across services
In the tensor-merge example, Shah reports that the quadratic pattern accounted for 8.8% of CPU time during the profiling period. That is the cost attributed to the pattern, not the amount saved by removing it. With sufficient skill or prompt instructions and a capable coding agent, the workflow could proceed through repository checkout, implementation discovery and a proposed code change.
Shah reports reaching code review in under five minutes in the large-codebase experiment. He also reports observing production CPU and latency savings after optimization. The useful operational result is that the agent could carry an investigation through to a reviewable change, rather than merely name an expensive method.
The next opportunity was to reuse a discovery. A profile exposed Spectator metrics counter objects being created on every iteration of a hot path. Once the agent recognized that pattern, it could search other repositories for the same usage. Shah reports finding the counter-creation pattern in seven services, with potential CPU-cycle savings of 0.5–4.6% if it were fixed across those repositories. Those savings remain conditional; the broader mechanism is a production finding becoming a search pattern for additional services.
Suggest correction
This note stays in this page until you copy or download it. Nothing is submitted; reloading clears the draft.
A shared catalog as durable memory
Once an agent can find and propose fixes, the next question is how to carry those discoveries into the development cycle. An individual invocation does not contain all the accumulated context of a performance engineer. Compact model memory is insufficient for remembering the organization’s patterns, previous investigations and framework-specific lessons.
Shah’s solution is a stateful catalog paired with a stateless LLM. Store patterns and anti-patterns centrally so agents working on different teams and products can reuse them. Some entries will be specific to an internal framework; others, such as quadratic accumulation, can be generalized across languages. The catalog becomes a durable description of what the organization has learned about efficient code.
The initial implementation can be Markdown files in a centralized Git repository. A vector database is unnecessary to get started. As production investigations uncover patterns, agents add entries; a later investigation in another service can consult those entries instead of rediscovering the same explanation. This is how one service’s profiling effort becomes reusable knowledge for the fleet.
Suggest correction
This note stays in this page until you copy or download it. Nothing is submitted; reloading clears the draft.
What belongs in a catalog entry
An empty catalog is a valid starting point, but existing material can seed it. Shah suggests Jeff Dean’s writing on C++ optimization, TorchFix and internal performance playbooks. TorchFix is more precisely a Python static-analysis linter for PyTorch code with best-effort autofixes; its repository was archived in January 2026. Its documented checks still illustrate the kind of reusable patterns a catalog can capture. Internal playbooks contribute the organization-specific knowledge that a general coding agent lacks.
A useful entry supplies query hints, relevant symbols, services where the pattern has been confirmed and a confidence level that can be updated as evidence accumulates. That confidence should support a decision to request human review. It should not authorize a direct production push: an optimization can change business behavior that the agent does not understand or that the tests fail to cover.
Pair the anti-pattern with the preferred implementation. For the ImmutableMap accumulation example, the distinction is repeatedly copying a growing map versus accumulating entries and making the immutable copy once. A Java illustration makes that difference explicit:
java
import com.google.common.collect.ImmutableMap;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;
final class MapAccumulation {
static <K, V> ImmutableMap<K, V> copyEachStep(
List<Map.Entry<K, V>> entries) {
ImmutableMap<K, V> result = ImmutableMap.of();
for (Map.Entry<K, V> entry : entries) {
Map<K, V> next = new LinkedHashMap<>(result);
next.put(entry.getKey(), entry.getValue());
result = ImmutableMap.copyOf(next);
}
return result;
}
static <K, V> ImmutableMap<K, V> copyOnce(
List<Map.Entry<K, V>> entries) {
Map<K, V> result = new LinkedHashMap<>();
for (Map.Entry<K, V> entry : entries) {
result.put(entry.getKey(), entry.getValue());
}
return ImmutableMap.copyOf(result);
}
}
For distinct, non-null keys and non-null values, the first method repeatedly copies an increasingly large map; the second accumulates into one mutable map before producing the immutable result. Both retain the last value for a repeated key. Recording the implementation alongside the pattern makes the catalog actionable, while preserving the need to check the actual application’s semantics.
Suggest correction
This note stays in this page until you copy or download it. Nothing is submitted; reloading clears the draft.
Tests and canaries before human review
A system that generates speculative optimization reviews can simply move the bottleneck onto reviewers. Before asking for attention, the agent should run unit, integration and basic functional tests. These checks establish whether the proposed change preserves the business behavior encoded in the test suite.
Incomplete coverage makes a second gate valuable: an automated canary comparison. Shah’s example uses two machines, one running the old code and one the proposed optimization. Send the same traffic to both for a period such as ten minutes, then compare their behavior. With suitable automation, this comparison can happen before the change requires a human reviewer’s attention.
The report gives the agent evidence for whether to open a review:
| Signal | Question |
|---|---|
| CPU usage | Does the proposed change reduce compute usage? |
| Latency | Does request processing improve? |
| Error rate | Has the optimization broken behavior? |
An increase in errors is a stop signal, even if CPU usage falls. Observability, canary execution and verification are standard engineering infrastructure that the agent must be able to use. The engineer remains the final decision-maker. Shah’s division of responsibility is direct: the profiler estimates the opportunity, the canary establishes the observed effect, and the engineer decides whether to accept the change.
Suggest correction
This note stays in this page until you copy or download it. Nothing is submitted; reloading clears the draft.
Move the catalog into review and authoring
Production profiling is a useful starting point, but changing code that already works in production requires care. As the catalog grows, its findings can move earlier in development. A reviewer agent can inspect a proposed change, look up the relevant pattern and leave an inline suggestion grounded in previous profiling evidence. The same catalog now supports both reactive diagnosis and preventative review.
The next step is to give the catalog to the authoring agent itself. Before writing a known inefficient pattern, the agent can retrieve the preferred approach and use it in the initial implementation. This consultation can slow code generation and consume additional tokens, so the catalog needs structure and indexing. Hierarchical navigation should lead the agent to the relevant entry without loading the whole collection into its context. Catching a pattern during authoring avoids both a later review correction and the possibility of deploying the known inefficiency.
Suggest correction
This note stays in this page until you copy or download it. Nothing is submitted; reloading clears the draft.
Build the integration foundations
Putting agents into more development stages only helps if the underlying checks are dependable. Business logic needs strong test coverage. Canary automation must be reliable, and the agent needs clear ways to invoke it and retrieve its numerical report. The Git catalog is another shared foundation: humans and agents can both read and author it. Engineers building a framework can record its good and bad usage patterns while they still have the design context in mind.
The integration chain should let the workflow trigger profiling on an instance in a CPU cluster, download the data, feed it to the model, retrieve the relevant source and validate a proposed fix through a production canary using shadow or real traffic. Weak connections between those steps create friction and can introduce production bugs. Begin with reactive investigation, make the foundations dependable and gradually move the accumulated knowledge into earlier development stages.
Suggest correction
This note stays in this page until you copy or download it. Nothing is submitted; reloading clears the draft.
From assisted diagnosis to scheduled orchestration
The first useful deployment does not need complete automation. In Shah’s manual baseline, engineers can spend hours finding problems. At level one, a person may still trigger the profiler, transfer the profile and run the canary, while the LLM identifies a potential fix. That already frees time previously spent inspecting flame graphs.
Level two connects the tools, integrations, harnesses and hooks into a predefined workflow. The sequence is fixed: trigger profiling, download the profile, analyze it, validate a candidate change with a canary and provide a suggested fix for review. The model does not need to invent the overall plan. Once the sequence works reliably, it can be scheduled—for example, weekly on each service—to find newly introduced problems closer to the time their code was written.
Suggest correction
This note stays in this page until you copy or download it. Nothing is submitted; reloading clears the draft.
The boundary of greater autonomy
Level three allows the agent to plan, reason and act beyond a fixed workflow. That flexibility brings additional obligations: stronger evaluation, sandboxing and security guardrails against prompt injection and other attacks on agent infrastructure. Shah recommends starting with assistance and progressing to orchestration, where he sees the greatest practical benefit. Greater autonomy is a further investment to make when the workflow actually needs it.
Suggest correction
This note stays in this page until you copy or download it. Nothing is submitted; reloading clears the draft.
Resources
From the talk
Archived Python linter for PyTorch code, with documented rules and best-effort autofixes that illustrate reusable code-pattern checks.
Further reading
- Performance HintsArticle
Jeff Dean and Sanjay Ghemawat's guide to performance tuning, illustrated with C++ changes and principles applicable across languages.
Documentation and Java examples for registries, meter identifiers, counters, and measurement collection in Netflix's Spectator library.
Rajat Shah's June 2026 presentation on Netflix model-serving infrastructure, routing, gateways, and service meshes.
Read the complete timestamped transcript
- 0:00
Hi there. Welcome to AI Engineer World's Fair 2026 event. I am Rajat Shah. I am a staff software engineer at Netflix, where I work in the AI platform organization, building large-scale distributed systems for machine learning model hosting.
- 0:15
In this talk, I'm here to, um, share how we did, uh, improve our performance engineering, uh, throughput by introducing AI agents into the mix. And this is more of a, uh, playbook or a practitioner's guide, uh, to help you also replicate similar learnings in your own organizations, uh, to improve, uh, the infrastructure cost and, uh, ship
- 0:39
faster. Let's first talk about the problem. Why does performance engineering doesn't scale, and, uh, what does it cost to actually do it right?
- 0:51
The problem is arising, arising from the fact is that you are authoring code now at a 10X faster speed. The, uh, coding agents are getting better and better, uh, at, uh, solving problems.
- 1:02
And, um, as more and more, uh, engineers, uh, adopt it, it, it gets very easy to produce code, uh, in your system. And this is slight exaggeration, but the compute cost also, uh, is increasing at a similar pace, uh, because, uh, it doesn't always sh- uh, write the fastest code.
- 1:24
Uh, so this is where the problem arises because of that new wild coding era. Uh, the AI agent ships code, uh, it is pretty much tuned to ship code fast.
- 1:35
Um, and of course, you could say that, uh, as the, uh, the coding agents are evolving, newer models are coming into play, uh, they get better and better at, uh, simply writing performant code.
- 1:47
But that's not always true. Your, um, agent doesn't know specific details about your platform and your frameworks, uh, and your internal code base patterns. So it, it tends to just produce code based on what it might have already, uh, seen, uh, other, uh, code bases using or inventing new, uh, patterns in your code bases that you did
- 2:08
not anticipate, uh, uh, an engineer to use, uh, as a pattern to use your framework.
- 2:16
So let's, uh, look at what, uh, a performance engineer typically does. Uh, I'm calling this as a human performance engineer, which is responsible for identifying bottlenecks in a service and fixing them.
- 2:30
Typically, a, a human would trigger profiling on a, a single production instance of a fleet of, uh, production instances. Uh, you would go and download it, uh, potentially open it in a visualizer.
- 2:44
The raw data that you download typically is not great to look at. It, it could be, for example, a JSON structured data of, uh, the call stack and, uh, where the CPU is spent.
- 2:55
So using a visualizer, uh, helps you at least see and visualize the call stack and CPU, uh, time of various, um, method in your services better. Once you have that visualizer opened, you pretty much end up spending a lot of time in, uh, like just looking at and, and finding in this, in this treasure, uh, hunt on,
- 3:19
uh, on the path-- o-on the potential places where you could, uh, improve, uh, the code to, uh, to make it more performant. This takes a lot of time, uh, in order to even learn how to look at it.
- 3:31
Um, and there's a learning curve to c-c-curve to it. And this is where the real bottleneck ends up being. You end up, you end up having to spend straight many, many minutes to, uh, to identify the bottlenecks.
- 3:45
Uh, once you have identified some code paths and some, uh, packages that, uh, that are spending significant CPU cycles, you, you would end up searching it in your code bases, in your code repos, uh, and see if it, uh, has a potential to improvement.
- 4:01
Uh, hopefully you, you hit, uh, you, you have luck here and, uh, you find a, uh, root cause and you produce a code review out, you merge it, and, uh, you get some performance wins.
- 4:15
And then you repeat all of this, uh, again. You see the problem, right? This is a very manual effort and very tedious effort to get right, and this ends up being a bottleneck if you were to do it across many of your code bases and code paths, and that's why this is done very rarely.
- 4:31
People typically end up looking at profiling data only when something is going wrong at 2:00 a.m. and, uh, somebody needs to, uh, fix a problem because your CPU is unbearable.
- 4:44
So we asked this question internally, can we, uh, can an L- LLM read this profiling data? The twenty minutes that I mentioned an engineer, uh, spends in identifying, uh, hot paths, can an LLM agent w-which is fed that, uh, data also, uh, do it much faster?
- 5:01
And we tried to answer this, uh, uh, question through some live services. So the next couple of slides will be about this experiment and how we do it right.
- 5:10
Uh, before we get to it, the, the foundation of, uh, of our assumption, uh, is that every profiler essentially speaks the same language. Uh, even though you would profile and you could have your services written in Java, Python, uh, Go, et cetera, uh, the profilers, uh, example that I mentioned here, uh, do the same, same thing.
- 5:31
They would, uh, run it, uh, in your-- uh, they would run against your production service, uh, on a single instance, and they would essentially try to capture the call stack, uh, the self CPU and inclusive CPU that is spent on, uh, on each of the, uh, methods in your call stack, uh, sampled at a very high frequency.
- 5:52
So irrespective of which language, which runtime you are using in production, the output of a profiling data is actually, uh, very similar and very well-structured for an LLM agent to use.
- 6:06
This is one assumption that we had going into the experiment The second assumption we had going into the experiment is that, uh, there are many common patterns that the coding agents have learned through their training sets across all the publicly available code sources that they might have had.
- 6:23
So things like, uh, O(N²) loops, uh, loop invariants, things that you are computing every time in your lee- loop, which could be computed just once outside it. Uh, if you have certain places where you are doing the object allocation, uh, very repeatedly and, uh, if you could move it out as well.
- 6:41
Uh, or there are times when you would be, uh, like having some contention and, uh, places where you could optimize, uh, through better batching. All of these are very common patterns that an agent already knows.
- 6:54
Uh, it, uh, I mean, assuming it is trained on very good quality, uh, software code, uh, the better the quality, the better agent knows, uh, which, uh, patterns are, uh, not great.
- 7:07
Uh, and this is a very good, uh, point for an LLM agent because it essentially means that it can technically, uh, look at the, uh, the code base, and it can identify those patterns very easily.
- 7:23
So this is more about like pattern recognition, like finding out these, uh, code patterns to find some code smells that, uh, that are worth fixing.
- 7:32
So when you have that profiling output that I mentioned, and you have a coding agent that could understand it, you feed it into it, um, the profiling data that it needs to read is actually very well-structured in a way that it could see that the, in this case, uh, the, um, the profiling data is, uh, in, in
- 7:55
the case of row one and row three, they are the same call path, and the immutable map copy of that I have in my row three is actually [chuckles] used inside, uh, a tensor merge method that we have.
- 8:09
Uh, so, uh, don't think too much about the method names here, but the key point that I wanted to call out is that it was able to use these functions.
- 8:20
Uh, it, it knows the meaning of these functions, and when it sees it is being used in a, a poor way, it can actually identify that this is a quadratic, uh, um, algorithm and not a linear algorithm.
- 8:33
So this is where, uh, our first aha moment was that, okay, if you feed a profiling data, it-- if it knows the pattern, it, uh, assuming the coding agent was trained on a very good quality data, it can actually identify and up-- and find out that, uh, find in your code base where that bad, uh, patterns are
- 8:50
actually, uh, running. And this is not by looking at the code base, this is purely by looking at the call stack that the profiling, uh, uh, data produced.
- 9:02
And once, uh, a prof... uh, an AI agent gets this, what, what are the steps that it needs to do in order to get to the potential fix? So we, we, we have mentioned that it can identify, uh, a pattern and say that, okay, this is a potential problem to be fixed.
- 9:19
What, what happens next? Um, it could, knowing where that method lives, it could do a code search and first of all, before, uh, I mean, yeah, it could do a code search and find out the code repo where this m-method is defined, uh, or this code is defined.
- 9:37
And it, it needs to extract out the exact commit that is currently running in production, which is typically easy to get. You know which build is running in your production, and you could point that to the LLM to, uh, check out the Git repo at that same commit.
- 9:50
And then, um, once it has, uh, find- found out, uh, and has the Git repo cloned, uh, it can look for, uh, that exact code path, uh, skip any internal library details, and find out, uh, the code patterns.
- 10:07
And now the te-- it, now once it has the, uh, full, uh, uh, code repo cloned out, the, um, the methods, uh, definition and implementation identified, it can trace the entire ca-call path of that method.
- 10:22
And this, uh, structured data, uh, once it, uh, has this information, becomes, uh, like very powerful. And we'll, we are going to talk about how, uh, it leverages this.
- 10:36
So these were our understanding going into the experiment. We, uh, we knew it could find, uh, the patterns. We tested it with, with a couple of, uh, of our services to see if it can actually not just find the pattern, but also take it one step further and, uh, produce a real fix and provide a real fix
- 10:57
that, uh, w- an engineer could approve and merge.
- 11:01
So first finding, uh, the, the O(N²) um, uh, example that I just mentioned. It, uh, once it knew, uh, that this is a problem and looking at the profil- uh, profiling data, it knows that this is consuming eight point eight percent of the CPU time during that, uh, uh, period of profiling.
- 11:22
So for us, uh, the coding agent not just ended up finding the problem, given enough instructions as a form of, let's say, skill or prompt, uh, you could actually have it, uh, do those four steps that I just mentioned, which is checking out the Git repo, uh, finding where that code is implemented, and actually, uh, sending a
- 11:40
code review out. All of it could be done, uh, in a very large code base with powerful enough code agents in less than five minutes. Um, and in this case, uh, we also, which I'll talk about a little bit in the later slides, uh, were able to identify what is the savings, uh, if you were to im-
- 11:59
re-implement it with a, uh, with an optimized implementation in terms of both CPU as well as latency savings. Uh, I, I've shown the numbers here of our real production, uh, savings that we were able to observe, uh, through this, uh, exercise So this was like a first, uh, proof for us that you could actually indeed introduce an,
- 12:19
a- an AI agent into the mix and get, uh, your productivity wins of not just identifying, but also going all the way to a code review. Uh, the second, uh, great benefit is that once you have this well set up, um, the, uh, other example that we are able to take it forward to it is, let's say
- 12:42
it identifies the, uh, pattern in one of the services that we profiled. Um, and the learning that we had is that it could actually, uh,
- 12:53
look at all your potential places where that same bad pattern, uh, is being reused. So in the previous example, it, it just identified one bad implementation. You fix it, you get all the benefits.
- 13:05
In this case, it identified not just a bad code, but because that pattern, in this case, which is a counter object, uh, for our, uh, spectator metrics, uh, that are, uh, being created on every single, uh, uh, iteration of a hot path in our service stack, um, it could essentially see that this is, uh, a real problem
- 13:30
and it could double down and search multiple services where that same pattern is being repeated and, uh, scale up the effort to fix it in multiple services. In this case, we found that same bad pattern were actually implemented in seven different services, uh, through cross-repo code searches.
- 13:51
And if fixed, it could actually, uh, if fixed across all of those different code repos, it could have savings between point five to four point six percent of CPU cycles.
- 14:01
Um, so we have discussed the problem, our hypothesis, and the experiment which proved out that a, a LLM coding agent could actually help improve, uh, the, uh, the finding and fixing of your, um, suboptimal code.
- 14:18
Let's see how we can actually build this into the development cycle. Uh, it doesn't have to be a very retrospective, uh, problem where once a production service is, uh, having issues, you end up doing all of those exercises.
- 14:32
I'll talk about how you can actually leverage in your end-to-end software development cycle so that you get the benefits, uh, much early and potentially avoid having that suboptimal code reach production altogether.
- 14:48
Uh, the first [chuckles] uh, real problem is that LLMs, if you invoke them, they do have some memory these days, but it's very compact memory, and it will, uh, it, it won't have all the, uh, information that, uh, you are, uh, uh, that, that you potentially as a performance engineer know when you are trying to debug.
- 15:08
So y- you... when you-- if you think of a coding agent and if you want to build it at par, uh, uh, as sufficient as, as efficient as a human engineer would typically be, you want to introduce a long-term memory that it could reuse.
- 15:23
Um, so that's our first, uh, real problem to solve for, and I'll talk about how you solve that. The simplest way is to first think of, uh, you want to build a catalog.
- 15:35
Patterns, anti-patterns. Once you have identified enough of them, you could put it in a catalog that, uh, that users, uh, that is used by an LLM agent, which can be stateless of its own.
- 15:48
Uh, and together, a stateful catalog and a state of stateless LLM can become a full fleet-wide memory, um, for, uh, for a coding agent to use. Um, the foundation for this and, and to foundation for incorporating in this development cycle is practically just this.
- 16:08
Uh, you want to keep this very central so that it's not very team specific, not very product specific, but rather a central ever-growing, uh, catalog. Uh, as the catalog patterns get written, if there are certain things that could be generalized, uh, in that example, the first example that I-- the first finding that I provided around O(N²)
- 16:29
implementation is actually very generalizable. All coding languages will potentially have the same problem if it, if the code is written and implemented in that way. So you, uh, you can take it a step further that your catalog can become even more, uh, ubiquitous and usable across languages and frameworks as well.
- 16:48
Um, and you think of it as a blueprint now. As, uh, as those, as that catalog starts growing, it becomes your building block for future coding agents to actually use for identifying the problem in your development cycle.
- 17:06
And that's the next thing I'm going to talk about. Um, the solution, uh, that I mentioned so far of a memory is not very fancy vector search or, or a, a vector database that needs to store all the, uh, catalog of, uh, patterns and anti-patterns.
- 17:22
Rather, you can start with just a markdown, uh, files in a, in a centralized Git repo.
- 17:30
Um, as the production findings appear, have the, uh, coding agent put more and more, uh, uh, patterns and anti-patterns into this. And the benefit is that even if one service finds this, even if one, uh, uh, profiling, even if one, uh, service did the profiling to find this pattern, multiple services that in the future are going to
- 17:52
run profiling, the agent that is doing the profiling of that other service can use the pattern catalog from the first service to find the patterns more optimally and not having to redo all the exercise that the first, uh, agent did in order to identify that anti-pattern.
- 18:12
Uh, you might think of like, how, how do I get started with this? Uh, well, y- you don't always have to start fresh, but you could start fresh. There is no harm in having a catalog that is just empty in the beginning, and as more and more pro-profiling happens, uh, more, uh, uh, powerful the, uh, coding agents
- 18:30
that are referring it could become. But there are few, many, in fact, uh, uh, sources of, uh, how you could, uh, public sources of how you could improve your, uh, coding agents.
- 18:40
If you're, uh, into C++ optimizations, Jeff Dean had this wonderful, uh, blog post, uh, around how to, uh, look for, uh, certain, uh, optimization opportunities in your C++ code.
- 18:53
PyTorch has a TorchFix code repo where it catalogs several anti-patterns that could help optimize kernels and, uh, the, uh, model graph of your PyTorch, uh, model. And then you might have your own pl-- uh, performance playbooks as well.
- 19:08
Typically, as your organization grows and your enterprise, uh, software evolves, you end up noting down certain patterns and anti-patterns. Those all could become the bootstrapping point for that, uh, catalog Git repo that I mentioned that can act as a centralized, um, place for all, uh, catalog or all patterns and anti-patterns to be noted.
- 19:32
And what would an entry in that catalog look like? Uh, the example is right here. Uh, as the left-hand side, it mentions the small hints that an LLM, uh, coding agent in the future could use to easily query that, uh, catalog.
- 19:47
It can mention a list of symbols, uh, the services where it was confirmed. Some confidence level is great here as well because as more and more services confirm this, you want to keep updating this so that, uh, the future agents get more and more confident that, okay, this is worth a human, uh, uh, human review, and I
- 20:05
would want to more confidently send out a code review to a human. Uh, I'm still keeping the confidence, uh, bar to just send a code review and not directly, uh, push it to production.
- 20:16
That's by intent. I, uh, I'll talk a little bit on why, but I do feel like there is still need for a human approval because you are modifying an existing code that is running just fine in, in production in order to optimize it, which is, which is very risky.
- 20:30
If you don't know the business context, if you don't have enough test coverage, uh, you might end up breaking. So there is a need for human, uh, to actually be the one responsible for approving that code review.
- 20:41
Uh, and on the right here, I mentioned what the entry in that pattern, anti-pattern catalog could look like. Uh, a anti-pattern and a good pattern so that both the things are well noted here.
- 20:53
Um, so I mentioned a code review and a human, uh, involvement in order to approve and merge that code review is still needed. So how do you optimize for noise there?
- 21:04
There could be enough signals that the, uh, AI agent, uh, could c-- think of, uh, improving, and it could, like, arbitrarily send code reviews for them without knowing enough about, uh, your system.
- 21:16
There are a few tips that I mentioned here could be very powerful in, uh, in making sure that the agent first has enough verifications done before, uh, uh, looking for an human's attention.
- 21:29
The integration tests, unit tests, the most basic functional tests that your, uh, system needs to have should be run ahead of time, uh, by the coding agent itself so that it knows that as it is making code changes to optimize it, it is also not, uh, causing any production, uh, business logic to, uh, fail.
- 21:48
So as, as you have good coverage and unit tests, it gets more confidence that, uh, it gets more confidence that your, um, cha-- that the change it is going to propose is actually right.
- 21:59
Once it has made that, uh, functional correctness check, you still...
- 22:04
Our code coverage isn't typically ideal. There are still surprises in production, uh, and canary deployments could be very powerful in this case. Uh, if you provide enough, uh, automation around this, the canary deployment could be a prerequisite before the code review, uh, uh, requires human attention.
- 22:25
What is a canary? Uh, you typically have as, um, you typically have two machines, one containing your old code, another containing your new code, which could be the performance, uh, fixed, uh, code.
- 22:38
And you send the same traffic to both of them over a period of, let's say, 10 minutes and try to compare, uh, the CPU, uh, usage across, uh, between them.
- 22:51
The comparison report typically is, is what you would want the AI agent to make decision on and judgment on whether, uh, it should open a code review for it.
- 23:02
In this case, the observability report could contain, uh, standard infra, uh, things like how, how much CPU reduction, how much latency reduced, uh, is there an increase in error rate?
- 23:12
If, if that's the case, it should see that as a red signal to not proceed because it might have gotten the business logic incorrect in an attempt to optimize the code.
- 23:23
And what I mentioned here is that this is not an AI problem. The observability, canary, verify logic, these are all standard checks that you need to have in your system.
- 23:32
And then final guardrail, uh, that you want to have is an engineer decision, like I mentioned. Still very important, critical, uh,
- 23:40
in the mix. Um, here's a mental model. Profiler gives the estimate, canary gives ground truth. Uh, canary is the way you verify and evaluate that your, uh, suggested fix is actually, uh, going to improve and have some, uh, positive impact and no negative impact.
- 23:58
An engineer makes the eventual decision. So the, uh, path so far has been about how do you, uh, improve the efficiency of getting from a profiled, uh, profiling data to producing a code review fix.
- 24:18
Uh, that's the re-reactive part that I just covered so far. Uh, which means you have the code already running in production, and now you're trying to improve it. That's a very-- that's typically too late in the game.
- 24:32
Now, anytime you try to change a thing that is running in production in order to improve the performance at it, you have to be very, very careful. So you want that to shift left.
- 24:43
You want that reactive path to be your initial guide to build that initial catalog. And as your pattern catalog grows, you want to move closer and closer to the proactive path, where, uh, as a human or a coding agent authors new code, uh, the s- the reviewer agent could actually look up that catalog and provide an inline,
- 25:05
uh, comment, uh, by understanding the code change and ensure-- and providing a suggestion that, "Hey, based on the pattern catalog and the observed, uh, profiling data that I have, I feel confident that this, uh, is an anti-pattern to introduce.
- 25:20
Can you, uh, rewrite this code?" That could be a, a review comment that a reviewer agent could be, uh, providing.
- 25:29
And if you shift left all the way, like why even wait until a code review? Uh, that, that's where you get the most power. Because you know the anti-patterns are already in a catalog, and if you are using a coding agent to write your code, you could actually ask the coding agent and hook that catalog in it
- 25:50
so that when it is, uh, producing newer tokens and producing newer code, it could actually, before writing out the inefficient code, directly reference the catalog upfront and, uh, and write your, um, code in an optimal way to start with.
- 26:08
Uh, this could sometimes slow down the, uh, speed of, uh, newer code, uh, being written and might end up consuming more tokens. And that's why the pattern catalog needs to be very well, uh, structured and indexed so that the, the way it parses and reads the catalog doesn't fill up the agent context too much, but rather it
- 26:29
can navigate it in a very hierarchical format and only, uh-- and be able to find out the exact, uh, places it needs to look for a, uh, a given pattern or an anti-pattern.
- 26:41
This means that if you can catch this in the code authoring phase itself, you skip all of the unnecessary, uh, overhead of, uh, somebody reviewing your code and providing a, a suggestion or even having that code change reach production.
- 26:56
So the sooner you catch it or even sooner you, uh, uh, introduce that pattern catalog into your software development end-to-end lifecycle, the easier it gets for you to keep the, uh, code and service running optimally.
- 27:13
And, uh, I do want to highlight this, that, uh, it's easier to imagine putting AI agent into every single step of your software development lifecycle for performance improvements, but that's not the intent of this, uh, discussion or the, uh, the thing, uh, or, or the playbook that I'm mentioning.
- 27:30
You still want these foundations very, very right. Your test coverage needs to be rock solid. Uh, business logic all needs to be very well encoded in your test. Your Canary automation needs to be amazing.
- 27:42
Uh, and this is where you don't need AI. You pretty much just want the AI agent to know how to invoke a Canary, where to get the downloaded report from a Canori- Canary, so that it can directly read the numbers from the report and, uh, make a judgment call.
- 27:56
And that pattern catalog that I mentioned is also a foundational piece which needs to be getten-- uh, which, which you need to get right. It, it is by design a Git repo so that it's both a human and a coding agent readable and, uh, authorable, and you could actually have humans also authoring patterns and anti-patterns as they're,
- 28:13
let's say, building new frameworks and new platform components that, uh, they have enough context on at the time of building.
- 28:21
The takeaways, uh, that I do want to mention. First, build your code foundations. Uh, think of, uh, all of the, uh, automation that you could do. Uh, but before introducing an LLM, try to see if there are good, uh, uh, integration points that an agent could, uh, use, such as, uh, can it automatically trigger profiling on an
- 28:43
instance on a, uh, CPU cluster that you have? Can it download the profiling data effectively, uh, then feed it into, uh, an LLM, um, uh, model? And can it, once it has identified the fixes by cloning the Git repo, et cetera, can it actually validate that through a real production canary through shadow traffic or real traffic?
- 29:05
All of those integration and foundation pieces needs to be really good in order for this entire life to life and, uh, this entire, uh, uh, lifecycle improvement that I'm mentioning.
- 29:16
Otherwise, it will just cause more friction and more bugs in the production. So you have to make these, uh, foundation pieces investment a lot, uh, more important. And start from here.
- 29:26
Don't think of, uh, the reactive path as a bad approach. Uh, reactive path is where you want to start with, and then gradually move towards, uh, towards the left and, uh, into the proactive path.
- 29:38
And the other takeaway, like I mentioned, uh, is important, is that as you build this, uh, memory of or essentially a catalog, the, um, the sooner you catch it, the better it gets for your, uh, end-to-end software development lifecycle to have optimus-- uh, optimal code running in production.
- 29:59
Um, this is a, I'll, uh, this is a great mental model for how you step-by-step proceed in automating, um, or improving your, uh, efficiency of software development lifecycle. The current state, uh, which is typically the norm, uh, you spend hours finding the problems.
- 30:15
It's all very manual, no LLM in the mix. Start with introducing an LLM into the mix just for the, um, the identification of, um,
- 30:26
uh, of a potential fix. It might be okay if you are still having to trigger a profiler, uh, and produce, uh, output and feed it into an AI agent and then having to manually run Canary, but it still gives you a lot of, uh, leeway to spend time on the other parts of the workflow as opposed to
- 30:42
just staring at those flame graphs to get the, um hot paths identified.
- 30:48
And then this talk mainly covered the, uh, level two orchestr-uh, tion, which is, um, or level two automation in an agentic spectrum, which is more about the tools, the integrations, the, the key harnesses, and the hooks that a AI agent needs to have in order to, uh, have full power-- uh, in order to have like good, uh,
- 31:10
uh, capability to identify a problem and give you in various development lifecycle areas of, uh, opportunities to, uh, improve your code base. And, uh, once you have this in place, once you have this standard step-by-step workflow, which could be very static, right?
- 31:27
In this case, the workflow that I mentioned is, is very, uh, well-defined, predefined. There is no, uh, uh, LLM to reason and plan and, uh, do the further level of automations.
- 31:39
All it has to do is, uh, you provide a tex-- uh, fixed workflow, which is download the profile, uh, from certain place, um, or rather trigger the profile, download the profile, uh, and then, uh, analyze it, uh, run the canary and provide a suggested fix.
- 31:56
Uh, you could-- Once you have that in place, you could essentially have a scheduled run on your services every week so that it can keep continuously identifying newer problems, uh, that might have not been, uh, uh, uh, or that might have been introduced in the last one week, for example, and keep, uh, the, the identification of the
- 32:18
problem closer to when you wrote that code. And if you were to think of, uh, more automation, uh, in this place, you could, uh,
- 32:28
imagine a, a, a level where the workflow is not very fixed and rather the AI agent has capabilities to even, uh, plan, reason, act, uh, you-- but you have to invest a lot more in evaluation, sandboxing.
- 32:41
Uh, you can't simply run AI agents, um, without the right level of security guardrails so that prompt injection and other security, uh, attacks that a typical, uh, agent infrastructure currently, um, cannot always, uh, solve for.
- 32:58
Uh, those, uh, things need to be heavily invested in if you were to go with level three autonomy. So start with level one, try to move to level two, and you get maximum benefits.
- 33:08
If you need more automation, uh, you could think of the next step, uh, as needed.
- 33:16
Thank you so much. Uh, I hope you got some learnings out of, uh, this small talk that I had. Uh, if, if you want to connect more and connect further, uh, I might end up putting a more detailed blog post on this on my shahrajat.com, uh, personal website.
- 33:32
I'll be happy to connect with you and, uh, provide more information. Take care. Thank you.