Line data Source code
1 : #pragma once 2 : 3 : #include <memory> 4 : #include <tuple> 5 : 6 : #include "envoy/extensions/http/stateful_session/header/v3/header.pb.h" 7 : #include "envoy/http/stateful_session.h" 8 : 9 : #include "source/common/common/base64.h" 10 : #include "source/common/http/headers.h" 11 : #include "source/common/http/utility.h" 12 : 13 : namespace Envoy { 14 : namespace Extensions { 15 : namespace Http { 16 : namespace StatefulSession { 17 : namespace Header { 18 : 19 : using HeaderBasedSessionStateProto = 20 : envoy::extensions::http::stateful_session::header::v3::HeaderBasedSessionState; 21 : 22 : class HeaderBasedSessionStateFactory : public Envoy::Http::SessionStateFactory { 23 : public: 24 : class SessionStateImpl : public Envoy::Http::SessionState { 25 : public: 26 : SessionStateImpl(absl::optional<std::string> address, 27 : const HeaderBasedSessionStateFactory& factory) 28 0 : : upstream_address_(std::move(address)), factory_(factory) {} 29 : 30 0 : absl::optional<absl::string_view> upstreamAddress() const override { return upstream_address_; } 31 : void onUpdate(const Upstream::HostDescription& host, 32 : Envoy::Http::ResponseHeaderMap& headers) override; 33 : 34 : private: 35 : absl::optional<std::string> upstream_address_; 36 : const HeaderBasedSessionStateFactory& factory_; 37 : }; 38 : 39 : HeaderBasedSessionStateFactory(const HeaderBasedSessionStateProto& config); 40 : 41 0 : Envoy::Http::SessionStatePtr create(const Envoy::Http::RequestHeaderMap& headers) const override { 42 0 : return std::make_unique<SessionStateImpl>(parseAddress(headers), *this); 43 0 : } 44 : 45 : private: 46 0 : absl::optional<std::string> parseAddress(const Envoy::Http::RequestHeaderMap& headers) const { 47 0 : auto hdr = headers.get(Envoy::Http::LowerCaseString(name_)); 48 0 : if (hdr.empty()) { 49 0 : return absl::nullopt; 50 0 : } 51 : 52 0 : auto header_value = hdr[0]->value().getStringView(); 53 0 : std::string address = Envoy::Base64::decode(header_value); 54 0 : return !address.empty() ? absl::make_optional(std::move(address)) : absl::nullopt; 55 0 : } 56 : 57 0 : const Envoy::Http::LowerCaseString& getHeaderName() const { return name_; } 58 : 59 : const Envoy::Http::LowerCaseString name_; 60 : }; 61 : 62 : } // namespace Header 63 : } // namespace StatefulSession 64 : } // namespace Http 65 : } // namespace Extensions 66 : } // namespace Envoy