1 // Licensed to the Apache Software Foundation (ASF) under one
2 // or more contributor license agreements. See the NOTICE file
3 // distributed with this work for additional information
4 // regarding copyright ownership. The ASF licenses this file
5 // to you under the Apache License, Version 2.0 (the
6 // "License"); you may not use this file except in compliance
7 // with the License. You may obtain a copy of the License at
9 // http://www.apache.org/licenses/LICENSE-2.0
11 // Unless required by applicable law or agreed to in writing,
12 // software distributed under the License is distributed on an
13 // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
14 // KIND, either express or implied. See the License for the
15 // specific language governing permissions and limitations
18 // Interfaces for defining middleware for Flight clients. Currently
23 #include "arrow/flight/client_middleware.h"
24 #include "arrow/result.h"
25 #include "arrow/util/optional.h"
27 #ifdef GRPCPP_PP_INCLUDE
28 #include <grpcpp/grpcpp.h>
29 #if defined(GRPC_NAMESPACE_FOR_TLS_CREDENTIALS_OPTIONS)
30 #include <grpcpp/security/tls_credentials_options.h>
33 #include <grpc++/grpc++.h>
40 #include <unordered_map>
46 /// \brief Case insensitive comparator for use by cookie caching map. Cookies are not
48 class ARROW_FLIGHT_EXPORT CaseInsensitiveComparator
{
50 bool operator()(const std::string
& t1
, const std::string
& t2
) const;
53 /// \brief Case insensitive hasher for use by cookie caching map. Cookies are not
55 class ARROW_FLIGHT_EXPORT CaseInsensitiveHash
{
57 size_t operator()(const std::string
& key
) const;
60 /// \brief Class to represent a cookie.
61 class ARROW_FLIGHT_EXPORT Cookie
{
63 /// \brief Parse function to parse a cookie header value and return a Cookie object.
65 /// \return Cookie object based on cookie header value.
66 static Cookie
parse(const arrow::util::string_view
& cookie_header_value
);
68 /// \brief Parse a cookie header string beginning at the given start_pos and identify
69 /// the name and value of an attribute.
71 /// \param cookie_header_value The value of the Set-Cookie header.
72 /// \param[out] start_pos An input/output parameter indicating the starting position
73 /// of the attribute. It will store the position of the next attribute when the
76 /// \return Optional cookie key value pair.
77 static arrow::util::optional
<std::pair
<std::string
, std::string
>> ParseCookieAttribute(
78 const std::string
& cookie_header_value
, std::string::size_type
* start_pos
);
80 /// \brief Function to fix cookie format date string so it is accepted by Windows
83 /// \param date Date to fix.
84 static void ConvertCookieDate(std::string
* date
);
86 /// \brief Function to check if the cookie has expired.
88 /// \return Returns true if the cookie has expired.
89 bool IsExpired() const;
91 /// \brief Function to get cookie as a string.
93 /// \return Cookie as a string.
94 std::string
AsCookieString() const;
96 /// \brief Function to get name of the cookie as a string.
98 /// \return Name of the cookie as a string.
99 std::string
GetName() const;
102 std::string cookie_name_
;
103 std::string cookie_value_
;
104 std::chrono::time_point
<std::chrono::system_clock
> expiration_time_
;
108 /// \brief Class to handle updating a cookie cache.
109 class ARROW_FLIGHT_EXPORT CookieCache
{
111 /// \brief Updates the cache of cookies with new Set-Cookie header values.
113 /// \param incoming_headers The range representing header values.
114 void UpdateCachedCookies(const CallHeaders
& incoming_headers
);
116 /// \brief Retrieve the cached cookie values as a string. This function discards
117 /// cookies that have expired.
119 /// \return a string that can be used in a Cookie header representing the cookies that
120 /// have been cached.
121 std::string
GetValidCookiesAsString();
124 /// \brief Removes cookies that are marked as expired from the cache.
125 void DiscardExpiredCookies();
127 // Mutex must be used to protect cookie cache.
129 std::unordered_map
<std::string
, Cookie
, CaseInsensitiveHash
, CaseInsensitiveComparator
>
133 /// \brief Add basic authentication header key value pair to context.
135 /// \param context grpc context variable to add header to.
136 /// \param username username to encode into header.
137 /// \param password password to to encode into header.
138 void ARROW_FLIGHT_EXPORT
AddBasicAuthHeaders(grpc::ClientContext
* context
,
139 const std::string
& username
,
140 const std::string
& password
);
142 /// \brief Get bearer token from incoming headers.
144 /// \param context context that contains headers which hold the bearer token.
145 /// \return Bearer token, parsed from headers, empty if one is not present.
146 arrow::Result
<std::pair
<std::string
, std::string
>> ARROW_FLIGHT_EXPORT
147 GetBearerTokenHeader(grpc::ClientContext
& context
);
149 } // namespace internal
150 } // namespace flight