WEBVTT

1
00:00:00.000 --> 00:00:06.000
Hi, in this video I'm going to go into more details on the Model Context Protocol,

2
00:00:06.000 --> 00:00:12.000
and in this video specifically about dynamic on-the-fly tools.

3
00:00:12.000 --> 00:00:18.299
So let's jump into some code where we don't have dynamic tools so far,

4
00:00:18.299 --> 00:00:23.299
but we'll put a few things in so they become dynamic.

5
00:00:23.299 --> 00:00:28.200
So in this sample, which is the remote server dynamic tools down here,

6
00:00:28.200 --> 00:00:33.900
I just have a normal MCP server, so we have the builder.addMCPServer

7
00:00:33.900 --> 00:00:38.599
with HTTP to port, so it's a remote server with tools from assembly,

8
00:00:38.599 --> 00:00:41.299
and then we map MCP.

9
00:00:41.299 --> 00:00:46.599
So the absolute minimum you can do, and in here I have three tools,

10
00:00:46.599 --> 00:00:51.700
one called tool1, one called tool2, and admin tool1.

11
00:00:51.700 --> 00:00:59.200
And I've just put in the names in some constants in a file here,

12
00:00:59.200 --> 00:01:04.199
and I put in which of the tools are admin tools.

13
00:01:04.199 --> 00:01:11.199
So if I connect to this, for example via Insomnia, and do the connection,

14
00:01:11.199 --> 00:01:17.000
we can see that we get three tools back, so I can call all three tools,

15
00:01:17.000 --> 00:01:24.900
and when I call tool1, I get a tool1 output, tool2, and get a tool2 output,

16
00:01:24.900 --> 00:01:28.900
and admin tool number 3.

17
00:01:31.000 --> 00:01:37.500
So that's good and well, but in order for us to say we might want to have

18
00:01:37.500 --> 00:01:42.599
certain users to have just tool number 1 and 2, the normal tools,

19
00:01:42.599 --> 00:01:48.300
and a user with more privileges to have the admin tools as well.

20
00:01:48.300 --> 00:01:52.300
So how do we go about doing that?

21
00:01:52.300 --> 00:01:55.300
Well, the first thing we need to do is, of course,

22
00:01:55.300 --> 00:01:59.300
we need to have some kind of authentication.

23
00:01:59.300 --> 00:02:05.800
So in here, we normally put in the builders here, add endpoint filters,

24
00:02:05.800 --> 00:02:10.100
or some of the other ways that you have seen in the previous videos

25
00:02:10.100 --> 00:02:12.500
about authentication.

26
00:02:12.500 --> 00:02:17.800
But in this case, I'm just going to put in an endpoint filter

27
00:02:17.800 --> 00:02:22.600
that have two valid keys, either a normal API key,

28
00:02:22.600 --> 00:02:24.500
which is just normal password in real life,

29
00:02:24.500 --> 00:02:29.000
it would be some kind of grid or something, and an admin key.

30
00:02:29.000 --> 00:02:35.600
And if none of the two are the keys, we just get an unauthorized,

31
00:02:35.600 --> 00:02:41.600
else we get access to the MCP server.

32
00:02:41.600 --> 00:02:47.100
So if we go restart the code, now if we look at Auth,

33
00:02:47.100 --> 00:02:52.600
and I can see we use the normal password, we are logged in,

34
00:02:52.600 --> 00:02:56.600
but we can still see the admin tool, we haven't done anything about that yet.

35
00:02:58.100 --> 00:03:05.100
Or if we take the admin password, we of course also can log in,

36
00:03:05.100 --> 00:03:07.899
and in this case we should of course get all the tools,

37
00:03:07.899 --> 00:03:11.899
but if we put something in that is not correct,

38
00:03:11.899 --> 00:03:15.399
we get an error message, unauthorized here.

39
00:03:16.600 --> 00:03:21.600
So authentication is up and running in a simple manner.

40
00:03:23.600 --> 00:03:27.399
But now we need to take that some of the tools should be there,

41
00:03:27.399 --> 00:03:29.899
and some of them should not be there.

42
00:03:29.899 --> 00:03:33.899
It is possible to use the authentication attribute

43
00:03:33.899 --> 00:03:36.899
if you use OAuth and stuff like that,

44
00:03:36.899 --> 00:03:40.399
but in my case I want to show you that you can control

45
00:03:40.399 --> 00:03:45.899
every single little thing about what goes into the tools

46
00:03:45.899 --> 00:03:48.899
by adding some extra things up here.

47
00:03:48.899 --> 00:03:51.899
Because we can put in something called request filters.

48
00:03:53.399 --> 00:03:57.699
And let me just grab the first request filter that we are going to put in,

49
00:03:57.699 --> 00:03:59.699
and then we will talk about it.

50
00:04:00.699 --> 00:04:05.199
So I just add one more with here.

51
00:04:05.199 --> 00:04:09.199
So I say I want request filters, meaning I want to filter

52
00:04:09.199 --> 00:04:12.199
what happens in the MCP server.

53
00:04:12.699 --> 00:04:15.699
And what I can do, I have a filter builder here,

54
00:04:15.699 --> 00:04:20.700
and I can add various filters for listing of tools,

55
00:04:20.700 --> 00:04:24.200
calling of tools, similar for resources,

56
00:04:24.200 --> 00:04:27.200
and the various things MCP servers can do.

57
00:04:27.200 --> 00:04:30.700
In this case we are only going to do anything with tools.

58
00:04:30.700 --> 00:04:34.700
So tools is essentially two things in an MCP server.

59
00:04:34.700 --> 00:04:38.700
It's the listing of the tools, and it's the calling of the tools.

60
00:04:38.700 --> 00:04:41.700
So what we're doing here is we're going to set a filter

61
00:04:41.700 --> 00:04:44.200
on the listing of the tools.

62
00:04:44.200 --> 00:04:49.200
Because when we go here and log in with a normal user,

63
00:04:49.200 --> 00:04:51.700
we don't want to see this extra tool.

64
00:04:51.700 --> 00:04:55.700
That would only confuse the AI using the MCP server.

65
00:04:55.700 --> 00:04:59.700
Hey, there's a tool, but it's not allowed to call it.

66
00:05:00.700 --> 00:05:03.700
So we want to get rid of that tool on the fly,

67
00:05:03.700 --> 00:05:07.700
and right now we can't because we haven't put anything in.

68
00:05:08.200 --> 00:05:13.200
But what we do is we get a normal next pattern,

69
00:05:13.200 --> 00:05:16.200
the middleware system of .NET,

70
00:05:16.700 --> 00:05:21.700
and whenever we call this next, we actually get all the tools back.

71
00:05:21.700 --> 00:05:25.700
The best way to see this is probably to set some breakpoints.

72
00:05:26.200 --> 00:05:28.700
But before we go through it, let me talk about the code.

73
00:05:28.700 --> 00:05:31.200
So this will actually give us all the tools back

74
00:05:31.200 --> 00:05:34.200
that are registered in this system,

75
00:05:34.200 --> 00:05:37.700
meaning from this with two tools from assembly.

76
00:05:39.200 --> 00:05:42.700
But we need to check what is the user who are actually logged in.

77
00:05:42.700 --> 00:05:47.200
And in order to do that, we use the HTTP context accessor.

78
00:05:47.200 --> 00:05:53.200
Because on the request, we can grab the iTech context accessor

79
00:05:53.200 --> 00:05:58.700
and get something about what the call has been about.

80
00:05:59.200 --> 00:06:02.200
So in our case, we will use the HTTP context,

81
00:06:02.200 --> 00:06:04.700
get the request, and get the header.

82
00:06:04.700 --> 00:06:07.200
Very similar to what we do down here,

83
00:06:07.200 --> 00:06:10.200
only here it's the real context already.

84
00:06:10.200 --> 00:06:13.700
Here we need this access contester before.

85
00:06:14.200 --> 00:06:18.700
And then if we get an API key,

86
00:06:18.700 --> 00:06:22.700
which we should, else we shouldn't have come here this far,

87
00:06:22.700 --> 00:06:27.200
but just the case, and if it's the admin key,

88
00:06:27.200 --> 00:06:30.200
then we just give all the tools back.

89
00:06:30.200 --> 00:06:33.700
But if it's not the admin key, we want to go in and say

90
00:06:33.700 --> 00:06:36.700
all the tools that we have in the result,

91
00:06:36.700 --> 00:06:39.200
meaning all the ones that was found,

92
00:06:39.700 --> 00:06:45.200
only give back the ones that is not contained in the admin tools,

93
00:06:45.200 --> 00:06:49.700
meaning give back this tool, this tool, but not this tool.

94
00:06:50.700 --> 00:06:52.700
And again, this is just a shop.

95
00:06:52.700 --> 00:06:56.700
You could have that certain tools were only available in the start of the month

96
00:06:56.700 --> 00:07:00.200
or whatever you would figure out what to do.

97
00:07:01.200 --> 00:07:04.700
This is a bit cumbersome because it's just authentication,

98
00:07:04.700 --> 00:07:10.700
but you can do whatever you want in these add list filters.

99
00:07:11.700 --> 00:07:14.700
So if we start the code again,

100
00:07:16.200 --> 00:07:19.200
try to do a connection to this one,

101
00:07:19.200 --> 00:07:22.200
and we can see now with a normal password,

102
00:07:23.200 --> 00:07:27.200
we will hit this filter on the fly.

103
00:07:28.200 --> 00:07:31.200
Because it doesn't run at startup, it runs on the fly

104
00:07:31.200 --> 00:07:33.700
because you might need to go down to a database

105
00:07:33.700 --> 00:07:38.200
to check what is the user's permissions and stuff like that.

106
00:07:38.200 --> 00:07:41.200
So everything can be done in here.

107
00:07:41.200 --> 00:07:44.200
So we get our results, and our result makes sense.

108
00:07:44.200 --> 00:07:48.700
We have our three tools, normal and admin tools.

109
00:07:49.200 --> 00:07:53.200
Then we grab the context assessor and the API key.

110
00:07:53.200 --> 00:07:57.200
So we can see that our API key was the normal password,

111
00:07:57.200 --> 00:08:00.200
and since that is not the admin password,

112
00:08:00.200 --> 00:08:04.700
we are sent down here where we actually just take our tools,

113
00:08:04.700 --> 00:08:10.200
but only get the ones that are not admin tools, meaning two tools.

114
00:08:11.200 --> 00:08:16.200
And if we do this, we can now see that I've logged in,

115
00:08:16.200 --> 00:08:18.700
but only with those two tools.

116
00:08:18.700 --> 00:08:21.200
Let's get rid of the breakpoints,

117
00:08:21.200 --> 00:08:26.200
and try to log in as the admin user instead.

118
00:08:27.200 --> 00:08:32.200
If we do that, we get the third tool back.

119
00:08:32.200 --> 00:08:38.200
Because in that case, we hit this if statement, it was true,

120
00:08:38.200 --> 00:08:41.200
so we just gave all the tools back.

121
00:08:42.200 --> 00:08:48.200
So some of you might think now, okay, now we're done, it's okay.

122
00:08:48.200 --> 00:08:54.200
But actually, this is just the listing of the tools.

123
00:08:54.700 --> 00:09:00.200
And most MCP servers would never be able to call a tool that hasn't listed,

124
00:09:00.200 --> 00:09:04.200
but you can technically do it if you begin to write code.

125
00:09:04.200 --> 00:09:09.200
So this is not enough to secure this system.

126
00:09:09.200 --> 00:09:13.700
We need to make sure that this tool cannot be called,

127
00:09:13.700 --> 00:09:17.700
even if it's not even listed in the system.

128
00:09:18.200 --> 00:09:23.200
So for that, we need one more builder.

129
00:09:24.200 --> 00:09:28.200
So let me bring in the last filter we need.

130
00:09:28.200 --> 00:09:32.200
And that should be in here.

131
00:09:32.200 --> 00:09:38.200
So we also add a filter for the add tool call filter.

132
00:09:38.200 --> 00:09:45.700
And in this case, we just say if the tool that we call inside MCP,

133
00:09:45.700 --> 00:09:47.700
they are called match primitives,

134
00:09:47.700 --> 00:09:51.200
this is the common word for resources, tools, and so on.

135
00:09:51.200 --> 00:09:55.200
So if it's an admin tool that we're calling,

136
00:09:55.200 --> 00:10:00.200
then we need to double-check that we can actually allow to call it,

137
00:10:00.200 --> 00:10:04.200
else we can just do the normal await next.

138
00:10:05.200 --> 00:10:07.200
And in here, we do exactly the same,

139
00:10:07.200 --> 00:10:11.700
we just get what the given API key was for the call,

140
00:10:11.700 --> 00:10:13.200
and check if we are admin.

141
00:10:13.200 --> 00:10:17.200
And if we are not admin, we throw an exception

142
00:10:17.200 --> 00:10:19.200
that we are not allowed to call this tool.

143
00:10:20.200 --> 00:10:24.200
So right now, I can't really show you this,

144
00:10:24.200 --> 00:10:26.700
unless I actually take away the filter,

145
00:10:26.700 --> 00:10:31.200
because Insomnia that I use for the testing of the MCPs

146
00:10:31.200 --> 00:10:33.200
will not be able to.

147
00:10:33.700 --> 00:10:40.700
But if I do it like this, and add a breakpoint here,

148
00:10:40.700 --> 00:10:47.700
we can now go in, disconnect, log in as a normal user.

149
00:10:50.200 --> 00:10:54.200
And a normal user in this case will get all tools,

150
00:10:54.200 --> 00:10:58.200
because we just removed the list part filtering.

151
00:10:58.200 --> 00:11:01.700
So we could have access to this tool,

152
00:11:01.700 --> 00:11:05.700
and when we call it, again, the filters will be hit.

153
00:11:06.200 --> 00:11:11.200
This tool we can see is the admin tool I called.

154
00:11:12.200 --> 00:11:15.700
I will check, I put in the normal password.

155
00:11:15.700 --> 00:11:18.200
Am I an admin? No.

156
00:11:18.200 --> 00:11:21.200
Then we are not allowed to call the tool.

157
00:11:21.700 --> 00:11:26.700
Meaning, back here, we get we are not allowed to call that tool.

158
00:11:28.200 --> 00:11:31.200
If I put in the admin instead,

159
00:11:36.200 --> 00:11:38.200
and call the tool,

160
00:11:42.200 --> 00:11:46.200
we see the admin password, we are admin, so we allow it.

161
00:11:47.200 --> 00:11:50.700
And of course, if we just call one of the normal tools,

162
00:11:50.700 --> 00:11:54.200
we will not even go into this section where we check,

163
00:11:54.200 --> 00:11:57.700
because it's just one of the tools everyone is allowed to call.

164
00:12:00.200 --> 00:12:04.200
So, in summary, if we put this back in,

165
00:12:05.200 --> 00:12:09.200
this is how you will see the sample up in GitHub.

166
00:12:10.700 --> 00:12:15.200
We add this request filters, and again, we can do all kinds of things here.

167
00:12:15.200 --> 00:12:20.200
We could make a tool only visible on Fridays for some reason,

168
00:12:21.700 --> 00:12:24.700
or whatever we want to do, we can go down to a database,

169
00:12:24.700 --> 00:12:28.700
check if we have access or not, and so on and so forth.

170
00:12:29.200 --> 00:12:35.200
And if we do that, and we then call our tool,

171
00:12:35.700 --> 00:12:41.200
if there's a way we get around this, we still lock the user.

172
00:12:42.200 --> 00:12:48.200
And in order to get authentication in the first place,

173
00:12:48.200 --> 00:12:50.200
we just add the endpoint filter,

174
00:12:50.200 --> 00:12:54.700
or one of the other ones from the previous videos

175
00:12:54.700 --> 00:12:58.200
on how to do authentication for an MCP.

176
00:12:59.700 --> 00:13:03.200
So, this is how you can make dynamic tool calls,

177
00:13:03.200 --> 00:13:06.200
and on the fly say, some users have these tools,

178
00:13:06.200 --> 00:13:09.700
some users have these tools, depending on what they want.

179
00:13:10.200 --> 00:13:18.700
Because now I'm doing it with a user that needs to have various credentials,

180
00:13:18.700 --> 00:13:21.700
but it could also be that you want to have an MCP server

181
00:13:21.700 --> 00:13:25.700
where the user in their configuration of the MCP server

182
00:13:26.200 --> 00:13:30.200
should be able to say, I want these tools, I don't want these tools,

183
00:13:30.200 --> 00:13:33.700
I'm this type of user, only give these tools back.

184
00:13:33.700 --> 00:13:40.200
So, that's the reason why, when we have normal C Sharp code here,

185
00:13:40.200 --> 00:13:45.200
where we can do anything, we have full control over what tools to go.

186
00:13:45.700 --> 00:13:48.200
So, that's everything. See you on the next one.

