16 #include "tensorflow_serving/model_servers/http_rest_api_util.h"
20 #include <gmock/gmock.h>
21 #include <gtest/gtest.h>
22 #include "tensorflow/core/lib/core/status_test_util.h"
23 #include "tensorflow_serving/test_util/test_util.h"
25 namespace tensorflow {
29 using ::testing::HasSubstr;
31 class HttpRestApiUtilTest :
public ::testing::Test {};
33 TEST_F(HttpRestApiUtilTest, TestParseModelInfoForGet) {
35 absl::optional<int64_t> model_version;
36 absl::optional<string> model_version_label;
38 string model_subresource;
39 bool parse_successful;
42 const absl::string_view request_path_1 =
44 "modelname%21%23%24%25%26%27%28%29%2A%2B%2C%2F%3A%3B%3D%3F%40%5B%5D";
45 TF_EXPECT_OK(ParseModelInfo(
"GET", request_path_1, &model_name,
46 &model_version, &model_version_label, &method,
47 &model_subresource, &parse_successful));
48 EXPECT_EQ(model_name,
"modelname!#$%&'()*+,/:;=?@[]");
49 EXPECT_TRUE(parse_successful);
52 const absl::string_view request_path_2 =
"/v1/models/modelname/versions/99";
53 TF_EXPECT_OK(ParseModelInfo(
"GET", request_path_2, &model_name,
54 &model_version, &model_version_label, &method,
55 &model_subresource, &parse_successful));
56 EXPECT_EQ(model_name,
"modelname");
57 EXPECT_EQ(model_version.value(), 99);
58 EXPECT_TRUE(parse_successful);
61 const absl::string_view request_path_3 =
"/v1/models/modelname/labels/latest";
62 TF_EXPECT_OK(ParseModelInfo(
"GET", request_path_3, &model_name,
63 &model_version, &model_version_label, &method,
64 &model_subresource, &parse_successful));
65 EXPECT_EQ(model_name,
"modelname");
66 EXPECT_EQ(model_version_label.value(),
"latest");
67 EXPECT_TRUE(parse_successful);
70 const absl::string_view request_path_4 =
71 "/v1/models/modelname/labels/"
72 "latest%21%23%24%25%26%27%28%29%2A%2B%2C%2F%3A%3B%3D%3F%40%5B%5D";
73 TF_EXPECT_OK(ParseModelInfo(
"GET", request_path_4, &model_name,
74 &model_version, &model_version_label, &method,
75 &model_subresource, &parse_successful));
76 EXPECT_EQ(model_name,
"modelname");
77 EXPECT_EQ(model_version_label.value(),
"latest!#$%&'()*+,/:;=?@[]");
78 EXPECT_TRUE(parse_successful);
81 const absl::string_view request_path_5 =
82 "/v1/models/modelname/labels/latest/metadata";
83 TF_EXPECT_OK(ParseModelInfo(
"GET", request_path_5, &model_name,
84 &model_version, &model_version_label, &method,
85 &model_subresource, &parse_successful));
86 EXPECT_EQ(model_name,
"modelname");
87 EXPECT_EQ(model_version_label.value(),
"latest");
88 EXPECT_EQ(model_subresource,
"metadata");
89 EXPECT_TRUE(parse_successful);
92 const absl::string_view request_path_6 =
94 "modelname%21%23%24%25%26%27%28%29%2A%2B%2C%2F%3A%3B%3D%3F%40%5B%5D/"
95 "labels/latest%21%23%24%25%26%27%28%29%2A%2B%2C%2F%3A%3B%3D%3F%40%5B%5D/"
97 TF_EXPECT_OK(ParseModelInfo(
"GET", request_path_6, &model_name,
98 &model_version, &model_version_label, &method,
99 &model_subresource, &parse_successful));
100 EXPECT_EQ(model_name,
"modelname!#$%&'()*+,/:;=?@[]");
101 EXPECT_EQ(model_version_label.value(),
"latest!#$%&'()*+,/:;=?@[]");
102 EXPECT_EQ(model_subresource,
"metadata");
103 EXPECT_TRUE(parse_successful);
106 TF_EXPECT_OK(ParseModelInfo(
"GET",
"/v1/foo", &model_name, &model_version,
107 &model_version_label, &method, &model_subresource,
109 EXPECT_FALSE(parse_successful);
110 TF_EXPECT_OK(ParseModelInfo(
"GET",
"/v1/models/foo:predict", &model_name,
111 &model_version, &model_version_label, &method,
112 &model_subresource, &parse_successful));
113 EXPECT_FALSE(parse_successful);
114 TF_EXPECT_OK(ParseModelInfo(
"GET",
"/v1/models/foo/version/50:predict",
115 &model_name, &model_version, &model_version_label,
116 &method, &model_subresource, &parse_successful));
117 EXPECT_FALSE(parse_successful);
120 TEST_F(HttpRestApiUtilTest, TestParseModelInfoForPost) {
122 absl::optional<int64_t> model_version;
123 absl::optional<string> model_version_label;
125 string model_subresource;
126 bool parse_successful;
129 const absl::string_view request_path_1 =
131 "modelname%21%23%24%25%26%27%28%29%2A%2B%2C%2F%3A%3B%3D%3F%40%5B%5D:"
133 TF_EXPECT_OK(ParseModelInfo(
"POST", request_path_1, &model_name,
134 &model_version, &model_version_label, &method,
135 &model_subresource, &parse_successful));
136 EXPECT_EQ(model_name,
"modelname!#$%&'()*+,/:;=?@[]");
137 EXPECT_EQ(method,
"predict");
138 EXPECT_TRUE(parse_successful);
141 const absl::string_view request_path_2 =
142 "/v1/models/modelname/versions/99:predict";
143 TF_EXPECT_OK(ParseModelInfo(
"POST", request_path_2, &model_name,
144 &model_version, &model_version_label, &method,
145 &model_subresource, &parse_successful));
146 EXPECT_EQ(model_name,
"modelname");
147 EXPECT_EQ(model_version.value(), 99);
148 EXPECT_EQ(method,
"predict");
149 EXPECT_TRUE(parse_successful);
152 const absl::string_view request_path_3 =
153 "/v1/models/modelname/labels/latest:predict";
154 TF_EXPECT_OK(ParseModelInfo(
"POST", request_path_3, &model_name,
155 &model_version, &model_version_label, &method,
156 &model_subresource, &parse_successful));
157 EXPECT_EQ(model_name,
"modelname");
158 EXPECT_EQ(model_version_label.value(),
"latest");
159 EXPECT_EQ(method,
"predict");
160 EXPECT_TRUE(parse_successful);
163 const absl::string_view request_path_4 =
164 "/v1/models/modelname/labels/"
165 "latest%21%23%24%25%26%27%28%29%2A%2B%2C%2F%3A%3B%3D%3F%40%5B%5D:predict";
166 TF_EXPECT_OK(ParseModelInfo(
"POST", request_path_4, &model_name,
167 &model_version, &model_version_label, &method,
168 &model_subresource, &parse_successful));
169 EXPECT_EQ(model_name,
"modelname");
170 EXPECT_EQ(model_version_label.value(),
"latest!#$%&'()*+,/:;=?@[]");
171 EXPECT_EQ(method,
"predict");
172 EXPECT_TRUE(parse_successful);
175 const absl::string_view request_path_6 =
177 "modelname%21%23%24%25%26%27%28%29%2A%2B%2C%2F%3A%3B%3D%3F%40%5B%5D/"
179 "latest%21%23%24%25%26%27%28%29%2A%2B%2C%2F%3A%3B%3D%3F%40%5B%5D:predict";
180 TF_EXPECT_OK(ParseModelInfo(
"POST", request_path_6, &model_name,
181 &model_version, &model_version_label, &method,
182 &model_subresource, &parse_successful));
183 EXPECT_EQ(model_name,
"modelname!#$%&'()*+,/:;=?@[]");
184 EXPECT_EQ(model_version_label.value(),
"latest!#$%&'()*+,/:;=?@[]");
185 EXPECT_EQ(method,
"predict");
186 EXPECT_TRUE(parse_successful);
189 TF_EXPECT_OK(ParseModelInfo(
"POST",
"/v1/foo", &model_name, &model_version,
190 &model_version_label, &method, &model_subresource,
192 EXPECT_FALSE(parse_successful);
193 TF_EXPECT_OK(ParseModelInfo(
"POST",
"/v1/models", &model_name, &model_version,
194 &model_version_label, &method, &model_subresource,
196 EXPECT_FALSE(parse_successful);
197 TF_EXPECT_OK(ParseModelInfo(
"POST",
"/v1/models/foo/version/50:predict",
198 &model_name, &model_version, &model_version_label,
199 &method, &model_subresource, &parse_successful));
200 EXPECT_FALSE(parse_successful);
201 TF_EXPECT_OK(ParseModelInfo(
"POST",
"/v1/models/foo/versions/string:predict",
202 &model_name, &model_version, &model_version_label,
203 &method, &model_subresource, &parse_successful));
204 EXPECT_FALSE(parse_successful);
205 auto status = ParseModelInfo(
207 absl::StrCat(
"/v1/models/foo/versions/",
208 std::numeric_limits<uint64_t>::max(),
":predict"),
209 &model_name, &model_version, &model_version_label, &method,
210 &model_subresource, &parse_successful);
211 EXPECT_TRUE(parse_successful);
212 EXPECT_TRUE(errors::IsInvalidArgument(status));
213 EXPECT_THAT(status.message(), HasSubstr(
"Failed to convert version"));
214 TF_EXPECT_OK(ParseModelInfo(
"POST",
"/v1/models/foo/metadata", &model_name,
215 &model_version, &model_version_label, &method,
216 &model_subresource, &parse_successful));
217 EXPECT_FALSE(parse_successful);
218 TF_EXPECT_OK(ParseModelInfo(
219 "POST",
"/v1/models/foo/versions/50/labels/some_label:regress",
220 &model_name, &model_version, &model_version_label, &method,
221 &model_subresource, &parse_successful));
222 EXPECT_FALSE(parse_successful);