xref: /aosp_15_r20/external/grpc-grpc/test/cpp/util/cli_credentials.cc (revision cc02d7e222339f7a4f6ba5f422e6413f4bd931f2)
1*cc02d7e2SAndroid Build Coastguard Worker //
2*cc02d7e2SAndroid Build Coastguard Worker //
3*cc02d7e2SAndroid Build Coastguard Worker // Copyright 2016 gRPC authors.
4*cc02d7e2SAndroid Build Coastguard Worker //
5*cc02d7e2SAndroid Build Coastguard Worker // Licensed under the Apache License, Version 2.0 (the "License");
6*cc02d7e2SAndroid Build Coastguard Worker // you may not use this file except in compliance with the License.
7*cc02d7e2SAndroid Build Coastguard Worker // You may obtain a copy of the License at
8*cc02d7e2SAndroid Build Coastguard Worker //
9*cc02d7e2SAndroid Build Coastguard Worker //     http://www.apache.org/licenses/LICENSE-2.0
10*cc02d7e2SAndroid Build Coastguard Worker //
11*cc02d7e2SAndroid Build Coastguard Worker // Unless required by applicable law or agreed to in writing, software
12*cc02d7e2SAndroid Build Coastguard Worker // distributed under the License is distributed on an "AS IS" BASIS,
13*cc02d7e2SAndroid Build Coastguard Worker // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14*cc02d7e2SAndroid Build Coastguard Worker // See the License for the specific language governing permissions and
15*cc02d7e2SAndroid Build Coastguard Worker // limitations under the License.
16*cc02d7e2SAndroid Build Coastguard Worker //
17*cc02d7e2SAndroid Build Coastguard Worker //
18*cc02d7e2SAndroid Build Coastguard Worker 
19*cc02d7e2SAndroid Build Coastguard Worker #include "test/cpp/util/cli_credentials.h"
20*cc02d7e2SAndroid Build Coastguard Worker 
21*cc02d7e2SAndroid Build Coastguard Worker #include "absl/flags/flag.h"
22*cc02d7e2SAndroid Build Coastguard Worker 
23*cc02d7e2SAndroid Build Coastguard Worker #include <grpc/slice.h>
24*cc02d7e2SAndroid Build Coastguard Worker #include <grpc/support/log.h>
25*cc02d7e2SAndroid Build Coastguard Worker #include <grpcpp/support/slice.h>
26*cc02d7e2SAndroid Build Coastguard Worker 
27*cc02d7e2SAndroid Build Coastguard Worker #include "src/core/lib/gprpp/crash.h"
28*cc02d7e2SAndroid Build Coastguard Worker #include "src/core/lib/gprpp/load_file.h"
29*cc02d7e2SAndroid Build Coastguard Worker 
30*cc02d7e2SAndroid Build Coastguard Worker ABSL_RETIRED_FLAG(bool, enable_ssl, false,
31*cc02d7e2SAndroid Build Coastguard Worker                   "Replaced by --channel_creds_type=ssl.");
32*cc02d7e2SAndroid Build Coastguard Worker ABSL_RETIRED_FLAG(bool, use_auth, false,
33*cc02d7e2SAndroid Build Coastguard Worker                   "Replaced by --channel_creds_type=gdc.");
34*cc02d7e2SAndroid Build Coastguard Worker ABSL_RETIRED_FLAG(std::string, access_token, "",
35*cc02d7e2SAndroid Build Coastguard Worker                   "Replaced by --call_creds=access_token=<token>.");
36*cc02d7e2SAndroid Build Coastguard Worker ABSL_FLAG(
37*cc02d7e2SAndroid Build Coastguard Worker     std::string, ssl_target, "",
38*cc02d7e2SAndroid Build Coastguard Worker     "If not empty, treat the server host name as this for ssl/tls certificate "
39*cc02d7e2SAndroid Build Coastguard Worker     "validation.");
40*cc02d7e2SAndroid Build Coastguard Worker ABSL_FLAG(
41*cc02d7e2SAndroid Build Coastguard Worker     std::string, ssl_client_cert, "",
42*cc02d7e2SAndroid Build Coastguard Worker     "If not empty, load this PEM formatted client certificate file. Requires "
43*cc02d7e2SAndroid Build Coastguard Worker     "use of --ssl_client_key.");
44*cc02d7e2SAndroid Build Coastguard Worker ABSL_FLAG(std::string, ssl_client_key, "",
45*cc02d7e2SAndroid Build Coastguard Worker           "If not empty, load this PEM formatted private key. Requires use of "
46*cc02d7e2SAndroid Build Coastguard Worker           "--ssl_client_cert");
47*cc02d7e2SAndroid Build Coastguard Worker ABSL_FLAG(
48*cc02d7e2SAndroid Build Coastguard Worker     std::string, local_connect_type, "local_tcp",
49*cc02d7e2SAndroid Build Coastguard Worker     "The type of local connections for which local channel credentials will "
50*cc02d7e2SAndroid Build Coastguard Worker     "be applied. Should be local_tcp or uds.");
51*cc02d7e2SAndroid Build Coastguard Worker ABSL_FLAG(
52*cc02d7e2SAndroid Build Coastguard Worker     std::string, channel_creds_type, "",
53*cc02d7e2SAndroid Build Coastguard Worker     "The channel creds type: insecure, ssl, gdc (Google Default Credentials), "
54*cc02d7e2SAndroid Build Coastguard Worker     "alts, or local.");
55*cc02d7e2SAndroid Build Coastguard Worker ABSL_FLAG(
56*cc02d7e2SAndroid Build Coastguard Worker     std::string, call_creds, "",
57*cc02d7e2SAndroid Build Coastguard Worker     "Call credentials to use: none (default), or access_token=<token>. If "
58*cc02d7e2SAndroid Build Coastguard Worker     "provided, the call creds are composited on top of channel creds.");
59*cc02d7e2SAndroid Build Coastguard Worker 
60*cc02d7e2SAndroid Build Coastguard Worker namespace grpc {
61*cc02d7e2SAndroid Build Coastguard Worker namespace testing {
62*cc02d7e2SAndroid Build Coastguard Worker 
63*cc02d7e2SAndroid Build Coastguard Worker namespace {
64*cc02d7e2SAndroid Build Coastguard Worker 
65*cc02d7e2SAndroid Build Coastguard Worker const char ACCESS_TOKEN_PREFIX[] = "access_token=";
66*cc02d7e2SAndroid Build Coastguard Worker constexpr int ACCESS_TOKEN_PREFIX_LEN =
67*cc02d7e2SAndroid Build Coastguard Worker     sizeof(ACCESS_TOKEN_PREFIX) / sizeof(*ACCESS_TOKEN_PREFIX) - 1;
68*cc02d7e2SAndroid Build Coastguard Worker 
IsAccessToken(const std::string & auth)69*cc02d7e2SAndroid Build Coastguard Worker bool IsAccessToken(const std::string& auth) {
70*cc02d7e2SAndroid Build Coastguard Worker   return auth.length() > ACCESS_TOKEN_PREFIX_LEN &&
71*cc02d7e2SAndroid Build Coastguard Worker          auth.compare(0, ACCESS_TOKEN_PREFIX_LEN, ACCESS_TOKEN_PREFIX) == 0;
72*cc02d7e2SAndroid Build Coastguard Worker }
73*cc02d7e2SAndroid Build Coastguard Worker 
AccessToken(const std::string & auth)74*cc02d7e2SAndroid Build Coastguard Worker std::string AccessToken(const std::string& auth) {
75*cc02d7e2SAndroid Build Coastguard Worker   if (!IsAccessToken(auth)) {
76*cc02d7e2SAndroid Build Coastguard Worker     return "";
77*cc02d7e2SAndroid Build Coastguard Worker   }
78*cc02d7e2SAndroid Build Coastguard Worker   return std::string(auth, ACCESS_TOKEN_PREFIX_LEN);
79*cc02d7e2SAndroid Build Coastguard Worker }
80*cc02d7e2SAndroid Build Coastguard Worker 
81*cc02d7e2SAndroid Build Coastguard Worker }  // namespace
82*cc02d7e2SAndroid Build Coastguard Worker 
GetDefaultChannelCredsType() const83*cc02d7e2SAndroid Build Coastguard Worker std::string CliCredentials::GetDefaultChannelCredsType() const {
84*cc02d7e2SAndroid Build Coastguard Worker   return "insecure";
85*cc02d7e2SAndroid Build Coastguard Worker }
86*cc02d7e2SAndroid Build Coastguard Worker 
GetDefaultCallCreds() const87*cc02d7e2SAndroid Build Coastguard Worker std::string CliCredentials::GetDefaultCallCreds() const { return "none"; }
88*cc02d7e2SAndroid Build Coastguard Worker 
89*cc02d7e2SAndroid Build Coastguard Worker std::shared_ptr<grpc::ChannelCredentials>
GetChannelCredentials() const90*cc02d7e2SAndroid Build Coastguard Worker CliCredentials::GetChannelCredentials() const {
91*cc02d7e2SAndroid Build Coastguard Worker   if (absl::GetFlag(FLAGS_channel_creds_type) == "insecure") {
92*cc02d7e2SAndroid Build Coastguard Worker     return grpc::InsecureChannelCredentials();
93*cc02d7e2SAndroid Build Coastguard Worker   } else if (absl::GetFlag(FLAGS_channel_creds_type) == "ssl") {
94*cc02d7e2SAndroid Build Coastguard Worker     grpc::SslCredentialsOptions ssl_creds_options;
95*cc02d7e2SAndroid Build Coastguard Worker     // TODO(@Capstan): This won't affect Google Default Credentials using SSL.
96*cc02d7e2SAndroid Build Coastguard Worker     if (!absl::GetFlag(FLAGS_ssl_client_cert).empty()) {
97*cc02d7e2SAndroid Build Coastguard Worker       auto cert = grpc_core::LoadFile(absl::GetFlag(FLAGS_ssl_client_cert),
98*cc02d7e2SAndroid Build Coastguard Worker                                       /*add_null_terminator=*/false);
99*cc02d7e2SAndroid Build Coastguard Worker       if (!cert.ok()) {
100*cc02d7e2SAndroid Build Coastguard Worker         gpr_log(GPR_ERROR, "error loading file %s: %s",
101*cc02d7e2SAndroid Build Coastguard Worker                 absl::GetFlag(FLAGS_ssl_client_cert).c_str(),
102*cc02d7e2SAndroid Build Coastguard Worker                 cert.status().ToString().c_str());
103*cc02d7e2SAndroid Build Coastguard Worker       } else {
104*cc02d7e2SAndroid Build Coastguard Worker         ssl_creds_options.pem_cert_chain = std::string(cert->as_string_view());
105*cc02d7e2SAndroid Build Coastguard Worker       }
106*cc02d7e2SAndroid Build Coastguard Worker     }
107*cc02d7e2SAndroid Build Coastguard Worker     if (!absl::GetFlag(FLAGS_ssl_client_key).empty()) {
108*cc02d7e2SAndroid Build Coastguard Worker       auto key = grpc_core::LoadFile(absl::GetFlag(FLAGS_ssl_client_key),
109*cc02d7e2SAndroid Build Coastguard Worker                                      /*add_null_terminator=*/false);
110*cc02d7e2SAndroid Build Coastguard Worker       if (!key.ok()) {
111*cc02d7e2SAndroid Build Coastguard Worker         gpr_log(GPR_ERROR, "error loading file %s: %s",
112*cc02d7e2SAndroid Build Coastguard Worker                 absl::GetFlag(FLAGS_ssl_client_key).c_str(),
113*cc02d7e2SAndroid Build Coastguard Worker                 key.status().ToString().c_str());
114*cc02d7e2SAndroid Build Coastguard Worker       } else {
115*cc02d7e2SAndroid Build Coastguard Worker         ssl_creds_options.pem_private_key = std::string(key->as_string_view());
116*cc02d7e2SAndroid Build Coastguard Worker       }
117*cc02d7e2SAndroid Build Coastguard Worker     }
118*cc02d7e2SAndroid Build Coastguard Worker     return grpc::SslCredentials(ssl_creds_options);
119*cc02d7e2SAndroid Build Coastguard Worker   } else if (absl::GetFlag(FLAGS_channel_creds_type) == "gdc") {
120*cc02d7e2SAndroid Build Coastguard Worker     return grpc::GoogleDefaultCredentials();
121*cc02d7e2SAndroid Build Coastguard Worker   } else if (absl::GetFlag(FLAGS_channel_creds_type) == "alts") {
122*cc02d7e2SAndroid Build Coastguard Worker     return grpc::experimental::AltsCredentials(
123*cc02d7e2SAndroid Build Coastguard Worker         grpc::experimental::AltsCredentialsOptions());
124*cc02d7e2SAndroid Build Coastguard Worker   } else if (absl::GetFlag(FLAGS_channel_creds_type) == "local") {
125*cc02d7e2SAndroid Build Coastguard Worker     if (absl::GetFlag(FLAGS_local_connect_type) == "local_tcp") {
126*cc02d7e2SAndroid Build Coastguard Worker       return grpc::experimental::LocalCredentials(LOCAL_TCP);
127*cc02d7e2SAndroid Build Coastguard Worker     } else if (absl::GetFlag(FLAGS_local_connect_type) == "uds") {
128*cc02d7e2SAndroid Build Coastguard Worker       return grpc::experimental::LocalCredentials(UDS);
129*cc02d7e2SAndroid Build Coastguard Worker     } else {
130*cc02d7e2SAndroid Build Coastguard Worker       fprintf(stderr,
131*cc02d7e2SAndroid Build Coastguard Worker               "--local_connect_type=%s invalid; must be local_tcp or uds.\n",
132*cc02d7e2SAndroid Build Coastguard Worker               absl::GetFlag(FLAGS_local_connect_type).c_str());
133*cc02d7e2SAndroid Build Coastguard Worker     }
134*cc02d7e2SAndroid Build Coastguard Worker   }
135*cc02d7e2SAndroid Build Coastguard Worker   fprintf(stderr,
136*cc02d7e2SAndroid Build Coastguard Worker           "--channel_creds_type=%s invalid; must be insecure, ssl, gdc, "
137*cc02d7e2SAndroid Build Coastguard Worker           "alts, or local.\n",
138*cc02d7e2SAndroid Build Coastguard Worker           absl::GetFlag(FLAGS_channel_creds_type).c_str());
139*cc02d7e2SAndroid Build Coastguard Worker   return std::shared_ptr<grpc::ChannelCredentials>();
140*cc02d7e2SAndroid Build Coastguard Worker }
141*cc02d7e2SAndroid Build Coastguard Worker 
GetCallCredentials() const142*cc02d7e2SAndroid Build Coastguard Worker std::shared_ptr<grpc::CallCredentials> CliCredentials::GetCallCredentials()
143*cc02d7e2SAndroid Build Coastguard Worker     const {
144*cc02d7e2SAndroid Build Coastguard Worker   if (IsAccessToken(absl::GetFlag(FLAGS_call_creds))) {
145*cc02d7e2SAndroid Build Coastguard Worker     return grpc::AccessTokenCredentials(
146*cc02d7e2SAndroid Build Coastguard Worker         AccessToken(absl::GetFlag(FLAGS_call_creds)));
147*cc02d7e2SAndroid Build Coastguard Worker   }
148*cc02d7e2SAndroid Build Coastguard Worker   if (absl::GetFlag(FLAGS_call_creds) == "none") {
149*cc02d7e2SAndroid Build Coastguard Worker     // Nothing to do; creds, if any, are baked into the channel.
150*cc02d7e2SAndroid Build Coastguard Worker     return std::shared_ptr<grpc::CallCredentials>();
151*cc02d7e2SAndroid Build Coastguard Worker   }
152*cc02d7e2SAndroid Build Coastguard Worker   fprintf(stderr,
153*cc02d7e2SAndroid Build Coastguard Worker           "--call_creds=%s invalid; must be none "
154*cc02d7e2SAndroid Build Coastguard Worker           "or access_token=<token>.\n",
155*cc02d7e2SAndroid Build Coastguard Worker           absl::GetFlag(FLAGS_call_creds).c_str());
156*cc02d7e2SAndroid Build Coastguard Worker   return std::shared_ptr<grpc::CallCredentials>();
157*cc02d7e2SAndroid Build Coastguard Worker }
158*cc02d7e2SAndroid Build Coastguard Worker 
GetCredentials() const159*cc02d7e2SAndroid Build Coastguard Worker std::shared_ptr<grpc::ChannelCredentials> CliCredentials::GetCredentials()
160*cc02d7e2SAndroid Build Coastguard Worker     const {
161*cc02d7e2SAndroid Build Coastguard Worker   if (absl::GetFlag(FLAGS_call_creds).empty()) {
162*cc02d7e2SAndroid Build Coastguard Worker     absl::SetFlag(&FLAGS_call_creds, GetDefaultCallCreds());
163*cc02d7e2SAndroid Build Coastguard Worker   }
164*cc02d7e2SAndroid Build Coastguard Worker   if (absl::GetFlag(FLAGS_channel_creds_type).empty()) {
165*cc02d7e2SAndroid Build Coastguard Worker     absl::SetFlag(&FLAGS_channel_creds_type, GetDefaultChannelCredsType());
166*cc02d7e2SAndroid Build Coastguard Worker   }
167*cc02d7e2SAndroid Build Coastguard Worker   std::shared_ptr<grpc::ChannelCredentials> channel_creds =
168*cc02d7e2SAndroid Build Coastguard Worker       GetChannelCredentials();
169*cc02d7e2SAndroid Build Coastguard Worker   // Composite any call-type credentials on top of the base channel.
170*cc02d7e2SAndroid Build Coastguard Worker   std::shared_ptr<grpc::CallCredentials> call_creds = GetCallCredentials();
171*cc02d7e2SAndroid Build Coastguard Worker   return (channel_creds == nullptr || call_creds == nullptr)
172*cc02d7e2SAndroid Build Coastguard Worker              ? channel_creds
173*cc02d7e2SAndroid Build Coastguard Worker              : grpc::CompositeChannelCredentials(channel_creds, call_creds);
174*cc02d7e2SAndroid Build Coastguard Worker }
175*cc02d7e2SAndroid Build Coastguard Worker 
GetCredentialUsage() const176*cc02d7e2SAndroid Build Coastguard Worker std::string CliCredentials::GetCredentialUsage() const {
177*cc02d7e2SAndroid Build Coastguard Worker   return "    --ssl_target             ; Set server host for ssl validation\n"
178*cc02d7e2SAndroid Build Coastguard Worker          "    --ssl_client_cert        ; Client cert for ssl\n"
179*cc02d7e2SAndroid Build Coastguard Worker          "    --ssl_client_key         ; Client private key for ssl\n"
180*cc02d7e2SAndroid Build Coastguard Worker          "    --local_connect_type     ; Set to local_tcp or uds\n"
181*cc02d7e2SAndroid Build Coastguard Worker          "    --channel_creds_type     ; Set to insecure, ssl, gdc, alts, or "
182*cc02d7e2SAndroid Build Coastguard Worker          "local\n"
183*cc02d7e2SAndroid Build Coastguard Worker          "    --call_creds             ; Set to none, or"
184*cc02d7e2SAndroid Build Coastguard Worker          " access_token=<token>\n";
185*cc02d7e2SAndroid Build Coastguard Worker }
186*cc02d7e2SAndroid Build Coastguard Worker 
GetSslTargetNameOverride() const187*cc02d7e2SAndroid Build Coastguard Worker std::string CliCredentials::GetSslTargetNameOverride() const {
188*cc02d7e2SAndroid Build Coastguard Worker   bool use_ssl = absl::GetFlag(FLAGS_channel_creds_type) == "ssl" ||
189*cc02d7e2SAndroid Build Coastguard Worker                  absl::GetFlag(FLAGS_channel_creds_type) == "gdc";
190*cc02d7e2SAndroid Build Coastguard Worker   return use_ssl ? absl::GetFlag(FLAGS_ssl_target) : "";
191*cc02d7e2SAndroid Build Coastguard Worker }
192*cc02d7e2SAndroid Build Coastguard Worker 
193*cc02d7e2SAndroid Build Coastguard Worker }  // namespace testing
194*cc02d7e2SAndroid Build Coastguard Worker }  // namespace grpc
195