From 78b931b935d69422a0c6a0c9424ac50c054b0677 Mon Sep 17 00:00:00 2001 From: enricoschiattarella Date: Tue, 10 Jan 2017 13:26:08 -0800 Subject: [PATCH 01/16] Simple TCP server to show how to retrieve original dest IP:port after an iptables redirect (#38) * Simple TCP server to show how to retrieve original dest IP:port after an iptables redirect * Fixed style. --- contrib/tools/server/Makefile | 6 ++ contrib/tools/server/README.md | 25 +++++ contrib/tools/server/server.c | 169 +++++++++++++++++++++++++++++++++ 3 files changed, 200 insertions(+) create mode 100644 contrib/tools/server/Makefile create mode 100644 contrib/tools/server/README.md create mode 100644 contrib/tools/server/server.c diff --git a/contrib/tools/server/Makefile b/contrib/tools/server/Makefile new file mode 100644 index 00000000000..d7c7d758686 --- /dev/null +++ b/contrib/tools/server/Makefile @@ -0,0 +1,6 @@ +server: + $(CC) -g -o server server.c + +clean: + rm server + diff --git a/contrib/tools/server/README.md b/contrib/tools/server/README.md new file mode 100644 index 00000000000..f962c2c640b --- /dev/null +++ b/contrib/tools/server/README.md @@ -0,0 +1,25 @@ +# Sample TCP Server + +This is a simple TCP server that listens on the specified port (3490 by default) and replies to incoming connections by providing info about src/destination ip/port. + +It demonstrates the use of the getsockopt() system call with the ORIGINAL_DST option to retrieve the original destination ip/port after an iptables redirect. + +So, for example, if you have the server listening on port 3490 on the local machine and an iptables rule like: + +``` +iptables -t nat -I OUTPUT 1 -p tcp --dport 4000:5000 -j REDIRECT --to-port 3490 +``` +your will see: + +``` +$ telnet localhost 3490 +FROM 127.0.0.1:44978, TO 127.0.0.1:3490, ORIG DEST 127.0.0.1:3490 + +$ telnet localhost 4100 +FROM 127.0.0.1:35476, TO 127.0.0.1:3490, ORIG DEST 127.0.0.1:4100 + +$ telnet 1.1.1.1 5000 +FROM 100.100.100.100:60275, TO 127.0.0.1:3490, ORIG DEST 1.1.1.1:5000 +``` + + diff --git a/contrib/tools/server/server.c b/contrib/tools/server/server.c new file mode 100644 index 00000000000..77a2d97e004 --- /dev/null +++ b/contrib/tools/server/server.c @@ -0,0 +1,169 @@ +/* +** server.c + * Demo server to check that we can extract all parameters from an incoming +*request + * and respond to it +*/ + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#define DEFAULT_PORT \ + "3490" // the port users will be connecting to, if not specified on command + // line + +#define QUEUE_SIZE 10 // pending connections queue size + +void sigchld_handler(int s) { + int saved_errno = errno; + + while (waitpid(-1, NULL, WNOHANG) > 0) + ; + + errno = saved_errno; +} + +int main(int argc, char *argv[]) { + struct sigaction sa; + const int yes = 1; + char *port = DEFAULT_PORT; + int rv; + + if (argc > 1) { + port = argv[1]; + } + + struct addrinfo hints; + memset(&hints, 0, sizeof hints); + hints.ai_family = AF_INET; + hints.ai_socktype = SOCK_STREAM; + hints.ai_flags = AI_PASSIVE; // use my IP + + struct addrinfo *server_info = NULL; + if ((rv = getaddrinfo(NULL, port, &hints, &server_info)) != 0) { + fprintf(stderr, "getaddrinfo: %s\n", gai_strerror(rv)); + return 1; + } + + struct addrinfo *p; + int sockfd; // listen on sock_fd + for (p = server_info; p != NULL; p = p->ai_next) { + if ((sockfd = socket(p->ai_family, p->ai_socktype, p->ai_protocol)) == -1) { + perror("server: socket"); + continue; + } + + if (setsockopt(sockfd, SOL_SOCKET, SO_REUSEADDR, &yes, sizeof(int)) == -1) { + perror("setsockopt"); + exit(1); + } + + if (bind(sockfd, p->ai_addr, p->ai_addrlen) == -1) { + close(sockfd); + perror("server: bind"); + continue; + } + + break; + } + + freeaddrinfo(server_info); + + if (p == NULL) { + fprintf(stderr, "server: failed to bind\n"); + exit(1); + } + if (listen(sockfd, QUEUE_SIZE) == -1) { + perror("listen"); + exit(1); + } + + sa.sa_handler = sigchld_handler; + sigemptyset(&sa.sa_mask); + sa.sa_flags = SA_RESTART; + if (sigaction(SIGCHLD, &sa, NULL) == -1) { + perror("sigaction"); + exit(1); + } + + char bind_addr_str[INET6_ADDRSTRLEN] = {0}; + struct sockaddr_in *bind_sock_addr = (struct sockaddr_in *)p->ai_addr; + inet_ntop(p->ai_family, &bind_sock_addr->sin_addr, bind_addr_str, + p->ai_addrlen); + printf("server %s: waiting for connections on port %s:%u...\n", port, + bind_addr_str, ntohs(bind_sock_addr->sin_port)); + + while (1) { + socklen_t addr_len = sizeof(struct sockaddr_storage); + int addr_str_len = INET6_ADDRSTRLEN; + + struct sockaddr_storage their_addr = { + 0}; // connector's address information + int accepted_fd = accept(sockfd, (struct sockaddr *)&their_addr, &addr_len); + if (accepted_fd == -1) { + perror("accept"); + continue; + } + + struct sockaddr_in *src_sock_addr = (struct sockaddr_in *)&their_addr; + char their_addr_str[INET6_ADDRSTRLEN] = {0}; + inet_ntop(their_addr.ss_family, &src_sock_addr->sin_addr, their_addr_str, + addr_str_len); + printf("server %s: got connection FROM %s:%u\n", port, their_addr_str, + ntohs(src_sock_addr->sin_port)); + + struct sockaddr_storage my_addr = {0}; // my address information + struct sockaddr_in *dst_sock_addr = (struct sockaddr_in *)&my_addr; + char my_addr_str[INET6_ADDRSTRLEN] = {0}; + getsockname(accepted_fd, (struct sockaddr *)dst_sock_addr, &addr_len); + inet_ntop(my_addr.ss_family, &dst_sock_addr->sin_addr, my_addr_str, + addr_str_len); + printf("server %s: got connection TO %s:%u\n", port, my_addr_str, + ntohs(dst_sock_addr->sin_port)); + + struct sockaddr_storage orig_addr = {0}; // orig address information + struct sockaddr_in *orig_sock_addr = (struct sockaddr_in *)&orig_addr; + char orig_addr_str[INET6_ADDRSTRLEN] = {0}; + int status = getsockopt(accepted_fd, SOL_IP, SO_ORIGINAL_DST, + orig_sock_addr, &addr_len); + + if (status == 0) { + inet_ntop(orig_addr.ss_family, &orig_sock_addr->sin_addr, orig_addr_str, + addr_str_len); + printf("server %s: ORIG DEST %s:%u\n", port, orig_addr_str, + ntohs(orig_sock_addr->sin_port)); + } else { + printf("Could not get orig destination from accepted socket.\n"); + } + + if (!fork()) { // this is the child process + + close(sockfd); + char msg[256] = {0}; + snprintf(msg, 256, "FROM %s:%u, TO %s:%u, ORIG DEST %s:%u\n", + their_addr_str, ntohs(src_sock_addr->sin_port), my_addr_str, + ntohs(dst_sock_addr->sin_port), orig_addr_str, + ntohs(orig_sock_addr->sin_port)); + + if (send(accepted_fd, msg, strlen(msg), 0) == -1) { + perror("send"); + } + close(accepted_fd); + exit(0); + } + close(accepted_fd); + } + + return 0; +} From 8b3a4429965ed1e792704e795e5d22782eca505b Mon Sep 17 00:00:00 2001 From: Kuat Date: Thu, 12 Jan 2017 11:23:47 -0800 Subject: [PATCH 02/16] Rebase Envoy (#41) --- src/envoy/repositories.bzl | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/envoy/repositories.bzl b/src/envoy/repositories.bzl index 56fabce07ac..4460b4c1c9d 100644 --- a/src/envoy/repositories.bzl +++ b/src/envoy/repositories.bzl @@ -629,6 +629,6 @@ cc_test( native.new_git_repository( name = "envoy_git", remote = "https://github.com/lyft/envoy.git", - commit = "6b1336a786ebe56c45a1a349ddf706e0526c1ec1", # 2017-01-03 + commit = "38990918a8672a0332b1ca2e048db90a5166d678", build_file_content = BUILD, ) From c3abd2aeb2b43e2c68b71b48449a5fa0de0f2fb8 Mon Sep 17 00:00:00 2001 From: Kuat Date: Thu, 12 Jan 2017 14:52:56 -0800 Subject: [PATCH 03/16] Update prototype to use iptables (#42) --- src/envoy/prototype/README.md | 13 +++++++++++++ src/envoy/prototype/envoy-esp.conf | 11 +++++++++-- test/backend/echo/echo.go | 21 +++++++-------------- 3 files changed, 29 insertions(+), 16 deletions(-) diff --git a/src/envoy/prototype/README.md b/src/envoy/prototype/README.md index 2ddbe98459c..00e73a169d6 100644 --- a/src/envoy/prototype/README.md +++ b/src/envoy/prototype/README.md @@ -36,6 +36,19 @@ This Proxy will use Envoy and talk to Mixer server. go run echo.go ``` +* Modify your iptables: + +``` + sudo iptables -t nat -A OUTPUT -p tcp --dport 9090 -j REDIRECT --to-port 9092 +``` + +Once you are done, you should remove this rule: + +``` + sudo iptables -t nat -D OUTPUT -p tcp --dport 9090 -j REDIRECT --to-port 9092 +``` + + * Start Envoy proxy, run ``` diff --git a/src/envoy/prototype/envoy-esp.conf b/src/envoy/prototype/envoy-esp.conf index dff3bd67b1a..11690bed565 100644 --- a/src/envoy/prototype/envoy-esp.conf +++ b/src/envoy/prototype/envoy-esp.conf @@ -1,7 +1,14 @@ { "listeners": [ + { + "port": 9092, + "bind_to_port": true, + "use_original_dst": true, + "filters": [] + }, { "port": 9090, + "bind_to_port": false, "filters": [ { "type": "read", @@ -26,7 +33,7 @@ }, "access_log": [ { - "path": "/tmp/access.envoy" + "path": "/dev/stdout" } ], "filters": [ @@ -50,7 +57,7 @@ } ], "admin": { - "access_log_path": "/tmp/access.envoy", + "access_log_path": "/dev/stdout", "port": 9001 }, "cluster_manager": { diff --git a/test/backend/echo/echo.go b/test/backend/echo/echo.go index 51aaa07e353..ef13f515ff1 100644 --- a/test/backend/echo/echo.go +++ b/test/backend/echo/echo.go @@ -23,19 +23,22 @@ import ( "io/ioutil" "net/http" "strconv" - "sync" - "time" ) var ( port = flag.Int("port", 8080, "default http port") - mu sync.Mutex requests = 0 data = 0 ) func handler(w http.ResponseWriter, r *http.Request) { + fmt.Printf("%v %v %v %v\n", r.Method, r.URL, r.Proto, r.RemoteAddr) + for name, headers := range r.Header { + for _, h := range headers { + fmt.Printf("%v: %v\n", name, h) + } + } body, err := ioutil.ReadAll(r.Body) if err != nil { http.Error(w, err.Error(), http.StatusInternalServerError) @@ -51,24 +54,14 @@ func handler(w http.ResponseWriter, r *http.Request) { w.WriteHeader(http.StatusOK) w.Write(body) - mu.Lock() requests++ data += len(body) - defer mu.Unlock() + fmt.Printf("Requests Requests: %v Data: %v\n", requests, data) } func main() { flag.Parse() - go func() { - for { - mu.Lock() - fmt.Printf("Requests Requests: %v Data: %v\n", requests, data) - mu.Unlock() - time.Sleep(time.Second) - } - }() - fmt.Printf("Listening on port %v\n", *port) http.HandleFunc("/", handler) From add363a037389ebf985defa8898465b3269e380f Mon Sep 17 00:00:00 2001 From: Kuat Date: Thu, 12 Jan 2017 20:18:53 -0800 Subject: [PATCH 04/16] Rebase to fixed Envoy (#43) --- src/envoy/repositories.bzl | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/envoy/repositories.bzl b/src/envoy/repositories.bzl index 4460b4c1c9d..dd36a23d456 100644 --- a/src/envoy/repositories.bzl +++ b/src/envoy/repositories.bzl @@ -629,6 +629,6 @@ cc_test( native.new_git_repository( name = "envoy_git", remote = "https://github.com/lyft/envoy.git", - commit = "38990918a8672a0332b1ca2e048db90a5166d678", + commit = "c36bb76e304ab4c5584a07303e2953a170888319", build_file_content = BUILD, ) From ee3cdeeb33b1de0b87c80809802de5246cbb3e25 Mon Sep 17 00:00:00 2001 From: Qian Sun Date: Fri, 13 Jan 2017 08:49:25 -0800 Subject: [PATCH 05/16] Handle HEAD request. (#34) * Handle HEAD request. * Try with GET if HEAD fails. * Address comments. * Format file. --- .../src/api_manager/context/service_context.cc | 13 ++++++++++++- 1 file changed, 12 insertions(+), 1 deletion(-) diff --git a/contrib/endpoints/src/api_manager/context/service_context.cc b/contrib/endpoints/src/api_manager/context/service_context.cc index b9f753f0625..d8fc9dfc409 100644 --- a/contrib/endpoints/src/api_manager/context/service_context.cc +++ b/contrib/endpoints/src/api_manager/context/service_context.cc @@ -41,6 +41,9 @@ const double kDefaultTraceSampleQps = 0.1; // The time window to send intermediate report for Grpc streaming (second). // Default to 10s. const int kIntermediateReportInterval = 10; + +const char kHTTPHeadMethod[] = "HEAD"; +const char kHTTPGetMethod[] = "GET"; } ServiceContext::ServiceContext(std::unique_ptr env, @@ -74,7 +77,15 @@ MethodCallInfo ServiceContext::GetMethodCallInfo( if (config_ == nullptr) { return MethodCallInfo(); } - return config_->GetMethodCallInfo(http_method, url, query_params); + MethodCallInfo method_call_info = + config_->GetMethodCallInfo(http_method, url, query_params); + // HEAD should be treated as GET unless it is specified from service_config. + if (method_call_info.method_info == nullptr && + http_method == kHTTPHeadMethod) { + method_call_info = + config_->GetMethodCallInfo(kHTTPGetMethod, url, query_params); + } + return method_call_info; } const std::string& ServiceContext::project_id() const { From efc32a2a83434e7169f00c56c08c4b7361febf3b Mon Sep 17 00:00:00 2001 From: Kuat Date: Fri, 20 Jan 2017 16:39:05 -0800 Subject: [PATCH 06/16] Expose bazel target (#48) --- src/envoy/prototype/BUILD | 2 ++ 1 file changed, 2 insertions(+) diff --git a/src/envoy/prototype/BUILD b/src/envoy/prototype/BUILD index e5cbaeba10c..5c8ab20e27a 100644 --- a/src/envoy/prototype/BUILD +++ b/src/envoy/prototype/BUILD @@ -15,6 +15,8 @@ ################################################################################ # +package(default_visibility = [":__subpackages__"]) + cc_binary( name = "envoy_esp", srcs = [ From 92541b79f45fb3ada59e36d3abd87bd7724b27f9 Mon Sep 17 00:00:00 2001 From: Kuat Date: Fri, 20 Jan 2017 16:51:15 -0800 Subject: [PATCH 07/16] Try again (#49) --- src/envoy/prototype/BUILD | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/envoy/prototype/BUILD b/src/envoy/prototype/BUILD index 5c8ab20e27a..258f2046cd7 100644 --- a/src/envoy/prototype/BUILD +++ b/src/envoy/prototype/BUILD @@ -15,7 +15,7 @@ ################################################################################ # -package(default_visibility = [":__subpackages__"]) +package(default_visibility = ["//visibility:public"]) cc_binary( name = "envoy_esp", From cea882799327dbea20ce849be36088a349a35f18 Mon Sep 17 00:00:00 2001 From: Wayne Zhang Date: Thu, 26 Jan 2017 22:02:18 -0800 Subject: [PATCH 08/16] Integrate with mixer client. (#55) * Integrate with mixer client. * Restore repositories.bzl back. --- WORKSPACE | 22 +- contrib/endpoints/repositories.bzl | 52 +--- contrib/endpoints/src/api_manager/mixer/BUILD | 6 +- .../endpoints/src/api_manager/mixer/mixer.cc | 255 ++++++------------ .../endpoints/src/api_manager/mixer/mixer.h | 6 +- src/envoy/prototype/api_manager_filter.cc | 9 +- src/envoy/prototype/envoy-esp.conf | 12 - src/envoy/prototype/server_config.pb.txt | 4 +- 8 files changed, 129 insertions(+), 237 deletions(-) diff --git a/WORKSPACE b/WORKSPACE index bbafd205918..95dcdde5cdc 100644 --- a/WORKSPACE +++ b/WORKSPACE @@ -31,16 +31,34 @@ googletest_repositories() load( "//contrib/endpoints:repositories.bzl", "grpc_repositories", - "mixerapi_repositories", + "mixer_client_repositories", "servicecontrol_client_repositories", ) grpc_repositories() -mixerapi_repositories() +mixer_client_repositories() servicecontrol_client_repositories() +# Workaround for Bazel > 0.4.0 since it needs newer protobuf.bzl from: +# https://github.com/google/protobuf/pull/2246 +# Do not use this git_repository for anything else than protobuf.bzl +new_git_repository( + name = "protobuf_bzl", + # Injecting an empty BUILD file to prevent using any build target + build_file_content = "", + commit = "05090726144b6e632c50f47720ff51049bfcbef6", + remote = "https://github.com/google/protobuf.git", +) + +load( + "@mixerclient_git//:repositories.bzl", + "mixerapi_repositories", +) + +mixerapi_repositories(protobuf_repo="@protobuf_bzl//") + load( "//src/envoy:repositories.bzl", "envoy_repositories", diff --git a/contrib/endpoints/repositories.bzl b/contrib/endpoints/repositories.bzl index f3df61722a2..7b77aa91c5a 100644 --- a/contrib/endpoints/repositories.bzl +++ b/contrib/endpoints/repositories.bzl @@ -334,51 +334,15 @@ def servicecontrol_client_repositories(bind=True): actual = "@servicecontrol_client_git//:service_control_client_lib", ) -def mixerapi_repositories(protobuf_repo="@protobuf_git//", bind=True): - BUILD = """ -# Copyright 2016 Google Inc. All Rights Reserved. -# -# Licensed under the Apache License, Version 2.0 (the "License"); -# you may not use this file except in compliance with the License. -# You may obtain a copy of the License at -# -# http://www.apache.org/licenses/LICENSE-2.0 -# -# Unless required by applicable law or agreed to in writing, software -# distributed under the License is distributed on an "AS IS" BASIS, -# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -# See the License for the specific language governing permissions and -# limitations under the License. -# -################################################################################ -# -licenses(["notice"]) - -load("{}:protobuf.bzl", "cc_proto_library") - -cc_proto_library( - name = "mixer_api_cc_proto", - srcs = glob( - ["mixer/api/v1/*.proto"], - ), - default_runtime = "//external:protobuf", - protoc = "//external:protoc", - visibility = ["//visibility:public"], - deps = [ - "//external:cc_wkt_protos", - "//external:servicecontrol", - ], -) -""".format(protobuf_repo) - - native.new_git_repository( - name = "mixerapi_git", - commit = "fc5a396185edc72d06d1937f30a8148a37d4fc1b", - remote = "https://github.com/istio/api.git", - build_file_content = BUILD, +def mixer_client_repositories(bind=True): + native.git_repository( + name = "mixerclient_git", + commit = "1569430f1e27b31e23c029c6bec0d8d5062d9e55", + remote = "https://github.com/istio/mixerclient.git", ) + if bind: native.bind( - name = "mixer_api_cc_proto", - actual = "@mixerapi_git//:mixer_api_cc_proto", + name = "mixer_client_lib", + actual = "@mixerclient_git//:mixer_client_lib", ) diff --git a/contrib/endpoints/src/api_manager/mixer/BUILD b/contrib/endpoints/src/api_manager/mixer/BUILD index 8082c61e201..affe09c7ddd 100644 --- a/contrib/endpoints/src/api_manager/mixer/BUILD +++ b/contrib/endpoints/src/api_manager/mixer/BUILD @@ -32,11 +32,11 @@ cc_library( ], }), deps = [ - "//external:grpc++", - "//external:mixer_api_cc_proto", - "//external:protobuf", "//contrib/endpoints/src/api_manager:impl_headers", "//contrib/endpoints/src/api_manager/service_control", "//contrib/endpoints/src/api_manager/utils", + "//external:grpc++", + "//external:mixer_client_lib", + "//external:protobuf", ], ) diff --git a/contrib/endpoints/src/api_manager/mixer/mixer.cc b/contrib/endpoints/src/api_manager/mixer/mixer.cc index 0c0bb5d793e..47f6c4a8a2f 100644 --- a/contrib/endpoints/src/api_manager/mixer/mixer.cc +++ b/contrib/endpoints/src/api_manager/mixer/mixer.cc @@ -14,169 +14,103 @@ */ #include "contrib/endpoints/src/api_manager/mixer/mixer.h" -#include -#include "mixer/api/v1/service.pb.h" - using ::google::api_manager::utils::Status; -using ::google::protobuf::util::error::Code; -using ::google::protobuf::Map; +using ::istio::mixer_client::Attributes; namespace google { namespace api_manager { namespace mixer { namespace { -const char kMixerServiceName[] = "istio.mixer.v1.Mixer"; - -enum AttributeIndex { - ATTR_SERVICE_NAME = 0, - ATTR_PEER_ID, - ATTR_OPERATION_NAME, - ATTR_API_KEY, - ATTR_RESPONSE_CODE, - ATTR_URL, - ATTR_LOCATION, - ATTR_API_NAME, - ATTR_API_VERSION, - ATTR_API_METHOD, - ATTR_REQUEST_SIZE, - ATTR_RESPONSE_SIZE, - ATTR_LOG_MESSAGE, -}; - -struct AttributeDict { - int index; - std::string name; -} kAttributeNames[] = { - { - ATTR_SERVICE_NAME, "serviceName", - }, - { - ATTR_PEER_ID, "peerId", - }, - { - ATTR_OPERATION_NAME, "operationName", - }, - { - ATTR_API_KEY, "apiKey", - }, - { - ATTR_RESPONSE_CODE, "responseCode", - }, - { - ATTR_URL, "URL", - }, - { - ATTR_LOCATION, "location", - }, - { - ATTR_API_NAME, "apiName", - }, - { - ATTR_API_VERSION, "apiVersion", - }, - { - ATTR_API_METHOD, "apiMethod", - }, - { - ATTR_REQUEST_SIZE, "requestSize", - }, - { - ATTR_RESPONSE_SIZE, "responesSize", - }, - { - ATTR_LOG_MESSAGE, "logMessage", - }, -}; - -void SetAttributeDict(Map* dict) { - for (auto attr : kAttributeNames) { - (*dict)[attr.index] = attr.name; - } +const std::string kAttrNameServiceName = "serviceName"; +const std::string kAttrNamePeerId = "peerId"; +const std::string kAttrNameOperationName = "operationName"; +const std::string kAttrNameApiKey = "apiKey"; +const std::string kAttrNameResponseCode = "responseCode"; +const std::string kAttrNameURL = "url"; +const std::string kAttrNameLocation = "location"; +const std::string kAttrNameApiName = "apiName"; +const std::string kAttrNameApiVersion = "apiVersion"; +const std::string kAttrNameApiMethod = "apiMethod"; +const std::string kAttrNameRequestSize = "requestSize"; +const std::string kAttrNameResponseSize = "responseSize"; +const std::string kAttrNameLogMessage = "logMessage"; + +Attributes::Value StringValue(const std::string& str) { + Attributes::Value v; + v.type = Attributes::Value::STRING; + v.str_v = str; + return v; } -void CovertToPb(const service_control::CheckRequestInfo& info, - const std::string& service_name, - ::istio::mixer::v1::Attributes* attr) { - SetAttributeDict(attr->mutable_dictionary()); - - auto* str_attrs = attr->mutable_string_attributes(); - (*str_attrs)[ATTR_SERVICE_NAME] = service_name; - (*str_attrs)[ATTR_PEER_ID] = "Proxy"; - (*str_attrs)[ATTR_OPERATION_NAME] = info.operation_name; - (*str_attrs)[ATTR_API_KEY] = info.api_key; +Attributes::Value Int64Value(int64_t value) { + Attributes::Value v; + v.type = Attributes::Value::INT64; + v.value.int64_v = value; + return v; } -void CovertToPb(const service_control::ReportRequestInfo& info, - const std::string& service_name, - ::istio::mixer::v1::Attributes* attr) { - SetAttributeDict(attr->mutable_dictionary()); +void FillCheckAttributes(const service_control::CheckRequestInfo& info, + const std::string& service_name, + ::istio::mixer_client::Attributes* attr) { + attr->attributes[kAttrNameServiceName] = StringValue(service_name); + attr->attributes[kAttrNamePeerId] = StringValue("Proxy"); + attr->attributes[kAttrNameOperationName] = StringValue(info.operation_name); + attr->attributes[kAttrNameApiKey] = StringValue(info.api_key); +} - auto* str_attrs = attr->mutable_string_attributes(); - (*str_attrs)[ATTR_SERVICE_NAME] = service_name; - (*str_attrs)[ATTR_PEER_ID] = "Proxy"; - (*str_attrs)[ATTR_OPERATION_NAME] = info.operation_name; - (*str_attrs)[ATTR_API_KEY] = info.api_key; +void FillReportAttributes(const service_control::ReportRequestInfo& info, + const std::string& service_name, + ::istio::mixer_client::Attributes* attr) { + attr->attributes[kAttrNameServiceName] = StringValue(service_name); + attr->attributes[kAttrNamePeerId] = StringValue("Proxy"); + attr->attributes[kAttrNameOperationName] = StringValue(info.operation_name); + attr->attributes[kAttrNameApiKey] = StringValue(info.api_key); - (*str_attrs)[ATTR_URL] = info.url; - (*str_attrs)[ATTR_LOCATION] = info.location; + attr->attributes[kAttrNameURL] = StringValue(info.url); + attr->attributes[kAttrNameLocation] = StringValue(info.location); - (*str_attrs)[ATTR_API_NAME] = info.api_name; - (*str_attrs)[ATTR_API_VERSION] = info.api_version; - (*str_attrs)[ATTR_API_METHOD] = info.api_method; + attr->attributes[kAttrNameApiName] = StringValue(info.api_name); + attr->attributes[kAttrNameApiVersion] = StringValue(info.api_version); + attr->attributes[kAttrNameApiMethod] = StringValue(info.api_method); - (*str_attrs)[ATTR_LOG_MESSAGE] = info.log_message; + attr->attributes[kAttrNameLogMessage] = StringValue(info.log_message); - auto* int_attrs = attr->mutable_int64_attributes(); - (*int_attrs)[ATTR_RESPONSE_CODE] = info.response_code; - (*int_attrs)[ATTR_REQUEST_SIZE] = info.request_size; - (*int_attrs)[ATTR_RESPONSE_SIZE] = info.response_size; + attr->attributes[kAttrNameResponseCode] = Int64Value(info.response_code); + attr->attributes[kAttrNameRequestSize] = Int64Value(info.request_size); + attr->attributes[kAttrNameResponseSize] = Int64Value(info.response_size); } } // namespace Mixer::Mixer(ApiManagerEnvInterface* env, const Config* config) - : env_(env), request_index_(0), config_(config) {} + : env_(env), config_(config) {} Mixer::~Mixer() {} -Status Mixer::Init() { return Status::OK; } +Status Mixer::Init() { + ::istio::mixer_client::MixerClientOptions options; + options.mixer_server = + config_->server_config()->mixer_options().mixer_server(); + mixer_client_ = ::istio::mixer_client::CreateMixerClient(options); + return Status::OK; +} Status Mixer::Close() { return Status::OK; } Status Mixer::Report(const service_control::ReportRequestInfo& info) { - std::unique_ptr grpc_request(new GRPCRequest([this]( - Status status, std::string&& body) { - if (status.ok()) { - // Handle 200 response - ::istio::mixer::v1::ReportResponse response; - if (!response.ParseFromString(body)) { - status = - Status(Code::INVALID_ARGUMENT, std::string("Invalid response")); - env_->LogError(std::string("Failed parse report response: ") + body); - } - env_->LogInfo(std::string("Report response: ") + response.DebugString()); - } else { - env_->LogError(std::string("Failed to call Mixer::report, Error: ") + - status.ToString()); - } - })); - - ::istio::mixer::v1::ReportRequest request; - request.set_request_index(++request_index_); - CovertToPb(info, config_->service_name(), request.mutable_attribute_update()); - env_->LogInfo(std::string("Send Report: ") + request.DebugString()); - - std::string request_body; - request.SerializeToString(&request_body); - - grpc_request - ->set_server(config_->server_config()->mixer_options().mixer_server()) - .set_service(kMixerServiceName) - .set_method("Report") - .set_body(request_body); - - env_->RunGRPCRequest(std::move(grpc_request)); + ::istio::mixer_client::Attributes attributes; + FillReportAttributes(info, config_->service_name(), &attributes); + env_->LogInfo("Send Report: "); + mixer_client_->Report( + attributes, [this](const ::google::protobuf::util::Status& status) { + if (status.ok()) { + env_->LogInfo("Report response: OK"); + } else { + env_->LogError(std::string("Failed to call Mixer::report, Error: ") + + status.ToString()); + } + }); return Status::OK; } @@ -185,40 +119,23 @@ void Mixer::Check( cloud_trace::CloudTraceSpan* parent_span, std::function on_done) { - std::unique_ptr grpc_request(new GRPCRequest([this, on_done]( - Status status, std::string&& body) { - if (status.ok()) { - // Handle 200 response - ::istio::mixer::v1::CheckResponse response; - if (!response.ParseFromString(body)) { - status = - Status(Code::INVALID_ARGUMENT, std::string("Invalid response")); - env_->LogError(std::string("Failed parse check response: ") + body); - } - env_->LogInfo(std::string("Check response: ") + response.DebugString()); - } else { - env_->LogError(std::string("Failed to call Mixer::check, Error: ") + - status.ToString()); - } - service_control::CheckResponseInfo info; - on_done(status, info); - })); - - ::istio::mixer::v1::CheckRequest request; - request.set_request_index(++request_index_); - CovertToPb(info, config_->service_name(), request.mutable_attribute_update()); - env_->LogInfo(std::string("Send Check: ") + request.DebugString()); - - std::string request_body; - request.SerializeToString(&request_body); - - grpc_request - ->set_server(config_->server_config()->mixer_options().mixer_server()) - .set_service(kMixerServiceName) - .set_method("Check") - .set_body(request_body); - - env_->RunGRPCRequest(std::move(grpc_request)); + ::istio::mixer_client::Attributes attributes; + FillCheckAttributes(info, config_->service_name(), &attributes); + env_->LogInfo("Send Check: "); + mixer_client_->Check( + attributes, + [this, on_done](const ::google::protobuf::util::Status& status) { + if (status.ok()) { + env_->LogInfo("Check response: OK"); + } else { + env_->LogError(std::string("Failed to call Mixer::check, Error: ") + + status.ToString()); + } + service_control::CheckResponseInfo info; + on_done(Status(status.error_code(), status.error_message(), + Status::SERVICE_CONTROL), + info); + }); } Status Mixer::GetStatistics(service_control::Statistics* esp_stat) const { diff --git a/contrib/endpoints/src/api_manager/mixer/mixer.h b/contrib/endpoints/src/api_manager/mixer/mixer.h index 0318a5f06f1..4cf2d1f54a7 100644 --- a/contrib/endpoints/src/api_manager/mixer/mixer.h +++ b/contrib/endpoints/src/api_manager/mixer/mixer.h @@ -18,6 +18,7 @@ #include "contrib/endpoints/include/api_manager/env_interface.h" #include "contrib/endpoints/src/api_manager/config.h" #include "contrib/endpoints/src/api_manager/service_control/interface.h" +#include "include/client.h" namespace google { namespace api_manager { @@ -51,9 +52,10 @@ class Mixer : public service_control::Interface { // The Api Manager environment interface. ApiManagerEnvInterface* env_; - int64_t request_index_; - + // The config. const Config* config_; + // The mixer client + std::unique_ptr<::istio::mixer_client::MixerClient> mixer_client_; }; } // namespace mixer diff --git a/src/envoy/prototype/api_manager_filter.cc b/src/envoy/prototype/api_manager_filter.cc index 2fca48de23c..4ccd9e6d120 100644 --- a/src/envoy/prototype/api_manager_filter.cc +++ b/src/envoy/prototype/api_manager_filter.cc @@ -214,13 +214,16 @@ class Instance : public Http::StreamFilter, status.ToJson()); if (!status.ok() && state_ != Responded) { state_ = Responded; - Utility::sendLocalReply(*decoder_callbacks_, Code(status.HttpCode()), - status.ToJson()); + decoder_callbacks_->dispatcher().post([this, status]() { + Utility::sendLocalReply(*decoder_callbacks_, Code(status.HttpCode()), + status.ToJson()); + }); return; } state_ = Complete; if (!initiating_call_) { - decoder_callbacks_->continueDecoding(); + decoder_callbacks_->dispatcher().post( + [this]() { decoder_callbacks_->continueDecoding(); }); } } diff --git a/src/envoy/prototype/envoy-esp.conf b/src/envoy/prototype/envoy-esp.conf index 11690bed565..d3ec54f405d 100644 --- a/src/envoy/prototype/envoy-esp.conf +++ b/src/envoy/prototype/envoy-esp.conf @@ -73,18 +73,6 @@ } ] }, - { - "name": "mixer_server", - "connect_timeout_ms": 5000, - "type": "strict_dns", - "lb_type": "round_robin", - "features": "http2", - "hosts": [ - { - "url": "tcp://localhost:9091" - } - ] - }, { "name": "api_manager", "connect_timeout_ms": 5000, diff --git a/src/envoy/prototype/server_config.pb.txt b/src/envoy/prototype/server_config.pb.txt index 9703886cc9e..19cb6cbb2c0 100644 --- a/src/envoy/prototype/server_config.pb.txt +++ b/src/envoy/prototype/server_config.pb.txt @@ -2,5 +2,5 @@ cloud_tracing_config { force_disable: true } mixer_options { - mixer_server: "mixer_server" -} \ No newline at end of file + mixer_server: "localhost:9091" +} From 6d7f0eebec4d00856987f9e8f55e4b9b4ddd8455 Mon Sep 17 00:00:00 2001 From: Wayne Zhang Date: Thu, 26 Jan 2017 23:38:51 -0800 Subject: [PATCH 09/16] Add originIp and originHost attributes. (#56) --- .../endpoints/include/api_manager/request.h | 2 + .../api_manager/context/request_context.cc | 3 +- .../endpoints/src/api_manager/mixer/mixer.cc | 107 ++++++++++++------ .../endpoints/src/api_manager/mixer/mixer.h | 10 ++ .../src/api_manager/service_control/info.h | 8 +- src/envoy/prototype/api_manager_filter.cc | 1 + 6 files changed, 95 insertions(+), 36 deletions(-) diff --git a/contrib/endpoints/include/api_manager/request.h b/contrib/endpoints/include/api_manager/request.h index ad604b5a41b..8d96ff356d6 100644 --- a/contrib/endpoints/include/api_manager/request.h +++ b/contrib/endpoints/include/api_manager/request.h @@ -43,6 +43,8 @@ class Request { // Gets Client IP // This will be used by service control Check() call. virtual std::string GetClientIP() = 0; + // Gets Client Host. + virtual std::string GetClientHost() { return ""; } // Get GRPC stats. virtual int64_t GetGrpcRequestBytes() = 0; diff --git a/contrib/endpoints/src/api_manager/context/request_context.cc b/contrib/endpoints/src/api_manager/context/request_context.cc index cbf4e925e37..59cc7c3d53f 100644 --- a/contrib/endpoints/src/api_manager/context/request_context.cc +++ b/contrib/endpoints/src/api_manager/context/request_context.cc @@ -171,6 +171,8 @@ void RequestContext::FillOperationInfo(service_control::OperationInfo *info) { info->producer_project_id = service_context()->project_id(); info->referer = http_referer_; info->request_start_time = start_time_; + info->client_ip = request_->GetClientIP(); + info->client_host = request_->GetClientHost(); } void RequestContext::FillLocation(service_control::ReportRequestInfo *info) { @@ -221,7 +223,6 @@ void RequestContext::FillLogMessage(service_control::ReportRequestInfo *info) { void RequestContext::FillCheckRequestInfo( service_control::CheckRequestInfo *info) { FillOperationInfo(info); - info->client_ip = request_->GetClientIP(); info->allow_unregistered_calls = method()->allow_unregistered_calls(); } diff --git a/contrib/endpoints/src/api_manager/mixer/mixer.cc b/contrib/endpoints/src/api_manager/mixer/mixer.cc index 47f6c4a8a2f..e9ea9a30ea5 100644 --- a/contrib/endpoints/src/api_manager/mixer/mixer.cc +++ b/contrib/endpoints/src/api_manager/mixer/mixer.cc @@ -22,8 +22,11 @@ namespace api_manager { namespace mixer { namespace { +const std::string kProxyPeerID = "Istio/Proxy"; + const std::string kAttrNameServiceName = "serviceName"; const std::string kAttrNamePeerId = "peerId"; +const std::string kAttrNameOperationId = "operationId"; const std::string kAttrNameOperationName = "operationName"; const std::string kAttrNameApiKey = "apiKey"; const std::string kAttrNameResponseCode = "responseCode"; @@ -35,6 +38,9 @@ const std::string kAttrNameApiMethod = "apiMethod"; const std::string kAttrNameRequestSize = "requestSize"; const std::string kAttrNameResponseSize = "responseSize"; const std::string kAttrNameLogMessage = "logMessage"; +const std::string kAttrNameResponseTime = "responseTime"; +const std::string kAttrNameOriginIp = "originIp"; +const std::string kAttrNameOriginHost = "originHost"; Attributes::Value StringValue(const std::string& str) { Attributes::Value v; @@ -50,37 +56,6 @@ Attributes::Value Int64Value(int64_t value) { return v; } -void FillCheckAttributes(const service_control::CheckRequestInfo& info, - const std::string& service_name, - ::istio::mixer_client::Attributes* attr) { - attr->attributes[kAttrNameServiceName] = StringValue(service_name); - attr->attributes[kAttrNamePeerId] = StringValue("Proxy"); - attr->attributes[kAttrNameOperationName] = StringValue(info.operation_name); - attr->attributes[kAttrNameApiKey] = StringValue(info.api_key); -} - -void FillReportAttributes(const service_control::ReportRequestInfo& info, - const std::string& service_name, - ::istio::mixer_client::Attributes* attr) { - attr->attributes[kAttrNameServiceName] = StringValue(service_name); - attr->attributes[kAttrNamePeerId] = StringValue("Proxy"); - attr->attributes[kAttrNameOperationName] = StringValue(info.operation_name); - attr->attributes[kAttrNameApiKey] = StringValue(info.api_key); - - attr->attributes[kAttrNameURL] = StringValue(info.url); - attr->attributes[kAttrNameLocation] = StringValue(info.location); - - attr->attributes[kAttrNameApiName] = StringValue(info.api_name); - attr->attributes[kAttrNameApiVersion] = StringValue(info.api_version); - attr->attributes[kAttrNameApiMethod] = StringValue(info.api_method); - - attr->attributes[kAttrNameLogMessage] = StringValue(info.log_message); - - attr->attributes[kAttrNameResponseCode] = Int64Value(info.response_code); - attr->attributes[kAttrNameRequestSize] = Int64Value(info.request_size); - attr->attributes[kAttrNameResponseSize] = Int64Value(info.response_size); -} - } // namespace Mixer::Mixer(ApiManagerEnvInterface* env, const Config* config) @@ -98,9 +73,75 @@ Status Mixer::Init() { Status Mixer::Close() { return Status::OK; } +void Mixer::FillCommonAttributes(const service_control::OperationInfo& info, + ::istio::mixer_client::Attributes* attr) { + attr->attributes[kAttrNameServiceName] = StringValue(config_->service_name()); + attr->attributes[kAttrNamePeerId] = StringValue(kProxyPeerID); + + if (!info.operation_id.empty()) { + attr->attributes[kAttrNameOperationId] = StringValue(info.operation_id); + } + if (!info.operation_name.empty()) { + attr->attributes[kAttrNameOperationName] = StringValue(info.operation_name); + } + if (!info.api_key.empty()) { + attr->attributes[kAttrNameApiKey] = StringValue(info.api_key); + } + if (!info.client_ip.empty()) { + attr->attributes[kAttrNameOriginIp] = StringValue(info.client_ip); + } + if (!info.client_host.empty()) { + attr->attributes[kAttrNameOriginHost] = StringValue(info.client_host); + } +} + +void Mixer::FillCheckAttributes(const service_control::CheckRequestInfo& info, + ::istio::mixer_client::Attributes* attr) { + FillCommonAttributes(info, attr); +} + +void Mixer::FillReportAttributes(const service_control::ReportRequestInfo& info, + ::istio::mixer_client::Attributes* attr) { + FillCommonAttributes(info, attr); + + if (!info.url.empty()) { + attr->attributes[kAttrNameURL] = StringValue(info.url); + } + if (!info.location.empty()) { + attr->attributes[kAttrNameLocation] = StringValue(info.location); + } + + if (!info.api_name.empty()) { + attr->attributes[kAttrNameApiName] = StringValue(info.api_name); + } + if (!info.api_version.empty()) { + attr->attributes[kAttrNameApiVersion] = StringValue(info.api_version); + } + if (!info.api_method.empty()) { + attr->attributes[kAttrNameApiMethod] = StringValue(info.api_method); + } + + if (!info.log_message.empty()) { + attr->attributes[kAttrNameLogMessage] = StringValue(info.log_message); + } + + attr->attributes[kAttrNameResponseCode] = Int64Value(info.response_code); + if (info.request_size >= 0) { + attr->attributes[kAttrNameRequestSize] = Int64Value(info.request_size); + } + if (info.response_size >= 0) { + attr->attributes[kAttrNameResponseSize] = Int64Value(info.response_size); + } + + if (info.latency.request_time_ms >= 0) { + attr->attributes[kAttrNameResponseTime] = + Int64Value(info.latency.request_time_ms); + } +} + Status Mixer::Report(const service_control::ReportRequestInfo& info) { ::istio::mixer_client::Attributes attributes; - FillReportAttributes(info, config_->service_name(), &attributes); + FillReportAttributes(info, &attributes); env_->LogInfo("Send Report: "); mixer_client_->Report( attributes, [this](const ::google::protobuf::util::Status& status) { @@ -120,7 +161,7 @@ void Mixer::Check( std::function on_done) { ::istio::mixer_client::Attributes attributes; - FillCheckAttributes(info, config_->service_name(), &attributes); + FillCheckAttributes(info, &attributes); env_->LogInfo("Send Check: "); mixer_client_->Check( attributes, diff --git a/contrib/endpoints/src/api_manager/mixer/mixer.h b/contrib/endpoints/src/api_manager/mixer/mixer.h index 4cf2d1f54a7..b020d2636f9 100644 --- a/contrib/endpoints/src/api_manager/mixer/mixer.h +++ b/contrib/endpoints/src/api_manager/mixer/mixer.h @@ -50,6 +50,16 @@ class Mixer : public service_control::Interface { // The constructor. Mixer(ApiManagerEnvInterface* env, const Config* config); + // Fill common attributes for both check and report. + void FillCommonAttributes(const service_control::OperationInfo& info, + ::istio::mixer_client::Attributes* attr); + // Fill attributes for check. + void FillCheckAttributes(const service_control::CheckRequestInfo& info, + ::istio::mixer_client::Attributes* attr); + // Fill attributes for report. + void FillReportAttributes(const service_control::ReportRequestInfo& info, + ::istio::mixer_client::Attributes* attr); + // The Api Manager environment interface. ApiManagerEnvInterface* env_; // The config. diff --git a/contrib/endpoints/src/api_manager/service_control/info.h b/contrib/endpoints/src/api_manager/service_control/info.h index 15364ad58c6..f203057cc9e 100644 --- a/contrib/endpoints/src/api_manager/service_control/info.h +++ b/contrib/endpoints/src/api_manager/service_control/info.h @@ -60,13 +60,17 @@ struct OperationInfo { // and Report. std::chrono::system_clock::time_point request_start_time; + // The client IP address. + std::string client_ip; + + // The client host name. + std::string client_host; + OperationInfo() {} }; // Information to fill Check request protobuf. struct CheckRequestInfo : public OperationInfo { - // The client IP address. - std::string client_ip; // Whether the method allow unregistered calls. bool allow_unregistered_calls; diff --git a/src/envoy/prototype/api_manager_filter.cc b/src/envoy/prototype/api_manager_filter.cc index 4ccd9e6d120..869d8e6c500 100644 --- a/src/envoy/prototype/api_manager_filter.cc +++ b/src/envoy/prototype/api_manager_filter.cc @@ -81,6 +81,7 @@ class Request : public google::api_manager::Request { return header_map_.Path()->value().c_str(); } virtual std::string GetClientIP() override { return ""; } + virtual std::string GetClientHost() override { return ""; } virtual bool FindQuery(const std::string& name, std::string* query) override { if (!query_parsed_) { auto header = header_map_.Path(); From 4cd5c9f1d7c8367239021c35b9d72229a82353de Mon Sep 17 00:00:00 2001 From: Lizan Zhou Date: Fri, 27 Jan 2017 17:54:34 -0800 Subject: [PATCH 10/16] Add uuid-dev dependency in README.md (#45) --- src/envoy/prototype/README.md | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/src/envoy/prototype/README.md b/src/envoy/prototype/README.md index 00e73a169d6..dc73f63f6c9 100644 --- a/src/envoy/prototype/README.md +++ b/src/envoy/prototype/README.md @@ -1,6 +1,11 @@ This Proxy will use Envoy and talk to Mixer server. +## Install dependencies + +``` + apt-get install uuid-dev +``` ## Build Mixer server From bcdb75d2703050cb3d7b9b11b242a2304068cf90 Mon Sep 17 00:00:00 2001 From: Wayne Zhang Date: Sat, 28 Jan 2017 14:15:11 -0800 Subject: [PATCH 11/16] Extract originIp and OriginHost. (#57) * Extract originIp and OriginHost. * Make header x-forwarded-host const. --- src/envoy/prototype/api_manager_filter.cc | 56 +++++++++++++++++++++-- 1 file changed, 51 insertions(+), 5 deletions(-) diff --git a/src/envoy/prototype/api_manager_filter.cc b/src/envoy/prototype/api_manager_filter.cc index 869d8e6c500..d616ddfdf0f 100644 --- a/src/envoy/prototype/api_manager_filter.cc +++ b/src/envoy/prototype/api_manager_filter.cc @@ -13,6 +13,12 @@ namespace Http { namespace ApiManager { +namespace { + +// Define lower case string for X-Forwarded-Host. +const LowerCaseString kHeaderNameXFH("x-forwarded-host", false); + +} // namespace std::string ReadFile(const std::string& file_name) { std::ifstream t(file_name); @@ -65,12 +71,18 @@ typedef std::shared_ptr ConfigPtr; class Request : public google::api_manager::Request { private: HeaderMap& header_map_; + std::string downstream_address_; + std::string virtual_host_; bool query_parsed_; std::map query_params_; public: - Request(HeaderMap& header_map) - : header_map_(header_map), query_parsed_(false) {} + Request(HeaderMap& header_map, const std::string& downstream_address, + const std::string& virtual_host) + : header_map_(header_map), + downstream_address_(downstream_address), + virtual_host_(virtual_host), + query_parsed_(false) {} virtual std::string GetRequestHTTPMethod() override { return header_map_.Method()->value().c_str(); } @@ -80,8 +92,31 @@ class Request : public google::api_manager::Request { virtual std::string GetUnparsedRequestPath() override { return header_map_.Path()->value().c_str(); } - virtual std::string GetClientIP() override { return ""; } - virtual std::string GetClientHost() override { return ""; } + + virtual std::string GetClientIP() override { + if (!header_map_.ForwardedFor()) { + return downstream_address_; + } + std::vector xff_address_list = + StringUtil::split(header_map_.ForwardedFor()->value().c_str(), ','); + if (xff_address_list.empty()) { + return downstream_address_; + } + return xff_address_list.front(); + } + + virtual std::string GetClientHost() override { + const HeaderEntry* entry = header_map_.get(kHeaderNameXFH); + if (entry == nullptr) { + return virtual_host_; + } + auto xff_list = StringUtil::split(entry->value().c_str(), ','); + if (xff_list.empty()) { + return virtual_host_; + } + return xff_list.back(); + } + virtual bool FindQuery(const std::string& name, std::string* query) override { if (!query_parsed_) { auto header = header_map_.Path(); @@ -159,6 +194,15 @@ class Instance : public Http::StreamFilter, bool initiating_call_; + std::string getRouteVirtualHost(HeaderMap& headers) const { + const Router::Route* route = + decoder_callbacks_->routeTable().route(headers); + if (route && route->routeEntry()) { + return route->routeEntry()->virtualHost().name(); + } + return ""; + } + public: Instance(ConfigPtr config) : api_manager_(config->api_manager()), @@ -170,7 +214,9 @@ class Instance : public Http::StreamFilter, FilterHeadersStatus decodeHeaders(HeaderMap& headers, bool end_stream) override { log().debug("Called ApiManager::Instance : {}", __func__); - std::unique_ptr request(new Request(headers)); + std::unique_ptr request( + new Request(headers, decoder_callbacks_->downstreamAddress(), + getRouteVirtualHost(headers))); request_handler_ = api_manager_->CreateRequestHandler(std::move(request)); state_ = Calling; initiating_call_ = true; From 2c9c1af3d6ac5ab4d295444c30acd42599edfcb3 Mon Sep 17 00:00:00 2001 From: Qian Sun Date: Mon, 30 Jan 2017 15:03:42 -0800 Subject: [PATCH 12/16] Update buckets for UI. (#58) * Update buckets for UI. * Only update time_distribution. --- .../src/api_manager/service_control/proto.cc | 2 +- .../testdata/final_report_request.golden | 150 ++++++++++++++++-- .../testdata/report_request.golden | 150 ++++++++++++++++-- .../testdata/report_request_failed.golden | 75 ++++++++- 4 files changed, 346 insertions(+), 31 deletions(-) diff --git a/contrib/endpoints/src/api_manager/service_control/proto.cc b/contrib/endpoints/src/api_manager/service_control/proto.cc index 17b921db076..3e7eba64d21 100644 --- a/contrib/endpoints/src/api_manager/service_control/proto.cc +++ b/contrib/endpoints/src/api_manager/service_control/proto.cc @@ -96,7 +96,7 @@ struct DistributionHelperOptions { double scale; }; -const DistributionHelperOptions time_distribution = {8, 10.0, 1e-6}; +const DistributionHelperOptions time_distribution = {29, 2.0, 1e-6}; const DistributionHelperOptions size_distribution = {8, 10.0, 1}; const double kMsToSecs = 1e-3; diff --git a/contrib/endpoints/src/api_manager/service_control/testdata/final_report_request.golden b/contrib/endpoints/src/api_manager/service_control/testdata/final_report_request.golden index b9eff9f28eb..d60b039987d 100644 --- a/contrib/endpoints/src/api_manager/service_control/testdata/final_report_request.golden +++ b/contrib/endpoints/src/api_manager/service_control/testdata/final_report_request.golden @@ -201,13 +201,34 @@ operations { bucket_counts: 0 bucket_counts: 0 bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 bucket_counts: 1 bucket_counts: 0 bucket_counts: 0 bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 exponential_buckets { - num_finite_buckets: 8 - growth_factor: 10 + num_finite_buckets: 29 + growth_factor: 2 scale: 1e-06 } } @@ -227,13 +248,34 @@ operations { bucket_counts: 0 bucket_counts: 0 bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 bucket_counts: 1 bucket_counts: 0 bucket_counts: 0 bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 exponential_buckets { - num_finite_buckets: 8 - growth_factor: 10 + num_finite_buckets: 29 + growth_factor: 2 scale: 1e-06 } } @@ -253,13 +295,34 @@ operations { bucket_counts: 0 bucket_counts: 0 bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 bucket_counts: 1 bucket_counts: 0 bucket_counts: 0 bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 exponential_buckets { - num_finite_buckets: 8 - growth_factor: 10 + num_finite_buckets: 29 + growth_factor: 2 scale: 1e-06 } } @@ -279,13 +342,34 @@ operations { bucket_counts: 0 bucket_counts: 0 bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 bucket_counts: 1 bucket_counts: 0 bucket_counts: 0 bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 exponential_buckets { - num_finite_buckets: 8 - growth_factor: 10 + num_finite_buckets: 29 + growth_factor: 2 scale: 1e-06 } } @@ -304,14 +388,35 @@ operations { bucket_counts: 0 bucket_counts: 0 bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 bucket_counts: 1 bucket_counts: 0 bucket_counts: 0 bucket_counts: 0 bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 exponential_buckets { - num_finite_buckets: 8 - growth_factor: 10 + num_finite_buckets: 29 + growth_factor: 2 scale: 1e-06 } } @@ -330,14 +435,35 @@ operations { bucket_counts: 0 bucket_counts: 0 bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 bucket_counts: 1 bucket_counts: 0 bucket_counts: 0 bucket_counts: 0 bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 exponential_buckets { - num_finite_buckets: 8 - growth_factor: 10 + num_finite_buckets: 29 + growth_factor: 2 scale: 1e-06 } } diff --git a/contrib/endpoints/src/api_manager/service_control/testdata/report_request.golden b/contrib/endpoints/src/api_manager/service_control/testdata/report_request.golden index 5d8a266ef88..faf96383418 100644 --- a/contrib/endpoints/src/api_manager/service_control/testdata/report_request.golden +++ b/contrib/endpoints/src/api_manager/service_control/testdata/report_request.golden @@ -213,13 +213,34 @@ operations { bucket_counts: 0 bucket_counts: 0 bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 bucket_counts: 1 bucket_counts: 0 bucket_counts: 0 bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 exponential_buckets { - num_finite_buckets: 8 - growth_factor: 10 + num_finite_buckets: 29 + growth_factor: 2 scale: 1e-06 } } @@ -239,13 +260,34 @@ operations { bucket_counts: 0 bucket_counts: 0 bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 bucket_counts: 1 bucket_counts: 0 bucket_counts: 0 bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 exponential_buckets { - num_finite_buckets: 8 - growth_factor: 10 + num_finite_buckets: 29 + growth_factor: 2 scale: 1e-06 } } @@ -265,13 +307,34 @@ operations { bucket_counts: 0 bucket_counts: 0 bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 bucket_counts: 1 bucket_counts: 0 bucket_counts: 0 bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 exponential_buckets { - num_finite_buckets: 8 - growth_factor: 10 + num_finite_buckets: 29 + growth_factor: 2 scale: 1e-06 } } @@ -291,13 +354,34 @@ operations { bucket_counts: 0 bucket_counts: 0 bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 bucket_counts: 1 bucket_counts: 0 bucket_counts: 0 bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 exponential_buckets { - num_finite_buckets: 8 - growth_factor: 10 + num_finite_buckets: 29 + growth_factor: 2 scale: 1e-06 } } @@ -316,14 +400,35 @@ operations { bucket_counts: 0 bucket_counts: 0 bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 bucket_counts: 1 bucket_counts: 0 bucket_counts: 0 bucket_counts: 0 bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 exponential_buckets { - num_finite_buckets: 8 - growth_factor: 10 + num_finite_buckets: 29 + growth_factor: 2 scale: 1e-06 } } @@ -342,14 +447,35 @@ operations { bucket_counts: 0 bucket_counts: 0 bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 bucket_counts: 1 bucket_counts: 0 bucket_counts: 0 bucket_counts: 0 bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 exponential_buckets { - num_finite_buckets: 8 - growth_factor: 10 + num_finite_buckets: 29 + growth_factor: 2 scale: 1e-06 } } diff --git a/contrib/endpoints/src/api_manager/service_control/testdata/report_request_failed.golden b/contrib/endpoints/src/api_manager/service_control/testdata/report_request_failed.golden index a3ffd58c30d..710772cd215 100644 --- a/contrib/endpoints/src/api_manager/service_control/testdata/report_request_failed.golden +++ b/contrib/endpoints/src/api_manager/service_control/testdata/report_request_failed.golden @@ -152,13 +152,34 @@ operations { bucket_counts: 0 bucket_counts: 0 bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 bucket_counts: 1 bucket_counts: 0 bucket_counts: 0 bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 exponential_buckets { - num_finite_buckets: 8 - growth_factor: 10 + num_finite_buckets: 29 + growth_factor: 2 scale: 1e-06 } } @@ -178,13 +199,34 @@ operations { bucket_counts: 0 bucket_counts: 0 bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 bucket_counts: 1 bucket_counts: 0 bucket_counts: 0 bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 exponential_buckets { - num_finite_buckets: 8 - growth_factor: 10 + num_finite_buckets: 29 + growth_factor: 2 scale: 1e-06 } } @@ -203,14 +245,35 @@ operations { bucket_counts: 0 bucket_counts: 0 bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 bucket_counts: 1 bucket_counts: 0 bucket_counts: 0 bucket_counts: 0 bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 + bucket_counts: 0 exponential_buckets { - num_finite_buckets: 8 - growth_factor: 10 + num_finite_buckets: 29 + growth_factor: 2 scale: 1e-06 } } From 27962094adf801685a8547284fb60ca7c75ad1f8 Mon Sep 17 00:00:00 2001 From: Wayne Zhang Date: Tue, 31 Jan 2017 16:12:56 -0800 Subject: [PATCH 13/16] Add targetService attribute. (#59) --- contrib/endpoints/repositories.bzl | 2 +- contrib/endpoints/src/api_manager/mixer/mixer.cc | 11 +++++++++++ contrib/endpoints/src/api_manager/mixer/mixer.h | 2 ++ src/envoy/prototype/api_manager_env.cc | 2 +- src/envoy/prototype/api_manager_filter.cc | 3 +-- src/envoy/repositories.bzl | 2 +- 6 files changed, 17 insertions(+), 5 deletions(-) diff --git a/contrib/endpoints/repositories.bzl b/contrib/endpoints/repositories.bzl index 7b77aa91c5a..b1f14aae8b5 100644 --- a/contrib/endpoints/repositories.bzl +++ b/contrib/endpoints/repositories.bzl @@ -337,7 +337,7 @@ def servicecontrol_client_repositories(bind=True): def mixer_client_repositories(bind=True): native.git_repository( name = "mixerclient_git", - commit = "1569430f1e27b31e23c029c6bec0d8d5062d9e55", + commit = "80e450a5126960e8e6337c3631cf2ef984038eab", remote = "https://github.com/istio/mixerclient.git", ) diff --git a/contrib/endpoints/src/api_manager/mixer/mixer.cc b/contrib/endpoints/src/api_manager/mixer/mixer.cc index e9ea9a30ea5..53837edaf67 100644 --- a/contrib/endpoints/src/api_manager/mixer/mixer.cc +++ b/contrib/endpoints/src/api_manager/mixer/mixer.cc @@ -23,6 +23,7 @@ namespace mixer { namespace { const std::string kProxyPeerID = "Istio/Proxy"; +const std::string kEnvNameTargetService = "TARGET_SERVICE"; const std::string kAttrNameServiceName = "serviceName"; const std::string kAttrNamePeerId = "peerId"; @@ -41,6 +42,7 @@ const std::string kAttrNameLogMessage = "logMessage"; const std::string kAttrNameResponseTime = "responseTime"; const std::string kAttrNameOriginIp = "originIp"; const std::string kAttrNameOriginHost = "originHost"; +const std::string kAttrNameTargetService = "targetService"; Attributes::Value StringValue(const std::string& str) { Attributes::Value v; @@ -68,6 +70,10 @@ Status Mixer::Init() { options.mixer_server = config_->server_config()->mixer_options().mixer_server(); mixer_client_ = ::istio::mixer_client::CreateMixerClient(options); + auto target_service = getenv(kEnvNameTargetService.c_str()); + if (target_service) { + target_service_ = target_service; + } return Status::OK; } @@ -93,6 +99,9 @@ void Mixer::FillCommonAttributes(const service_control::OperationInfo& info, if (!info.client_host.empty()) { attr->attributes[kAttrNameOriginHost] = StringValue(info.client_host); } + if (!target_service_.empty()) { + attr->attributes[kAttrNameTargetService] = StringValue(target_service_); + } } void Mixer::FillCheckAttributes(const service_control::CheckRequestInfo& info, @@ -143,6 +152,7 @@ Status Mixer::Report(const service_control::ReportRequestInfo& info) { ::istio::mixer_client::Attributes attributes; FillReportAttributes(info, &attributes); env_->LogInfo("Send Report: "); + env_->LogInfo(attributes.DebugString()); mixer_client_->Report( attributes, [this](const ::google::protobuf::util::Status& status) { if (status.ok()) { @@ -163,6 +173,7 @@ void Mixer::Check( ::istio::mixer_client::Attributes attributes; FillCheckAttributes(info, &attributes); env_->LogInfo("Send Check: "); + env_->LogInfo(attributes.DebugString()); mixer_client_->Check( attributes, [this, on_done](const ::google::protobuf::util::Status& status) { diff --git a/contrib/endpoints/src/api_manager/mixer/mixer.h b/contrib/endpoints/src/api_manager/mixer/mixer.h index b020d2636f9..81276e1227d 100644 --- a/contrib/endpoints/src/api_manager/mixer/mixer.h +++ b/contrib/endpoints/src/api_manager/mixer/mixer.h @@ -66,6 +66,8 @@ class Mixer : public service_control::Interface { const Config* config_; // The mixer client std::unique_ptr<::istio::mixer_client::MixerClient> mixer_client_; + // Target service + std::string target_service_; }; } // namespace mixer diff --git a/src/envoy/prototype/api_manager_env.cc b/src/envoy/prototype/api_manager_env.cc index 6b1619a6faa..f8536bcc10a 100644 --- a/src/envoy/prototype/api_manager_env.cc +++ b/src/envoy/prototype/api_manager_env.cc @@ -103,7 +103,7 @@ class HTTPRequest : public Http::Message { virtual void body(Buffer::InstancePtr &&body) override {} virtual HeaderMap *trailers() override { return nullptr; } virtual void trailers(HeaderMapPtr &&trailers) override {} - virtual std::string bodyAsString() override { return ""; } + virtual std::string bodyAsString() const override { return ""; } }; class HTTPRequestCallbacks : public AsyncClient::Callbacks { diff --git a/src/envoy/prototype/api_manager_filter.cc b/src/envoy/prototype/api_manager_filter.cc index d616ddfdf0f..87a3beeb48a 100644 --- a/src/envoy/prototype/api_manager_filter.cc +++ b/src/envoy/prototype/api_manager_filter.cc @@ -195,8 +195,7 @@ class Instance : public Http::StreamFilter, bool initiating_call_; std::string getRouteVirtualHost(HeaderMap& headers) const { - const Router::Route* route = - decoder_callbacks_->routeTable().route(headers); + const Router::Route* route = decoder_callbacks_->route(); if (route && route->routeEntry()) { return route->routeEntry()->virtualHost().name(); } diff --git a/src/envoy/repositories.bzl b/src/envoy/repositories.bzl index dd36a23d456..e19efc6dce1 100644 --- a/src/envoy/repositories.bzl +++ b/src/envoy/repositories.bzl @@ -629,6 +629,6 @@ cc_test( native.new_git_repository( name = "envoy_git", remote = "https://github.com/lyft/envoy.git", - commit = "c36bb76e304ab4c5584a07303e2953a170888319", + commit = "39f42378fa41c10996d4c3ffba534951de30ceb8", build_file_content = BUILD, ) From 8218f92089a6ac36f851f3cacbf761e443e5f8a1 Mon Sep 17 00:00:00 2001 From: Wayne Zhang Date: Wed, 1 Feb 2017 12:08:31 -0800 Subject: [PATCH 14/16] Use envoy new access_log handler for sending Report. (#60) * use access_log handler. * Not to use Loggable base class. --- src/envoy/prototype/api_manager_filter.cc | 61 ++++++++++++++--------- src/envoy/prototype/envoy-esp.conf | 3 +- src/envoy/repositories.bzl | 2 +- 3 files changed, 40 insertions(+), 26 deletions(-) diff --git a/src/envoy/prototype/api_manager_filter.cc b/src/envoy/prototype/api_manager_filter.cc index 87a3beeb48a..3983a4d8b41 100644 --- a/src/envoy/prototype/api_manager_filter.cc +++ b/src/envoy/prototype/api_manager_filter.cc @@ -163,24 +163,30 @@ class Request : public google::api_manager::Request { }; class Response : public google::api_manager::Response { + const AccessLog::RequestInfo& request_info_; + + public: + Response(const AccessLog::RequestInfo& request_info) + : request_info_(request_info) {} + google::api_manager::utils::Status GetResponseStatus() { return google::api_manager::utils::Status::OK; } - std::size_t GetRequestSize() { return 0; } + std::size_t GetRequestSize() { return request_info_.bytesReceived(); } - std::size_t GetResponseSize() { return 0; } + std::size_t GetResponseSize() { return request_info_.bytesSent(); } google::api_manager::utils::Status GetLatencyInfo( google::api_manager::service_control::LatencyInfo* info) { + info->request_time_ms = request_info_.duration().count(); return google::api_manager::utils::Status::OK; } }; const Http::HeaderMapImpl BadRequest{{Http::Headers::get().Status, "400"}}; -class Instance : public Http::StreamFilter, - public Logger::Loggable { +class Instance : public Http::StreamFilter, public Http::AccessLog::Instance { private: std::shared_ptr api_manager_; std::unique_ptr @@ -207,12 +213,12 @@ class Instance : public Http::StreamFilter, : api_manager_(config->api_manager()), state_(NotStarted), initiating_call_(false) { - log().debug("Called ApiManager::Instance : {}", __func__); + Log().debug("Called ApiManager::Instance : {}", __func__); } FilterHeadersStatus decodeHeaders(HeaderMap& headers, bool end_stream) override { - log().debug("Called ApiManager::Instance : {}", __func__); + Log().debug("Called ApiManager::Instance : {}", __func__); std::unique_ptr request( new Request(headers, decoder_callbacks_->downstreamAddress(), getRouteVirtualHost(headers))); @@ -227,13 +233,13 @@ class Instance : public Http::StreamFilter, if (state_ == Complete) { return FilterHeadersStatus::Continue; } - log().debug("Called ApiManager::Instance : {} Stop", __func__); + Log().debug("Called ApiManager::Instance : {} Stop", __func__); return FilterHeadersStatus::StopIteration; } FilterDataStatus decodeData(Buffer::Instance& data, bool end_stream) override { - log().debug("Called ApiManager::Instance : {} ({}, {})", __func__, + Log().debug("Called ApiManager::Instance : {} ({}, {})", __func__, data.length(), end_stream); if (state_ == Calling) { return FilterDataStatus::StopIterationAndBuffer; @@ -242,7 +248,7 @@ class Instance : public Http::StreamFilter, } FilterTrailersStatus decodeTrailers(HeaderMap& trailers) override { - log().debug("Called ApiManager::Instance : {}", __func__); + Log().debug("Called ApiManager::Instance : {}", __func__); if (state_ == Calling) { return FilterTrailersStatus::StopIteration; } @@ -250,13 +256,13 @@ class Instance : public Http::StreamFilter, } void setDecoderFilterCallbacks( StreamDecoderFilterCallbacks& callbacks) override { - log().debug("Called ApiManager::Instance : {}", __func__); + Log().debug("Called ApiManager::Instance : {}", __func__); decoder_callbacks_ = &callbacks; decoder_callbacks_->addResetStreamCallback( [this]() { state_ = Responded; }); } void completeCheck(const google::api_manager::utils::Status& status) { - log().debug("Called ApiManager::Instance : check complete {}", + Log().debug("Called ApiManager::Instance : check complete {}", status.ToJson()); if (!status.ok() && state_ != Responded) { state_ = Responded; @@ -275,30 +281,37 @@ class Instance : public Http::StreamFilter, virtual FilterHeadersStatus encodeHeaders(HeaderMap& headers, bool end_stream) override { - log().debug("Called ApiManager::Instance : {}", __func__); + Log().debug("Called ApiManager::Instance : {}", __func__); return FilterHeadersStatus::Continue; } virtual FilterDataStatus encodeData(Buffer::Instance& data, bool end_stream) override { - log().debug("Called ApiManager::Instance : {}", __func__); + Log().debug("Called ApiManager::Instance : {}", __func__); return FilterDataStatus::Continue; } virtual FilterTrailersStatus encodeTrailers(HeaderMap& trailers) override { - log().debug("Called ApiManager::Instance : {}", __func__); + Log().debug("Called ApiManager::Instance : {}", __func__); return FilterTrailersStatus::Continue; } virtual void setEncoderFilterCallbacks( StreamEncoderFilterCallbacks& callbacks) override { - log().debug("Called ApiManager::Instance : {}", __func__); + Log().debug("Called ApiManager::Instance : {}", __func__); encoder_callbacks_ = &callbacks; } - // note: cannot extend ~ActiveStream for access log, placing it here - ~Instance() { - log().debug("Called ApiManager::Instance : {}", __func__); - std::unique_ptr response(new Response()); - request_handler_->Report(std::move(response), - [this]() { log().debug("Report returns"); }); + virtual void log(const HeaderMap* request_headers, + const HeaderMap* response_headers, + const AccessLog::RequestInfo& request_info) override { + Log().debug("Called ApiManager::Instance : {}", __func__); + std::unique_ptr response( + new Response(request_info)); + request_handler_->Report(std::move(response), []() {}); + } + + spdlog::logger& Log() { + static spdlog::logger& instance = + Logger::Registry::getLog(Logger::Id::http); + return instance; } }; } @@ -320,8 +333,10 @@ class ApiManagerConfig : public HttpFilterConfigFactory { new Http::ApiManager::Config(config, server)); return [api_manager_config]( Http::FilterChainFactoryCallbacks& callbacks) -> void { - auto instance = new Http::ApiManager::Instance(api_manager_config); - callbacks.addStreamFilter(Http::StreamFilterPtr{instance}); + std::shared_ptr instance( + new Http::ApiManager::Instance(api_manager_config)); + callbacks.addStreamFilter(Http::StreamFilterPtr(instance)); + callbacks.addAccessLogHandler(Http::AccessLog::InstancePtr(instance)); }; } }; diff --git a/src/envoy/prototype/envoy-esp.conf b/src/envoy/prototype/envoy-esp.conf index d3ec54f405d..27ea9f1b397 100644 --- a/src/envoy/prototype/envoy-esp.conf +++ b/src/envoy/prototype/envoy-esp.conf @@ -85,6 +85,5 @@ ] } ] - }, - "tracing_enabled": "true" + } } diff --git a/src/envoy/repositories.bzl b/src/envoy/repositories.bzl index e19efc6dce1..d14053308e1 100644 --- a/src/envoy/repositories.bzl +++ b/src/envoy/repositories.bzl @@ -629,6 +629,6 @@ cc_test( native.new_git_repository( name = "envoy_git", remote = "https://github.com/lyft/envoy.git", - commit = "39f42378fa41c10996d4c3ffba534951de30ceb8", + commit = "0bac7508c6803ec315c2228672728281b99149bd", build_file_content = BUILD, ) From 1d2d6a84989321ed20c3504704ce6c249188c166 Mon Sep 17 00:00:00 2001 From: Wayne Zhang Date: Wed, 1 Feb 2017 17:57:55 -0800 Subject: [PATCH 15/16] Update to the latest envoy with #396. (#61) --- src/envoy/repositories.bzl | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/envoy/repositories.bzl b/src/envoy/repositories.bzl index d14053308e1..7cc4cb2db48 100644 --- a/src/envoy/repositories.bzl +++ b/src/envoy/repositories.bzl @@ -629,6 +629,6 @@ cc_test( native.new_git_repository( name = "envoy_git", remote = "https://github.com/lyft/envoy.git", - commit = "0bac7508c6803ec315c2228672728281b99149bd", + commit = "02c6fc97b4c21d25ab596a25208fbe283e927f6a", build_file_content = BUILD, ) From 53fd02610571f8c05af2e50fea911f89f935e678 Mon Sep 17 00:00:00 2001 From: Kuat Date: Thu, 2 Feb 2017 11:52:57 -0800 Subject: [PATCH 16/16] Fix tclap dependency fetching error (#62) --- src/envoy/repositories.bzl | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/envoy/repositories.bzl b/src/envoy/repositories.bzl index 7cc4cb2db48..94f371ebc7d 100644 --- a/src/envoy/repositories.bzl +++ b/src/envoy/repositories.bzl @@ -221,7 +221,7 @@ cc_library( native.new_http_archive( name = "tclap_tar", - url = "https://sourceforge.net/projects/tclap/files/tclap-1.2.1.tar.gz/download", + url = "https://storage.googleapis.com/istio-build-deps/tclap-1.2.1.tar.gz", type = "tar.gz", strip_prefix = "tclap-1.2.1", build_file_content = BUILD,