Welcome to mirror list, hosted at ThFree Co, Russian Federation.

gitlab.com/gitlab-org/gitaly.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--CHANGELOG.md46
-rw-r--r--Dockerfile2
-rw-r--r--NOTICE947
-rw-r--r--README.md20
-rw-r--r--VERSION2
-rw-r--r--_support/makegen.go6
-rw-r--r--auth/extract_test.go2
-rw-r--r--auth/rpccredentials.go2
-rw-r--r--auth/token.go2
-rw-r--r--changelogs/unreleased/1302-fix-rename-namespace-rpc-logging.yml5
-rw-r--r--changelogs/unreleased/1441-1442-update-docs-monitoring.yml5
-rw-r--r--changelogs/unreleased/fix-raw-changes-bug.yml5
-rw-r--r--changelogs/unreleased/fix-rebase-test-flake.yml5
-rw-r--r--changelogs/unreleased/jc-migrate-find-commits.yml5
-rw-r--r--changelogs/unreleased/jc-rewrite-get-commit-message.yml5
-rw-r--r--changelogs/unreleased/jv-prepare-hooks.yml5
-rw-r--r--changelogs/unreleased/megacheck-staticcheck.yml5
-rw-r--r--changelogs/unreleased/migrate-writeref.yml5
-rw-r--r--changelogs/unreleased/remove-request-store.yml5
-rw-r--r--changelogs/unreleased/sh-fix-issue-1329.yml5
-rw-r--r--changelogs/unreleased/simplify-error-handling.yml5
-rw-r--r--client/address_parser.go32
-rw-r--r--client/address_parser_test.go74
-rw-r--r--client/dial.go70
-rw-r--r--client/dial_test.go250
-rw-r--r--client/pool_darwin.go (renamed from client/pool-darwin.go)5
-rw-r--r--client/receive_pack.go2
-rw-r--r--client/testdata/gitalycert.pem30
-rw-r--r--client/testdata/gitalykey.pem52
-rw-r--r--client/upload_archive.go2
-rw-r--r--client/upload_pack.go2
-rw-r--r--cmd/gitaly-ssh/auth_test.go65
-rw-r--r--cmd/gitaly/main.go2
-rw-r--r--internal/featureflag/grpc_header.go2
-rw-r--r--internal/featureflag/grpc_header_test.go2
-rw-r--r--internal/helper/chunker/chunker.go59
-rw-r--r--internal/helper/housekeeping/housekeeping.go2
-rw-r--r--internal/helper/housekeeping/housekeeping_test.go2
-rw-r--r--internal/helper/storage.go2
-rw-r--r--internal/middleware/cancelhandler/cancelhandler.go3
-rw-r--r--internal/middleware/limithandler/concurrency_limiter.go2
-rw-r--r--internal/middleware/limithandler/concurrency_limiter_test.go2
-rw-r--r--internal/middleware/limithandler/limithandler.go3
-rw-r--r--internal/middleware/limithandler/limithandler_test.go2
-rw-r--r--internal/middleware/limithandler/metrics.go2
-rw-r--r--internal/middleware/limithandler/testhelper_test.go2
-rw-r--r--internal/middleware/limithandler/testpb/test.pb.go3
-rw-r--r--internal/middleware/metadatahandler/metadatahandler.go3
-rw-r--r--internal/middleware/panichandler/panic_handler.go3
-rw-r--r--internal/middleware/sentryhandler/sentryhandler.go2
-rw-r--r--internal/middleware/sentryhandler/sentryhandler_test.go2
-rw-r--r--internal/rubyserver/health.go2
-rw-r--r--internal/rubyserver/rubyserver.go5
-rw-r--r--internal/server/auth/auth.go2
-rw-r--r--internal/server/auth_test.go2
-rw-r--r--internal/server/server.go5
-rw-r--r--internal/service/commit/between_test.go2
-rw-r--r--internal/service/commit/commits_by_message_test.go2
-rw-r--r--internal/service/commit/count_commits.go2
-rw-r--r--internal/service/commit/count_commits_test.go2
-rw-r--r--internal/service/commit/extractsignature_test.go2
-rw-r--r--internal/service/commit/find_all_commits_test.go2
-rw-r--r--internal/service/commit/find_commit.go3
-rw-r--r--internal/service/commit/find_commit_test.go2
-rw-r--r--internal/service/commit/isancestor.go3
-rw-r--r--internal/service/commit/isancestor_test.go2
-rw-r--r--internal/service/commit/languages.go2
-rw-r--r--internal/service/commit/last_commit_for_path.go2
-rw-r--r--internal/service/commit/last_commit_for_path_test.go2
-rw-r--r--internal/service/commit/list_commits_by_oid.go33
-rw-r--r--internal/service/commit/list_commits_by_oid_test.go2
-rw-r--r--internal/service/commit/list_files.go86
-rw-r--r--internal/service/commit/list_files_test.go2
-rw-r--r--internal/service/commit/list_last_commits_for_tree_test.go2
-rw-r--r--internal/service/commit/raw_blame_test.go2
-rw-r--r--internal/service/commit/stats.go3
-rw-r--r--internal/service/commit/tree_entries.go28
-rw-r--r--internal/service/commit/tree_entries_test.go2
-rw-r--r--internal/service/commit/tree_entry_test.go2
-rw-r--r--internal/service/diff/commit_test.go2
-rw-r--r--internal/service/diff/numstat_test.go2
-rw-r--r--internal/service/diff/raw.go2
-rw-r--r--internal/service/namespace/namespace.go2
-rw-r--r--internal/service/namespace/namespace_test.go2
-rw-r--r--internal/service/operations/branches.go3
-rw-r--r--internal/service/operations/branches_test.go2
-rw-r--r--internal/service/operations/cherry_pick.go3
-rw-r--r--internal/service/operations/merge.go2
-rw-r--r--internal/service/operations/rebase.go2
-rw-r--r--internal/service/operations/revert.go3
-rw-r--r--internal/service/operations/squash.go2
-rw-r--r--internal/service/operations/submodules.go2
-rw-r--r--internal/service/operations/tags.go3
-rw-r--r--internal/service/operations/update_branches_test.go2
-rw-r--r--internal/service/ref/branches.go2
-rw-r--r--internal/service/ref/delete_refs.go2
-rw-r--r--internal/service/ref/refexists.go2
-rw-r--r--internal/service/ref/refname.go2
-rw-r--r--internal/service/ref/refname_test.go2
-rw-r--r--internal/service/ref/refs.go2
-rw-r--r--internal/service/ref/refs_test.go2
-rw-r--r--internal/service/ref/remote_branches_test.go2
-rw-r--r--internal/service/remote/fetch_internal_remote.go2
-rw-r--r--internal/service/remote/find_remote_root_ref.go2
-rw-r--r--internal/service/remote/remotes.go2
-rw-r--r--internal/service/remote/remotes_test.go2
-rw-r--r--internal/service/remote/update_remote_mirror_test.go2
-rw-r--r--internal/service/repository/apply_gitattributes.go2
-rw-r--r--internal/service/repository/calculate_checksum.go2
-rw-r--r--internal/service/repository/cleanup.go2
-rw-r--r--internal/service/repository/config.go3
-rw-r--r--internal/service/repository/create.go3
-rw-r--r--internal/service/repository/create_from_snapshot.go5
-rw-r--r--internal/service/repository/create_from_url.go2
-rw-r--r--internal/service/repository/fetch.go3
-rw-r--r--internal/service/repository/fetch_remote.go3
-rw-r--r--internal/service/repository/fork.go2
-rw-r--r--internal/service/repository/fsck.go2
-rw-r--r--internal/service/repository/gc.go2
-rw-r--r--internal/service/repository/license.go3
-rw-r--r--internal/service/repository/merge_base.go2
-rw-r--r--internal/service/repository/rebase_in_progress.go2
-rw-r--r--internal/service/repository/repack.go3
-rw-r--r--internal/service/repository/repository.go2
-rw-r--r--internal/service/repository/repository_test.go2
-rw-r--r--internal/service/repository/size.go2
-rw-r--r--internal/service/repository/size_test.go2
-rw-r--r--internal/service/repository/squash_in_progress.go2
-rw-r--r--internal/service/repository/util.go2
-rw-r--r--internal/service/repository/write_config.go3
-rw-r--r--internal/service/repository/write_ref.go2
-rw-r--r--internal/service/server/info.go2
-rw-r--r--internal/service/smarthttp/inforefs_test.go2
-rw-r--r--internal/service/smarthttp/receive_pack_test.go2
-rw-r--r--internal/service/smarthttp/upload_pack_test.go2
-rw-r--r--internal/service/ssh/receive_pack.go35
-rw-r--r--internal/service/ssh/receive_pack_test.go2
-rw-r--r--internal/service/ssh/upload_archive.go36
-rw-r--r--internal/service/ssh/upload_archive_test.go2
-rw-r--r--internal/service/ssh/upload_pack.go33
-rw-r--r--internal/service/ssh/upload_pack_test.go2
-rw-r--r--internal/service/storage/deleteall.go2
-rw-r--r--internal/service/wiki/delete_page.go2
-rw-r--r--ruby/lib/gitaly_server/repository_service.rb16
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/tracing/opentracing/DOC.md118
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/tracing/opentracing/README.md118
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/tracing/opentracing/client_interceptors.go142
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/tracing/opentracing/doc.go22
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/tracing/opentracing/id_extract.go50
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/tracing/opentracing/metadata.go56
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/tracing/opentracing/options.go55
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/tracing/opentracing/server_interceptors.go86
-rw-r--r--vendor/github.com/lightstep/lightstep-tracer-go/CHANGELOG.md54
-rw-r--r--vendor/github.com/lightstep/lightstep-tracer-go/Gopkg.lock217
-rw-r--r--vendor/github.com/lightstep/lightstep-tracer-go/Gopkg.toml23
-rw-r--r--vendor/github.com/lightstep/lightstep-tracer-go/LICENSE21
-rw-r--r--vendor/github.com/lightstep/lightstep-tracer-go/Makefile87
-rw-r--r--vendor/github.com/lightstep/lightstep-tracer-go/README.md116
-rw-r--r--vendor/github.com/lightstep/lightstep-tracer-go/VERSION1
-rw-r--r--vendor/github.com/lightstep/lightstep-tracer-go/collector_client.go55
-rw-r--r--vendor/github.com/lightstep/lightstep-tracer-go/collector_client_grpc.go134
-rw-r--r--vendor/github.com/lightstep/lightstep-tracer-go/collector_client_http.go188
-rw-r--r--vendor/github.com/lightstep/lightstep-tracer-go/collector_client_thrift.go201
-rw-r--r--vendor/github.com/lightstep/lightstep-tracer-go/collectorpb/collector.go10
-rw-r--r--vendor/github.com/lightstep/lightstep-tracer-go/collectorpb/collector.pb.go903
-rw-r--r--vendor/github.com/lightstep/lightstep-tracer-go/event_handlers.go97
-rw-r--r--vendor/github.com/lightstep/lightstep-tracer-go/events.go330
-rw-r--r--vendor/github.com/lightstep/lightstep-tracer-go/lightstep/rand/locked_rand.go138
-rw-r--r--vendor/github.com/lightstep/lightstep-tracer-go/lightstep/rand/num_gen.go7
-rw-r--r--vendor/github.com/lightstep/lightstep-tracer-go/lightstep/rand/pool.go59
-rw-r--r--vendor/github.com/lightstep/lightstep-tracer-go/lightstep_thrift/constants.go18
-rw-r--r--vendor/github.com/lightstep/lightstep-tracer-go/lightstep_thrift/reportingservice.go449
-rw-r--r--vendor/github.com/lightstep/lightstep-tracer-go/lightstep_thrift/reportingservice_methods.go10
-rw-r--r--vendor/github.com/lightstep/lightstep-tracer-go/lightstep_thrift/ttypes.go3489
-rw-r--r--vendor/github.com/lightstep/lightstep-tracer-go/lightsteppb/lightstep.pb.go127
-rw-r--r--vendor/github.com/lightstep/lightstep-tracer-go/options.go344
-rw-r--r--vendor/github.com/lightstep/lightstep-tracer-go/propagation_binary.go111
-rw-r--r--vendor/github.com/lightstep/lightstep-tracer-go/propagation_text.go97
-rw-r--r--vendor/github.com/lightstep/lightstep-tracer-go/proto_converter.go191
-rw-r--r--vendor/github.com/lightstep/lightstep-tracer-go/proto_logencoder.go110
-rw-r--r--vendor/github.com/lightstep/lightstep-tracer-go/raw_span.go72
-rw-r--r--vendor/github.com/lightstep/lightstep-tracer-go/report_buffer.go79
-rw-r--r--vendor/github.com/lightstep/lightstep-tracer-go/span.go266
-rwxr-xr-xvendor/github.com/lightstep/lightstep-tracer-go/tag_version.sh10
-rw-r--r--vendor/github.com/lightstep/lightstep-tracer-go/thrift_logencoder.go76
-rw-r--r--vendor/github.com/lightstep/lightstep-tracer-go/tracer.go376
-rw-r--r--vendor/github.com/lightstep/lightstep-tracer-go/tracer_0_14.go45
-rw-r--r--vendor/github.com/lightstep/lightstep-tracer-go/tracer_helpers.go83
-rw-r--r--vendor/github.com/lightstep/lightstep-tracer-go/util.go32
-rw-r--r--vendor/github.com/lightstep/lightstep-tracer-go/version.go4
-rw-r--r--vendor/github.com/lightstep/thrift/LICENSE261
-rw-r--r--vendor/github.com/lightstep/thrift/NOTICE5
-rw-r--r--vendor/github.com/lightstep/thrift/lib/go/thrift/application_exception.go142
-rw-r--r--vendor/github.com/lightstep/thrift/lib/go/thrift/binary_protocol.go484
-rw-r--r--vendor/github.com/lightstep/thrift/lib/go/thrift/buffered_transport.go70
-rw-r--r--vendor/github.com/lightstep/thrift/lib/go/thrift/compact_protocol.go797
-rw-r--r--vendor/github.com/lightstep/thrift/lib/go/thrift/debug_protocol.go269
-rw-r--r--vendor/github.com/lightstep/thrift/lib/go/thrift/deserializer.go58
-rw-r--r--vendor/github.com/lightstep/thrift/lib/go/thrift/exception.go25
-rw-r--r--vendor/github.com/lightstep/thrift/lib/go/thrift/field.go79
-rw-r--r--vendor/github.com/lightstep/thrift/lib/go/thrift/framed_transport.go151
-rw-r--r--vendor/github.com/lightstep/thrift/lib/go/thrift/http_client.go286
-rw-r--r--vendor/github.com/lightstep/thrift/lib/go/thrift/iostream_transport.go205
-rw-r--r--vendor/github.com/lightstep/thrift/lib/go/thrift/json_protocol.go552
-rw-r--r--vendor/github.com/lightstep/thrift/lib/go/thrift/memory_buffer.go79
-rw-r--r--vendor/github.com/lightstep/thrift/lib/go/thrift/messagetype.go31
-rw-r--r--vendor/github.com/lightstep/thrift/lib/go/thrift/multiplexed_protocol.go169
-rw-r--r--vendor/github.com/lightstep/thrift/lib/go/thrift/numeric.go164
-rw-r--r--vendor/github.com/lightstep/thrift/lib/go/thrift/pointerize.go50
-rw-r--r--vendor/github.com/lightstep/thrift/lib/go/thrift/processor.go30
-rw-r--r--vendor/github.com/lightstep/thrift/lib/go/thrift/processor_factory.go58
-rw-r--r--vendor/github.com/lightstep/thrift/lib/go/thrift/protocol.go154
-rw-r--r--vendor/github.com/lightstep/thrift/lib/go/thrift/protocol_exception.go77
-rw-r--r--vendor/github.com/lightstep/thrift/lib/go/thrift/protocol_factory.go25
-rw-r--r--vendor/github.com/lightstep/thrift/lib/go/thrift/rich_transport.go64
-rw-r--r--vendor/github.com/lightstep/thrift/lib/go/thrift/serializer.go75
-rw-r--r--vendor/github.com/lightstep/thrift/lib/go/thrift/serializer_types.go595
-rw-r--r--vendor/github.com/lightstep/thrift/lib/go/thrift/server.go35
-rw-r--r--vendor/github.com/lightstep/thrift/lib/go/thrift/server_socket.go127
-rw-r--r--vendor/github.com/lightstep/thrift/lib/go/thrift/server_transport.go34
-rw-r--r--vendor/github.com/lightstep/thrift/lib/go/thrift/simple_json_protocol.go1250
-rw-r--r--vendor/github.com/lightstep/thrift/lib/go/thrift/simple_server.go188
-rw-r--r--vendor/github.com/lightstep/thrift/lib/go/thrift/socket.go159
-rw-r--r--vendor/github.com/lightstep/thrift/lib/go/thrift/ssl_server_socket.go109
-rw-r--r--vendor/github.com/lightstep/thrift/lib/go/thrift/ssl_socket.go161
-rw-r--r--vendor/github.com/lightstep/thrift/lib/go/thrift/transport.go59
-rw-r--r--vendor/github.com/lightstep/thrift/lib/go/thrift/transport_exception.go90
-rw-r--r--vendor/github.com/lightstep/thrift/lib/go/thrift/transport_factory.go39
-rw-r--r--vendor/github.com/lightstep/thrift/lib/go/thrift/type.go68
-rw-r--r--vendor/github.com/opentracing/opentracing-go/CHANGELOG.md14
-rw-r--r--vendor/github.com/opentracing/opentracing-go/LICENSE201
-rw-r--r--vendor/github.com/opentracing/opentracing-go/Makefile32
-rw-r--r--vendor/github.com/opentracing/opentracing-go/README.md171
-rw-r--r--vendor/github.com/opentracing/opentracing-go/ext/tags.go210
-rw-r--r--vendor/github.com/opentracing/opentracing-go/globaltracer.go32
-rw-r--r--vendor/github.com/opentracing/opentracing-go/gocontext.go54
-rw-r--r--vendor/github.com/opentracing/opentracing-go/log/field.go269
-rw-r--r--vendor/github.com/opentracing/opentracing-go/log/util.go54
-rw-r--r--vendor/github.com/opentracing/opentracing-go/noop.go64
-rw-r--r--vendor/github.com/opentracing/opentracing-go/propagation.go176
-rw-r--r--vendor/github.com/opentracing/opentracing-go/span.go189
-rw-r--r--vendor/github.com/opentracing/opentracing-go/tracer.go305
-rw-r--r--vendor/github.com/philhofer/fwd/LICENSE.md7
-rw-r--r--vendor/github.com/philhofer/fwd/README.md315
-rw-r--r--vendor/github.com/philhofer/fwd/reader.go383
-rw-r--r--vendor/github.com/philhofer/fwd/writer.go224
-rw-r--r--vendor/github.com/philhofer/fwd/writer_appengine.go5
-rw-r--r--vendor/github.com/philhofer/fwd/writer_unsafe.go18
-rw-r--r--vendor/github.com/tinylib/msgp/LICENSE8
-rw-r--r--vendor/github.com/tinylib/msgp/msgp/advise_linux.go24
-rw-r--r--vendor/github.com/tinylib/msgp/msgp/advise_other.go17
-rw-r--r--vendor/github.com/tinylib/msgp/msgp/circular.go39
-rw-r--r--vendor/github.com/tinylib/msgp/msgp/defs.go142
-rw-r--r--vendor/github.com/tinylib/msgp/msgp/edit.go242
-rw-r--r--vendor/github.com/tinylib/msgp/msgp/elsize.go99
-rw-r--r--vendor/github.com/tinylib/msgp/msgp/errors.go314
-rw-r--r--vendor/github.com/tinylib/msgp/msgp/extension.go549
-rw-r--r--vendor/github.com/tinylib/msgp/msgp/file.go92
-rw-r--r--vendor/github.com/tinylib/msgp/msgp/file_port.go47
-rw-r--r--vendor/github.com/tinylib/msgp/msgp/integers.go174
-rw-r--r--vendor/github.com/tinylib/msgp/msgp/json.go542
-rw-r--r--vendor/github.com/tinylib/msgp/msgp/json_bytes.go363
-rw-r--r--vendor/github.com/tinylib/msgp/msgp/number.go267
-rw-r--r--vendor/github.com/tinylib/msgp/msgp/purego.go15
-rw-r--r--vendor/github.com/tinylib/msgp/msgp/read.go1358
-rw-r--r--vendor/github.com/tinylib/msgp/msgp/read_bytes.go1197
-rw-r--r--vendor/github.com/tinylib/msgp/msgp/size.go38
-rw-r--r--vendor/github.com/tinylib/msgp/msgp/unsafe.go41
-rw-r--r--vendor/github.com/tinylib/msgp/msgp/write.go845
-rw-r--r--vendor/github.com/tinylib/msgp/msgp/write_bytes.go411
-rw-r--r--vendor/github.com/uber/jaeger-client-go/CHANGELOG.md197
-rw-r--r--vendor/github.com/uber/jaeger-client-go/CONTRIBUTING.md170
-rw-r--r--vendor/github.com/uber/jaeger-client-go/DCO37
-rw-r--r--vendor/github.com/uber/jaeger-client-go/Gopkg.lock164
-rw-r--r--vendor/github.com/uber/jaeger-client-go/Gopkg.toml27
-rw-r--r--vendor/github.com/uber/jaeger-client-go/LICENSE201
-rw-r--r--vendor/github.com/uber/jaeger-client-go/Makefile117
-rw-r--r--vendor/github.com/uber/jaeger-client-go/README.md270
-rw-r--r--vendor/github.com/uber/jaeger-client-go/RELEASE.md11
-rw-r--r--vendor/github.com/uber/jaeger-client-go/baggage_setter.go77
-rw-r--r--vendor/github.com/uber/jaeger-client-go/config/config.go394
-rw-r--r--vendor/github.com/uber/jaeger-client-go/config/config_env.go221
-rw-r--r--vendor/github.com/uber/jaeger-client-go/config/options.go148
-rw-r--r--vendor/github.com/uber/jaeger-client-go/constants.go88
-rw-r--r--vendor/github.com/uber/jaeger-client-go/context.go258
-rw-r--r--vendor/github.com/uber/jaeger-client-go/contrib_observer.go56
-rw-r--r--vendor/github.com/uber/jaeger-client-go/doc.go24
-rw-r--r--vendor/github.com/uber/jaeger-client-go/glide.lock89
-rw-r--r--vendor/github.com/uber/jaeger-client-go/glide.yaml22
-rw-r--r--vendor/github.com/uber/jaeger-client-go/header.go64
-rw-r--r--vendor/github.com/uber/jaeger-client-go/internal/baggage/remote/options.go101
-rw-r--r--vendor/github.com/uber/jaeger-client-go/internal/baggage/remote/restriction_manager.go157
-rw-r--r--vendor/github.com/uber/jaeger-client-go/internal/baggage/restriction_manager.go71
-rw-r--r--vendor/github.com/uber/jaeger-client-go/internal/spanlog/json.go81
-rw-r--r--vendor/github.com/uber/jaeger-client-go/internal/throttler/remote/options.go99
-rw-r--r--vendor/github.com/uber/jaeger-client-go/internal/throttler/remote/throttler.go216
-rw-r--r--vendor/github.com/uber/jaeger-client-go/internal/throttler/throttler.go32
-rw-r--r--vendor/github.com/uber/jaeger-client-go/interop.go55
-rw-r--r--vendor/github.com/uber/jaeger-client-go/jaeger_tag.go84
-rw-r--r--vendor/github.com/uber/jaeger-client-go/jaeger_thrift_span.go179
-rw-r--r--vendor/github.com/uber/jaeger-client-go/log/logger.go90
-rw-r--r--vendor/github.com/uber/jaeger-client-go/logger.go53
-rw-r--r--vendor/github.com/uber/jaeger-client-go/metrics.go107
-rw-r--r--vendor/github.com/uber/jaeger-client-go/observer.go88
-rw-r--r--vendor/github.com/uber/jaeger-client-go/process.go29
-rw-r--r--vendor/github.com/uber/jaeger-client-go/propagation.go300
-rw-r--r--vendor/github.com/uber/jaeger-client-go/reference.go23
-rw-r--r--vendor/github.com/uber/jaeger-client-go/reporter.go289
-rw-r--r--vendor/github.com/uber/jaeger-client-go/reporter_options.go69
-rw-r--r--vendor/github.com/uber/jaeger-client-go/rpcmetrics/README.md5
-rw-r--r--vendor/github.com/uber/jaeger-client-go/rpcmetrics/doc.go16
-rw-r--r--vendor/github.com/uber/jaeger-client-go/rpcmetrics/endpoints.go63
-rw-r--r--vendor/github.com/uber/jaeger-client-go/rpcmetrics/metrics.go124
-rw-r--r--vendor/github.com/uber/jaeger-client-go/rpcmetrics/normalizer.go101
-rw-r--r--vendor/github.com/uber/jaeger-client-go/rpcmetrics/observer.go171
-rw-r--r--vendor/github.com/uber/jaeger-client-go/sampler.go557
-rw-r--r--vendor/github.com/uber/jaeger-client-go/sampler_options.go81
-rw-r--r--vendor/github.com/uber/jaeger-client-go/span.go249
-rw-r--r--vendor/github.com/uber/jaeger-client-go/thrift-gen/agent/agent.go411
-rw-r--r--vendor/github.com/uber/jaeger-client-go/thrift-gen/agent/constants.go23
-rw-r--r--vendor/github.com/uber/jaeger-client-go/thrift-gen/agent/ttypes.go21
-rw-r--r--vendor/github.com/uber/jaeger-client-go/thrift-gen/baggage/baggagerestrictionmanager.go435
-rw-r--r--vendor/github.com/uber/jaeger-client-go/thrift-gen/baggage/constants.go18
-rw-r--r--vendor/github.com/uber/jaeger-client-go/thrift-gen/baggage/ttypes.go154
-rw-r--r--vendor/github.com/uber/jaeger-client-go/thrift-gen/jaeger/agent.go242
-rw-r--r--vendor/github.com/uber/jaeger-client-go/thrift-gen/jaeger/constants.go18
-rw-r--r--vendor/github.com/uber/jaeger-client-go/thrift-gen/jaeger/ttypes.go1838
-rw-r--r--vendor/github.com/uber/jaeger-client-go/thrift-gen/sampling/constants.go18
-rw-r--r--vendor/github.com/uber/jaeger-client-go/thrift-gen/sampling/samplingmanager.go410
-rw-r--r--vendor/github.com/uber/jaeger-client-go/thrift-gen/sampling/ttypes.go873
-rw-r--r--vendor/github.com/uber/jaeger-client-go/thrift-gen/zipkincore/constants.go32
-rw-r--r--vendor/github.com/uber/jaeger-client-go/thrift-gen/zipkincore/ttypes.go1247
-rw-r--r--vendor/github.com/uber/jaeger-client-go/thrift-gen/zipkincore/zipkincollector.go446
-rw-r--r--vendor/github.com/uber/jaeger-client-go/thrift/README.md7
-rw-r--r--vendor/github.com/uber/jaeger-client-go/thrift/application_exception.go142
-rw-r--r--vendor/github.com/uber/jaeger-client-go/thrift/binary_protocol.go514
-rw-r--r--vendor/github.com/uber/jaeger-client-go/thrift/compact_protocol.go815
-rw-r--r--vendor/github.com/uber/jaeger-client-go/thrift/exception.go44
-rw-r--r--vendor/github.com/uber/jaeger-client-go/thrift/memory_buffer.go79
-rw-r--r--vendor/github.com/uber/jaeger-client-go/thrift/messagetype.go31
-rw-r--r--vendor/github.com/uber/jaeger-client-go/thrift/numeric.go164
-rw-r--r--vendor/github.com/uber/jaeger-client-go/thrift/processor.go30
-rw-r--r--vendor/github.com/uber/jaeger-client-go/thrift/protocol.go175
-rw-r--r--vendor/github.com/uber/jaeger-client-go/thrift/protocol_exception.go78
-rw-r--r--vendor/github.com/uber/jaeger-client-go/thrift/protocol_factory.go25
-rw-r--r--vendor/github.com/uber/jaeger-client-go/thrift/rich_transport.go69
-rw-r--r--vendor/github.com/uber/jaeger-client-go/thrift/serializer.go75
-rw-r--r--vendor/github.com/uber/jaeger-client-go/thrift/simple_json_protocol.go1337
-rw-r--r--vendor/github.com/uber/jaeger-client-go/thrift/transport.go68
-rw-r--r--vendor/github.com/uber/jaeger-client-go/thrift/transport_exception.go90
-rw-r--r--vendor/github.com/uber/jaeger-client-go/thrift/transport_factory.go39
-rw-r--r--vendor/github.com/uber/jaeger-client-go/thrift/type.go69
-rw-r--r--vendor/github.com/uber/jaeger-client-go/tracer.go431
-rw-r--r--vendor/github.com/uber/jaeger-client-go/tracer_options.go159
-rw-r--r--vendor/github.com/uber/jaeger-client-go/transport.go38
-rw-r--r--vendor/github.com/uber/jaeger-client-go/transport/doc.go23
-rw-r--r--vendor/github.com/uber/jaeger-client-go/transport/http.go163
-rw-r--r--vendor/github.com/uber/jaeger-client-go/transport_udp.go131
-rw-r--r--vendor/github.com/uber/jaeger-client-go/utils/http_json.go54
-rw-r--r--vendor/github.com/uber/jaeger-client-go/utils/localip.go84
-rw-r--r--vendor/github.com/uber/jaeger-client-go/utils/rand.go46
-rw-r--r--vendor/github.com/uber/jaeger-client-go/utils/rate_limiter.go77
-rw-r--r--vendor/github.com/uber/jaeger-client-go/utils/udp_client.go98
-rw-r--r--vendor/github.com/uber/jaeger-client-go/utils/utils.go87
-rw-r--r--vendor/github.com/uber/jaeger-client-go/zipkin.go76
-rw-r--r--vendor/github.com/uber/jaeger-client-go/zipkin_thrift_span.go322
-rw-r--r--vendor/github.com/uber/jaeger-lib/LICENSE201
-rw-r--r--vendor/github.com/uber/jaeger-lib/metrics/counter.go28
-rw-r--r--vendor/github.com/uber/jaeger-lib/metrics/factory.go35
-rw-r--r--vendor/github.com/uber/jaeger-lib/metrics/gauge.go28
-rw-r--r--vendor/github.com/uber/jaeger-lib/metrics/keys.go35
-rw-r--r--vendor/github.com/uber/jaeger-lib/metrics/metrics.go90
-rw-r--r--vendor/github.com/uber/jaeger-lib/metrics/stopwatch.go43
-rw-r--r--vendor/github.com/uber/jaeger-lib/metrics/timer.go33
-rw-r--r--vendor/gitlab.com/gitlab-org/labkit/correlation/context.go3
-rw-r--r--vendor/gitlab.com/gitlab-org/labkit/correlation/doc.go18
-rw-r--r--vendor/gitlab.com/gitlab-org/labkit/correlation/inbound_http.go22
-rw-r--r--vendor/gitlab.com/gitlab-org/labkit/correlation/inbound_http_options.go14
-rw-r--r--vendor/gitlab.com/gitlab-org/labkit/correlation/outbound_http.go5
-rw-r--r--vendor/gitlab.com/gitlab-org/labkit/tracing/connstr/connection_string_parser.go55
-rw-r--r--vendor/gitlab.com/gitlab-org/labkit/tracing/errors.go8
-rw-r--r--vendor/gitlab.com/gitlab-org/labkit/tracing/grpc/client_interceptors.go16
-rw-r--r--vendor/gitlab.com/gitlab-org/labkit/tracing/grpc/server_interceptors.go16
-rw-r--r--vendor/gitlab.com/gitlab-org/labkit/tracing/impl/constants.go3
-rw-r--r--vendor/gitlab.com/gitlab-org/labkit/tracing/impl/datadog_tracer.go24
-rw-r--r--vendor/gitlab.com/gitlab-org/labkit/tracing/impl/jaeger_tracer.go96
-rw-r--r--vendor/gitlab.com/gitlab-org/labkit/tracing/impl/lightstep_tracer.go71
-rw-r--r--vendor/gitlab.com/gitlab-org/labkit/tracing/impl/null_tracer.go15
-rw-r--r--vendor/gitlab.com/gitlab-org/labkit/tracing/impl/static_tracer.go20
-rw-r--r--vendor/gitlab.com/gitlab-org/labkit/tracing/impl/tracer_registry.go15
-rw-r--r--vendor/gitlab.com/gitlab-org/labkit/tracing/inbound_http.go48
-rw-r--r--vendor/gitlab.com/gitlab-org/labkit/tracing/inbound_http_options.go42
-rw-r--r--vendor/gitlab.com/gitlab-org/labkit/tracing/initialization.go53
-rw-r--r--vendor/gitlab.com/gitlab-org/labkit/tracing/initialization_options.go43
-rw-r--r--vendor/gitlab.com/gitlab-org/labkit/tracing/outbound_http.go143
-rw-r--r--vendor/gitlab.com/gitlab-org/labkit/tracing/outbound_http_options.go28
-rw-r--r--vendor/google.golang.org/genproto/googleapis/api/annotations/annotations.pb.go54
-rw-r--r--vendor/google.golang.org/genproto/googleapis/api/annotations/http.pb.go688
-rw-r--r--vendor/gopkg.in/DataDog/dd-trace-go.v1/LICENSE24
-rw-r--r--vendor/gopkg.in/DataDog/dd-trace-go.v1/LICENSE-3rdparty.csv2
-rw-r--r--vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/Gopkg.toml9
-rw-r--r--vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/ddtrace.go111
-rw-r--r--vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/ext/app_types.go70
-rw-r--r--vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/ext/cassandra.go21
-rw-r--r--vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/ext/db.go16
-rw-r--r--vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/ext/peer.go14
-rw-r--r--vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/ext/priority.go22
-rw-r--r--vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/ext/system.go7
-rw-r--r--vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/ext/tags.go57
-rw-r--r--vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/internal/globaltracer.go98
-rw-r--r--vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/opentracer/option.go24
-rw-r--r--vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/opentracer/span.go83
-rw-r--r--vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/opentracer/tracer.go81
-rw-r--r--vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/context.go42
-rw-r--r--vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/doc.go50
-rw-r--r--vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/errors.go69
-rw-r--r--vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/option.go198
-rw-r--r--vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/payload.go116
-rw-r--r--vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/propagator.go52
-rw-r--r--vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/rand.go50
-rw-r--r--vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/sampler.go140
-rw-r--r--vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/span.go241
-rw-r--r--vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/span_msgp.go448
-rw-r--r--vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/spancontext.go193
-rw-r--r--vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/textmap.go197
-rw-r--r--vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/time.go10
-rw-r--r--vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/time_windows.go35
-rw-r--r--vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/tracer.go380
-rw-r--r--vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/transport.go152
-rw-r--r--vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/util.go50
-rw-r--r--vendor/vendor.json274
431 files changed, 51240 insertions, 373 deletions
diff --git a/CHANGELOG.md b/CHANGELOG.md
index 0b6fba80e..1c021ee59 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -1,5 +1,51 @@
# Gitaly changelog
+## v1.13.0
+
+#### Fixed
+- Fix 503 errors when Git outputs warnings to stderr
+ https://gitlab.com/gitlab-org/gitaly/merge_requests/1024
+- Fix regression for https_proxy and unix socket connections
+ https://gitlab.com/gitlab-org/gitaly/merge_requests/1032
+- Fix flaky rebase test
+ https://gitlab.com/gitlab-org/gitaly/merge_requests/1028
+- Rewrite GetRawChanges and fix quoting bug
+ https://gitlab.com/gitlab-org/gitaly/merge_requests/1026
+- Fix logging of RenameNamespace RPC parameters
+ https://gitlab.com/gitlab-org/gitaly/merge_requests/847
+
+#### Other
+- Small refactors to gitaly/client
+ https://gitlab.com/gitlab-org/gitaly/merge_requests/1034
+- Prepare for vendoring gitlab-shell hooks
+ https://gitlab.com/gitlab-org/gitaly/merge_requests/1020
+- Replace golang.org/x/net/context with context package
+ https://gitlab.com/gitlab-org/gitaly/merge_requests/1038
+- Migrate writeref from using the ruby implementation to go
+ https://gitlab.com/gitlab-org/gitaly/merge_requests/1008
+ Contributed by johncai
+- Switch from honnef.co/go/tools/megacheck to staticcheck
+ https://gitlab.com/gitlab-org/gitaly/merge_requests/1021
+- Add distributed tracing support with LabKit
+ https://gitlab.com/gitlab-org/gitaly/merge_requests/976
+- Simplify error wrapping in service/ref
+ https://gitlab.com/gitlab-org/gitaly/merge_requests/1009
+- Remove dummy RequestStore
+ https://gitlab.com/gitlab-org/gitaly/merge_requests/1007
+- Simplify error handling in ssh package
+ https://gitlab.com/gitlab-org/gitaly/merge_requests/1029
+- Add response chunker abstraction
+ https://gitlab.com/gitlab-org/gitaly/merge_requests/1031
+- Use go implementation of FindCommits
+ https://gitlab.com/gitlab-org/gitaly/merge_requests/1025
+- Rewrite get commit message
+ https://gitlab.com/gitlab-org/gitaly/merge_requests/1012
+- Update docs about monitoring and README
+ https://gitlab.com/gitlab-org/gitaly/merge_requests/1016
+ Contributed by Takuya Noguchi
+- Remove unused Ruby rebase/squash code
+ https://gitlab.com/gitlab-org/gitaly/merge_requests/1033
+
## v1.12.0
#### Fixed
diff --git a/Dockerfile b/Dockerfile
index 12e952066..11959e0ca 100644
--- a/Dockerfile
+++ b/Dockerfile
@@ -6,7 +6,7 @@
# See the _support/load-cluster/docker-compose.yml for an example of how to use
# this image
#
-FROM registry.gitlab.com/gitlab-org/gitlab-build-images:ruby-2-5-golang-1.11-git-2.18
+FROM registry.gitlab.com/gitlab-org/gitlab-build-images:ruby-2.5-golang-1.11-git-2.18
RUN mkdir -p /app/ruby
diff --git a/NOTICE b/NOTICE
index d07b2643b..bb67bf9c4 100644
--- a/NOTICE
+++ b/NOTICE
@@ -664,6 +664,298 @@ The above copyright notice and this permission notice shall be included in all c
THE SOFTWARE IS PROVIDED 'AS IS', WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+LICENSE - gitlab.com/gitlab-org/gitaly/vendor/github.com/lightstep/lightstep-tracer-go
+The MIT License (MIT)
+
+Copyright (c) 2016
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in all
+copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+SOFTWARE.
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+LICENSE - gitlab.com/gitlab-org/gitaly/vendor/github.com/lightstep/thrift
+
+ Apache License
+ Version 2.0, January 2004
+ http://www.apache.org/licenses/
+
+ TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
+
+ 1. Definitions.
+
+ "License" shall mean the terms and conditions for use, reproduction,
+ and distribution as defined by Sections 1 through 9 of this document.
+
+ "Licensor" shall mean the copyright owner or entity authorized by
+ the copyright owner that is granting the License.
+
+ "Legal Entity" shall mean the union of the acting entity and all
+ other entities that control, are controlled by, or are under common
+ control with that entity. For the purposes of this definition,
+ "control" means (i) the power, direct or indirect, to cause the
+ direction or management of such entity, whether by contract or
+ otherwise, or (ii) ownership of fifty percent (50%) or more of the
+ outstanding shares, or (iii) beneficial ownership of such entity.
+
+ "You" (or "Your") shall mean an individual or Legal Entity
+ exercising permissions granted by this License.
+
+ "Source" form shall mean the preferred form for making modifications,
+ including but not limited to software source code, documentation
+ source, and configuration files.
+
+ "Object" form shall mean any form resulting from mechanical
+ transformation or translation of a Source form, including but
+ not limited to compiled object code, generated documentation,
+ and conversions to other media types.
+
+ "Work" shall mean the work of authorship, whether in Source or
+ Object form, made available under the License, as indicated by a
+ copyright notice that is included in or attached to the work
+ (an example is provided in the Appendix below).
+
+ "Derivative Works" shall mean any work, whether in Source or Object
+ form, that is based on (or derived from) the Work and for which the
+ editorial revisions, annotations, elaborations, or other modifications
+ represent, as a whole, an original work of authorship. For the purposes
+ of this License, Derivative Works shall not include works that remain
+ separable from, or merely link (or bind by name) to the interfaces of,
+ the Work and Derivative Works thereof.
+
+ "Contribution" shall mean any work of authorship, including
+ the original version of the Work and any modifications or additions
+ to that Work or Derivative Works thereof, that is intentionally
+ submitted to Licensor for inclusion in the Work by the copyright owner
+ or by an individual or Legal Entity authorized to submit on behalf of
+ the copyright owner. For the purposes of this definition, "submitted"
+ means any form of electronic, verbal, or written communication sent
+ to the Licensor or its representatives, including but not limited to
+ communication on electronic mailing lists, source code control systems,
+ and issue tracking systems that are managed by, or on behalf of, the
+ Licensor for the purpose of discussing and improving the Work, but
+ excluding communication that is conspicuously marked or otherwise
+ designated in writing by the copyright owner as "Not a Contribution."
+
+ "Contributor" shall mean Licensor and any individual or Legal Entity
+ on behalf of whom a Contribution has been received by Licensor and
+ subsequently incorporated within the Work.
+
+ 2. Grant of Copyright License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ copyright license to reproduce, prepare Derivative Works of,
+ publicly display, publicly perform, sublicense, and distribute the
+ Work and such Derivative Works in Source or Object form.
+
+ 3. Grant of Patent License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ (except as stated in this section) patent license to make, have made,
+ use, offer to sell, sell, import, and otherwise transfer the Work,
+ where such license applies only to those patent claims licensable
+ by such Contributor that are necessarily infringed by their
+ Contribution(s) alone or by combination of their Contribution(s)
+ with the Work to which such Contribution(s) was submitted. If You
+ institute patent litigation against any entity (including a
+ cross-claim or counterclaim in a lawsuit) alleging that the Work
+ or a Contribution incorporated within the Work constitutes direct
+ or contributory patent infringement, then any patent licenses
+ granted to You under this License for that Work shall terminate
+ as of the date such litigation is filed.
+
+ 4. Redistribution. You may reproduce and distribute copies of the
+ Work or Derivative Works thereof in any medium, with or without
+ modifications, and in Source or Object form, provided that You
+ meet the following conditions:
+
+ (a) You must give any other recipients of the Work or
+ Derivative Works a copy of this License; and
+
+ (b) You must cause any modified files to carry prominent notices
+ stating that You changed the files; and
+
+ (c) You must retain, in the Source form of any Derivative Works
+ that You distribute, all copyright, patent, trademark, and
+ attribution notices from the Source form of the Work,
+ excluding those notices that do not pertain to any part of
+ the Derivative Works; and
+
+ (d) If the Work includes a "NOTICE" text file as part of its
+ distribution, then any Derivative Works that You distribute must
+ include a readable copy of the attribution notices contained
+ within such NOTICE file, excluding those notices that do not
+ pertain to any part of the Derivative Works, in at least one
+ of the following places: within a NOTICE text file distributed
+ as part of the Derivative Works; within the Source form or
+ documentation, if provided along with the Derivative Works; or,
+ within a display generated by the Derivative Works, if and
+ wherever such third-party notices normally appear. The contents
+ of the NOTICE file are for informational purposes only and
+ do not modify the License. You may add Your own attribution
+ notices within Derivative Works that You distribute, alongside
+ or as an addendum to the NOTICE text from the Work, provided
+ that such additional attribution notices cannot be construed
+ as modifying the License.
+
+ You may add Your own copyright statement to Your modifications and
+ may provide additional or different license terms and conditions
+ for use, reproduction, or distribution of Your modifications, or
+ for any such Derivative Works as a whole, provided Your use,
+ reproduction, and distribution of the Work otherwise complies with
+ the conditions stated in this License.
+
+ 5. Submission of Contributions. Unless You explicitly state otherwise,
+ any Contribution intentionally submitted for inclusion in the Work
+ by You to the Licensor shall be under the terms and conditions of
+ this License, without any additional terms or conditions.
+ Notwithstanding the above, nothing herein shall supersede or modify
+ the terms of any separate license agreement you may have executed
+ with Licensor regarding such Contributions.
+
+ 6. Trademarks. This License does not grant permission to use the trade
+ names, trademarks, service marks, or product names of the Licensor,
+ except as required for reasonable and customary use in describing the
+ origin of the Work and reproducing the content of the NOTICE file.
+
+ 7. Disclaimer of Warranty. Unless required by applicable law or
+ agreed to in writing, Licensor provides the Work (and each
+ Contributor provides its Contributions) on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
+ implied, including, without limitation, any warranties or conditions
+ of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
+ PARTICULAR PURPOSE. You are solely responsible for determining the
+ appropriateness of using or redistributing the Work and assume any
+ risks associated with Your exercise of permissions under this License.
+
+ 8. Limitation of Liability. In no event and under no legal theory,
+ whether in tort (including negligence), contract, or otherwise,
+ unless required by applicable law (such as deliberate and grossly
+ negligent acts) or agreed to in writing, shall any Contributor be
+ liable to You for damages, including any direct, indirect, special,
+ incidental, or consequential damages of any character arising as a
+ result of this License or out of the use or inability to use the
+ Work (including but not limited to damages for loss of goodwill,
+ work stoppage, computer failure or malfunction, or any and all
+ other commercial damages or losses), even if such Contributor
+ has been advised of the possibility of such damages.
+
+ 9. Accepting Warranty or Additional Liability. While redistributing
+ the Work or Derivative Works thereof, You may choose to offer,
+ and charge a fee for, acceptance of support, warranty, indemnity,
+ or other liability obligations and/or rights consistent with this
+ License. However, in accepting such obligations, You may act only
+ on Your own behalf and on Your sole responsibility, not on behalf
+ of any other Contributor, and only if You agree to indemnify,
+ defend, and hold each Contributor harmless for any liability
+ incurred by, or claims asserted against, such Contributor by reason
+ of your accepting any such warranty or additional liability.
+
+ END OF TERMS AND CONDITIONS
+
+ APPENDIX: How to apply the Apache License to your work.
+
+ To apply the Apache License to your work, attach the following
+ boilerplate notice, with the fields enclosed by brackets "[]"
+ replaced with your own identifying information. (Don't include
+ the brackets!) The text should be enclosed in the appropriate
+ comment syntax for the file format. We also recommend that a
+ file or class name and description of purpose be included on the
+ same "printed page" as the copyright notice for easier
+ identification within third-party archives.
+
+ Copyright [yyyy] [name of copyright owner]
+
+ 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.
+
+--------------------------------------------------
+SOFTWARE DISTRIBUTED WITH THRIFT:
+
+The Apache Thrift software includes a number of subcomponents with
+separate copyright notices and license terms. Your use of the source
+code for the these subcomponents is subject to the terms and
+conditions of the following licenses.
+
+--------------------------------------------------
+Portions of the following files are licensed under the MIT License:
+
+ lib/erl/src/Makefile.am
+
+Please see doc/otp-base-license.txt for the full terms of this license.
+
+--------------------------------------------------
+For the aclocal/ax_boost_base.m4 and contrib/fb303/aclocal/ax_boost_base.m4 components:
+
+# Copyright (c) 2007 Thomas Porschberg <thomas@randspringer.de>
+#
+# Copying and distribution of this file, with or without
+# modification, are permitted in any medium without royalty provided
+# the copyright notice and this notice are preserved.
+
+--------------------------------------------------
+For the compiler/cpp/src/thrift/md5.[ch] components:
+
+/*
+ Copyright (C) 1999, 2000, 2002 Aladdin Enterprises. All rights reserved.
+
+ This software is provided 'as-is', without any express or implied
+ warranty. In no event will the authors be held liable for any damages
+ arising from the use of this software.
+
+ Permission is granted to anyone to use this software for any purpose,
+ including commercial applications, and to alter it and redistribute it
+ freely, subject to the following restrictions:
+
+ 1. The origin of this software must not be misrepresented; you must not
+ claim that you wrote the original software. If you use this software
+ in a product, an acknowledgment in the product documentation would be
+ appreciated but is not required.
+ 2. Altered source versions must be plainly marked as such, and must not be
+ misrepresented as being the original software.
+ 3. This notice may not be removed or altered from any source distribution.
+
+ L. Peter Deutsch
+ ghost@aladdin.com
+
+ */
+
+---------------------------------------------------
+For the lib/rb/setup.rb: Copyright (c) 2000-2005 Minero Aoki,
+lib/ocaml/OCamlMakefile and lib/ocaml/README-OCamlMakefile components:
+ Copyright (C) 1999 - 2007 Markus Mottl
+
+Licensed under the terms of the GNU Lesser General Public License 2.1
+(see doc/lgpl-2.1.txt for the full terms of this license)
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+NOTICE - gitlab.com/gitlab-org/gitaly/vendor/github.com/lightstep/thrift
+Apache Thrift
+Copyright 2006-2010 The Apache Software Foundation.
+
+This product includes software developed at
+The Apache Software Foundation (http://www.apache.org/).~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
LICENSE - gitlab.com/gitlab-org/gitaly/vendor/github.com/matttproud/golang_protobuf_extensions
Apache License
Version 2.0, January 2004
@@ -870,6 +1162,217 @@ LICENSE - gitlab.com/gitlab-org/gitaly/vendor/github.com/matttproud/golang_proto
NOTICE - gitlab.com/gitlab-org/gitaly/vendor/github.com/matttproud/golang_protobuf_extensions
Copyright 2012 Matt T. Proud (matt.proud@gmail.com)
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+LICENSE - gitlab.com/gitlab-org/gitaly/vendor/github.com/opentracing/opentracing-go
+ Apache License
+ Version 2.0, January 2004
+ http://www.apache.org/licenses/
+
+ TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
+
+ 1. Definitions.
+
+ "License" shall mean the terms and conditions for use, reproduction,
+ and distribution as defined by Sections 1 through 9 of this document.
+
+ "Licensor" shall mean the copyright owner or entity authorized by
+ the copyright owner that is granting the License.
+
+ "Legal Entity" shall mean the union of the acting entity and all
+ other entities that control, are controlled by, or are under common
+ control with that entity. For the purposes of this definition,
+ "control" means (i) the power, direct or indirect, to cause the
+ direction or management of such entity, whether by contract or
+ otherwise, or (ii) ownership of fifty percent (50%) or more of the
+ outstanding shares, or (iii) beneficial ownership of such entity.
+
+ "You" (or "Your") shall mean an individual or Legal Entity
+ exercising permissions granted by this License.
+
+ "Source" form shall mean the preferred form for making modifications,
+ including but not limited to software source code, documentation
+ source, and configuration files.
+
+ "Object" form shall mean any form resulting from mechanical
+ transformation or translation of a Source form, including but
+ not limited to compiled object code, generated documentation,
+ and conversions to other media types.
+
+ "Work" shall mean the work of authorship, whether in Source or
+ Object form, made available under the License, as indicated by a
+ copyright notice that is included in or attached to the work
+ (an example is provided in the Appendix below).
+
+ "Derivative Works" shall mean any work, whether in Source or Object
+ form, that is based on (or derived from) the Work and for which the
+ editorial revisions, annotations, elaborations, or other modifications
+ represent, as a whole, an original work of authorship. For the purposes
+ of this License, Derivative Works shall not include works that remain
+ separable from, or merely link (or bind by name) to the interfaces of,
+ the Work and Derivative Works thereof.
+
+ "Contribution" shall mean any work of authorship, including
+ the original version of the Work and any modifications or additions
+ to that Work or Derivative Works thereof, that is intentionally
+ submitted to Licensor for inclusion in the Work by the copyright owner
+ or by an individual or Legal Entity authorized to submit on behalf of
+ the copyright owner. For the purposes of this definition, "submitted"
+ means any form of electronic, verbal, or written communication sent
+ to the Licensor or its representatives, including but not limited to
+ communication on electronic mailing lists, source code control systems,
+ and issue tracking systems that are managed by, or on behalf of, the
+ Licensor for the purpose of discussing and improving the Work, but
+ excluding communication that is conspicuously marked or otherwise
+ designated in writing by the copyright owner as "Not a Contribution."
+
+ "Contributor" shall mean Licensor and any individual or Legal Entity
+ on behalf of whom a Contribution has been received by Licensor and
+ subsequently incorporated within the Work.
+
+ 2. Grant of Copyright License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ copyright license to reproduce, prepare Derivative Works of,
+ publicly display, publicly perform, sublicense, and distribute the
+ Work and such Derivative Works in Source or Object form.
+
+ 3. Grant of Patent License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ (except as stated in this section) patent license to make, have made,
+ use, offer to sell, sell, import, and otherwise transfer the Work,
+ where such license applies only to those patent claims licensable
+ by such Contributor that are necessarily infringed by their
+ Contribution(s) alone or by combination of their Contribution(s)
+ with the Work to which such Contribution(s) was submitted. If You
+ institute patent litigation against any entity (including a
+ cross-claim or counterclaim in a lawsuit) alleging that the Work
+ or a Contribution incorporated within the Work constitutes direct
+ or contributory patent infringement, then any patent licenses
+ granted to You under this License for that Work shall terminate
+ as of the date such litigation is filed.
+
+ 4. Redistribution. You may reproduce and distribute copies of the
+ Work or Derivative Works thereof in any medium, with or without
+ modifications, and in Source or Object form, provided that You
+ meet the following conditions:
+
+ (a) You must give any other recipients of the Work or
+ Derivative Works a copy of this License; and
+
+ (b) You must cause any modified files to carry prominent notices
+ stating that You changed the files; and
+
+ (c) You must retain, in the Source form of any Derivative Works
+ that You distribute, all copyright, patent, trademark, and
+ attribution notices from the Source form of the Work,
+ excluding those notices that do not pertain to any part of
+ the Derivative Works; and
+
+ (d) If the Work includes a "NOTICE" text file as part of its
+ distribution, then any Derivative Works that You distribute must
+ include a readable copy of the attribution notices contained
+ within such NOTICE file, excluding those notices that do not
+ pertain to any part of the Derivative Works, in at least one
+ of the following places: within a NOTICE text file distributed
+ as part of the Derivative Works; within the Source form or
+ documentation, if provided along with the Derivative Works; or,
+ within a display generated by the Derivative Works, if and
+ wherever such third-party notices normally appear. The contents
+ of the NOTICE file are for informational purposes only and
+ do not modify the License. You may add Your own attribution
+ notices within Derivative Works that You distribute, alongside
+ or as an addendum to the NOTICE text from the Work, provided
+ that such additional attribution notices cannot be construed
+ as modifying the License.
+
+ You may add Your own copyright statement to Your modifications and
+ may provide additional or different license terms and conditions
+ for use, reproduction, or distribution of Your modifications, or
+ for any such Derivative Works as a whole, provided Your use,
+ reproduction, and distribution of the Work otherwise complies with
+ the conditions stated in this License.
+
+ 5. Submission of Contributions. Unless You explicitly state otherwise,
+ any Contribution intentionally submitted for inclusion in the Work
+ by You to the Licensor shall be under the terms and conditions of
+ this License, without any additional terms or conditions.
+ Notwithstanding the above, nothing herein shall supersede or modify
+ the terms of any separate license agreement you may have executed
+ with Licensor regarding such Contributions.
+
+ 6. Trademarks. This License does not grant permission to use the trade
+ names, trademarks, service marks, or product names of the Licensor,
+ except as required for reasonable and customary use in describing the
+ origin of the Work and reproducing the content of the NOTICE file.
+
+ 7. Disclaimer of Warranty. Unless required by applicable law or
+ agreed to in writing, Licensor provides the Work (and each
+ Contributor provides its Contributions) on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
+ implied, including, without limitation, any warranties or conditions
+ of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
+ PARTICULAR PURPOSE. You are solely responsible for determining the
+ appropriateness of using or redistributing the Work and assume any
+ risks associated with Your exercise of permissions under this License.
+
+ 8. Limitation of Liability. In no event and under no legal theory,
+ whether in tort (including negligence), contract, or otherwise,
+ unless required by applicable law (such as deliberate and grossly
+ negligent acts) or agreed to in writing, shall any Contributor be
+ liable to You for damages, including any direct, indirect, special,
+ incidental, or consequential damages of any character arising as a
+ result of this License or out of the use or inability to use the
+ Work (including but not limited to damages for loss of goodwill,
+ work stoppage, computer failure or malfunction, or any and all
+ other commercial damages or losses), even if such Contributor
+ has been advised of the possibility of such damages.
+
+ 9. Accepting Warranty or Additional Liability. While redistributing
+ the Work or Derivative Works thereof, You may choose to offer,
+ and charge a fee for, acceptance of support, warranty, indemnity,
+ or other liability obligations and/or rights consistent with this
+ License. However, in accepting such obligations, You may act only
+ on Your own behalf and on Your sole responsibility, not on behalf
+ of any other Contributor, and only if You agree to indemnify,
+ defend, and hold each Contributor harmless for any liability
+ incurred by, or claims asserted against, such Contributor by reason
+ of your accepting any such warranty or additional liability.
+
+ END OF TERMS AND CONDITIONS
+
+ APPENDIX: How to apply the Apache License to your work.
+
+ To apply the Apache License to your work, attach the following
+ boilerplate notice, with the fields enclosed by brackets "{}"
+ replaced with your own identifying information. (Don't include
+ the brackets!) The text should be enclosed in the appropriate
+ comment syntax for the file format. We also recommend that a
+ file or class name and description of purpose be included on the
+ same "printed page" as the copyright notice for easier
+ identification within third-party archives.
+
+ Copyright 2016 The OpenTracing Authors
+
+ 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.
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+LICENSE.md - gitlab.com/gitlab-org/gitaly/vendor/github.com/philhofer/fwd
+Copyright (c) 2014-2015, Philip Hofer
+
+Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
LICENSE - gitlab.com/gitlab-org/gitaly/vendor/github.com/pkg/errors
Copyright (c) 2015, Dave Cheney <dave@cheney.net>
All rights reserved.
@@ -1831,6 +2334,421 @@ DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT
OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE
OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+LICENSE - gitlab.com/gitlab-org/gitaly/vendor/github.com/tinylib/msgp
+Copyright (c) 2014 Philip Hofer
+Portions Copyright (c) 2009 The Go Authors (license at http://golang.org) where indicated
+
+Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+LICENSE - gitlab.com/gitlab-org/gitaly/vendor/github.com/uber/jaeger-client-go
+ Apache License
+ Version 2.0, January 2004
+ http://www.apache.org/licenses/
+
+ TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
+
+ 1. Definitions.
+
+ "License" shall mean the terms and conditions for use, reproduction,
+ and distribution as defined by Sections 1 through 9 of this document.
+
+ "Licensor" shall mean the copyright owner or entity authorized by
+ the copyright owner that is granting the License.
+
+ "Legal Entity" shall mean the union of the acting entity and all
+ other entities that control, are controlled by, or are under common
+ control with that entity. For the purposes of this definition,
+ "control" means (i) the power, direct or indirect, to cause the
+ direction or management of such entity, whether by contract or
+ otherwise, or (ii) ownership of fifty percent (50%) or more of the
+ outstanding shares, or (iii) beneficial ownership of such entity.
+
+ "You" (or "Your") shall mean an individual or Legal Entity
+ exercising permissions granted by this License.
+
+ "Source" form shall mean the preferred form for making modifications,
+ including but not limited to software source code, documentation
+ source, and configuration files.
+
+ "Object" form shall mean any form resulting from mechanical
+ transformation or translation of a Source form, including but
+ not limited to compiled object code, generated documentation,
+ and conversions to other media types.
+
+ "Work" shall mean the work of authorship, whether in Source or
+ Object form, made available under the License, as indicated by a
+ copyright notice that is included in or attached to the work
+ (an example is provided in the Appendix below).
+
+ "Derivative Works" shall mean any work, whether in Source or Object
+ form, that is based on (or derived from) the Work and for which the
+ editorial revisions, annotations, elaborations, or other modifications
+ represent, as a whole, an original work of authorship. For the purposes
+ of this License, Derivative Works shall not include works that remain
+ separable from, or merely link (or bind by name) to the interfaces of,
+ the Work and Derivative Works thereof.
+
+ "Contribution" shall mean any work of authorship, including
+ the original version of the Work and any modifications or additions
+ to that Work or Derivative Works thereof, that is intentionally
+ submitted to Licensor for inclusion in the Work by the copyright owner
+ or by an individual or Legal Entity authorized to submit on behalf of
+ the copyright owner. For the purposes of this definition, "submitted"
+ means any form of electronic, verbal, or written communication sent
+ to the Licensor or its representatives, including but not limited to
+ communication on electronic mailing lists, source code control systems,
+ and issue tracking systems that are managed by, or on behalf of, the
+ Licensor for the purpose of discussing and improving the Work, but
+ excluding communication that is conspicuously marked or otherwise
+ designated in writing by the copyright owner as "Not a Contribution."
+
+ "Contributor" shall mean Licensor and any individual or Legal Entity
+ on behalf of whom a Contribution has been received by Licensor and
+ subsequently incorporated within the Work.
+
+ 2. Grant of Copyright License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ copyright license to reproduce, prepare Derivative Works of,
+ publicly display, publicly perform, sublicense, and distribute the
+ Work and such Derivative Works in Source or Object form.
+
+ 3. Grant of Patent License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ (except as stated in this section) patent license to make, have made,
+ use, offer to sell, sell, import, and otherwise transfer the Work,
+ where such license applies only to those patent claims licensable
+ by such Contributor that are necessarily infringed by their
+ Contribution(s) alone or by combination of their Contribution(s)
+ with the Work to which such Contribution(s) was submitted. If You
+ institute patent litigation against any entity (including a
+ cross-claim or counterclaim in a lawsuit) alleging that the Work
+ or a Contribution incorporated within the Work constitutes direct
+ or contributory patent infringement, then any patent licenses
+ granted to You under this License for that Work shall terminate
+ as of the date such litigation is filed.
+
+ 4. Redistribution. You may reproduce and distribute copies of the
+ Work or Derivative Works thereof in any medium, with or without
+ modifications, and in Source or Object form, provided that You
+ meet the following conditions:
+
+ (a) You must give any other recipients of the Work or
+ Derivative Works a copy of this License; and
+
+ (b) You must cause any modified files to carry prominent notices
+ stating that You changed the files; and
+
+ (c) You must retain, in the Source form of any Derivative Works
+ that You distribute, all copyright, patent, trademark, and
+ attribution notices from the Source form of the Work,
+ excluding those notices that do not pertain to any part of
+ the Derivative Works; and
+
+ (d) If the Work includes a "NOTICE" text file as part of its
+ distribution, then any Derivative Works that You distribute must
+ include a readable copy of the attribution notices contained
+ within such NOTICE file, excluding those notices that do not
+ pertain to any part of the Derivative Works, in at least one
+ of the following places: within a NOTICE text file distributed
+ as part of the Derivative Works; within the Source form or
+ documentation, if provided along with the Derivative Works; or,
+ within a display generated by the Derivative Works, if and
+ wherever such third-party notices normally appear. The contents
+ of the NOTICE file are for informational purposes only and
+ do not modify the License. You may add Your own attribution
+ notices within Derivative Works that You distribute, alongside
+ or as an addendum to the NOTICE text from the Work, provided
+ that such additional attribution notices cannot be construed
+ as modifying the License.
+
+ You may add Your own copyright statement to Your modifications and
+ may provide additional or different license terms and conditions
+ for use, reproduction, or distribution of Your modifications, or
+ for any such Derivative Works as a whole, provided Your use,
+ reproduction, and distribution of the Work otherwise complies with
+ the conditions stated in this License.
+
+ 5. Submission of Contributions. Unless You explicitly state otherwise,
+ any Contribution intentionally submitted for inclusion in the Work
+ by You to the Licensor shall be under the terms and conditions of
+ this License, without any additional terms or conditions.
+ Notwithstanding the above, nothing herein shall supersede or modify
+ the terms of any separate license agreement you may have executed
+ with Licensor regarding such Contributions.
+
+ 6. Trademarks. This License does not grant permission to use the trade
+ names, trademarks, service marks, or product names of the Licensor,
+ except as required for reasonable and customary use in describing the
+ origin of the Work and reproducing the content of the NOTICE file.
+
+ 7. Disclaimer of Warranty. Unless required by applicable law or
+ agreed to in writing, Licensor provides the Work (and each
+ Contributor provides its Contributions) on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
+ implied, including, without limitation, any warranties or conditions
+ of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
+ PARTICULAR PURPOSE. You are solely responsible for determining the
+ appropriateness of using or redistributing the Work and assume any
+ risks associated with Your exercise of permissions under this License.
+
+ 8. Limitation of Liability. In no event and under no legal theory,
+ whether in tort (including negligence), contract, or otherwise,
+ unless required by applicable law (such as deliberate and grossly
+ negligent acts) or agreed to in writing, shall any Contributor be
+ liable to You for damages, including any direct, indirect, special,
+ incidental, or consequential damages of any character arising as a
+ result of this License or out of the use or inability to use the
+ Work (including but not limited to damages for loss of goodwill,
+ work stoppage, computer failure or malfunction, or any and all
+ other commercial damages or losses), even if such Contributor
+ has been advised of the possibility of such damages.
+
+ 9. Accepting Warranty or Additional Liability. While redistributing
+ the Work or Derivative Works thereof, You may choose to offer,
+ and charge a fee for, acceptance of support, warranty, indemnity,
+ or other liability obligations and/or rights consistent with this
+ License. However, in accepting such obligations, You may act only
+ on Your own behalf and on Your sole responsibility, not on behalf
+ of any other Contributor, and only if You agree to indemnify,
+ defend, and hold each Contributor harmless for any liability
+ incurred by, or claims asserted against, such Contributor by reason
+ of your accepting any such warranty or additional liability.
+
+ END OF TERMS AND CONDITIONS
+
+ APPENDIX: How to apply the Apache License to your work.
+
+ To apply the Apache License to your work, attach the following
+ boilerplate notice, with the fields enclosed by brackets "[]"
+ replaced with your own identifying information. (Don't include
+ the brackets!) The text should be enclosed in the appropriate
+ comment syntax for the file format. We also recommend that a
+ file or class name and description of purpose be included on the
+ same "printed page" as the copyright notice for easier
+ identification within third-party archives.
+
+ Copyright [yyyy] [name of copyright owner]
+
+ 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.
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+LICENSE - gitlab.com/gitlab-org/gitaly/vendor/github.com/uber/jaeger-lib
+ Apache License
+ Version 2.0, January 2004
+ http://www.apache.org/licenses/
+
+ TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
+
+ 1. Definitions.
+
+ "License" shall mean the terms and conditions for use, reproduction,
+ and distribution as defined by Sections 1 through 9 of this document.
+
+ "Licensor" shall mean the copyright owner or entity authorized by
+ the copyright owner that is granting the License.
+
+ "Legal Entity" shall mean the union of the acting entity and all
+ other entities that control, are controlled by, or are under common
+ control with that entity. For the purposes of this definition,
+ "control" means (i) the power, direct or indirect, to cause the
+ direction or management of such entity, whether by contract or
+ otherwise, or (ii) ownership of fifty percent (50%) or more of the
+ outstanding shares, or (iii) beneficial ownership of such entity.
+
+ "You" (or "Your") shall mean an individual or Legal Entity
+ exercising permissions granted by this License.
+
+ "Source" form shall mean the preferred form for making modifications,
+ including but not limited to software source code, documentation
+ source, and configuration files.
+
+ "Object" form shall mean any form resulting from mechanical
+ transformation or translation of a Source form, including but
+ not limited to compiled object code, generated documentation,
+ and conversions to other media types.
+
+ "Work" shall mean the work of authorship, whether in Source or
+ Object form, made available under the License, as indicated by a
+ copyright notice that is included in or attached to the work
+ (an example is provided in the Appendix below).
+
+ "Derivative Works" shall mean any work, whether in Source or Object
+ form, that is based on (or derived from) the Work and for which the
+ editorial revisions, annotations, elaborations, or other modifications
+ represent, as a whole, an original work of authorship. For the purposes
+ of this License, Derivative Works shall not include works that remain
+ separable from, or merely link (or bind by name) to the interfaces of,
+ the Work and Derivative Works thereof.
+
+ "Contribution" shall mean any work of authorship, including
+ the original version of the Work and any modifications or additions
+ to that Work or Derivative Works thereof, that is intentionally
+ submitted to Licensor for inclusion in the Work by the copyright owner
+ or by an individual or Legal Entity authorized to submit on behalf of
+ the copyright owner. For the purposes of this definition, "submitted"
+ means any form of electronic, verbal, or written communication sent
+ to the Licensor or its representatives, including but not limited to
+ communication on electronic mailing lists, source code control systems,
+ and issue tracking systems that are managed by, or on behalf of, the
+ Licensor for the purpose of discussing and improving the Work, but
+ excluding communication that is conspicuously marked or otherwise
+ designated in writing by the copyright owner as "Not a Contribution."
+
+ "Contributor" shall mean Licensor and any individual or Legal Entity
+ on behalf of whom a Contribution has been received by Licensor and
+ subsequently incorporated within the Work.
+
+ 2. Grant of Copyright License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ copyright license to reproduce, prepare Derivative Works of,
+ publicly display, publicly perform, sublicense, and distribute the
+ Work and such Derivative Works in Source or Object form.
+
+ 3. Grant of Patent License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ (except as stated in this section) patent license to make, have made,
+ use, offer to sell, sell, import, and otherwise transfer the Work,
+ where such license applies only to those patent claims licensable
+ by such Contributor that are necessarily infringed by their
+ Contribution(s) alone or by combination of their Contribution(s)
+ with the Work to which such Contribution(s) was submitted. If You
+ institute patent litigation against any entity (including a
+ cross-claim or counterclaim in a lawsuit) alleging that the Work
+ or a Contribution incorporated within the Work constitutes direct
+ or contributory patent infringement, then any patent licenses
+ granted to You under this License for that Work shall terminate
+ as of the date such litigation is filed.
+
+ 4. Redistribution. You may reproduce and distribute copies of the
+ Work or Derivative Works thereof in any medium, with or without
+ modifications, and in Source or Object form, provided that You
+ meet the following conditions:
+
+ (a) You must give any other recipients of the Work or
+ Derivative Works a copy of this License; and
+
+ (b) You must cause any modified files to carry prominent notices
+ stating that You changed the files; and
+
+ (c) You must retain, in the Source form of any Derivative Works
+ that You distribute, all copyright, patent, trademark, and
+ attribution notices from the Source form of the Work,
+ excluding those notices that do not pertain to any part of
+ the Derivative Works; and
+
+ (d) If the Work includes a "NOTICE" text file as part of its
+ distribution, then any Derivative Works that You distribute must
+ include a readable copy of the attribution notices contained
+ within such NOTICE file, excluding those notices that do not
+ pertain to any part of the Derivative Works, in at least one
+ of the following places: within a NOTICE text file distributed
+ as part of the Derivative Works; within the Source form or
+ documentation, if provided along with the Derivative Works; or,
+ within a display generated by the Derivative Works, if and
+ wherever such third-party notices normally appear. The contents
+ of the NOTICE file are for informational purposes only and
+ do not modify the License. You may add Your own attribution
+ notices within Derivative Works that You distribute, alongside
+ or as an addendum to the NOTICE text from the Work, provided
+ that such additional attribution notices cannot be construed
+ as modifying the License.
+
+ You may add Your own copyright statement to Your modifications and
+ may provide additional or different license terms and conditions
+ for use, reproduction, or distribution of Your modifications, or
+ for any such Derivative Works as a whole, provided Your use,
+ reproduction, and distribution of the Work otherwise complies with
+ the conditions stated in this License.
+
+ 5. Submission of Contributions. Unless You explicitly state otherwise,
+ any Contribution intentionally submitted for inclusion in the Work
+ by You to the Licensor shall be under the terms and conditions of
+ this License, without any additional terms or conditions.
+ Notwithstanding the above, nothing herein shall supersede or modify
+ the terms of any separate license agreement you may have executed
+ with Licensor regarding such Contributions.
+
+ 6. Trademarks. This License does not grant permission to use the trade
+ names, trademarks, service marks, or product names of the Licensor,
+ except as required for reasonable and customary use in describing the
+ origin of the Work and reproducing the content of the NOTICE file.
+
+ 7. Disclaimer of Warranty. Unless required by applicable law or
+ agreed to in writing, Licensor provides the Work (and each
+ Contributor provides its Contributions) on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
+ implied, including, without limitation, any warranties or conditions
+ of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
+ PARTICULAR PURPOSE. You are solely responsible for determining the
+ appropriateness of using or redistributing the Work and assume any
+ risks associated with Your exercise of permissions under this License.
+
+ 8. Limitation of Liability. In no event and under no legal theory,
+ whether in tort (including negligence), contract, or otherwise,
+ unless required by applicable law (such as deliberate and grossly
+ negligent acts) or agreed to in writing, shall any Contributor be
+ liable to You for damages, including any direct, indirect, special,
+ incidental, or consequential damages of any character arising as a
+ result of this License or out of the use or inability to use the
+ Work (including but not limited to damages for loss of goodwill,
+ work stoppage, computer failure or malfunction, or any and all
+ other commercial damages or losses), even if such Contributor
+ has been advised of the possibility of such damages.
+
+ 9. Accepting Warranty or Additional Liability. While redistributing
+ the Work or Derivative Works thereof, You may choose to offer,
+ and charge a fee for, acceptance of support, warranty, indemnity,
+ or other liability obligations and/or rights consistent with this
+ License. However, in accepting such obligations, You may act only
+ on Your own behalf and on Your sole responsibility, not on behalf
+ of any other Contributor, and only if You agree to indemnify,
+ defend, and hold each Contributor harmless for any liability
+ incurred by, or claims asserted against, such Contributor by reason
+ of your accepting any such warranty or additional liability.
+
+ END OF TERMS AND CONDITIONS
+
+ APPENDIX: How to apply the Apache License to your work.
+
+ To apply the Apache License to your work, attach the following
+ boilerplate notice, with the fields enclosed by brackets "[]"
+ replaced with your own identifying information. (Don't include
+ the brackets!) The text should be enclosed in the appropriate
+ comment syntax for the file format. We also recommend that a
+ file or class name and description of purpose be included on the
+ same "printed page" as the copyright notice for easier
+ identification within third-party archives.
+
+ Copyright [yyyy] [name of copyright owner]
+
+ 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.
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
LICENSE - gitlab.com/gitlab-org/gitaly/vendor/gitlab.com/gitlab-org/gitaly-proto
The MIT License (MIT)
@@ -2549,4 +3467,33 @@ LICENSE - gitlab.com/gitlab-org/gitaly/vendor/google.golang.org/grpc
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.
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+LICENSE - gitlab.com/gitlab-org/gitaly/vendor/gopkg.in/DataDog/dd-trace-go.v1
+Copyright (c) 2016, Datadog <info@datadoghq.com>
+All rights reserved.
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions are met:
+ * Redistributions of source code must retain the above copyright
+ notice, this list of conditions and the following disclaimer.
+ * Redistributions in binary form must reproduce the above copyright
+ notice, this list of conditions and the following disclaimer in the
+ documentation and/or other materials provided with the distribution.
+ * Neither the name of Datadog nor the
+ names of its contributors may be used to endorse or promote products
+ derived from this software without specific prior written permission.
+
+THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
+ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+DISCLAIMED. IN NO EVENT SHALL <COPYRIGHT HOLDER> BE LIABLE FOR ANY
+DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+LICENSE-3rdparty.csv - gitlab.com/gitlab-org/gitaly/vendor/gopkg.in/DataDog/dd-trace-go.v1
+Component,Origin,License,Copyright
+import,io.opentracing,Apache-2.0,Copyright 2016-2017 The OpenTracing Authors
diff --git a/README.md b/README.md
index 3e59797ec..2eba51b04 100644
--- a/README.md
+++ b/README.md
@@ -111,6 +111,26 @@ use library code from the
[gitlab.com/gitlab-org/gitaly/client](https://gitlab.com/gitlab-org/gitaly/tree/master/client)
package.
+## Distributed Tracing
+
+Gitaly supports distributed tracing through [LabKit](https://gitlab.com/gitlab-org/labkit/) using [OpenTracing APIs](https://opentracing.io).
+
+By default, no tracing implementation is linked into the binary, but different OpenTracing providers can be linked in using [build tags](https://golang.org/pkg/go/build/#hdr-Build_Constraints)/[build constraints](https://golang.org/pkg/go/build/#hdr-Build_Constraints). This can be done by setting the `BUILD_TAGS` make variable.
+
+For more details of the supported providers, see LabKit, but as an example, for Jaeger tracing support, include the tags: `BUILD_TAGS="tracer_static tracer_static_jaeger"`.
+
+```shell
+$ make BUILD_TAGS="tracer_static tracer_static_jaeger"
+```
+
+Once Gitaly is compiled with an opentracing provider, the tracing configuration is configured via the `GITLAB_TRACING` environment variable.
+
+For example, to configure Jaeger, you could use the following command:
+
+```shell
+GITLAB_TRACING=opentracing://jaeger ./gitaly config.toml
+```
+
## Presentations
- [Git Paris meetup, 2017-02-22](https://docs.google.com/presentation/d/19OZUalFMIDM8WujXrrIyCuVb_oVeaUzpb-UdGThOvAo/edit?usp=sharing) a high-level overview of what our plans are and where we are.
diff --git a/VERSION b/VERSION
index 0eed1a29e..feaae22ba 100644
--- a/VERSION
+++ b/VERSION
@@ -1 +1 @@
-1.12.0
+1.13.0
diff --git a/_support/makegen.go b/_support/makegen.go
index e8e7de6ba..3200f3d25 100644
--- a/_support/makegen.go
+++ b/_support/makegen.go
@@ -243,7 +243,7 @@ all: build
.PHONY: build
build: ../.ruby-bundle
- go install {{ .GoLdFlags }} {{ join .CommandPackages " " }}
+ go install {{ .GoLdFlags }} -tags "$(BUILD_TAGS)" {{ join .CommandPackages " " }}
# This file is used by Omnibus and CNG to skip the "bundle install"
# step. Both Omnibus and CNG assume it is in the Gitaly root, not in
@@ -314,11 +314,11 @@ test: test-go rspec rspec-gitlab-shell
.PHONY: test-go
test-go: prepare-tests
- @go test -count=1 {{ join .AllPackages " " }} # count=1 bypasses go 1.10 test caching
+ @go test -tags "$(BUILD_TAGS)" -count=1 {{ join .AllPackages " " }} # count=1 bypasses go 1.10 test caching
.PHONY: race-go
race-go: prepare-tests
- @go test -race {{ join .AllPackages " " }}
+ @go test -tags "$(BUILD_TAGS)" -race {{ join .AllPackages " " }}
.PHONY: rspec
rspec: assemble-go prepare-tests
diff --git a/auth/extract_test.go b/auth/extract_test.go
index 7d6df8fb0..db742ddec 100644
--- a/auth/extract_test.go
+++ b/auth/extract_test.go
@@ -1,12 +1,12 @@
package gitalyauth
import (
+ "context"
"testing"
"time"
"github.com/grpc-ecosystem/go-grpc-middleware/util/metautils"
"github.com/stretchr/testify/require"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/credentials"
"google.golang.org/grpc/metadata"
diff --git a/auth/rpccredentials.go b/auth/rpccredentials.go
index c35cd4d61..ca54901da 100644
--- a/auth/rpccredentials.go
+++ b/auth/rpccredentials.go
@@ -1,12 +1,12 @@
package gitalyauth
import (
+ "context"
"encoding/base64"
"fmt"
"strconv"
"time"
- "golang.org/x/net/context"
"google.golang.org/grpc/credentials"
)
diff --git a/auth/token.go b/auth/token.go
index a5b5747c4..6eb62e6d9 100644
--- a/auth/token.go
+++ b/auth/token.go
@@ -1,6 +1,7 @@
package gitalyauth
import (
+ "context"
"crypto/hmac"
"crypto/sha256"
"crypto/subtle"
@@ -11,7 +12,6 @@ import (
"time"
grpc_auth "github.com/grpc-ecosystem/go-grpc-middleware/auth"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
)
diff --git a/changelogs/unreleased/1302-fix-rename-namespace-rpc-logging.yml b/changelogs/unreleased/1302-fix-rename-namespace-rpc-logging.yml
deleted file mode 100644
index add78ad2b..000000000
--- a/changelogs/unreleased/1302-fix-rename-namespace-rpc-logging.yml
+++ /dev/null
@@ -1,5 +0,0 @@
----
-title: Fix logging of RenameNamespace RPC parameters
-merge_request: 847
-author:
-type: fixed
diff --git a/changelogs/unreleased/1441-1442-update-docs-monitoring.yml b/changelogs/unreleased/1441-1442-update-docs-monitoring.yml
deleted file mode 100644
index 664064212..000000000
--- a/changelogs/unreleased/1441-1442-update-docs-monitoring.yml
+++ /dev/null
@@ -1,5 +0,0 @@
----
-title: Update docs about monitoring and README
-merge_request: 1016
-author: Takuya Noguchi
-type: other
diff --git a/changelogs/unreleased/fix-raw-changes-bug.yml b/changelogs/unreleased/fix-raw-changes-bug.yml
deleted file mode 100644
index 39d84e4bd..000000000
--- a/changelogs/unreleased/fix-raw-changes-bug.yml
+++ /dev/null
@@ -1,5 +0,0 @@
----
-title: Rewrite GetRawChanges and fix quoting bug
-merge_request: 1026
-author:
-type: fixed
diff --git a/changelogs/unreleased/fix-rebase-test-flake.yml b/changelogs/unreleased/fix-rebase-test-flake.yml
deleted file mode 100644
index 2377849d5..000000000
--- a/changelogs/unreleased/fix-rebase-test-flake.yml
+++ /dev/null
@@ -1,5 +0,0 @@
----
-title: Fix flaky rebase test
-merge_request: 1028
-author:
-type: fixed
diff --git a/changelogs/unreleased/jc-migrate-find-commits.yml b/changelogs/unreleased/jc-migrate-find-commits.yml
deleted file mode 100644
index 91f4f7f30..000000000
--- a/changelogs/unreleased/jc-migrate-find-commits.yml
+++ /dev/null
@@ -1,5 +0,0 @@
----
-title: Use go implementation of FindCommits
-merge_request: 1025
-author:
-type: other
diff --git a/changelogs/unreleased/jc-rewrite-get-commit-message.yml b/changelogs/unreleased/jc-rewrite-get-commit-message.yml
deleted file mode 100644
index 71a1080c2..000000000
--- a/changelogs/unreleased/jc-rewrite-get-commit-message.yml
+++ /dev/null
@@ -1,5 +0,0 @@
----
-title: Rewrite get commit message
-merge_request: 1012
-author:
-type: other
diff --git a/changelogs/unreleased/jv-prepare-hooks.yml b/changelogs/unreleased/jv-prepare-hooks.yml
deleted file mode 100644
index a2f4b9051..000000000
--- a/changelogs/unreleased/jv-prepare-hooks.yml
+++ /dev/null
@@ -1,5 +0,0 @@
----
-title: Prepare for vendoring gitlab-shell hooks
-merge_request: 1020
-author:
-type: other
diff --git a/changelogs/unreleased/megacheck-staticcheck.yml b/changelogs/unreleased/megacheck-staticcheck.yml
deleted file mode 100644
index 4bb45552c..000000000
--- a/changelogs/unreleased/megacheck-staticcheck.yml
+++ /dev/null
@@ -1,5 +0,0 @@
----
-title: Switch from honnef.co/go/tools/megacheck to staticcheck
-merge_request: 1021
-author:
-type: other
diff --git a/changelogs/unreleased/migrate-writeref.yml b/changelogs/unreleased/migrate-writeref.yml
deleted file mode 100644
index adee7d3e1..000000000
--- a/changelogs/unreleased/migrate-writeref.yml
+++ /dev/null
@@ -1,5 +0,0 @@
----
-title: Migrate writeref from using the ruby implementation to go
-merge_request: 1008
-author: johncai
-type: other
diff --git a/changelogs/unreleased/remove-request-store.yml b/changelogs/unreleased/remove-request-store.yml
deleted file mode 100644
index d4b03414a..000000000
--- a/changelogs/unreleased/remove-request-store.yml
+++ /dev/null
@@ -1,5 +0,0 @@
----
-title: Remove dummy RequestStore
-merge_request: 1007
-author:
-type: other
diff --git a/changelogs/unreleased/sh-fix-issue-1329.yml b/changelogs/unreleased/sh-fix-issue-1329.yml
deleted file mode 100644
index 16f9503eb..000000000
--- a/changelogs/unreleased/sh-fix-issue-1329.yml
+++ /dev/null
@@ -1,5 +0,0 @@
----
-title: Fix 503 errors when Git outputs warnings to stderr
-merge_request: 1024
-author:
-type: fixed
diff --git a/changelogs/unreleased/simplify-error-handling.yml b/changelogs/unreleased/simplify-error-handling.yml
deleted file mode 100644
index c4e3119e4..000000000
--- a/changelogs/unreleased/simplify-error-handling.yml
+++ /dev/null
@@ -1,5 +0,0 @@
----
-title: Simplify error wrapping in service/ref
-merge_request: 1009
-author:
-type: other
diff --git a/client/address_parser.go b/client/address_parser.go
index 55969e909..a052342ae 100644
--- a/client/address_parser.go
+++ b/client/address_parser.go
@@ -3,22 +3,36 @@ package client
import (
"fmt"
"net/url"
+ "strings"
)
-func parseAddress(rawAddress string) (canonicalAddress string, err error) {
+// extractHostFromRemoteURL will convert Gitaly-style URL addresses of the form
+// scheme://host:port to the "host:port" addresses used by `grpc.Dial`
+func extractHostFromRemoteURL(rawAddress string) (hostAndPort string, err error) {
u, err := url.Parse(rawAddress)
if err != nil {
return "", err
}
- // tcp:// addresses are a special case which `grpc.Dial` expects in a
- // different format
- if u.Scheme == "tcp" || u.Scheme == "tls" {
- if u.Path != "" {
- return "", fmt.Errorf("%s addresses should not have a path", u.Scheme)
- }
- return u.Host, nil
+ if u.Path != "" {
+ return "", fmt.Errorf("remote addresses should not have a path")
}
- return u.String(), nil
+ if u.Host == "" {
+ return "", fmt.Errorf("remote addresses should have a host")
+ }
+
+ return u.Host, nil
+}
+
+// extractPathFromSocketURL will convert Gitaly-style URL addresses of the form
+// unix:/path/to/socket into file paths: `/path/to/socket`
+const unixPrefix = "unix:"
+
+func extractPathFromSocketURL(rawAddress string) (socketPath string, err error) {
+ if !strings.HasPrefix(rawAddress, unixPrefix) {
+ return "", fmt.Errorf("invalid socket address: %s", rawAddress)
+ }
+
+ return strings.TrimPrefix(rawAddress, unixPrefix), nil
}
diff --git a/client/address_parser_test.go b/client/address_parser_test.go
index 820a902b3..f5dc2f31b 100644
--- a/client/address_parser_test.go
+++ b/client/address_parser_test.go
@@ -2,19 +2,16 @@ package client
import (
"testing"
+
+ "github.com/stretchr/testify/require"
)
-func TestParseAddress(t *testing.T) {
+func Test_extractHostFromRemoteURL(t *testing.T) {
testCases := []struct {
raw string
canonical string
invalid bool
}{
- {raw: "unix:/foo/bar.socket", canonical: "unix:///foo/bar.socket"},
- {raw: "unix:///foo/bar.socket", canonical: "unix:///foo/bar.socket"},
- // Mainly for test purposes we explicitly want to support relative paths
- {raw: "unix://foo/bar.socket", canonical: "unix://foo/bar.socket"},
- {raw: "unix:foo/bar.socket", canonical: "unix:foo/bar.socket"},
{raw: "tcp://1.2.3.4", canonical: "1.2.3.4"},
{raw: "tcp://1.2.3.4:567", canonical: "1.2.3.4:567"},
{raw: "tcp://foobar", canonical: "foobar"},
@@ -24,28 +21,53 @@ func TestParseAddress(t *testing.T) {
{raw: "tcp:///foo/bar.socket", invalid: true},
{raw: "tcp:/foo/bar.socket", invalid: true},
{raw: "tcp://[2001:0db8:85a3:0000:0000:8a2e:0370:7334]:9999", canonical: "[2001:0db8:85a3:0000:0000:8a2e:0370:7334]:9999"},
- {raw: "foobar:9999", canonical: "foobar:9999"},
- // As per https://github.com/grpc/grpc/blob/master/doc/naming.md...
- {raw: "dns:///127.0.0.1:9999", canonical: "dns:///127.0.0.1:9999"},
- {raw: "dns:///[2001:0db8:85a3:0000:0000:8a2e:0370:7334]:9999", canonical: "dns:///[2001:0db8:85a3:0000:0000:8a2e:0370:7334]:9999"},
+ {raw: "foobar:9999", invalid: true},
+ {raw: "unix:/foo/bar.socket", invalid: true},
+ {raw: "unix:///foo/bar.socket", invalid: true},
+ {raw: "unix://foo/bar.socket", invalid: true},
+ {raw: "unix:foo/bar.socket", invalid: true},
+ }
+
+ for _, tc := range testCases {
+ t.Run(tc.raw, func(t *testing.T) {
+ canonical, err := extractHostFromRemoteURL(tc.raw)
+ if tc.invalid {
+ require.Error(t, err)
+ return
+ }
+
+ require.NoError(t, err)
+ require.Equal(t, tc.canonical, canonical)
+ })
+ }
+}
+
+func Test_extractPathFromSocketURL(t *testing.T) {
+ testCases := []struct {
+ raw string
+ path string
+ invalid bool
+ }{
+ {raw: "unix:/foo/bar.socket", path: "/foo/bar.socket"},
+ {raw: "unix:///foo/bar.socket", path: "///foo/bar.socket"}, // Silly but valid
+ {raw: "unix:foo/bar.socket", path: "foo/bar.socket"},
+ {raw: "unix:../foo/bar.socket", path: "../foo/bar.socket"},
+ {raw: "unix:path/with/a/colon:/in/it", path: "path/with/a/colon:/in/it"},
+ {raw: "tcp://1.2.3.4", invalid: true},
+ {raw: "foo/bar.socket", invalid: true},
}
for _, tc := range testCases {
- canonical, err := parseAddress(tc.raw)
-
- if err == nil && tc.invalid {
- t.Errorf("%v: expected error, got none", tc)
- } else if err != nil && !tc.invalid {
- t.Errorf("%v: parse error: %v", tc, err)
- continue
- }
-
- if tc.invalid {
- continue
- }
-
- if tc.canonical != canonical {
- t.Errorf("%v: expected %q, got %q", tc, tc.canonical, canonical)
- }
+ t.Run(tc.raw, func(t *testing.T) {
+ path, err := extractPathFromSocketURL(tc.raw)
+
+ if tc.invalid {
+ require.Error(t, err)
+ return
+ }
+
+ require.NoError(t, err)
+ require.Equal(t, tc.path, path)
+ })
}
}
diff --git a/client/dial.go b/client/dial.go
index d0a51c0c1..fe4a3e683 100644
--- a/client/dial.go
+++ b/client/dial.go
@@ -1,6 +1,10 @@
package client
import (
+ "fmt"
+ "net"
+ "time"
+
"google.golang.org/grpc/credentials"
"net/url"
@@ -11,14 +15,30 @@ import (
// DefaultDialOpts hold the default DialOptions for connection to Gitaly over UNIX-socket
var DefaultDialOpts = []grpc.DialOption{}
+type connectionType int
+
+const (
+ invalidConnection connectionType = iota
+ tcpConnection
+ tlsConnection
+ unixConnection
+)
+
// Dial gitaly
func Dial(rawAddress string, connOpts []grpc.DialOption) (*grpc.ClientConn, error) {
- canonicalAddress, err := parseAddress(rawAddress)
- if err != nil {
- return nil, err
- }
+ var canonicalAddress string
+ var err error
+
+ switch getConnectionType(rawAddress) {
+ case invalidConnection:
+ return nil, fmt.Errorf("invalid connection string: %s", rawAddress)
+
+ case tlsConnection:
+ canonicalAddress, err = extractHostFromRemoteURL(rawAddress) // Ensure the form: "host:port" ...
+ if err != nil {
+ return nil, err
+ }
- if isTLS(rawAddress) {
certPool, err := systemCertPool()
if err != nil {
return nil, err
@@ -26,8 +46,29 @@ func Dial(rawAddress string, connOpts []grpc.DialOption) (*grpc.ClientConn, erro
creds := credentials.NewClientTLSFromCert(certPool, "")
connOpts = append(connOpts, grpc.WithTransportCredentials(creds))
- } else {
+
+ case tcpConnection:
+ canonicalAddress, err = extractHostFromRemoteURL(rawAddress) // Ensure the form: "host:port" ...
+ if err != nil {
+ return nil, err
+ }
connOpts = append(connOpts, grpc.WithInsecure())
+
+ case unixConnection:
+ canonicalAddress = rawAddress // This will be overriden by the custom dialer...
+ connOpts = append(
+ connOpts,
+ grpc.WithInsecure(),
+ grpc.WithDialer(func(addr string, timeout time.Duration) (net.Conn, error) {
+ path, err := extractPathFromSocketURL(addr)
+ if err != nil {
+ return nil, err
+ }
+
+ return net.DialTimeout("unix", path, timeout)
+ }),
+ )
+
}
conn, err := grpc.Dial(canonicalAddress, connOpts...)
@@ -38,7 +79,20 @@ func Dial(rawAddress string, connOpts []grpc.DialOption) (*grpc.ClientConn, erro
return conn, nil
}
-func isTLS(rawAddress string) bool {
+func getConnectionType(rawAddress string) connectionType {
u, err := url.Parse(rawAddress)
- return err == nil && u.Scheme == "tls"
+ if err != nil {
+ return invalidConnection
+ }
+
+ switch u.Scheme {
+ case "tls":
+ return tlsConnection
+ case "unix":
+ return unixConnection
+ case "tcp":
+ return tcpConnection
+ default:
+ return invalidConnection
+ }
}
diff --git a/client/dial_test.go b/client/dial_test.go
new file mode 100644
index 000000000..a7edd5598
--- /dev/null
+++ b/client/dial_test.go
@@ -0,0 +1,250 @@
+package client
+
+import (
+ "context"
+ "crypto/tls"
+ "fmt"
+ "net"
+ "os"
+ "path/filepath"
+ "strings"
+ "testing"
+
+ "github.com/stretchr/testify/require"
+ "gitlab.com/gitlab-org/gitaly/internal/testhelper"
+ "google.golang.org/grpc"
+ "google.golang.org/grpc/codes"
+ "google.golang.org/grpc/credentials"
+ healthpb "google.golang.org/grpc/health/grpc_health_v1"
+ "google.golang.org/grpc/status"
+)
+
+var proxyEnvironmentKeys = []string{"http_proxy", "https_proxy", "no_proxy"}
+
+func doDialAndExecuteCall(addr string) error {
+ conn, err := Dial(addr, nil)
+ if err != nil {
+ return fmt.Errorf("dial: %v", err)
+ }
+
+ client := healthpb.NewHealthClient(conn)
+ _, err = client.Check(context.Background(), &healthpb.HealthCheckRequest{})
+ return err
+}
+
+func TestDial(t *testing.T) {
+ if emitProxyWarning() {
+ t.Log("WARNING. Proxy configuration detected from environment settings. This test failure may be related to proxy configuration. Please process with caution")
+ }
+
+ stop, connectionMap, err := startListeners()
+ require.NoError(t, err, "start listeners: %v. %s", err)
+ defer stop()
+
+ wd, err := os.Getwd()
+ require.NoError(t, err, "getwd: %v. %s", err)
+
+ unixSocketAbsPath := connectionMap["unix"]
+ unixSocketRelPath, err := filepath.Rel(wd, unixSocketAbsPath)
+ require.NoError(t, err, "relative path failure: %v. %s", err)
+
+ tests := []struct {
+ name string
+ rawAddress string
+ envSSLCertFile string
+ expectFailure bool
+ }{
+ {
+ name: "tcp localhost with prefix",
+ rawAddress: "tcp://localhost:" + connectionMap["tcp"], // "tcp://localhost:1234"
+ expectFailure: false,
+ },
+ {
+ name: "tls localhost",
+ rawAddress: "tls://localhost:" + connectionMap["tls"], // "tls://localhost:1234"
+ envSSLCertFile: "./testdata/gitalycert.pem",
+ expectFailure: false,
+ },
+ {
+ name: "unix absolute",
+ rawAddress: "unix:" + unixSocketAbsPath, // "unix:/tmp/temp-socket"
+ expectFailure: false,
+ },
+ {
+ name: "unix relative",
+ rawAddress: "unix:" + unixSocketRelPath, // "unix:../../tmp/temp-socket"
+ expectFailure: false,
+ },
+ {
+ name: "unix absolute does not exist",
+ rawAddress: "unix:" + unixSocketAbsPath + ".does_not_exist", // "unix:/tmp/temp-socket.does_not_exist"
+ expectFailure: true,
+ },
+ {
+ name: "unix relative does not exist",
+ rawAddress: "unix:" + unixSocketRelPath + ".does_not_exist", // "unix:../../tmp/temp-socket.does_not_exist"
+ expectFailure: true,
+ },
+ {
+ // Gitaly does not support connections that do not have a scheme.
+ name: "tcp localhost no prefix",
+ rawAddress: "localhost:" + connectionMap["tcp"], // "localhost:1234"
+ expectFailure: true,
+ },
+ {
+ name: "invalid",
+ rawAddress: ".",
+ expectFailure: true,
+ },
+ {
+ name: "empty",
+ rawAddress: "",
+ expectFailure: true,
+ },
+ }
+
+ for _, tt := range tests {
+ t.Run(tt.name, func(t *testing.T) {
+ if emitProxyWarning() {
+ t.Log("WARNING. Proxy configuration detected from environment settings. This test failure may be related to proxy configuration. Please process with caution")
+ }
+
+ if tt.envSSLCertFile != "" {
+ restore := modifyEnvironment("SSL_CERT_FILE", tt.envSSLCertFile)
+ defer restore()
+ }
+
+ err := doDialAndExecuteCall(tt.rawAddress)
+ if tt.expectFailure {
+ require.Error(t, err)
+ return
+ }
+ require.NoError(t, err)
+ })
+ }
+}
+
+// healthServer provide a basic GRPC health service endpoint for testing purposes
+type healthServer struct {
+}
+
+func (*healthServer) Check(context.Context, *healthpb.HealthCheckRequest) (*healthpb.HealthCheckResponse, error) {
+ return &healthpb.HealthCheckResponse{Status: healthpb.HealthCheckResponse_SERVING}, nil
+}
+
+func (*healthServer) Watch(*healthpb.HealthCheckRequest, healthpb.Health_WatchServer) error {
+ return status.Errorf(codes.Unimplemented, "Not implemented")
+}
+
+// startTCPListener will start a insecure TCP listener on a random unused port
+func startTCPListener() (func(), string, error) {
+ listener, err := net.Listen("tcp", ":0")
+ if err != nil {
+ return nil, "", err
+ }
+ tcpPort := listener.Addr().(*net.TCPAddr).Port
+ address := fmt.Sprintf("%d", tcpPort)
+
+ grpcServer := grpc.NewServer()
+ healthpb.RegisterHealthServer(grpcServer, &healthServer{})
+ go grpcServer.Serve(listener)
+
+ return func() {
+ grpcServer.Stop()
+ }, address, nil
+}
+
+// startUnixListener will start a unix socket listener using a temporary file
+func startUnixListener() (func(), string, error) {
+ serverSocketPath := testhelper.GetTemporaryGitalySocketFileName()
+
+ listener, err := net.Listen("unix", serverSocketPath)
+ if err != nil {
+ return nil, "", err
+ }
+
+ grpcServer := grpc.NewServer()
+ healthpb.RegisterHealthServer(grpcServer, &healthServer{})
+ go grpcServer.Serve(listener)
+
+ return func() {
+ grpcServer.Stop()
+ }, serverSocketPath, nil
+}
+
+// startTLSListener will start a secure TLS listener on a random unused port
+func startTLSListener() (func(), string, error) {
+ listener, err := net.Listen("tcp", ":0")
+ if err != nil {
+ return nil, "", err
+ }
+ tcpPort := listener.Addr().(*net.TCPAddr).Port
+ address := fmt.Sprintf("%d", tcpPort)
+
+ cert, err := tls.LoadX509KeyPair("./testdata/gitalycert.pem", "./testdata/gitalykey.pem")
+ if err != nil {
+ return nil, "", err
+ }
+
+ grpcServer := grpc.NewServer(grpc.Creds(credentials.NewServerTLSFromCert(&cert)))
+ healthpb.RegisterHealthServer(grpcServer, &healthServer{})
+ go grpcServer.Serve(listener)
+
+ return func() {
+ grpcServer.Stop()
+ }, address, nil
+}
+
+var listeners = map[string]func() (func(), string, error){
+ "tcp": startTCPListener,
+ "unix": startUnixListener,
+ "tls": startTLSListener,
+}
+
+// startListeners will start all the different listeners used in this test
+func startListeners() (func(), map[string]string, error) {
+ var closers []func()
+ connectionMap := map[string]string{}
+ for k, v := range listeners {
+ closer, address, err := v()
+ if err != nil {
+ return nil, nil, err
+ }
+ closers = append(closers, closer)
+ connectionMap[k] = address
+ }
+
+ return func() {
+ for _, v := range closers {
+ v()
+ }
+ }, connectionMap, nil
+}
+
+// modifyEnvironment will change an environment variable and return a func suitable
+// for `defer` to change the value back.
+func modifyEnvironment(key string, value string) func() {
+ oldValue, hasOldValue := os.LookupEnv(key)
+ os.Setenv(key, value)
+ return func() {
+ if hasOldValue {
+ os.Setenv(key, oldValue)
+ } else {
+ os.Unsetenv(key)
+ }
+ }
+}
+
+func emitProxyWarning() bool {
+ for _, key := range proxyEnvironmentKeys {
+ value := os.Getenv(key)
+ if value != "" {
+ return true
+ }
+ value = os.Getenv(strings.ToUpper(key))
+ if value != "" {
+ return true
+ }
+ }
+ return false
+}
diff --git a/client/pool-darwin.go b/client/pool_darwin.go
index e392a4d70..62589ce28 100644
--- a/client/pool-darwin.go
+++ b/client/pool_darwin.go
@@ -1,5 +1,3 @@
-// +build darwin
-
package client
import (
@@ -13,7 +11,6 @@ import (
// SSL_CERT_{DIR,FILE}.
func systemCertPool() (*x509.CertPool, error) {
var certPem []byte
- count := 0
if f := os.Getenv("SSL_CERT_FILE"); len(f) > 0 {
pem, err := ioutil.ReadFile(f)
@@ -23,7 +20,6 @@ func systemCertPool() (*x509.CertPool, error) {
pem = append(pem, '\n')
certPem = append(certPem, pem...)
- count++
}
if d := os.Getenv("SSL_CERT_DIR"); len(d) > 0 {
@@ -44,7 +40,6 @@ func systemCertPool() (*x509.CertPool, error) {
pem = append(pem, '\n')
certPem = append(certPem, pem...)
- count++
}
}
diff --git a/client/receive_pack.go b/client/receive_pack.go
index 767b392e5..afa972522 100644
--- a/client/receive_pack.go
+++ b/client/receive_pack.go
@@ -1,11 +1,11 @@
package client
import (
+ "context"
"io"
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/streamio"
- "golang.org/x/net/context"
"google.golang.org/grpc"
)
diff --git a/client/testdata/gitalycert.pem b/client/testdata/gitalycert.pem
new file mode 100644
index 000000000..8b1514548
--- /dev/null
+++ b/client/testdata/gitalycert.pem
@@ -0,0 +1,30 @@
+-----BEGIN CERTIFICATE-----
+MIIFODCCAyACCQDpPfNtveVc8TANBgkqhkiG9w0BAQsFADBdMQswCQYDVQQGEwJV
+UzELMAkGA1UECAwCVVMxCzAJBgNVBAcMAlVTMQ8wDQYDVQQKDAZHaXRMYWIxDzAN
+BgNVBAsMBmdpdGFseTESMBAGA1UEAwwJbG9jYWxob3N0MCAXDTE4MTEwMjA5MDIx
+MloYDzIxMTgxMDA5MDkwMjEyWjBdMQswCQYDVQQGEwJVUzELMAkGA1UECAwCVVMx
+CzAJBgNVBAcMAlVTMQ8wDQYDVQQKDAZHaXRMYWIxDzANBgNVBAsMBmdpdGFseTES
+MBAGA1UEAwwJbG9jYWxob3N0MIICIjANBgkqhkiG9w0BAQEFAAOCAg8AMIICCgKC
+AgEApJXJOWpUkV32v8gRXLWn6TEsQmy2WeilQXg96V6VOQjGZAGMEJLEjH9WHBNe
+Zi4V+W+j1FB8vWTNRGTcOcpSEmDFuewoBJVA8dFtNF4jj7QQymmnKeDuOW4fWLeU
+YcyGxyjlpkm2+DUg5CavT4bMZILqbsAavxJ8SKCdJpMtW3sxklnGuTHcAckHldab
+9ZxH/qYqLxc5Ek2BK4OibBxA84h1RUsqe2EdzZUOoet3xpwG3Vr8bGPqR7Psghs6
+TDdWU8hYYHlReCWezgZHiYDoRqY9HCZrHSpUZ1lbRo++2j4bvdFHOAUm4BEQ6fFc
+sgtW+xkNK8bxj9XTcpuDrEVscv3fyBlCMSvD+HpNbr2k1oZSOFhxISIwBLKWQBjq
+5muvMRbmrG5RgWqMWjXb+g0UmlyMa2YWAWsBgSuUSjJePgbUZWHuxp/dM8CQ4lHJ
+ADvfSI9ysJQM/trqjRu5BRhxiKWR72QSi1qpDPT0nKWlzQ58zs3RSuOJbWm8oOqr
+XL9G/XmvgzK1qwToI/WmXBeaqmfpkagYZm+TJW0GVnDqTC+EoXdFKW7aWIjlcb4p
+tYoiRA/2jjq5OqeV6iKnxz7mEJQR1xDebm6+AWgFy4zyB/QvzanaUTvNiLhyBy6Q
+YwXJHkNh+KrVszBlXxkARrGesXgqOznmDeErkOKDjxzQv+cCAwEAATANBgkqhkiG
+9w0BAQsFAAOCAgEAk83b9wY9iwRrx5Yep3DA3xZkVu3GJcKf0tTL8apP1MzVBSUK
+5tkvW2Z4D41jpZWgJDRF8/nT2lvVwvd5xQ8/oTUerFeG/ZZ+AiBagkBKl8piPHqD
+cefAO8N2SKoYHV4xBeoVU6InUuJ7xu7BLF6tY3xKvx0XsjGC7B621xmq+E56dPZg
+sQwekkxODbUw4NekqYFY21BT4xiWVrTRLIGY9AfV9Ry4gqQTxda7yst4ykWh1a9e
+O+426uz3jshzpQTjZwk8kCZquJKa8Qzqfdlevns0FQDP5jck4BH/YkMNsa/g9XCd
+ZHSB7gqAfNoNTB1rqNKIfPUF4mTu/RWMVwxb8f6h0TfywHZ4q/4R3Zfu3jUyeVVY
+ziJu2CJpcoR9SESKFbN4WFzk91nIhf2pCGo/qNO5f+n5ZPnS2jrrWL5h64e1rz2h
+rVKIYLfeM2M8lVzSL1V0aJ+POcruTRsmlrFT5f7na/5YFt5N+5Z5fzixCLr1MK2w
+4gFw+KhN7CAhKGzHq3NBdWpRFFMR53hyeYsb1vvwFu07JTRh+NbaePk/sk07WtCo
+u2w6pD7xlayTAWcR9WRBv7c3lDejN80U8DONb8fLwtI5oIrkSuwOqvmlDOeFpKiT
+MwTB6oC81Ar39P0R53247w7u9plhPUrmDn/A5KphW633UvgbkH6VmB4Isiw=
+-----END CERTIFICATE-----
diff --git a/client/testdata/gitalykey.pem b/client/testdata/gitalykey.pem
new file mode 100644
index 000000000..8df87e633
--- /dev/null
+++ b/client/testdata/gitalykey.pem
@@ -0,0 +1,52 @@
+-----BEGIN PRIVATE KEY-----
+MIIJRAIBADANBgkqhkiG9w0BAQEFAASCCS4wggkqAgEAAoICAQCklck5alSRXfa/
+yBFctafpMSxCbLZZ6KVBeD3pXpU5CMZkAYwQksSMf1YcE15mLhX5b6PUUHy9ZM1E
+ZNw5ylISYMW57CgElUDx0W00XiOPtBDKaacp4O45bh9Yt5RhzIbHKOWmSbb4NSDk
+Jq9PhsxkgupuwBq/EnxIoJ0mky1bezGSWca5MdwByQeV1pv1nEf+piovFzkSTYEr
+g6JsHEDziHVFSyp7YR3NlQ6h63fGnAbdWvxsY+pHs+yCGzpMN1ZTyFhgeVF4JZ7O
+BkeJgOhGpj0cJmsdKlRnWVtGj77aPhu90Uc4BSbgERDp8VyyC1b7GQ0rxvGP1dNy
+m4OsRWxy/d/IGUIxK8P4ek1uvaTWhlI4WHEhIjAEspZAGOrma68xFuasblGBaoxa
+Ndv6DRSaXIxrZhYBawGBK5RKMl4+BtRlYe7Gn90zwJDiUckAO99Ij3KwlAz+2uqN
+G7kFGHGIpZHvZBKLWqkM9PScpaXNDnzOzdFK44ltabyg6qtcv0b9ea+DMrWrBOgj
+9aZcF5qqZ+mRqBhmb5MlbQZWcOpML4Shd0UpbtpYiOVxvim1iiJED/aOOrk6p5Xq
+IqfHPuYQlBHXEN5ubr4BaAXLjPIH9C/NqdpRO82IuHIHLpBjBckeQ2H4qtWzMGVf
+GQBGsZ6xeCo7OeYN4SuQ4oOPHNC/5wIDAQABAoICAHjlPeZa4LvXFcVSJM7A8RIt
++KDiUiBA8ALjXDbsLxiyBWi4ajZSWOYLMyl0YMcV2zZadzEh3j8QqGcw30PkBd1S
+EGu9uLeFGyuF9n2dGOoaDqtgaFYuz06IQaZdUzVzkx0AQZCgXTJ9dCei8uurzL+Y
+GrQ3kG4CGiEPOeB4A71LBOLH511p7n2xOU0rU2xa29eGHz5wBJAZNmTMUKaxKlS5
+S8sWp6HxeH7mmtT9rgHJ4pD+oKTNz+3TkEsRzQTnMRZh9+kFtH5YxAn6OtoaQoSC
+4CipX80QpuczkASI2lxdeus3quTPg/rbDl2J2dk+0ymnATHC9PX+z09ERLhqVnoD
+QBY+vIw8Opj7GB/viWm/IiF0wseM+qEgr+f1qgl8pRe4N+EeD2OCnB++kslOhol+
+50KJbMJ/bfHo/3NKCqAHoKd/gk4HAiqmEKHRgSaXXjvE6bBRoFeL20zFitzCWm8z
+H3CexwDRY0qJqy80Qahg+NQX58MkYskOA42fFMzuvUxfYIu/mpTTDvRK5jxsDffe
+cPU2BTcbxi5hCJjo7ertid5JGp51jr6XvViuDYf77hhw8Cm5KdeavHcF1XgksRa3
+SHTtDv/Um1RvOqMzINy1Z5mFdBN8TdzEA+9gPCm+pqpD0FTDiu/IkggYeszk0syf
+AIhoEJI8PkBKqQj0DxoBAoIBAQDZ96DL+fzwXN13aqhvYNTfGxZ3RCP40KCuCSrQ
+gjcGcGavFOR21Y5CHaFmIFNmrtXTj3P950N+a8/KNAmm9zFx6060HEHyR6rN5b0h
+BMMlp7ezyPY+VCWJWCEi3TD+4LseAynyP05rWdm2+nsGBxaXWB8yAq0CwuyYTQdZ
+IZHGKeGI9irv+5mIe7bVRCVEug22u6gHmOLERXCqO70Mzi/c/UFxjGmF0LR4d7TY
+VIQ5r/PPvXJzf72PVIPwJQzRsaOXnZvD1UzSahyaB3fABB6I1y6OfXyU8BukwBQ5
+J0qVRFpzMc46PFULQC5KTUIzPcnrW73UWEu5XGiAooN5SysnAoIBAQDBTaGC/5xO
+755EdZggpx+05LlmoW0ijeDnuRcKPlwap4dPFUSQS2EOWxjmm4K8sNAOdiQt7Jwf
+gX/S6jdY79V0rkyktWk1uCfiwu1c/rvyLdl2Jg1RW6HByL7MTBuASfuCgJsfzhev
+yu+HzPJMQNFhgQTcLL9LYHp5moGKCbJzIp+FXOeFokjjlynrrmPoHV0A8To6s7q2
+yH5qu9OaOu75kWqDul5b9cXO+isxUBZbEjUy7OEa3Zezuhq8XgZVE5t2QgJOnDI/
+NNp5d16N7GcDpaEZzSNag95F0+wsFIgT29LL2zSF6h3+VjeqKTxwbRtFsMboN9TZ
+QHIgBB+2ib1BAoIBAQDC31r6ovFacJxsZIZctcT8BzrJvLkwfk356yZFLvZFIn8b
+r2EnQX0jbVxcczA9kLiJoirA6V91iqxHCslKZpzlTcyayNzI4Pw7g1fZSmmyo8Vg
+zp4hUZgRuCJACmQArCl/BrMc6y6QWc+FgWI2HGY9P0L8slm+K0neTJfyP0oWUmFa
+00PGNTqqRHlNKNTtIi6aniH3UOAFPFQjTq+R4FH4kNBO1YuOYO7I+bVM6BsjfEVO
+CQFnc+ClYZloPae9XsV1Cys1JeG+CbKyn1SX7tbh3wi3ykd03UrJvBUYmCFdXLRF
+Y1UOydv66BG6ymISb/60FtycGajx+0VPJHzJF8RnAoIBAQCVVyyY0HIqaeWUbmWB
+lJxiXPL/32c5cvN3EwBB4bu2vAdFieDWueXZ+Xdbcnmm3dNf2NZKxKo5jQr8IAdy
+ppf69U4xUhZeclAeWQqY9hSuHc4MAYn4eRqXZEhD/eihTIcLY+B0yfxyzA4SlLv9
+PXaGJe9jSw7fZUI6AKxjwOolGXK0zfnwvFgjvP2eH7T/9u+LctLR11lBLdS9ES+B
+0FYgacAo1SthUJfqOEx2ZLFg2shO98NRxjEVoYpWTS4HPIa27nhp0zLesi63+QkM
+DL/piWTVUi8mFwr6V6f2xkX7UbGh3VDOxPk3LdUDmaggE6smRFTnw3ql/awuIAGA
+PRoBAoIBAQCwIkbP/Py8qXkrUil/ZW2+7yPXy4DeOkduLBrLBXH5fxAPUoyOywjl
+CFOVcHNuioRZnN22M64VzlCgRhY4gD+ypyeFmVR4fHBWZuQObwt6jkaGXxvcGl+U
+cDrMYt1xjJbjEdvX4+VjkLwJzIAzBG09agk3eLwcVAH8w5uteyKNdi0Kg9mClFJm
+LRJNjI6fp5KfVitMEthx9WEe5Zu9phBLCtqYNYQoH+VY3yp8aD9NB0X5sgHYKCaK
+jgQUpEnGU9zSnKeK8MglhWson3a6NEjPufsAjHgGHbTAfGEXLkiHZee3gAB2BJdk
+eM9aMpgdAlLOJrfZHS3kK3968ZclB4GB
+-----END PRIVATE KEY-----
diff --git a/client/upload_archive.go b/client/upload_archive.go
index 2459519b3..b361b3d85 100644
--- a/client/upload_archive.go
+++ b/client/upload_archive.go
@@ -1,11 +1,11 @@
package client
import (
+ "context"
"io"
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/streamio"
- "golang.org/x/net/context"
"google.golang.org/grpc"
)
diff --git a/client/upload_pack.go b/client/upload_pack.go
index 08372c5fc..781eddbb7 100644
--- a/client/upload_pack.go
+++ b/client/upload_pack.go
@@ -1,11 +1,11 @@
package client
import (
+ "context"
"io"
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/streamio"
- "golang.org/x/net/context"
"google.golang.org/grpc"
)
diff --git a/cmd/gitaly-ssh/auth_test.go b/cmd/gitaly-ssh/auth_test.go
index 432c8f207..33f76ef21 100644
--- a/cmd/gitaly-ssh/auth_test.go
+++ b/cmd/gitaly-ssh/auth_test.go
@@ -6,6 +6,7 @@ import (
"os"
"os/exec"
"path"
+ "path/filepath"
"strconv"
"strings"
"testing"
@@ -44,6 +45,9 @@ func TestConnectivity(t *testing.T) {
socketPath := testhelper.GetTemporaryGitalySocketFileName()
+ relativeSocketPath, err := filepath.Rel(cwd, socketPath)
+ require.NoError(t, err, "relative path failure: %v. %s", err)
+
tcpServer, tcpPort := runServer(t, server.NewInsecure, "tcp", "localhost:0")
defer tcpServer.Stop()
@@ -54,15 +58,35 @@ func TestConnectivity(t *testing.T) {
defer unixServer.Stop()
testCases := []struct {
- addr string
+ name string
+ addr string
+ proxy bool
}{
{
+ name: "tcp",
addr: fmt.Sprintf("tcp://localhost:%d", tcpPort),
},
{
- addr: fmt.Sprintf("unix://%s", socketPath),
+ name: "unix absolute",
+ addr: fmt.Sprintf("unix:%s", socketPath),
+ },
+ {
+ name: "unix abs with proxy",
+ addr: fmt.Sprintf("unix:%s", socketPath),
+ proxy: true,
+ },
+ {
+ name: "unix relative",
+ addr: fmt.Sprintf("unix:%s", relativeSocketPath),
+ },
+ {
+ name: "unix relative with proxy",
+ addr: fmt.Sprintf("unix:%s", relativeSocketPath),
+ proxy: true,
},
+
{
+ name: "tls",
addr: fmt.Sprintf("tls://localhost:%d", tlsPort),
},
}
@@ -74,20 +98,29 @@ func TestConnectivity(t *testing.T) {
require.NoError(t, err)
for _, testcase := range testCases {
- cmd := exec.Command("git", "ls-remote", "git@localhost:test/test.git", "refs/heads/master")
- cmd.Stderr = os.Stderr
- cmd.Env = []string{
- fmt.Sprintf("GITALY_PAYLOAD=%s", payload),
- fmt.Sprintf("GITALY_ADDRESS=%s", testcase.addr),
- fmt.Sprintf("PATH=.:%s", os.Getenv("PATH")),
- fmt.Sprintf("GIT_SSH_COMMAND=%s upload-pack", gitalySSHPath),
- fmt.Sprintf("SSL_CERT_DIR=%s", certPoolPath),
- }
-
- output, err := cmd.Output()
-
- require.NoError(t, err, "git ls-remote exit status")
- require.True(t, strings.HasSuffix(strings.TrimSpace(string(output)), "refs/heads/master"))
+ t.Run(testcase.name, func(t *testing.T) {
+ cmd := exec.Command("git", "ls-remote", "git@localhost:test/test.git", "refs/heads/master")
+ cmd.Stderr = os.Stderr
+ cmd.Env = []string{
+ fmt.Sprintf("GITALY_PAYLOAD=%s", payload),
+ fmt.Sprintf("GITALY_ADDRESS=%s", testcase.addr),
+ fmt.Sprintf("PATH=.:%s", os.Getenv("PATH")),
+ fmt.Sprintf("GIT_SSH_COMMAND=%s upload-pack", gitalySSHPath),
+ fmt.Sprintf("SSL_CERT_DIR=%s", certPoolPath),
+ }
+
+ if testcase.proxy {
+ cmd.Env = append(cmd.Env,
+ "http_proxy=http://invalid:1234",
+ "https_proxy=https://invalid:1234",
+ )
+ }
+
+ output, err := cmd.Output()
+
+ require.NoError(t, err, "git ls-remote exit status")
+ require.True(t, strings.HasSuffix(strings.TrimSpace(string(output)), "refs/heads/master"))
+ })
}
}
diff --git a/cmd/gitaly/main.go b/cmd/gitaly/main.go
index c12defa28..3be1e38e8 100644
--- a/cmd/gitaly/main.go
+++ b/cmd/gitaly/main.go
@@ -20,6 +20,7 @@ import (
"gitlab.com/gitlab-org/gitaly/internal/server"
"gitlab.com/gitlab-org/gitaly/internal/tempdir"
"gitlab.com/gitlab-org/gitaly/internal/version"
+ "gitlab.com/gitlab-org/labkit/tracing"
)
var (
@@ -103,6 +104,7 @@ func main() {
config.ConfigureSentry(version.GetVersion())
config.ConfigurePrometheus()
config.ConfigureConcurrencyLimits()
+ tracing.Initialize(tracing.WithServiceName("gitaly"))
tempdir.StartCleaning()
diff --git a/internal/featureflag/grpc_header.go b/internal/featureflag/grpc_header.go
index 28d3c978c..e71f1cfe9 100644
--- a/internal/featureflag/grpc_header.go
+++ b/internal/featureflag/grpc_header.go
@@ -1,9 +1,9 @@
package featureflag
import (
+ "context"
"fmt"
- "golang.org/x/net/context"
"google.golang.org/grpc/metadata"
)
diff --git a/internal/featureflag/grpc_header_test.go b/internal/featureflag/grpc_header_test.go
index 76e0925c5..8d18c6037 100644
--- a/internal/featureflag/grpc_header_test.go
+++ b/internal/featureflag/grpc_header_test.go
@@ -1,10 +1,10 @@
package featureflag
import (
+ "context"
"testing"
"github.com/stretchr/testify/assert"
- "golang.org/x/net/context"
"google.golang.org/grpc/metadata"
)
diff --git a/internal/helper/chunker/chunker.go b/internal/helper/chunker/chunker.go
new file mode 100644
index 000000000..f8bf5dc1b
--- /dev/null
+++ b/internal/helper/chunker/chunker.go
@@ -0,0 +1,59 @@
+package chunker
+
+// Item could be e.g. a commit in an RPC that returns a chunked stream of
+// commits.
+type Item interface{}
+
+// Sender encapsulates a gRPC response stream and the current chunk
+// that's being built.
+//
+// Reset, Append, [Append...], Send, Reset, Append, [Append...], Send, ...
+type Sender interface {
+ // Reset should create a fresh response message.
+ Reset()
+ // Append should append the given item to the slice in the current response message
+ Append(Item)
+ // Send should send the current response message
+ Send() error
+}
+
+// New returns a new Chunker.
+func New(s Sender) *Chunker { return &Chunker{s: s} }
+
+// Chunker lets you spread items you want to send over multiple chunks.
+// This type is not thread-safe.
+type Chunker struct {
+ s Sender
+ n int
+}
+
+// Send will append an item to the current chunk and send the chunk if it is full.
+func (c *Chunker) Send(it Item) error {
+ if c.n == 0 {
+ c.s.Reset()
+ }
+
+ c.s.Append(it)
+ c.n++
+
+ const chunkSize = 20
+ if c.n >= chunkSize {
+ return c.sendResponseMsg()
+ }
+
+ return nil
+}
+
+func (c *Chunker) sendResponseMsg() error {
+ c.n = 0
+ return c.s.Send()
+}
+
+// Flush sends remaining items in the current chunk, if any.
+func (c *Chunker) Flush() error {
+ if c.n == 0 {
+ return nil
+ }
+
+ return c.sendResponseMsg()
+}
diff --git a/internal/helper/housekeeping/housekeeping.go b/internal/helper/housekeeping/housekeeping.go
index 3b30c8484..5d05b0c06 100644
--- a/internal/helper/housekeeping/housekeeping.go
+++ b/internal/helper/housekeeping/housekeeping.go
@@ -1,6 +1,7 @@
package housekeeping
import (
+ "context"
"os"
"path/filepath"
"strings"
@@ -8,7 +9,6 @@ import (
grpc_logrus "github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus"
log "github.com/sirupsen/logrus"
- "golang.org/x/net/context"
)
const deleteTempFilesOlderThanDuration = 7 * 24 * time.Hour
diff --git a/internal/helper/housekeeping/housekeeping_test.go b/internal/helper/housekeeping/housekeeping_test.go
index 8f6defa73..21c486db5 100644
--- a/internal/helper/housekeeping/housekeeping_test.go
+++ b/internal/helper/housekeeping/housekeeping_test.go
@@ -1,6 +1,7 @@
package housekeeping
import (
+ "context"
"io/ioutil"
"os"
"path/filepath"
@@ -8,7 +9,6 @@ import (
"time"
"github.com/stretchr/testify/assert"
- "golang.org/x/net/context"
)
type entryFinalState int
diff --git a/internal/helper/storage.go b/internal/helper/storage.go
index 5405421ce..83341b0c4 100644
--- a/internal/helper/storage.go
+++ b/internal/helper/storage.go
@@ -1,12 +1,12 @@
package helper
import (
+ "context"
"encoding/base64"
"encoding/json"
"fmt"
"gitlab.com/gitlab-org/gitaly/internal/storage"
- "golang.org/x/net/context"
"google.golang.org/grpc/metadata"
)
diff --git a/internal/middleware/cancelhandler/cancelhandler.go b/internal/middleware/cancelhandler/cancelhandler.go
index 4592059d5..8ee870522 100644
--- a/internal/middleware/cancelhandler/cancelhandler.go
+++ b/internal/middleware/cancelhandler/cancelhandler.go
@@ -1,7 +1,8 @@
package cancelhandler
import (
- "golang.org/x/net/context"
+ "context"
+
"google.golang.org/grpc"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
diff --git a/internal/middleware/limithandler/concurrency_limiter.go b/internal/middleware/limithandler/concurrency_limiter.go
index 56c67ae89..66343f715 100644
--- a/internal/middleware/limithandler/concurrency_limiter.go
+++ b/internal/middleware/limithandler/concurrency_limiter.go
@@ -1,10 +1,10 @@
package limithandler
import (
+ "context"
"sync"
"time"
- "golang.org/x/net/context"
"golang.org/x/sync/semaphore"
)
diff --git a/internal/middleware/limithandler/concurrency_limiter_test.go b/internal/middleware/limithandler/concurrency_limiter_test.go
index e89dbcb97..8fe1c829e 100644
--- a/internal/middleware/limithandler/concurrency_limiter_test.go
+++ b/internal/middleware/limithandler/concurrency_limiter_test.go
@@ -1,13 +1,13 @@
package limithandler
import (
+ "context"
"strconv"
"sync"
"testing"
"time"
"github.com/stretchr/testify/assert"
- "golang.org/x/net/context"
)
type counter struct {
diff --git a/internal/middleware/limithandler/limithandler.go b/internal/middleware/limithandler/limithandler.go
index a70e4a309..7d8d6ab8f 100644
--- a/internal/middleware/limithandler/limithandler.go
+++ b/internal/middleware/limithandler/limithandler.go
@@ -1,7 +1,8 @@
package limithandler
import (
- "golang.org/x/net/context"
+ "context"
+
"google.golang.org/grpc"
)
diff --git a/internal/middleware/limithandler/limithandler_test.go b/internal/middleware/limithandler/limithandler_test.go
index 4a6e6ffc8..c98f7f389 100644
--- a/internal/middleware/limithandler/limithandler_test.go
+++ b/internal/middleware/limithandler/limithandler_test.go
@@ -1,6 +1,7 @@
package limithandler_test
import (
+ "context"
"net"
"sync"
"testing"
@@ -10,7 +11,6 @@ import (
"gitlab.com/gitlab-org/gitaly/internal/middleware/limithandler"
pb "gitlab.com/gitlab-org/gitaly/internal/middleware/limithandler/testpb"
"gitlab.com/gitlab-org/gitaly/internal/testhelper"
- "golang.org/x/net/context"
"google.golang.org/grpc"
)
diff --git a/internal/middleware/limithandler/metrics.go b/internal/middleware/limithandler/metrics.go
index 3e0accd7a..6628044a0 100644
--- a/internal/middleware/limithandler/metrics.go
+++ b/internal/middleware/limithandler/metrics.go
@@ -1,12 +1,12 @@
package limithandler
import (
+ "context"
"strings"
"time"
grpc_logrus "github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus"
"github.com/prometheus/client_golang/prometheus"
- "golang.org/x/net/context"
)
const acquireDurationLogThreshold = 10 * time.Millisecond
diff --git a/internal/middleware/limithandler/testhelper_test.go b/internal/middleware/limithandler/testhelper_test.go
index 40eff4f01..424804928 100644
--- a/internal/middleware/limithandler/testhelper_test.go
+++ b/internal/middleware/limithandler/testhelper_test.go
@@ -1,10 +1,10 @@
package limithandler_test
import (
+ "context"
"sync/atomic"
pb "gitlab.com/gitlab-org/gitaly/internal/middleware/limithandler/testpb"
- "golang.org/x/net/context"
)
type server struct {
diff --git a/internal/middleware/limithandler/testpb/test.pb.go b/internal/middleware/limithandler/testpb/test.pb.go
index f94d68549..03a700107 100644
--- a/internal/middleware/limithandler/testpb/test.pb.go
+++ b/internal/middleware/limithandler/testpb/test.pb.go
@@ -24,7 +24,8 @@ import fmt "fmt"
import math "math"
import (
- context "golang.org/x/net/context"
+ context "context"
+
grpc "google.golang.org/grpc"
)
diff --git a/internal/middleware/metadatahandler/metadatahandler.go b/internal/middleware/metadatahandler/metadatahandler.go
index 5091e6654..ca3690662 100644
--- a/internal/middleware/metadatahandler/metadatahandler.go
+++ b/internal/middleware/metadatahandler/metadatahandler.go
@@ -1,12 +1,13 @@
package metadatahandler
import (
+ "context"
+
grpc_ctxtags "github.com/grpc-ecosystem/go-grpc-middleware/tags"
"github.com/prometheus/client_golang/prometheus"
gitalyauth "gitlab.com/gitlab-org/gitaly/auth"
"gitlab.com/gitlab-org/gitaly/internal/helper"
"gitlab.com/gitlab-org/labkit/correlation"
- "golang.org/x/net/context"
"google.golang.org/grpc"
"google.golang.org/grpc/metadata"
)
diff --git a/internal/middleware/panichandler/panic_handler.go b/internal/middleware/panichandler/panic_handler.go
index 58f9c0abf..58e644e12 100644
--- a/internal/middleware/panichandler/panic_handler.go
+++ b/internal/middleware/panichandler/panic_handler.go
@@ -1,8 +1,9 @@
package panichandler
import (
+ "context"
+
log "github.com/sirupsen/logrus"
- "golang.org/x/net/context"
"google.golang.org/grpc"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
diff --git a/internal/middleware/sentryhandler/sentryhandler.go b/internal/middleware/sentryhandler/sentryhandler.go
index 44d398a12..47991a82a 100644
--- a/internal/middleware/sentryhandler/sentryhandler.go
+++ b/internal/middleware/sentryhandler/sentryhandler.go
@@ -1,6 +1,7 @@
package sentryhandler
import (
+ "context"
"fmt"
"strings"
"time"
@@ -8,7 +9,6 @@ import (
raven "github.com/getsentry/raven-go"
grpc_ctxtags "github.com/grpc-ecosystem/go-grpc-middleware/tags"
"gitlab.com/gitlab-org/gitaly/internal/helper"
- "golang.org/x/net/context"
"google.golang.org/grpc"
"google.golang.org/grpc/codes"
)
diff --git a/internal/middleware/sentryhandler/sentryhandler_test.go b/internal/middleware/sentryhandler/sentryhandler_test.go
index 2803d45dc..88888acb9 100644
--- a/internal/middleware/sentryhandler/sentryhandler_test.go
+++ b/internal/middleware/sentryhandler/sentryhandler_test.go
@@ -1,12 +1,12 @@
package sentryhandler
import (
+ "context"
"fmt"
"testing"
"time"
"github.com/stretchr/testify/assert"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
)
diff --git a/internal/rubyserver/health.go b/internal/rubyserver/health.go
index 10550d7dc..cc6005f89 100644
--- a/internal/rubyserver/health.go
+++ b/internal/rubyserver/health.go
@@ -1,9 +1,9 @@
package rubyserver
import (
+ "context"
"time"
- "golang.org/x/net/context"
"google.golang.org/grpc"
healthpb "google.golang.org/grpc/health/grpc_health_v1"
)
diff --git a/internal/rubyserver/rubyserver.go b/internal/rubyserver/rubyserver.go
index eb6a40a0b..8eab03025 100644
--- a/internal/rubyserver/rubyserver.go
+++ b/internal/rubyserver/rubyserver.go
@@ -1,6 +1,7 @@
package rubyserver
import (
+ "context"
"fmt"
"io/ioutil"
"os"
@@ -23,7 +24,7 @@ import (
"gitlab.com/gitlab-org/gitaly/internal/version"
"gitlab.com/gitlab-org/gitaly/streamio"
grpccorrelation "gitlab.com/gitlab-org/labkit/correlation/grpc"
- "golang.org/x/net/context"
+ grpctracing "gitlab.com/gitlab-org/labkit/tracing/grpc"
"google.golang.org/grpc"
)
@@ -258,12 +259,14 @@ func dialOptions() []grpc.DialOption {
grpc.WithUnaryInterceptor(
grpc_middleware.ChainUnaryClient(
grpc_prometheus.UnaryClientInterceptor,
+ grpctracing.UnaryClientTracingInterceptor(),
grpccorrelation.UnaryClientCorrelationInterceptor(),
),
),
grpc.WithStreamInterceptor(
grpc_middleware.ChainStreamClient(
grpc_prometheus.StreamClientInterceptor,
+ grpctracing.StreamClientTracingInterceptor(),
grpccorrelation.StreamClientCorrelationInterceptor(),
),
),
diff --git a/internal/server/auth/auth.go b/internal/server/auth/auth.go
index b97bca8fc..c83ddd615 100644
--- a/internal/server/auth/auth.go
+++ b/internal/server/auth/auth.go
@@ -1,13 +1,13 @@
package auth
import (
+ "context"
"time"
grpc_auth "github.com/grpc-ecosystem/go-grpc-middleware/auth"
"github.com/prometheus/client_golang/prometheus"
gitalyauth "gitlab.com/gitlab-org/gitaly/auth"
"gitlab.com/gitlab-org/gitaly/internal/config"
- "golang.org/x/net/context"
"google.golang.org/grpc"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
diff --git a/internal/server/auth_test.go b/internal/server/auth_test.go
index 9448df134..fdbf3d6b0 100644
--- a/internal/server/auth_test.go
+++ b/internal/server/auth_test.go
@@ -1,6 +1,7 @@
package server
import (
+ netctx "context"
"crypto/x509"
"io/ioutil"
"net"
@@ -11,7 +12,6 @@ import (
gitalyauth "gitlab.com/gitlab-org/gitaly/auth"
"gitlab.com/gitlab-org/gitaly/internal/config"
"gitlab.com/gitlab-org/gitaly/internal/testhelper"
- netctx "golang.org/x/net/context"
"google.golang.org/grpc"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/credentials"
diff --git a/internal/server/server.go b/internal/server/server.go
index cf5630bad..32bae8d2a 100644
--- a/internal/server/server.go
+++ b/internal/server/server.go
@@ -1,6 +1,7 @@
package server
import (
+ "context"
"crypto/tls"
grpc_middleware "github.com/grpc-ecosystem/go-grpc-middleware"
@@ -21,7 +22,7 @@ import (
"gitlab.com/gitlab-org/gitaly/internal/server/auth"
"gitlab.com/gitlab-org/gitaly/internal/service"
grpccorrelation "gitlab.com/gitlab-org/labkit/correlation/grpc"
- "golang.org/x/net/context"
+ grpctracing "gitlab.com/gitlab-org/labkit/tracing/grpc"
"google.golang.org/grpc"
"google.golang.org/grpc/credentials"
"google.golang.org/grpc/reflection"
@@ -82,6 +83,7 @@ func createNewServer(rubyServer *rubyserver.Server, secure bool) *grpc.Server {
cancelhandler.Stream, // Should be below LogHandler
lh.StreamInterceptor(),
auth.StreamServerInterceptor(),
+ grpctracing.StreamServerTracingInterceptor(),
// Panic handler should remain last so that application panics will be
// converted to errors and logged
panichandler.StreamPanicHandler,
@@ -96,6 +98,7 @@ func createNewServer(rubyServer *rubyserver.Server, secure bool) *grpc.Server {
cancelhandler.Unary, // Should be below LogHandler
lh.UnaryInterceptor(),
auth.UnaryServerInterceptor(),
+ grpctracing.UnaryServerTracingInterceptor(),
// Panic handler should remain last so that application panics will be
// converted to errors and logged
panichandler.UnaryPanicHandler,
diff --git a/internal/service/commit/between_test.go b/internal/service/commit/between_test.go
index 8f6fdd1cc..00187a32f 100644
--- a/internal/service/commit/between_test.go
+++ b/internal/service/commit/between_test.go
@@ -1,6 +1,7 @@
package commit
import (
+ "context"
"io"
"testing"
@@ -8,7 +9,6 @@ import (
"github.com/stretchr/testify/require"
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/testhelper"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
)
diff --git a/internal/service/commit/commits_by_message_test.go b/internal/service/commit/commits_by_message_test.go
index ca183c3ef..1801eb1cf 100644
--- a/internal/service/commit/commits_by_message_test.go
+++ b/internal/service/commit/commits_by_message_test.go
@@ -1,6 +1,7 @@
package commit
import (
+ "context"
"io"
"testing"
@@ -8,7 +9,6 @@ import (
"github.com/stretchr/testify/require"
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/testhelper"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
)
diff --git a/internal/service/commit/count_commits.go b/internal/service/commit/count_commits.go
index 1167c23c0..55d82d83e 100644
--- a/internal/service/commit/count_commits.go
+++ b/internal/service/commit/count_commits.go
@@ -2,6 +2,7 @@ package commit
import (
"bytes"
+ "context"
"fmt"
"io/ioutil"
"strconv"
@@ -10,7 +11,6 @@ import (
grpc_logrus "github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus"
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/git"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
)
diff --git a/internal/service/commit/count_commits_test.go b/internal/service/commit/count_commits_test.go
index ec0acae17..8c41f0755 100644
--- a/internal/service/commit/count_commits_test.go
+++ b/internal/service/commit/count_commits_test.go
@@ -1,6 +1,7 @@
package commit
import (
+ "context"
"fmt"
"testing"
"time"
@@ -9,7 +10,6 @@ import (
"github.com/stretchr/testify/require"
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/testhelper"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
)
diff --git a/internal/service/commit/extractsignature_test.go b/internal/service/commit/extractsignature_test.go
index 786fde75f..049178a7c 100644
--- a/internal/service/commit/extractsignature_test.go
+++ b/internal/service/commit/extractsignature_test.go
@@ -1,6 +1,7 @@
package commit
import (
+ "context"
"io"
"io/ioutil"
"testing"
@@ -8,7 +9,6 @@ import (
"github.com/stretchr/testify/require"
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/testhelper"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
)
diff --git a/internal/service/commit/find_all_commits_test.go b/internal/service/commit/find_all_commits_test.go
index e1e696b52..95a8082f1 100644
--- a/internal/service/commit/find_all_commits_test.go
+++ b/internal/service/commit/find_all_commits_test.go
@@ -1,6 +1,7 @@
package commit
import (
+ "context"
"io"
"testing"
@@ -9,7 +10,6 @@ import (
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/service/ref"
"gitlab.com/gitlab-org/gitaly/internal/testhelper"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
)
diff --git a/internal/service/commit/find_commit.go b/internal/service/commit/find_commit.go
index a0a474e9f..de9c970d8 100644
--- a/internal/service/commit/find_commit.go
+++ b/internal/service/commit/find_commit.go
@@ -1,10 +1,11 @@
package commit
import (
+ "context"
+
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/git"
"gitlab.com/gitlab-org/gitaly/internal/git/log"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
)
diff --git a/internal/service/commit/find_commit_test.go b/internal/service/commit/find_commit_test.go
index bdf8e35b2..12d730e69 100644
--- a/internal/service/commit/find_commit_test.go
+++ b/internal/service/commit/find_commit_test.go
@@ -1,6 +1,7 @@
package commit
import (
+ "context"
"io/ioutil"
"strings"
"testing"
@@ -12,7 +13,6 @@ import (
"gitlab.com/gitlab-org/gitaly/internal/git/log"
"gitlab.com/gitlab-org/gitaly/internal/helper"
"gitlab.com/gitlab-org/gitaly/internal/testhelper"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/metadata"
"google.golang.org/grpc/status"
diff --git a/internal/service/commit/isancestor.go b/internal/service/commit/isancestor.go
index 4c54427fa..e6d35a11c 100644
--- a/internal/service/commit/isancestor.go
+++ b/internal/service/commit/isancestor.go
@@ -1,11 +1,12 @@
package commit
import (
+ "context"
+
grpc_logrus "github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus"
log "github.com/sirupsen/logrus"
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/git"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
)
diff --git a/internal/service/commit/isancestor_test.go b/internal/service/commit/isancestor_test.go
index 1d958ef97..d4c7af209 100644
--- a/internal/service/commit/isancestor_test.go
+++ b/internal/service/commit/isancestor_test.go
@@ -1,6 +1,7 @@
package commit
import (
+ "context"
"fmt"
"os/exec"
"testing"
@@ -9,7 +10,6 @@ import (
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/helper"
"gitlab.com/gitlab-org/gitaly/internal/testhelper"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
)
diff --git a/internal/service/commit/languages.go b/internal/service/commit/languages.go
index 052de5bf9..166ff5b8c 100644
--- a/internal/service/commit/languages.go
+++ b/internal/service/commit/languages.go
@@ -1,6 +1,7 @@
package commit
import (
+ "context"
"io/ioutil"
"sort"
"strings"
@@ -10,7 +11,6 @@ import (
"gitlab.com/gitlab-org/gitaly/internal/helper"
"gitlab.com/gitlab-org/gitaly/internal/linguist"
"gitlab.com/gitlab-org/gitaly/internal/service/ref"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
)
diff --git a/internal/service/commit/last_commit_for_path.go b/internal/service/commit/last_commit_for_path.go
index 9cf65f39c..9d7015671 100644
--- a/internal/service/commit/last_commit_for_path.go
+++ b/internal/service/commit/last_commit_for_path.go
@@ -1,11 +1,11 @@
package commit
import (
+ "context"
"fmt"
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/git/log"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
)
diff --git a/internal/service/commit/last_commit_for_path_test.go b/internal/service/commit/last_commit_for_path_test.go
index 33232e986..3552fc701 100644
--- a/internal/service/commit/last_commit_for_path_test.go
+++ b/internal/service/commit/last_commit_for_path_test.go
@@ -1,13 +1,13 @@
package commit
import (
+ "context"
"testing"
"github.com/golang/protobuf/ptypes/timestamp"
"github.com/stretchr/testify/require"
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/testhelper"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
)
diff --git a/internal/service/commit/list_commits_by_oid.go b/internal/service/commit/list_commits_by_oid.go
index 05a7a1deb..1fd31f7ae 100644
--- a/internal/service/commit/list_commits_by_oid.go
+++ b/internal/service/commit/list_commits_by_oid.go
@@ -4,10 +4,9 @@ import (
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/git/catfile"
gitlog "gitlab.com/gitlab-org/gitaly/internal/git/log"
+ "gitlab.com/gitlab-org/gitaly/internal/helper/chunker"
)
-const batchSizeListCommitsByOid = 20
-
func (s *server) ListCommitsByOid(in *gitalypb.ListCommitsByOidRequest, stream gitalypb.CommitService_ListCommitsByOidServer) error {
ctx := stream.Context()
@@ -16,11 +15,8 @@ func (s *server) ListCommitsByOid(in *gitalypb.ListCommitsByOidRequest, stream g
return err
}
- send := func(commits []*gitalypb.GitCommit) error {
- return stream.Send(&gitalypb.ListCommitsByOidResponse{Commits: commits})
- }
+ sender := chunker.New(&commitsByOidSender{stream: stream})
- var commits []*gitalypb.GitCommit
for _, oid := range in.Oid {
commit, err := gitlog.GetCommitCatfile(c, oid)
if err != nil {
@@ -31,19 +27,22 @@ func (s *server) ListCommitsByOid(in *gitalypb.ListCommitsByOidRequest, stream g
continue
}
- commits = append(commits, commit)
-
- if len(commits) == batchSizeListCommitsByOid {
- if err := send(commits); err != nil {
- return err
- }
- commits = nil
+ if err := sender.Send(commit); err != nil {
+ return err
}
}
- if len(commits) > 0 {
- return send(commits)
- }
+ return sender.Flush()
+}
+
+type commitsByOidSender struct {
+ response *gitalypb.ListCommitsByOidResponse
+ stream gitalypb.CommitService_ListCommitsByOidServer
+}
- return nil
+func (c *commitsByOidSender) Append(it chunker.Item) {
+ c.response.Commits = append(c.response.Commits, it.(*gitalypb.GitCommit))
}
+
+func (c *commitsByOidSender) Send() error { return c.stream.Send(c.response) }
+func (c *commitsByOidSender) Reset() { c.response = &gitalypb.ListCommitsByOidResponse{} }
diff --git a/internal/service/commit/list_commits_by_oid_test.go b/internal/service/commit/list_commits_by_oid_test.go
index 2c994c9e2..af2edd962 100644
--- a/internal/service/commit/list_commits_by_oid_test.go
+++ b/internal/service/commit/list_commits_by_oid_test.go
@@ -1,13 +1,13 @@
package commit
import (
+ "context"
"io"
"testing"
"github.com/stretchr/testify/require"
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/testhelper"
- "golang.org/x/net/context"
)
func TestSuccessfulListCommitsByOidRequest(t *testing.T) {
diff --git a/internal/service/commit/list_files.go b/internal/service/commit/list_files.go
index 54db537ce..f5a100e8c 100644
--- a/internal/service/commit/list_files.go
+++ b/internal/service/commit/list_files.go
@@ -1,16 +1,17 @@
package commit
import (
- "bytes"
+ "fmt"
+ "io"
grpc_logrus "github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus"
log "github.com/sirupsen/logrus"
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/git"
+ "gitlab.com/gitlab-org/gitaly/internal/git/lstree"
"gitlab.com/gitlab-org/gitaly/internal/helper"
- "gitlab.com/gitlab-org/gitaly/internal/helper/lines"
+ "gitlab.com/gitlab-org/gitaly/internal/helper/chunker"
"google.golang.org/grpc/codes"
- "google.golang.org/grpc/status"
)
func (s *server) ListFiles(in *gitalypb.ListFilesRequest, stream gitalypb.CommitService_ListFilesServer) error {
@@ -23,51 +24,64 @@ func (s *server) ListFiles(in *gitalypb.ListFilesRequest, stream gitalypb.Commit
return err
}
- revision := in.GetRevision()
+ revision := string(in.GetRevision())
if len(revision) == 0 {
- var err error
-
- revision, err = defaultBranchName(stream.Context(), repo)
+ defaultBranch, err := defaultBranchName(stream.Context(), repo)
if err != nil {
- if _, ok := status.FromError(err); ok {
- return err
- }
- return status.Errorf(codes.NotFound, "Revision not found %q", in.GetRevision())
+ return helper.DecorateError(codes.NotFound, fmt.Errorf("revision not found %q", revision))
}
+
+ revision = string(defaultBranch)
}
- if !git.IsValidRef(stream.Context(), repo, string(revision)) {
+
+ if !git.IsValidRef(stream.Context(), repo, revision) {
return stream.Send(&gitalypb.ListFilesResponse{})
}
- cmd, err := git.Command(stream.Context(), repo, "ls-tree", "-z", "-r", "--full-tree", "--full-name", "--", string(revision))
+ if err := listFiles(repo, revision, stream); err != nil {
+ return helper.ErrInternal(err)
+ }
+
+ return nil
+}
+
+func listFiles(repo *gitalypb.Repository, revision string, stream gitalypb.CommitService_ListFilesServer) error {
+ args := []string{"ls-tree", "-z", "-r", "--full-tree", "--full-name", "--", revision}
+ cmd, err := git.Command(stream.Context(), repo, args...)
if err != nil {
- if _, ok := status.FromError(err); ok {
+ return err
+ }
+
+ sender := chunker.New(&listFilesSender{stream: stream})
+
+ for parser := lstree.NewParser(cmd); ; {
+ entry, err := parser.NextEntry()
+ if err == io.EOF {
+ break
+ }
+ if err != nil {
return err
}
- return status.Errorf(codes.Internal, err.Error())
- }
- return lines.Send(cmd, listFilesWriter(stream), []byte{'\x00'})
-}
+ if entry.Type != lstree.Blob {
+ continue
+ }
-func listFilesWriter(stream gitalypb.CommitService_ListFilesServer) lines.Sender {
- return func(objs [][]byte) error {
- paths := make([][]byte, 0)
- for _, obj := range objs {
- data := bytes.SplitN(obj, []byte{'\t'}, 2)
- if len(data) != 2 {
- return status.Errorf(codes.Internal, "ListFiles: failed parsing line")
- }
-
- meta := bytes.SplitN(data[0], []byte{' '}, 3)
- if len(meta) != 3 {
- return status.Errorf(codes.Internal, "ListFiles: failed parsing meta")
- }
-
- if bytes.Equal(meta[1], []byte("blob")) {
- paths = append(paths, data[1])
- }
+ if err := sender.Send([]byte(entry.Path)); err != nil {
+ return err
}
- return stream.Send(&gitalypb.ListFilesResponse{Paths: paths})
}
+
+ return sender.Flush()
+}
+
+type listFilesSender struct {
+ stream gitalypb.CommitService_ListFilesServer
+ response *gitalypb.ListFilesResponse
+}
+
+func (s *listFilesSender) Reset() { s.response = &gitalypb.ListFilesResponse{} }
+func (s *listFilesSender) Send() error { return s.stream.Send(s.response) }
+func (s *listFilesSender) Append(it chunker.Item) {
+ s.response.Paths = append(s.response.Paths, it.([]byte))
}
diff --git a/internal/service/commit/list_files_test.go b/internal/service/commit/list_files_test.go
index d1eb82112..c2a702368 100644
--- a/internal/service/commit/list_files_test.go
+++ b/internal/service/commit/list_files_test.go
@@ -2,6 +2,7 @@ package commit
import (
"bytes"
+ "context"
"fmt"
"io"
"testing"
@@ -9,7 +10,6 @@ import (
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/service/ref"
"gitlab.com/gitlab-org/gitaly/internal/testhelper"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
)
diff --git a/internal/service/commit/list_last_commits_for_tree_test.go b/internal/service/commit/list_last_commits_for_tree_test.go
index ed7e30dd5..d3d2cd3e0 100644
--- a/internal/service/commit/list_last_commits_for_tree_test.go
+++ b/internal/service/commit/list_last_commits_for_tree_test.go
@@ -1,13 +1,13 @@
package commit
import (
+ "context"
"io"
"testing"
"github.com/stretchr/testify/require"
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/testhelper"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
)
diff --git a/internal/service/commit/raw_blame_test.go b/internal/service/commit/raw_blame_test.go
index 034176c83..932b34e1c 100644
--- a/internal/service/commit/raw_blame_test.go
+++ b/internal/service/commit/raw_blame_test.go
@@ -1,6 +1,7 @@
package commit
import (
+ "context"
"fmt"
"io/ioutil"
"testing"
@@ -9,7 +10,6 @@ import (
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/testhelper"
"gitlab.com/gitlab-org/gitaly/streamio"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
)
diff --git a/internal/service/commit/stats.go b/internal/service/commit/stats.go
index 30605c808..b1b9628f1 100644
--- a/internal/service/commit/stats.go
+++ b/internal/service/commit/stats.go
@@ -1,10 +1,11 @@
package commit
import (
+ "context"
+
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/helper"
"gitlab.com/gitlab-org/gitaly/internal/rubyserver"
- "golang.org/x/net/context"
)
func (s *server) CommitStats(ctx context.Context, in *gitalypb.CommitStatsRequest) (*gitalypb.CommitStatsResponse, error) {
diff --git a/internal/service/commit/tree_entries.go b/internal/service/commit/tree_entries.go
index 1d3b09129..f1456a71f 100644
--- a/internal/service/commit/tree_entries.go
+++ b/internal/service/commit/tree_entries.go
@@ -7,6 +7,7 @@ import (
log "github.com/sirupsen/logrus"
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/git/catfile"
+ "gitlab.com/gitlab-org/gitaly/internal/helper/chunker"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
)
@@ -62,23 +63,26 @@ func sendTreeEntries(stream gitalypb.CommitService_GetTreeEntriesServer, c *catf
}
}
- for len(entries) > maxTreeEntries {
- chunk := &gitalypb.GetTreeEntriesResponse{
- Entries: entries[:maxTreeEntries],
- }
- if err := stream.Send(chunk); err != nil {
- return err
- }
- entries = entries[maxTreeEntries:]
+ sender := chunker.New(&treeEntriesSender{stream: stream})
+ for _, e := range entries {
+ sender.Send(e)
}
- if len(entries) > 0 {
- return stream.Send(&gitalypb.GetTreeEntriesResponse{Entries: entries})
- }
+ return sender.Flush()
+}
- return nil
+type treeEntriesSender struct {
+ response *gitalypb.GetTreeEntriesResponse
+ stream gitalypb.CommitService_GetTreeEntriesServer
+}
+
+func (c *treeEntriesSender) Append(it chunker.Item) {
+ c.response.Entries = append(c.response.Entries, it.(*gitalypb.TreeEntry))
}
+func (c *treeEntriesSender) Send() error { return c.stream.Send(c.response) }
+func (c *treeEntriesSender) Reset() { c.response = &gitalypb.GetTreeEntriesResponse{} }
+
func (s *server) GetTreeEntries(in *gitalypb.GetTreeEntriesRequest, stream gitalypb.CommitService_GetTreeEntriesServer) error {
grpc_logrus.Extract(stream.Context()).WithFields(log.Fields{
"Revision": in.Revision,
diff --git a/internal/service/commit/tree_entries_test.go b/internal/service/commit/tree_entries_test.go
index f496e49d2..5eb422499 100644
--- a/internal/service/commit/tree_entries_test.go
+++ b/internal/service/commit/tree_entries_test.go
@@ -1,6 +1,7 @@
package commit
import (
+ "context"
"fmt"
"io"
"os"
@@ -10,7 +11,6 @@ import (
"github.com/stretchr/testify/require"
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/testhelper"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
)
diff --git a/internal/service/commit/tree_entry_test.go b/internal/service/commit/tree_entry_test.go
index 5d9a34f13..d7a75d592 100644
--- a/internal/service/commit/tree_entry_test.go
+++ b/internal/service/commit/tree_entry_test.go
@@ -2,13 +2,13 @@ package commit
import (
"bytes"
+ "context"
"fmt"
"io"
"testing"
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/testhelper"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
)
diff --git a/internal/service/diff/commit_test.go b/internal/service/diff/commit_test.go
index 6c0feb938..b1f1ca56c 100644
--- a/internal/service/diff/commit_test.go
+++ b/internal/service/diff/commit_test.go
@@ -2,6 +2,7 @@ package diff
import (
"bytes"
+ "context"
"fmt"
"io"
"testing"
@@ -10,7 +11,6 @@ import (
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/diff"
"gitlab.com/gitlab-org/gitaly/internal/testhelper"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
)
diff --git a/internal/service/diff/numstat_test.go b/internal/service/diff/numstat_test.go
index cb38d17e8..ddebbf7c1 100644
--- a/internal/service/diff/numstat_test.go
+++ b/internal/service/diff/numstat_test.go
@@ -1,6 +1,7 @@
package diff
import (
+ "context"
"io"
"testing"
@@ -8,7 +9,6 @@ import (
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/diff"
"gitlab.com/gitlab-org/gitaly/internal/testhelper"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
)
diff --git a/internal/service/diff/raw.go b/internal/service/diff/raw.go
index 73fde92e5..bbafc36ee 100644
--- a/internal/service/diff/raw.go
+++ b/internal/service/diff/raw.go
@@ -1,12 +1,12 @@
package diff
import (
+ "context"
"io"
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/git"
"gitlab.com/gitlab-org/gitaly/streamio"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
)
diff --git a/internal/service/namespace/namespace.go b/internal/service/namespace/namespace.go
index ef8abffe0..afd4caf87 100644
--- a/internal/service/namespace/namespace.go
+++ b/internal/service/namespace/namespace.go
@@ -1,12 +1,12 @@
package namespace
import (
+ "context"
"os"
"path"
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/helper"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
)
diff --git a/internal/service/namespace/namespace_test.go b/internal/service/namespace/namespace_test.go
index f5ac3471f..a01fe0b0a 100644
--- a/internal/service/namespace/namespace_test.go
+++ b/internal/service/namespace/namespace_test.go
@@ -1,6 +1,7 @@
package namespace
import (
+ "context"
"io/ioutil"
"os"
"testing"
@@ -10,7 +11,6 @@ import (
"gitlab.com/gitlab-org/gitaly/internal/config"
"gitlab.com/gitlab-org/gitaly/internal/helper"
"gitlab.com/gitlab-org/gitaly/internal/testhelper"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
)
diff --git a/internal/service/operations/branches.go b/internal/service/operations/branches.go
index 9a8840ded..943da6ee4 100644
--- a/internal/service/operations/branches.go
+++ b/internal/service/operations/branches.go
@@ -1,9 +1,10 @@
package operations
import (
+ "context"
+
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/rubyserver"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
)
diff --git a/internal/service/operations/branches_test.go b/internal/service/operations/branches_test.go
index 9c41aac21..7b6597afd 100644
--- a/internal/service/operations/branches_test.go
+++ b/internal/service/operations/branches_test.go
@@ -1,6 +1,7 @@
package operations
import (
+ "context"
"os"
"os/exec"
"testing"
@@ -9,7 +10,6 @@ import (
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/git/log"
"gitlab.com/gitlab-org/gitaly/internal/testhelper"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
)
diff --git a/internal/service/operations/cherry_pick.go b/internal/service/operations/cherry_pick.go
index eaea55558..ef0e9cb00 100644
--- a/internal/service/operations/cherry_pick.go
+++ b/internal/service/operations/cherry_pick.go
@@ -1,9 +1,10 @@
package operations
import (
+ "context"
+
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/rubyserver"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
)
diff --git a/internal/service/operations/merge.go b/internal/service/operations/merge.go
index 2e9470f5a..9fa3888b3 100644
--- a/internal/service/operations/merge.go
+++ b/internal/service/operations/merge.go
@@ -1,11 +1,11 @@
package operations
import (
+ "context"
"fmt"
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/rubyserver"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
)
diff --git a/internal/service/operations/rebase.go b/internal/service/operations/rebase.go
index 1fa5ea341..abd012396 100644
--- a/internal/service/operations/rebase.go
+++ b/internal/service/operations/rebase.go
@@ -1,11 +1,11 @@
package operations
import (
+ "context"
"fmt"
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/rubyserver"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
)
diff --git a/internal/service/operations/revert.go b/internal/service/operations/revert.go
index 2c501c449..8a9a78524 100644
--- a/internal/service/operations/revert.go
+++ b/internal/service/operations/revert.go
@@ -1,9 +1,10 @@
package operations
import (
+ "context"
+
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/rubyserver"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
)
diff --git a/internal/service/operations/squash.go b/internal/service/operations/squash.go
index 8e007f693..83207907a 100644
--- a/internal/service/operations/squash.go
+++ b/internal/service/operations/squash.go
@@ -1,11 +1,11 @@
package operations
import (
+ "context"
"fmt"
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/rubyserver"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
)
diff --git a/internal/service/operations/submodules.go b/internal/service/operations/submodules.go
index 3d37efec8..7bffd8d47 100644
--- a/internal/service/operations/submodules.go
+++ b/internal/service/operations/submodules.go
@@ -1,12 +1,12 @@
package operations
import (
+ "context"
"fmt"
"regexp"
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/rubyserver"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
)
diff --git a/internal/service/operations/tags.go b/internal/service/operations/tags.go
index 09827d81a..585addeac 100644
--- a/internal/service/operations/tags.go
+++ b/internal/service/operations/tags.go
@@ -1,9 +1,10 @@
package operations
import (
+ "context"
+
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/rubyserver"
- "golang.org/x/net/context"
)
func (s *server) UserDeleteTag(ctx context.Context, req *gitalypb.UserDeleteTagRequest) (*gitalypb.UserDeleteTagResponse, error) {
diff --git a/internal/service/operations/update_branches_test.go b/internal/service/operations/update_branches_test.go
index 56be3faf2..8dd910dc9 100644
--- a/internal/service/operations/update_branches_test.go
+++ b/internal/service/operations/update_branches_test.go
@@ -1,6 +1,7 @@
package operations
import (
+ "context"
"os"
"testing"
@@ -8,7 +9,6 @@ import (
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/git/log"
"gitlab.com/gitlab-org/gitaly/internal/testhelper"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
)
diff --git a/internal/service/ref/branches.go b/internal/service/ref/branches.go
index 09aa25189..603d6d6fd 100644
--- a/internal/service/ref/branches.go
+++ b/internal/service/ref/branches.go
@@ -2,6 +2,7 @@ package ref
import (
"bufio"
+ "context"
"io"
"strings"
@@ -9,7 +10,6 @@ import (
"gitlab.com/gitlab-org/gitaly/internal/git"
"gitlab.com/gitlab-org/gitaly/internal/git/log"
"gitlab.com/gitlab-org/gitaly/internal/rubyserver"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
)
diff --git a/internal/service/ref/delete_refs.go b/internal/service/ref/delete_refs.go
index 27d9f9211..34fc0c2aa 100644
--- a/internal/service/ref/delete_refs.go
+++ b/internal/service/ref/delete_refs.go
@@ -1,11 +1,11 @@
package ref
import (
+ "context"
"fmt"
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/rubyserver"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
)
diff --git a/internal/service/ref/refexists.go b/internal/service/ref/refexists.go
index e94ce97fa..31f7ae05f 100644
--- a/internal/service/ref/refexists.go
+++ b/internal/service/ref/refexists.go
@@ -1,6 +1,7 @@
package ref
import (
+ "context"
"fmt"
"strings"
@@ -8,7 +9,6 @@ import (
"gitlab.com/gitlab-org/gitaly/internal/command"
"gitlab.com/gitlab-org/gitaly/internal/git"
"gitlab.com/gitlab-org/gitaly/internal/helper"
- "golang.org/x/net/context"
)
// RefExists returns true if the given reference exists. The ref must start with the string `ref/`
diff --git a/internal/service/ref/refname.go b/internal/service/ref/refname.go
index ad6c488df..ac4e3ca2d 100644
--- a/internal/service/ref/refname.go
+++ b/internal/service/ref/refname.go
@@ -2,13 +2,13 @@ package ref
import (
"bufio"
+ "context"
"fmt"
"strings"
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/git"
"gitlab.com/gitlab-org/gitaly/internal/helper"
- "golang.org/x/net/context"
)
// FindRefName returns a ref that starts with the given prefix, if one exists.
diff --git a/internal/service/ref/refname_test.go b/internal/service/ref/refname_test.go
index 497135a25..e9501de03 100644
--- a/internal/service/ref/refname_test.go
+++ b/internal/service/ref/refname_test.go
@@ -1,12 +1,12 @@
package ref
import (
+ "context"
"testing"
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/helper"
"gitlab.com/gitlab-org/gitaly/internal/testhelper"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
)
diff --git a/internal/service/ref/refs.go b/internal/service/ref/refs.go
index dadf91457..08334be86 100644
--- a/internal/service/ref/refs.go
+++ b/internal/service/ref/refs.go
@@ -3,6 +3,7 @@ package ref
import (
"bufio"
"bytes"
+ "context"
"fmt"
"strings"
@@ -12,7 +13,6 @@ import (
"gitlab.com/gitlab-org/gitaly/internal/helper"
"gitlab.com/gitlab-org/gitaly/internal/helper/lines"
"gitlab.com/gitlab-org/gitaly/internal/rubyserver"
- "golang.org/x/net/context"
)
var (
diff --git a/internal/service/ref/refs_test.go b/internal/service/ref/refs_test.go
index f675c2c9a..4648b56d0 100644
--- a/internal/service/ref/refs_test.go
+++ b/internal/service/ref/refs_test.go
@@ -2,6 +2,7 @@ package ref
import (
"bytes"
+ "context"
"io"
"io/ioutil"
"strings"
@@ -13,7 +14,6 @@ import (
"gitlab.com/gitlab-org/gitaly/internal/git/log"
"gitlab.com/gitlab-org/gitaly/internal/helper"
"gitlab.com/gitlab-org/gitaly/internal/testhelper"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
)
diff --git a/internal/service/ref/remote_branches_test.go b/internal/service/ref/remote_branches_test.go
index efb411342..1d1be32ad 100644
--- a/internal/service/ref/remote_branches_test.go
+++ b/internal/service/ref/remote_branches_test.go
@@ -1,6 +1,7 @@
package ref
import (
+ "context"
"io"
"testing"
@@ -8,7 +9,6 @@ import (
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/git/log"
"gitlab.com/gitlab-org/gitaly/internal/testhelper"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
)
diff --git a/internal/service/remote/fetch_internal_remote.go b/internal/service/remote/fetch_internal_remote.go
index 15961aa29..8ca4d6ab0 100644
--- a/internal/service/remote/fetch_internal_remote.go
+++ b/internal/service/remote/fetch_internal_remote.go
@@ -1,11 +1,11 @@
package remote
import (
+ "context"
"fmt"
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/rubyserver"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
)
diff --git a/internal/service/remote/find_remote_root_ref.go b/internal/service/remote/find_remote_root_ref.go
index 56602be8d..fb6bcec4d 100644
--- a/internal/service/remote/find_remote_root_ref.go
+++ b/internal/service/remote/find_remote_root_ref.go
@@ -2,11 +2,11 @@ package remote
import (
"bufio"
+ "context"
"strings"
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/git"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
)
diff --git a/internal/service/remote/remotes.go b/internal/service/remote/remotes.go
index 45fda5caa..c075750d6 100644
--- a/internal/service/remote/remotes.go
+++ b/internal/service/remote/remotes.go
@@ -2,6 +2,7 @@ package remote
import (
"bytes"
+ "context"
"fmt"
"io/ioutil"
"strings"
@@ -9,7 +10,6 @@ import (
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/git"
"gitlab.com/gitlab-org/gitaly/internal/rubyserver"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
)
diff --git a/internal/service/remote/remotes_test.go b/internal/service/remote/remotes_test.go
index b38f9398e..b90d8c8b4 100644
--- a/internal/service/remote/remotes_test.go
+++ b/internal/service/remote/remotes_test.go
@@ -2,6 +2,7 @@ package remote
import (
"bytes"
+ "context"
"fmt"
"io"
"net/http"
@@ -11,7 +12,6 @@ import (
"github.com/stretchr/testify/require"
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/testhelper"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
)
diff --git a/internal/service/remote/update_remote_mirror_test.go b/internal/service/remote/update_remote_mirror_test.go
index dfa173829..75ee77f4a 100644
--- a/internal/service/remote/update_remote_mirror_test.go
+++ b/internal/service/remote/update_remote_mirror_test.go
@@ -1,13 +1,13 @@
package remote
import (
+ "context"
"strings"
"testing"
"github.com/stretchr/testify/require"
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/testhelper"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
)
diff --git a/internal/service/repository/apply_gitattributes.go b/internal/service/repository/apply_gitattributes.go
index e7103f03b..9868f4b83 100644
--- a/internal/service/repository/apply_gitattributes.go
+++ b/internal/service/repository/apply_gitattributes.go
@@ -1,6 +1,7 @@
package repository
import (
+ "context"
"fmt"
"io"
"io/ioutil"
@@ -11,7 +12,6 @@ import (
"gitlab.com/gitlab-org/gitaly/internal/git"
"gitlab.com/gitlab-org/gitaly/internal/git/catfile"
"gitlab.com/gitlab-org/gitaly/internal/helper"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
)
diff --git a/internal/service/repository/calculate_checksum.go b/internal/service/repository/calculate_checksum.go
index d58a6627d..b0804d036 100644
--- a/internal/service/repository/calculate_checksum.go
+++ b/internal/service/repository/calculate_checksum.go
@@ -3,6 +3,7 @@ package repository
import (
"bufio"
"bytes"
+ "context"
"crypto/sha1"
"encoding/hex"
"math/big"
@@ -13,7 +14,6 @@ import (
"gitlab.com/gitlab-org/gitaly/internal/git"
"gitlab.com/gitlab-org/gitaly/internal/git/alternates"
"gitlab.com/gitlab-org/gitaly/internal/helper"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
)
diff --git a/internal/service/repository/cleanup.go b/internal/service/repository/cleanup.go
index 99fd9d343..9cae1580b 100644
--- a/internal/service/repository/cleanup.go
+++ b/internal/service/repository/cleanup.go
@@ -1,6 +1,7 @@
package repository
import (
+ "context"
"io/ioutil"
"os"
"path/filepath"
@@ -9,7 +10,6 @@ import (
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/helper"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
)
diff --git a/internal/service/repository/config.go b/internal/service/repository/config.go
index 30314f432..d189ce9b6 100644
--- a/internal/service/repository/config.go
+++ b/internal/service/repository/config.go
@@ -1,11 +1,12 @@
package repository
import (
+ "context"
+
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/command"
"gitlab.com/gitlab-org/gitaly/internal/git"
"gitlab.com/gitlab-org/gitaly/internal/rubyserver"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
)
diff --git a/internal/service/repository/create.go b/internal/service/repository/create.go
index 58928b166..397b00238 100644
--- a/internal/service/repository/create.go
+++ b/internal/service/repository/create.go
@@ -1,9 +1,10 @@
package repository
import (
+ "context"
+
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/rubyserver"
- "golang.org/x/net/context"
)
func (s *server) CreateRepository(ctx context.Context, req *gitalypb.CreateRepositoryRequest) (*gitalypb.CreateRepositoryResponse, error) {
diff --git a/internal/service/repository/create_from_snapshot.go b/internal/service/repository/create_from_snapshot.go
index de8db898b..f307a8d3f 100644
--- a/internal/service/repository/create_from_snapshot.go
+++ b/internal/service/repository/create_from_snapshot.go
@@ -1,6 +1,7 @@
package repository
import (
+ "context"
"net"
"net/http"
"os"
@@ -12,7 +13,7 @@ import (
"gitlab.com/gitlab-org/gitaly/internal/helper"
"gitlab.com/gitlab-org/gitaly/internal/tempdir"
"gitlab.com/gitlab-org/labkit/correlation"
- "golang.org/x/net/context"
+ "gitlab.com/gitlab-org/labkit/tracing"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
)
@@ -39,7 +40,7 @@ var httpTransport = &http.Transport{
// (above). It also disables following redirects, as we don't expect this to be
// required for this RPC.
var httpClient = &http.Client{
- Transport: correlation.NewInstrumentedRoundTripper(httpTransport),
+ Transport: correlation.NewInstrumentedRoundTripper(tracing.NewRoundTripper(httpTransport)),
CheckRedirect: func(*http.Request, []*http.Request) error {
return http.ErrUseLastResponse
},
diff --git a/internal/service/repository/create_from_url.go b/internal/service/repository/create_from_url.go
index 7274bf7f0..c17b9ec3a 100644
--- a/internal/service/repository/create_from_url.go
+++ b/internal/service/repository/create_from_url.go
@@ -1,13 +1,13 @@
package repository
import (
+ "context"
"fmt"
"os"
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/git"
"gitlab.com/gitlab-org/gitaly/internal/helper"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
)
diff --git a/internal/service/repository/fetch.go b/internal/service/repository/fetch.go
index f09488893..58102c56f 100644
--- a/internal/service/repository/fetch.go
+++ b/internal/service/repository/fetch.go
@@ -1,9 +1,10 @@
package repository
import (
+ "context"
+
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/rubyserver"
- "golang.org/x/net/context"
)
func (s *server) FetchSourceBranch(ctx context.Context, req *gitalypb.FetchSourceBranchRequest) (*gitalypb.FetchSourceBranchResponse, error) {
diff --git a/internal/service/repository/fetch_remote.go b/internal/service/repository/fetch_remote.go
index 6f3c35f3d..b29db8b56 100644
--- a/internal/service/repository/fetch_remote.go
+++ b/internal/service/repository/fetch_remote.go
@@ -1,11 +1,12 @@
package repository
import (
+ "context"
+
grpc_logrus "github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus"
log "github.com/sirupsen/logrus"
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/rubyserver"
- "golang.org/x/net/context"
)
func (s *server) FetchRemote(ctx context.Context, in *gitalypb.FetchRemoteRequest) (*gitalypb.FetchRemoteResponse, error) {
diff --git a/internal/service/repository/fork.go b/internal/service/repository/fork.go
index 3cfef7738..fedef0227 100644
--- a/internal/service/repository/fork.go
+++ b/internal/service/repository/fork.go
@@ -1,6 +1,7 @@
package repository
import (
+ "context"
"fmt"
"os"
"path"
@@ -10,7 +11,6 @@ import (
"gitlab.com/gitlab-org/gitaly/internal/config"
"gitlab.com/gitlab-org/gitaly/internal/git"
"gitlab.com/gitlab-org/gitaly/internal/helper"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
)
diff --git a/internal/service/repository/fsck.go b/internal/service/repository/fsck.go
index 2e4f4195e..b92ca8cf5 100644
--- a/internal/service/repository/fsck.go
+++ b/internal/service/repository/fsck.go
@@ -2,11 +2,11 @@ package repository
import (
"bytes"
+ "context"
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/git"
"gitlab.com/gitlab-org/gitaly/internal/git/alternates"
- "golang.org/x/net/context"
)
func (s *server) Fsck(ctx context.Context, req *gitalypb.FsckRequest) (*gitalypb.FsckResponse, error) {
diff --git a/internal/service/repository/gc.go b/internal/service/repository/gc.go
index cd06bce0e..128e343c7 100644
--- a/internal/service/repository/gc.go
+++ b/internal/service/repository/gc.go
@@ -1,6 +1,7 @@
package repository
import (
+ "context"
"errors"
"fmt"
"io/ioutil"
@@ -14,7 +15,6 @@ import (
"gitlab.com/gitlab-org/gitaly/internal/git/catfile"
"gitlab.com/gitlab-org/gitaly/internal/helper"
"gitlab.com/gitlab-org/gitaly/internal/helper/housekeeping"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
)
diff --git a/internal/service/repository/license.go b/internal/service/repository/license.go
index 584cdba6b..fcc0e4916 100644
--- a/internal/service/repository/license.go
+++ b/internal/service/repository/license.go
@@ -1,9 +1,10 @@
package repository
import (
+ "context"
+
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/rubyserver"
- "golang.org/x/net/context"
)
func (s *server) FindLicense(ctx context.Context, in *gitalypb.FindLicenseRequest) (*gitalypb.FindLicenseResponse, error) {
diff --git a/internal/service/repository/merge_base.go b/internal/service/repository/merge_base.go
index 192a00c7c..68850ce70 100644
--- a/internal/service/repository/merge_base.go
+++ b/internal/service/repository/merge_base.go
@@ -1,12 +1,12 @@
package repository
import (
+ "context"
"io/ioutil"
"strings"
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/git"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
)
diff --git a/internal/service/repository/rebase_in_progress.go b/internal/service/repository/rebase_in_progress.go
index 2fff4d7f6..3cb5d8242 100644
--- a/internal/service/repository/rebase_in_progress.go
+++ b/internal/service/repository/rebase_in_progress.go
@@ -1,6 +1,7 @@
package repository
import (
+ "context"
"fmt"
"os"
"path"
@@ -10,7 +11,6 @@ import (
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/helper"
"gitlab.com/gitlab-org/gitaly/internal/helper/housekeeping"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
)
diff --git a/internal/service/repository/repack.go b/internal/service/repository/repack.go
index 075577fc6..e7a08f433 100644
--- a/internal/service/repository/repack.go
+++ b/internal/service/repository/repack.go
@@ -1,11 +1,12 @@
package repository
import (
+ "context"
+
grpc_logrus "github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus"
log "github.com/sirupsen/logrus"
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/git"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
)
diff --git a/internal/service/repository/repository.go b/internal/service/repository/repository.go
index 2fb780f5d..a5e5ec468 100644
--- a/internal/service/repository/repository.go
+++ b/internal/service/repository/repository.go
@@ -1,12 +1,12 @@
package repository
import (
+ "context"
"io/ioutil"
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/git"
"gitlab.com/gitlab-org/gitaly/internal/helper"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
)
diff --git a/internal/service/repository/repository_test.go b/internal/service/repository/repository_test.go
index 7d4998299..840cf24e6 100644
--- a/internal/service/repository/repository_test.go
+++ b/internal/service/repository/repository_test.go
@@ -1,6 +1,7 @@
package repository
import (
+ "context"
"io/ioutil"
"os"
"path"
@@ -11,7 +12,6 @@ import (
"gitlab.com/gitlab-org/gitaly/internal/config"
"gitlab.com/gitlab-org/gitaly/internal/helper"
"gitlab.com/gitlab-org/gitaly/internal/testhelper"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
)
diff --git a/internal/service/repository/size.go b/internal/service/repository/size.go
index 7cf3a3e18..937308cdc 100644
--- a/internal/service/repository/size.go
+++ b/internal/service/repository/size.go
@@ -2,6 +2,7 @@ package repository
import (
"bytes"
+ "context"
"fmt"
"io/ioutil"
"os/exec"
@@ -11,7 +12,6 @@ import (
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/command"
"gitlab.com/gitlab-org/gitaly/internal/helper"
- "golang.org/x/net/context"
)
func (s *server) RepositorySize(ctx context.Context, in *gitalypb.RepositorySizeRequest) (*gitalypb.RepositorySizeResponse, error) {
diff --git a/internal/service/repository/size_test.go b/internal/service/repository/size_test.go
index 6dc9a37b3..15fce8d2e 100644
--- a/internal/service/repository/size_test.go
+++ b/internal/service/repository/size_test.go
@@ -1,6 +1,7 @@
package repository
import (
+ "context"
"os"
"path"
"testing"
@@ -9,7 +10,6 @@ import (
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/config"
"gitlab.com/gitlab-org/gitaly/internal/testhelper"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
)
diff --git a/internal/service/repository/squash_in_progress.go b/internal/service/repository/squash_in_progress.go
index 81b6441fd..87ebaaeb6 100644
--- a/internal/service/repository/squash_in_progress.go
+++ b/internal/service/repository/squash_in_progress.go
@@ -1,12 +1,12 @@
package repository
import (
+ "context"
"fmt"
"strings"
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/helper"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
)
diff --git a/internal/service/repository/util.go b/internal/service/repository/util.go
index f859358fc..05772034a 100644
--- a/internal/service/repository/util.go
+++ b/internal/service/repository/util.go
@@ -1,11 +1,11 @@
package repository
import (
+ "context"
"fmt"
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/git"
- "golang.org/x/net/context"
)
func removeOriginInRepo(ctx context.Context, repository *gitalypb.Repository) error {
diff --git a/internal/service/repository/write_config.go b/internal/service/repository/write_config.go
index 0a6b3d279..e80ced88b 100644
--- a/internal/service/repository/write_config.go
+++ b/internal/service/repository/write_config.go
@@ -1,9 +1,10 @@
package repository
import (
+ "context"
+
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/rubyserver"
- "golang.org/x/net/context"
)
func (s *server) WriteConfig(ctx context.Context, req *gitalypb.WriteConfigRequest) (*gitalypb.WriteConfigResponse, error) {
diff --git a/internal/service/repository/write_ref.go b/internal/service/repository/write_ref.go
index 600646eb8..1d4fe269d 100644
--- a/internal/service/repository/write_ref.go
+++ b/internal/service/repository/write_ref.go
@@ -2,13 +2,13 @@ package repository
import (
"bytes"
+ "context"
"fmt"
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/git"
"gitlab.com/gitlab-org/gitaly/internal/git/updateref"
"gitlab.com/gitlab-org/gitaly/internal/helper"
- "golang.org/x/net/context"
)
func (s *server) WriteRef(ctx context.Context, req *gitalypb.WriteRefRequest) (*gitalypb.WriteRefResponse, error) {
diff --git a/internal/service/server/info.go b/internal/service/server/info.go
index 323014ab3..4c4762fbd 100644
--- a/internal/service/server/info.go
+++ b/internal/service/server/info.go
@@ -1,6 +1,7 @@
package server
import (
+ "context"
"io/ioutil"
"os"
"path"
@@ -9,7 +10,6 @@ import (
"gitlab.com/gitlab-org/gitaly/internal/config"
"gitlab.com/gitlab-org/gitaly/internal/git"
"gitlab.com/gitlab-org/gitaly/internal/version"
- "golang.org/x/net/context"
)
func (s *server) ServerInfo(ctx context.Context, in *gitalypb.ServerInfoRequest) (*gitalypb.ServerInfoResponse, error) {
diff --git a/internal/service/smarthttp/inforefs_test.go b/internal/service/smarthttp/inforefs_test.go
index e2ed888d4..939b56826 100644
--- a/internal/service/smarthttp/inforefs_test.go
+++ b/internal/service/smarthttp/inforefs_test.go
@@ -1,6 +1,7 @@
package smarthttp
import (
+ "context"
"fmt"
"io"
"io/ioutil"
@@ -13,7 +14,6 @@ import (
"gitlab.com/gitlab-org/gitaly/internal/git"
"gitlab.com/gitlab-org/gitaly/internal/testhelper"
"gitlab.com/gitlab-org/gitaly/streamio"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
)
diff --git a/internal/service/smarthttp/receive_pack_test.go b/internal/service/smarthttp/receive_pack_test.go
index 8e51b6aa0..0503b669b 100644
--- a/internal/service/smarthttp/receive_pack_test.go
+++ b/internal/service/smarthttp/receive_pack_test.go
@@ -2,6 +2,7 @@ package smarthttp
import (
"bytes"
+ "context"
"fmt"
"io"
"io/ioutil"
@@ -18,7 +19,6 @@ import (
"gitlab.com/gitlab-org/gitaly/internal/git/hooks"
"gitlab.com/gitlab-org/gitaly/internal/testhelper"
"gitlab.com/gitlab-org/gitaly/streamio"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
)
diff --git a/internal/service/smarthttp/upload_pack_test.go b/internal/service/smarthttp/upload_pack_test.go
index 3c44fcd45..b8bbb1a57 100644
--- a/internal/service/smarthttp/upload_pack_test.go
+++ b/internal/service/smarthttp/upload_pack_test.go
@@ -2,6 +2,7 @@ package smarthttp
import (
"bytes"
+ "context"
"encoding/binary"
"fmt"
"io"
@@ -20,7 +21,6 @@ import (
"gitlab.com/gitlab-org/gitaly/internal/helper"
"gitlab.com/gitlab-org/gitaly/internal/testhelper"
"gitlab.com/gitlab-org/gitaly/streamio"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
)
diff --git a/internal/service/ssh/receive_pack.go b/internal/service/ssh/receive_pack.go
index 51df1774a..e952e7777 100644
--- a/internal/service/ssh/receive_pack.go
+++ b/internal/service/ssh/receive_pack.go
@@ -12,18 +12,15 @@ import (
"gitlab.com/gitlab-org/gitaly/internal/git/hooks"
"gitlab.com/gitlab-org/gitaly/internal/helper"
"gitlab.com/gitlab-org/gitaly/streamio"
- "google.golang.org/grpc/codes"
- "google.golang.org/grpc/status"
)
func (s *server) SSHReceivePack(stream gitalypb.SSHService_SSHReceivePackServer) error {
- ctx := stream.Context()
req, err := stream.Recv() // First request contains only Repository, GlId, and GlUsername
if err != nil {
- return err
+ return helper.ErrInternal(err)
}
- grpc_logrus.Extract(ctx).WithFields(log.Fields{
+ grpc_logrus.Extract(stream.Context()).WithFields(log.Fields{
"GlID": req.GlId,
"GlRepository": req.GlRepository,
"GlUsername": req.GlUsername,
@@ -31,9 +28,19 @@ func (s *server) SSHReceivePack(stream gitalypb.SSHService_SSHReceivePackServer)
}).Debug("SSHReceivePack")
if err = validateFirstReceivePackRequest(req); err != nil {
- return err
+ return helper.ErrInvalidArgument(err)
}
+ if err := sshReceivePack(stream, req); err != nil {
+ return helper.ErrInternal(err)
+ }
+
+ return nil
+}
+
+func sshReceivePack(stream gitalypb.SSHService_SSHReceivePackServer, req *gitalypb.SSHReceivePackRequest) error {
+ ctx := stream.Context()
+
stdin := streamio.NewReader(func() ([]byte, error) {
request, err := stream.Recv()
return request.GetStdin(), err
@@ -67,17 +74,17 @@ func (s *server) SSHReceivePack(stream gitalypb.SSHService_SSHReceivePackServer)
cmd, err := git.BareCommand(ctx, stdin, stdout, stderr, env, gitOptions...)
if err != nil {
- return status.Errorf(codes.Unavailable, "SSHReceivePack: cmd: %v", err)
+ return fmt.Errorf("start cmd: %v", err)
}
if err := cmd.Wait(); err != nil {
if status, ok := command.ExitStatus(err); ok {
- return helper.DecorateError(
- codes.Internal,
- stream.Send(&gitalypb.SSHReceivePackResponse{ExitStatus: &gitalypb.ExitStatus{Value: int32(status)}}),
- )
+ return stream.Send(&gitalypb.SSHReceivePackResponse{
+ ExitStatus: &gitalypb.ExitStatus{Value: int32(status)},
+ })
}
- return status.Errorf(codes.Unavailable, "SSHReceivePack: %v", err)
+
+ return fmt.Errorf("cmd wait: %v", err)
}
return nil
@@ -85,10 +92,10 @@ func (s *server) SSHReceivePack(stream gitalypb.SSHService_SSHReceivePackServer)
func validateFirstReceivePackRequest(req *gitalypb.SSHReceivePackRequest) error {
if req.GlId == "" {
- return status.Errorf(codes.InvalidArgument, "SSHReceivePack: empty GlId")
+ return fmt.Errorf("empty GlId")
}
if req.Stdin != nil {
- return status.Errorf(codes.InvalidArgument, "SSHReceivePack: non-empty data")
+ return fmt.Errorf("non-empty data in first request")
}
return nil
diff --git a/internal/service/ssh/receive_pack_test.go b/internal/service/ssh/receive_pack_test.go
index a40a1ec1b..f4237646d 100644
--- a/internal/service/ssh/receive_pack_test.go
+++ b/internal/service/ssh/receive_pack_test.go
@@ -2,6 +2,7 @@ package ssh
import (
"bytes"
+ "context"
"fmt"
"io/ioutil"
"os"
@@ -18,7 +19,6 @@ import (
"gitlab.com/gitlab-org/gitaly/internal/git"
"gitlab.com/gitlab-org/gitaly/internal/git/hooks"
"gitlab.com/gitlab-org/gitaly/internal/testhelper"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
)
diff --git a/internal/service/ssh/upload_archive.go b/internal/service/ssh/upload_archive.go
index c29ebf07b..683ebe6bb 100644
--- a/internal/service/ssh/upload_archive.go
+++ b/internal/service/ssh/upload_archive.go
@@ -1,24 +1,32 @@
package ssh
import (
+ "fmt"
+
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/command"
"gitlab.com/gitlab-org/gitaly/internal/git"
"gitlab.com/gitlab-org/gitaly/internal/helper"
"gitlab.com/gitlab-org/gitaly/streamio"
- "google.golang.org/grpc/codes"
- "google.golang.org/grpc/status"
)
func (s *server) SSHUploadArchive(stream gitalypb.SSHService_SSHUploadArchiveServer) error {
req, err := stream.Recv() // First request contains Repository only
if err != nil {
- return err
+ return helper.ErrInternal(err)
}
if err = validateFirstUploadArchiveRequest(req); err != nil {
- return err
+ return helper.ErrInvalidArgument(err)
+ }
+
+ if err = sshUploadArchive(stream, req); err != nil {
+ return helper.ErrInternal(err)
}
+ return nil
+}
+
+func sshUploadArchive(stream gitalypb.SSHService_SSHUploadArchiveServer, req *gitalypb.SSHUploadArchiveRequest) error {
repoPath, err := helper.GetRepoPath(req.Repository)
if err != nil {
return err
@@ -37,28 +45,26 @@ func (s *server) SSHUploadArchive(stream gitalypb.SSHService_SSHUploadArchiveSer
cmd, err := git.BareCommand(stream.Context(), stdin, stdout, stderr, nil, "upload-archive", repoPath)
if err != nil {
- return status.Errorf(codes.Unavailable, "SSHUploadArchive: cmd: %v", err)
+ return fmt.Errorf("start cmd: %v", err)
}
if err := cmd.Wait(); err != nil {
if status, ok := command.ExitStatus(err); ok {
- return helper.DecorateError(
- codes.Internal,
- stream.Send(&gitalypb.SSHUploadArchiveResponse{ExitStatus: &gitalypb.ExitStatus{Value: int32(status)}}),
- )
+ return stream.Send(&gitalypb.SSHUploadArchiveResponse{
+ ExitStatus: &gitalypb.ExitStatus{Value: int32(status)},
+ })
}
- return status.Errorf(codes.Unavailable, "SSHUploadArchive: %v", err)
+ return fmt.Errorf("wait cmd: %v", err)
}
- return helper.DecorateError(
- codes.Internal,
- stream.Send(&gitalypb.SSHUploadArchiveResponse{ExitStatus: &gitalypb.ExitStatus{Value: 0}}),
- )
+ return stream.Send(&gitalypb.SSHUploadArchiveResponse{
+ ExitStatus: &gitalypb.ExitStatus{Value: 0},
+ })
}
func validateFirstUploadArchiveRequest(req *gitalypb.SSHUploadArchiveRequest) error {
if req.Stdin != nil {
- return status.Errorf(codes.InvalidArgument, "SSHUploadArchive: non-empty stdin")
+ return fmt.Errorf("non-empty stdin in first request")
}
return nil
diff --git a/internal/service/ssh/upload_archive_test.go b/internal/service/ssh/upload_archive_test.go
index 8264b6314..59b2a9d94 100644
--- a/internal/service/ssh/upload_archive_test.go
+++ b/internal/service/ssh/upload_archive_test.go
@@ -1,6 +1,7 @@
package ssh
import (
+ "context"
"fmt"
"os"
"os/exec"
@@ -10,7 +11,6 @@ import (
"github.com/stretchr/testify/require"
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/testhelper"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
)
diff --git a/internal/service/ssh/upload_pack.go b/internal/service/ssh/upload_pack.go
index add35b0b3..324cd4275 100644
--- a/internal/service/ssh/upload_pack.go
+++ b/internal/service/ssh/upload_pack.go
@@ -1,27 +1,35 @@
package ssh
import (
+ "fmt"
+
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/command"
"gitlab.com/gitlab-org/gitaly/internal/git"
"gitlab.com/gitlab-org/gitaly/internal/helper"
"gitlab.com/gitlab-org/gitaly/streamio"
- "google.golang.org/grpc/codes"
- "google.golang.org/grpc/status"
)
func (s *server) SSHUploadPack(stream gitalypb.SSHService_SSHUploadPackServer) error {
- ctx := stream.Context()
-
req, err := stream.Recv() // First request contains Repository only
if err != nil {
- return err
+ return helper.ErrInternal(err)
}
if err = validateFirstUploadPackRequest(req); err != nil {
- return err
+ return helper.ErrInvalidArgument(err)
+ }
+
+ if err = sshUploadPack(stream, req); err != nil {
+ return helper.ErrInternal(err)
}
+ return nil
+}
+
+func sshUploadPack(stream gitalypb.SSHService_SSHUploadPackServer, req *gitalypb.SSHUploadPackRequest) error {
+ ctx := stream.Context()
+
stdin := streamio.NewReader(func() ([]byte, error) {
request, err := stream.Recv()
return request.GetStdin(), err
@@ -51,17 +59,16 @@ func (s *server) SSHUploadPack(stream gitalypb.SSHService_SSHUploadPackServer) e
cmd, err := git.BareCommand(ctx, stdin, stdout, stderr, env, args...)
if err != nil {
- return status.Errorf(codes.Unavailable, "SSHUploadPack: cmd: %v", err)
+ return fmt.Errorf("start cmd: %v", err)
}
if err := cmd.Wait(); err != nil {
if status, ok := command.ExitStatus(err); ok {
- return helper.DecorateError(
- codes.Internal,
- stream.Send(&gitalypb.SSHUploadPackResponse{ExitStatus: &gitalypb.ExitStatus{Value: int32(status)}}),
- )
+ return stream.Send(&gitalypb.SSHUploadPackResponse{
+ ExitStatus: &gitalypb.ExitStatus{Value: int32(status)},
+ })
}
- return status.Errorf(codes.Unavailable, "SSHUploadPack: %v", err)
+ return fmt.Errorf("cmd wait: %v", err)
}
return nil
@@ -69,7 +76,7 @@ func (s *server) SSHUploadPack(stream gitalypb.SSHService_SSHUploadPackServer) e
func validateFirstUploadPackRequest(req *gitalypb.SSHUploadPackRequest) error {
if req.Stdin != nil {
- return status.Errorf(codes.InvalidArgument, "SSHUploadPack: non-empty stdin")
+ return fmt.Errorf("non-empty stdin in first request")
}
return nil
diff --git a/internal/service/ssh/upload_pack_test.go b/internal/service/ssh/upload_pack_test.go
index a52cc99ae..a36c2d848 100644
--- a/internal/service/ssh/upload_pack_test.go
+++ b/internal/service/ssh/upload_pack_test.go
@@ -2,6 +2,7 @@ package ssh
import (
"bytes"
+ "context"
"fmt"
"os"
"os/exec"
@@ -15,7 +16,6 @@ import (
"gitlab.com/gitlab-org/gitaly/internal/config"
"gitlab.com/gitlab-org/gitaly/internal/git"
"gitlab.com/gitlab-org/gitaly/internal/testhelper"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
)
diff --git a/internal/service/storage/deleteall.go b/internal/service/storage/deleteall.go
index 1a54ce1b1..436bbdc97 100644
--- a/internal/service/storage/deleteall.go
+++ b/internal/service/storage/deleteall.go
@@ -1,6 +1,7 @@
package storage
import (
+ "context"
"io"
"os"
"path"
@@ -10,7 +11,6 @@ import (
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/helper"
"gitlab.com/gitlab-org/gitaly/internal/tempdir"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
)
diff --git a/internal/service/wiki/delete_page.go b/internal/service/wiki/delete_page.go
index cd1ecbaff..8d0a5b70b 100644
--- a/internal/service/wiki/delete_page.go
+++ b/internal/service/wiki/delete_page.go
@@ -1,11 +1,11 @@
package wiki
import (
+ "context"
"fmt"
"gitlab.com/gitlab-org/gitaly-proto/go/gitalypb"
"gitlab.com/gitlab-org/gitaly/internal/rubyserver"
- "golang.org/x/net/context"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
)
diff --git a/ruby/lib/gitaly_server/repository_service.rb b/ruby/lib/gitaly_server/repository_service.rb
index b4abd31bf..223176eb1 100644
--- a/ruby/lib/gitaly_server/repository_service.rb
+++ b/ruby/lib/gitaly_server/repository_service.rb
@@ -38,22 +38,6 @@ module GitalyServer
Gitaly::FetchRemoteResponse.new
end
- def is_rebase_in_progress(request, call) # rubocop:disable Naming/PredicateName
- repo = Gitlab::Git::Repository.from_gitaly(request.repository, call)
-
- result = repo.rebase_in_progress?(request.rebase_id)
-
- Gitaly::IsRebaseInProgressResponse.new(in_progress: result)
- end
-
- def is_squash_in_progress(request, call) # rubocop:disable Naming/PredicateName
- repo = Gitlab::Git::Repository.from_gitaly(request.repository, call)
-
- result = repo.squash_in_progress?(request.squash_id)
-
- Gitaly::IsSquashInProgressResponse.new(in_progress: result)
- end
-
def write_ref(request, call)
Gitlab::Git::Repository.from_gitaly(request.repository, call)
.write_ref(request.ref, request.revision, old_ref: request.old_revision)
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tracing/opentracing/DOC.md b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tracing/opentracing/DOC.md
new file mode 100644
index 000000000..b8e1c2207
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tracing/opentracing/DOC.md
@@ -0,0 +1,118 @@
+# grpc_opentracing
+`import "github.com/grpc-ecosystem/go-grpc-middleware/tracing/opentracing"`
+
+* [Overview](#pkg-overview)
+* [Imported Packages](#pkg-imports)
+* [Index](#pkg-index)
+
+## <a name="pkg-overview">Overview</a>
+`grpc_opentracing` adds OpenTracing
+
+### OpenTracing Interceptors
+These are both client-side and server-side interceptors for OpenTracing. They are a provider-agnostic, with backends
+such as Zipkin, or Google Stackdriver Trace.
+
+For a service that sends out requests and receives requests, you *need* to use both, otherwise downstream requests will
+not have the appropriate requests propagated.
+
+All server-side spans are tagged with grpc_ctxtags information.
+
+For more information see:
+<a href="http://opentracing.io/documentation/">http://opentracing.io/documentation/</a>
+<a href="https://github.com/opentracing/specification/blob/master/semantic_conventions.md">https://github.com/opentracing/specification/blob/master/semantic_conventions.md</a>
+
+## <a name="pkg-imports">Imported Packages</a>
+
+- [github.com/grpc-ecosystem/go-grpc-middleware](./../..)
+- [github.com/grpc-ecosystem/go-grpc-middleware/tags](./../../tags)
+- [github.com/grpc-ecosystem/go-grpc-middleware/util/metautils](./../../util/metautils)
+- [github.com/opentracing/opentracing-go](https://godoc.org/github.com/opentracing/opentracing-go)
+- [github.com/opentracing/opentracing-go/ext](https://godoc.org/github.com/opentracing/opentracing-go/ext)
+- [github.com/opentracing/opentracing-go/log](https://godoc.org/github.com/opentracing/opentracing-go/log)
+- [golang.org/x/net/context](https://godoc.org/golang.org/x/net/context)
+- [google.golang.org/grpc](https://godoc.org/google.golang.org/grpc)
+- [google.golang.org/grpc/grpclog](https://godoc.org/google.golang.org/grpc/grpclog)
+- [google.golang.org/grpc/metadata](https://godoc.org/google.golang.org/grpc/metadata)
+
+## <a name="pkg-index">Index</a>
+* [Constants](#pkg-constants)
+* [func ClientAddContextTags(ctx context.Context, tags opentracing.Tags) context.Context](#ClientAddContextTags)
+* [func StreamClientInterceptor(opts ...Option) grpc.StreamClientInterceptor](#StreamClientInterceptor)
+* [func StreamServerInterceptor(opts ...Option) grpc.StreamServerInterceptor](#StreamServerInterceptor)
+* [func UnaryClientInterceptor(opts ...Option) grpc.UnaryClientInterceptor](#UnaryClientInterceptor)
+* [func UnaryServerInterceptor(opts ...Option) grpc.UnaryServerInterceptor](#UnaryServerInterceptor)
+* [type FilterFunc](#FilterFunc)
+* [type Option](#Option)
+ * [func WithFilterFunc(f FilterFunc) Option](#WithFilterFunc)
+ * [func WithTracer(tracer opentracing.Tracer) Option](#WithTracer)
+
+#### <a name="pkg-files">Package files</a>
+[client_interceptors.go](./client_interceptors.go) [doc.go](./doc.go) [id_extract.go](./id_extract.go) [metadata.go](./metadata.go) [options.go](./options.go) [server_interceptors.go](./server_interceptors.go)
+
+## <a name="pkg-constants">Constants</a>
+``` go
+const (
+ TagTraceId = "trace.traceid"
+ TagSpanId = "trace.spanid"
+)
+```
+
+## <a name="ClientAddContextTags">func</a> [ClientAddContextTags](./client_interceptors.go#L105)
+``` go
+func ClientAddContextTags(ctx context.Context, tags opentracing.Tags) context.Context
+```
+ClientAddContextTags returns a context with specified opentracing tags, which
+are used by UnaryClientInterceptor/StreamClientInterceptor when creating a
+new span.
+
+## <a name="StreamClientInterceptor">func</a> [StreamClientInterceptor](./client_interceptors.go#L35)
+``` go
+func StreamClientInterceptor(opts ...Option) grpc.StreamClientInterceptor
+```
+StreamClientInterceptor returns a new streaming client interceptor for OpenTracing.
+
+## <a name="StreamServerInterceptor">func</a> [StreamServerInterceptor](./server_interceptors.go#L37)
+``` go
+func StreamServerInterceptor(opts ...Option) grpc.StreamServerInterceptor
+```
+StreamServerInterceptor returns a new streaming server interceptor for OpenTracing.
+
+## <a name="UnaryClientInterceptor">func</a> [UnaryClientInterceptor](./client_interceptors.go#L21)
+``` go
+func UnaryClientInterceptor(opts ...Option) grpc.UnaryClientInterceptor
+```
+UnaryClientInterceptor returns a new unary client interceptor for OpenTracing.
+
+## <a name="UnaryServerInterceptor">func</a> [UnaryServerInterceptor](./server_interceptors.go#L23)
+``` go
+func UnaryServerInterceptor(opts ...Option) grpc.UnaryServerInterceptor
+```
+UnaryServerInterceptor returns a new unary server interceptor for OpenTracing.
+
+## <a name="FilterFunc">type</a> [FilterFunc](./options.go#L22)
+``` go
+type FilterFunc func(ctx context.Context, fullMethodName string) bool
+```
+FilterFunc allows users to provide a function that filters out certain methods from being traced.
+
+If it returns false, the given request will not be traced.
+
+## <a name="Option">type</a> [Option](./options.go#L41)
+``` go
+type Option func(*options)
+```
+
+### <a name="WithFilterFunc">func</a> [WithFilterFunc](./options.go#L44)
+``` go
+func WithFilterFunc(f FilterFunc) Option
+```
+WithFilterFunc customizes the function used for deciding whether a given call is traced or not.
+
+### <a name="WithTracer">func</a> [WithTracer](./options.go#L51)
+``` go
+func WithTracer(tracer opentracing.Tracer) Option
+```
+WithTracer sets a custom tracer to be used for this middleware, otherwise the opentracing.GlobalTracer is used.
+
+- - -
+Generated by [godoc2ghmd](https://github.com/GandalfUK/godoc2ghmd) \ No newline at end of file
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tracing/opentracing/README.md b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tracing/opentracing/README.md
new file mode 100644
index 000000000..b8e1c2207
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tracing/opentracing/README.md
@@ -0,0 +1,118 @@
+# grpc_opentracing
+`import "github.com/grpc-ecosystem/go-grpc-middleware/tracing/opentracing"`
+
+* [Overview](#pkg-overview)
+* [Imported Packages](#pkg-imports)
+* [Index](#pkg-index)
+
+## <a name="pkg-overview">Overview</a>
+`grpc_opentracing` adds OpenTracing
+
+### OpenTracing Interceptors
+These are both client-side and server-side interceptors for OpenTracing. They are a provider-agnostic, with backends
+such as Zipkin, or Google Stackdriver Trace.
+
+For a service that sends out requests and receives requests, you *need* to use both, otherwise downstream requests will
+not have the appropriate requests propagated.
+
+All server-side spans are tagged with grpc_ctxtags information.
+
+For more information see:
+<a href="http://opentracing.io/documentation/">http://opentracing.io/documentation/</a>
+<a href="https://github.com/opentracing/specification/blob/master/semantic_conventions.md">https://github.com/opentracing/specification/blob/master/semantic_conventions.md</a>
+
+## <a name="pkg-imports">Imported Packages</a>
+
+- [github.com/grpc-ecosystem/go-grpc-middleware](./../..)
+- [github.com/grpc-ecosystem/go-grpc-middleware/tags](./../../tags)
+- [github.com/grpc-ecosystem/go-grpc-middleware/util/metautils](./../../util/metautils)
+- [github.com/opentracing/opentracing-go](https://godoc.org/github.com/opentracing/opentracing-go)
+- [github.com/opentracing/opentracing-go/ext](https://godoc.org/github.com/opentracing/opentracing-go/ext)
+- [github.com/opentracing/opentracing-go/log](https://godoc.org/github.com/opentracing/opentracing-go/log)
+- [golang.org/x/net/context](https://godoc.org/golang.org/x/net/context)
+- [google.golang.org/grpc](https://godoc.org/google.golang.org/grpc)
+- [google.golang.org/grpc/grpclog](https://godoc.org/google.golang.org/grpc/grpclog)
+- [google.golang.org/grpc/metadata](https://godoc.org/google.golang.org/grpc/metadata)
+
+## <a name="pkg-index">Index</a>
+* [Constants](#pkg-constants)
+* [func ClientAddContextTags(ctx context.Context, tags opentracing.Tags) context.Context](#ClientAddContextTags)
+* [func StreamClientInterceptor(opts ...Option) grpc.StreamClientInterceptor](#StreamClientInterceptor)
+* [func StreamServerInterceptor(opts ...Option) grpc.StreamServerInterceptor](#StreamServerInterceptor)
+* [func UnaryClientInterceptor(opts ...Option) grpc.UnaryClientInterceptor](#UnaryClientInterceptor)
+* [func UnaryServerInterceptor(opts ...Option) grpc.UnaryServerInterceptor](#UnaryServerInterceptor)
+* [type FilterFunc](#FilterFunc)
+* [type Option](#Option)
+ * [func WithFilterFunc(f FilterFunc) Option](#WithFilterFunc)
+ * [func WithTracer(tracer opentracing.Tracer) Option](#WithTracer)
+
+#### <a name="pkg-files">Package files</a>
+[client_interceptors.go](./client_interceptors.go) [doc.go](./doc.go) [id_extract.go](./id_extract.go) [metadata.go](./metadata.go) [options.go](./options.go) [server_interceptors.go](./server_interceptors.go)
+
+## <a name="pkg-constants">Constants</a>
+``` go
+const (
+ TagTraceId = "trace.traceid"
+ TagSpanId = "trace.spanid"
+)
+```
+
+## <a name="ClientAddContextTags">func</a> [ClientAddContextTags](./client_interceptors.go#L105)
+``` go
+func ClientAddContextTags(ctx context.Context, tags opentracing.Tags) context.Context
+```
+ClientAddContextTags returns a context with specified opentracing tags, which
+are used by UnaryClientInterceptor/StreamClientInterceptor when creating a
+new span.
+
+## <a name="StreamClientInterceptor">func</a> [StreamClientInterceptor](./client_interceptors.go#L35)
+``` go
+func StreamClientInterceptor(opts ...Option) grpc.StreamClientInterceptor
+```
+StreamClientInterceptor returns a new streaming client interceptor for OpenTracing.
+
+## <a name="StreamServerInterceptor">func</a> [StreamServerInterceptor](./server_interceptors.go#L37)
+``` go
+func StreamServerInterceptor(opts ...Option) grpc.StreamServerInterceptor
+```
+StreamServerInterceptor returns a new streaming server interceptor for OpenTracing.
+
+## <a name="UnaryClientInterceptor">func</a> [UnaryClientInterceptor](./client_interceptors.go#L21)
+``` go
+func UnaryClientInterceptor(opts ...Option) grpc.UnaryClientInterceptor
+```
+UnaryClientInterceptor returns a new unary client interceptor for OpenTracing.
+
+## <a name="UnaryServerInterceptor">func</a> [UnaryServerInterceptor](./server_interceptors.go#L23)
+``` go
+func UnaryServerInterceptor(opts ...Option) grpc.UnaryServerInterceptor
+```
+UnaryServerInterceptor returns a new unary server interceptor for OpenTracing.
+
+## <a name="FilterFunc">type</a> [FilterFunc](./options.go#L22)
+``` go
+type FilterFunc func(ctx context.Context, fullMethodName string) bool
+```
+FilterFunc allows users to provide a function that filters out certain methods from being traced.
+
+If it returns false, the given request will not be traced.
+
+## <a name="Option">type</a> [Option](./options.go#L41)
+``` go
+type Option func(*options)
+```
+
+### <a name="WithFilterFunc">func</a> [WithFilterFunc](./options.go#L44)
+``` go
+func WithFilterFunc(f FilterFunc) Option
+```
+WithFilterFunc customizes the function used for deciding whether a given call is traced or not.
+
+### <a name="WithTracer">func</a> [WithTracer](./options.go#L51)
+``` go
+func WithTracer(tracer opentracing.Tracer) Option
+```
+WithTracer sets a custom tracer to be used for this middleware, otherwise the opentracing.GlobalTracer is used.
+
+- - -
+Generated by [godoc2ghmd](https://github.com/GandalfUK/godoc2ghmd) \ No newline at end of file
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tracing/opentracing/client_interceptors.go b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tracing/opentracing/client_interceptors.go
new file mode 100644
index 000000000..f8fdecf5a
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tracing/opentracing/client_interceptors.go
@@ -0,0 +1,142 @@
+// Copyright 2017 Michal Witkowski. All Rights Reserved.
+// See LICENSE for licensing terms.
+
+package grpc_opentracing
+
+import (
+ "io"
+ "sync"
+
+ "github.com/grpc-ecosystem/go-grpc-middleware/util/metautils"
+ opentracing "github.com/opentracing/opentracing-go"
+ "github.com/opentracing/opentracing-go/ext"
+ "github.com/opentracing/opentracing-go/log"
+ "golang.org/x/net/context"
+ "google.golang.org/grpc"
+ "google.golang.org/grpc/grpclog"
+ "google.golang.org/grpc/metadata"
+)
+
+// UnaryClientInterceptor returns a new unary client interceptor for OpenTracing.
+func UnaryClientInterceptor(opts ...Option) grpc.UnaryClientInterceptor {
+ o := evaluateOptions(opts)
+ return func(parentCtx context.Context, method string, req, reply interface{}, cc *grpc.ClientConn, invoker grpc.UnaryInvoker, opts ...grpc.CallOption) error {
+ if o.filterOutFunc != nil && !o.filterOutFunc(parentCtx, method) {
+ return invoker(parentCtx, method, req, reply, cc, opts...)
+ }
+ newCtx, clientSpan := newClientSpanFromContext(parentCtx, o.tracer, method)
+ err := invoker(newCtx, method, req, reply, cc, opts...)
+ finishClientSpan(clientSpan, err)
+ return err
+ }
+}
+
+// StreamClientInterceptor returns a new streaming client interceptor for OpenTracing.
+func StreamClientInterceptor(opts ...Option) grpc.StreamClientInterceptor {
+ o := evaluateOptions(opts)
+ return func(parentCtx context.Context, desc *grpc.StreamDesc, cc *grpc.ClientConn, method string, streamer grpc.Streamer, opts ...grpc.CallOption) (grpc.ClientStream, error) {
+ if o.filterOutFunc != nil && !o.filterOutFunc(parentCtx, method) {
+ return streamer(parentCtx, desc, cc, method, opts...)
+ }
+ newCtx, clientSpan := newClientSpanFromContext(parentCtx, o.tracer, method)
+ clientStream, err := streamer(newCtx, desc, cc, method, opts...)
+ if err != nil {
+ finishClientSpan(clientSpan, err)
+ return nil, err
+ }
+ return &tracedClientStream{ClientStream: clientStream, clientSpan: clientSpan}, nil
+ }
+}
+
+// type serverStreamingRetryingStream is the implementation of grpc.ClientStream that acts as a
+// proxy to the underlying call. If any of the RecvMsg() calls fail, it will try to reestablish
+// a new ClientStream according to the retry policy.
+type tracedClientStream struct {
+ grpc.ClientStream
+ mu sync.Mutex
+ alreadyFinished bool
+ clientSpan opentracing.Span
+}
+
+func (s *tracedClientStream) Header() (metadata.MD, error) {
+ h, err := s.ClientStream.Header()
+ if err != nil {
+ s.finishClientSpan(err)
+ }
+ return h, err
+}
+
+func (s *tracedClientStream) SendMsg(m interface{}) error {
+ err := s.ClientStream.SendMsg(m)
+ if err != nil {
+ s.finishClientSpan(err)
+ }
+ return err
+}
+
+func (s *tracedClientStream) CloseSend() error {
+ err := s.ClientStream.CloseSend()
+ if err != nil {
+ s.finishClientSpan(err)
+ }
+ return err
+}
+
+func (s *tracedClientStream) RecvMsg(m interface{}) error {
+ err := s.ClientStream.RecvMsg(m)
+ if err != nil {
+ s.finishClientSpan(err)
+ }
+ return err
+}
+
+func (s *tracedClientStream) finishClientSpan(err error) {
+ s.mu.Lock()
+ defer s.mu.Unlock()
+ if !s.alreadyFinished {
+ finishClientSpan(s.clientSpan, err)
+ s.alreadyFinished = true
+ }
+}
+
+// ClientAddContextTags returns a context with specified opentracing tags, which
+// are used by UnaryClientInterceptor/StreamClientInterceptor when creating a
+// new span.
+func ClientAddContextTags(ctx context.Context, tags opentracing.Tags) context.Context {
+ return context.WithValue(ctx, clientSpanTagKey{}, tags)
+}
+
+type clientSpanTagKey struct{}
+
+func newClientSpanFromContext(ctx context.Context, tracer opentracing.Tracer, fullMethodName string) (context.Context, opentracing.Span) {
+ var parentSpanCtx opentracing.SpanContext
+ if parent := opentracing.SpanFromContext(ctx); parent != nil {
+ parentSpanCtx = parent.Context()
+ }
+ opts := []opentracing.StartSpanOption{
+ opentracing.ChildOf(parentSpanCtx),
+ ext.SpanKindRPCClient,
+ grpcTag,
+ }
+ if tagx := ctx.Value(clientSpanTagKey{}); tagx != nil {
+ if opt, ok := tagx.(opentracing.StartSpanOption); ok {
+ opts = append(opts, opt)
+ }
+ }
+ clientSpan := tracer.StartSpan(fullMethodName, opts...)
+ // Make sure we add this to the metadata of the call, so it gets propagated:
+ md := metautils.ExtractOutgoing(ctx).Clone()
+ if err := tracer.Inject(clientSpan.Context(), opentracing.HTTPHeaders, metadataTextMap(md)); err != nil {
+ grpclog.Printf("grpc_opentracing: failed serializing trace information: %v", err)
+ }
+ ctxWithMetadata := md.ToOutgoing(ctx)
+ return opentracing.ContextWithSpan(ctxWithMetadata, clientSpan), clientSpan
+}
+
+func finishClientSpan(clientSpan opentracing.Span, err error) {
+ if err != nil && err != io.EOF {
+ ext.Error.Set(clientSpan, true)
+ clientSpan.LogFields(log.String("event", "error"), log.String("message", err.Error()))
+ }
+ clientSpan.Finish()
+}
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tracing/opentracing/doc.go b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tracing/opentracing/doc.go
new file mode 100644
index 000000000..7a58efc22
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tracing/opentracing/doc.go
@@ -0,0 +1,22 @@
+// Copyright 2017 Michal Witkowski. All Rights Reserved.
+// See LICENSE for licensing terms.
+
+/*
+`grpc_opentracing` adds OpenTracing
+
+OpenTracing Interceptors
+
+These are both client-side and server-side interceptors for OpenTracing. They are a provider-agnostic, with backends
+such as Zipkin, or Google Stackdriver Trace.
+
+For a service that sends out requests and receives requests, you *need* to use both, otherwise downstream requests will
+not have the appropriate requests propagated.
+
+All server-side spans are tagged with grpc_ctxtags information.
+
+For more information see:
+http://opentracing.io/documentation/
+https://github.com/opentracing/specification/blob/master/semantic_conventions.md
+
+*/
+package grpc_opentracing
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tracing/opentracing/id_extract.go b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tracing/opentracing/id_extract.go
new file mode 100644
index 000000000..196240fd6
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tracing/opentracing/id_extract.go
@@ -0,0 +1,50 @@
+// Copyright 2017 Michal Witkowski. All Rights Reserved.
+// See LICENSE for licensing terms.
+
+package grpc_opentracing
+
+import (
+ "strings"
+
+ "github.com/grpc-ecosystem/go-grpc-middleware/tags"
+ "github.com/opentracing/opentracing-go"
+ "google.golang.org/grpc/grpclog"
+)
+
+const (
+ TagTraceId = "trace.traceid"
+ TagSpanId = "trace.spanid"
+)
+
+// hackyInjectOpentracingIdsToTags writes the given context to the ctxtags.
+// This is done in an incredibly hacky way, because the public-facing interface of opentracing doesn't give access to
+// the TraceId and SpanId of the SpanContext. Only the Tracer's Inject/Extract methods know what these are.
+// Most tracers have them encoded as keys with 'traceid' and 'spanid':
+// https://github.com/openzipkin/zipkin-go-opentracing/blob/594640b9ef7e5c994e8d9499359d693c032d738c/propagation_ot.go#L29
+// https://github.com/opentracing/basictracer-go/blob/1b32af207119a14b1b231d451df3ed04a72efebf/propagation_ot.go#L26
+// Jaeger from Uber use one-key schema with next format '{trace-id}:{span-id}:{parent-span-id}:{flags}'
+// https://www.jaegertracing.io/docs/client-libraries/#trace-span-identity
+func hackyInjectOpentracingIdsToTags(span opentracing.Span, tags grpc_ctxtags.Tags) {
+ if err := span.Tracer().Inject(span.Context(), opentracing.HTTPHeaders, &hackyTagsCarrier{tags}); err != nil {
+ grpclog.Printf("grpc_opentracing: failed extracting trace info into ctx %v", err)
+ }
+}
+
+// hackyTagsCarrier is a really hacky way of
+type hackyTagsCarrier struct {
+ grpc_ctxtags.Tags
+}
+
+func (t *hackyTagsCarrier) Set(key, val string) {
+ if strings.Contains(key, "traceid") || strings.Contains(strings.ToLower(key), "traceid") {
+ t.Tags.Set(TagTraceId, val) // this will most likely be base-16 (hex) encoded
+ } else if (strings.Contains(key, "spanid") && !strings.Contains(key, "parent")) || (strings.Contains(strings.ToLower(key), "spanid") && !strings.Contains(strings.ToLower(key), "parent")) {
+ t.Tags.Set(TagSpanId, val) // this will most likely be base-16 (hex) encoded
+ } else if key == "uber-trace-id" {
+ parts := strings.Split(val, ":")
+ if len(parts) >= 2 {
+ t.Tags.Set(TagTraceId, parts[0])
+ t.Tags.Set(TagSpanId, parts[1])
+ }
+ }
+}
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tracing/opentracing/metadata.go b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tracing/opentracing/metadata.go
new file mode 100644
index 000000000..38f251d31
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tracing/opentracing/metadata.go
@@ -0,0 +1,56 @@
+// Copyright 2017 Michal Witkowski. All Rights Reserved.
+// See LICENSE for licensing terms.
+
+package grpc_opentracing
+
+import (
+ "encoding/base64"
+ "strings"
+
+ "fmt"
+
+ "google.golang.org/grpc/metadata"
+)
+
+const (
+ binHdrSuffix = "-bin"
+)
+
+// metadataTextMap extends a metadata.MD to be an opentracing textmap
+type metadataTextMap metadata.MD
+
+// Set is a opentracing.TextMapReader interface that extracts values.
+func (m metadataTextMap) Set(key, val string) {
+ // gRPC allows for complex binary values to be written.
+ encodedKey, encodedVal := encodeKeyValue(key, val)
+ // The metadata object is a multimap, and previous values may exist, but for opentracing headers, we do not append
+ // we just override.
+ m[encodedKey] = []string{encodedVal}
+}
+
+// ForeachKey is a opentracing.TextMapReader interface that extracts values.
+func (m metadataTextMap) ForeachKey(callback func(key, val string) error) error {
+ for k, vv := range m {
+ for _, v := range vv {
+ if decodedKey, decodedVal, err := metadata.DecodeKeyValue(k, v); err == nil {
+ if err = callback(decodedKey, decodedVal); err != nil {
+ return err
+ }
+ } else {
+ return fmt.Errorf("failed decoding opentracing from gRPC metadata: %v", err)
+ }
+ }
+ }
+ return nil
+}
+
+// encodeKeyValue encodes key and value qualified for transmission via gRPC.
+// note: copy pasted from private values of grpc.metadata
+func encodeKeyValue(k, v string) (string, string) {
+ k = strings.ToLower(k)
+ if strings.HasSuffix(k, binHdrSuffix) {
+ val := base64.StdEncoding.EncodeToString([]byte(v))
+ v = string(val)
+ }
+ return k, v
+}
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tracing/opentracing/options.go b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tracing/opentracing/options.go
new file mode 100644
index 000000000..e75102b25
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tracing/opentracing/options.go
@@ -0,0 +1,55 @@
+// Copyright 2017 Michal Witkowski. All Rights Reserved.
+// See LICENSE for licensing terms.
+
+package grpc_opentracing
+
+import (
+ "context"
+
+ "github.com/opentracing/opentracing-go"
+)
+
+var (
+ defaultOptions = &options{
+ filterOutFunc: nil,
+ tracer: nil,
+ }
+)
+
+// FilterFunc allows users to provide a function that filters out certain methods from being traced.
+//
+// If it returns false, the given request will not be traced.
+type FilterFunc func(ctx context.Context, fullMethodName string) bool
+
+type options struct {
+ filterOutFunc FilterFunc
+ tracer opentracing.Tracer
+}
+
+func evaluateOptions(opts []Option) *options {
+ optCopy := &options{}
+ *optCopy = *defaultOptions
+ for _, o := range opts {
+ o(optCopy)
+ }
+ if optCopy.tracer == nil {
+ optCopy.tracer = opentracing.GlobalTracer()
+ }
+ return optCopy
+}
+
+type Option func(*options)
+
+// WithFilterFunc customizes the function used for deciding whether a given call is traced or not.
+func WithFilterFunc(f FilterFunc) Option {
+ return func(o *options) {
+ o.filterOutFunc = f
+ }
+}
+
+// WithTracer sets a custom tracer to be used for this middleware, otherwise the opentracing.GlobalTracer is used.
+func WithTracer(tracer opentracing.Tracer) Option {
+ return func(o *options) {
+ o.tracer = tracer
+ }
+}
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tracing/opentracing/server_interceptors.go b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tracing/opentracing/server_interceptors.go
new file mode 100644
index 000000000..498e8efae
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tracing/opentracing/server_interceptors.go
@@ -0,0 +1,86 @@
+// Copyright 2017 Michal Witkowski. All Rights Reserved.
+// See LICENSE for licensing terms.
+
+package grpc_opentracing
+
+import (
+ "github.com/grpc-ecosystem/go-grpc-middleware"
+ "github.com/grpc-ecosystem/go-grpc-middleware/tags"
+ "github.com/grpc-ecosystem/go-grpc-middleware/util/metautils"
+ "github.com/opentracing/opentracing-go"
+ "github.com/opentracing/opentracing-go/ext"
+ "github.com/opentracing/opentracing-go/log"
+ "golang.org/x/net/context"
+ "google.golang.org/grpc"
+ "google.golang.org/grpc/grpclog"
+)
+
+var (
+ grpcTag = opentracing.Tag{Key: string(ext.Component), Value: "gRPC"}
+)
+
+// UnaryServerInterceptor returns a new unary server interceptor for OpenTracing.
+func UnaryServerInterceptor(opts ...Option) grpc.UnaryServerInterceptor {
+ o := evaluateOptions(opts)
+ return func(ctx context.Context, req interface{}, info *grpc.UnaryServerInfo, handler grpc.UnaryHandler) (interface{}, error) {
+ if o.filterOutFunc != nil && !o.filterOutFunc(ctx, info.FullMethod) {
+ return handler(ctx, req)
+ }
+ newCtx, serverSpan := newServerSpanFromInbound(ctx, o.tracer, info.FullMethod)
+ resp, err := handler(newCtx, req)
+ finishServerSpan(ctx, serverSpan, err)
+ return resp, err
+ }
+}
+
+// StreamServerInterceptor returns a new streaming server interceptor for OpenTracing.
+func StreamServerInterceptor(opts ...Option) grpc.StreamServerInterceptor {
+ o := evaluateOptions(opts)
+ return func(srv interface{}, stream grpc.ServerStream, info *grpc.StreamServerInfo, handler grpc.StreamHandler) error {
+ if o.filterOutFunc != nil && !o.filterOutFunc(stream.Context(), info.FullMethod) {
+ return handler(srv, stream)
+ }
+ newCtx, serverSpan := newServerSpanFromInbound(stream.Context(), o.tracer, info.FullMethod)
+ wrappedStream := grpc_middleware.WrapServerStream(stream)
+ wrappedStream.WrappedContext = newCtx
+ err := handler(srv, wrappedStream)
+ finishServerSpan(newCtx, serverSpan, err)
+ return err
+ }
+}
+
+func newServerSpanFromInbound(ctx context.Context, tracer opentracing.Tracer, fullMethodName string) (context.Context, opentracing.Span) {
+ md := metautils.ExtractIncoming(ctx)
+ parentSpanContext, err := tracer.Extract(opentracing.HTTPHeaders, metadataTextMap(md))
+ if err != nil && err != opentracing.ErrSpanContextNotFound {
+ grpclog.Printf("grpc_opentracing: failed parsing trace information: %v", err)
+ }
+
+ serverSpan := tracer.StartSpan(
+ fullMethodName,
+ // this is magical, it attaches the new span to the parent parentSpanContext, and creates an unparented one if empty.
+ ext.RPCServerOption(parentSpanContext),
+ grpcTag,
+ )
+ hackyInjectOpentracingIdsToTags(serverSpan, grpc_ctxtags.Extract(ctx))
+ return opentracing.ContextWithSpan(ctx, serverSpan), serverSpan
+}
+
+func finishServerSpan(ctx context.Context, serverSpan opentracing.Span, err error) {
+ // Log context information
+ tags := grpc_ctxtags.Extract(ctx)
+ for k, v := range tags.Values() {
+ // Don't tag errors, log them instead.
+ if vErr, ok := v.(error); ok {
+ serverSpan.LogKV(k, vErr.Error())
+
+ } else {
+ serverSpan.SetTag(k, v)
+ }
+ }
+ if err != nil {
+ ext.Error.Set(serverSpan, true)
+ serverSpan.LogFields(log.String("event", "error"), log.String("message", err.Error()))
+ }
+ serverSpan.Finish()
+}
diff --git a/vendor/github.com/lightstep/lightstep-tracer-go/CHANGELOG.md b/vendor/github.com/lightstep/lightstep-tracer-go/CHANGELOG.md
new file mode 100644
index 000000000..5388f08dd
--- /dev/null
+++ b/vendor/github.com/lightstep/lightstep-tracer-go/CHANGELOG.md
@@ -0,0 +1,54 @@
+# Changelog
+
+## [Pending Release](https://github.com/lightstep/lightstep-tracer-go/compare/v0.15.6...HEAD)
+* Requires go >= 1.7
+* Imports `context` via the standard library instead of `golang.org/x/net/context`
+* Fixes [#182](https://github.com/lightstep/lightstep-tracer-go/issues/182), so that `StartSpan` can now take `SpanReference`s to non-LightStep `SpanContext`s use
+
+## [v0.15.6](https://github.com/lightstep/lightstep-tracer-go/compare/v0.15.5...v0.15.6)
+
+* Minor update to `sendspan` to make it easier to pick which transport protocol to use.
+* Add a new field to Options: DialOptions. These allow setting custom grpc dial options when using grpc.
+ * This is necessary to have customer balancers or interceptors.
+ * DialOptions shouldn't be set unless it is needed, it will default correctly.
+* Added a new field to Endpoint: Scheme. Scheme can be used to override the default schemes (http/https) or set a custom scheme (for grpc).
+ * This is necessary for using custom grpc resolvers.
+ * If callers are using struct construction without field names (i.e. Endpoint{"host", port, ...}), they will need to add a new field (scheme = "").
+ * Scheme shouldn't be set unless it needs to overridden, it will default correctly.
+
+## [v0.15.5](https://github.com/lightstep/lightstep-tracer-go/compare/v0.15.4...v0.15.5)
+* Internal performance optimizations and a bug fix for issue [#161](https://github.com/lightstep/lightstep-tracer-go/issues/161)
+
+## [v0.15.4](https://github.com/lightstep/lightstep-tracer-go/compare/v0.15.3...v0.15.4)
+* This change affects LightStep's internal testing, not a functional change.
+
+## [v0.15.3](https://github.com/lightstep/lightstep-tracer-go/compare/v0.15.2...v0.15.3)
+* Adds compatibility for io.Writer and io.Reader in Inject/Extract, as required by Open Tracing.
+
+## [v0.15.2](https://github.com/lightstep/lightstep-tracer-go/compare/v0.15.1...v0.15.2)
+* Adds lightstep.GetLightStepReporterID.
+
+## [v0.15.1](https://github.com/lightstep/lightstep-tracer-go/compare/v0.15.0...v0.15.1)
+* Adds Gopkg.toml
+
+## [v0.15.0](https://github.com/lightstep/lightstep-tracer-go/compare/v0.14.0...v0.15.0)
+* We are replacing the internal diagnostic logging with a more flexible “Event” framework. This enables you to track and understand tracer problems with metrics and logging tools of your choice.
+* We are also changed the types of the Close() and Flush() methods to take a context parameter to support cancellation. These changes are *not* backwards compatible and *you will need to update your instrumentation*. We are providing a NewTracerv0_14() method that is a drop-in replacement for the previous version.
+
+## [v0.14.0](https://github.com/lightstep/lightstep-tracer-go/compare/v0.13.0...v0.14.0)
+* Flush buffer syncronously on Close.
+* Flush twice if a flush is already in flight.
+* Remove gogo in favor of golang/protobuf.
+* Requires grpc-go >= 1.4.0.
+
+## [v0.13.0](https://github.com/lightstep/lightstep-tracer-go/compare/v0.12.0...v0.13.0)
+* BasicTracer has been removed.
+* Tracer now takes a SpanRecorder as an option.
+* Tracer interface now includes Close and Flush.
+* Tests redone with ginkgo/gomega.
+
+## [v0.12.0](https://github.com/lightstep/lightstep-tracer-go/compare/v0.11.0...v0.12.0)
+* Added CloseTracer function to flush and close a lightstep recorder.
+
+## [v0.11.0](https://github.com/lightstep/lightstep-tracer-go/compare/v0.10.0...v0.11.0)
+* Thrift transport is now deprecated, gRPC is the default.
diff --git a/vendor/github.com/lightstep/lightstep-tracer-go/Gopkg.lock b/vendor/github.com/lightstep/lightstep-tracer-go/Gopkg.lock
new file mode 100644
index 000000000..17d5d8f6d
--- /dev/null
+++ b/vendor/github.com/lightstep/lightstep-tracer-go/Gopkg.lock
@@ -0,0 +1,217 @@
+# This file is autogenerated, do not edit; changes may be undone by the next 'dep ensure'.
+
+
+[[projects]]
+ branch = "master"
+ digest = "1:3b760d3b93f994df8eb1d9ebfad17d3e9e37edcb7f7efaa15b427c0d7a64f4e4"
+ name = "github.com/golang/protobuf"
+ packages = [
+ "proto",
+ "protoc-gen-go/descriptor",
+ "ptypes",
+ "ptypes/any",
+ "ptypes/duration",
+ "ptypes/timestamp",
+ ]
+ pruneopts = ""
+ revision = "1e59b77b52bf8e4b449a57e6f79f21226d571845"
+
+[[projects]]
+ branch = "master"
+ digest = "1:b486888585e9070ef97f0c9b2df560e007dc2eafb8ace96b13a2cb85ccec3df1"
+ name = "github.com/lightstep/thrift"
+ packages = ["lib/go/thrift"]
+ pruneopts = ""
+ revision = "de6c3c01b88c1fc8ae76cec4a30f0441ef55a4a4"
+
+[[projects]]
+ digest = "1:32b27072cd55bd2fb7244de0425943d125da6a552ae2b6517cdd965a662baf18"
+ name = "github.com/onsi/ginkgo"
+ packages = [
+ ".",
+ "config",
+ "internal/codelocation",
+ "internal/containernode",
+ "internal/failer",
+ "internal/leafnodes",
+ "internal/remote",
+ "internal/spec",
+ "internal/spec_iterator",
+ "internal/specrunner",
+ "internal/suite",
+ "internal/testingtproxy",
+ "internal/writer",
+ "reporters",
+ "reporters/stenographer",
+ "reporters/stenographer/support/go-colorable",
+ "reporters/stenographer/support/go-isatty",
+ "types",
+ ]
+ pruneopts = ""
+ revision = "9eda700730cba42af70d53180f9dcce9266bc2bc"
+ version = "v1.4.0"
+
+[[projects]]
+ digest = "1:a4e59d0b2821c983b58c317f141cd77df20570979632da8a7a352e5d12698de7"
+ name = "github.com/onsi/gomega"
+ packages = [
+ ".",
+ "format",
+ "internal/assertion",
+ "internal/asyncassertion",
+ "internal/oraclematcher",
+ "internal/testingtsupport",
+ "matchers",
+ "matchers/support/goraph/bipartitegraph",
+ "matchers/support/goraph/edge",
+ "matchers/support/goraph/node",
+ "matchers/support/goraph/util",
+ "types",
+ ]
+ pruneopts = ""
+ revision = "c893efa28eb45626cdaa76c9f653b62488858837"
+ version = "v1.2.0"
+
+[[projects]]
+ digest = "1:78fb99d6011c2ae6c72f3293a83951311147b12b06a5ffa43abf750c4fab6ac5"
+ name = "github.com/opentracing/opentracing-go"
+ packages = [
+ ".",
+ "log",
+ ]
+ pruneopts = ""
+ revision = "1949ddbfd147afd4d964a9f00b24eb291e0e7c38"
+ version = "v1.0.2"
+
+[[projects]]
+ branch = "master"
+ digest = "1:950b672f2ee80d0fc4c95a15a976ba9ee573a6fb8ede8a777770b2230776367e"
+ name = "golang.org/x/net"
+ packages = [
+ "context",
+ "html",
+ "html/atom",
+ "html/charset",
+ "http2",
+ "http2/hpack",
+ "idna",
+ "internal/timeseries",
+ "lex/httplex",
+ "trace",
+ ]
+ pruneopts = ""
+ revision = "dc871a5d77e227f5bbf6545176ef3eeebf87e76e"
+
+[[projects]]
+ branch = "master"
+ digest = "1:5da11ab130476e2736f32140f3c1aed2a3a96e9ba8963711a7d38db783d042bd"
+ name = "golang.org/x/sys"
+ packages = ["unix"]
+ pruneopts = ""
+ revision = "a0f4589a76f1f83070cb9e5613809e1d07b97c13"
+
+[[projects]]
+ branch = "master"
+ digest = "1:1c70f7bb89783a026dc32920575a3feef48e065ef6e170ad227903e8194d7a36"
+ name = "golang.org/x/text"
+ packages = [
+ "collate",
+ "collate/build",
+ "encoding",
+ "encoding/charmap",
+ "encoding/htmlindex",
+ "encoding/internal",
+ "encoding/internal/identifier",
+ "encoding/japanese",
+ "encoding/korean",
+ "encoding/simplifiedchinese",
+ "encoding/traditionalchinese",
+ "encoding/unicode",
+ "internal/colltab",
+ "internal/gen",
+ "internal/tag",
+ "internal/triegen",
+ "internal/ucd",
+ "internal/utf8internal",
+ "language",
+ "runes",
+ "secure/bidirule",
+ "transform",
+ "unicode/bidi",
+ "unicode/cldr",
+ "unicode/norm",
+ "unicode/rangetable",
+ ]
+ pruneopts = ""
+ revision = "be25de41fadfae372d6470bda81ca6beb55ef551"
+
+[[projects]]
+ branch = "master"
+ digest = "1:6c15114fafeac4c833544476dec4207a3476799d50ab5165af79eb97806884cf"
+ name = "google.golang.org/genproto"
+ packages = [
+ "googleapis/api/annotations",
+ "googleapis/rpc/status",
+ ]
+ pruneopts = ""
+ revision = "7f0da29060c682909f650ad8ed4e515bd74fa12a"
+
+[[projects]]
+ digest = "1:6c00b4702c146631d30396090d40bfc0486f8b3af5c976d6f0daf2bc737cd7b2"
+ name = "google.golang.org/grpc"
+ packages = [
+ ".",
+ "balancer",
+ "balancer/roundrobin",
+ "codes",
+ "connectivity",
+ "credentials",
+ "encoding",
+ "grpclb/grpc_lb_v1/messages",
+ "grpclog",
+ "internal",
+ "keepalive",
+ "metadata",
+ "naming",
+ "peer",
+ "resolver",
+ "resolver/dns",
+ "resolver/manual",
+ "resolver/passthrough",
+ "stats",
+ "status",
+ "tap",
+ "transport",
+ ]
+ pruneopts = ""
+ revision = "be077907e29fdb945d351e4284eb5361e7f8924e"
+ version = "v1.8.1"
+
+[[projects]]
+ branch = "v2"
+ digest = "1:f769ed60e075e4221612c2f4162fccc9d3795ef358fa463425e3b3d7a5debb27"
+ name = "gopkg.in/yaml.v2"
+ packages = ["."]
+ pruneopts = ""
+ revision = "287cf08546ab5e7e37d55a84f7ed3fd1db036de5"
+
+[solve-meta]
+ analyzer-name = "dep"
+ analyzer-version = 1
+ input-imports = [
+ "github.com/golang/protobuf/proto",
+ "github.com/golang/protobuf/ptypes/timestamp",
+ "github.com/lightstep/thrift/lib/go/thrift",
+ "github.com/onsi/ginkgo",
+ "github.com/onsi/gomega",
+ "github.com/onsi/gomega/types",
+ "github.com/opentracing/opentracing-go",
+ "github.com/opentracing/opentracing-go/log",
+ "golang.org/x/net/context",
+ "golang.org/x/net/http2",
+ "google.golang.org/genproto/googleapis/api/annotations",
+ "google.golang.org/grpc",
+ "google.golang.org/grpc/credentials",
+ ]
+ solver-name = "gps-cdcl"
+ solver-version = 1
diff --git a/vendor/github.com/lightstep/lightstep-tracer-go/Gopkg.toml b/vendor/github.com/lightstep/lightstep-tracer-go/Gopkg.toml
new file mode 100644
index 000000000..3d24828ba
--- /dev/null
+++ b/vendor/github.com/lightstep/lightstep-tracer-go/Gopkg.toml
@@ -0,0 +1,23 @@
+[[constraint]]
+ name = "github.com/onsi/ginkgo"
+ version = "1.4.0"
+
+[[constraint]]
+ name = "github.com/onsi/gomega"
+ version = "1.2.0"
+
+[[constraint]]
+ name = "github.com/opentracing/opentracing-go"
+ version = "1.0.2"
+
+[[constraint]]
+ branch = "master"
+ name = "golang.org/x/net"
+
+[[constraint]]
+ name = "google.golang.org/grpc"
+ version = "1.4.3"
+
+[[constraint]]
+ name = "github.com/lightstep/thrift"
+ branch = "master"
diff --git a/vendor/github.com/lightstep/lightstep-tracer-go/LICENSE b/vendor/github.com/lightstep/lightstep-tracer-go/LICENSE
new file mode 100644
index 000000000..853b46db1
--- /dev/null
+++ b/vendor/github.com/lightstep/lightstep-tracer-go/LICENSE
@@ -0,0 +1,21 @@
+The MIT License (MIT)
+
+Copyright (c) 2016
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in all
+copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+SOFTWARE.
diff --git a/vendor/github.com/lightstep/lightstep-tracer-go/Makefile b/vendor/github.com/lightstep/lightstep-tracer-go/Makefile
new file mode 100644
index 000000000..aae12906d
--- /dev/null
+++ b/vendor/github.com/lightstep/lightstep-tracer-go/Makefile
@@ -0,0 +1,87 @@
+# tools
+GO=go
+DOCKER_PRESENT = $(shell command -v docker 2> /dev/null)
+
+LOCAL_GOPATH = $(PWD)/../../../../
+
+default: build
+.PHONY: default build test
+
+# generate_fake: runs counterfeiter in docker container to generate fake classes
+# $(1) output file path
+# $(2) input file path
+# $(3) class name
+define generate_fake
+ docker run --rm -v $(LOCAL_GOPATH):/usergo \
+ lightstep/gobuild:latest /bin/bash -c "\
+ cd /usergo/src/github.com/lightstep/lightstep-tracer-go; \
+ counterfeiter -o $(1) $(2) $(3)"
+endef
+# Thrift
+ifeq (,$(wildcard $(LIGHTSTEP_REPO_ROOT)/go/src/github.com/lightstep/common-go/crouton.thrift))
+lightstep_thrift/constants.go:
+else
+# LightStep-specific: rebuilds the LightStep thrift protocol files.
+# Assumes the command is run within the LightStep development
+# environment (LIGHTSTEP_REPO_ROOT is set).
+lightstep_thrift/constants.go: $(LIGHTSTEP_REPO_ROOT)/go/src/github.com/lightstep/common-go/crouton.thrift
+ docker run --rm -v "$(LIGHTSTEP_REPO_ROOT)/go/src/github.com/lightstep/common-go:/data" -v "$(PWD):/out" thrift:0.9.2 \
+ thrift --gen go:package_prefix='github.com/lightstep/lightstep-tracer-go/',thrift_import='github.com/lightstep/lightstep-tracer-go/thrift_0_9_2/lib/go/thrift' -out /out /data/crouton.thrift
+ rm -rf lightstep_thrift/reporting_service-remote
+endif
+
+lightstepfakes/fake_recorder.go: options.go
+ $(call generate_fake,lightstepfakes/fake_recorder.go,options.go,SpanRecorder)
+
+lightstep_thrift/lightstep_thriftfakes/fake_reporting_service.go: lightstep_thrift/reportingservice.go
+ $(call generate_fake,lightstep_thrift/lightstep_thriftfakes/fake_reporting_service.go,lightstep_thrift/reportingservice.go,ReportingService)
+
+collectorpb/collectorpbfakes/fake_collector_service_client.go: collectorpb/collector.pb.go
+ $(call generate_fake,collectorpb/collectorpbfakes/fake_collector_service_client.go,collectorpb/collector.pb.go,CollectorServiceClient)
+
+# gRPC
+ifeq (,$(wildcard lightstep-tracer-common/collector.proto))
+collectorpb/collector.pb.go:
+else
+collectorpb/collector.pb.go: lightstep-tracer-common/collector.proto
+ docker run --rm -v $(shell pwd)/lightstep-tracer-common:/input:ro -v $(shell pwd)/collectorpb:/output \
+ lightstep/grpc-gateway:latest \
+ protoc -I/root/go/src/tmp/vendor/github.com/grpc-ecosystem/grpc-gateway/third_party/googleapis --go_out=plugins=grpc:/output --proto_path=/input /input/collector.proto
+endif
+
+# gRPC
+ifeq (,$(wildcard lightstep-tracer-common/collector.proto))
+lightsteppb/lightstep.pb.go:
+else
+lightsteppb/lightstep.pb.go: lightstep-tracer-common/lightstep.proto
+ docker run --rm -v $(shell pwd)/lightstep-tracer-common:/input:ro -v $(shell pwd)/lightsteppb:/output \
+ lightstep/protoc:latest \
+ protoc --go_out=plugins=grpc:/output --proto_path=/input /input/lightstep.proto
+endif
+
+test: lightstep_thrift/constants.go collectorpb/collector.pb.go lightsteppb/lightstep.pb.go \
+ collectorpb/collectorpbfakes/fake_collector_service_client.go \
+ lightstep_thrift/lightstep_thriftfakes/fake_reporting_service.go lightstepfakes/fake_recorder.go
+ifeq ($(DOCKER_PRESENT),)
+ $(error "docker not found. Please install from https://www.docker.com/")
+endif
+ docker run --rm -v $(LOCAL_GOPATH):/usergo lightstep/gobuild:latest \
+ ginkgo -race -p /usergo/src/github.com/lightstep/lightstep-tracer-go
+ bash -c "! git grep -q '[g]ithub.com/golang/glog'"
+
+build: lightstep_thrift/constants.go collectorpb/collector.pb.go lightsteppb/lightstep.pb.go \
+ collectorpb/collectorpbfakes/fake_collector_service_client.go version.go \
+ lightstep_thrift/lightstep_thriftfakes/fake_reporting_service.go lightstepfakes/fake_recorder.go
+ifeq ($(DOCKER_PRESENT),)
+ $(error "docker not found. Please install from https://www.docker.com/")
+endif
+ ${GO} build github.com/lightstep/lightstep-tracer-go
+
+# When releasing significant changes, make sure to update the semantic
+# version number in `./VERSION`, merge changes, then run `make release_tag`.
+version.go: VERSION
+ ./tag_version.sh
+
+release_tag:
+ git tag -a v`cat ./VERSION`
+ git push origin v`cat ./VERSION`
diff --git a/vendor/github.com/lightstep/lightstep-tracer-go/README.md b/vendor/github.com/lightstep/lightstep-tracer-go/README.md
new file mode 100644
index 000000000..6617e6871
--- /dev/null
+++ b/vendor/github.com/lightstep/lightstep-tracer-go/README.md
@@ -0,0 +1,116 @@
+# lightstep-tracer-go
+
+[![Circle CI](https://circleci.com/gh/lightstep/lightstep-tracer-go.svg?style=shield)](https://circleci.com/gh/lightstep/lightstep-tracer-go)
+[![MIT license](http://img.shields.io/badge/license-MIT-blue.svg)](http://opensource.org/licenses/MIT)
+[![GoDoc](https://godoc.org/github.com/lightstep/lightstep-tracer-go?status.svg)](https://godoc.org/github.com/lightstep/lightstep-tracer-go)
+
+The LightStep distributed tracing library for Go.
+
+## Installation
+
+```
+$ go get 'github.com/lightstep/lightstep-tracer-go'
+```
+
+## API Documentation
+
+Godoc: https://godoc.org/github.com/lightstep/lightstep-tracer-go
+
+## Initialization: Starting a new tracer
+To initialize a tracer, configure it with a valid Access Token and optional tuning parameters. Register the tracer as the OpenTracing global tracer so that it will become available to your installed intstrumentations libraries.
+
+```go
+import (
+ "github.com/opentracing/opentracing-go"
+ "github.com/lightstep/lightstep-tracer-go"
+)
+
+func main() {
+ lightstepTracer := lightstep.NewTracer(lightstep.Options{
+ AccessToken: "YourAccessToken",
+ })
+
+ opentracing.SetGlobalTracer(lightstepTracer)
+}
+```
+
+## Instrumenting Code: Using the OpenTracing API
+
+All instrumentation should be done through the OpenTracing API, rather than using the lightstep tracer type directly. For API documentation and advice on instrumentation in general, see the opentracing godocs and the opentracing website.
+
+- https://godoc.org/github.com/opentracing/opentracing-go
+- http://opentracing.io
+
+## Flushing and Closing: Managing the tracer lifecycle
+
+As part of managaing your application lifecycle, the lightstep tracer extends the `opentracing.Tracer` interface with methods for manual flushing and closing. To access these methods, you can take the global tracer and typecast it to a `lightstep.Tracer`. As a convenience, the lightstep package provides static methods which perform the typecasting.
+
+```go
+import (
+ "context"
+ "github.com/opentracing/opentracing-go"
+ "github.com/lightstep/lightstep-tracer-go"
+)
+
+func shutdown(ctx context.Context) {
+ // access the running tracer
+ tracer := opentracing.GlobalTracer()
+
+ // typecast from opentracing.Tracer to lightstep.Tracer
+ lsTracer, ok := tracer.(lightstep.Tracer)
+ if (!ok) {
+ return
+ }
+ lsTracer.Close(ctx)
+
+ // or use static methods
+ lightstep.Close(ctx, tracer)
+}
+```
+
+## Event Handling: Observing the LightStep tracer
+In order to connect diagnostic information from the lightstep tracer into an application's logging and metrics systems, inject an event handler using the `OnEvent` static method. Events may be typecast to check for errors or specific events such as status reports.
+
+```go
+import (
+ "example/logger"
+ "example/metrics"
+ "github.com/lightstep/lightstep-tracer-go"
+)
+
+logAndMetricsHandler := func(event lightstep.Event){
+ switch event := event.(type) {
+ case EventStatusReport:
+ metrics.Count("tracer.dropped_spans", event.DroppedSpans())
+ case ErrorEvent:
+ logger.Error("LS Tracer error: %s", event)
+ default:
+ logger.Info("LS Tracer info: %s", event)
+ }
+}
+
+func main() {
+ // setup event handler first to catch startup errors
+ lightstep.SetGlobalEventHandler(logAndMetricsHandler)
+
+ lightstepTracer := lightstep.NewTracer(lightstep.Options{
+ AccessToken: "YourAccessToken",
+ })
+
+ opentracing.SetGlobalTracer(lightstepTracer)
+}
+```
+
+Event handlers will receive events from any active tracers, as well as errors in static functions. It is suggested that you set up event handling before initializing your tracer to catch any errors on initialization.
+
+## Advanced Configuration: Transport and Serialization Protocols
+
+By default, the tracer will send information to LightStep using GRPC and Protocol Buffers which is the recommended configuration. If there are no specific transport protocol needs you have, there is no need to change this default.
+
+There are three total options for transport protocols:
+
+- [Protocol Buffers](https://developers.google.com/protocol-buffers/) over [GRPC](https://grpc.io/) - The recommended, default, and most performant solution.
+- [Thrift](https://thrift.apache.org/) over HTTP - A legacy implementation not recommended for new deployments.
+- \[ EXPERIMENTAL \] [Protocol Buffers](https://developers.google.com/protocol-buffers/) over HTTP - New transport protocol supported for use cases where GRPC isn't an option. In order to enable HTTP you will need to configure the LightStep collectors receiving the data to accept HTTP traffic. Reach out to LightStep for support in this.
+
+You can configure which transport protocol the tracer uses using the `UseGRPC`, `UseThrift`, and `UseHttp` flags in the options. \ No newline at end of file
diff --git a/vendor/github.com/lightstep/lightstep-tracer-go/VERSION b/vendor/github.com/lightstep/lightstep-tracer-go/VERSION
new file mode 100644
index 000000000..c61939452
--- /dev/null
+++ b/vendor/github.com/lightstep/lightstep-tracer-go/VERSION
@@ -0,0 +1 @@
+0.15.6
diff --git a/vendor/github.com/lightstep/lightstep-tracer-go/collector_client.go b/vendor/github.com/lightstep/lightstep-tracer-go/collector_client.go
new file mode 100644
index 000000000..b81e70f66
--- /dev/null
+++ b/vendor/github.com/lightstep/lightstep-tracer-go/collector_client.go
@@ -0,0 +1,55 @@
+package lightstep
+
+import (
+ "context"
+ "io"
+ "net/http"
+
+ cpb "github.com/lightstep/lightstep-tracer-go/collectorpb"
+ "github.com/lightstep/lightstep-tracer-go/lightstep_thrift"
+)
+
+// Connection describes a closable connection. Exposed for testing.
+type Connection interface {
+ io.Closer
+}
+
+// ConnectorFactory is for testing purposes.
+type ConnectorFactory func() (interface{}, Connection, error)
+
+// collectorResponse encapsulates internal thrift/grpc responses.
+type collectorResponse interface {
+ GetErrors() []string
+ Disable() bool
+}
+
+type reportRequest struct {
+ thriftRequest *lightstep_thrift.ReportRequest
+ protoRequest *cpb.ReportRequest
+ httpRequest *http.Request
+}
+
+// collectorClient encapsulates internal thrift/grpc transports.
+type collectorClient interface {
+ Report(context.Context, reportRequest) (collectorResponse, error)
+ Translate(context.Context, *reportBuffer) (reportRequest, error)
+ ConnectClient() (Connection, error)
+ ShouldReconnect() bool
+}
+
+func newCollectorClient(opts Options, reporterID uint64, attributes map[string]string) (collectorClient, error) {
+ if opts.UseThrift {
+ return newThriftCollectorClient(opts, reporterID, attributes), nil
+ }
+
+ if opts.UseHttp {
+ return newHTTPCollectorClient(opts, reporterID, attributes)
+ }
+
+ if opts.UseGRPC {
+ return newGrpcCollectorClient(opts, reporterID, attributes), nil
+ }
+
+ // No transport specified, defaulting to GRPC
+ return newGrpcCollectorClient(opts, reporterID, attributes), nil
+}
diff --git a/vendor/github.com/lightstep/lightstep-tracer-go/collector_client_grpc.go b/vendor/github.com/lightstep/lightstep-tracer-go/collector_client_grpc.go
new file mode 100644
index 000000000..5b6f88508
--- /dev/null
+++ b/vendor/github.com/lightstep/lightstep-tracer-go/collector_client_grpc.go
@@ -0,0 +1,134 @@
+package lightstep
+
+import (
+ "context"
+ "fmt"
+ "reflect"
+ "time"
+
+ "google.golang.org/grpc"
+ "google.golang.org/grpc/credentials"
+
+ // N.B.(jmacd): Do not use google.golang.org/glog in this package.
+ cpb "github.com/lightstep/lightstep-tracer-go/collectorpb"
+)
+
+const (
+ spansDropped = "spans.dropped"
+ logEncoderErrors = "log_encoder.errors"
+)
+
+var (
+ intType = reflect.TypeOf(int64(0))
+)
+
+// grpcCollectorClient specifies how to send reports back to a LightStep
+// collector via grpc.
+type grpcCollectorClient struct {
+ // auth and runtime information
+ attributes map[string]string
+ reporterID uint64
+
+ // accessToken is the access token used for explicit trace collection requests.
+ accessToken string
+ maxReportingPeriod time.Duration // set by GrpcOptions.MaxReportingPeriod
+ reconnectPeriod time.Duration // set by GrpcOptions.ReconnectPeriod
+ reportingTimeout time.Duration // set by GrpcOptions.ReportTimeout
+
+ // Remote service that will receive reports.
+ address string
+ grpcClient cpb.CollectorServiceClient
+ connTimestamp time.Time
+ dialOptions []grpc.DialOption
+
+ // converters
+ converter *protoConverter
+
+ // For testing purposes only
+ grpcConnectorFactory ConnectorFactory
+}
+
+func newGrpcCollectorClient(opts Options, reporterID uint64, attributes map[string]string) *grpcCollectorClient {
+ rec := &grpcCollectorClient{
+ attributes: attributes,
+ reporterID: reporterID,
+ accessToken: opts.AccessToken,
+ maxReportingPeriod: opts.ReportingPeriod,
+ reconnectPeriod: opts.ReconnectPeriod,
+ reportingTimeout: opts.ReportTimeout,
+ dialOptions: opts.DialOptions,
+ converter: newProtoConverter(opts),
+ grpcConnectorFactory: opts.ConnFactory,
+ }
+
+ if len(opts.Collector.Scheme) > 0 {
+ rec.address = opts.Collector.urlWithoutPath()
+ } else {
+ rec.address = opts.Collector.SocketAddress()
+ }
+
+ rec.dialOptions = append(rec.dialOptions, grpc.WithDefaultCallOptions(grpc.MaxCallSendMsgSize(opts.GRPCMaxCallSendMsgSizeBytes)))
+ if opts.Collector.Plaintext {
+ rec.dialOptions = append(rec.dialOptions, grpc.WithInsecure())
+ } else {
+ rec.dialOptions = append(rec.dialOptions, grpc.WithTransportCredentials(credentials.NewClientTLSFromCert(nil, "")))
+ }
+
+ return rec
+}
+
+func (client *grpcCollectorClient) ConnectClient() (Connection, error) {
+ now := time.Now()
+ var conn Connection
+ if client.grpcConnectorFactory != nil {
+ uncheckedClient, transport, err := client.grpcConnectorFactory()
+ if err != nil {
+ return nil, err
+ }
+
+ grpcClient, ok := uncheckedClient.(cpb.CollectorServiceClient)
+ if !ok {
+ return nil, fmt.Errorf("gRPC connector factory did not provide valid client")
+ }
+
+ conn = transport
+ client.grpcClient = grpcClient
+ } else {
+ transport, err := grpc.Dial(client.address, client.dialOptions...)
+ if err != nil {
+ return nil, err
+ }
+
+ conn = transport
+ client.grpcClient = cpb.NewCollectorServiceClient(transport)
+ }
+ client.connTimestamp = now
+ return conn, nil
+}
+
+func (client *grpcCollectorClient) ShouldReconnect() bool {
+ return time.Since(client.connTimestamp) > client.reconnectPeriod
+}
+
+func (client *grpcCollectorClient) Report(ctx context.Context, req reportRequest) (collectorResponse, error) {
+ if req.protoRequest == nil {
+ return nil, fmt.Errorf("protoRequest cannot be null")
+ }
+ resp, err := client.grpcClient.Report(ctx, req.protoRequest)
+ if err != nil {
+ return nil, err
+ }
+ return resp, nil
+}
+
+func (client *grpcCollectorClient) Translate(ctx context.Context, buffer *reportBuffer) (reportRequest, error) {
+ req := client.converter.toReportRequest(
+ client.reporterID,
+ client.attributes,
+ client.accessToken,
+ buffer,
+ )
+ return reportRequest{
+ protoRequest: req,
+ }, nil
+}
diff --git a/vendor/github.com/lightstep/lightstep-tracer-go/collector_client_http.go b/vendor/github.com/lightstep/lightstep-tracer-go/collector_client_http.go
new file mode 100644
index 000000000..08a1cf2d0
--- /dev/null
+++ b/vendor/github.com/lightstep/lightstep-tracer-go/collector_client_http.go
@@ -0,0 +1,188 @@
+package lightstep
+
+import (
+ "bytes"
+ "context"
+ "fmt"
+ "io/ioutil"
+ "net"
+ "net/http"
+ "net/url"
+ "time"
+
+ "github.com/golang/protobuf/proto"
+ "github.com/lightstep/lightstep-tracer-go/collectorpb"
+)
+
+var (
+ acceptHeader = http.CanonicalHeaderKey("Accept")
+ contentTypeHeader = http.CanonicalHeaderKey("Content-Type")
+)
+
+const (
+ collectorHTTPMethod = "POST"
+ collectorHTTPPath = "/api/v2/reports"
+ protoContentType = "application/octet-stream"
+)
+
+// grpcCollectorClient specifies how to send reports back to a LightStep
+// collector via grpc.
+type httpCollectorClient struct {
+ // auth and runtime information
+ reporterID uint64
+ accessToken string // accessToken is the access token used for explicit trace collection requests.
+ attributes map[string]string
+
+ reportTimeout time.Duration
+ reportingPeriod time.Duration
+
+ // Remote service that will receive reports.
+ url *url.URL
+ client *http.Client
+
+ // converters
+ converter *protoConverter
+}
+
+type transportCloser struct {
+ *http.Transport
+}
+
+func (closer transportCloser) Close() error {
+ closer.CloseIdleConnections()
+ return nil
+}
+
+func newHTTPCollectorClient(
+ opts Options,
+ reporterID uint64,
+ attributes map[string]string,
+) (*httpCollectorClient, error) {
+ url, err := url.Parse(opts.Collector.URL())
+ if err != nil {
+ fmt.Println("collector config does not produce valid url", err)
+ return nil, err
+ }
+ url.Path = collectorHTTPPath
+
+ return &httpCollectorClient{
+ reporterID: reporterID,
+ accessToken: opts.AccessToken,
+ attributes: attributes,
+ reportTimeout: opts.ReportTimeout,
+ reportingPeriod: opts.ReportingPeriod,
+ url: url,
+ converter: newProtoConverter(opts),
+ }, nil
+}
+
+func (client *httpCollectorClient) ConnectClient() (Connection, error) {
+ // Use a transport independent from http.DefaultTransport to provide sane
+ // defaults that make sense in the context of the lightstep client. The
+ // differences are mostly on setting timeouts based on the report timeout
+ // and period.
+ transport := &http.Transport{
+ Proxy: http.ProxyFromEnvironment,
+ DialContext: (&net.Dialer{
+ Timeout: client.reportTimeout / 2,
+ DualStack: true,
+ }).DialContext,
+ // The collector responses are very small, there is no point asking for
+ // a compressed payload, explicitly disabling it.
+ DisableCompression: true,
+ IdleConnTimeout: 2 * client.reportingPeriod,
+ TLSHandshakeTimeout: client.reportTimeout / 2,
+ ResponseHeaderTimeout: client.reportTimeout,
+ ExpectContinueTimeout: client.reportTimeout,
+ MaxResponseHeaderBytes: 64 * 1024, // 64 KB, just a safeguard
+ }
+
+ client.client = &http.Client{
+ Transport: transport,
+ Timeout: client.reportTimeout,
+ }
+
+ return transportCloser{transport}, nil
+}
+
+func (client *httpCollectorClient) ShouldReconnect() bool {
+ // http.Transport will handle connection reuse under the hood
+ return false
+}
+
+func (client *httpCollectorClient) Report(context context.Context, req reportRequest) (collectorResponse, error) {
+ if req.httpRequest == nil {
+ return nil, fmt.Errorf("httpRequest cannot be null")
+ }
+
+ httpResponse, err := client.client.Do(req.httpRequest.WithContext(context))
+ if err != nil {
+ return nil, err
+ }
+ defer httpResponse.Body.Close()
+
+ response, err := client.toResponse(httpResponse)
+ if err != nil {
+ return nil, err
+ }
+
+ return response, nil
+}
+
+func (client *httpCollectorClient) Translate(ctx context.Context, buffer *reportBuffer) (reportRequest, error) {
+
+ httpRequest, err := client.toRequest(ctx, buffer)
+ if err != nil {
+ return reportRequest{}, err
+ }
+ return reportRequest{
+ httpRequest: httpRequest,
+ }, nil
+}
+
+func (client *httpCollectorClient) toRequest(
+ context context.Context,
+ buffer *reportBuffer,
+) (*http.Request, error) {
+ protoRequest := client.converter.toReportRequest(
+ client.reporterID,
+ client.attributes,
+ client.accessToken,
+ buffer,
+ )
+
+ buf, err := proto.Marshal(protoRequest)
+ if err != nil {
+ return nil, err
+ }
+
+ requestBody := bytes.NewReader(buf)
+
+ request, err := http.NewRequest(collectorHTTPMethod, client.url.String(), requestBody)
+ if err != nil {
+ return nil, err
+ }
+ request = request.WithContext(context)
+ request.Header.Set(contentTypeHeader, protoContentType)
+ request.Header.Set(acceptHeader, protoContentType)
+
+ return request, nil
+}
+
+func (client *httpCollectorClient) toResponse(response *http.Response) (collectorResponse, error) {
+ if response.StatusCode != http.StatusOK {
+ return nil, fmt.Errorf("status code (%d) is not ok", response.StatusCode)
+ }
+
+ body, err := ioutil.ReadAll(response.Body)
+ if err != nil {
+ return nil, err
+ }
+
+ protoResponse := &collectorpb.ReportResponse{}
+ if err := proto.Unmarshal(body, protoResponse); err != nil {
+ return nil, err
+ }
+
+ return protoResponse, nil
+}
diff --git a/vendor/github.com/lightstep/lightstep-tracer-go/collector_client_thrift.go b/vendor/github.com/lightstep/lightstep-tracer-go/collector_client_thrift.go
new file mode 100644
index 000000000..896c778f3
--- /dev/null
+++ b/vendor/github.com/lightstep/lightstep-tracer-go/collector_client_thrift.go
@@ -0,0 +1,201 @@
+package lightstep
+
+import (
+ "context"
+ "fmt"
+ "strconv"
+ "strings"
+ "time"
+
+ "github.com/lightstep/lightstep-tracer-go/lightstep_thrift"
+ "github.com/lightstep/thrift/lib/go/thrift"
+)
+
+// thriftCollectorClient specifies how to send reports back to a LightStep
+// collector via thrift
+type thriftCollectorClient struct {
+ // auth and runtime information
+ auth *lightstep_thrift.Auth
+ attributes map[string]string
+ startTime time.Time
+ reporterID uint64
+
+ maxReportingPeriod time.Duration
+ // Remote service that will receive reports
+ thriftClient lightstep_thrift.ReportingService
+
+ // apiURL is the base URL of the LightStep web API, used for
+ // explicit trace collection requests.
+ collectorURL string
+
+ // AccessToken is the access token used for explicit trace
+ // collection requests.
+ AccessToken string
+
+ verbose bool
+
+ // flags replacement
+ maxLogMessageLen int
+ maxLogKeyLen int
+
+ reportTimeout time.Duration
+
+ thriftConnectorFactory ConnectorFactory
+}
+
+func newThriftCollectorClient(opts Options, guid uint64, attributes map[string]string) *thriftCollectorClient {
+ reportTimeout := 60 * time.Second
+ if opts.ReportTimeout > 0 {
+ reportTimeout = opts.ReportTimeout
+ }
+
+ now := time.Now()
+ rec := &thriftCollectorClient{
+ auth: &lightstep_thrift.Auth{
+ AccessToken: thrift.StringPtr(opts.AccessToken),
+ },
+ attributes: attributes,
+ startTime: now,
+ maxReportingPeriod: opts.ReportingPeriod,
+ verbose: opts.Verbose,
+ collectorURL: opts.Collector.URL(),
+ AccessToken: opts.AccessToken,
+ maxLogMessageLen: opts.MaxLogValueLen,
+ maxLogKeyLen: opts.MaxLogKeyLen,
+ reportTimeout: reportTimeout,
+ thriftConnectorFactory: opts.ConnFactory,
+ reporterID: guid,
+ }
+ return rec
+}
+
+func (client *thriftCollectorClient) ConnectClient() (Connection, error) {
+ var conn Connection
+
+ if client.thriftConnectorFactory != nil {
+ uncheckedClient, transport, err := client.thriftConnectorFactory()
+ if err != nil {
+ return nil, err
+ }
+
+ thriftClient, ok := uncheckedClient.(lightstep_thrift.ReportingService)
+ if !ok {
+ return nil, fmt.Errorf("thrift connector factory did not provide valid client")
+ }
+
+ conn = transport
+ client.thriftClient = thriftClient
+ } else {
+ transport, err := thrift.NewTHttpPostClient(client.collectorURL, client.reportTimeout)
+ if err != nil {
+ return nil, err
+ }
+
+ conn = transport
+ client.thriftClient = lightstep_thrift.NewReportingServiceClientFactory(
+ transport,
+ thrift.NewTBinaryProtocolFactoryDefault(),
+ )
+ }
+ return conn, nil
+}
+
+func (*thriftCollectorClient) ShouldReconnect() bool {
+ return false
+}
+
+func (client *thriftCollectorClient) Report(_ context.Context, req reportRequest) (collectorResponse, error) {
+ if req.thriftRequest == nil {
+ return nil, fmt.Errorf("thriftRequest cannot be null")
+ }
+ resp, err := client.thriftClient.Report(client.auth, req.thriftRequest)
+ if err != nil {
+ return nil, err
+ }
+
+ return resp, err
+}
+
+func (client *thriftCollectorClient) Translate(_ context.Context, buffer *reportBuffer) (reportRequest, error) {
+ rawSpans := buffer.rawSpans
+ // Convert them to thrift.
+ recs := make([]*lightstep_thrift.SpanRecord, len(rawSpans))
+ // TODO: could pool lightstep_thrift.SpanRecords
+ for i, raw := range rawSpans {
+ var joinIds []*lightstep_thrift.TraceJoinId
+ var attributes []*lightstep_thrift.KeyValue
+ for key, value := range raw.Tags {
+ // Note: the gRPC tracer uses Sprintf("%#v") for non-scalar non-string
+ // values, differs from the treatment here:
+ if strings.HasPrefix(key, "join:") {
+ joinIds = append(joinIds, &lightstep_thrift.TraceJoinId{TraceKey: key, Value: fmt.Sprint(value)})
+ } else {
+ attributes = append(attributes, &lightstep_thrift.KeyValue{Key: key, Value: fmt.Sprint(value)})
+ }
+ }
+ logs := make([]*lightstep_thrift.LogRecord, len(raw.Logs))
+ for j, log := range raw.Logs {
+ thriftLogRecord := &lightstep_thrift.LogRecord{
+ TimestampMicros: thrift.Int64Ptr(log.Timestamp.UnixNano() / 1000),
+ }
+ // In the deprecated thrift case, we can reuse a single "field"
+ // encoder across all of the N log fields.
+ lfe := thriftLogFieldEncoder{thriftLogRecord, client}
+ for _, f := range log.Fields {
+ f.Marshal(&lfe)
+ }
+ logs[j] = thriftLogRecord
+ }
+
+ // TODO implement baggage
+ if raw.ParentSpanID != 0 {
+ attributes = append(attributes, &lightstep_thrift.KeyValue{Key: ParentSpanGUIDKey,
+ Value: strconv.FormatUint(raw.ParentSpanID, 16)})
+ }
+
+ recs[i] = &lightstep_thrift.SpanRecord{
+ SpanGuid: thrift.StringPtr(strconv.FormatUint(raw.Context.SpanID, 16)),
+ TraceGuid: thrift.StringPtr(strconv.FormatUint(raw.Context.TraceID, 16)),
+ SpanName: thrift.StringPtr(raw.Operation),
+ JoinIds: joinIds,
+ OldestMicros: thrift.Int64Ptr(raw.Start.UnixNano() / 1000),
+ YoungestMicros: thrift.Int64Ptr(raw.Start.Add(raw.Duration).UnixNano() / 1000),
+ Attributes: attributes,
+ LogRecords: logs,
+ }
+ }
+
+ metrics := lightstep_thrift.Metrics{
+ Counts: []*lightstep_thrift.MetricsSample{
+ &lightstep_thrift.MetricsSample{
+ Name: "spans.dropped",
+ Int64Value: &buffer.droppedSpanCount,
+ },
+ },
+ }
+
+ req := &lightstep_thrift.ReportRequest{
+ OldestMicros: thrift.Int64Ptr(buffer.reportEnd.UnixNano() / 1000),
+ YoungestMicros: thrift.Int64Ptr(buffer.reportStart.UnixNano() / 1000),
+ Runtime: client.thriftRuntime(),
+ SpanRecords: recs,
+ InternalMetrics: &metrics,
+ }
+ return reportRequest{
+ thriftRequest: req,
+ }, nil
+}
+
+// caller must hold r.lock
+func (client *thriftCollectorClient) thriftRuntime() *lightstep_thrift.Runtime {
+ guid := strconv.FormatUint(client.reporterID, 10)
+ runtimeAttrs := []*lightstep_thrift.KeyValue{}
+ for k, v := range client.attributes {
+ runtimeAttrs = append(runtimeAttrs, &lightstep_thrift.KeyValue{Key: k, Value: v})
+ }
+ return &lightstep_thrift.Runtime{
+ StartMicros: thrift.Int64Ptr(client.startTime.UnixNano() / 1000),
+ Attrs: runtimeAttrs,
+ Guid: &guid,
+ }
+}
diff --git a/vendor/github.com/lightstep/lightstep-tracer-go/collectorpb/collector.go b/vendor/github.com/lightstep/lightstep-tracer-go/collectorpb/collector.go
new file mode 100644
index 000000000..d419bd24c
--- /dev/null
+++ b/vendor/github.com/lightstep/lightstep-tracer-go/collectorpb/collector.go
@@ -0,0 +1,10 @@
+package collectorpb
+
+func (res *ReportResponse) Disable() bool {
+ for _, command := range res.GetCommands() {
+ if command.Disable {
+ return true
+ }
+ }
+ return false
+}
diff --git a/vendor/github.com/lightstep/lightstep-tracer-go/collectorpb/collector.pb.go b/vendor/github.com/lightstep/lightstep-tracer-go/collectorpb/collector.pb.go
new file mode 100644
index 000000000..6710c06ac
--- /dev/null
+++ b/vendor/github.com/lightstep/lightstep-tracer-go/collectorpb/collector.pb.go
@@ -0,0 +1,903 @@
+// Code generated by protoc-gen-go. DO NOT EDIT.
+// source: collector.proto
+
+/*
+Package collectorpb is a generated protocol buffer package.
+
+It is generated from these files:
+ collector.proto
+
+It has these top-level messages:
+ SpanContext
+ KeyValue
+ Log
+ Reference
+ Span
+ Reporter
+ MetricsSample
+ InternalMetrics
+ Auth
+ ReportRequest
+ Command
+ ReportResponse
+*/
+package collectorpb
+
+import proto "github.com/golang/protobuf/proto"
+import fmt "fmt"
+import math "math"
+import google_protobuf "github.com/golang/protobuf/ptypes/timestamp"
+import _ "google.golang.org/genproto/googleapis/api/annotations"
+
+import (
+ context "golang.org/x/net/context"
+ grpc "google.golang.org/grpc"
+)
+
+// Reference imports to suppress errors if they are not otherwise used.
+var _ = proto.Marshal
+var _ = fmt.Errorf
+var _ = math.Inf
+
+// This is a compile-time assertion to ensure that this generated file
+// is compatible with the proto package it is being compiled against.
+// A compilation error at this line likely means your copy of the
+// proto package needs to be updated.
+const _ = proto.ProtoPackageIsVersion2 // please upgrade the proto package
+
+type Reference_Relationship int32
+
+const (
+ Reference_CHILD_OF Reference_Relationship = 0
+ Reference_FOLLOWS_FROM Reference_Relationship = 1
+)
+
+var Reference_Relationship_name = map[int32]string{
+ 0: "CHILD_OF",
+ 1: "FOLLOWS_FROM",
+}
+var Reference_Relationship_value = map[string]int32{
+ "CHILD_OF": 0,
+ "FOLLOWS_FROM": 1,
+}
+
+func (x Reference_Relationship) String() string {
+ return proto.EnumName(Reference_Relationship_name, int32(x))
+}
+func (Reference_Relationship) EnumDescriptor() ([]byte, []int) { return fileDescriptor0, []int{3, 0} }
+
+type SpanContext struct {
+ TraceId uint64 `protobuf:"varint,1,opt,name=trace_id,json=traceId" json:"trace_id,omitempty"`
+ SpanId uint64 `protobuf:"varint,2,opt,name=span_id,json=spanId" json:"span_id,omitempty"`
+ Baggage map[string]string `protobuf:"bytes,3,rep,name=baggage" json:"baggage,omitempty" protobuf_key:"bytes,1,opt,name=key" protobuf_val:"bytes,2,opt,name=value"`
+}
+
+func (m *SpanContext) Reset() { *m = SpanContext{} }
+func (m *SpanContext) String() string { return proto.CompactTextString(m) }
+func (*SpanContext) ProtoMessage() {}
+func (*SpanContext) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{0} }
+
+func (m *SpanContext) GetTraceId() uint64 {
+ if m != nil {
+ return m.TraceId
+ }
+ return 0
+}
+
+func (m *SpanContext) GetSpanId() uint64 {
+ if m != nil {
+ return m.SpanId
+ }
+ return 0
+}
+
+func (m *SpanContext) GetBaggage() map[string]string {
+ if m != nil {
+ return m.Baggage
+ }
+ return nil
+}
+
+// Represent both tags and log fields.
+type KeyValue struct {
+ Key string `protobuf:"bytes,1,opt,name=key" json:"key,omitempty"`
+ // Types that are valid to be assigned to Value:
+ // *KeyValue_StringValue
+ // *KeyValue_IntValue
+ // *KeyValue_DoubleValue
+ // *KeyValue_BoolValue
+ // *KeyValue_JsonValue
+ Value isKeyValue_Value `protobuf_oneof:"value"`
+}
+
+func (m *KeyValue) Reset() { *m = KeyValue{} }
+func (m *KeyValue) String() string { return proto.CompactTextString(m) }
+func (*KeyValue) ProtoMessage() {}
+func (*KeyValue) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{1} }
+
+type isKeyValue_Value interface {
+ isKeyValue_Value()
+}
+
+type KeyValue_StringValue struct {
+ StringValue string `protobuf:"bytes,2,opt,name=string_value,json=stringValue,oneof"`
+}
+type KeyValue_IntValue struct {
+ IntValue int64 `protobuf:"varint,3,opt,name=int_value,json=intValue,oneof"`
+}
+type KeyValue_DoubleValue struct {
+ DoubleValue float64 `protobuf:"fixed64,4,opt,name=double_value,json=doubleValue,oneof"`
+}
+type KeyValue_BoolValue struct {
+ BoolValue bool `protobuf:"varint,5,opt,name=bool_value,json=boolValue,oneof"`
+}
+type KeyValue_JsonValue struct {
+ JsonValue string `protobuf:"bytes,6,opt,name=json_value,json=jsonValue,oneof"`
+}
+
+func (*KeyValue_StringValue) isKeyValue_Value() {}
+func (*KeyValue_IntValue) isKeyValue_Value() {}
+func (*KeyValue_DoubleValue) isKeyValue_Value() {}
+func (*KeyValue_BoolValue) isKeyValue_Value() {}
+func (*KeyValue_JsonValue) isKeyValue_Value() {}
+
+func (m *KeyValue) GetValue() isKeyValue_Value {
+ if m != nil {
+ return m.Value
+ }
+ return nil
+}
+
+func (m *KeyValue) GetKey() string {
+ if m != nil {
+ return m.Key
+ }
+ return ""
+}
+
+func (m *KeyValue) GetStringValue() string {
+ if x, ok := m.GetValue().(*KeyValue_StringValue); ok {
+ return x.StringValue
+ }
+ return ""
+}
+
+func (m *KeyValue) GetIntValue() int64 {
+ if x, ok := m.GetValue().(*KeyValue_IntValue); ok {
+ return x.IntValue
+ }
+ return 0
+}
+
+func (m *KeyValue) GetDoubleValue() float64 {
+ if x, ok := m.GetValue().(*KeyValue_DoubleValue); ok {
+ return x.DoubleValue
+ }
+ return 0
+}
+
+func (m *KeyValue) GetBoolValue() bool {
+ if x, ok := m.GetValue().(*KeyValue_BoolValue); ok {
+ return x.BoolValue
+ }
+ return false
+}
+
+func (m *KeyValue) GetJsonValue() string {
+ if x, ok := m.GetValue().(*KeyValue_JsonValue); ok {
+ return x.JsonValue
+ }
+ return ""
+}
+
+// XXX_OneofFuncs is for the internal use of the proto package.
+func (*KeyValue) XXX_OneofFuncs() (func(msg proto.Message, b *proto.Buffer) error, func(msg proto.Message, tag, wire int, b *proto.Buffer) (bool, error), func(msg proto.Message) (n int), []interface{}) {
+ return _KeyValue_OneofMarshaler, _KeyValue_OneofUnmarshaler, _KeyValue_OneofSizer, []interface{}{
+ (*KeyValue_StringValue)(nil),
+ (*KeyValue_IntValue)(nil),
+ (*KeyValue_DoubleValue)(nil),
+ (*KeyValue_BoolValue)(nil),
+ (*KeyValue_JsonValue)(nil),
+ }
+}
+
+func _KeyValue_OneofMarshaler(msg proto.Message, b *proto.Buffer) error {
+ m := msg.(*KeyValue)
+ // value
+ switch x := m.Value.(type) {
+ case *KeyValue_StringValue:
+ b.EncodeVarint(2<<3 | proto.WireBytes)
+ b.EncodeStringBytes(x.StringValue)
+ case *KeyValue_IntValue:
+ b.EncodeVarint(3<<3 | proto.WireVarint)
+ b.EncodeVarint(uint64(x.IntValue))
+ case *KeyValue_DoubleValue:
+ b.EncodeVarint(4<<3 | proto.WireFixed64)
+ b.EncodeFixed64(math.Float64bits(x.DoubleValue))
+ case *KeyValue_BoolValue:
+ t := uint64(0)
+ if x.BoolValue {
+ t = 1
+ }
+ b.EncodeVarint(5<<3 | proto.WireVarint)
+ b.EncodeVarint(t)
+ case *KeyValue_JsonValue:
+ b.EncodeVarint(6<<3 | proto.WireBytes)
+ b.EncodeStringBytes(x.JsonValue)
+ case nil:
+ default:
+ return fmt.Errorf("KeyValue.Value has unexpected type %T", x)
+ }
+ return nil
+}
+
+func _KeyValue_OneofUnmarshaler(msg proto.Message, tag, wire int, b *proto.Buffer) (bool, error) {
+ m := msg.(*KeyValue)
+ switch tag {
+ case 2: // value.string_value
+ if wire != proto.WireBytes {
+ return true, proto.ErrInternalBadWireType
+ }
+ x, err := b.DecodeStringBytes()
+ m.Value = &KeyValue_StringValue{x}
+ return true, err
+ case 3: // value.int_value
+ if wire != proto.WireVarint {
+ return true, proto.ErrInternalBadWireType
+ }
+ x, err := b.DecodeVarint()
+ m.Value = &KeyValue_IntValue{int64(x)}
+ return true, err
+ case 4: // value.double_value
+ if wire != proto.WireFixed64 {
+ return true, proto.ErrInternalBadWireType
+ }
+ x, err := b.DecodeFixed64()
+ m.Value = &KeyValue_DoubleValue{math.Float64frombits(x)}
+ return true, err
+ case 5: // value.bool_value
+ if wire != proto.WireVarint {
+ return true, proto.ErrInternalBadWireType
+ }
+ x, err := b.DecodeVarint()
+ m.Value = &KeyValue_BoolValue{x != 0}
+ return true, err
+ case 6: // value.json_value
+ if wire != proto.WireBytes {
+ return true, proto.ErrInternalBadWireType
+ }
+ x, err := b.DecodeStringBytes()
+ m.Value = &KeyValue_JsonValue{x}
+ return true, err
+ default:
+ return false, nil
+ }
+}
+
+func _KeyValue_OneofSizer(msg proto.Message) (n int) {
+ m := msg.(*KeyValue)
+ // value
+ switch x := m.Value.(type) {
+ case *KeyValue_StringValue:
+ n += proto.SizeVarint(2<<3 | proto.WireBytes)
+ n += proto.SizeVarint(uint64(len(x.StringValue)))
+ n += len(x.StringValue)
+ case *KeyValue_IntValue:
+ n += proto.SizeVarint(3<<3 | proto.WireVarint)
+ n += proto.SizeVarint(uint64(x.IntValue))
+ case *KeyValue_DoubleValue:
+ n += proto.SizeVarint(4<<3 | proto.WireFixed64)
+ n += 8
+ case *KeyValue_BoolValue:
+ n += proto.SizeVarint(5<<3 | proto.WireVarint)
+ n += 1
+ case *KeyValue_JsonValue:
+ n += proto.SizeVarint(6<<3 | proto.WireBytes)
+ n += proto.SizeVarint(uint64(len(x.JsonValue)))
+ n += len(x.JsonValue)
+ case nil:
+ default:
+ panic(fmt.Sprintf("proto: unexpected type %T in oneof", x))
+ }
+ return n
+}
+
+type Log struct {
+ Timestamp *google_protobuf.Timestamp `protobuf:"bytes,1,opt,name=timestamp" json:"timestamp,omitempty"`
+ Fields []*KeyValue `protobuf:"bytes,2,rep,name=fields" json:"fields,omitempty"`
+}
+
+func (m *Log) Reset() { *m = Log{} }
+func (m *Log) String() string { return proto.CompactTextString(m) }
+func (*Log) ProtoMessage() {}
+func (*Log) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{2} }
+
+func (m *Log) GetTimestamp() *google_protobuf.Timestamp {
+ if m != nil {
+ return m.Timestamp
+ }
+ return nil
+}
+
+func (m *Log) GetFields() []*KeyValue {
+ if m != nil {
+ return m.Fields
+ }
+ return nil
+}
+
+type Reference struct {
+ Relationship Reference_Relationship `protobuf:"varint,1,opt,name=relationship,enum=lightstep.collector.Reference_Relationship" json:"relationship,omitempty"`
+ SpanContext *SpanContext `protobuf:"bytes,2,opt,name=span_context,json=spanContext" json:"span_context,omitempty"`
+}
+
+func (m *Reference) Reset() { *m = Reference{} }
+func (m *Reference) String() string { return proto.CompactTextString(m) }
+func (*Reference) ProtoMessage() {}
+func (*Reference) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{3} }
+
+func (m *Reference) GetRelationship() Reference_Relationship {
+ if m != nil {
+ return m.Relationship
+ }
+ return Reference_CHILD_OF
+}
+
+func (m *Reference) GetSpanContext() *SpanContext {
+ if m != nil {
+ return m.SpanContext
+ }
+ return nil
+}
+
+type Span struct {
+ SpanContext *SpanContext `protobuf:"bytes,1,opt,name=span_context,json=spanContext" json:"span_context,omitempty"`
+ OperationName string `protobuf:"bytes,2,opt,name=operation_name,json=operationName" json:"operation_name,omitempty"`
+ References []*Reference `protobuf:"bytes,3,rep,name=references" json:"references,omitempty"`
+ StartTimestamp *google_protobuf.Timestamp `protobuf:"bytes,4,opt,name=start_timestamp,json=startTimestamp" json:"start_timestamp,omitempty"`
+ DurationMicros uint64 `protobuf:"varint,5,opt,name=duration_micros,json=durationMicros" json:"duration_micros,omitempty"`
+ Tags []*KeyValue `protobuf:"bytes,6,rep,name=tags" json:"tags,omitempty"`
+ Logs []*Log `protobuf:"bytes,7,rep,name=logs" json:"logs,omitempty"`
+}
+
+func (m *Span) Reset() { *m = Span{} }
+func (m *Span) String() string { return proto.CompactTextString(m) }
+func (*Span) ProtoMessage() {}
+func (*Span) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{4} }
+
+func (m *Span) GetSpanContext() *SpanContext {
+ if m != nil {
+ return m.SpanContext
+ }
+ return nil
+}
+
+func (m *Span) GetOperationName() string {
+ if m != nil {
+ return m.OperationName
+ }
+ return ""
+}
+
+func (m *Span) GetReferences() []*Reference {
+ if m != nil {
+ return m.References
+ }
+ return nil
+}
+
+func (m *Span) GetStartTimestamp() *google_protobuf.Timestamp {
+ if m != nil {
+ return m.StartTimestamp
+ }
+ return nil
+}
+
+func (m *Span) GetDurationMicros() uint64 {
+ if m != nil {
+ return m.DurationMicros
+ }
+ return 0
+}
+
+func (m *Span) GetTags() []*KeyValue {
+ if m != nil {
+ return m.Tags
+ }
+ return nil
+}
+
+func (m *Span) GetLogs() []*Log {
+ if m != nil {
+ return m.Logs
+ }
+ return nil
+}
+
+type Reporter struct {
+ ReporterId uint64 `protobuf:"varint,1,opt,name=reporter_id,json=reporterId" json:"reporter_id,omitempty"`
+ Tags []*KeyValue `protobuf:"bytes,4,rep,name=tags" json:"tags,omitempty"`
+}
+
+func (m *Reporter) Reset() { *m = Reporter{} }
+func (m *Reporter) String() string { return proto.CompactTextString(m) }
+func (*Reporter) ProtoMessage() {}
+func (*Reporter) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{5} }
+
+func (m *Reporter) GetReporterId() uint64 {
+ if m != nil {
+ return m.ReporterId
+ }
+ return 0
+}
+
+func (m *Reporter) GetTags() []*KeyValue {
+ if m != nil {
+ return m.Tags
+ }
+ return nil
+}
+
+type MetricsSample struct {
+ Name string `protobuf:"bytes,1,opt,name=name" json:"name,omitempty"`
+ // Types that are valid to be assigned to Value:
+ // *MetricsSample_IntValue
+ // *MetricsSample_DoubleValue
+ Value isMetricsSample_Value `protobuf_oneof:"value"`
+}
+
+func (m *MetricsSample) Reset() { *m = MetricsSample{} }
+func (m *MetricsSample) String() string { return proto.CompactTextString(m) }
+func (*MetricsSample) ProtoMessage() {}
+func (*MetricsSample) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{6} }
+
+type isMetricsSample_Value interface {
+ isMetricsSample_Value()
+}
+
+type MetricsSample_IntValue struct {
+ IntValue int64 `protobuf:"varint,2,opt,name=int_value,json=intValue,oneof"`
+}
+type MetricsSample_DoubleValue struct {
+ DoubleValue float64 `protobuf:"fixed64,3,opt,name=double_value,json=doubleValue,oneof"`
+}
+
+func (*MetricsSample_IntValue) isMetricsSample_Value() {}
+func (*MetricsSample_DoubleValue) isMetricsSample_Value() {}
+
+func (m *MetricsSample) GetValue() isMetricsSample_Value {
+ if m != nil {
+ return m.Value
+ }
+ return nil
+}
+
+func (m *MetricsSample) GetName() string {
+ if m != nil {
+ return m.Name
+ }
+ return ""
+}
+
+func (m *MetricsSample) GetIntValue() int64 {
+ if x, ok := m.GetValue().(*MetricsSample_IntValue); ok {
+ return x.IntValue
+ }
+ return 0
+}
+
+func (m *MetricsSample) GetDoubleValue() float64 {
+ if x, ok := m.GetValue().(*MetricsSample_DoubleValue); ok {
+ return x.DoubleValue
+ }
+ return 0
+}
+
+// XXX_OneofFuncs is for the internal use of the proto package.
+func (*MetricsSample) XXX_OneofFuncs() (func(msg proto.Message, b *proto.Buffer) error, func(msg proto.Message, tag, wire int, b *proto.Buffer) (bool, error), func(msg proto.Message) (n int), []interface{}) {
+ return _MetricsSample_OneofMarshaler, _MetricsSample_OneofUnmarshaler, _MetricsSample_OneofSizer, []interface{}{
+ (*MetricsSample_IntValue)(nil),
+ (*MetricsSample_DoubleValue)(nil),
+ }
+}
+
+func _MetricsSample_OneofMarshaler(msg proto.Message, b *proto.Buffer) error {
+ m := msg.(*MetricsSample)
+ // value
+ switch x := m.Value.(type) {
+ case *MetricsSample_IntValue:
+ b.EncodeVarint(2<<3 | proto.WireVarint)
+ b.EncodeVarint(uint64(x.IntValue))
+ case *MetricsSample_DoubleValue:
+ b.EncodeVarint(3<<3 | proto.WireFixed64)
+ b.EncodeFixed64(math.Float64bits(x.DoubleValue))
+ case nil:
+ default:
+ return fmt.Errorf("MetricsSample.Value has unexpected type %T", x)
+ }
+ return nil
+}
+
+func _MetricsSample_OneofUnmarshaler(msg proto.Message, tag, wire int, b *proto.Buffer) (bool, error) {
+ m := msg.(*MetricsSample)
+ switch tag {
+ case 2: // value.int_value
+ if wire != proto.WireVarint {
+ return true, proto.ErrInternalBadWireType
+ }
+ x, err := b.DecodeVarint()
+ m.Value = &MetricsSample_IntValue{int64(x)}
+ return true, err
+ case 3: // value.double_value
+ if wire != proto.WireFixed64 {
+ return true, proto.ErrInternalBadWireType
+ }
+ x, err := b.DecodeFixed64()
+ m.Value = &MetricsSample_DoubleValue{math.Float64frombits(x)}
+ return true, err
+ default:
+ return false, nil
+ }
+}
+
+func _MetricsSample_OneofSizer(msg proto.Message) (n int) {
+ m := msg.(*MetricsSample)
+ // value
+ switch x := m.Value.(type) {
+ case *MetricsSample_IntValue:
+ n += proto.SizeVarint(2<<3 | proto.WireVarint)
+ n += proto.SizeVarint(uint64(x.IntValue))
+ case *MetricsSample_DoubleValue:
+ n += proto.SizeVarint(3<<3 | proto.WireFixed64)
+ n += 8
+ case nil:
+ default:
+ panic(fmt.Sprintf("proto: unexpected type %T in oneof", x))
+ }
+ return n
+}
+
+type InternalMetrics struct {
+ StartTimestamp *google_protobuf.Timestamp `protobuf:"bytes,1,opt,name=start_timestamp,json=startTimestamp" json:"start_timestamp,omitempty"`
+ DurationMicros uint64 `protobuf:"varint,2,opt,name=duration_micros,json=durationMicros" json:"duration_micros,omitempty"`
+ Logs []*Log `protobuf:"bytes,3,rep,name=logs" json:"logs,omitempty"`
+ Counts []*MetricsSample `protobuf:"bytes,4,rep,name=counts" json:"counts,omitempty"`
+ Gauges []*MetricsSample `protobuf:"bytes,5,rep,name=gauges" json:"gauges,omitempty"`
+}
+
+func (m *InternalMetrics) Reset() { *m = InternalMetrics{} }
+func (m *InternalMetrics) String() string { return proto.CompactTextString(m) }
+func (*InternalMetrics) ProtoMessage() {}
+func (*InternalMetrics) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{7} }
+
+func (m *InternalMetrics) GetStartTimestamp() *google_protobuf.Timestamp {
+ if m != nil {
+ return m.StartTimestamp
+ }
+ return nil
+}
+
+func (m *InternalMetrics) GetDurationMicros() uint64 {
+ if m != nil {
+ return m.DurationMicros
+ }
+ return 0
+}
+
+func (m *InternalMetrics) GetLogs() []*Log {
+ if m != nil {
+ return m.Logs
+ }
+ return nil
+}
+
+func (m *InternalMetrics) GetCounts() []*MetricsSample {
+ if m != nil {
+ return m.Counts
+ }
+ return nil
+}
+
+func (m *InternalMetrics) GetGauges() []*MetricsSample {
+ if m != nil {
+ return m.Gauges
+ }
+ return nil
+}
+
+type Auth struct {
+ AccessToken string `protobuf:"bytes,1,opt,name=access_token,json=accessToken" json:"access_token,omitempty"`
+}
+
+func (m *Auth) Reset() { *m = Auth{} }
+func (m *Auth) String() string { return proto.CompactTextString(m) }
+func (*Auth) ProtoMessage() {}
+func (*Auth) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{8} }
+
+func (m *Auth) GetAccessToken() string {
+ if m != nil {
+ return m.AccessToken
+ }
+ return ""
+}
+
+type ReportRequest struct {
+ Reporter *Reporter `protobuf:"bytes,1,opt,name=reporter" json:"reporter,omitempty"`
+ Auth *Auth `protobuf:"bytes,2,opt,name=auth" json:"auth,omitempty"`
+ Spans []*Span `protobuf:"bytes,3,rep,name=spans" json:"spans,omitempty"`
+ TimestampOffsetMicros int64 `protobuf:"varint,5,opt,name=timestamp_offset_micros,json=timestampOffsetMicros" json:"timestamp_offset_micros,omitempty"`
+ InternalMetrics *InternalMetrics `protobuf:"bytes,6,opt,name=internal_metrics,json=internalMetrics" json:"internal_metrics,omitempty"`
+}
+
+func (m *ReportRequest) Reset() { *m = ReportRequest{} }
+func (m *ReportRequest) String() string { return proto.CompactTextString(m) }
+func (*ReportRequest) ProtoMessage() {}
+func (*ReportRequest) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{9} }
+
+func (m *ReportRequest) GetReporter() *Reporter {
+ if m != nil {
+ return m.Reporter
+ }
+ return nil
+}
+
+func (m *ReportRequest) GetAuth() *Auth {
+ if m != nil {
+ return m.Auth
+ }
+ return nil
+}
+
+func (m *ReportRequest) GetSpans() []*Span {
+ if m != nil {
+ return m.Spans
+ }
+ return nil
+}
+
+func (m *ReportRequest) GetTimestampOffsetMicros() int64 {
+ if m != nil {
+ return m.TimestampOffsetMicros
+ }
+ return 0
+}
+
+func (m *ReportRequest) GetInternalMetrics() *InternalMetrics {
+ if m != nil {
+ return m.InternalMetrics
+ }
+ return nil
+}
+
+type Command struct {
+ Disable bool `protobuf:"varint,1,opt,name=disable" json:"disable,omitempty"`
+}
+
+func (m *Command) Reset() { *m = Command{} }
+func (m *Command) String() string { return proto.CompactTextString(m) }
+func (*Command) ProtoMessage() {}
+func (*Command) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{10} }
+
+func (m *Command) GetDisable() bool {
+ if m != nil {
+ return m.Disable
+ }
+ return false
+}
+
+type ReportResponse struct {
+ Commands []*Command `protobuf:"bytes,1,rep,name=commands" json:"commands,omitempty"`
+ ReceiveTimestamp *google_protobuf.Timestamp `protobuf:"bytes,2,opt,name=receive_timestamp,json=receiveTimestamp" json:"receive_timestamp,omitempty"`
+ TransmitTimestamp *google_protobuf.Timestamp `protobuf:"bytes,3,opt,name=transmit_timestamp,json=transmitTimestamp" json:"transmit_timestamp,omitempty"`
+ Errors []string `protobuf:"bytes,4,rep,name=errors" json:"errors,omitempty"`
+ Warnings []string `protobuf:"bytes,5,rep,name=warnings" json:"warnings,omitempty"`
+ Infos []string `protobuf:"bytes,6,rep,name=infos" json:"infos,omitempty"`
+}
+
+func (m *ReportResponse) Reset() { *m = ReportResponse{} }
+func (m *ReportResponse) String() string { return proto.CompactTextString(m) }
+func (*ReportResponse) ProtoMessage() {}
+func (*ReportResponse) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{11} }
+
+func (m *ReportResponse) GetCommands() []*Command {
+ if m != nil {
+ return m.Commands
+ }
+ return nil
+}
+
+func (m *ReportResponse) GetReceiveTimestamp() *google_protobuf.Timestamp {
+ if m != nil {
+ return m.ReceiveTimestamp
+ }
+ return nil
+}
+
+func (m *ReportResponse) GetTransmitTimestamp() *google_protobuf.Timestamp {
+ if m != nil {
+ return m.TransmitTimestamp
+ }
+ return nil
+}
+
+func (m *ReportResponse) GetErrors() []string {
+ if m != nil {
+ return m.Errors
+ }
+ return nil
+}
+
+func (m *ReportResponse) GetWarnings() []string {
+ if m != nil {
+ return m.Warnings
+ }
+ return nil
+}
+
+func (m *ReportResponse) GetInfos() []string {
+ if m != nil {
+ return m.Infos
+ }
+ return nil
+}
+
+func init() {
+ proto.RegisterType((*SpanContext)(nil), "lightstep.collector.SpanContext")
+ proto.RegisterType((*KeyValue)(nil), "lightstep.collector.KeyValue")
+ proto.RegisterType((*Log)(nil), "lightstep.collector.Log")
+ proto.RegisterType((*Reference)(nil), "lightstep.collector.Reference")
+ proto.RegisterType((*Span)(nil), "lightstep.collector.Span")
+ proto.RegisterType((*Reporter)(nil), "lightstep.collector.Reporter")
+ proto.RegisterType((*MetricsSample)(nil), "lightstep.collector.MetricsSample")
+ proto.RegisterType((*InternalMetrics)(nil), "lightstep.collector.InternalMetrics")
+ proto.RegisterType((*Auth)(nil), "lightstep.collector.Auth")
+ proto.RegisterType((*ReportRequest)(nil), "lightstep.collector.ReportRequest")
+ proto.RegisterType((*Command)(nil), "lightstep.collector.Command")
+ proto.RegisterType((*ReportResponse)(nil), "lightstep.collector.ReportResponse")
+ proto.RegisterEnum("lightstep.collector.Reference_Relationship", Reference_Relationship_name, Reference_Relationship_value)
+}
+
+// Reference imports to suppress errors if they are not otherwise used.
+var _ context.Context
+var _ grpc.ClientConn
+
+// This is a compile-time assertion to ensure that this generated file
+// is compatible with the grpc package it is being compiled against.
+const _ = grpc.SupportPackageIsVersion4
+
+// Client API for CollectorService service
+
+type CollectorServiceClient interface {
+ Report(ctx context.Context, in *ReportRequest, opts ...grpc.CallOption) (*ReportResponse, error)
+}
+
+type collectorServiceClient struct {
+ cc *grpc.ClientConn
+}
+
+func NewCollectorServiceClient(cc *grpc.ClientConn) CollectorServiceClient {
+ return &collectorServiceClient{cc}
+}
+
+func (c *collectorServiceClient) Report(ctx context.Context, in *ReportRequest, opts ...grpc.CallOption) (*ReportResponse, error) {
+ out := new(ReportResponse)
+ err := grpc.Invoke(ctx, "/lightstep.collector.CollectorService/Report", in, out, c.cc, opts...)
+ if err != nil {
+ return nil, err
+ }
+ return out, nil
+}
+
+// Server API for CollectorService service
+
+type CollectorServiceServer interface {
+ Report(context.Context, *ReportRequest) (*ReportResponse, error)
+}
+
+func RegisterCollectorServiceServer(s *grpc.Server, srv CollectorServiceServer) {
+ s.RegisterService(&_CollectorService_serviceDesc, srv)
+}
+
+func _CollectorService_Report_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) {
+ in := new(ReportRequest)
+ if err := dec(in); err != nil {
+ return nil, err
+ }
+ if interceptor == nil {
+ return srv.(CollectorServiceServer).Report(ctx, in)
+ }
+ info := &grpc.UnaryServerInfo{
+ Server: srv,
+ FullMethod: "/lightstep.collector.CollectorService/Report",
+ }
+ handler := func(ctx context.Context, req interface{}) (interface{}, error) {
+ return srv.(CollectorServiceServer).Report(ctx, req.(*ReportRequest))
+ }
+ return interceptor(ctx, in, info, handler)
+}
+
+var _CollectorService_serviceDesc = grpc.ServiceDesc{
+ ServiceName: "lightstep.collector.CollectorService",
+ HandlerType: (*CollectorServiceServer)(nil),
+ Methods: []grpc.MethodDesc{
+ {
+ MethodName: "Report",
+ Handler: _CollectorService_Report_Handler,
+ },
+ },
+ Streams: []grpc.StreamDesc{},
+ Metadata: "collector.proto",
+}
+
+func init() { proto.RegisterFile("collector.proto", fileDescriptor0) }
+
+var fileDescriptor0 = []byte{
+ // 1064 bytes of a gzipped FileDescriptorProto
+ 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xac, 0x56, 0xdf, 0x6e, 0x23, 0xb5,
+ 0x17, 0xee, 0x24, 0xb3, 0xf9, 0x73, 0x92, 0x6d, 0x52, 0xff, 0x7e, 0xb0, 0x69, 0xb4, 0xa5, 0x61,
+ 0x0a, 0xda, 0xf2, 0xa7, 0xa9, 0x36, 0x08, 0x54, 0x7a, 0x81, 0x44, 0x03, 0xdd, 0x46, 0xa4, 0x64,
+ 0xe5, 0xae, 0x40, 0xda, 0x0b, 0x22, 0x67, 0xe2, 0x4c, 0x87, 0x9d, 0xd8, 0x83, 0xed, 0x14, 0x7a,
+ 0x07, 0xbc, 0x02, 0xe2, 0x05, 0x90, 0x90, 0xb8, 0xe7, 0x1d, 0xb8, 0x06, 0xf1, 0x0a, 0x3c, 0x08,
+ 0x1a, 0xdb, 0x33, 0x49, 0x97, 0xd9, 0xb6, 0x42, 0xdc, 0xe5, 0x1c, 0x7f, 0x9f, 0x7d, 0x7c, 0xbe,
+ 0xef, 0x38, 0x03, 0x0d, 0x9f, 0x47, 0x11, 0xf5, 0x15, 0x17, 0xdd, 0x58, 0x70, 0xc5, 0xd1, 0xff,
+ 0xa2, 0x30, 0x38, 0x57, 0x52, 0xd1, 0xb8, 0x9b, 0x2d, 0xb5, 0xb7, 0x03, 0xce, 0x83, 0x88, 0xee,
+ 0x6b, 0xc8, 0x64, 0x31, 0xdb, 0x57, 0xe1, 0x9c, 0x4a, 0x45, 0xe6, 0xb1, 0x61, 0xb5, 0xef, 0x5b,
+ 0x00, 0x89, 0xc3, 0x7d, 0xc2, 0x18, 0x57, 0x44, 0x85, 0x9c, 0x49, 0xb3, 0xea, 0xfd, 0xe6, 0x40,
+ 0xed, 0x2c, 0x26, 0xac, 0xcf, 0x99, 0xa2, 0xdf, 0x28, 0xb4, 0x09, 0x15, 0x25, 0x88, 0x4f, 0xc7,
+ 0xe1, 0xb4, 0xe5, 0x74, 0x9c, 0x5d, 0x17, 0x97, 0x75, 0x3c, 0x98, 0xa2, 0x7b, 0x50, 0x96, 0x31,
+ 0x61, 0xc9, 0x4a, 0x41, 0xaf, 0x94, 0x92, 0x70, 0x30, 0x45, 0x8f, 0xa0, 0x3c, 0x21, 0x41, 0x40,
+ 0x02, 0xda, 0x2a, 0x76, 0x8a, 0xbb, 0xb5, 0xde, 0x5e, 0x37, 0xa7, 0xd2, 0xee, 0xca, 0x31, 0xdd,
+ 0x23, 0x83, 0xff, 0x98, 0x29, 0x71, 0x89, 0x53, 0x76, 0xfb, 0x10, 0xea, 0xab, 0x0b, 0xa8, 0x09,
+ 0xc5, 0x67, 0xf4, 0x52, 0xd7, 0x51, 0xc5, 0xc9, 0x4f, 0xf4, 0x7f, 0xb8, 0x73, 0x41, 0xa2, 0x05,
+ 0xd5, 0x15, 0x54, 0xb1, 0x09, 0x0e, 0x0b, 0x07, 0x8e, 0xf7, 0xbb, 0x03, 0x95, 0x4f, 0xe8, 0xe5,
+ 0x67, 0x49, 0x22, 0x87, 0xb8, 0x03, 0x75, 0xa9, 0x44, 0xc8, 0x82, 0xf1, 0x0a, 0xff, 0x64, 0x0d,
+ 0xd7, 0x4c, 0xd6, 0xd0, 0xb6, 0xa0, 0x1a, 0x32, 0x65, 0x11, 0xc5, 0x8e, 0xb3, 0x5b, 0x3c, 0x59,
+ 0xc3, 0x95, 0x90, 0x29, 0xb3, 0xbc, 0x03, 0xf5, 0x29, 0x5f, 0x4c, 0x22, 0x6a, 0x11, 0x6e, 0xc7,
+ 0xd9, 0x75, 0x92, 0x3d, 0x4c, 0xd6, 0x80, 0xb6, 0x01, 0x26, 0x9c, 0x47, 0x16, 0x72, 0xa7, 0xe3,
+ 0xec, 0x56, 0x4e, 0xd6, 0x70, 0x35, 0xc9, 0x65, 0x80, 0x2f, 0x25, 0x67, 0x16, 0x50, 0xb2, 0x75,
+ 0x54, 0x93, 0x9c, 0x06, 0x1c, 0x95, 0xed, 0x1d, 0xbd, 0x0b, 0x28, 0x0e, 0x79, 0x80, 0x0e, 0xa0,
+ 0x9a, 0x69, 0xaa, 0xaf, 0x54, 0xeb, 0xb5, 0xbb, 0x46, 0xd4, 0x6e, 0xaa, 0x7a, 0xf7, 0x49, 0x8a,
+ 0xc0, 0x4b, 0x30, 0x7a, 0x17, 0x4a, 0xb3, 0x90, 0x46, 0x53, 0xd9, 0x2a, 0x68, 0x5d, 0xb6, 0x72,
+ 0x75, 0x49, 0xbb, 0x86, 0x2d, 0xd8, 0xfb, 0xc3, 0x81, 0x2a, 0xa6, 0x33, 0x2a, 0x28, 0xf3, 0x29,
+ 0x1a, 0x41, 0x5d, 0xd0, 0xc8, 0x98, 0xe6, 0x3c, 0x34, 0x15, 0xac, 0xf7, 0xde, 0xca, 0xdd, 0x2a,
+ 0x63, 0x75, 0xf1, 0x0a, 0x05, 0x5f, 0xd9, 0x00, 0xf5, 0xa1, 0xae, 0x7d, 0xe4, 0x1b, 0x2f, 0x68,
+ 0x29, 0x6a, 0xbd, 0xce, 0x4d, 0x9e, 0xc1, 0x35, 0xb9, 0x0c, 0xbc, 0x2e, 0xd4, 0x57, 0x8f, 0x40,
+ 0x75, 0xa8, 0xf4, 0x4f, 0x06, 0xc3, 0x8f, 0xc6, 0xa3, 0xe3, 0xe6, 0x1a, 0x6a, 0x42, 0xfd, 0x78,
+ 0x34, 0x1c, 0x8e, 0x3e, 0x3f, 0x1b, 0x1f, 0xe3, 0xd1, 0x69, 0xd3, 0xf1, 0xbe, 0x2b, 0x82, 0x9b,
+ 0x6c, 0xf6, 0x8f, 0xd3, 0x9d, 0x7f, 0x71, 0x3a, 0x7a, 0x1d, 0xd6, 0x79, 0x4c, 0x85, 0x3e, 0x7e,
+ 0xcc, 0xc8, 0x3c, 0xf5, 0xe3, 0xdd, 0x2c, 0xfb, 0x29, 0x99, 0x53, 0xf4, 0x01, 0x80, 0x48, 0x3b,
+ 0x22, 0xed, 0x6c, 0xbc, 0x72, 0x7d, 0xe3, 0xf0, 0x0a, 0x03, 0xf5, 0xa1, 0x21, 0x15, 0x11, 0x6a,
+ 0xbc, 0xd4, 0xdf, 0xbd, 0x51, 0xff, 0x75, 0x4d, 0xc9, 0x62, 0xf4, 0x00, 0x1a, 0xd3, 0x85, 0x2d,
+ 0x75, 0x1e, 0xfa, 0x82, 0x4b, 0xed, 0x4a, 0x17, 0xaf, 0xa7, 0xe9, 0x53, 0x9d, 0x45, 0x0f, 0xc1,
+ 0x55, 0x24, 0x90, 0xad, 0xd2, 0x6d, 0xbc, 0xa2, 0xa1, 0xe8, 0x6d, 0x70, 0x23, 0x1e, 0xc8, 0x56,
+ 0x59, 0x53, 0x5a, 0xb9, 0x94, 0x21, 0x0f, 0xb0, 0x46, 0x79, 0x5f, 0x40, 0x05, 0xd3, 0x98, 0x0b,
+ 0x45, 0x05, 0xda, 0x86, 0x9a, 0xb0, 0xbf, 0x97, 0x4f, 0x0d, 0xa4, 0xa9, 0xc1, 0x34, 0xab, 0xc6,
+ 0xbd, 0x75, 0x35, 0x5e, 0x0c, 0x77, 0x4f, 0xa9, 0x12, 0xa1, 0x2f, 0xcf, 0xc8, 0x3c, 0x8e, 0x28,
+ 0x42, 0xe0, 0x6a, 0x71, 0xcc, 0x3b, 0xa0, 0x7f, 0x5f, 0x9d, 0xf1, 0xc2, 0x8d, 0x33, 0x5e, 0xcc,
+ 0x99, 0xf1, 0xe5, 0x84, 0xfe, 0x5c, 0x80, 0xc6, 0x80, 0x29, 0x2a, 0x18, 0x89, 0xec, 0xd1, 0x79,
+ 0xa2, 0x39, 0xff, 0x85, 0x68, 0x85, 0x5c, 0xd1, 0x52, 0x05, 0x8a, 0xb7, 0x51, 0x00, 0x1d, 0x42,
+ 0xc9, 0xe7, 0x0b, 0xa6, 0xd2, 0xb6, 0x7a, 0xb9, 0xf8, 0x2b, 0x4d, 0xc4, 0x96, 0x91, 0x70, 0x03,
+ 0xb2, 0x08, 0x68, 0x62, 0x9f, 0x5b, 0x73, 0x0d, 0xc3, 0x7b, 0x03, 0xdc, 0x0f, 0x17, 0xea, 0x1c,
+ 0xbd, 0x0a, 0x75, 0xe2, 0xfb, 0x54, 0xca, 0xb1, 0xe2, 0xcf, 0x28, 0xb3, 0xc2, 0xd4, 0x4c, 0xee,
+ 0x49, 0x92, 0xf2, 0x7e, 0x2d, 0xc0, 0x5d, 0xe3, 0x12, 0x4c, 0xbf, 0x5a, 0x50, 0xa9, 0xd0, 0xfb,
+ 0x50, 0x49, 0x7d, 0x61, 0x3b, 0xb9, 0xf5, 0x82, 0x19, 0x32, 0x20, 0x9c, 0xc1, 0xd1, 0x1e, 0xb8,
+ 0x64, 0xa1, 0xce, 0xed, 0x13, 0xb3, 0x99, 0x4b, 0x4b, 0x0a, 0xc3, 0x1a, 0x86, 0xf6, 0xe1, 0x4e,
+ 0x32, 0xe5, 0x69, 0x37, 0x37, 0x5f, 0xf8, 0x28, 0x60, 0x83, 0x43, 0xef, 0xc1, 0xbd, 0x4c, 0xe5,
+ 0x31, 0x9f, 0xcd, 0x24, 0x55, 0xab, 0x33, 0x56, 0xc4, 0x2f, 0x65, 0xcb, 0x23, 0xbd, 0x6a, 0x55,
+ 0x1b, 0x41, 0x33, 0xb4, 0xb6, 0x19, 0xcf, 0x4d, 0xc7, 0xf4, 0x3f, 0x41, 0xad, 0xf7, 0x5a, 0xee,
+ 0x99, 0xcf, 0x79, 0x0c, 0x37, 0xc2, 0xab, 0x09, 0x6f, 0x07, 0xca, 0x7d, 0x3e, 0x9f, 0x13, 0x36,
+ 0x45, 0x2d, 0x28, 0x4f, 0x43, 0x49, 0x26, 0x91, 0xf1, 0x7d, 0x05, 0xa7, 0xa1, 0xf7, 0x4b, 0x01,
+ 0xd6, 0xd3, 0xd6, 0xca, 0x98, 0x33, 0x49, 0xd1, 0x01, 0x54, 0x7c, 0xc3, 0x93, 0x2d, 0x47, 0x5f,
+ 0xfa, 0x7e, 0x6e, 0x01, 0x76, 0x73, 0x9c, 0xa1, 0xd1, 0x23, 0xd8, 0x10, 0xd4, 0xa7, 0xe1, 0x05,
+ 0x5d, 0x31, 0x7a, 0xe1, 0x46, 0xa3, 0x37, 0x2d, 0x69, 0x69, 0xf5, 0x01, 0x20, 0x25, 0x08, 0x93,
+ 0xf3, 0x70, 0x75, 0x64, 0x8a, 0x37, 0xee, 0xb4, 0x91, 0xb2, 0x96, 0x5b, 0xbd, 0x0c, 0x25, 0x2a,
+ 0x04, 0x17, 0xc6, 0xde, 0x55, 0x6c, 0x23, 0xd4, 0x86, 0xca, 0xd7, 0x44, 0xb0, 0x90, 0x05, 0xc6,
+ 0xbc, 0x55, 0x9c, 0xc5, 0xc9, 0x17, 0x45, 0xc8, 0x66, 0xdc, 0x3c, 0x7b, 0x55, 0x6c, 0x82, 0xde,
+ 0x8f, 0x0e, 0x34, 0xfb, 0xe9, 0xed, 0xcf, 0xa8, 0xb8, 0x08, 0x7d, 0x8a, 0xbe, 0x75, 0xa0, 0x64,
+ 0xfa, 0x87, 0xbc, 0x6b, 0x1c, 0x68, 0x7d, 0xdb, 0xde, 0xb9, 0x16, 0x63, 0x04, 0xf0, 0xf6, 0xbe,
+ 0xff, 0xf3, 0xaf, 0x1f, 0x0a, 0x0f, 0xbc, 0x86, 0xfe, 0x3e, 0xbb, 0xe8, 0xed, 0x1b, 0xef, 0xca,
+ 0x43, 0xe7, 0xcd, 0xa7, 0x1b, 0xe8, 0xf9, 0xec, 0xd1, 0x43, 0xd8, 0xf4, 0xf9, 0x7c, 0x65, 0x63,
+ 0xfd, 0x71, 0x26, 0xba, 0x81, 0x88, 0xfd, 0xc7, 0xce, 0xd3, 0x5a, 0x76, 0x4e, 0x3c, 0xf9, 0xa9,
+ 0xe0, 0x0e, 0xcf, 0x1e, 0x1f, 0x4d, 0x4a, 0xba, 0x77, 0xef, 0xfc, 0x1d, 0x00, 0x00, 0xff, 0xff,
+ 0x53, 0x43, 0x3f, 0x2c, 0x4f, 0x0a, 0x00, 0x00,
+}
diff --git a/vendor/github.com/lightstep/lightstep-tracer-go/event_handlers.go b/vendor/github.com/lightstep/lightstep-tracer-go/event_handlers.go
new file mode 100644
index 000000000..4e4ee5f85
--- /dev/null
+++ b/vendor/github.com/lightstep/lightstep-tracer-go/event_handlers.go
@@ -0,0 +1,97 @@
+package lightstep
+
+import (
+ "log"
+ "sync"
+ "sync/atomic"
+)
+
+func init() {
+ SetGlobalEventHandler(NewEventLogOneError())
+}
+
+var eventHandler atomic.Value
+
+// An EventHandler can be registered with SetGlobalEventHandler to
+type EventHandler func(Event)
+
+// emitEvent is a thread-safe function for emiting tracer events.
+func emitEvent(event Event) {
+ handler := eventHandler.Load().(EventHandler)
+ handler(event)
+}
+
+// SetGlobalEventHandler sets a global handler to receive tracer events as they occur. Events
+// may be emitted by the tracer, or by calls to static functions in this package.
+// It is suggested that you set your EventHandler before starting your tracer,
+// but it is safe to set a new handler at any time. Setting a new handler removes
+// the previous one.
+//
+// The EventHandler is called synchronously – do not block in your handler as it
+// may interfere with the tracer. If no EventHandler handler is set, a
+// LogOnceOnError handler is set by default.
+//
+// NOTE: Event handling is for reporting purposes only. It is not intended as a
+// mechanism for controling or restarting the tracer. Connection issues, retry
+// logic, and other transient errors are handled internally by the tracer.
+func SetGlobalEventHandler(handler EventHandler) {
+ eventHandler.Store(handler)
+}
+
+/*
+ SetGlobalEventHandler Handlers
+*/
+
+// NewEventLogger logs events using the standard go logger.
+func NewEventLogger() EventHandler {
+ return logOnEvent
+}
+
+func logOnEvent(event Event) {
+ switch event := event.(type) {
+ case ErrorEvent:
+ log.Println("LS Tracer error: ", event)
+ default:
+ log.Println("LS Tracer event: ", event)
+ }
+}
+
+// NewEventLogOneError logs the first error event that occurs.
+func NewEventLogOneError() EventHandler {
+ logger := logOneError{}
+ return logger.OnEvent
+}
+
+type logOneError struct {
+ sync.Once
+}
+
+func (l *logOneError) OnEvent(event Event) {
+ switch event := event.(type) {
+ case ErrorEvent:
+ l.Once.Do(func() {
+ log.Printf("LS Tracer error: (%s). NOTE: Set the SetGlobalEventHandler handler to log events.\n", event.Error())
+ })
+ }
+}
+
+// NewEventChannel returns an SetGlobalEventHandler callback handler, and a channel that
+// produces the errors. When the channel buffer is full, subsequent errors will
+// be dropped. A buffer size of less than one is incorrect, and will be adjusted
+// to a buffer size of one.
+func NewEventChannel(buffer int) (EventHandler, <-chan Event) {
+ if buffer < 1 {
+ buffer = 1
+ }
+
+ eventChan := make(chan Event, buffer)
+
+ handler := func(event Event) {
+ select {
+ case eventChan <- event:
+ default:
+ }
+ }
+
+ return handler, eventChan
+}
diff --git a/vendor/github.com/lightstep/lightstep-tracer-go/events.go b/vendor/github.com/lightstep/lightstep-tracer-go/events.go
new file mode 100644
index 000000000..e5bd91fc3
--- /dev/null
+++ b/vendor/github.com/lightstep/lightstep-tracer-go/events.go
@@ -0,0 +1,330 @@
+package lightstep
+
+import (
+ "errors"
+ "fmt"
+ "reflect"
+ "time"
+
+ opentracing "github.com/opentracing/opentracing-go"
+)
+
+// An Event is emitted by the LightStep tracer as a reporting mechanism. They are
+// handled by registering an EventHandler callback via SetGlobalEventHandler. The
+// emitted events may be cast to specific event types in order access additional
+// information.
+//
+// NOTE: To ensure that events can be accurately identified, each event type contains
+// a sentinel method matching the name of the type. This method is a no-op, it is
+// only used for type coersion.
+type Event interface {
+ Event()
+ String() string
+}
+
+// The ErrorEvent type can be used to filter events. The `Err` method
+// retuns the underlying error.
+type ErrorEvent interface {
+ Event
+ error
+ Err() error
+}
+
+// EventStartError occurs if the Options passed to NewTracer are invalid, and
+// the Tracer has failed to start.
+type EventStartError interface {
+ ErrorEvent
+ EventStartError()
+}
+
+type eventStartError struct {
+ err error
+}
+
+func newEventStartError(err error) *eventStartError {
+ return &eventStartError{err: err}
+}
+
+func (*eventStartError) Event() {}
+func (*eventStartError) EventStartError() {}
+
+func (e *eventStartError) String() string {
+ return e.err.Error()
+}
+
+func (e *eventStartError) Error() string {
+ return e.err.Error()
+}
+
+func (e *eventStartError) Err() error {
+ return e.err
+}
+
+// EventFlushErrorState lists the possible causes for a flush to fail.
+type EventFlushErrorState string
+
+// Constant strings corresponding to flush errors
+const (
+ FlushErrorTracerClosed EventFlushErrorState = "flush failed, the tracer is closed."
+ FlushErrorTracerDisabled EventFlushErrorState = "flush failed, the tracer is disabled."
+ FlushErrorTransport EventFlushErrorState = "flush failed, could not send report to Collector"
+ FlushErrorReport EventFlushErrorState = "flush failed, report contained errors"
+ FlushErrorTranslate EventFlushErrorState = "flush failed, could not translate report"
+)
+
+var (
+ errFlushFailedTracerClosed = errors.New(string(FlushErrorTracerClosed))
+)
+
+// EventFlushError occurs when a flush fails to send. Call the `State` method to
+// determine the type of error.
+type EventFlushError interface {
+ ErrorEvent
+ EventFlushError()
+ State() EventFlushErrorState
+}
+
+type eventFlushError struct {
+ err error
+ state EventFlushErrorState
+}
+
+func newEventFlushError(err error, state EventFlushErrorState) *eventFlushError {
+ return &eventFlushError{err: err, state: state}
+}
+
+func (*eventFlushError) Event() {}
+func (*eventFlushError) EventFlushError() {}
+
+func (e *eventFlushError) State() EventFlushErrorState {
+ return e.state
+}
+
+func (e *eventFlushError) String() string {
+ return e.err.Error()
+}
+
+func (e *eventFlushError) Error() string {
+ return e.err.Error()
+}
+
+func (e *eventFlushError) Err() error {
+ return e.err
+}
+
+// EventConnectionError occurs when the tracer fails to maintain it's connection
+// with the Collector.
+type EventConnectionError interface {
+ ErrorEvent
+ EventConnectionError()
+}
+
+type eventConnectionError struct {
+ err error
+}
+
+func newEventConnectionError(err error) *eventConnectionError {
+ return &eventConnectionError{err: err}
+}
+
+func (*eventConnectionError) Event() {}
+func (*eventConnectionError) EventConnectionError() {}
+
+func (e *eventConnectionError) String() string {
+ return e.err.Error()
+}
+
+func (e *eventConnectionError) Error() string {
+ return e.err.Error()
+}
+
+func (e *eventConnectionError) Err() error {
+ return e.err
+}
+
+// EventStatusReport occurs on every successful flush. It contains all metrics
+// collected since the previous succesful flush.
+type EventStatusReport interface {
+ Event
+ EventStatusReport()
+ StartTime() time.Time
+ FinishTime() time.Time
+ Duration() time.Duration
+ SentSpans() int
+ DroppedSpans() int
+ EncodingErrors() int
+}
+
+type eventStatusReport struct {
+ startTime time.Time
+ finishTime time.Time
+ sentSpans int
+ droppedSpans int
+ encodingErrors int
+}
+
+func newEventStatusReport(
+ startTime, finishTime time.Time,
+ sentSpans, droppedSpans, encodingErrors int,
+) *eventStatusReport {
+ return &eventStatusReport{
+ startTime: startTime,
+ finishTime: finishTime,
+ sentSpans: sentSpans,
+ droppedSpans: droppedSpans,
+ encodingErrors: encodingErrors,
+ }
+}
+
+func (*eventStatusReport) Event() {}
+
+func (*eventStatusReport) EventStatusReport() {}
+
+func (s *eventStatusReport) SetSentSpans(sent int) {
+ s.sentSpans = sent
+}
+
+func (s *eventStatusReport) StartTime() time.Time {
+ return s.startTime
+}
+
+func (s *eventStatusReport) FinishTime() time.Time {
+ return s.finishTime
+}
+
+func (s *eventStatusReport) Duration() time.Duration {
+ return s.finishTime.Sub(s.startTime)
+}
+
+func (s *eventStatusReport) SentSpans() int {
+ return s.sentSpans
+}
+
+func (s *eventStatusReport) DroppedSpans() int {
+ return s.droppedSpans
+}
+
+func (s *eventStatusReport) EncodingErrors() int {
+ return s.encodingErrors
+}
+
+func (s *eventStatusReport) String() string {
+ return fmt.Sprint(
+ "STATUS REPORT start: ", s.startTime,
+ ", end: ", s.finishTime,
+ ", dropped spans: ", s.droppedSpans,
+ ", encoding errors: ", s.encodingErrors,
+ )
+}
+
+// EventUnsupportedTracer occurs when a tracer being passed to a helper function
+// fails to typecast as a LightStep tracer.
+type EventUnsupportedTracer interface {
+ ErrorEvent
+ EventUnsupportedTracer()
+ Tracer() opentracing.Tracer
+}
+
+type eventUnsupportedTracer struct {
+ tracer opentracing.Tracer
+ err error
+}
+
+func newEventUnsupportedTracer(tracer opentracing.Tracer) EventUnsupportedTracer {
+ return &eventUnsupportedTracer{
+ tracer: tracer,
+ err: fmt.Errorf("unsupported tracer type: %v", reflect.TypeOf(tracer)),
+ }
+}
+
+func (e *eventUnsupportedTracer) Event() {}
+func (e *eventUnsupportedTracer) EventUnsupportedTracer() {}
+
+func (e *eventUnsupportedTracer) Tracer() opentracing.Tracer {
+ return e.tracer
+}
+
+func (e *eventUnsupportedTracer) String() string {
+ return e.err.Error()
+}
+
+func (e *eventUnsupportedTracer) Error() string {
+ return e.err.Error()
+}
+
+func (e *eventUnsupportedTracer) Err() error {
+ return e.err
+}
+
+// EventUnsupportedValue occurs when a tracer encounters an unserializable tag
+// or log field.
+type EventUnsupportedValue interface {
+ ErrorEvent
+ EventUnsupportedValue()
+ Key() string
+ Value() interface{}
+}
+
+type eventUnsupportedValue struct {
+ key string
+ value interface{}
+ err error
+}
+
+func newEventUnsupportedValue(key string, value interface{}, err error) EventUnsupportedValue {
+ if err == nil {
+ err = fmt.Errorf(
+ "value `%v` of type `%T` for key `%s` is an unsupported type",
+ value, value, key,
+ )
+ }
+ return &eventUnsupportedValue{
+ key: key,
+ value: value,
+ err: err,
+ }
+}
+
+func (e *eventUnsupportedValue) Event() {}
+func (e *eventUnsupportedValue) EventUnsupportedValue() {}
+
+func (e *eventUnsupportedValue) Key() string {
+ return e.key
+}
+
+func (e *eventUnsupportedValue) Value() interface{} {
+ return e.value
+}
+
+func (e *eventUnsupportedValue) String() string {
+ return e.err.Error()
+}
+
+func (e *eventUnsupportedValue) Error() string {
+ return e.err.Error()
+}
+
+func (e *eventUnsupportedValue) Err() error {
+ return e.err
+}
+
+const tracerDisabled = "the tracer has been disabled"
+
+// EventTracerDisabled occurs when a tracer is disabled by either the user or
+// the collector.
+type EventTracerDisabled interface {
+ Event
+ EventTracerDisabled()
+}
+
+type eventTracerDisabled struct{}
+
+func newEventTracerDisabled() EventTracerDisabled {
+ return eventTracerDisabled{}
+}
+
+func (eventTracerDisabled) Event() {}
+func (eventTracerDisabled) EventTracerDisabled() {}
+func (eventTracerDisabled) String() string {
+ return tracerDisabled
+}
diff --git a/vendor/github.com/lightstep/lightstep-tracer-go/lightstep/rand/locked_rand.go b/vendor/github.com/lightstep/lightstep-tracer-go/lightstep/rand/locked_rand.go
new file mode 100644
index 000000000..325c0f2bd
--- /dev/null
+++ b/vendor/github.com/lightstep/lightstep-tracer-go/lightstep/rand/locked_rand.go
@@ -0,0 +1,138 @@
+package rand
+
+import (
+ "math/rand"
+ "sync"
+)
+
+// LockedRand implements NumberGenerator and embeds Rand that is safe for concurrent use.
+type LockedRand struct {
+ lk sync.Mutex
+ r *rand.Rand
+}
+
+// NewLockedRand creates a new LockedRand that implements all Rand functions that is safe
+// for concurrent use.
+func NewLockedRand(seed int64) *LockedRand {
+ return &LockedRand{
+ r: rand.New(rand.NewSource(seed)),
+ }
+}
+
+// Seed uses the provided seed value to initialize the generator to a deterministic state.
+// Seed should not be called concurrently with any other Rand method.
+func (lr *LockedRand) Seed(seed int64) {
+ lr.lk.Lock()
+ lr.r.Seed(seed)
+ lr.lk.Unlock()
+}
+
+// TwoInt63 generates 2 random int64 without locking twice.
+func (lr *LockedRand) TwoInt63() (n1, n2 int64) {
+ lr.lk.Lock()
+ n1 = lr.r.Int63()
+ n2 = lr.r.Int63()
+ lr.lk.Unlock()
+ return
+}
+
+// Int63 returns a non-negative pseudo-random 63-bit integer as an int64.
+func (lr *LockedRand) Int63() (n int64) {
+ lr.lk.Lock()
+ n = lr.r.Int63()
+ lr.lk.Unlock()
+ return
+}
+
+// Uint32 returns a pseudo-random 32-bit value as a uint32.
+func (lr *LockedRand) Uint32() (n uint32) {
+ lr.lk.Lock()
+ n = lr.r.Uint32()
+ lr.lk.Unlock()
+ return
+}
+
+// Uint64 returns a pseudo-random 64-bit value as a uint64.
+func (lr *LockedRand) Uint64() (n uint64) {
+ lr.lk.Lock()
+ n = lr.r.Uint64()
+ lr.lk.Unlock()
+ return
+}
+
+// Int31 returns a non-negative pseudo-random 31-bit integer as an int32.
+func (lr *LockedRand) Int31() (n int32) {
+ lr.lk.Lock()
+ n = lr.r.Int31()
+ lr.lk.Unlock()
+ return
+}
+
+// Int returns a non-negative pseudo-random int.
+func (lr *LockedRand) Int() (n int) {
+ lr.lk.Lock()
+ n = lr.r.Int()
+ lr.lk.Unlock()
+ return
+}
+
+// Int63n returns, as an int64, a non-negative pseudo-random number in [0,n).
+// It panics if n <= 0.
+func (lr *LockedRand) Int63n(n int64) (r int64) {
+ lr.lk.Lock()
+ r = lr.r.Int63n(n)
+ lr.lk.Unlock()
+ return
+}
+
+// Int31n returns, as an int32, a non-negative pseudo-random number in [0,n).
+// It panics if n <= 0.
+func (lr *LockedRand) Int31n(n int32) (r int32) {
+ lr.lk.Lock()
+ r = lr.r.Int31n(n)
+ lr.lk.Unlock()
+ return
+}
+
+// Intn returns, as an int, a non-negative pseudo-random number in [0,n).
+// It panics if n <= 0.
+func (lr *LockedRand) Intn(n int) (r int) {
+ lr.lk.Lock()
+ r = lr.r.Intn(n)
+ lr.lk.Unlock()
+ return
+}
+
+// Float64 returns, as a float64, a pseudo-random number in [0.0,1.0).
+func (lr *LockedRand) Float64() (n float64) {
+ lr.lk.Lock()
+ n = lr.r.Float64()
+ lr.lk.Unlock()
+ return
+}
+
+// Float32 returns, as a float32, a pseudo-random number in [0.0,1.0).
+func (lr *LockedRand) Float32() (n float32) {
+ lr.lk.Lock()
+ n = lr.r.Float32()
+ lr.lk.Unlock()
+ return
+}
+
+// Perm returns, as a slice of n ints, a pseudo-random permutation of the integers [0,n).
+func (lr *LockedRand) Perm(n int) (r []int) {
+ lr.lk.Lock()
+ r = lr.r.Perm(n)
+ lr.lk.Unlock()
+ return
+}
+
+// Read generates len(p) random bytes and writes them into p. It
+// always returns len(p) and a nil error.
+// Read should not be called concurrently with any other Rand method.
+func (lr *LockedRand) Read(p []byte) (n int, err error) {
+ lr.lk.Lock()
+ n, err = lr.r.Read(p)
+ lr.lk.Unlock()
+ return
+}
diff --git a/vendor/github.com/lightstep/lightstep-tracer-go/lightstep/rand/num_gen.go b/vendor/github.com/lightstep/lightstep-tracer-go/lightstep/rand/num_gen.go
new file mode 100644
index 000000000..6ad94e4b6
--- /dev/null
+++ b/vendor/github.com/lightstep/lightstep-tracer-go/lightstep/rand/num_gen.go
@@ -0,0 +1,7 @@
+package rand
+
+// NumberGenerator defines an interface to generate numbers.
+type NumberGenerator interface {
+ Int63() int64
+ TwoInt63() (int64, int64)
+}
diff --git a/vendor/github.com/lightstep/lightstep-tracer-go/lightstep/rand/pool.go b/vendor/github.com/lightstep/lightstep-tracer-go/lightstep/rand/pool.go
new file mode 100644
index 000000000..c3526bad2
--- /dev/null
+++ b/vendor/github.com/lightstep/lightstep-tracer-go/lightstep/rand/pool.go
@@ -0,0 +1,59 @@
+package rand
+
+import (
+ "math/rand"
+ "sync/atomic"
+)
+
+// Pool represents a pool of random number generators.
+// To generate a random id, round robin through the source pool with atomic increment.
+// With more and more goroutines, Pool improves the performance of Random vs naive global random
+// mutex exponentially.
+// Try tests with 20000 goroutines and 500 calls to observe the difference
+type Pool struct {
+ sources []NumberGenerator
+ counter uint64 // used for round robin
+ size uint64
+}
+
+// see bit twiddling hacks: https://graphics.stanford.edu/~seander/bithacks.html#RoundUpPowerOf2
+func nextNearestPow2uint64(v uint64) uint64 {
+ v--
+ v |= v >> 1
+ v |= v >> 2
+ v |= v >> 4
+ v |= v >> 8
+ v |= v >> 16
+ v |= v >> 32
+ v++
+ return v
+}
+
+// NewPool takes in a size and creates a pool of random id generators with size equal to next closest power of 2.
+// eg: NewPool(10) returns a pool with 2^4 = 16 random sources.
+func NewPool(seed int64, size uint64) *Pool {
+ groupsize := nextNearestPow2uint64(size)
+ pool := &Pool{
+ size: groupsize,
+ sources: make([]NumberGenerator, groupsize),
+ }
+ // seed the pool
+ pool.seed(seed)
+ return pool
+}
+
+// seed initializes the pool using a randomized sequence with given seed.
+func (r *Pool) seed(seed int64) {
+ // init a random sequence to seed all sources
+ seedRan := rand.NewSource(seed)
+ for i := uint64(0); i < r.size; i++ {
+ r.sources[i] = NewLockedRand(seedRan.Int63())
+ }
+}
+
+// Pick returns a NumberGenerator from a pool of NumberGenerators
+func (r *Pool) Pick() NumberGenerator {
+ // use round robin with fast modulus of pow2 numbers
+ selection := atomic.AddUint64(&r.counter, 1) & (r.size - 1)
+ return r.sources[selection]
+}
diff --git a/vendor/github.com/lightstep/lightstep-tracer-go/lightstep_thrift/constants.go b/vendor/github.com/lightstep/lightstep-tracer-go/lightstep_thrift/constants.go
new file mode 100644
index 000000000..7bad366a6
--- /dev/null
+++ b/vendor/github.com/lightstep/lightstep-tracer-go/lightstep_thrift/constants.go
@@ -0,0 +1,18 @@
+// Autogenerated by Thrift Compiler (0.9.2)
+// DO NOT EDIT UNLESS YOU ARE SURE THAT YOU KNOW WHAT YOU ARE DOING
+
+package lightstep_thrift
+
+import (
+ "bytes"
+ "fmt"
+ "github.com/lightstep/thrift/lib/go/thrift"
+)
+
+// (needed to ensure safety because of naive import list construction.)
+var _ = thrift.ZERO
+var _ = fmt.Printf
+var _ = bytes.Equal
+
+func init() {
+}
diff --git a/vendor/github.com/lightstep/lightstep-tracer-go/lightstep_thrift/reportingservice.go b/vendor/github.com/lightstep/lightstep-tracer-go/lightstep_thrift/reportingservice.go
new file mode 100644
index 000000000..7fc611abb
--- /dev/null
+++ b/vendor/github.com/lightstep/lightstep-tracer-go/lightstep_thrift/reportingservice.go
@@ -0,0 +1,449 @@
+// Autogenerated by Thrift Compiler (0.9.2)
+// DO NOT EDIT UNLESS YOU ARE SURE THAT YOU KNOW WHAT YOU ARE DOING
+
+package lightstep_thrift
+
+import (
+ "bytes"
+ "fmt"
+ "github.com/lightstep/thrift/lib/go/thrift"
+)
+
+// (needed to ensure safety because of naive import list construction.)
+var _ = thrift.ZERO
+var _ = fmt.Printf
+var _ = bytes.Equal
+
+type ReportingService interface {
+ // Parameters:
+ // - Auth
+ // - Request
+ Report(auth *Auth, request *ReportRequest) (r *ReportResponse, err error)
+}
+
+type ReportingServiceClient struct {
+ Transport thrift.TTransport
+ ProtocolFactory thrift.TProtocolFactory
+ InputProtocol thrift.TProtocol
+ OutputProtocol thrift.TProtocol
+ SeqId int32
+}
+
+func NewReportingServiceClientFactory(t thrift.TTransport, f thrift.TProtocolFactory) *ReportingServiceClient {
+ return &ReportingServiceClient{Transport: t,
+ ProtocolFactory: f,
+ InputProtocol: f.GetProtocol(t),
+ OutputProtocol: f.GetProtocol(t),
+ SeqId: 0,
+ }
+}
+
+func NewReportingServiceClientProtocol(t thrift.TTransport, iprot thrift.TProtocol, oprot thrift.TProtocol) *ReportingServiceClient {
+ return &ReportingServiceClient{Transport: t,
+ ProtocolFactory: nil,
+ InputProtocol: iprot,
+ OutputProtocol: oprot,
+ SeqId: 0,
+ }
+}
+
+// Parameters:
+// - Auth
+// - Request
+func (p *ReportingServiceClient) Report(auth *Auth, request *ReportRequest) (r *ReportResponse, err error) {
+ if err = p.sendReport(auth, request); err != nil {
+ return
+ }
+ return p.recvReport()
+}
+
+func (p *ReportingServiceClient) sendReport(auth *Auth, request *ReportRequest) (err error) {
+ oprot := p.OutputProtocol
+ if oprot == nil {
+ oprot = p.ProtocolFactory.GetProtocol(p.Transport)
+ p.OutputProtocol = oprot
+ }
+ p.SeqId++
+ if err = oprot.WriteMessageBegin("Report", thrift.CALL, p.SeqId); err != nil {
+ return
+ }
+ args := ReportArgs{
+ Auth: auth,
+ Request: request,
+ }
+ if err = args.Write(oprot); err != nil {
+ return
+ }
+ if err = oprot.WriteMessageEnd(); err != nil {
+ return
+ }
+ return oprot.Flush()
+}
+
+func (p *ReportingServiceClient) recvReport() (value *ReportResponse, err error) {
+ iprot := p.InputProtocol
+ if iprot == nil {
+ iprot = p.ProtocolFactory.GetProtocol(p.Transport)
+ p.InputProtocol = iprot
+ }
+ _, mTypeId, seqId, err := iprot.ReadMessageBegin()
+ if err != nil {
+ return
+ }
+ if mTypeId == thrift.EXCEPTION {
+ error14 := thrift.NewTApplicationException(thrift.UNKNOWN_APPLICATION_EXCEPTION, "Unknown Exception")
+ var error15 error
+ error15, err = error14.Read(iprot)
+ if err != nil {
+ return
+ }
+ if err = iprot.ReadMessageEnd(); err != nil {
+ return
+ }
+ err = error15
+ return
+ }
+ if p.SeqId != seqId {
+ err = thrift.NewTApplicationException(thrift.BAD_SEQUENCE_ID, "Report failed: out of sequence response")
+ return
+ }
+ result := ReportResult{}
+ if err = result.Read(iprot); err != nil {
+ return
+ }
+ if err = iprot.ReadMessageEnd(); err != nil {
+ return
+ }
+ value = result.GetSuccess()
+ return
+}
+
+type ReportingServiceProcessor struct {
+ processorMap map[string]thrift.TProcessorFunction
+ handler ReportingService
+}
+
+func (p *ReportingServiceProcessor) AddToProcessorMap(key string, processor thrift.TProcessorFunction) {
+ p.processorMap[key] = processor
+}
+
+func (p *ReportingServiceProcessor) GetProcessorFunction(key string) (processor thrift.TProcessorFunction, ok bool) {
+ processor, ok = p.processorMap[key]
+ return processor, ok
+}
+
+func (p *ReportingServiceProcessor) ProcessorMap() map[string]thrift.TProcessorFunction {
+ return p.processorMap
+}
+
+func NewReportingServiceProcessor(handler ReportingService) *ReportingServiceProcessor {
+
+ self16 := &ReportingServiceProcessor{handler: handler, processorMap: make(map[string]thrift.TProcessorFunction)}
+ self16.processorMap["Report"] = &reportingServiceProcessorReport{handler: handler}
+ return self16
+}
+
+func (p *ReportingServiceProcessor) Process(iprot, oprot thrift.TProtocol) (success bool, err thrift.TException) {
+ name, _, seqId, err := iprot.ReadMessageBegin()
+ if err != nil {
+ return false, err
+ }
+ if processor, ok := p.GetProcessorFunction(name); ok {
+ return processor.Process(seqId, iprot, oprot)
+ }
+ iprot.Skip(thrift.STRUCT)
+ iprot.ReadMessageEnd()
+ x17 := thrift.NewTApplicationException(thrift.UNKNOWN_METHOD, "Unknown function "+name)
+ oprot.WriteMessageBegin(name, thrift.EXCEPTION, seqId)
+ x17.Write(oprot)
+ oprot.WriteMessageEnd()
+ oprot.Flush()
+ return false, x17
+
+}
+
+type reportingServiceProcessorReport struct {
+ handler ReportingService
+}
+
+func (p *reportingServiceProcessorReport) Process(seqId int32, iprot, oprot thrift.TProtocol) (success bool, err thrift.TException) {
+ args := ReportArgs{}
+ if err = args.Read(iprot); err != nil {
+ iprot.ReadMessageEnd()
+ x := thrift.NewTApplicationException(thrift.PROTOCOL_ERROR, err.Error())
+ oprot.WriteMessageBegin("Report", thrift.EXCEPTION, seqId)
+ x.Write(oprot)
+ oprot.WriteMessageEnd()
+ oprot.Flush()
+ return false, err
+ }
+
+ iprot.ReadMessageEnd()
+ result := ReportResult{}
+ var retval *ReportResponse
+ var err2 error
+ if retval, err2 = p.handler.Report(args.Auth, args.Request); err2 != nil {
+ x := thrift.NewTApplicationException(thrift.INTERNAL_ERROR, "Internal error processing Report: "+err2.Error())
+ oprot.WriteMessageBegin("Report", thrift.EXCEPTION, seqId)
+ x.Write(oprot)
+ oprot.WriteMessageEnd()
+ oprot.Flush()
+ return true, err2
+ } else {
+ result.Success = retval
+ }
+ if err2 = oprot.WriteMessageBegin("Report", thrift.REPLY, seqId); err2 != nil {
+ err = err2
+ }
+ if err2 = result.Write(oprot); err == nil && err2 != nil {
+ err = err2
+ }
+ if err2 = oprot.WriteMessageEnd(); err == nil && err2 != nil {
+ err = err2
+ }
+ if err2 = oprot.Flush(); err == nil && err2 != nil {
+ err = err2
+ }
+ if err != nil {
+ return
+ }
+ return true, err
+}
+
+// HELPER FUNCTIONS AND STRUCTURES
+
+type ReportArgs struct {
+ Auth *Auth `thrift:"auth,1" json:"auth"`
+ Request *ReportRequest `thrift:"request,2" json:"request"`
+}
+
+func NewReportArgs() *ReportArgs {
+ return &ReportArgs{}
+}
+
+var ReportArgs_Auth_DEFAULT *Auth
+
+func (p *ReportArgs) GetAuth() *Auth {
+ if !p.IsSetAuth() {
+ return ReportArgs_Auth_DEFAULT
+ }
+ return p.Auth
+}
+
+var ReportArgs_Request_DEFAULT *ReportRequest
+
+func (p *ReportArgs) GetRequest() *ReportRequest {
+ if !p.IsSetRequest() {
+ return ReportArgs_Request_DEFAULT
+ }
+ return p.Request
+}
+func (p *ReportArgs) IsSetAuth() bool {
+ return p.Auth != nil
+}
+
+func (p *ReportArgs) IsSetRequest() bool {
+ return p.Request != nil
+}
+
+func (p *ReportArgs) Read(iprot thrift.TProtocol) error {
+ if _, err := iprot.ReadStructBegin(); err != nil {
+ return fmt.Errorf("%T read error: %s", p, err)
+ }
+ for {
+ _, fieldTypeId, fieldId, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return fmt.Errorf("%T field %d read error: %s", p, fieldId, err)
+ }
+ if fieldTypeId == thrift.STOP {
+ break
+ }
+ switch fieldId {
+ case 1:
+ if err := p.ReadField1(iprot); err != nil {
+ return err
+ }
+ case 2:
+ if err := p.ReadField2(iprot); err != nil {
+ return err
+ }
+ default:
+ if err := iprot.Skip(fieldTypeId); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadFieldEnd(); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadStructEnd(); err != nil {
+ return fmt.Errorf("%T read struct end error: %s", p, err)
+ }
+ return nil
+}
+
+func (p *ReportArgs) ReadField1(iprot thrift.TProtocol) error {
+ p.Auth = &Auth{}
+ if err := p.Auth.Read(iprot); err != nil {
+ return fmt.Errorf("%T error reading struct: %s", p.Auth, err)
+ }
+ return nil
+}
+
+func (p *ReportArgs) ReadField2(iprot thrift.TProtocol) error {
+ p.Request = &ReportRequest{}
+ if err := p.Request.Read(iprot); err != nil {
+ return fmt.Errorf("%T error reading struct: %s", p.Request, err)
+ }
+ return nil
+}
+
+func (p *ReportArgs) Write(oprot thrift.TProtocol) error {
+ if err := oprot.WriteStructBegin("Report_args"); err != nil {
+ return fmt.Errorf("%T write struct begin error: %s", p, err)
+ }
+ if err := p.writeField1(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField2(oprot); err != nil {
+ return err
+ }
+ if err := oprot.WriteFieldStop(); err != nil {
+ return fmt.Errorf("write field stop error: %s", err)
+ }
+ if err := oprot.WriteStructEnd(); err != nil {
+ return fmt.Errorf("write struct stop error: %s", err)
+ }
+ return nil
+}
+
+func (p *ReportArgs) writeField1(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("auth", thrift.STRUCT, 1); err != nil {
+ return fmt.Errorf("%T write field begin error 1:auth: %s", p, err)
+ }
+ if err := p.Auth.Write(oprot); err != nil {
+ return fmt.Errorf("%T error writing struct: %s", p.Auth, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 1:auth: %s", p, err)
+ }
+ return err
+}
+
+func (p *ReportArgs) writeField2(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("request", thrift.STRUCT, 2); err != nil {
+ return fmt.Errorf("%T write field begin error 2:request: %s", p, err)
+ }
+ if err := p.Request.Write(oprot); err != nil {
+ return fmt.Errorf("%T error writing struct: %s", p.Request, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 2:request: %s", p, err)
+ }
+ return err
+}
+
+func (p *ReportArgs) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return fmt.Sprintf("ReportArgs(%+v)", *p)
+}
+
+type ReportResult struct {
+ Success *ReportResponse `thrift:"success,0" json:"success"`
+}
+
+func NewReportResult() *ReportResult {
+ return &ReportResult{}
+}
+
+var ReportResult_Success_DEFAULT *ReportResponse
+
+func (p *ReportResult) GetSuccess() *ReportResponse {
+ if !p.IsSetSuccess() {
+ return ReportResult_Success_DEFAULT
+ }
+ return p.Success
+}
+func (p *ReportResult) IsSetSuccess() bool {
+ return p.Success != nil
+}
+
+func (p *ReportResult) Read(iprot thrift.TProtocol) error {
+ if _, err := iprot.ReadStructBegin(); err != nil {
+ return fmt.Errorf("%T read error: %s", p, err)
+ }
+ for {
+ _, fieldTypeId, fieldId, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return fmt.Errorf("%T field %d read error: %s", p, fieldId, err)
+ }
+ if fieldTypeId == thrift.STOP {
+ break
+ }
+ switch fieldId {
+ case 0:
+ if err := p.ReadField0(iprot); err != nil {
+ return err
+ }
+ default:
+ if err := iprot.Skip(fieldTypeId); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadFieldEnd(); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadStructEnd(); err != nil {
+ return fmt.Errorf("%T read struct end error: %s", p, err)
+ }
+ return nil
+}
+
+func (p *ReportResult) ReadField0(iprot thrift.TProtocol) error {
+ p.Success = &ReportResponse{}
+ if err := p.Success.Read(iprot); err != nil {
+ return fmt.Errorf("%T error reading struct: %s", p.Success, err)
+ }
+ return nil
+}
+
+func (p *ReportResult) Write(oprot thrift.TProtocol) error {
+ if err := oprot.WriteStructBegin("Report_result"); err != nil {
+ return fmt.Errorf("%T write struct begin error: %s", p, err)
+ }
+ if err := p.writeField0(oprot); err != nil {
+ return err
+ }
+ if err := oprot.WriteFieldStop(); err != nil {
+ return fmt.Errorf("write field stop error: %s", err)
+ }
+ if err := oprot.WriteStructEnd(); err != nil {
+ return fmt.Errorf("write struct stop error: %s", err)
+ }
+ return nil
+}
+
+func (p *ReportResult) writeField0(oprot thrift.TProtocol) (err error) {
+ if p.IsSetSuccess() {
+ if err := oprot.WriteFieldBegin("success", thrift.STRUCT, 0); err != nil {
+ return fmt.Errorf("%T write field begin error 0:success: %s", p, err)
+ }
+ if err := p.Success.Write(oprot); err != nil {
+ return fmt.Errorf("%T error writing struct: %s", p.Success, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 0:success: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *ReportResult) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return fmt.Sprintf("ReportResult(%+v)", *p)
+}
diff --git a/vendor/github.com/lightstep/lightstep-tracer-go/lightstep_thrift/reportingservice_methods.go b/vendor/github.com/lightstep/lightstep-tracer-go/lightstep_thrift/reportingservice_methods.go
new file mode 100644
index 000000000..8a7864c2d
--- /dev/null
+++ b/vendor/github.com/lightstep/lightstep-tracer-go/lightstep_thrift/reportingservice_methods.go
@@ -0,0 +1,10 @@
+package lightstep_thrift
+
+func (res *ReportResponse) Disable() bool {
+ for _, command := range res.GetCommands() {
+ if *command.Disable {
+ return true
+ }
+ }
+ return false
+}
diff --git a/vendor/github.com/lightstep/lightstep-tracer-go/lightstep_thrift/ttypes.go b/vendor/github.com/lightstep/lightstep-tracer-go/lightstep_thrift/ttypes.go
new file mode 100644
index 000000000..26eb5d847
--- /dev/null
+++ b/vendor/github.com/lightstep/lightstep-tracer-go/lightstep_thrift/ttypes.go
@@ -0,0 +1,3489 @@
+// Autogenerated by Thrift Compiler (0.9.2)
+// DO NOT EDIT UNLESS YOU ARE SURE THAT YOU KNOW WHAT YOU ARE DOING
+
+package lightstep_thrift
+
+import (
+ "bytes"
+ "fmt"
+ "github.com/lightstep/thrift/lib/go/thrift"
+)
+
+// (needed to ensure safety because of naive import list construction.)
+var _ = thrift.ZERO
+var _ = fmt.Printf
+var _ = bytes.Equal
+
+var GoUnusedProtection__ int
+
+type KeyValue struct {
+ Key string `thrift:"Key,1,required" json:"Key"`
+ Value string `thrift:"Value,2,required" json:"Value"`
+}
+
+func NewKeyValue() *KeyValue {
+ return &KeyValue{}
+}
+
+func (p *KeyValue) GetKey() string {
+ return p.Key
+}
+
+func (p *KeyValue) GetValue() string {
+ return p.Value
+}
+func (p *KeyValue) Read(iprot thrift.TProtocol) error {
+ if _, err := iprot.ReadStructBegin(); err != nil {
+ return fmt.Errorf("%T read error: %s", p, err)
+ }
+ for {
+ _, fieldTypeId, fieldId, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return fmt.Errorf("%T field %d read error: %s", p, fieldId, err)
+ }
+ if fieldTypeId == thrift.STOP {
+ break
+ }
+ switch fieldId {
+ case 1:
+ if err := p.ReadField1(iprot); err != nil {
+ return err
+ }
+ case 2:
+ if err := p.ReadField2(iprot); err != nil {
+ return err
+ }
+ default:
+ if err := iprot.Skip(fieldTypeId); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadFieldEnd(); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadStructEnd(); err != nil {
+ return fmt.Errorf("%T read struct end error: %s", p, err)
+ }
+ return nil
+}
+
+func (p *KeyValue) ReadField1(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadString(); err != nil {
+ return fmt.Errorf("error reading field 1: %s", err)
+ } else {
+ p.Key = v
+ }
+ return nil
+}
+
+func (p *KeyValue) ReadField2(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadString(); err != nil {
+ return fmt.Errorf("error reading field 2: %s", err)
+ } else {
+ p.Value = v
+ }
+ return nil
+}
+
+func (p *KeyValue) Write(oprot thrift.TProtocol) error {
+ if err := oprot.WriteStructBegin("KeyValue"); err != nil {
+ return fmt.Errorf("%T write struct begin error: %s", p, err)
+ }
+ if err := p.writeField1(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField2(oprot); err != nil {
+ return err
+ }
+ if err := oprot.WriteFieldStop(); err != nil {
+ return fmt.Errorf("write field stop error: %s", err)
+ }
+ if err := oprot.WriteStructEnd(); err != nil {
+ return fmt.Errorf("write struct stop error: %s", err)
+ }
+ return nil
+}
+
+func (p *KeyValue) writeField1(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("Key", thrift.STRING, 1); err != nil {
+ return fmt.Errorf("%T write field begin error 1:Key: %s", p, err)
+ }
+ if err := oprot.WriteString(string(p.Key)); err != nil {
+ return fmt.Errorf("%T.Key (1) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 1:Key: %s", p, err)
+ }
+ return err
+}
+
+func (p *KeyValue) writeField2(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("Value", thrift.STRING, 2); err != nil {
+ return fmt.Errorf("%T write field begin error 2:Value: %s", p, err)
+ }
+ if err := oprot.WriteString(string(p.Value)); err != nil {
+ return fmt.Errorf("%T.Value (2) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 2:Value: %s", p, err)
+ }
+ return err
+}
+
+func (p *KeyValue) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return fmt.Sprintf("KeyValue(%+v)", *p)
+}
+
+type NamedCounter struct {
+ Name string `thrift:"Name,1,required" json:"Name"`
+ Value int64 `thrift:"Value,2,required" json:"Value"`
+}
+
+func NewNamedCounter() *NamedCounter {
+ return &NamedCounter{}
+}
+
+func (p *NamedCounter) GetName() string {
+ return p.Name
+}
+
+func (p *NamedCounter) GetValue() int64 {
+ return p.Value
+}
+func (p *NamedCounter) Read(iprot thrift.TProtocol) error {
+ if _, err := iprot.ReadStructBegin(); err != nil {
+ return fmt.Errorf("%T read error: %s", p, err)
+ }
+ for {
+ _, fieldTypeId, fieldId, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return fmt.Errorf("%T field %d read error: %s", p, fieldId, err)
+ }
+ if fieldTypeId == thrift.STOP {
+ break
+ }
+ switch fieldId {
+ case 1:
+ if err := p.ReadField1(iprot); err != nil {
+ return err
+ }
+ case 2:
+ if err := p.ReadField2(iprot); err != nil {
+ return err
+ }
+ default:
+ if err := iprot.Skip(fieldTypeId); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadFieldEnd(); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadStructEnd(); err != nil {
+ return fmt.Errorf("%T read struct end error: %s", p, err)
+ }
+ return nil
+}
+
+func (p *NamedCounter) ReadField1(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadString(); err != nil {
+ return fmt.Errorf("error reading field 1: %s", err)
+ } else {
+ p.Name = v
+ }
+ return nil
+}
+
+func (p *NamedCounter) ReadField2(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadI64(); err != nil {
+ return fmt.Errorf("error reading field 2: %s", err)
+ } else {
+ p.Value = v
+ }
+ return nil
+}
+
+func (p *NamedCounter) Write(oprot thrift.TProtocol) error {
+ if err := oprot.WriteStructBegin("NamedCounter"); err != nil {
+ return fmt.Errorf("%T write struct begin error: %s", p, err)
+ }
+ if err := p.writeField1(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField2(oprot); err != nil {
+ return err
+ }
+ if err := oprot.WriteFieldStop(); err != nil {
+ return fmt.Errorf("write field stop error: %s", err)
+ }
+ if err := oprot.WriteStructEnd(); err != nil {
+ return fmt.Errorf("write struct stop error: %s", err)
+ }
+ return nil
+}
+
+func (p *NamedCounter) writeField1(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("Name", thrift.STRING, 1); err != nil {
+ return fmt.Errorf("%T write field begin error 1:Name: %s", p, err)
+ }
+ if err := oprot.WriteString(string(p.Name)); err != nil {
+ return fmt.Errorf("%T.Name (1) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 1:Name: %s", p, err)
+ }
+ return err
+}
+
+func (p *NamedCounter) writeField2(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("Value", thrift.I64, 2); err != nil {
+ return fmt.Errorf("%T write field begin error 2:Value: %s", p, err)
+ }
+ if err := oprot.WriteI64(int64(p.Value)); err != nil {
+ return fmt.Errorf("%T.Value (2) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 2:Value: %s", p, err)
+ }
+ return err
+}
+
+func (p *NamedCounter) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return fmt.Sprintf("NamedCounter(%+v)", *p)
+}
+
+type Runtime struct {
+ Guid *string `thrift:"guid,1" json:"guid"`
+ StartMicros *int64 `thrift:"start_micros,2" json:"start_micros"`
+ GroupName *string `thrift:"group_name,3" json:"group_name"`
+ Attrs []*KeyValue `thrift:"attrs,4" json:"attrs"`
+}
+
+func NewRuntime() *Runtime {
+ return &Runtime{}
+}
+
+var Runtime_Guid_DEFAULT string
+
+func (p *Runtime) GetGuid() string {
+ if !p.IsSetGuid() {
+ return Runtime_Guid_DEFAULT
+ }
+ return *p.Guid
+}
+
+var Runtime_StartMicros_DEFAULT int64
+
+func (p *Runtime) GetStartMicros() int64 {
+ if !p.IsSetStartMicros() {
+ return Runtime_StartMicros_DEFAULT
+ }
+ return *p.StartMicros
+}
+
+var Runtime_GroupName_DEFAULT string
+
+func (p *Runtime) GetGroupName() string {
+ if !p.IsSetGroupName() {
+ return Runtime_GroupName_DEFAULT
+ }
+ return *p.GroupName
+}
+
+var Runtime_Attrs_DEFAULT []*KeyValue
+
+func (p *Runtime) GetAttrs() []*KeyValue {
+ return p.Attrs
+}
+func (p *Runtime) IsSetGuid() bool {
+ return p.Guid != nil
+}
+
+func (p *Runtime) IsSetStartMicros() bool {
+ return p.StartMicros != nil
+}
+
+func (p *Runtime) IsSetGroupName() bool {
+ return p.GroupName != nil
+}
+
+func (p *Runtime) IsSetAttrs() bool {
+ return p.Attrs != nil
+}
+
+func (p *Runtime) Read(iprot thrift.TProtocol) error {
+ if _, err := iprot.ReadStructBegin(); err != nil {
+ return fmt.Errorf("%T read error: %s", p, err)
+ }
+ for {
+ _, fieldTypeId, fieldId, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return fmt.Errorf("%T field %d read error: %s", p, fieldId, err)
+ }
+ if fieldTypeId == thrift.STOP {
+ break
+ }
+ switch fieldId {
+ case 1:
+ if err := p.ReadField1(iprot); err != nil {
+ return err
+ }
+ case 2:
+ if err := p.ReadField2(iprot); err != nil {
+ return err
+ }
+ case 3:
+ if err := p.ReadField3(iprot); err != nil {
+ return err
+ }
+ case 4:
+ if err := p.ReadField4(iprot); err != nil {
+ return err
+ }
+ default:
+ if err := iprot.Skip(fieldTypeId); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadFieldEnd(); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadStructEnd(); err != nil {
+ return fmt.Errorf("%T read struct end error: %s", p, err)
+ }
+ return nil
+}
+
+func (p *Runtime) ReadField1(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadString(); err != nil {
+ return fmt.Errorf("error reading field 1: %s", err)
+ } else {
+ p.Guid = &v
+ }
+ return nil
+}
+
+func (p *Runtime) ReadField2(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadI64(); err != nil {
+ return fmt.Errorf("error reading field 2: %s", err)
+ } else {
+ p.StartMicros = &v
+ }
+ return nil
+}
+
+func (p *Runtime) ReadField3(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadString(); err != nil {
+ return fmt.Errorf("error reading field 3: %s", err)
+ } else {
+ p.GroupName = &v
+ }
+ return nil
+}
+
+func (p *Runtime) ReadField4(iprot thrift.TProtocol) error {
+ _, size, err := iprot.ReadListBegin()
+ if err != nil {
+ return fmt.Errorf("error reading list begin: %s", err)
+ }
+ tSlice := make([]*KeyValue, 0, size)
+ p.Attrs = tSlice
+ for i := 0; i < size; i++ {
+ _elem0 := &KeyValue{}
+ if err := _elem0.Read(iprot); err != nil {
+ return fmt.Errorf("%T error reading struct: %s", _elem0, err)
+ }
+ p.Attrs = append(p.Attrs, _elem0)
+ }
+ if err := iprot.ReadListEnd(); err != nil {
+ return fmt.Errorf("error reading list end: %s", err)
+ }
+ return nil
+}
+
+func (p *Runtime) Write(oprot thrift.TProtocol) error {
+ if err := oprot.WriteStructBegin("Runtime"); err != nil {
+ return fmt.Errorf("%T write struct begin error: %s", p, err)
+ }
+ if err := p.writeField1(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField2(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField3(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField4(oprot); err != nil {
+ return err
+ }
+ if err := oprot.WriteFieldStop(); err != nil {
+ return fmt.Errorf("write field stop error: %s", err)
+ }
+ if err := oprot.WriteStructEnd(); err != nil {
+ return fmt.Errorf("write struct stop error: %s", err)
+ }
+ return nil
+}
+
+func (p *Runtime) writeField1(oprot thrift.TProtocol) (err error) {
+ if p.IsSetGuid() {
+ if err := oprot.WriteFieldBegin("guid", thrift.STRING, 1); err != nil {
+ return fmt.Errorf("%T write field begin error 1:guid: %s", p, err)
+ }
+ if err := oprot.WriteString(string(*p.Guid)); err != nil {
+ return fmt.Errorf("%T.guid (1) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 1:guid: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *Runtime) writeField2(oprot thrift.TProtocol) (err error) {
+ if p.IsSetStartMicros() {
+ if err := oprot.WriteFieldBegin("start_micros", thrift.I64, 2); err != nil {
+ return fmt.Errorf("%T write field begin error 2:start_micros: %s", p, err)
+ }
+ if err := oprot.WriteI64(int64(*p.StartMicros)); err != nil {
+ return fmt.Errorf("%T.start_micros (2) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 2:start_micros: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *Runtime) writeField3(oprot thrift.TProtocol) (err error) {
+ if p.IsSetGroupName() {
+ if err := oprot.WriteFieldBegin("group_name", thrift.STRING, 3); err != nil {
+ return fmt.Errorf("%T write field begin error 3:group_name: %s", p, err)
+ }
+ if err := oprot.WriteString(string(*p.GroupName)); err != nil {
+ return fmt.Errorf("%T.group_name (3) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 3:group_name: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *Runtime) writeField4(oprot thrift.TProtocol) (err error) {
+ if p.IsSetAttrs() {
+ if err := oprot.WriteFieldBegin("attrs", thrift.LIST, 4); err != nil {
+ return fmt.Errorf("%T write field begin error 4:attrs: %s", p, err)
+ }
+ if err := oprot.WriteListBegin(thrift.STRUCT, len(p.Attrs)); err != nil {
+ return fmt.Errorf("error writing list begin: %s", err)
+ }
+ for _, v := range p.Attrs {
+ if err := v.Write(oprot); err != nil {
+ return fmt.Errorf("%T error writing struct: %s", v, err)
+ }
+ }
+ if err := oprot.WriteListEnd(); err != nil {
+ return fmt.Errorf("error writing list end: %s", err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 4:attrs: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *Runtime) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return fmt.Sprintf("Runtime(%+v)", *p)
+}
+
+type LogRecord struct {
+ TimestampMicros *int64 `thrift:"timestamp_micros,1" json:"timestamp_micros"`
+ RuntimeGuid *string `thrift:"runtime_guid,2" json:"runtime_guid"`
+ SpanGuid *string `thrift:"span_guid,3" json:"span_guid"`
+ StableName *string `thrift:"stable_name,4" json:"stable_name"`
+ Message *string `thrift:"message,5" json:"message"`
+ Level *string `thrift:"level,6" json:"level"`
+ ThreadId *int64 `thrift:"thread_id,7" json:"thread_id"`
+ Filename *string `thrift:"filename,8" json:"filename"`
+ LineNumber *int64 `thrift:"line_number,9" json:"line_number"`
+ StackFrames []string `thrift:"stack_frames,10" json:"stack_frames"`
+ PayloadJson *string `thrift:"payload_json,11" json:"payload_json"`
+ ErrorFlag *bool `thrift:"error_flag,12" json:"error_flag"`
+ Fields []*KeyValue `thrift:"fields,13" json:"fields"`
+}
+
+func NewLogRecord() *LogRecord {
+ return &LogRecord{}
+}
+
+var LogRecord_TimestampMicros_DEFAULT int64
+
+func (p *LogRecord) GetTimestampMicros() int64 {
+ if !p.IsSetTimestampMicros() {
+ return LogRecord_TimestampMicros_DEFAULT
+ }
+ return *p.TimestampMicros
+}
+
+var LogRecord_Fields_DEFAULT []*KeyValue
+
+func (p *LogRecord) GetFields() []*KeyValue {
+ return p.Fields
+}
+
+var LogRecord_RuntimeGuid_DEFAULT string
+
+func (p *LogRecord) GetRuntimeGuid() string {
+ if !p.IsSetRuntimeGuid() {
+ return LogRecord_RuntimeGuid_DEFAULT
+ }
+ return *p.RuntimeGuid
+}
+
+var LogRecord_SpanGuid_DEFAULT string
+
+func (p *LogRecord) GetSpanGuid() string {
+ if !p.IsSetSpanGuid() {
+ return LogRecord_SpanGuid_DEFAULT
+ }
+ return *p.SpanGuid
+}
+
+var LogRecord_StableName_DEFAULT string
+
+func (p *LogRecord) GetStableName() string {
+ if !p.IsSetStableName() {
+ return LogRecord_StableName_DEFAULT
+ }
+ return *p.StableName
+}
+
+var LogRecord_Message_DEFAULT string
+
+func (p *LogRecord) GetMessage() string {
+ if !p.IsSetMessage() {
+ return LogRecord_Message_DEFAULT
+ }
+ return *p.Message
+}
+
+var LogRecord_Level_DEFAULT string
+
+func (p *LogRecord) GetLevel() string {
+ if !p.IsSetLevel() {
+ return LogRecord_Level_DEFAULT
+ }
+ return *p.Level
+}
+
+var LogRecord_ThreadId_DEFAULT int64
+
+func (p *LogRecord) GetThreadId() int64 {
+ if !p.IsSetThreadId() {
+ return LogRecord_ThreadId_DEFAULT
+ }
+ return *p.ThreadId
+}
+
+var LogRecord_Filename_DEFAULT string
+
+func (p *LogRecord) GetFilename() string {
+ if !p.IsSetFilename() {
+ return LogRecord_Filename_DEFAULT
+ }
+ return *p.Filename
+}
+
+var LogRecord_LineNumber_DEFAULT int64
+
+func (p *LogRecord) GetLineNumber() int64 {
+ if !p.IsSetLineNumber() {
+ return LogRecord_LineNumber_DEFAULT
+ }
+ return *p.LineNumber
+}
+
+var LogRecord_StackFrames_DEFAULT []string
+
+func (p *LogRecord) GetStackFrames() []string {
+ return p.StackFrames
+}
+
+var LogRecord_PayloadJson_DEFAULT string
+
+func (p *LogRecord) GetPayloadJson() string {
+ if !p.IsSetPayloadJson() {
+ return LogRecord_PayloadJson_DEFAULT
+ }
+ return *p.PayloadJson
+}
+
+var LogRecord_ErrorFlag_DEFAULT bool
+
+func (p *LogRecord) GetErrorFlag() bool {
+ if !p.IsSetErrorFlag() {
+ return LogRecord_ErrorFlag_DEFAULT
+ }
+ return *p.ErrorFlag
+}
+func (p *LogRecord) IsSetTimestampMicros() bool {
+ return p.TimestampMicros != nil
+}
+
+func (p *LogRecord) IsSetFields() bool {
+ return p.Fields != nil
+}
+
+func (p *LogRecord) IsSetRuntimeGuid() bool {
+ return p.RuntimeGuid != nil
+}
+
+func (p *LogRecord) IsSetSpanGuid() bool {
+ return p.SpanGuid != nil
+}
+
+func (p *LogRecord) IsSetStableName() bool {
+ return p.StableName != nil
+}
+
+func (p *LogRecord) IsSetMessage() bool {
+ return p.Message != nil
+}
+
+func (p *LogRecord) IsSetLevel() bool {
+ return p.Level != nil
+}
+
+func (p *LogRecord) IsSetThreadId() bool {
+ return p.ThreadId != nil
+}
+
+func (p *LogRecord) IsSetFilename() bool {
+ return p.Filename != nil
+}
+
+func (p *LogRecord) IsSetLineNumber() bool {
+ return p.LineNumber != nil
+}
+
+func (p *LogRecord) IsSetStackFrames() bool {
+ return p.StackFrames != nil
+}
+
+func (p *LogRecord) IsSetPayloadJson() bool {
+ return p.PayloadJson != nil
+}
+
+func (p *LogRecord) IsSetErrorFlag() bool {
+ return p.ErrorFlag != nil
+}
+
+func (p *LogRecord) Read(iprot thrift.TProtocol) error {
+ if _, err := iprot.ReadStructBegin(); err != nil {
+ return fmt.Errorf("%T read error: %s", p, err)
+ }
+ for {
+ _, fieldTypeId, fieldId, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return fmt.Errorf("%T field %d read error: %s", p, fieldId, err)
+ }
+ if fieldTypeId == thrift.STOP {
+ break
+ }
+ switch fieldId {
+ case 1:
+ if err := p.ReadField1(iprot); err != nil {
+ return err
+ }
+ case 13:
+ if err := p.ReadField13(iprot); err != nil {
+ return err
+ }
+ case 2:
+ if err := p.ReadField2(iprot); err != nil {
+ return err
+ }
+ case 3:
+ if err := p.ReadField3(iprot); err != nil {
+ return err
+ }
+ case 4:
+ if err := p.ReadField4(iprot); err != nil {
+ return err
+ }
+ case 5:
+ if err := p.ReadField5(iprot); err != nil {
+ return err
+ }
+ case 6:
+ if err := p.ReadField6(iprot); err != nil {
+ return err
+ }
+ case 7:
+ if err := p.ReadField7(iprot); err != nil {
+ return err
+ }
+ case 8:
+ if err := p.ReadField8(iprot); err != nil {
+ return err
+ }
+ case 9:
+ if err := p.ReadField9(iprot); err != nil {
+ return err
+ }
+ case 10:
+ if err := p.ReadField10(iprot); err != nil {
+ return err
+ }
+ case 11:
+ if err := p.ReadField11(iprot); err != nil {
+ return err
+ }
+ case 12:
+ if err := p.ReadField12(iprot); err != nil {
+ return err
+ }
+ default:
+ if err := iprot.Skip(fieldTypeId); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadFieldEnd(); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadStructEnd(); err != nil {
+ return fmt.Errorf("%T read struct end error: %s", p, err)
+ }
+ return nil
+}
+
+func (p *LogRecord) ReadField1(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadI64(); err != nil {
+ return fmt.Errorf("error reading field 1: %s", err)
+ } else {
+ p.TimestampMicros = &v
+ }
+ return nil
+}
+
+func (p *LogRecord) ReadField13(iprot thrift.TProtocol) error {
+ _, size, err := iprot.ReadListBegin()
+ if err != nil {
+ return fmt.Errorf("error reading list begin: %s", err)
+ }
+ tSlice := make([]*KeyValue, 0, size)
+ p.Fields = tSlice
+ for i := 0; i < size; i++ {
+ _elem1 := &KeyValue{}
+ if err := _elem1.Read(iprot); err != nil {
+ return fmt.Errorf("%T error reading struct: %s", _elem1, err)
+ }
+ p.Fields = append(p.Fields, _elem1)
+ }
+ if err := iprot.ReadListEnd(); err != nil {
+ return fmt.Errorf("error reading list end: %s", err)
+ }
+ return nil
+}
+
+func (p *LogRecord) ReadField2(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadString(); err != nil {
+ return fmt.Errorf("error reading field 2: %s", err)
+ } else {
+ p.RuntimeGuid = &v
+ }
+ return nil
+}
+
+func (p *LogRecord) ReadField3(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadString(); err != nil {
+ return fmt.Errorf("error reading field 3: %s", err)
+ } else {
+ p.SpanGuid = &v
+ }
+ return nil
+}
+
+func (p *LogRecord) ReadField4(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadString(); err != nil {
+ return fmt.Errorf("error reading field 4: %s", err)
+ } else {
+ p.StableName = &v
+ }
+ return nil
+}
+
+func (p *LogRecord) ReadField5(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadString(); err != nil {
+ return fmt.Errorf("error reading field 5: %s", err)
+ } else {
+ p.Message = &v
+ }
+ return nil
+}
+
+func (p *LogRecord) ReadField6(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadString(); err != nil {
+ return fmt.Errorf("error reading field 6: %s", err)
+ } else {
+ p.Level = &v
+ }
+ return nil
+}
+
+func (p *LogRecord) ReadField7(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadI64(); err != nil {
+ return fmt.Errorf("error reading field 7: %s", err)
+ } else {
+ p.ThreadId = &v
+ }
+ return nil
+}
+
+func (p *LogRecord) ReadField8(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadString(); err != nil {
+ return fmt.Errorf("error reading field 8: %s", err)
+ } else {
+ p.Filename = &v
+ }
+ return nil
+}
+
+func (p *LogRecord) ReadField9(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadI64(); err != nil {
+ return fmt.Errorf("error reading field 9: %s", err)
+ } else {
+ p.LineNumber = &v
+ }
+ return nil
+}
+
+func (p *LogRecord) ReadField10(iprot thrift.TProtocol) error {
+ _, size, err := iprot.ReadListBegin()
+ if err != nil {
+ return fmt.Errorf("error reading list begin: %s", err)
+ }
+ tSlice := make([]string, 0, size)
+ p.StackFrames = tSlice
+ for i := 0; i < size; i++ {
+ var _elem2 string
+ if v, err := iprot.ReadString(); err != nil {
+ return fmt.Errorf("error reading field 0: %s", err)
+ } else {
+ _elem2 = v
+ }
+ p.StackFrames = append(p.StackFrames, _elem2)
+ }
+ if err := iprot.ReadListEnd(); err != nil {
+ return fmt.Errorf("error reading list end: %s", err)
+ }
+ return nil
+}
+
+func (p *LogRecord) ReadField11(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadString(); err != nil {
+ return fmt.Errorf("error reading field 11: %s", err)
+ } else {
+ p.PayloadJson = &v
+ }
+ return nil
+}
+
+func (p *LogRecord) ReadField12(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadBool(); err != nil {
+ return fmt.Errorf("error reading field 12: %s", err)
+ } else {
+ p.ErrorFlag = &v
+ }
+ return nil
+}
+
+func (p *LogRecord) Write(oprot thrift.TProtocol) error {
+ if err := oprot.WriteStructBegin("LogRecord"); err != nil {
+ return fmt.Errorf("%T write struct begin error: %s", p, err)
+ }
+ if err := p.writeField1(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField2(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField3(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField4(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField5(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField6(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField7(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField8(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField9(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField10(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField11(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField12(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField13(oprot); err != nil {
+ return err
+ }
+ if err := oprot.WriteFieldStop(); err != nil {
+ return fmt.Errorf("write field stop error: %s", err)
+ }
+ if err := oprot.WriteStructEnd(); err != nil {
+ return fmt.Errorf("write struct stop error: %s", err)
+ }
+ return nil
+}
+
+func (p *LogRecord) writeField1(oprot thrift.TProtocol) (err error) {
+ if p.IsSetTimestampMicros() {
+ if err := oprot.WriteFieldBegin("timestamp_micros", thrift.I64, 1); err != nil {
+ return fmt.Errorf("%T write field begin error 1:timestamp_micros: %s", p, err)
+ }
+ if err := oprot.WriteI64(int64(*p.TimestampMicros)); err != nil {
+ return fmt.Errorf("%T.timestamp_micros (1) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 1:timestamp_micros: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *LogRecord) writeField2(oprot thrift.TProtocol) (err error) {
+ if p.IsSetRuntimeGuid() {
+ if err := oprot.WriteFieldBegin("runtime_guid", thrift.STRING, 2); err != nil {
+ return fmt.Errorf("%T write field begin error 2:runtime_guid: %s", p, err)
+ }
+ if err := oprot.WriteString(string(*p.RuntimeGuid)); err != nil {
+ return fmt.Errorf("%T.runtime_guid (2) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 2:runtime_guid: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *LogRecord) writeField3(oprot thrift.TProtocol) (err error) {
+ if p.IsSetSpanGuid() {
+ if err := oprot.WriteFieldBegin("span_guid", thrift.STRING, 3); err != nil {
+ return fmt.Errorf("%T write field begin error 3:span_guid: %s", p, err)
+ }
+ if err := oprot.WriteString(string(*p.SpanGuid)); err != nil {
+ return fmt.Errorf("%T.span_guid (3) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 3:span_guid: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *LogRecord) writeField4(oprot thrift.TProtocol) (err error) {
+ if p.IsSetStableName() {
+ if err := oprot.WriteFieldBegin("stable_name", thrift.STRING, 4); err != nil {
+ return fmt.Errorf("%T write field begin error 4:stable_name: %s", p, err)
+ }
+ if err := oprot.WriteString(string(*p.StableName)); err != nil {
+ return fmt.Errorf("%T.stable_name (4) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 4:stable_name: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *LogRecord) writeField5(oprot thrift.TProtocol) (err error) {
+ if p.IsSetMessage() {
+ if err := oprot.WriteFieldBegin("message", thrift.STRING, 5); err != nil {
+ return fmt.Errorf("%T write field begin error 5:message: %s", p, err)
+ }
+ if err := oprot.WriteString(string(*p.Message)); err != nil {
+ return fmt.Errorf("%T.message (5) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 5:message: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *LogRecord) writeField6(oprot thrift.TProtocol) (err error) {
+ if p.IsSetLevel() {
+ if err := oprot.WriteFieldBegin("level", thrift.STRING, 6); err != nil {
+ return fmt.Errorf("%T write field begin error 6:level: %s", p, err)
+ }
+ if err := oprot.WriteString(string(*p.Level)); err != nil {
+ return fmt.Errorf("%T.level (6) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 6:level: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *LogRecord) writeField7(oprot thrift.TProtocol) (err error) {
+ if p.IsSetThreadId() {
+ if err := oprot.WriteFieldBegin("thread_id", thrift.I64, 7); err != nil {
+ return fmt.Errorf("%T write field begin error 7:thread_id: %s", p, err)
+ }
+ if err := oprot.WriteI64(int64(*p.ThreadId)); err != nil {
+ return fmt.Errorf("%T.thread_id (7) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 7:thread_id: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *LogRecord) writeField8(oprot thrift.TProtocol) (err error) {
+ if p.IsSetFilename() {
+ if err := oprot.WriteFieldBegin("filename", thrift.STRING, 8); err != nil {
+ return fmt.Errorf("%T write field begin error 8:filename: %s", p, err)
+ }
+ if err := oprot.WriteString(string(*p.Filename)); err != nil {
+ return fmt.Errorf("%T.filename (8) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 8:filename: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *LogRecord) writeField9(oprot thrift.TProtocol) (err error) {
+ if p.IsSetLineNumber() {
+ if err := oprot.WriteFieldBegin("line_number", thrift.I64, 9); err != nil {
+ return fmt.Errorf("%T write field begin error 9:line_number: %s", p, err)
+ }
+ if err := oprot.WriteI64(int64(*p.LineNumber)); err != nil {
+ return fmt.Errorf("%T.line_number (9) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 9:line_number: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *LogRecord) writeField10(oprot thrift.TProtocol) (err error) {
+ if p.IsSetStackFrames() {
+ if err := oprot.WriteFieldBegin("stack_frames", thrift.LIST, 10); err != nil {
+ return fmt.Errorf("%T write field begin error 10:stack_frames: %s", p, err)
+ }
+ if err := oprot.WriteListBegin(thrift.STRING, len(p.StackFrames)); err != nil {
+ return fmt.Errorf("error writing list begin: %s", err)
+ }
+ for _, v := range p.StackFrames {
+ if err := oprot.WriteString(string(v)); err != nil {
+ return fmt.Errorf("%T. (0) field write error: %s", p, err)
+ }
+ }
+ if err := oprot.WriteListEnd(); err != nil {
+ return fmt.Errorf("error writing list end: %s", err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 10:stack_frames: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *LogRecord) writeField11(oprot thrift.TProtocol) (err error) {
+ if p.IsSetPayloadJson() {
+ if err := oprot.WriteFieldBegin("payload_json", thrift.STRING, 11); err != nil {
+ return fmt.Errorf("%T write field begin error 11:payload_json: %s", p, err)
+ }
+ if err := oprot.WriteString(string(*p.PayloadJson)); err != nil {
+ return fmt.Errorf("%T.payload_json (11) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 11:payload_json: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *LogRecord) writeField12(oprot thrift.TProtocol) (err error) {
+ if p.IsSetErrorFlag() {
+ if err := oprot.WriteFieldBegin("error_flag", thrift.BOOL, 12); err != nil {
+ return fmt.Errorf("%T write field begin error 12:error_flag: %s", p, err)
+ }
+ if err := oprot.WriteBool(bool(*p.ErrorFlag)); err != nil {
+ return fmt.Errorf("%T.error_flag (12) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 12:error_flag: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *LogRecord) writeField13(oprot thrift.TProtocol) (err error) {
+ if p.IsSetFields() {
+ if err := oprot.WriteFieldBegin("fields", thrift.LIST, 13); err != nil {
+ return fmt.Errorf("%T write field begin error 13:fields: %s", p, err)
+ }
+ if err := oprot.WriteListBegin(thrift.STRUCT, len(p.Fields)); err != nil {
+ return fmt.Errorf("error writing list begin: %s", err)
+ }
+ for _, v := range p.Fields {
+ if err := v.Write(oprot); err != nil {
+ return fmt.Errorf("%T error writing struct: %s", v, err)
+ }
+ }
+ if err := oprot.WriteListEnd(); err != nil {
+ return fmt.Errorf("error writing list end: %s", err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 13:fields: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *LogRecord) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return fmt.Sprintf("LogRecord(%+v)", *p)
+}
+
+type TraceJoinId struct {
+ TraceKey string `thrift:"TraceKey,1,required" json:"TraceKey"`
+ Value string `thrift:"Value,2,required" json:"Value"`
+}
+
+func NewTraceJoinId() *TraceJoinId {
+ return &TraceJoinId{}
+}
+
+func (p *TraceJoinId) GetTraceKey() string {
+ return p.TraceKey
+}
+
+func (p *TraceJoinId) GetValue() string {
+ return p.Value
+}
+func (p *TraceJoinId) Read(iprot thrift.TProtocol) error {
+ if _, err := iprot.ReadStructBegin(); err != nil {
+ return fmt.Errorf("%T read error: %s", p, err)
+ }
+ for {
+ _, fieldTypeId, fieldId, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return fmt.Errorf("%T field %d read error: %s", p, fieldId, err)
+ }
+ if fieldTypeId == thrift.STOP {
+ break
+ }
+ switch fieldId {
+ case 1:
+ if err := p.ReadField1(iprot); err != nil {
+ return err
+ }
+ case 2:
+ if err := p.ReadField2(iprot); err != nil {
+ return err
+ }
+ default:
+ if err := iprot.Skip(fieldTypeId); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadFieldEnd(); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadStructEnd(); err != nil {
+ return fmt.Errorf("%T read struct end error: %s", p, err)
+ }
+ return nil
+}
+
+func (p *TraceJoinId) ReadField1(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadString(); err != nil {
+ return fmt.Errorf("error reading field 1: %s", err)
+ } else {
+ p.TraceKey = v
+ }
+ return nil
+}
+
+func (p *TraceJoinId) ReadField2(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadString(); err != nil {
+ return fmt.Errorf("error reading field 2: %s", err)
+ } else {
+ p.Value = v
+ }
+ return nil
+}
+
+func (p *TraceJoinId) Write(oprot thrift.TProtocol) error {
+ if err := oprot.WriteStructBegin("TraceJoinId"); err != nil {
+ return fmt.Errorf("%T write struct begin error: %s", p, err)
+ }
+ if err := p.writeField1(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField2(oprot); err != nil {
+ return err
+ }
+ if err := oprot.WriteFieldStop(); err != nil {
+ return fmt.Errorf("write field stop error: %s", err)
+ }
+ if err := oprot.WriteStructEnd(); err != nil {
+ return fmt.Errorf("write struct stop error: %s", err)
+ }
+ return nil
+}
+
+func (p *TraceJoinId) writeField1(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("TraceKey", thrift.STRING, 1); err != nil {
+ return fmt.Errorf("%T write field begin error 1:TraceKey: %s", p, err)
+ }
+ if err := oprot.WriteString(string(p.TraceKey)); err != nil {
+ return fmt.Errorf("%T.TraceKey (1) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 1:TraceKey: %s", p, err)
+ }
+ return err
+}
+
+func (p *TraceJoinId) writeField2(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("Value", thrift.STRING, 2); err != nil {
+ return fmt.Errorf("%T write field begin error 2:Value: %s", p, err)
+ }
+ if err := oprot.WriteString(string(p.Value)); err != nil {
+ return fmt.Errorf("%T.Value (2) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 2:Value: %s", p, err)
+ }
+ return err
+}
+
+func (p *TraceJoinId) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return fmt.Sprintf("TraceJoinId(%+v)", *p)
+}
+
+type SpanRecord struct {
+ SpanGuid *string `thrift:"span_guid,1" json:"span_guid"`
+ RuntimeGuid *string `thrift:"runtime_guid,2" json:"runtime_guid"`
+ SpanName *string `thrift:"span_name,3" json:"span_name"`
+ JoinIds []*TraceJoinId `thrift:"join_ids,4" json:"join_ids"`
+ OldestMicros *int64 `thrift:"oldest_micros,5" json:"oldest_micros"`
+ YoungestMicros *int64 `thrift:"youngest_micros,6" json:"youngest_micros"`
+ // unused field # 7
+ Attributes []*KeyValue `thrift:"attributes,8" json:"attributes"`
+ ErrorFlag *bool `thrift:"error_flag,9" json:"error_flag"`
+ LogRecords []*LogRecord `thrift:"log_records,10" json:"log_records"`
+ TraceGuid *string `thrift:"trace_guid,11" json:"trace_guid"`
+}
+
+func NewSpanRecord() *SpanRecord {
+ return &SpanRecord{}
+}
+
+var SpanRecord_SpanGuid_DEFAULT string
+
+func (p *SpanRecord) GetSpanGuid() string {
+ if !p.IsSetSpanGuid() {
+ return SpanRecord_SpanGuid_DEFAULT
+ }
+ return *p.SpanGuid
+}
+
+var SpanRecord_TraceGuid_DEFAULT string
+
+func (p *SpanRecord) GetTraceGuid() string {
+ if !p.IsSetTraceGuid() {
+ return SpanRecord_TraceGuid_DEFAULT
+ }
+ return *p.TraceGuid
+}
+
+var SpanRecord_RuntimeGuid_DEFAULT string
+
+func (p *SpanRecord) GetRuntimeGuid() string {
+ if !p.IsSetRuntimeGuid() {
+ return SpanRecord_RuntimeGuid_DEFAULT
+ }
+ return *p.RuntimeGuid
+}
+
+var SpanRecord_SpanName_DEFAULT string
+
+func (p *SpanRecord) GetSpanName() string {
+ if !p.IsSetSpanName() {
+ return SpanRecord_SpanName_DEFAULT
+ }
+ return *p.SpanName
+}
+
+var SpanRecord_JoinIds_DEFAULT []*TraceJoinId
+
+func (p *SpanRecord) GetJoinIds() []*TraceJoinId {
+ return p.JoinIds
+}
+
+var SpanRecord_OldestMicros_DEFAULT int64
+
+func (p *SpanRecord) GetOldestMicros() int64 {
+ if !p.IsSetOldestMicros() {
+ return SpanRecord_OldestMicros_DEFAULT
+ }
+ return *p.OldestMicros
+}
+
+var SpanRecord_YoungestMicros_DEFAULT int64
+
+func (p *SpanRecord) GetYoungestMicros() int64 {
+ if !p.IsSetYoungestMicros() {
+ return SpanRecord_YoungestMicros_DEFAULT
+ }
+ return *p.YoungestMicros
+}
+
+var SpanRecord_Attributes_DEFAULT []*KeyValue
+
+func (p *SpanRecord) GetAttributes() []*KeyValue {
+ return p.Attributes
+}
+
+var SpanRecord_ErrorFlag_DEFAULT bool
+
+func (p *SpanRecord) GetErrorFlag() bool {
+ if !p.IsSetErrorFlag() {
+ return SpanRecord_ErrorFlag_DEFAULT
+ }
+ return *p.ErrorFlag
+}
+
+var SpanRecord_LogRecords_DEFAULT []*LogRecord
+
+func (p *SpanRecord) GetLogRecords() []*LogRecord {
+ return p.LogRecords
+}
+func (p *SpanRecord) IsSetSpanGuid() bool {
+ return p.SpanGuid != nil
+}
+
+func (p *SpanRecord) IsSetTraceGuid() bool {
+ return p.TraceGuid != nil
+}
+
+func (p *SpanRecord) IsSetRuntimeGuid() bool {
+ return p.RuntimeGuid != nil
+}
+
+func (p *SpanRecord) IsSetSpanName() bool {
+ return p.SpanName != nil
+}
+
+func (p *SpanRecord) IsSetJoinIds() bool {
+ return p.JoinIds != nil
+}
+
+func (p *SpanRecord) IsSetOldestMicros() bool {
+ return p.OldestMicros != nil
+}
+
+func (p *SpanRecord) IsSetYoungestMicros() bool {
+ return p.YoungestMicros != nil
+}
+
+func (p *SpanRecord) IsSetAttributes() bool {
+ return p.Attributes != nil
+}
+
+func (p *SpanRecord) IsSetErrorFlag() bool {
+ return p.ErrorFlag != nil
+}
+
+func (p *SpanRecord) IsSetLogRecords() bool {
+ return p.LogRecords != nil
+}
+
+func (p *SpanRecord) Read(iprot thrift.TProtocol) error {
+ if _, err := iprot.ReadStructBegin(); err != nil {
+ return fmt.Errorf("%T read error: %s", p, err)
+ }
+ for {
+ _, fieldTypeId, fieldId, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return fmt.Errorf("%T field %d read error: %s", p, fieldId, err)
+ }
+ if fieldTypeId == thrift.STOP {
+ break
+ }
+ switch fieldId {
+ case 1:
+ if err := p.ReadField1(iprot); err != nil {
+ return err
+ }
+ case 11:
+ if err := p.ReadField11(iprot); err != nil {
+ return err
+ }
+ case 2:
+ if err := p.ReadField2(iprot); err != nil {
+ return err
+ }
+ case 3:
+ if err := p.ReadField3(iprot); err != nil {
+ return err
+ }
+ case 4:
+ if err := p.ReadField4(iprot); err != nil {
+ return err
+ }
+ case 5:
+ if err := p.ReadField5(iprot); err != nil {
+ return err
+ }
+ case 6:
+ if err := p.ReadField6(iprot); err != nil {
+ return err
+ }
+ case 8:
+ if err := p.ReadField8(iprot); err != nil {
+ return err
+ }
+ case 9:
+ if err := p.ReadField9(iprot); err != nil {
+ return err
+ }
+ case 10:
+ if err := p.ReadField10(iprot); err != nil {
+ return err
+ }
+ default:
+ if err := iprot.Skip(fieldTypeId); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadFieldEnd(); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadStructEnd(); err != nil {
+ return fmt.Errorf("%T read struct end error: %s", p, err)
+ }
+ return nil
+}
+
+func (p *SpanRecord) ReadField1(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadString(); err != nil {
+ return fmt.Errorf("error reading field 1: %s", err)
+ } else {
+ p.SpanGuid = &v
+ }
+ return nil
+}
+
+func (p *SpanRecord) ReadField11(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadString(); err != nil {
+ return fmt.Errorf("error reading field 11: %s", err)
+ } else {
+ p.TraceGuid = &v
+ }
+ return nil
+}
+
+func (p *SpanRecord) ReadField2(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadString(); err != nil {
+ return fmt.Errorf("error reading field 2: %s", err)
+ } else {
+ p.RuntimeGuid = &v
+ }
+ return nil
+}
+
+func (p *SpanRecord) ReadField3(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadString(); err != nil {
+ return fmt.Errorf("error reading field 3: %s", err)
+ } else {
+ p.SpanName = &v
+ }
+ return nil
+}
+
+func (p *SpanRecord) ReadField4(iprot thrift.TProtocol) error {
+ _, size, err := iprot.ReadListBegin()
+ if err != nil {
+ return fmt.Errorf("error reading list begin: %s", err)
+ }
+ tSlice := make([]*TraceJoinId, 0, size)
+ p.JoinIds = tSlice
+ for i := 0; i < size; i++ {
+ _elem3 := &TraceJoinId{}
+ if err := _elem3.Read(iprot); err != nil {
+ return fmt.Errorf("%T error reading struct: %s", _elem3, err)
+ }
+ p.JoinIds = append(p.JoinIds, _elem3)
+ }
+ if err := iprot.ReadListEnd(); err != nil {
+ return fmt.Errorf("error reading list end: %s", err)
+ }
+ return nil
+}
+
+func (p *SpanRecord) ReadField5(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadI64(); err != nil {
+ return fmt.Errorf("error reading field 5: %s", err)
+ } else {
+ p.OldestMicros = &v
+ }
+ return nil
+}
+
+func (p *SpanRecord) ReadField6(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadI64(); err != nil {
+ return fmt.Errorf("error reading field 6: %s", err)
+ } else {
+ p.YoungestMicros = &v
+ }
+ return nil
+}
+
+func (p *SpanRecord) ReadField8(iprot thrift.TProtocol) error {
+ _, size, err := iprot.ReadListBegin()
+ if err != nil {
+ return fmt.Errorf("error reading list begin: %s", err)
+ }
+ tSlice := make([]*KeyValue, 0, size)
+ p.Attributes = tSlice
+ for i := 0; i < size; i++ {
+ _elem4 := &KeyValue{}
+ if err := _elem4.Read(iprot); err != nil {
+ return fmt.Errorf("%T error reading struct: %s", _elem4, err)
+ }
+ p.Attributes = append(p.Attributes, _elem4)
+ }
+ if err := iprot.ReadListEnd(); err != nil {
+ return fmt.Errorf("error reading list end: %s", err)
+ }
+ return nil
+}
+
+func (p *SpanRecord) ReadField9(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadBool(); err != nil {
+ return fmt.Errorf("error reading field 9: %s", err)
+ } else {
+ p.ErrorFlag = &v
+ }
+ return nil
+}
+
+func (p *SpanRecord) ReadField10(iprot thrift.TProtocol) error {
+ _, size, err := iprot.ReadListBegin()
+ if err != nil {
+ return fmt.Errorf("error reading list begin: %s", err)
+ }
+ tSlice := make([]*LogRecord, 0, size)
+ p.LogRecords = tSlice
+ for i := 0; i < size; i++ {
+ _elem5 := &LogRecord{}
+ if err := _elem5.Read(iprot); err != nil {
+ return fmt.Errorf("%T error reading struct: %s", _elem5, err)
+ }
+ p.LogRecords = append(p.LogRecords, _elem5)
+ }
+ if err := iprot.ReadListEnd(); err != nil {
+ return fmt.Errorf("error reading list end: %s", err)
+ }
+ return nil
+}
+
+func (p *SpanRecord) Write(oprot thrift.TProtocol) error {
+ if err := oprot.WriteStructBegin("SpanRecord"); err != nil {
+ return fmt.Errorf("%T write struct begin error: %s", p, err)
+ }
+ if err := p.writeField1(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField2(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField3(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField4(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField5(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField6(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField8(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField9(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField10(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField11(oprot); err != nil {
+ return err
+ }
+ if err := oprot.WriteFieldStop(); err != nil {
+ return fmt.Errorf("write field stop error: %s", err)
+ }
+ if err := oprot.WriteStructEnd(); err != nil {
+ return fmt.Errorf("write struct stop error: %s", err)
+ }
+ return nil
+}
+
+func (p *SpanRecord) writeField1(oprot thrift.TProtocol) (err error) {
+ if p.IsSetSpanGuid() {
+ if err := oprot.WriteFieldBegin("span_guid", thrift.STRING, 1); err != nil {
+ return fmt.Errorf("%T write field begin error 1:span_guid: %s", p, err)
+ }
+ if err := oprot.WriteString(string(*p.SpanGuid)); err != nil {
+ return fmt.Errorf("%T.span_guid (1) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 1:span_guid: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *SpanRecord) writeField2(oprot thrift.TProtocol) (err error) {
+ if p.IsSetRuntimeGuid() {
+ if err := oprot.WriteFieldBegin("runtime_guid", thrift.STRING, 2); err != nil {
+ return fmt.Errorf("%T write field begin error 2:runtime_guid: %s", p, err)
+ }
+ if err := oprot.WriteString(string(*p.RuntimeGuid)); err != nil {
+ return fmt.Errorf("%T.runtime_guid (2) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 2:runtime_guid: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *SpanRecord) writeField3(oprot thrift.TProtocol) (err error) {
+ if p.IsSetSpanName() {
+ if err := oprot.WriteFieldBegin("span_name", thrift.STRING, 3); err != nil {
+ return fmt.Errorf("%T write field begin error 3:span_name: %s", p, err)
+ }
+ if err := oprot.WriteString(string(*p.SpanName)); err != nil {
+ return fmt.Errorf("%T.span_name (3) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 3:span_name: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *SpanRecord) writeField4(oprot thrift.TProtocol) (err error) {
+ if p.IsSetJoinIds() {
+ if err := oprot.WriteFieldBegin("join_ids", thrift.LIST, 4); err != nil {
+ return fmt.Errorf("%T write field begin error 4:join_ids: %s", p, err)
+ }
+ if err := oprot.WriteListBegin(thrift.STRUCT, len(p.JoinIds)); err != nil {
+ return fmt.Errorf("error writing list begin: %s", err)
+ }
+ for _, v := range p.JoinIds {
+ if err := v.Write(oprot); err != nil {
+ return fmt.Errorf("%T error writing struct: %s", v, err)
+ }
+ }
+ if err := oprot.WriteListEnd(); err != nil {
+ return fmt.Errorf("error writing list end: %s", err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 4:join_ids: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *SpanRecord) writeField5(oprot thrift.TProtocol) (err error) {
+ if p.IsSetOldestMicros() {
+ if err := oprot.WriteFieldBegin("oldest_micros", thrift.I64, 5); err != nil {
+ return fmt.Errorf("%T write field begin error 5:oldest_micros: %s", p, err)
+ }
+ if err := oprot.WriteI64(int64(*p.OldestMicros)); err != nil {
+ return fmt.Errorf("%T.oldest_micros (5) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 5:oldest_micros: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *SpanRecord) writeField6(oprot thrift.TProtocol) (err error) {
+ if p.IsSetYoungestMicros() {
+ if err := oprot.WriteFieldBegin("youngest_micros", thrift.I64, 6); err != nil {
+ return fmt.Errorf("%T write field begin error 6:youngest_micros: %s", p, err)
+ }
+ if err := oprot.WriteI64(int64(*p.YoungestMicros)); err != nil {
+ return fmt.Errorf("%T.youngest_micros (6) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 6:youngest_micros: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *SpanRecord) writeField8(oprot thrift.TProtocol) (err error) {
+ if p.IsSetAttributes() {
+ if err := oprot.WriteFieldBegin("attributes", thrift.LIST, 8); err != nil {
+ return fmt.Errorf("%T write field begin error 8:attributes: %s", p, err)
+ }
+ if err := oprot.WriteListBegin(thrift.STRUCT, len(p.Attributes)); err != nil {
+ return fmt.Errorf("error writing list begin: %s", err)
+ }
+ for _, v := range p.Attributes {
+ if err := v.Write(oprot); err != nil {
+ return fmt.Errorf("%T error writing struct: %s", v, err)
+ }
+ }
+ if err := oprot.WriteListEnd(); err != nil {
+ return fmt.Errorf("error writing list end: %s", err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 8:attributes: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *SpanRecord) writeField9(oprot thrift.TProtocol) (err error) {
+ if p.IsSetErrorFlag() {
+ if err := oprot.WriteFieldBegin("error_flag", thrift.BOOL, 9); err != nil {
+ return fmt.Errorf("%T write field begin error 9:error_flag: %s", p, err)
+ }
+ if err := oprot.WriteBool(bool(*p.ErrorFlag)); err != nil {
+ return fmt.Errorf("%T.error_flag (9) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 9:error_flag: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *SpanRecord) writeField10(oprot thrift.TProtocol) (err error) {
+ if p.IsSetLogRecords() {
+ if err := oprot.WriteFieldBegin("log_records", thrift.LIST, 10); err != nil {
+ return fmt.Errorf("%T write field begin error 10:log_records: %s", p, err)
+ }
+ if err := oprot.WriteListBegin(thrift.STRUCT, len(p.LogRecords)); err != nil {
+ return fmt.Errorf("error writing list begin: %s", err)
+ }
+ for _, v := range p.LogRecords {
+ if err := v.Write(oprot); err != nil {
+ return fmt.Errorf("%T error writing struct: %s", v, err)
+ }
+ }
+ if err := oprot.WriteListEnd(); err != nil {
+ return fmt.Errorf("error writing list end: %s", err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 10:log_records: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *SpanRecord) writeField11(oprot thrift.TProtocol) (err error) {
+ if p.IsSetTraceGuid() {
+ if err := oprot.WriteFieldBegin("trace_guid", thrift.STRING, 11); err != nil {
+ return fmt.Errorf("%T write field begin error 11:trace_guid: %s", p, err)
+ }
+ if err := oprot.WriteString(string(*p.TraceGuid)); err != nil {
+ return fmt.Errorf("%T.trace_guid (11) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 11:trace_guid: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *SpanRecord) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return fmt.Sprintf("SpanRecord(%+v)", *p)
+}
+
+type Auth struct {
+ AccessToken *string `thrift:"access_token,1" json:"access_token"`
+}
+
+func NewAuth() *Auth {
+ return &Auth{}
+}
+
+var Auth_AccessToken_DEFAULT string
+
+func (p *Auth) GetAccessToken() string {
+ if !p.IsSetAccessToken() {
+ return Auth_AccessToken_DEFAULT
+ }
+ return *p.AccessToken
+}
+func (p *Auth) IsSetAccessToken() bool {
+ return p.AccessToken != nil
+}
+
+func (p *Auth) Read(iprot thrift.TProtocol) error {
+ if _, err := iprot.ReadStructBegin(); err != nil {
+ return fmt.Errorf("%T read error: %s", p, err)
+ }
+ for {
+ _, fieldTypeId, fieldId, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return fmt.Errorf("%T field %d read error: %s", p, fieldId, err)
+ }
+ if fieldTypeId == thrift.STOP {
+ break
+ }
+ switch fieldId {
+ case 1:
+ if err := p.ReadField1(iprot); err != nil {
+ return err
+ }
+ default:
+ if err := iprot.Skip(fieldTypeId); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadFieldEnd(); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadStructEnd(); err != nil {
+ return fmt.Errorf("%T read struct end error: %s", p, err)
+ }
+ return nil
+}
+
+func (p *Auth) ReadField1(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadString(); err != nil {
+ return fmt.Errorf("error reading field 1: %s", err)
+ } else {
+ p.AccessToken = &v
+ }
+ return nil
+}
+
+func (p *Auth) Write(oprot thrift.TProtocol) error {
+ if err := oprot.WriteStructBegin("Auth"); err != nil {
+ return fmt.Errorf("%T write struct begin error: %s", p, err)
+ }
+ if err := p.writeField1(oprot); err != nil {
+ return err
+ }
+ if err := oprot.WriteFieldStop(); err != nil {
+ return fmt.Errorf("write field stop error: %s", err)
+ }
+ if err := oprot.WriteStructEnd(); err != nil {
+ return fmt.Errorf("write struct stop error: %s", err)
+ }
+ return nil
+}
+
+func (p *Auth) writeField1(oprot thrift.TProtocol) (err error) {
+ if p.IsSetAccessToken() {
+ if err := oprot.WriteFieldBegin("access_token", thrift.STRING, 1); err != nil {
+ return fmt.Errorf("%T write field begin error 1:access_token: %s", p, err)
+ }
+ if err := oprot.WriteString(string(*p.AccessToken)); err != nil {
+ return fmt.Errorf("%T.access_token (1) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 1:access_token: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *Auth) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return fmt.Sprintf("Auth(%+v)", *p)
+}
+
+type Timing struct {
+ ReceiveMicros *int64 `thrift:"receive_micros,1" json:"receive_micros"`
+ TransmitMicros *int64 `thrift:"transmit_micros,2" json:"transmit_micros"`
+}
+
+func NewTiming() *Timing {
+ return &Timing{}
+}
+
+var Timing_ReceiveMicros_DEFAULT int64
+
+func (p *Timing) GetReceiveMicros() int64 {
+ if !p.IsSetReceiveMicros() {
+ return Timing_ReceiveMicros_DEFAULT
+ }
+ return *p.ReceiveMicros
+}
+
+var Timing_TransmitMicros_DEFAULT int64
+
+func (p *Timing) GetTransmitMicros() int64 {
+ if !p.IsSetTransmitMicros() {
+ return Timing_TransmitMicros_DEFAULT
+ }
+ return *p.TransmitMicros
+}
+func (p *Timing) IsSetReceiveMicros() bool {
+ return p.ReceiveMicros != nil
+}
+
+func (p *Timing) IsSetTransmitMicros() bool {
+ return p.TransmitMicros != nil
+}
+
+func (p *Timing) Read(iprot thrift.TProtocol) error {
+ if _, err := iprot.ReadStructBegin(); err != nil {
+ return fmt.Errorf("%T read error: %s", p, err)
+ }
+ for {
+ _, fieldTypeId, fieldId, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return fmt.Errorf("%T field %d read error: %s", p, fieldId, err)
+ }
+ if fieldTypeId == thrift.STOP {
+ break
+ }
+ switch fieldId {
+ case 1:
+ if err := p.ReadField1(iprot); err != nil {
+ return err
+ }
+ case 2:
+ if err := p.ReadField2(iprot); err != nil {
+ return err
+ }
+ default:
+ if err := iprot.Skip(fieldTypeId); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadFieldEnd(); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadStructEnd(); err != nil {
+ return fmt.Errorf("%T read struct end error: %s", p, err)
+ }
+ return nil
+}
+
+func (p *Timing) ReadField1(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadI64(); err != nil {
+ return fmt.Errorf("error reading field 1: %s", err)
+ } else {
+ p.ReceiveMicros = &v
+ }
+ return nil
+}
+
+func (p *Timing) ReadField2(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadI64(); err != nil {
+ return fmt.Errorf("error reading field 2: %s", err)
+ } else {
+ p.TransmitMicros = &v
+ }
+ return nil
+}
+
+func (p *Timing) Write(oprot thrift.TProtocol) error {
+ if err := oprot.WriteStructBegin("Timing"); err != nil {
+ return fmt.Errorf("%T write struct begin error: %s", p, err)
+ }
+ if err := p.writeField1(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField2(oprot); err != nil {
+ return err
+ }
+ if err := oprot.WriteFieldStop(); err != nil {
+ return fmt.Errorf("write field stop error: %s", err)
+ }
+ if err := oprot.WriteStructEnd(); err != nil {
+ return fmt.Errorf("write struct stop error: %s", err)
+ }
+ return nil
+}
+
+func (p *Timing) writeField1(oprot thrift.TProtocol) (err error) {
+ if p.IsSetReceiveMicros() {
+ if err := oprot.WriteFieldBegin("receive_micros", thrift.I64, 1); err != nil {
+ return fmt.Errorf("%T write field begin error 1:receive_micros: %s", p, err)
+ }
+ if err := oprot.WriteI64(int64(*p.ReceiveMicros)); err != nil {
+ return fmt.Errorf("%T.receive_micros (1) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 1:receive_micros: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *Timing) writeField2(oprot thrift.TProtocol) (err error) {
+ if p.IsSetTransmitMicros() {
+ if err := oprot.WriteFieldBegin("transmit_micros", thrift.I64, 2); err != nil {
+ return fmt.Errorf("%T write field begin error 2:transmit_micros: %s", p, err)
+ }
+ if err := oprot.WriteI64(int64(*p.TransmitMicros)); err != nil {
+ return fmt.Errorf("%T.transmit_micros (2) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 2:transmit_micros: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *Timing) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return fmt.Sprintf("Timing(%+v)", *p)
+}
+
+type SampleCount struct {
+ OldestMicros *int64 `thrift:"oldest_micros,1" json:"oldest_micros"`
+ YoungestMicros *int64 `thrift:"youngest_micros,2" json:"youngest_micros"`
+ Count *int64 `thrift:"count,3" json:"count"`
+}
+
+func NewSampleCount() *SampleCount {
+ return &SampleCount{}
+}
+
+var SampleCount_OldestMicros_DEFAULT int64
+
+func (p *SampleCount) GetOldestMicros() int64 {
+ if !p.IsSetOldestMicros() {
+ return SampleCount_OldestMicros_DEFAULT
+ }
+ return *p.OldestMicros
+}
+
+var SampleCount_YoungestMicros_DEFAULT int64
+
+func (p *SampleCount) GetYoungestMicros() int64 {
+ if !p.IsSetYoungestMicros() {
+ return SampleCount_YoungestMicros_DEFAULT
+ }
+ return *p.YoungestMicros
+}
+
+var SampleCount_Count_DEFAULT int64
+
+func (p *SampleCount) GetCount() int64 {
+ if !p.IsSetCount() {
+ return SampleCount_Count_DEFAULT
+ }
+ return *p.Count
+}
+func (p *SampleCount) IsSetOldestMicros() bool {
+ return p.OldestMicros != nil
+}
+
+func (p *SampleCount) IsSetYoungestMicros() bool {
+ return p.YoungestMicros != nil
+}
+
+func (p *SampleCount) IsSetCount() bool {
+ return p.Count != nil
+}
+
+func (p *SampleCount) Read(iprot thrift.TProtocol) error {
+ if _, err := iprot.ReadStructBegin(); err != nil {
+ return fmt.Errorf("%T read error: %s", p, err)
+ }
+ for {
+ _, fieldTypeId, fieldId, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return fmt.Errorf("%T field %d read error: %s", p, fieldId, err)
+ }
+ if fieldTypeId == thrift.STOP {
+ break
+ }
+ switch fieldId {
+ case 1:
+ if err := p.ReadField1(iprot); err != nil {
+ return err
+ }
+ case 2:
+ if err := p.ReadField2(iprot); err != nil {
+ return err
+ }
+ case 3:
+ if err := p.ReadField3(iprot); err != nil {
+ return err
+ }
+ default:
+ if err := iprot.Skip(fieldTypeId); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadFieldEnd(); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadStructEnd(); err != nil {
+ return fmt.Errorf("%T read struct end error: %s", p, err)
+ }
+ return nil
+}
+
+func (p *SampleCount) ReadField1(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadI64(); err != nil {
+ return fmt.Errorf("error reading field 1: %s", err)
+ } else {
+ p.OldestMicros = &v
+ }
+ return nil
+}
+
+func (p *SampleCount) ReadField2(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadI64(); err != nil {
+ return fmt.Errorf("error reading field 2: %s", err)
+ } else {
+ p.YoungestMicros = &v
+ }
+ return nil
+}
+
+func (p *SampleCount) ReadField3(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadI64(); err != nil {
+ return fmt.Errorf("error reading field 3: %s", err)
+ } else {
+ p.Count = &v
+ }
+ return nil
+}
+
+func (p *SampleCount) Write(oprot thrift.TProtocol) error {
+ if err := oprot.WriteStructBegin("SampleCount"); err != nil {
+ return fmt.Errorf("%T write struct begin error: %s", p, err)
+ }
+ if err := p.writeField1(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField2(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField3(oprot); err != nil {
+ return err
+ }
+ if err := oprot.WriteFieldStop(); err != nil {
+ return fmt.Errorf("write field stop error: %s", err)
+ }
+ if err := oprot.WriteStructEnd(); err != nil {
+ return fmt.Errorf("write struct stop error: %s", err)
+ }
+ return nil
+}
+
+func (p *SampleCount) writeField1(oprot thrift.TProtocol) (err error) {
+ if p.IsSetOldestMicros() {
+ if err := oprot.WriteFieldBegin("oldest_micros", thrift.I64, 1); err != nil {
+ return fmt.Errorf("%T write field begin error 1:oldest_micros: %s", p, err)
+ }
+ if err := oprot.WriteI64(int64(*p.OldestMicros)); err != nil {
+ return fmt.Errorf("%T.oldest_micros (1) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 1:oldest_micros: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *SampleCount) writeField2(oprot thrift.TProtocol) (err error) {
+ if p.IsSetYoungestMicros() {
+ if err := oprot.WriteFieldBegin("youngest_micros", thrift.I64, 2); err != nil {
+ return fmt.Errorf("%T write field begin error 2:youngest_micros: %s", p, err)
+ }
+ if err := oprot.WriteI64(int64(*p.YoungestMicros)); err != nil {
+ return fmt.Errorf("%T.youngest_micros (2) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 2:youngest_micros: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *SampleCount) writeField3(oprot thrift.TProtocol) (err error) {
+ if p.IsSetCount() {
+ if err := oprot.WriteFieldBegin("count", thrift.I64, 3); err != nil {
+ return fmt.Errorf("%T write field begin error 3:count: %s", p, err)
+ }
+ if err := oprot.WriteI64(int64(*p.Count)); err != nil {
+ return fmt.Errorf("%T.count (3) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 3:count: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *SampleCount) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return fmt.Sprintf("SampleCount(%+v)", *p)
+}
+
+type MetricsSample struct {
+ Name string `thrift:"name,1,required" json:"name"`
+ Int64Value *int64 `thrift:"int64_value,2" json:"int64_value"`
+ DoubleValue *float64 `thrift:"double_value,3" json:"double_value"`
+}
+
+func NewMetricsSample() *MetricsSample {
+ return &MetricsSample{}
+}
+
+func (p *MetricsSample) GetName() string {
+ return p.Name
+}
+
+var MetricsSample_Int64Value_DEFAULT int64
+
+func (p *MetricsSample) GetInt64Value() int64 {
+ if !p.IsSetInt64Value() {
+ return MetricsSample_Int64Value_DEFAULT
+ }
+ return *p.Int64Value
+}
+
+var MetricsSample_DoubleValue_DEFAULT float64
+
+func (p *MetricsSample) GetDoubleValue() float64 {
+ if !p.IsSetDoubleValue() {
+ return MetricsSample_DoubleValue_DEFAULT
+ }
+ return *p.DoubleValue
+}
+func (p *MetricsSample) IsSetInt64Value() bool {
+ return p.Int64Value != nil
+}
+
+func (p *MetricsSample) IsSetDoubleValue() bool {
+ return p.DoubleValue != nil
+}
+
+func (p *MetricsSample) Read(iprot thrift.TProtocol) error {
+ if _, err := iprot.ReadStructBegin(); err != nil {
+ return fmt.Errorf("%T read error: %s", p, err)
+ }
+ for {
+ _, fieldTypeId, fieldId, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return fmt.Errorf("%T field %d read error: %s", p, fieldId, err)
+ }
+ if fieldTypeId == thrift.STOP {
+ break
+ }
+ switch fieldId {
+ case 1:
+ if err := p.ReadField1(iprot); err != nil {
+ return err
+ }
+ case 2:
+ if err := p.ReadField2(iprot); err != nil {
+ return err
+ }
+ case 3:
+ if err := p.ReadField3(iprot); err != nil {
+ return err
+ }
+ default:
+ if err := iprot.Skip(fieldTypeId); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadFieldEnd(); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadStructEnd(); err != nil {
+ return fmt.Errorf("%T read struct end error: %s", p, err)
+ }
+ return nil
+}
+
+func (p *MetricsSample) ReadField1(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadString(); err != nil {
+ return fmt.Errorf("error reading field 1: %s", err)
+ } else {
+ p.Name = v
+ }
+ return nil
+}
+
+func (p *MetricsSample) ReadField2(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadI64(); err != nil {
+ return fmt.Errorf("error reading field 2: %s", err)
+ } else {
+ p.Int64Value = &v
+ }
+ return nil
+}
+
+func (p *MetricsSample) ReadField3(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadDouble(); err != nil {
+ return fmt.Errorf("error reading field 3: %s", err)
+ } else {
+ p.DoubleValue = &v
+ }
+ return nil
+}
+
+func (p *MetricsSample) Write(oprot thrift.TProtocol) error {
+ if err := oprot.WriteStructBegin("MetricsSample"); err != nil {
+ return fmt.Errorf("%T write struct begin error: %s", p, err)
+ }
+ if err := p.writeField1(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField2(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField3(oprot); err != nil {
+ return err
+ }
+ if err := oprot.WriteFieldStop(); err != nil {
+ return fmt.Errorf("write field stop error: %s", err)
+ }
+ if err := oprot.WriteStructEnd(); err != nil {
+ return fmt.Errorf("write struct stop error: %s", err)
+ }
+ return nil
+}
+
+func (p *MetricsSample) writeField1(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("name", thrift.STRING, 1); err != nil {
+ return fmt.Errorf("%T write field begin error 1:name: %s", p, err)
+ }
+ if err := oprot.WriteString(string(p.Name)); err != nil {
+ return fmt.Errorf("%T.name (1) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 1:name: %s", p, err)
+ }
+ return err
+}
+
+func (p *MetricsSample) writeField2(oprot thrift.TProtocol) (err error) {
+ if p.IsSetInt64Value() {
+ if err := oprot.WriteFieldBegin("int64_value", thrift.I64, 2); err != nil {
+ return fmt.Errorf("%T write field begin error 2:int64_value: %s", p, err)
+ }
+ if err := oprot.WriteI64(int64(*p.Int64Value)); err != nil {
+ return fmt.Errorf("%T.int64_value (2) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 2:int64_value: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *MetricsSample) writeField3(oprot thrift.TProtocol) (err error) {
+ if p.IsSetDoubleValue() {
+ if err := oprot.WriteFieldBegin("double_value", thrift.DOUBLE, 3); err != nil {
+ return fmt.Errorf("%T write field begin error 3:double_value: %s", p, err)
+ }
+ if err := oprot.WriteDouble(float64(*p.DoubleValue)); err != nil {
+ return fmt.Errorf("%T.double_value (3) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 3:double_value: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *MetricsSample) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return fmt.Sprintf("MetricsSample(%+v)", *p)
+}
+
+type Metrics struct {
+ Counts []*MetricsSample `thrift:"counts,1" json:"counts"`
+ Gauges []*MetricsSample `thrift:"gauges,2" json:"gauges"`
+}
+
+func NewMetrics() *Metrics {
+ return &Metrics{}
+}
+
+var Metrics_Counts_DEFAULT []*MetricsSample
+
+func (p *Metrics) GetCounts() []*MetricsSample {
+ return p.Counts
+}
+
+var Metrics_Gauges_DEFAULT []*MetricsSample
+
+func (p *Metrics) GetGauges() []*MetricsSample {
+ return p.Gauges
+}
+func (p *Metrics) IsSetCounts() bool {
+ return p.Counts != nil
+}
+
+func (p *Metrics) IsSetGauges() bool {
+ return p.Gauges != nil
+}
+
+func (p *Metrics) Read(iprot thrift.TProtocol) error {
+ if _, err := iprot.ReadStructBegin(); err != nil {
+ return fmt.Errorf("%T read error: %s", p, err)
+ }
+ for {
+ _, fieldTypeId, fieldId, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return fmt.Errorf("%T field %d read error: %s", p, fieldId, err)
+ }
+ if fieldTypeId == thrift.STOP {
+ break
+ }
+ switch fieldId {
+ case 1:
+ if err := p.ReadField1(iprot); err != nil {
+ return err
+ }
+ case 2:
+ if err := p.ReadField2(iprot); err != nil {
+ return err
+ }
+ default:
+ if err := iprot.Skip(fieldTypeId); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadFieldEnd(); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadStructEnd(); err != nil {
+ return fmt.Errorf("%T read struct end error: %s", p, err)
+ }
+ return nil
+}
+
+func (p *Metrics) ReadField1(iprot thrift.TProtocol) error {
+ _, size, err := iprot.ReadListBegin()
+ if err != nil {
+ return fmt.Errorf("error reading list begin: %s", err)
+ }
+ tSlice := make([]*MetricsSample, 0, size)
+ p.Counts = tSlice
+ for i := 0; i < size; i++ {
+ _elem6 := &MetricsSample{}
+ if err := _elem6.Read(iprot); err != nil {
+ return fmt.Errorf("%T error reading struct: %s", _elem6, err)
+ }
+ p.Counts = append(p.Counts, _elem6)
+ }
+ if err := iprot.ReadListEnd(); err != nil {
+ return fmt.Errorf("error reading list end: %s", err)
+ }
+ return nil
+}
+
+func (p *Metrics) ReadField2(iprot thrift.TProtocol) error {
+ _, size, err := iprot.ReadListBegin()
+ if err != nil {
+ return fmt.Errorf("error reading list begin: %s", err)
+ }
+ tSlice := make([]*MetricsSample, 0, size)
+ p.Gauges = tSlice
+ for i := 0; i < size; i++ {
+ _elem7 := &MetricsSample{}
+ if err := _elem7.Read(iprot); err != nil {
+ return fmt.Errorf("%T error reading struct: %s", _elem7, err)
+ }
+ p.Gauges = append(p.Gauges, _elem7)
+ }
+ if err := iprot.ReadListEnd(); err != nil {
+ return fmt.Errorf("error reading list end: %s", err)
+ }
+ return nil
+}
+
+func (p *Metrics) Write(oprot thrift.TProtocol) error {
+ if err := oprot.WriteStructBegin("Metrics"); err != nil {
+ return fmt.Errorf("%T write struct begin error: %s", p, err)
+ }
+ if err := p.writeField1(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField2(oprot); err != nil {
+ return err
+ }
+ if err := oprot.WriteFieldStop(); err != nil {
+ return fmt.Errorf("write field stop error: %s", err)
+ }
+ if err := oprot.WriteStructEnd(); err != nil {
+ return fmt.Errorf("write struct stop error: %s", err)
+ }
+ return nil
+}
+
+func (p *Metrics) writeField1(oprot thrift.TProtocol) (err error) {
+ if p.IsSetCounts() {
+ if err := oprot.WriteFieldBegin("counts", thrift.LIST, 1); err != nil {
+ return fmt.Errorf("%T write field begin error 1:counts: %s", p, err)
+ }
+ if err := oprot.WriteListBegin(thrift.STRUCT, len(p.Counts)); err != nil {
+ return fmt.Errorf("error writing list begin: %s", err)
+ }
+ for _, v := range p.Counts {
+ if err := v.Write(oprot); err != nil {
+ return fmt.Errorf("%T error writing struct: %s", v, err)
+ }
+ }
+ if err := oprot.WriteListEnd(); err != nil {
+ return fmt.Errorf("error writing list end: %s", err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 1:counts: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *Metrics) writeField2(oprot thrift.TProtocol) (err error) {
+ if p.IsSetGauges() {
+ if err := oprot.WriteFieldBegin("gauges", thrift.LIST, 2); err != nil {
+ return fmt.Errorf("%T write field begin error 2:gauges: %s", p, err)
+ }
+ if err := oprot.WriteListBegin(thrift.STRUCT, len(p.Gauges)); err != nil {
+ return fmt.Errorf("error writing list begin: %s", err)
+ }
+ for _, v := range p.Gauges {
+ if err := v.Write(oprot); err != nil {
+ return fmt.Errorf("%T error writing struct: %s", v, err)
+ }
+ }
+ if err := oprot.WriteListEnd(); err != nil {
+ return fmt.Errorf("error writing list end: %s", err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 2:gauges: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *Metrics) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return fmt.Sprintf("Metrics(%+v)", *p)
+}
+
+type ReportRequest struct {
+ Runtime *Runtime `thrift:"runtime,1" json:"runtime"`
+ // unused field # 2
+ SpanRecords []*SpanRecord `thrift:"span_records,3" json:"span_records"`
+ LogRecords []*LogRecord `thrift:"log_records,4" json:"log_records"`
+ TimestampOffsetMicros *int64 `thrift:"timestamp_offset_micros,5" json:"timestamp_offset_micros"`
+ // unused field # 6
+ OldestMicros *int64 `thrift:"oldest_micros,7" json:"oldest_micros"`
+ YoungestMicros *int64 `thrift:"youngest_micros,8" json:"youngest_micros"`
+ Counters []*NamedCounter `thrift:"counters,9" json:"counters"`
+ InternalLogs []*LogRecord `thrift:"internal_logs,10" json:"internal_logs"`
+ InternalMetrics *Metrics `thrift:"internal_metrics,11" json:"internal_metrics"`
+}
+
+func NewReportRequest() *ReportRequest {
+ return &ReportRequest{}
+}
+
+var ReportRequest_Runtime_DEFAULT *Runtime
+
+func (p *ReportRequest) GetRuntime() *Runtime {
+ if !p.IsSetRuntime() {
+ return ReportRequest_Runtime_DEFAULT
+ }
+ return p.Runtime
+}
+
+var ReportRequest_SpanRecords_DEFAULT []*SpanRecord
+
+func (p *ReportRequest) GetSpanRecords() []*SpanRecord {
+ return p.SpanRecords
+}
+
+var ReportRequest_LogRecords_DEFAULT []*LogRecord
+
+func (p *ReportRequest) GetLogRecords() []*LogRecord {
+ return p.LogRecords
+}
+
+var ReportRequest_TimestampOffsetMicros_DEFAULT int64
+
+func (p *ReportRequest) GetTimestampOffsetMicros() int64 {
+ if !p.IsSetTimestampOffsetMicros() {
+ return ReportRequest_TimestampOffsetMicros_DEFAULT
+ }
+ return *p.TimestampOffsetMicros
+}
+
+var ReportRequest_OldestMicros_DEFAULT int64
+
+func (p *ReportRequest) GetOldestMicros() int64 {
+ if !p.IsSetOldestMicros() {
+ return ReportRequest_OldestMicros_DEFAULT
+ }
+ return *p.OldestMicros
+}
+
+var ReportRequest_YoungestMicros_DEFAULT int64
+
+func (p *ReportRequest) GetYoungestMicros() int64 {
+ if !p.IsSetYoungestMicros() {
+ return ReportRequest_YoungestMicros_DEFAULT
+ }
+ return *p.YoungestMicros
+}
+
+var ReportRequest_Counters_DEFAULT []*NamedCounter
+
+func (p *ReportRequest) GetCounters() []*NamedCounter {
+ return p.Counters
+}
+
+var ReportRequest_InternalLogs_DEFAULT []*LogRecord
+
+func (p *ReportRequest) GetInternalLogs() []*LogRecord {
+ return p.InternalLogs
+}
+
+var ReportRequest_InternalMetrics_DEFAULT *Metrics
+
+func (p *ReportRequest) GetInternalMetrics() *Metrics {
+ if !p.IsSetInternalMetrics() {
+ return ReportRequest_InternalMetrics_DEFAULT
+ }
+ return p.InternalMetrics
+}
+func (p *ReportRequest) IsSetRuntime() bool {
+ return p.Runtime != nil
+}
+
+func (p *ReportRequest) IsSetSpanRecords() bool {
+ return p.SpanRecords != nil
+}
+
+func (p *ReportRequest) IsSetLogRecords() bool {
+ return p.LogRecords != nil
+}
+
+func (p *ReportRequest) IsSetTimestampOffsetMicros() bool {
+ return p.TimestampOffsetMicros != nil
+}
+
+func (p *ReportRequest) IsSetOldestMicros() bool {
+ return p.OldestMicros != nil
+}
+
+func (p *ReportRequest) IsSetYoungestMicros() bool {
+ return p.YoungestMicros != nil
+}
+
+func (p *ReportRequest) IsSetCounters() bool {
+ return p.Counters != nil
+}
+
+func (p *ReportRequest) IsSetInternalLogs() bool {
+ return p.InternalLogs != nil
+}
+
+func (p *ReportRequest) IsSetInternalMetrics() bool {
+ return p.InternalMetrics != nil
+}
+
+func (p *ReportRequest) Read(iprot thrift.TProtocol) error {
+ if _, err := iprot.ReadStructBegin(); err != nil {
+ return fmt.Errorf("%T read error: %s", p, err)
+ }
+ for {
+ _, fieldTypeId, fieldId, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return fmt.Errorf("%T field %d read error: %s", p, fieldId, err)
+ }
+ if fieldTypeId == thrift.STOP {
+ break
+ }
+ switch fieldId {
+ case 1:
+ if err := p.ReadField1(iprot); err != nil {
+ return err
+ }
+ case 3:
+ if err := p.ReadField3(iprot); err != nil {
+ return err
+ }
+ case 4:
+ if err := p.ReadField4(iprot); err != nil {
+ return err
+ }
+ case 5:
+ if err := p.ReadField5(iprot); err != nil {
+ return err
+ }
+ case 7:
+ if err := p.ReadField7(iprot); err != nil {
+ return err
+ }
+ case 8:
+ if err := p.ReadField8(iprot); err != nil {
+ return err
+ }
+ case 9:
+ if err := p.ReadField9(iprot); err != nil {
+ return err
+ }
+ case 10:
+ if err := p.ReadField10(iprot); err != nil {
+ return err
+ }
+ case 11:
+ if err := p.ReadField11(iprot); err != nil {
+ return err
+ }
+ default:
+ if err := iprot.Skip(fieldTypeId); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadFieldEnd(); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadStructEnd(); err != nil {
+ return fmt.Errorf("%T read struct end error: %s", p, err)
+ }
+ return nil
+}
+
+func (p *ReportRequest) ReadField1(iprot thrift.TProtocol) error {
+ p.Runtime = &Runtime{}
+ if err := p.Runtime.Read(iprot); err != nil {
+ return fmt.Errorf("%T error reading struct: %s", p.Runtime, err)
+ }
+ return nil
+}
+
+func (p *ReportRequest) ReadField3(iprot thrift.TProtocol) error {
+ _, size, err := iprot.ReadListBegin()
+ if err != nil {
+ return fmt.Errorf("error reading list begin: %s", err)
+ }
+ tSlice := make([]*SpanRecord, 0, size)
+ p.SpanRecords = tSlice
+ for i := 0; i < size; i++ {
+ _elem8 := &SpanRecord{}
+ if err := _elem8.Read(iprot); err != nil {
+ return fmt.Errorf("%T error reading struct: %s", _elem8, err)
+ }
+ p.SpanRecords = append(p.SpanRecords, _elem8)
+ }
+ if err := iprot.ReadListEnd(); err != nil {
+ return fmt.Errorf("error reading list end: %s", err)
+ }
+ return nil
+}
+
+func (p *ReportRequest) ReadField4(iprot thrift.TProtocol) error {
+ _, size, err := iprot.ReadListBegin()
+ if err != nil {
+ return fmt.Errorf("error reading list begin: %s", err)
+ }
+ tSlice := make([]*LogRecord, 0, size)
+ p.LogRecords = tSlice
+ for i := 0; i < size; i++ {
+ _elem9 := &LogRecord{}
+ if err := _elem9.Read(iprot); err != nil {
+ return fmt.Errorf("%T error reading struct: %s", _elem9, err)
+ }
+ p.LogRecords = append(p.LogRecords, _elem9)
+ }
+ if err := iprot.ReadListEnd(); err != nil {
+ return fmt.Errorf("error reading list end: %s", err)
+ }
+ return nil
+}
+
+func (p *ReportRequest) ReadField5(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadI64(); err != nil {
+ return fmt.Errorf("error reading field 5: %s", err)
+ } else {
+ p.TimestampOffsetMicros = &v
+ }
+ return nil
+}
+
+func (p *ReportRequest) ReadField7(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadI64(); err != nil {
+ return fmt.Errorf("error reading field 7: %s", err)
+ } else {
+ p.OldestMicros = &v
+ }
+ return nil
+}
+
+func (p *ReportRequest) ReadField8(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadI64(); err != nil {
+ return fmt.Errorf("error reading field 8: %s", err)
+ } else {
+ p.YoungestMicros = &v
+ }
+ return nil
+}
+
+func (p *ReportRequest) ReadField9(iprot thrift.TProtocol) error {
+ _, size, err := iprot.ReadListBegin()
+ if err != nil {
+ return fmt.Errorf("error reading list begin: %s", err)
+ }
+ tSlice := make([]*NamedCounter, 0, size)
+ p.Counters = tSlice
+ for i := 0; i < size; i++ {
+ _elem10 := &NamedCounter{}
+ if err := _elem10.Read(iprot); err != nil {
+ return fmt.Errorf("%T error reading struct: %s", _elem10, err)
+ }
+ p.Counters = append(p.Counters, _elem10)
+ }
+ if err := iprot.ReadListEnd(); err != nil {
+ return fmt.Errorf("error reading list end: %s", err)
+ }
+ return nil
+}
+
+func (p *ReportRequest) ReadField10(iprot thrift.TProtocol) error {
+ _, size, err := iprot.ReadListBegin()
+ if err != nil {
+ return fmt.Errorf("error reading list begin: %s", err)
+ }
+ tSlice := make([]*LogRecord, 0, size)
+ p.InternalLogs = tSlice
+ for i := 0; i < size; i++ {
+ _elem11 := &LogRecord{}
+ if err := _elem11.Read(iprot); err != nil {
+ return fmt.Errorf("%T error reading struct: %s", _elem11, err)
+ }
+ p.InternalLogs = append(p.InternalLogs, _elem11)
+ }
+ if err := iprot.ReadListEnd(); err != nil {
+ return fmt.Errorf("error reading list end: %s", err)
+ }
+ return nil
+}
+
+func (p *ReportRequest) ReadField11(iprot thrift.TProtocol) error {
+ p.InternalMetrics = &Metrics{}
+ if err := p.InternalMetrics.Read(iprot); err != nil {
+ return fmt.Errorf("%T error reading struct: %s", p.InternalMetrics, err)
+ }
+ return nil
+}
+
+func (p *ReportRequest) Write(oprot thrift.TProtocol) error {
+ if err := oprot.WriteStructBegin("ReportRequest"); err != nil {
+ return fmt.Errorf("%T write struct begin error: %s", p, err)
+ }
+ if err := p.writeField1(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField3(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField4(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField5(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField7(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField8(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField9(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField10(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField11(oprot); err != nil {
+ return err
+ }
+ if err := oprot.WriteFieldStop(); err != nil {
+ return fmt.Errorf("write field stop error: %s", err)
+ }
+ if err := oprot.WriteStructEnd(); err != nil {
+ return fmt.Errorf("write struct stop error: %s", err)
+ }
+ return nil
+}
+
+func (p *ReportRequest) writeField1(oprot thrift.TProtocol) (err error) {
+ if p.IsSetRuntime() {
+ if err := oprot.WriteFieldBegin("runtime", thrift.STRUCT, 1); err != nil {
+ return fmt.Errorf("%T write field begin error 1:runtime: %s", p, err)
+ }
+ if err := p.Runtime.Write(oprot); err != nil {
+ return fmt.Errorf("%T error writing struct: %s", p.Runtime, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 1:runtime: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *ReportRequest) writeField3(oprot thrift.TProtocol) (err error) {
+ if p.IsSetSpanRecords() {
+ if err := oprot.WriteFieldBegin("span_records", thrift.LIST, 3); err != nil {
+ return fmt.Errorf("%T write field begin error 3:span_records: %s", p, err)
+ }
+ if err := oprot.WriteListBegin(thrift.STRUCT, len(p.SpanRecords)); err != nil {
+ return fmt.Errorf("error writing list begin: %s", err)
+ }
+ for _, v := range p.SpanRecords {
+ if err := v.Write(oprot); err != nil {
+ return fmt.Errorf("%T error writing struct: %s", v, err)
+ }
+ }
+ if err := oprot.WriteListEnd(); err != nil {
+ return fmt.Errorf("error writing list end: %s", err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 3:span_records: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *ReportRequest) writeField4(oprot thrift.TProtocol) (err error) {
+ if p.IsSetLogRecords() {
+ if err := oprot.WriteFieldBegin("log_records", thrift.LIST, 4); err != nil {
+ return fmt.Errorf("%T write field begin error 4:log_records: %s", p, err)
+ }
+ if err := oprot.WriteListBegin(thrift.STRUCT, len(p.LogRecords)); err != nil {
+ return fmt.Errorf("error writing list begin: %s", err)
+ }
+ for _, v := range p.LogRecords {
+ if err := v.Write(oprot); err != nil {
+ return fmt.Errorf("%T error writing struct: %s", v, err)
+ }
+ }
+ if err := oprot.WriteListEnd(); err != nil {
+ return fmt.Errorf("error writing list end: %s", err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 4:log_records: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *ReportRequest) writeField5(oprot thrift.TProtocol) (err error) {
+ if p.IsSetTimestampOffsetMicros() {
+ if err := oprot.WriteFieldBegin("timestamp_offset_micros", thrift.I64, 5); err != nil {
+ return fmt.Errorf("%T write field begin error 5:timestamp_offset_micros: %s", p, err)
+ }
+ if err := oprot.WriteI64(int64(*p.TimestampOffsetMicros)); err != nil {
+ return fmt.Errorf("%T.timestamp_offset_micros (5) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 5:timestamp_offset_micros: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *ReportRequest) writeField7(oprot thrift.TProtocol) (err error) {
+ if p.IsSetOldestMicros() {
+ if err := oprot.WriteFieldBegin("oldest_micros", thrift.I64, 7); err != nil {
+ return fmt.Errorf("%T write field begin error 7:oldest_micros: %s", p, err)
+ }
+ if err := oprot.WriteI64(int64(*p.OldestMicros)); err != nil {
+ return fmt.Errorf("%T.oldest_micros (7) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 7:oldest_micros: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *ReportRequest) writeField8(oprot thrift.TProtocol) (err error) {
+ if p.IsSetYoungestMicros() {
+ if err := oprot.WriteFieldBegin("youngest_micros", thrift.I64, 8); err != nil {
+ return fmt.Errorf("%T write field begin error 8:youngest_micros: %s", p, err)
+ }
+ if err := oprot.WriteI64(int64(*p.YoungestMicros)); err != nil {
+ return fmt.Errorf("%T.youngest_micros (8) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 8:youngest_micros: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *ReportRequest) writeField9(oprot thrift.TProtocol) (err error) {
+ if p.IsSetCounters() {
+ if err := oprot.WriteFieldBegin("counters", thrift.LIST, 9); err != nil {
+ return fmt.Errorf("%T write field begin error 9:counters: %s", p, err)
+ }
+ if err := oprot.WriteListBegin(thrift.STRUCT, len(p.Counters)); err != nil {
+ return fmt.Errorf("error writing list begin: %s", err)
+ }
+ for _, v := range p.Counters {
+ if err := v.Write(oprot); err != nil {
+ return fmt.Errorf("%T error writing struct: %s", v, err)
+ }
+ }
+ if err := oprot.WriteListEnd(); err != nil {
+ return fmt.Errorf("error writing list end: %s", err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 9:counters: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *ReportRequest) writeField10(oprot thrift.TProtocol) (err error) {
+ if p.IsSetInternalLogs() {
+ if err := oprot.WriteFieldBegin("internal_logs", thrift.LIST, 10); err != nil {
+ return fmt.Errorf("%T write field begin error 10:internal_logs: %s", p, err)
+ }
+ if err := oprot.WriteListBegin(thrift.STRUCT, len(p.InternalLogs)); err != nil {
+ return fmt.Errorf("error writing list begin: %s", err)
+ }
+ for _, v := range p.InternalLogs {
+ if err := v.Write(oprot); err != nil {
+ return fmt.Errorf("%T error writing struct: %s", v, err)
+ }
+ }
+ if err := oprot.WriteListEnd(); err != nil {
+ return fmt.Errorf("error writing list end: %s", err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 10:internal_logs: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *ReportRequest) writeField11(oprot thrift.TProtocol) (err error) {
+ if p.IsSetInternalMetrics() {
+ if err := oprot.WriteFieldBegin("internal_metrics", thrift.STRUCT, 11); err != nil {
+ return fmt.Errorf("%T write field begin error 11:internal_metrics: %s", p, err)
+ }
+ if err := p.InternalMetrics.Write(oprot); err != nil {
+ return fmt.Errorf("%T error writing struct: %s", p.InternalMetrics, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 11:internal_metrics: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *ReportRequest) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return fmt.Sprintf("ReportRequest(%+v)", *p)
+}
+
+type Command struct {
+ Disable *bool `thrift:"disable,1" json:"disable"`
+}
+
+func NewCommand() *Command {
+ return &Command{}
+}
+
+var Command_Disable_DEFAULT bool
+
+func (p *Command) GetDisable() bool {
+ if !p.IsSetDisable() {
+ return Command_Disable_DEFAULT
+ }
+ return *p.Disable
+}
+func (p *Command) IsSetDisable() bool {
+ return p.Disable != nil
+}
+
+func (p *Command) Read(iprot thrift.TProtocol) error {
+ if _, err := iprot.ReadStructBegin(); err != nil {
+ return fmt.Errorf("%T read error: %s", p, err)
+ }
+ for {
+ _, fieldTypeId, fieldId, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return fmt.Errorf("%T field %d read error: %s", p, fieldId, err)
+ }
+ if fieldTypeId == thrift.STOP {
+ break
+ }
+ switch fieldId {
+ case 1:
+ if err := p.ReadField1(iprot); err != nil {
+ return err
+ }
+ default:
+ if err := iprot.Skip(fieldTypeId); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadFieldEnd(); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadStructEnd(); err != nil {
+ return fmt.Errorf("%T read struct end error: %s", p, err)
+ }
+ return nil
+}
+
+func (p *Command) ReadField1(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadBool(); err != nil {
+ return fmt.Errorf("error reading field 1: %s", err)
+ } else {
+ p.Disable = &v
+ }
+ return nil
+}
+
+func (p *Command) Write(oprot thrift.TProtocol) error {
+ if err := oprot.WriteStructBegin("Command"); err != nil {
+ return fmt.Errorf("%T write struct begin error: %s", p, err)
+ }
+ if err := p.writeField1(oprot); err != nil {
+ return err
+ }
+ if err := oprot.WriteFieldStop(); err != nil {
+ return fmt.Errorf("write field stop error: %s", err)
+ }
+ if err := oprot.WriteStructEnd(); err != nil {
+ return fmt.Errorf("write struct stop error: %s", err)
+ }
+ return nil
+}
+
+func (p *Command) writeField1(oprot thrift.TProtocol) (err error) {
+ if p.IsSetDisable() {
+ if err := oprot.WriteFieldBegin("disable", thrift.BOOL, 1); err != nil {
+ return fmt.Errorf("%T write field begin error 1:disable: %s", p, err)
+ }
+ if err := oprot.WriteBool(bool(*p.Disable)); err != nil {
+ return fmt.Errorf("%T.disable (1) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 1:disable: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *Command) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return fmt.Sprintf("Command(%+v)", *p)
+}
+
+type ReportResponse struct {
+ Commands []*Command `thrift:"commands,1" json:"commands"`
+ Timing *Timing `thrift:"timing,2" json:"timing"`
+ Errors []string `thrift:"errors,3" json:"errors"`
+}
+
+func NewReportResponse() *ReportResponse {
+ return &ReportResponse{}
+}
+
+var ReportResponse_Commands_DEFAULT []*Command
+
+func (p *ReportResponse) GetCommands() []*Command {
+ return p.Commands
+}
+
+var ReportResponse_Timing_DEFAULT *Timing
+
+func (p *ReportResponse) GetTiming() *Timing {
+ if !p.IsSetTiming() {
+ return ReportResponse_Timing_DEFAULT
+ }
+ return p.Timing
+}
+
+var ReportResponse_Errors_DEFAULT []string
+
+func (p *ReportResponse) GetErrors() []string {
+ return p.Errors
+}
+func (p *ReportResponse) IsSetCommands() bool {
+ return p.Commands != nil
+}
+
+func (p *ReportResponse) IsSetTiming() bool {
+ return p.Timing != nil
+}
+
+func (p *ReportResponse) IsSetErrors() bool {
+ return p.Errors != nil
+}
+
+func (p *ReportResponse) Read(iprot thrift.TProtocol) error {
+ if _, err := iprot.ReadStructBegin(); err != nil {
+ return fmt.Errorf("%T read error: %s", p, err)
+ }
+ for {
+ _, fieldTypeId, fieldId, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return fmt.Errorf("%T field %d read error: %s", p, fieldId, err)
+ }
+ if fieldTypeId == thrift.STOP {
+ break
+ }
+ switch fieldId {
+ case 1:
+ if err := p.ReadField1(iprot); err != nil {
+ return err
+ }
+ case 2:
+ if err := p.ReadField2(iprot); err != nil {
+ return err
+ }
+ case 3:
+ if err := p.ReadField3(iprot); err != nil {
+ return err
+ }
+ default:
+ if err := iprot.Skip(fieldTypeId); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadFieldEnd(); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadStructEnd(); err != nil {
+ return fmt.Errorf("%T read struct end error: %s", p, err)
+ }
+ return nil
+}
+
+func (p *ReportResponse) ReadField1(iprot thrift.TProtocol) error {
+ _, size, err := iprot.ReadListBegin()
+ if err != nil {
+ return fmt.Errorf("error reading list begin: %s", err)
+ }
+ tSlice := make([]*Command, 0, size)
+ p.Commands = tSlice
+ for i := 0; i < size; i++ {
+ _elem12 := &Command{}
+ if err := _elem12.Read(iprot); err != nil {
+ return fmt.Errorf("%T error reading struct: %s", _elem12, err)
+ }
+ p.Commands = append(p.Commands, _elem12)
+ }
+ if err := iprot.ReadListEnd(); err != nil {
+ return fmt.Errorf("error reading list end: %s", err)
+ }
+ return nil
+}
+
+func (p *ReportResponse) ReadField2(iprot thrift.TProtocol) error {
+ p.Timing = &Timing{}
+ if err := p.Timing.Read(iprot); err != nil {
+ return fmt.Errorf("%T error reading struct: %s", p.Timing, err)
+ }
+ return nil
+}
+
+func (p *ReportResponse) ReadField3(iprot thrift.TProtocol) error {
+ _, size, err := iprot.ReadListBegin()
+ if err != nil {
+ return fmt.Errorf("error reading list begin: %s", err)
+ }
+ tSlice := make([]string, 0, size)
+ p.Errors = tSlice
+ for i := 0; i < size; i++ {
+ var _elem13 string
+ if v, err := iprot.ReadString(); err != nil {
+ return fmt.Errorf("error reading field 0: %s", err)
+ } else {
+ _elem13 = v
+ }
+ p.Errors = append(p.Errors, _elem13)
+ }
+ if err := iprot.ReadListEnd(); err != nil {
+ return fmt.Errorf("error reading list end: %s", err)
+ }
+ return nil
+}
+
+func (p *ReportResponse) Write(oprot thrift.TProtocol) error {
+ if err := oprot.WriteStructBegin("ReportResponse"); err != nil {
+ return fmt.Errorf("%T write struct begin error: %s", p, err)
+ }
+ if err := p.writeField1(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField2(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField3(oprot); err != nil {
+ return err
+ }
+ if err := oprot.WriteFieldStop(); err != nil {
+ return fmt.Errorf("write field stop error: %s", err)
+ }
+ if err := oprot.WriteStructEnd(); err != nil {
+ return fmt.Errorf("write struct stop error: %s", err)
+ }
+ return nil
+}
+
+func (p *ReportResponse) writeField1(oprot thrift.TProtocol) (err error) {
+ if p.IsSetCommands() {
+ if err := oprot.WriteFieldBegin("commands", thrift.LIST, 1); err != nil {
+ return fmt.Errorf("%T write field begin error 1:commands: %s", p, err)
+ }
+ if err := oprot.WriteListBegin(thrift.STRUCT, len(p.Commands)); err != nil {
+ return fmt.Errorf("error writing list begin: %s", err)
+ }
+ for _, v := range p.Commands {
+ if err := v.Write(oprot); err != nil {
+ return fmt.Errorf("%T error writing struct: %s", v, err)
+ }
+ }
+ if err := oprot.WriteListEnd(); err != nil {
+ return fmt.Errorf("error writing list end: %s", err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 1:commands: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *ReportResponse) writeField2(oprot thrift.TProtocol) (err error) {
+ if p.IsSetTiming() {
+ if err := oprot.WriteFieldBegin("timing", thrift.STRUCT, 2); err != nil {
+ return fmt.Errorf("%T write field begin error 2:timing: %s", p, err)
+ }
+ if err := p.Timing.Write(oprot); err != nil {
+ return fmt.Errorf("%T error writing struct: %s", p.Timing, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 2:timing: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *ReportResponse) writeField3(oprot thrift.TProtocol) (err error) {
+ if p.IsSetErrors() {
+ if err := oprot.WriteFieldBegin("errors", thrift.LIST, 3); err != nil {
+ return fmt.Errorf("%T write field begin error 3:errors: %s", p, err)
+ }
+ if err := oprot.WriteListBegin(thrift.STRING, len(p.Errors)); err != nil {
+ return fmt.Errorf("error writing list begin: %s", err)
+ }
+ for _, v := range p.Errors {
+ if err := oprot.WriteString(string(v)); err != nil {
+ return fmt.Errorf("%T. (0) field write error: %s", p, err)
+ }
+ }
+ if err := oprot.WriteListEnd(); err != nil {
+ return fmt.Errorf("error writing list end: %s", err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 3:errors: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *ReportResponse) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return fmt.Sprintf("ReportResponse(%+v)", *p)
+}
diff --git a/vendor/github.com/lightstep/lightstep-tracer-go/lightsteppb/lightstep.pb.go b/vendor/github.com/lightstep/lightstep-tracer-go/lightsteppb/lightstep.pb.go
new file mode 100644
index 000000000..e2b47ef6e
--- /dev/null
+++ b/vendor/github.com/lightstep/lightstep-tracer-go/lightsteppb/lightstep.pb.go
@@ -0,0 +1,127 @@
+// Code generated by protoc-gen-go. DO NOT EDIT.
+// source: lightstep.proto
+
+/*
+Package lightsteppb is a generated protocol buffer package.
+
+It is generated from these files:
+ lightstep.proto
+
+It has these top-level messages:
+ BinaryCarrier
+ BasicTracerCarrier
+*/
+package lightsteppb
+
+import proto "github.com/golang/protobuf/proto"
+import fmt "fmt"
+import math "math"
+
+// Reference imports to suppress errors if they are not otherwise used.
+var _ = proto.Marshal
+var _ = fmt.Errorf
+var _ = math.Inf
+
+// This is a compile-time assertion to ensure that this generated file
+// is compatible with the proto package it is being compiled against.
+// A compilation error at this line likely means your copy of the
+// proto package needs to be updated.
+const _ = proto.ProtoPackageIsVersion2 // please upgrade the proto package
+
+// The standard carrier for binary context propagation into LightStep.
+type BinaryCarrier struct {
+ // "text_ctx" was deprecated following lightstep-tracer-cpp-0.36
+ DeprecatedTextCtx [][]byte `protobuf:"bytes,1,rep,name=deprecated_text_ctx,json=deprecatedTextCtx,proto3" json:"deprecated_text_ctx,omitempty"`
+ // The Opentracing "basictracer" proto.
+ BasicCtx *BasicTracerCarrier `protobuf:"bytes,2,opt,name=basic_ctx,json=basicCtx" json:"basic_ctx,omitempty"`
+}
+
+func (m *BinaryCarrier) Reset() { *m = BinaryCarrier{} }
+func (m *BinaryCarrier) String() string { return proto.CompactTextString(m) }
+func (*BinaryCarrier) ProtoMessage() {}
+func (*BinaryCarrier) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{0} }
+
+func (m *BinaryCarrier) GetDeprecatedTextCtx() [][]byte {
+ if m != nil {
+ return m.DeprecatedTextCtx
+ }
+ return nil
+}
+
+func (m *BinaryCarrier) GetBasicCtx() *BasicTracerCarrier {
+ if m != nil {
+ return m.BasicCtx
+ }
+ return nil
+}
+
+// Copy of https://github.com/opentracing/basictracer-go/blob/master/wire/wire.proto
+type BasicTracerCarrier struct {
+ TraceId uint64 `protobuf:"fixed64,1,opt,name=trace_id,json=traceId" json:"trace_id,omitempty"`
+ SpanId uint64 `protobuf:"fixed64,2,opt,name=span_id,json=spanId" json:"span_id,omitempty"`
+ Sampled bool `protobuf:"varint,3,opt,name=sampled" json:"sampled,omitempty"`
+ BaggageItems map[string]string `protobuf:"bytes,4,rep,name=baggage_items,json=baggageItems" json:"baggage_items,omitempty" protobuf_key:"bytes,1,opt,name=key" protobuf_val:"bytes,2,opt,name=value"`
+}
+
+func (m *BasicTracerCarrier) Reset() { *m = BasicTracerCarrier{} }
+func (m *BasicTracerCarrier) String() string { return proto.CompactTextString(m) }
+func (*BasicTracerCarrier) ProtoMessage() {}
+func (*BasicTracerCarrier) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{1} }
+
+func (m *BasicTracerCarrier) GetTraceId() uint64 {
+ if m != nil {
+ return m.TraceId
+ }
+ return 0
+}
+
+func (m *BasicTracerCarrier) GetSpanId() uint64 {
+ if m != nil {
+ return m.SpanId
+ }
+ return 0
+}
+
+func (m *BasicTracerCarrier) GetSampled() bool {
+ if m != nil {
+ return m.Sampled
+ }
+ return false
+}
+
+func (m *BasicTracerCarrier) GetBaggageItems() map[string]string {
+ if m != nil {
+ return m.BaggageItems
+ }
+ return nil
+}
+
+func init() {
+ proto.RegisterType((*BinaryCarrier)(nil), "lightstep.BinaryCarrier")
+ proto.RegisterType((*BasicTracerCarrier)(nil), "lightstep.BasicTracerCarrier")
+}
+
+func init() { proto.RegisterFile("lightstep.proto", fileDescriptor0) }
+
+var fileDescriptor0 = []byte{
+ // 290 bytes of a gzipped FileDescriptorProto
+ 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0x7c, 0x91, 0xcf, 0x4b, 0xf3, 0x30,
+ 0x18, 0xc7, 0xc9, 0xfa, 0xbe, 0xdb, 0xfa, 0x6c, 0x43, 0x17, 0x05, 0xab, 0x20, 0x94, 0x9d, 0x7a,
+ 0xaa, 0x30, 0x2f, 0xb2, 0x8b, 0xd0, 0xe1, 0x61, 0xd7, 0xb0, 0x93, 0x97, 0x92, 0x36, 0x0f, 0x35,
+ 0xb8, 0x75, 0x21, 0x7d, 0x94, 0x16, 0xff, 0x72, 0x6f, 0x92, 0x4c, 0x37, 0x61, 0xe0, 0x2d, 0xdf,
+ 0x1f, 0x0f, 0xdf, 0x0f, 0x04, 0xce, 0x36, 0xba, 0x7a, 0xa1, 0x86, 0xd0, 0xa4, 0xc6, 0xee, 0x68,
+ 0xc7, 0xc3, 0x83, 0x31, 0xfb, 0x80, 0x49, 0xa6, 0x6b, 0x69, 0xbb, 0xa5, 0xb4, 0x56, 0xa3, 0xe5,
+ 0x29, 0x5c, 0x28, 0x34, 0x16, 0x4b, 0x49, 0xa8, 0x72, 0xc2, 0x96, 0xf2, 0x92, 0xda, 0x88, 0xc5,
+ 0x41, 0x32, 0x16, 0xd3, 0x63, 0xb4, 0xc6, 0x96, 0x96, 0xd4, 0xf2, 0x05, 0x84, 0x85, 0x6c, 0x74,
+ 0xe9, 0x5b, 0xbd, 0x98, 0x25, 0xa3, 0xf9, 0x6d, 0x7a, 0x1c, 0xcc, 0x5c, 0xb6, 0xb6, 0xb2, 0x44,
+ 0xfb, 0xbd, 0x20, 0x86, 0xbe, 0xbf, 0xa4, 0x76, 0xf6, 0xc9, 0x80, 0x9f, 0x16, 0xf8, 0x35, 0x0c,
+ 0xc9, 0x19, 0xb9, 0x56, 0x11, 0x8b, 0x59, 0xd2, 0x17, 0x03, 0xaf, 0x57, 0x8a, 0x5f, 0xc1, 0xa0,
+ 0x31, 0xb2, 0x76, 0x49, 0xcf, 0x27, 0x7d, 0x27, 0x57, 0x8a, 0x47, 0x30, 0x68, 0xe4, 0xd6, 0x6c,
+ 0x50, 0x45, 0x41, 0xcc, 0x92, 0xa1, 0xf8, 0x91, 0x7c, 0x0d, 0x93, 0x42, 0x56, 0x95, 0xac, 0x30,
+ 0xd7, 0x84, 0xdb, 0x26, 0xfa, 0x17, 0x07, 0xc9, 0x68, 0x7e, 0xf7, 0x27, 0x64, 0x9a, 0xed, 0x4f,
+ 0x56, 0xee, 0xe2, 0xa9, 0x26, 0xdb, 0x89, 0x71, 0xf1, 0xcb, 0xba, 0x79, 0x84, 0xe9, 0x49, 0x85,
+ 0x9f, 0x43, 0xf0, 0x8a, 0x9d, 0x67, 0x0e, 0x85, 0x7b, 0xf2, 0x4b, 0xf8, 0xff, 0x2e, 0x37, 0x6f,
+ 0xe8, 0x69, 0x43, 0xb1, 0x17, 0x8b, 0xde, 0x03, 0xcb, 0x26, 0xcf, 0xa3, 0x03, 0x80, 0x29, 0x8a,
+ 0xbe, 0xff, 0x99, 0xfb, 0xaf, 0x00, 0x00, 0x00, 0xff, 0xff, 0x7a, 0xf7, 0xd5, 0xf5, 0xac, 0x01,
+ 0x00, 0x00,
+}
diff --git a/vendor/github.com/lightstep/lightstep-tracer-go/options.go b/vendor/github.com/lightstep/lightstep-tracer-go/options.go
new file mode 100644
index 000000000..dfa71b1e2
--- /dev/null
+++ b/vendor/github.com/lightstep/lightstep-tracer-go/options.go
@@ -0,0 +1,344 @@
+package lightstep
+
+import (
+ "fmt"
+ "math"
+ "math/rand"
+ "os"
+ "path"
+ "strings"
+ "time"
+
+ // N.B.(jmacd): Do not use google.golang.org/glog in this package.
+
+ ot "github.com/opentracing/opentracing-go"
+ "google.golang.org/grpc"
+)
+
+// Default Option values.
+const (
+ DefaultCollectorPath = "/_rpc/v1/reports/binary"
+ DefaultPlainPort = 80
+ DefaultSecurePort = 443
+ DefaultThriftCollectorHost = "collector.lightstep.com"
+ DefaultGRPCCollectorHost = "collector-grpc.lightstep.com"
+
+ DefaultMaxReportingPeriod = 2500 * time.Millisecond
+ DefaultMinReportingPeriod = 500 * time.Millisecond
+ DefaultMaxSpans = 1000
+ DefaultReportTimeout = 30 * time.Second
+ DefaultReconnectPeriod = 5 * time.Minute
+
+ DefaultMaxLogKeyLen = 256
+ DefaultMaxLogValueLen = 1024
+ DefaultMaxLogsPerSpan = 500
+
+ DefaultGRPCMaxCallSendMsgSizeBytes = math.MaxInt32
+)
+
+// Tag and Tracer Attribute keys.
+const (
+ ParentSpanGUIDKey = "parent_span_guid" // ParentSpanGUIDKey is the tag key used to record the relationship between child and parent spans.
+ ComponentNameKey = "lightstep.component_name"
+ GUIDKey = "lightstep.guid" // <- runtime guid, not span guid
+ HostnameKey = "lightstep.hostname"
+ CommandLineKey = "lightstep.command_line"
+
+ TracerPlatformKey = "lightstep.tracer_platform"
+ TracerPlatformValue = "go"
+ TracerPlatformVersionKey = "lightstep.tracer_platform_version"
+ TracerVersionKey = "lightstep.tracer_version" // Note: TracerVersionValue is generated from ./VERSION
+)
+
+const (
+ secureScheme = "https"
+ plaintextScheme = "http"
+)
+
+// Validation Errors
+var (
+ errNoAccessToken = fmt.Errorf("Options invalid: AccessToken must not be empty")
+ errInvalidGUIDKey = fmt.Errorf("Options invalid: setting the %v tag is no longer supported", GUIDKey)
+)
+
+// A SpanRecorder handles all of the `RawSpan` data generated via an
+// associated `Tracer` instance.
+type SpanRecorder interface {
+ RecordSpan(RawSpan)
+}
+
+// Endpoint describes a collector or web API host/port and whether or
+// not to use plaintext communication.
+type Endpoint struct {
+ Scheme string `yaml:"scheme" json:"scheme" usage:"scheme to use for the endpoint, defaults to appropriate one if no custom one is required"`
+ Host string `yaml:"host" json:"host" usage:"host on which the endpoint is running"`
+ Port int `yaml:"port" json:"port" usage:"port on which the endpoint is listening"`
+ Plaintext bool `yaml:"plaintext" json:"plaintext" usage:"whether or not to encrypt data send to the endpoint"`
+}
+
+// HostPort use SocketAddress instead.
+// DEPRECATED
+func (e Endpoint) HostPort() string {
+ return e.SocketAddress()
+}
+
+// SocketAddress returns an address suitable for dialing grpc connections
+func (e Endpoint) SocketAddress() string {
+ return fmt.Sprintf("%s:%d", e.Host, e.Port)
+}
+
+// URL returns an address suitable for dialing thrift connections
+func (e Endpoint) URL() string {
+ return fmt.Sprintf("%s%s", e.urlWithoutPath(), DefaultCollectorPath)
+}
+
+// urlWithoutPath returns an address suitable for grpc connections if a custom scheme is provided
+func (e Endpoint) urlWithoutPath() string {
+ return fmt.Sprintf("%s://%s", e.scheme(), e.SocketAddress())
+}
+
+func (e Endpoint) scheme() string {
+ if len(e.Scheme) > 0 {
+ return e.Scheme
+ }
+
+ if e.Plaintext {
+ return plaintextScheme
+ }
+
+ return secureScheme
+}
+
+// Options control how the LightStep Tracer behaves.
+type Options struct {
+ // AccessToken is the unique API key for your LightStep project. It is
+ // available on your account page at https://app.lightstep.com/account
+ AccessToken string `yaml:"access_token" usage:"access token for reporting to LightStep"`
+
+ // Collector is the host, port, and plaintext option to use
+ // for the collector.
+ Collector Endpoint `yaml:"collector"`
+
+ // Tags are arbitrary key-value pairs that apply to all spans generated by
+ // this Tracer.
+ Tags ot.Tags
+
+ // LightStep is the host, port, and plaintext option to use
+ // for the LightStep web API.
+ LightStepAPI Endpoint `yaml:"lightstep_api"`
+
+ // MaxBufferedSpans is the maximum number of spans that will be buffered
+ // before sending them to a collector.
+ MaxBufferedSpans int `yaml:"max_buffered_spans"`
+
+ // MaxLogKeyLen is the maximum allowable size (in characters) of an
+ // OpenTracing logging key. Longer keys are truncated.
+ MaxLogKeyLen int `yaml:"max_log_key_len"`
+
+ // MaxLogValueLen is the maximum allowable size (in characters) of an
+ // OpenTracing logging value. Longer values are truncated. Only applies to
+ // variable-length value types (strings, interface{}, etc).
+ MaxLogValueLen int `yaml:"max_log_value_len"`
+
+ // MaxLogsPerSpan limits the number of logs in a single span.
+ MaxLogsPerSpan int `yaml:"max_logs_per_span"`
+
+ // GRPCMaxCallSendMsgSizeBytes limits the size in bytes of grpc messages
+ // sent by a client.
+ GRPCMaxCallSendMsgSizeBytes int `yaml:"grpc_max_call_send_msg_size_bytes"`
+
+ // ReportingPeriod is the maximum duration of time between sending spans
+ // to a collector. If zero, the default will be used.
+ ReportingPeriod time.Duration `yaml:"reporting_period"`
+
+ // MinReportingPeriod is the minimum duration of time between sending spans
+ // to a collector. If zero, the default will be used. It is strongly
+ // recommended to use the default.
+ MinReportingPeriod time.Duration `yaml:"min_reporting_period"`
+
+ ReportTimeout time.Duration `yaml:"report_timeout"`
+
+ // DropSpanLogs turns log events on all Spans into no-ops.
+ DropSpanLogs bool `yaml:"drop_span_logs"`
+
+ // DEPRECATED: The LightStep library prints the first error to stdout by default.
+ // See the documentation on the SetGlobalEventHandler function for guidance on
+ // how to integrate tracer diagnostics with your applicaiton's logging and
+ // metrics systems.
+ Verbose bool `yaml:"verbose"`
+
+ // Force the use of a specific transport protocol. If multiple are set to true,
+ // the following order is used to select for the first option: thrift, http, grpc.
+ // If none are set to true, GRPC is defaulted to.
+ UseThrift bool `yaml:"use_thrift"`
+ UseHttp bool `yaml:"use_http"`
+ UseGRPC bool `yaml:"usegrpc"`
+
+ ReconnectPeriod time.Duration `yaml:"reconnect_period"`
+
+ // DialOptions allows customizing the grpc dial options passed to the grpc.Dial(...) call.
+ // This is an advanced feature added to allow for a custom balancer or middleware.
+ // It can be safely ignored if you have no custom dialing requirements.
+ // If UseGRPC is not set, these dial options are ignored.
+ DialOptions []grpc.DialOption `yaml:"-" json:"-"`
+
+ // A hook for receiving finished span events
+ Recorder SpanRecorder `yaml:"-" json:"-"`
+
+ // For testing purposes only
+ ConnFactory ConnectorFactory `yaml:"-" json:"-"`
+}
+
+// Initialize validates options, and sets default values for unset options.
+// This is called automatically when creating a new Tracer.
+func (opts *Options) Initialize() error {
+ err := opts.Validate()
+ if err != nil {
+ return err
+ }
+
+ // Note: opts is a copy of the user's data, ok to modify.
+ if opts.MaxBufferedSpans == 0 {
+ opts.MaxBufferedSpans = DefaultMaxSpans
+ }
+ if opts.MaxLogKeyLen == 0 {
+ opts.MaxLogKeyLen = DefaultMaxLogKeyLen
+ }
+ if opts.MaxLogValueLen == 0 {
+ opts.MaxLogValueLen = DefaultMaxLogValueLen
+ }
+ if opts.MaxLogsPerSpan == 0 {
+ opts.MaxLogsPerSpan = DefaultMaxLogsPerSpan
+ }
+ if opts.GRPCMaxCallSendMsgSizeBytes == 0 {
+ opts.GRPCMaxCallSendMsgSizeBytes = DefaultGRPCMaxCallSendMsgSizeBytes
+ }
+ if opts.ReportingPeriod == 0 {
+ opts.ReportingPeriod = DefaultMaxReportingPeriod
+ }
+ if opts.MinReportingPeriod == 0 {
+ opts.MinReportingPeriod = DefaultMinReportingPeriod
+ }
+ if opts.ReportTimeout == 0 {
+ opts.ReportTimeout = DefaultReportTimeout
+ }
+ if opts.ReconnectPeriod == 0 {
+ opts.ReconnectPeriod = DefaultReconnectPeriod
+ }
+ if opts.Tags == nil {
+ opts.Tags = map[string]interface{}{}
+ }
+
+ // Set some default attributes if not found in options
+ if _, found := opts.Tags[ComponentNameKey]; !found {
+ opts.Tags[ComponentNameKey] = path.Base(os.Args[0])
+ }
+ if _, found := opts.Tags[HostnameKey]; !found {
+ hostname, _ := os.Hostname()
+ opts.Tags[HostnameKey] = hostname
+ }
+ if _, found := opts.Tags[CommandLineKey]; !found {
+ opts.Tags[CommandLineKey] = strings.Join(os.Args, " ")
+ }
+
+ opts.ReconnectPeriod = time.Duration(float64(opts.ReconnectPeriod) * (1 + 0.2*rand.Float64()))
+
+ if opts.Collector.Host == "" {
+ if opts.UseThrift {
+ opts.Collector.Host = DefaultThriftCollectorHost
+ } else {
+ opts.Collector.Host = DefaultGRPCCollectorHost
+ }
+ }
+
+ if opts.Collector.Port <= 0 {
+ if opts.Collector.Plaintext {
+ opts.Collector.Port = DefaultPlainPort
+ } else {
+ opts.Collector.Port = DefaultSecurePort
+ }
+ }
+
+ return nil
+}
+
+// Validate checks that all required fields are set, and no options are incorrectly
+// configured.
+func (opts *Options) Validate() error {
+ if len(opts.AccessToken) == 0 {
+ return errNoAccessToken
+ }
+
+ if _, found := opts.Tags[GUIDKey]; found {
+ return errInvalidGUIDKey
+ }
+
+ return nil
+}
+
+// SetSpanID is a opentracing.StartSpanOption that sets an
+// explicit SpanID. It must be used in conjunction with
+// SetTraceID or the result is undefined.
+type SetSpanID uint64
+
+// Apply satisfies the StartSpanOption interface.
+func (sid SetSpanID) Apply(sso *ot.StartSpanOptions) {}
+func (sid SetSpanID) applyLS(sso *startSpanOptions) {
+ sso.SetSpanID = uint64(sid)
+}
+
+// SetTraceID is an opentracing.StartSpanOption that sets an
+// explicit TraceID. It must be used in order to set an
+// explicit SpanID or ParentSpanID. If a ChildOf or
+// FollowsFrom span relation is also set in the start options,
+// it will override this value.
+type SetTraceID uint64
+
+// Apply satisfies the StartSpanOption interface.
+func (sid SetTraceID) Apply(sso *ot.StartSpanOptions) {}
+func (sid SetTraceID) applyLS(sso *startSpanOptions) {
+ sso.SetTraceID = uint64(sid)
+}
+
+// SetParentSpanID is an opentracing.StartSpanOption that sets
+// an explicit parent SpanID. It must be used in conjunction
+// with SetTraceID or the result is undefined. If the value
+// is zero, it will be disregarded. If a ChildOf or
+// FollowsFrom span relation is also set in the start options,
+// it will override this value.
+type SetParentSpanID uint64
+
+// Apply satisfies the StartSpanOption interface.
+func (sid SetParentSpanID) Apply(sso *ot.StartSpanOptions) {}
+func (sid SetParentSpanID) applyLS(sso *startSpanOptions) {
+ sso.SetParentSpanID = uint64(sid)
+}
+
+// lightStepStartSpanOption is used to identify lightstep-specific Span options.
+type lightStepStartSpanOption interface {
+ applyLS(*startSpanOptions)
+}
+
+type startSpanOptions struct {
+ Options ot.StartSpanOptions
+
+ // Options to explicitly set span_id, trace_id,
+ // parent_span_id, expected to be used when exporting spans
+ // from another system into LightStep via opentracing APIs.
+ SetSpanID uint64
+ SetParentSpanID uint64
+ SetTraceID uint64
+}
+
+func newStartSpanOptions(sso []ot.StartSpanOption) startSpanOptions {
+ opts := startSpanOptions{}
+ for _, o := range sso {
+ switch o := o.(type) {
+ case lightStepStartSpanOption:
+ o.applyLS(&opts)
+ default:
+ o.Apply(&opts.Options)
+ }
+ }
+ return opts
+}
diff --git a/vendor/github.com/lightstep/lightstep-tracer-go/propagation_binary.go b/vendor/github.com/lightstep/lightstep-tracer-go/propagation_binary.go
new file mode 100644
index 000000000..5fadf7fce
--- /dev/null
+++ b/vendor/github.com/lightstep/lightstep-tracer-go/propagation_binary.go
@@ -0,0 +1,111 @@
+package lightstep
+
+import (
+ "encoding/base64"
+ "io"
+ "io/ioutil"
+
+ "github.com/golang/protobuf/proto"
+ lightstep "github.com/lightstep/lightstep-tracer-go/lightsteppb"
+ opentracing "github.com/opentracing/opentracing-go"
+)
+
+// BinaryCarrier is used as the format parameter in inject/extract for lighstep binary propagation.
+const BinaryCarrier = opentracing.Binary
+
+var theBinaryPropagator binaryPropagator
+
+type binaryPropagator struct{}
+
+func (binaryPropagator) Inject(
+ spanContext opentracing.SpanContext,
+ opaqueCarrier interface{},
+) error {
+ sc, ok := spanContext.(SpanContext)
+ if !ok {
+ return opentracing.ErrInvalidSpanContext
+ }
+ data, err := proto.Marshal(&lightstep.BinaryCarrier{
+ BasicCtx: &lightstep.BasicTracerCarrier{
+ TraceId: sc.TraceID,
+ SpanId: sc.SpanID,
+ Sampled: true,
+ BaggageItems: sc.Baggage,
+ },
+ })
+ if err != nil {
+ return err
+ }
+
+ switch carrier := opaqueCarrier.(type) {
+ case io.Writer:
+ buf := make([]byte, base64.StdEncoding.EncodedLen(len(data)))
+ base64.StdEncoding.Encode(buf, data)
+ _, err = carrier.Write(buf)
+ return err
+ case *string:
+ *carrier = base64.StdEncoding.EncodeToString(data)
+ case *[]byte:
+ *carrier = make([]byte, base64.StdEncoding.EncodedLen(len(data)))
+ base64.StdEncoding.Encode(*carrier, data)
+ default:
+ return opentracing.ErrInvalidCarrier
+ }
+ return nil
+}
+
+func (binaryPropagator) Extract(
+ opaqueCarrier interface{},
+) (opentracing.SpanContext, error) {
+ var data []byte
+ var err error
+
+ // Decode from string, *string, *[]byte, or []byte
+ switch carrier := opaqueCarrier.(type) {
+ case io.Reader:
+ buf, err := ioutil.ReadAll(carrier)
+ if err != nil {
+ return nil, err
+ }
+ data, err = decodeBase64Bytes(buf)
+ case *string:
+ if carrier != nil {
+ data, err = base64.StdEncoding.DecodeString(*carrier)
+ }
+ case string:
+ data, err = base64.StdEncoding.DecodeString(carrier)
+ case *[]byte:
+ if carrier != nil {
+ data, err = decodeBase64Bytes(*carrier)
+ }
+ case []byte:
+ data, err = decodeBase64Bytes(carrier)
+ default:
+ return nil, opentracing.ErrInvalidCarrier
+ }
+ if err != nil {
+ return nil, err
+ }
+ pb := &lightstep.BinaryCarrier{}
+ if err := proto.Unmarshal(data, pb); err != nil {
+ return nil, err
+ }
+ if pb.BasicCtx == nil {
+ return nil, opentracing.ErrInvalidCarrier
+ }
+
+ return SpanContext{
+ TraceID: pb.BasicCtx.TraceId,
+ SpanID: pb.BasicCtx.SpanId,
+ Baggage: pb.BasicCtx.BaggageItems,
+ }, nil
+}
+
+func decodeBase64Bytes(in []byte) ([]byte, error) {
+ data := make([]byte, base64.StdEncoding.DecodedLen(len(in)))
+ n, err := base64.StdEncoding.Decode(data, in)
+ if err != nil {
+ return nil, err
+ }
+ return data[:n], nil
+}
diff --git a/vendor/github.com/lightstep/lightstep-tracer-go/propagation_text.go b/vendor/github.com/lightstep/lightstep-tracer-go/propagation_text.go
new file mode 100644
index 000000000..bc1cfe906
--- /dev/null
+++ b/vendor/github.com/lightstep/lightstep-tracer-go/propagation_text.go
@@ -0,0 +1,97 @@
+package lightstep
+
+import (
+ "strconv"
+ "strings"
+
+ opentracing "github.com/opentracing/opentracing-go"
+)
+
+const (
+ prefixTracerState = "ot-tracer-"
+ prefixBaggage = "ot-baggage-"
+
+ tracerStateFieldCount = 3
+ fieldNameTraceID = prefixTracerState + "traceid"
+ fieldNameSpanID = prefixTracerState + "spanid"
+ fieldNameSampled = prefixTracerState + "sampled"
+)
+
+var theTextMapPropagator textMapPropagator
+
+type textMapPropagator struct{}
+
+func (textMapPropagator) Inject(
+ spanContext opentracing.SpanContext,
+ opaqueCarrier interface{},
+) error {
+ sc, ok := spanContext.(SpanContext)
+ if !ok {
+ return opentracing.ErrInvalidSpanContext
+ }
+ carrier, ok := opaqueCarrier.(opentracing.TextMapWriter)
+ if !ok {
+ return opentracing.ErrInvalidCarrier
+ }
+ carrier.Set(fieldNameTraceID, strconv.FormatUint(sc.TraceID, 16))
+ carrier.Set(fieldNameSpanID, strconv.FormatUint(sc.SpanID, 16))
+ carrier.Set(fieldNameSampled, "true")
+
+ for k, v := range sc.Baggage {
+ carrier.Set(prefixBaggage+k, v)
+ }
+ return nil
+}
+
+func (textMapPropagator) Extract(
+ opaqueCarrier interface{},
+) (opentracing.SpanContext, error) {
+ carrier, ok := opaqueCarrier.(opentracing.TextMapReader)
+ if !ok {
+ return nil, opentracing.ErrInvalidCarrier
+ }
+
+ requiredFieldCount := 0
+ var traceID, spanID uint64
+ var err error
+ decodedBaggage := map[string]string{}
+ err = carrier.ForeachKey(func(k, v string) error {
+ switch strings.ToLower(k) {
+ case fieldNameTraceID:
+ traceID, err = strconv.ParseUint(v, 16, 64)
+ if err != nil {
+ return opentracing.ErrSpanContextCorrupted
+ }
+ requiredFieldCount++
+ case fieldNameSpanID:
+ spanID, err = strconv.ParseUint(v, 16, 64)
+ if err != nil {
+ return opentracing.ErrSpanContextCorrupted
+ }
+ requiredFieldCount++
+ case fieldNameSampled:
+ requiredFieldCount++
+ default:
+ lowercaseK := strings.ToLower(k)
+ if strings.HasPrefix(lowercaseK, prefixBaggage) {
+ decodedBaggage[strings.TrimPrefix(lowercaseK, prefixBaggage)] = v
+ }
+ }
+ return nil
+ })
+ if err != nil {
+ return nil, err
+ }
+ if requiredFieldCount < tracerStateFieldCount {
+ if requiredFieldCount == 0 {
+ return nil, opentracing.ErrSpanContextNotFound
+ }
+ return nil, opentracing.ErrSpanContextCorrupted
+ }
+
+ return SpanContext{
+ TraceID: traceID,
+ SpanID: spanID,
+ Baggage: decodedBaggage,
+ }, nil
+}
diff --git a/vendor/github.com/lightstep/lightstep-tracer-go/proto_converter.go b/vendor/github.com/lightstep/lightstep-tracer-go/proto_converter.go
new file mode 100644
index 000000000..1f1dc2b82
--- /dev/null
+++ b/vendor/github.com/lightstep/lightstep-tracer-go/proto_converter.go
@@ -0,0 +1,191 @@
+package lightstep
+
+import (
+ "fmt"
+ "reflect"
+ "time"
+
+ google_protobuf "github.com/golang/protobuf/ptypes/timestamp"
+ cpb "github.com/lightstep/lightstep-tracer-go/collectorpb"
+ ot "github.com/opentracing/opentracing-go"
+)
+
+type protoConverter struct {
+ verbose bool
+ maxLogKeyLen int // see GrpcOptions.MaxLogKeyLen
+ maxLogValueLen int // see GrpcOptions.MaxLogValueLen
+}
+
+func newProtoConverter(options Options) *protoConverter {
+ return &protoConverter{
+ verbose: options.Verbose,
+ maxLogKeyLen: options.MaxLogKeyLen,
+ maxLogValueLen: options.MaxLogValueLen,
+ }
+}
+
+func (converter *protoConverter) toReportRequest(
+ reporterID uint64,
+ attributes map[string]string,
+ accessToken string,
+ buffer *reportBuffer,
+) *cpb.ReportRequest {
+ return &cpb.ReportRequest{
+ Reporter: converter.toReporter(reporterID, attributes),
+ Auth: converter.toAuth(accessToken),
+ Spans: converter.toSpans(buffer),
+ InternalMetrics: converter.toInternalMetrics(buffer),
+ }
+
+}
+
+func (converter *protoConverter) toReporter(reporterID uint64, attributes map[string]string) *cpb.Reporter {
+ return &cpb.Reporter{
+ ReporterId: reporterID,
+ Tags: converter.toFields(attributes),
+ }
+}
+
+func (converter *protoConverter) toAuth(accessToken string) *cpb.Auth {
+ return &cpb.Auth{
+ AccessToken: accessToken,
+ }
+}
+
+func (converter *protoConverter) toSpans(buffer *reportBuffer) []*cpb.Span {
+ spans := make([]*cpb.Span, len(buffer.rawSpans))
+ for i, span := range buffer.rawSpans {
+ spans[i] = converter.toSpan(span, buffer)
+ }
+ return spans
+}
+
+func (converter *protoConverter) toSpan(span RawSpan, buffer *reportBuffer) *cpb.Span {
+ return &cpb.Span{
+ SpanContext: converter.toSpanContext(&span.Context),
+ OperationName: span.Operation,
+ References: converter.toReference(span.ParentSpanID),
+ StartTimestamp: converter.toTimestamp(span.Start),
+ DurationMicros: converter.fromDuration(span.Duration),
+ Tags: converter.fromTags(span.Tags),
+ Logs: converter.toLogs(span.Logs, buffer),
+ }
+}
+
+func (converter *protoConverter) toInternalMetrics(buffer *reportBuffer) *cpb.InternalMetrics {
+ return &cpb.InternalMetrics{
+ StartTimestamp: converter.toTimestamp(buffer.reportStart),
+ DurationMicros: converter.fromTimeRange(buffer.reportStart, buffer.reportEnd),
+ Counts: converter.toMetricsSample(buffer),
+ }
+}
+
+func (converter *protoConverter) toMetricsSample(buffer *reportBuffer) []*cpb.MetricsSample {
+ return []*cpb.MetricsSample{
+ {
+ Name: spansDropped,
+ Value: &cpb.MetricsSample_IntValue{IntValue: buffer.droppedSpanCount},
+ },
+ {
+ Name: logEncoderErrors,
+ Value: &cpb.MetricsSample_IntValue{IntValue: buffer.logEncoderErrorCount},
+ },
+ }
+}
+
+func (converter *protoConverter) fromTags(tags ot.Tags) []*cpb.KeyValue {
+ fields := make([]*cpb.KeyValue, 0, len(tags))
+ for key, tag := range tags {
+ fields = append(fields, converter.toField(key, tag))
+ }
+ return fields
+}
+
+func (converter *protoConverter) toField(key string, value interface{}) *cpb.KeyValue {
+ field := cpb.KeyValue{Key: key}
+ reflectedValue := reflect.ValueOf(value)
+ switch reflectedValue.Kind() {
+ case reflect.String:
+ field.Value = &cpb.KeyValue_StringValue{StringValue: reflectedValue.String()}
+ case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64, reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64:
+ field.Value = &cpb.KeyValue_IntValue{IntValue: reflectedValue.Convert(intType).Int()}
+ case reflect.Float32, reflect.Float64:
+ field.Value = &cpb.KeyValue_DoubleValue{DoubleValue: reflectedValue.Float()}
+ case reflect.Bool:
+ field.Value = &cpb.KeyValue_BoolValue{BoolValue: reflectedValue.Bool()}
+ default:
+ var s string
+ switch value := value.(type) {
+ case fmt.Stringer:
+ s = value.String()
+ case error:
+ s = value.Error()
+ default:
+ s = fmt.Sprintf("%#v", value)
+ emitEvent(newEventUnsupportedValue(key, value, nil))
+ }
+ field.Value = &cpb.KeyValue_StringValue{StringValue: s}
+ }
+ return &field
+}
+
+func (converter *protoConverter) toLogs(records []ot.LogRecord, buffer *reportBuffer) []*cpb.Log {
+ logs := make([]*cpb.Log, len(records))
+ for i, record := range records {
+ logs[i] = converter.toLog(record, buffer)
+ }
+ return logs
+}
+
+func (converter *protoConverter) toLog(record ot.LogRecord, buffer *reportBuffer) *cpb.Log {
+ log := &cpb.Log{
+ Timestamp: converter.toTimestamp(record.Timestamp),
+ }
+ marshalFields(converter, log, record.Fields, buffer)
+ return log
+}
+
+func (converter *protoConverter) toFields(attributes map[string]string) []*cpb.KeyValue {
+ tags := make([]*cpb.KeyValue, 0, len(attributes))
+ for key, value := range attributes {
+ tags = append(tags, converter.toField(key, value))
+ }
+ return tags
+}
+
+func (converter *protoConverter) toSpanContext(sc *SpanContext) *cpb.SpanContext {
+ return &cpb.SpanContext{
+ TraceId: sc.TraceID,
+ SpanId: sc.SpanID,
+ Baggage: sc.Baggage,
+ }
+}
+
+func (converter *protoConverter) toReference(parentSpanID uint64) []*cpb.Reference {
+ if parentSpanID == 0 {
+ return nil
+ }
+ return []*cpb.Reference{
+ {
+ Relationship: cpb.Reference_CHILD_OF,
+ SpanContext: &cpb.SpanContext{
+ SpanId: parentSpanID,
+ },
+ },
+ }
+}
+
+func (converter *protoConverter) toTimestamp(t time.Time) *google_protobuf.Timestamp {
+ return &google_protobuf.Timestamp{
+ Seconds: t.Unix(),
+ Nanos: int32(t.Nanosecond()),
+ }
+}
+
+func (converter *protoConverter) fromDuration(d time.Duration) uint64 {
+ return uint64(d / time.Microsecond)
+}
+
+func (converter *protoConverter) fromTimeRange(oldestTime time.Time, youngestTime time.Time) uint64 {
+ return converter.fromDuration(youngestTime.Sub(oldestTime))
+}
diff --git a/vendor/github.com/lightstep/lightstep-tracer-go/proto_logencoder.go b/vendor/github.com/lightstep/lightstep-tracer-go/proto_logencoder.go
new file mode 100644
index 000000000..be8887c0b
--- /dev/null
+++ b/vendor/github.com/lightstep/lightstep-tracer-go/proto_logencoder.go
@@ -0,0 +1,110 @@
+package lightstep
+
+import (
+ "encoding/json"
+
+ cpb "github.com/lightstep/lightstep-tracer-go/collectorpb"
+ "github.com/opentracing/opentracing-go/log"
+)
+
+const (
+ ellipsis = "…"
+)
+
+// An implementation of the log.Encoder interface
+type grpcLogFieldEncoder struct {
+ converter *protoConverter
+ buffer *reportBuffer
+ currentKeyValue *cpb.KeyValue
+}
+
+func marshalFields(
+ converter *protoConverter,
+ protoLog *cpb.Log,
+ fields []log.Field,
+ buffer *reportBuffer,
+) {
+ logFieldEncoder := grpcLogFieldEncoder{
+ converter: converter,
+ buffer: buffer,
+ }
+ protoLog.Fields = make([]*cpb.KeyValue, len(fields))
+ for i, field := range fields {
+ logFieldEncoder.currentKeyValue = &cpb.KeyValue{}
+ field.Marshal(&logFieldEncoder)
+ protoLog.Fields[i] = logFieldEncoder.currentKeyValue
+ }
+}
+
+func (lfe *grpcLogFieldEncoder) EmitString(key, value string) {
+ lfe.emitSafeKey(key)
+ lfe.emitSafeString(value)
+}
+func (lfe *grpcLogFieldEncoder) EmitBool(key string, value bool) {
+ lfe.emitSafeKey(key)
+ lfe.currentKeyValue.Value = &cpb.KeyValue_BoolValue{BoolValue: value}
+}
+func (lfe *grpcLogFieldEncoder) EmitInt(key string, value int) {
+ lfe.emitSafeKey(key)
+ lfe.currentKeyValue.Value = &cpb.KeyValue_IntValue{IntValue: int64(value)}
+}
+func (lfe *grpcLogFieldEncoder) EmitInt32(key string, value int32) {
+ lfe.emitSafeKey(key)
+ lfe.currentKeyValue.Value = &cpb.KeyValue_IntValue{IntValue: int64(value)}
+}
+func (lfe *grpcLogFieldEncoder) EmitInt64(key string, value int64) {
+ lfe.emitSafeKey(key)
+ lfe.currentKeyValue.Value = &cpb.KeyValue_IntValue{IntValue: value}
+}
+func (lfe *grpcLogFieldEncoder) EmitUint32(key string, value uint32) {
+ lfe.emitSafeKey(key)
+ lfe.currentKeyValue.Value = &cpb.KeyValue_IntValue{IntValue: int64(value)}
+}
+func (lfe *grpcLogFieldEncoder) EmitUint64(key string, value uint64) {
+ lfe.emitSafeKey(key)
+ lfe.currentKeyValue.Value = &cpb.KeyValue_IntValue{IntValue: int64(value)}
+}
+func (lfe *grpcLogFieldEncoder) EmitFloat32(key string, value float32) {
+ lfe.emitSafeKey(key)
+ lfe.currentKeyValue.Value = &cpb.KeyValue_DoubleValue{DoubleValue: float64(value)}
+}
+func (lfe *grpcLogFieldEncoder) EmitFloat64(key string, value float64) {
+ lfe.emitSafeKey(key)
+ lfe.currentKeyValue.Value = &cpb.KeyValue_DoubleValue{DoubleValue: value}
+}
+func (lfe *grpcLogFieldEncoder) EmitObject(key string, value interface{}) {
+ lfe.emitSafeKey(key)
+ jsonBytes, err := json.Marshal(value)
+ if err != nil {
+ emitEvent(newEventUnsupportedValue(key, value, err))
+ lfe.buffer.logEncoderErrorCount++
+ lfe.emitSafeString("<json.Marshal error>")
+ return
+ }
+ lfe.emitSafeJSON(string(jsonBytes))
+}
+func (lfe *grpcLogFieldEncoder) EmitLazyLogger(value log.LazyLogger) {
+ // Delegate to `value` to do the late-bound encoding.
+ value(lfe)
+}
+
+func (lfe *grpcLogFieldEncoder) emitSafeKey(key string) {
+ if len(key) > lfe.converter.maxLogKeyLen {
+ key = key[:(lfe.converter.maxLogKeyLen-1)] + ellipsis
+ }
+ lfe.currentKeyValue.Key = key
+}
+func (lfe *grpcLogFieldEncoder) emitSafeString(str string) {
+ if len(str) > lfe.converter.maxLogValueLen {
+ str = str[:(lfe.converter.maxLogValueLen-1)] + ellipsis
+ }
+ lfe.currentKeyValue.Value = &cpb.KeyValue_StringValue{StringValue: str}
+}
+func (lfe *grpcLogFieldEncoder) emitSafeJSON(json string) {
+ if len(json) > lfe.converter.maxLogValueLen {
+ str := json[:(lfe.converter.maxLogValueLen-1)] + ellipsis
+ lfe.currentKeyValue.Value = &cpb.KeyValue_StringValue{StringValue: str}
+ return
+ }
+ lfe.currentKeyValue.Value = &cpb.KeyValue_JsonValue{JsonValue: json}
+}
diff --git a/vendor/github.com/lightstep/lightstep-tracer-go/raw_span.go b/vendor/github.com/lightstep/lightstep-tracer-go/raw_span.go
new file mode 100644
index 000000000..b63b14b2d
--- /dev/null
+++ b/vendor/github.com/lightstep/lightstep-tracer-go/raw_span.go
@@ -0,0 +1,72 @@
+package lightstep
+
+import (
+ "time"
+
+ opentracing "github.com/opentracing/opentracing-go"
+)
+
+// RawSpan encapsulates all state associated with a (finished) LightStep Span.
+type RawSpan struct {
+ // Those recording the RawSpan should also record the contents of its
+ // SpanContext.
+ Context SpanContext
+
+ // The SpanID of this SpanContext's first intra-trace reference (i.e.,
+ // "parent"), or 0 if there is no parent.
+ ParentSpanID uint64
+
+ // The name of the "operation" this span is an instance of. (Called a "span
+ // name" in some implementations)
+ Operation string
+
+ // We store <start, duration> rather than <start, end> so that only
+ // one of the timestamps has global clock uncertainty issues.
+ Start time.Time
+ Duration time.Duration
+
+ // Essentially an extension mechanism. Can be used for many purposes,
+ // not to be enumerated here.
+ Tags opentracing.Tags
+
+ // The span's "microlog".
+ Logs []opentracing.LogRecord
+}
+
+// SpanContext holds lightstep-specific Span metadata.
+type SpanContext struct {
+ // A probabilistically unique identifier for a [multi-span] trace.
+ TraceID uint64
+
+ // A probabilistically unique identifier for a span.
+ SpanID uint64
+
+ // The span's associated baggage.
+ Baggage map[string]string // initialized on first use
+}
+
+// ForeachBaggageItem belongs to the opentracing.SpanContext interface
+func (c SpanContext) ForeachBaggageItem(handler func(k, v string) bool) {
+ for k, v := range c.Baggage {
+ if !handler(k, v) {
+ break
+ }
+ }
+}
+
+// WithBaggageItem returns an entirely new basictracer SpanContext with the
+// given key:value baggage pair set.
+func (c SpanContext) WithBaggageItem(key, val string) SpanContext {
+ var newBaggage map[string]string
+ if c.Baggage == nil {
+ newBaggage = map[string]string{key: val}
+ } else {
+ newBaggage = make(map[string]string, len(c.Baggage)+1)
+ for k, v := range c.Baggage {
+ newBaggage[k] = v
+ }
+ newBaggage[key] = val
+ }
+ // Use positional parameters so the compiler will help catch new fields.
+ return SpanContext{c.TraceID, c.SpanID, newBaggage}
+}
diff --git a/vendor/github.com/lightstep/lightstep-tracer-go/report_buffer.go b/vendor/github.com/lightstep/lightstep-tracer-go/report_buffer.go
new file mode 100644
index 000000000..ae58a4d27
--- /dev/null
+++ b/vendor/github.com/lightstep/lightstep-tracer-go/report_buffer.go
@@ -0,0 +1,79 @@
+package lightstep
+
+import (
+ "time"
+)
+
+type reportBuffer struct {
+ rawSpans []RawSpan
+ droppedSpanCount int64
+ logEncoderErrorCount int64
+ reportStart time.Time
+ reportEnd time.Time
+}
+
+func newSpansBuffer(size int) (b reportBuffer) {
+ b.rawSpans = make([]RawSpan, 0, size)
+ b.reportStart = time.Time{}
+ b.reportEnd = time.Time{}
+ return
+}
+
+func (b *reportBuffer) isHalfFull() bool {
+ return len(b.rawSpans) > cap(b.rawSpans)/2
+}
+
+func (b *reportBuffer) setCurrent(now time.Time) {
+ b.reportStart = now
+ b.reportEnd = now
+}
+
+func (b *reportBuffer) setFlushing(now time.Time) {
+ b.reportEnd = now
+}
+
+func (b *reportBuffer) clear() {
+ b.rawSpans = b.rawSpans[:0]
+ b.reportStart = time.Time{}
+ b.reportEnd = time.Time{}
+ b.droppedSpanCount = 0
+ b.logEncoderErrorCount = 0
+}
+
+func (b *reportBuffer) addSpan(span RawSpan) {
+ if len(b.rawSpans) == cap(b.rawSpans) {
+ b.droppedSpanCount++
+ return
+ }
+ b.rawSpans = append(b.rawSpans, span)
+}
+
+// mergeFrom combines the spans and metadata in `from` with `into`,
+// returning with `from` empty and `into` having a subset of the
+// combined data.
+func (b *reportBuffer) mergeFrom(from *reportBuffer) {
+ b.droppedSpanCount += from.droppedSpanCount
+ b.logEncoderErrorCount += from.logEncoderErrorCount
+ if from.reportStart.Before(b.reportStart) {
+ b.reportStart = from.reportStart
+ }
+ if from.reportEnd.After(b.reportEnd) {
+ b.reportEnd = from.reportEnd
+ }
+
+ // Note: Somewhat arbitrarily dropping the spans that won't
+ // fit; could be more principled here to avoid bias.
+ have := len(b.rawSpans)
+ space := cap(b.rawSpans) - have
+ unreported := len(from.rawSpans)
+
+ if space > unreported {
+ space = unreported
+ }
+
+ b.rawSpans = append(b.rawSpans, from.rawSpans[0:space]...)
+
+ b.droppedSpanCount += int64(unreported - space)
+
+ from.clear()
+}
diff --git a/vendor/github.com/lightstep/lightstep-tracer-go/span.go b/vendor/github.com/lightstep/lightstep-tracer-go/span.go
new file mode 100644
index 000000000..ae418e864
--- /dev/null
+++ b/vendor/github.com/lightstep/lightstep-tracer-go/span.go
@@ -0,0 +1,266 @@
+package lightstep
+
+import (
+ "sync"
+ "time"
+
+ ot "github.com/opentracing/opentracing-go"
+ "github.com/opentracing/opentracing-go/log"
+)
+
+// Implements the `Span` interface. Created via tracerImpl (see
+// `New()`).
+type spanImpl struct {
+ tracer *tracerImpl
+ sync.Mutex // protects the fields below
+ raw RawSpan
+ // The number of logs dropped because of MaxLogsPerSpan.
+ numDroppedLogs int
+}
+
+func newSpan(operationName string, tracer *tracerImpl, sso []ot.StartSpanOption) *spanImpl {
+ opts := newStartSpanOptions(sso)
+
+ // Start time.
+ startTime := opts.Options.StartTime
+ if startTime.IsZero() {
+ startTime = time.Now()
+ }
+
+ // Build the new span. This is the only allocation: We'll return this as
+ // an opentracing.Span.
+ sp := &spanImpl{}
+
+ // It's meaningless to provide either SpanID or ParentSpanID
+ // without also providing TraceID, so just test for TraceID.
+ if opts.SetTraceID != 0 {
+ sp.raw.Context.TraceID = opts.SetTraceID
+ sp.raw.Context.SpanID = opts.SetSpanID
+ sp.raw.ParentSpanID = opts.SetParentSpanID
+ }
+
+ // Look for a parent in the list of References.
+ //
+ // TODO: would be nice if we did something with all References, not just
+ // the first one.
+ReferencesLoop:
+ for _, ref := range opts.Options.References {
+ switch ref.Type {
+ case ot.ChildOfRef, ot.FollowsFromRef:
+ refCtx, ok := ref.ReferencedContext.(SpanContext)
+ if !ok {
+ break ReferencesLoop
+ }
+ sp.raw.Context.TraceID = refCtx.TraceID
+ sp.raw.ParentSpanID = refCtx.SpanID
+
+ if l := len(refCtx.Baggage); l > 0 {
+ sp.raw.Context.Baggage = make(map[string]string, l)
+ for k, v := range refCtx.Baggage {
+ sp.raw.Context.Baggage[k] = v
+ }
+ }
+ break ReferencesLoop
+ }
+ }
+
+ if sp.raw.Context.TraceID == 0 {
+ // TraceID not set by parent reference or explicitly
+ sp.raw.Context.TraceID, sp.raw.Context.SpanID = genSeededGUID2()
+ } else if sp.raw.Context.SpanID == 0 {
+ // TraceID set but SpanID not set
+ sp.raw.Context.SpanID = genSeededGUID()
+ }
+
+ sp.tracer = tracer
+ sp.raw.Operation = operationName
+ sp.raw.Start = startTime
+ sp.raw.Duration = -1
+ sp.raw.Tags = opts.Options.Tags
+ return sp
+}
+
+func (s *spanImpl) SetOperationName(operationName string) ot.Span {
+ s.Lock()
+ defer s.Unlock()
+ s.raw.Operation = operationName
+ return s
+}
+
+func (s *spanImpl) SetTag(key string, value interface{}) ot.Span {
+ s.Lock()
+ defer s.Unlock()
+
+ if s.raw.Tags == nil {
+ s.raw.Tags = ot.Tags{}
+ }
+ s.raw.Tags[key] = value
+ return s
+}
+
+func (s *spanImpl) LogKV(keyValues ...interface{}) {
+ fields, err := log.InterleavedKVToFields(keyValues...)
+ if err != nil {
+ s.LogFields(log.Error(err), log.String("function", "LogKV"))
+ return
+ }
+ s.LogFields(fields...)
+}
+
+func (s *spanImpl) appendLog(lr ot.LogRecord) {
+ maxLogs := s.tracer.opts.MaxLogsPerSpan
+ if maxLogs == 0 || len(s.raw.Logs) < maxLogs {
+ s.raw.Logs = append(s.raw.Logs, lr)
+ return
+ }
+
+ // We have too many logs. We don't touch the first numOld logs; we treat the
+ // rest as a circular buffer and overwrite the oldest log among those.
+ numOld := (maxLogs - 1) / 2
+ numNew := maxLogs - numOld
+ s.raw.Logs[numOld+s.numDroppedLogs%numNew] = lr
+ s.numDroppedLogs++
+}
+
+func (s *spanImpl) LogFields(fields ...log.Field) {
+ lr := ot.LogRecord{
+ Fields: fields,
+ }
+ s.Lock()
+ defer s.Unlock()
+ if s.tracer.opts.DropSpanLogs {
+ return
+ }
+ if lr.Timestamp.IsZero() {
+ lr.Timestamp = time.Now()
+ }
+ s.appendLog(lr)
+}
+
+func (s *spanImpl) LogEvent(event string) {
+ s.Log(ot.LogData{
+ Event: event,
+ })
+}
+
+func (s *spanImpl) LogEventWithPayload(event string, payload interface{}) {
+ s.Log(ot.LogData{
+ Event: event,
+ Payload: payload,
+ })
+}
+
+func (s *spanImpl) Log(ld ot.LogData) {
+ s.Lock()
+ defer s.Unlock()
+ if s.tracer.opts.DropSpanLogs {
+ return
+ }
+
+ if ld.Timestamp.IsZero() {
+ ld.Timestamp = time.Now()
+ }
+
+ s.appendLog(ld.ToLogRecord())
+}
+
+func (s *spanImpl) Finish() {
+ s.FinishWithOptions(ot.FinishOptions{})
+}
+
+// rotateLogBuffer rotates the records in the buffer: records 0 to pos-1 move at
+// the end (i.e. pos circular left shifts).
+func rotateLogBuffer(buf []ot.LogRecord, pos int) {
+ // This algorithm is described in:
+ // http://www.cplusplus.com/reference/algorithm/rotate
+ for first, middle, next := 0, pos, pos; first != middle; {
+ buf[first], buf[next] = buf[next], buf[first]
+ first++
+ next++
+ if next == len(buf) {
+ next = middle
+ } else if first == middle {
+ middle = next
+ }
+ }
+}
+
+func (s *spanImpl) FinishWithOptions(opts ot.FinishOptions) {
+ finishTime := opts.FinishTime
+ if finishTime.IsZero() {
+ finishTime = time.Now()
+ }
+ duration := finishTime.Sub(s.raw.Start)
+
+ s.Lock()
+ defer s.Unlock()
+
+ // If the duration is already set, this span has already been finished.
+ // Return so we don't double submit the span.
+ if s.raw.Duration >= 0 {
+ return
+ }
+
+ for _, lr := range opts.LogRecords {
+ s.appendLog(lr)
+ }
+ for _, ld := range opts.BulkLogData {
+ s.appendLog(ld.ToLogRecord())
+ }
+
+ if s.numDroppedLogs > 0 {
+ // We dropped some log events, which means that we used part of Logs as a
+ // circular buffer (see appendLog). De-circularize it.
+ numOld := (len(s.raw.Logs) - 1) / 2
+ numNew := len(s.raw.Logs) - numOld
+ rotateLogBuffer(s.raw.Logs[numOld:], s.numDroppedLogs%numNew)
+
+ // Replace the log in the middle (the oldest "new" log) with information
+ // about the dropped logs. This means that we are effectively dropping one
+ // more "new" log.
+ numDropped := s.numDroppedLogs + 1
+ s.raw.Logs[numOld] = ot.LogRecord{
+ // Keep the timestamp of the last dropped event.
+ Timestamp: s.raw.Logs[numOld].Timestamp,
+ Fields: []log.Field{
+ log.String("event", "dropped Span logs"),
+ log.Int("dropped_log_count", numDropped),
+ log.String("component", "basictracer"),
+ },
+ }
+ }
+
+ s.raw.Duration = duration
+
+ s.tracer.RecordSpan(s.raw)
+}
+
+func (s *spanImpl) Tracer() ot.Tracer {
+ return s.tracer
+}
+
+func (s *spanImpl) Context() ot.SpanContext {
+ return s.raw.Context
+}
+
+func (s *spanImpl) SetBaggageItem(key, val string) ot.Span {
+
+ s.Lock()
+ defer s.Unlock()
+ s.raw.Context = s.raw.Context.WithBaggageItem(key, val)
+ return s
+}
+
+func (s *spanImpl) BaggageItem(key string) string {
+ s.Lock()
+ defer s.Unlock()
+ return s.raw.Context.Baggage[key]
+}
+
+func (s *spanImpl) Operation() string {
+ return s.raw.Operation
+}
+
+func (s *spanImpl) Start() time.Time {
+ return s.raw.Start
+}
diff --git a/vendor/github.com/lightstep/lightstep-tracer-go/tag_version.sh b/vendor/github.com/lightstep/lightstep-tracer-go/tag_version.sh
new file mode 100755
index 000000000..1cab1fc57
--- /dev/null
+++ b/vendor/github.com/lightstep/lightstep-tracer-go/tag_version.sh
@@ -0,0 +1,10 @@
+#!/bin/sh
+
+VERSION=$(cat ./VERSION)
+
+cat > version.go <<EOF
+package lightstep
+
+// TracerVersionValue provides the current version of the lightstep-tracer-go release
+const TracerVersionValue = "$VERSION"
+EOF
diff --git a/vendor/github.com/lightstep/lightstep-tracer-go/thrift_logencoder.go b/vendor/github.com/lightstep/lightstep-tracer-go/thrift_logencoder.go
new file mode 100644
index 000000000..5e354e2d2
--- /dev/null
+++ b/vendor/github.com/lightstep/lightstep-tracer-go/thrift_logencoder.go
@@ -0,0 +1,76 @@
+package lightstep
+
+import (
+ "encoding/json"
+ "fmt"
+
+ "github.com/lightstep/lightstep-tracer-go/lightstep_thrift"
+ "github.com/opentracing/opentracing-go/log"
+)
+
+// thrift_rpc.thriftLogFieldEncoder is an implementation of the log.Encoder interface
+// that handles only the deprecated OpenTracing
+// Span.LogEvent/LogEventWithPayload calls. (Since the thrift client is being
+// phased out anyway)
+type thriftLogFieldEncoder struct {
+ logRecord *lightstep_thrift.LogRecord
+ recorder *thriftCollectorClient
+}
+
+func (lfe *thriftLogFieldEncoder) EmitString(key, value string) {
+ if len(key) > lfe.recorder.maxLogMessageLen {
+ key = key[:(lfe.recorder.maxLogKeyLen-1)] + ellipsis
+ }
+
+ if len(value) > lfe.recorder.maxLogMessageLen {
+ value = value[:(lfe.recorder.maxLogMessageLen-1)] + ellipsis
+ }
+
+ lfe.logRecord.Fields = append(lfe.logRecord.Fields, &lightstep_thrift.KeyValue{
+ Key: key,
+ Value: value,
+ })
+}
+
+func (lfe *thriftLogFieldEncoder) EmitObject(key string, value interface{}) {
+ var thriftPayload string
+ jsonString, err := json.Marshal(value)
+ if err != nil {
+ thriftPayload = fmt.Sprintf("Error encoding payload object: %v", err)
+ } else {
+ thriftPayload = string(jsonString)
+ }
+ if len(thriftPayload) > lfe.recorder.maxLogMessageLen {
+ thriftPayload = thriftPayload[:(lfe.recorder.maxLogMessageLen-1)] + ellipsis
+ }
+ lfe.logRecord.Fields = append(lfe.logRecord.Fields, &lightstep_thrift.KeyValue{
+ Key: key,
+ Value: thriftPayload,
+ })
+}
+
+func (lfe *thriftLogFieldEncoder) EmitBool(key string, value bool) {
+ lfe.EmitString(key, fmt.Sprint(value))
+}
+func (lfe *thriftLogFieldEncoder) EmitInt(key string, value int) {
+ lfe.EmitString(key, fmt.Sprint(value))
+}
+func (lfe *thriftLogFieldEncoder) EmitInt32(key string, value int32) {
+ lfe.EmitString(key, fmt.Sprint(value))
+}
+func (lfe *thriftLogFieldEncoder) EmitInt64(key string, value int64) {
+ lfe.EmitString(key, fmt.Sprint(value))
+}
+func (lfe *thriftLogFieldEncoder) EmitUint32(key string, value uint32) {
+ lfe.EmitString(key, fmt.Sprint(value))
+}
+func (lfe *thriftLogFieldEncoder) EmitUint64(key string, value uint64) {
+ lfe.EmitString(key, fmt.Sprint(value))
+}
+func (lfe *thriftLogFieldEncoder) EmitFloat32(key string, value float32) {
+ lfe.EmitString(key, fmt.Sprint(value))
+}
+func (lfe *thriftLogFieldEncoder) EmitFloat64(key string, value float64) {
+ lfe.EmitString(key, fmt.Sprint(value))
+}
+func (lfe *thriftLogFieldEncoder) EmitLazyLogger(value log.LazyLogger) {}
diff --git a/vendor/github.com/lightstep/lightstep-tracer-go/tracer.go b/vendor/github.com/lightstep/lightstep-tracer-go/tracer.go
new file mode 100644
index 000000000..78f5d9b3c
--- /dev/null
+++ b/vendor/github.com/lightstep/lightstep-tracer-go/tracer.go
@@ -0,0 +1,376 @@
+// Package lightstep implements the LightStep OpenTracing client for Go.
+package lightstep
+
+import (
+ "context"
+ "fmt"
+ "time"
+
+ "runtime"
+ "sync"
+
+ ot "github.com/opentracing/opentracing-go"
+)
+
+// Tracer extends the `opentracing.Tracer` interface with methods for manual
+// flushing and closing. To access these methods, you can take the global
+// tracer and typecast it to a `lightstep.Tracer`. As a convenience, the
+// lightstep package provides static functions which perform the typecasting.
+type Tracer interface {
+ ot.Tracer
+
+ // Close flushes and then terminates the LightStep collector
+ Close(context.Context)
+ // Flush sends all spans currently in the buffer to the LighStep collector
+ Flush(context.Context)
+ // Options gets the Options used in New() or NewWithOptions().
+ Options() Options
+ // Disable prevents the tracer from recording spans or flushing
+ Disable()
+}
+
+// Implements the `Tracer` interface. Buffers spans and forwards the to a Lightstep collector.
+type tracerImpl struct {
+ //////////////////////////////////////////////////////////////
+ // IMMUTABLE IMMUTABLE IMMUTABLE IMMUTABLE IMMUTABLE IMMUTABLE
+ //////////////////////////////////////////////////////////////
+
+ // Note: there may be a desire to update some of these fields
+ // at runtime, in which case suitable changes may be needed
+ // for variables accessed during Flush.
+
+ reporterID uint64 // the LightStep tracer guid
+ opts Options
+
+ // report loop management
+ closeOnce sync.Once
+ closeReportLoopChannel chan struct{}
+ reportLoopClosedChannel chan struct{}
+
+ //////////////////////////////////////////////////////////
+ // MUTABLE MUTABLE MUTABLE MUTABLE MUTABLE MUTABLE MUTABLE
+ //////////////////////////////////////////////////////////
+
+ // the following fields are modified under `lock`.
+ lock sync.Mutex
+
+ // Remote service that will receive reports.
+ client collectorClient
+ connection Connection
+
+ // Two buffers of data.
+ buffer reportBuffer
+ flushing reportBuffer
+
+ // Flush state.
+ flushingLock sync.Mutex
+ reportInFlight bool
+ lastReportAttempt time.Time
+
+ // We allow our remote peer to disable this instrumentation at any
+ // time, turning all potentially costly runtime operations into
+ // no-ops.
+ //
+ // TODO this should use atomic load/store to test disabled
+ // prior to taking the lock, do please.
+ disabled bool
+}
+
+// NewTracer creates and starts a new Lightstep Tracer.
+func NewTracer(opts Options) Tracer {
+ err := opts.Initialize()
+ if err != nil {
+ emitEvent(newEventStartError(err))
+ return nil
+ }
+
+ attributes := map[string]string{}
+ for k, v := range opts.Tags {
+ attributes[k] = fmt.Sprint(v)
+ }
+ // Don't let the GrpcOptions override these values. That would be confusing.
+ attributes[TracerPlatformKey] = TracerPlatformValue
+ attributes[TracerPlatformVersionKey] = runtime.Version()
+ attributes[TracerVersionKey] = TracerVersionValue
+
+ now := time.Now()
+ impl := &tracerImpl{
+ opts: opts,
+ reporterID: genSeededGUID(),
+ buffer: newSpansBuffer(opts.MaxBufferedSpans),
+ flushing: newSpansBuffer(opts.MaxBufferedSpans),
+ closeReportLoopChannel: make(chan struct{}),
+ reportLoopClosedChannel: make(chan struct{}),
+ }
+
+ impl.buffer.setCurrent(now)
+
+ impl.client, err = newCollectorClient(opts, impl.reporterID, attributes)
+ if err != nil {
+ fmt.Println("Failed to create to Collector client!", err)
+ return nil
+ }
+
+ conn, err := impl.client.ConnectClient()
+ if err != nil {
+ emitEvent(newEventStartError(err))
+ return nil
+ }
+ impl.connection = conn
+
+ go impl.reportLoop()
+
+ return impl
+}
+
+func (tracer *tracerImpl) Options() Options {
+ return tracer.opts
+}
+
+func (tracer *tracerImpl) StartSpan(
+ operationName string,
+ sso ...ot.StartSpanOption,
+) ot.Span {
+ return newSpan(operationName, tracer, sso)
+}
+
+func (tracer *tracerImpl) Inject(sc ot.SpanContext, format interface{}, carrier interface{}) error {
+ switch format {
+ case ot.TextMap, ot.HTTPHeaders:
+ return theTextMapPropagator.Inject(sc, carrier)
+ case ot.Binary:
+ return theBinaryPropagator.Inject(sc, carrier)
+ }
+ return ot.ErrUnsupportedFormat
+}
+
+func (tracer *tracerImpl) Extract(format interface{}, carrier interface{}) (ot.SpanContext, error) {
+ switch format {
+ case ot.TextMap, ot.HTTPHeaders:
+ return theTextMapPropagator.Extract(carrier)
+ case ot.Binary:
+ return theBinaryPropagator.Extract(carrier)
+ }
+ return nil, ot.ErrUnsupportedFormat
+}
+
+func (tracer *tracerImpl) reconnectClient(now time.Time) {
+ conn, err := tracer.client.ConnectClient()
+ if err != nil {
+ emitEvent(newEventConnectionError(err))
+ } else {
+ tracer.lock.Lock()
+ oldConn := tracer.connection
+ tracer.connection = conn
+ tracer.lock.Unlock()
+
+ oldConn.Close()
+ }
+}
+
+// Close flushes and then terminates the LightStep collector. Close may only be
+// called once; subsequent calls to Close are no-ops.
+func (tracer *tracerImpl) Close(ctx context.Context) {
+ tracer.closeOnce.Do(func() {
+ // notify report loop that we are closing
+ close(tracer.closeReportLoopChannel)
+ select {
+ case <-tracer.reportLoopClosedChannel:
+ tracer.Flush(ctx)
+ case <-ctx.Done():
+ return
+ }
+
+ // now its safe to close the connection
+ tracer.lock.Lock()
+ conn := tracer.connection
+ tracer.connection = nil
+ tracer.lock.Unlock()
+
+ if conn != nil {
+ err := conn.Close()
+ if err != nil {
+ emitEvent(newEventConnectionError(err))
+ }
+ }
+ })
+}
+
+// RecordSpan records a finished Span.
+func (tracer *tracerImpl) RecordSpan(raw RawSpan) {
+ tracer.lock.Lock()
+
+ // Early-out for disabled runtimes
+ if tracer.disabled {
+ tracer.lock.Unlock()
+ return
+ }
+
+ tracer.buffer.addSpan(raw)
+ tracer.lock.Unlock()
+
+ if tracer.opts.Recorder != nil {
+ tracer.opts.Recorder.RecordSpan(raw)
+ }
+}
+
+// Flush sends all buffered data to the collector.
+func (tracer *tracerImpl) Flush(ctx context.Context) {
+ tracer.flushingLock.Lock()
+ defer tracer.flushingLock.Unlock()
+
+ if errorEvent := tracer.preFlush(); errorEvent != nil {
+ emitEvent(errorEvent)
+ return
+ }
+
+ ctx, cancel := context.WithTimeout(ctx, tracer.opts.ReportTimeout)
+ defer cancel()
+
+ req, err := tracer.client.Translate(ctx, &tracer.flushing)
+ if err != nil {
+ errorEvent := newEventFlushError(err, FlushErrorTranslate)
+ emitEvent(errorEvent)
+ // call postflush to prevent the tracer from going into an invalid state.
+ emitEvent(tracer.postFlush(errorEvent))
+ return
+ }
+
+ var reportErrorEvent *eventFlushError
+ resp, err := tracer.client.Report(ctx, req)
+ if err != nil {
+ reportErrorEvent = newEventFlushError(err, FlushErrorTransport)
+ } else if len(resp.GetErrors()) > 0 {
+ reportErrorEvent = newEventFlushError(fmt.Errorf(resp.GetErrors()[0]), FlushErrorReport)
+ }
+
+ if reportErrorEvent != nil {
+ emitEvent(reportErrorEvent)
+ }
+ emitEvent(tracer.postFlush(reportErrorEvent))
+
+ if err == nil && resp.Disable() {
+ tracer.Disable()
+ }
+}
+
+// preFlush handles lock-protected data manipulation before flushing
+func (tracer *tracerImpl) preFlush() *eventFlushError {
+ tracer.lock.Lock()
+ defer tracer.lock.Unlock()
+
+ if tracer.disabled {
+ return newEventFlushError(errFlushFailedTracerClosed, FlushErrorTracerDisabled)
+ }
+
+ if tracer.connection == nil {
+ return newEventFlushError(errFlushFailedTracerClosed, FlushErrorTracerClosed)
+ }
+
+ now := time.Now()
+ tracer.buffer, tracer.flushing = tracer.flushing, tracer.buffer
+ tracer.reportInFlight = true
+ tracer.flushing.setFlushing(now)
+ tracer.buffer.setCurrent(now)
+ tracer.lastReportAttempt = now
+ return nil
+}
+
+// postFlush handles lock-protected data manipulation after flushing
+func (tracer *tracerImpl) postFlush(flushEventError *eventFlushError) *eventStatusReport {
+ tracer.lock.Lock()
+ defer tracer.lock.Unlock()
+
+ tracer.reportInFlight = false
+
+ statusReportEvent := newEventStatusReport(
+ tracer.flushing.reportStart,
+ tracer.flushing.reportEnd,
+ len(tracer.flushing.rawSpans),
+ int(tracer.flushing.droppedSpanCount+tracer.buffer.droppedSpanCount),
+ int(tracer.flushing.logEncoderErrorCount+tracer.buffer.logEncoderErrorCount),
+ )
+
+ if flushEventError == nil {
+ tracer.flushing.clear()
+ return statusReportEvent
+ }
+
+ switch flushEventError.State() {
+ case FlushErrorTranslate:
+ // When there's a translation error, we do not want to retry.
+ tracer.flushing.clear()
+ default:
+ // Restore the records that did not get sent correctly
+ tracer.buffer.mergeFrom(&tracer.flushing)
+ }
+
+ statusReportEvent.SetSentSpans(0)
+
+ return statusReportEvent
+}
+
+func (tracer *tracerImpl) Disable() {
+ tracer.lock.Lock()
+ if tracer.disabled {
+ tracer.lock.Unlock()
+ return
+ }
+ tracer.disabled = true
+ tracer.buffer.clear()
+ tracer.lock.Unlock()
+
+ emitEvent(newEventTracerDisabled())
+}
+
+// Every MinReportingPeriod the reporting loop wakes up and checks to see if
+// either (a) the Runtime's max reporting period is about to expire (see
+// maxReportingPeriod()), (b) the number of buffered log records is
+// approaching kMaxBufferedLogs, or if (c) the number of buffered span records
+// is approaching kMaxBufferedSpans. If any of those conditions are true,
+// pending data is flushed to the remote peer. If not, the reporting loop waits
+// until the next cycle. See Runtime.maybeFlush() for details.
+//
+// This could alternatively be implemented using flush channels and so forth,
+// but that would introduce opportunities for client code to block on the
+// runtime library, and we want to avoid that at all costs (even dropping data,
+// which can certainly happen with high data rates and/or unresponsive remote
+// peers).
+
+func (tracer *tracerImpl) shouldFlushLocked(now time.Time) bool {
+ if now.Add(tracer.opts.MinReportingPeriod).Sub(tracer.lastReportAttempt) > tracer.opts.ReportingPeriod {
+ return true
+ } else if tracer.buffer.isHalfFull() {
+ return true
+ }
+ return false
+}
+
+func (tracer *tracerImpl) reportLoop() {
+ tickerChan := time.Tick(tracer.opts.MinReportingPeriod)
+ for {
+ select {
+ case <-tickerChan:
+ now := time.Now()
+
+ tracer.lock.Lock()
+ disabled := tracer.disabled
+ reconnect := !tracer.reportInFlight && tracer.client.ShouldReconnect()
+ shouldFlush := tracer.shouldFlushLocked(now)
+ tracer.lock.Unlock()
+
+ if disabled {
+ return
+ }
+ if shouldFlush {
+ tracer.Flush(context.Background())
+ }
+ if reconnect {
+ tracer.reconnectClient(now)
+ }
+ case <-tracer.closeReportLoopChannel:
+ close(tracer.reportLoopClosedChannel)
+ return
+ }
+ }
+}
diff --git a/vendor/github.com/lightstep/lightstep-tracer-go/tracer_0_14.go b/vendor/github.com/lightstep/lightstep-tracer-go/tracer_0_14.go
new file mode 100644
index 000000000..e1d7eb7c8
--- /dev/null
+++ b/vendor/github.com/lightstep/lightstep-tracer-go/tracer_0_14.go
@@ -0,0 +1,45 @@
+package lightstep
+
+import (
+ "context"
+
+ opentracing "github.com/opentracing/opentracing-go"
+)
+
+// Tracerv0_14 matches the Tracer interface from v0.14.0
+// DEPRECATED
+type Tracerv0_14 interface {
+ opentracing.Tracer
+
+ // DEPRECATED: error is always nil. Equivalent to Tracer.Close(context.Background())
+ Close() error
+ // DEPRECATED: error is always nil. Equivalent to Tracer.Flush(context.Background())
+ Flush() error
+ // Options gets the Options used in New().
+ Options() Options
+ // Disable prevents the tracer from recording spans or flushing.
+ Disable()
+}
+
+type tracerv0_14 struct {
+ Tracer
+}
+
+// NewTracerv0_14 returns a tracer which conforms to the Tracer interface from v0.14.0,
+// for backwards compatibility.
+// DEPRECATED
+func NewTracerv0_14(opts Options) Tracerv0_14 {
+ return &tracerv0_14{
+ Tracer: NewTracer(opts),
+ }
+}
+
+func (t *tracerv0_14) Close() error {
+ t.Tracer.Close(context.Background())
+ return nil
+}
+
+func (t *tracerv0_14) Flush() error {
+ t.Tracer.Flush(context.Background())
+ return nil
+}
diff --git a/vendor/github.com/lightstep/lightstep-tracer-go/tracer_helpers.go b/vendor/github.com/lightstep/lightstep-tracer-go/tracer_helpers.go
new file mode 100644
index 000000000..a6aacb8a0
--- /dev/null
+++ b/vendor/github.com/lightstep/lightstep-tracer-go/tracer_helpers.go
@@ -0,0 +1,83 @@
+package lightstep
+
+import (
+ "context"
+
+ opentracing "github.com/opentracing/opentracing-go"
+)
+
+// Flush forces a synchronous Flush.
+func Flush(ctx context.Context, tracer opentracing.Tracer) {
+ switch lsTracer := tracer.(type) {
+ case Tracer:
+ lsTracer.Flush(ctx)
+ case *tracerv0_14:
+ Flush(ctx, lsTracer.Tracer)
+ default:
+ emitEvent(newEventUnsupportedTracer(tracer))
+ }
+}
+
+// Close synchronously flushes the tracer, then terminates it.
+func Close(ctx context.Context, tracer opentracing.Tracer) {
+ switch lsTracer := tracer.(type) {
+ case Tracer:
+ lsTracer.Close(ctx)
+ case *tracerv0_14:
+ Close(ctx, lsTracer.Tracer)
+ default:
+ emitEvent(newEventUnsupportedTracer(tracer))
+ }
+}
+
+// GetLightStepAccessToken returns the currently configured AccessToken.
+func GetLightStepAccessToken(tracer opentracing.Tracer) (string, error) {
+ switch lsTracer := tracer.(type) {
+ case Tracer:
+ return lsTracer.Options().AccessToken, nil
+ case *tracerv0_14:
+ return GetLightStepAccessToken(lsTracer.Tracer)
+ default:
+ return "", newEventUnsupportedTracer(tracer)
+ }
+}
+
+// FlushLightStepTracer flushes the tracer
+// DEPRECATED: use Flush instead.
+func FlushLightStepTracer(tracer opentracing.Tracer) error {
+ switch lsTracer := tracer.(type) {
+ case Tracer:
+ lsTracer.Flush(context.Background())
+ return nil
+ case *tracerv0_14:
+ return FlushLightStepTracer(lsTracer.Tracer)
+ default:
+ return newEventUnsupportedTracer(tracer)
+ }
+}
+
+// CloseTracer closes the tracer
+// DEPRECATED: use Close instead.
+func CloseTracer(tracer opentracing.Tracer) error {
+ switch lsTracer := tracer.(type) {
+ case Tracer:
+ lsTracer.Close(context.Background())
+ return nil
+ case *tracerv0_14:
+ return CloseTracer(lsTracer.Tracer)
+ default:
+ return newEventUnsupportedTracer(tracer)
+ }
+}
+
+// GetLightStepReporterID returns the currently configured Reporter ID.
+func GetLightStepReporterID(tracer opentracing.Tracer) (uint64, error) {
+ switch lsTracer := tracer.(type) {
+ case *tracerImpl:
+ return lsTracer.reporterID, nil
+ case *tracerv0_14:
+ return GetLightStepReporterID(lsTracer.Tracer)
+ default:
+ return 0, newEventUnsupportedTracer(tracer)
+ }
+}
diff --git a/vendor/github.com/lightstep/lightstep-tracer-go/util.go b/vendor/github.com/lightstep/lightstep-tracer-go/util.go
new file mode 100644
index 000000000..bc27f9e3a
--- /dev/null
+++ b/vendor/github.com/lightstep/lightstep-tracer-go/util.go
@@ -0,0 +1,32 @@
+package lightstep
+
+import (
+ "runtime"
+ "time"
+
+ "github.com/lightstep/lightstep-tracer-go/lightstep/rand"
+)
+
+var (
+ // create a random pool with size equal to 16 generators or number of CPU Cores which ever is higher to spread
+ // random int call loads across multiple go routines. This number is obtained via local benchmarking
+ // where any number more than 16 reaches a point of diminishing return given the test scenario.
+ randompool = rand.NewPool(time.Now().UnixNano(), uint64(max(16, runtime.NumCPU())))
+)
+
+// max returns the larger value among a and b
+func max(x, y int) int {
+ if x > y {
+ return x
+ }
+ return y
+}
+
+func genSeededGUID() uint64 {
+ return uint64(randompool.Pick().Int63())
+}
+
+func genSeededGUID2() (uint64, uint64) {
+ n1, n2 := randompool.Pick().TwoInt63()
+ return uint64(n1), uint64(n2)
+}
diff --git a/vendor/github.com/lightstep/lightstep-tracer-go/version.go b/vendor/github.com/lightstep/lightstep-tracer-go/version.go
new file mode 100644
index 000000000..1cba4ebe9
--- /dev/null
+++ b/vendor/github.com/lightstep/lightstep-tracer-go/version.go
@@ -0,0 +1,4 @@
+package lightstep
+
+// TracerVersionValue provides the current version of the lightstep-tracer-go release
+const TracerVersionValue = "0.15.6"
diff --git a/vendor/github.com/lightstep/thrift/LICENSE b/vendor/github.com/lightstep/thrift/LICENSE
new file mode 100644
index 000000000..8db837b70
--- /dev/null
+++ b/vendor/github.com/lightstep/thrift/LICENSE
@@ -0,0 +1,261 @@
+
+ Apache License
+ Version 2.0, January 2004
+ http://www.apache.org/licenses/
+
+ TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
+
+ 1. Definitions.
+
+ "License" shall mean the terms and conditions for use, reproduction,
+ and distribution as defined by Sections 1 through 9 of this document.
+
+ "Licensor" shall mean the copyright owner or entity authorized by
+ the copyright owner that is granting the License.
+
+ "Legal Entity" shall mean the union of the acting entity and all
+ other entities that control, are controlled by, or are under common
+ control with that entity. For the purposes of this definition,
+ "control" means (i) the power, direct or indirect, to cause the
+ direction or management of such entity, whether by contract or
+ otherwise, or (ii) ownership of fifty percent (50%) or more of the
+ outstanding shares, or (iii) beneficial ownership of such entity.
+
+ "You" (or "Your") shall mean an individual or Legal Entity
+ exercising permissions granted by this License.
+
+ "Source" form shall mean the preferred form for making modifications,
+ including but not limited to software source code, documentation
+ source, and configuration files.
+
+ "Object" form shall mean any form resulting from mechanical
+ transformation or translation of a Source form, including but
+ not limited to compiled object code, generated documentation,
+ and conversions to other media types.
+
+ "Work" shall mean the work of authorship, whether in Source or
+ Object form, made available under the License, as indicated by a
+ copyright notice that is included in or attached to the work
+ (an example is provided in the Appendix below).
+
+ "Derivative Works" shall mean any work, whether in Source or Object
+ form, that is based on (or derived from) the Work and for which the
+ editorial revisions, annotations, elaborations, or other modifications
+ represent, as a whole, an original work of authorship. For the purposes
+ of this License, Derivative Works shall not include works that remain
+ separable from, or merely link (or bind by name) to the interfaces of,
+ the Work and Derivative Works thereof.
+
+ "Contribution" shall mean any work of authorship, including
+ the original version of the Work and any modifications or additions
+ to that Work or Derivative Works thereof, that is intentionally
+ submitted to Licensor for inclusion in the Work by the copyright owner
+ or by an individual or Legal Entity authorized to submit on behalf of
+ the copyright owner. For the purposes of this definition, "submitted"
+ means any form of electronic, verbal, or written communication sent
+ to the Licensor or its representatives, including but not limited to
+ communication on electronic mailing lists, source code control systems,
+ and issue tracking systems that are managed by, or on behalf of, the
+ Licensor for the purpose of discussing and improving the Work, but
+ excluding communication that is conspicuously marked or otherwise
+ designated in writing by the copyright owner as "Not a Contribution."
+
+ "Contributor" shall mean Licensor and any individual or Legal Entity
+ on behalf of whom a Contribution has been received by Licensor and
+ subsequently incorporated within the Work.
+
+ 2. Grant of Copyright License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ copyright license to reproduce, prepare Derivative Works of,
+ publicly display, publicly perform, sublicense, and distribute the
+ Work and such Derivative Works in Source or Object form.
+
+ 3. Grant of Patent License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ (except as stated in this section) patent license to make, have made,
+ use, offer to sell, sell, import, and otherwise transfer the Work,
+ where such license applies only to those patent claims licensable
+ by such Contributor that are necessarily infringed by their
+ Contribution(s) alone or by combination of their Contribution(s)
+ with the Work to which such Contribution(s) was submitted. If You
+ institute patent litigation against any entity (including a
+ cross-claim or counterclaim in a lawsuit) alleging that the Work
+ or a Contribution incorporated within the Work constitutes direct
+ or contributory patent infringement, then any patent licenses
+ granted to You under this License for that Work shall terminate
+ as of the date such litigation is filed.
+
+ 4. Redistribution. You may reproduce and distribute copies of the
+ Work or Derivative Works thereof in any medium, with or without
+ modifications, and in Source or Object form, provided that You
+ meet the following conditions:
+
+ (a) You must give any other recipients of the Work or
+ Derivative Works a copy of this License; and
+
+ (b) You must cause any modified files to carry prominent notices
+ stating that You changed the files; and
+
+ (c) You must retain, in the Source form of any Derivative Works
+ that You distribute, all copyright, patent, trademark, and
+ attribution notices from the Source form of the Work,
+ excluding those notices that do not pertain to any part of
+ the Derivative Works; and
+
+ (d) If the Work includes a "NOTICE" text file as part of its
+ distribution, then any Derivative Works that You distribute must
+ include a readable copy of the attribution notices contained
+ within such NOTICE file, excluding those notices that do not
+ pertain to any part of the Derivative Works, in at least one
+ of the following places: within a NOTICE text file distributed
+ as part of the Derivative Works; within the Source form or
+ documentation, if provided along with the Derivative Works; or,
+ within a display generated by the Derivative Works, if and
+ wherever such third-party notices normally appear. The contents
+ of the NOTICE file are for informational purposes only and
+ do not modify the License. You may add Your own attribution
+ notices within Derivative Works that You distribute, alongside
+ or as an addendum to the NOTICE text from the Work, provided
+ that such additional attribution notices cannot be construed
+ as modifying the License.
+
+ You may add Your own copyright statement to Your modifications and
+ may provide additional or different license terms and conditions
+ for use, reproduction, or distribution of Your modifications, or
+ for any such Derivative Works as a whole, provided Your use,
+ reproduction, and distribution of the Work otherwise complies with
+ the conditions stated in this License.
+
+ 5. Submission of Contributions. Unless You explicitly state otherwise,
+ any Contribution intentionally submitted for inclusion in the Work
+ by You to the Licensor shall be under the terms and conditions of
+ this License, without any additional terms or conditions.
+ Notwithstanding the above, nothing herein shall supersede or modify
+ the terms of any separate license agreement you may have executed
+ with Licensor regarding such Contributions.
+
+ 6. Trademarks. This License does not grant permission to use the trade
+ names, trademarks, service marks, or product names of the Licensor,
+ except as required for reasonable and customary use in describing the
+ origin of the Work and reproducing the content of the NOTICE file.
+
+ 7. Disclaimer of Warranty. Unless required by applicable law or
+ agreed to in writing, Licensor provides the Work (and each
+ Contributor provides its Contributions) on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
+ implied, including, without limitation, any warranties or conditions
+ of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
+ PARTICULAR PURPOSE. You are solely responsible for determining the
+ appropriateness of using or redistributing the Work and assume any
+ risks associated with Your exercise of permissions under this License.
+
+ 8. Limitation of Liability. In no event and under no legal theory,
+ whether in tort (including negligence), contract, or otherwise,
+ unless required by applicable law (such as deliberate and grossly
+ negligent acts) or agreed to in writing, shall any Contributor be
+ liable to You for damages, including any direct, indirect, special,
+ incidental, or consequential damages of any character arising as a
+ result of this License or out of the use or inability to use the
+ Work (including but not limited to damages for loss of goodwill,
+ work stoppage, computer failure or malfunction, or any and all
+ other commercial damages or losses), even if such Contributor
+ has been advised of the possibility of such damages.
+
+ 9. Accepting Warranty or Additional Liability. While redistributing
+ the Work or Derivative Works thereof, You may choose to offer,
+ and charge a fee for, acceptance of support, warranty, indemnity,
+ or other liability obligations and/or rights consistent with this
+ License. However, in accepting such obligations, You may act only
+ on Your own behalf and on Your sole responsibility, not on behalf
+ of any other Contributor, and only if You agree to indemnify,
+ defend, and hold each Contributor harmless for any liability
+ incurred by, or claims asserted against, such Contributor by reason
+ of your accepting any such warranty or additional liability.
+
+ END OF TERMS AND CONDITIONS
+
+ APPENDIX: How to apply the Apache License to your work.
+
+ To apply the Apache License to your work, attach the following
+ boilerplate notice, with the fields enclosed by brackets "[]"
+ replaced with your own identifying information. (Don't include
+ the brackets!) The text should be enclosed in the appropriate
+ comment syntax for the file format. We also recommend that a
+ file or class name and description of purpose be included on the
+ same "printed page" as the copyright notice for easier
+ identification within third-party archives.
+
+ Copyright [yyyy] [name of copyright owner]
+
+ 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.
+
+--------------------------------------------------
+SOFTWARE DISTRIBUTED WITH THRIFT:
+
+The Apache Thrift software includes a number of subcomponents with
+separate copyright notices and license terms. Your use of the source
+code for the these subcomponents is subject to the terms and
+conditions of the following licenses.
+
+--------------------------------------------------
+Portions of the following files are licensed under the MIT License:
+
+ lib/erl/src/Makefile.am
+
+Please see doc/otp-base-license.txt for the full terms of this license.
+
+--------------------------------------------------
+For the aclocal/ax_boost_base.m4 and contrib/fb303/aclocal/ax_boost_base.m4 components:
+
+# Copyright (c) 2007 Thomas Porschberg <thomas@randspringer.de>
+#
+# Copying and distribution of this file, with or without
+# modification, are permitted in any medium without royalty provided
+# the copyright notice and this notice are preserved.
+
+--------------------------------------------------
+For the compiler/cpp/src/thrift/md5.[ch] components:
+
+/*
+ Copyright (C) 1999, 2000, 2002 Aladdin Enterprises. All rights reserved.
+
+ This software is provided 'as-is', without any express or implied
+ warranty. In no event will the authors be held liable for any damages
+ arising from the use of this software.
+
+ Permission is granted to anyone to use this software for any purpose,
+ including commercial applications, and to alter it and redistribute it
+ freely, subject to the following restrictions:
+
+ 1. The origin of this software must not be misrepresented; you must not
+ claim that you wrote the original software. If you use this software
+ in a product, an acknowledgment in the product documentation would be
+ appreciated but is not required.
+ 2. Altered source versions must be plainly marked as such, and must not be
+ misrepresented as being the original software.
+ 3. This notice may not be removed or altered from any source distribution.
+
+ L. Peter Deutsch
+ ghost@aladdin.com
+
+ */
+
+---------------------------------------------------
+For the lib/rb/setup.rb: Copyright (c) 2000-2005 Minero Aoki,
+lib/ocaml/OCamlMakefile and lib/ocaml/README-OCamlMakefile components:
+ Copyright (C) 1999 - 2007 Markus Mottl
+
+Licensed under the terms of the GNU Lesser General Public License 2.1
+(see doc/lgpl-2.1.txt for the full terms of this license)
diff --git a/vendor/github.com/lightstep/thrift/NOTICE b/vendor/github.com/lightstep/thrift/NOTICE
new file mode 100644
index 000000000..c23995a23
--- /dev/null
+++ b/vendor/github.com/lightstep/thrift/NOTICE
@@ -0,0 +1,5 @@
+Apache Thrift
+Copyright 2006-2010 The Apache Software Foundation.
+
+This product includes software developed at
+The Apache Software Foundation (http://www.apache.org/). \ No newline at end of file
diff --git a/vendor/github.com/lightstep/thrift/lib/go/thrift/application_exception.go b/vendor/github.com/lightstep/thrift/lib/go/thrift/application_exception.go
new file mode 100644
index 000000000..6655cc5a9
--- /dev/null
+++ b/vendor/github.com/lightstep/thrift/lib/go/thrift/application_exception.go
@@ -0,0 +1,142 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+const (
+ UNKNOWN_APPLICATION_EXCEPTION = 0
+ UNKNOWN_METHOD = 1
+ INVALID_MESSAGE_TYPE_EXCEPTION = 2
+ WRONG_METHOD_NAME = 3
+ BAD_SEQUENCE_ID = 4
+ MISSING_RESULT = 5
+ INTERNAL_ERROR = 6
+ PROTOCOL_ERROR = 7
+)
+
+// Application level Thrift exception
+type TApplicationException interface {
+ TException
+ TypeId() int32
+ Read(iprot TProtocol) (TApplicationException, error)
+ Write(oprot TProtocol) error
+}
+
+type tApplicationException struct {
+ message string
+ type_ int32
+}
+
+func (e tApplicationException) Error() string {
+ return e.message
+}
+
+func NewTApplicationException(type_ int32, message string) TApplicationException {
+ return &tApplicationException{message, type_}
+}
+
+func (p *tApplicationException) TypeId() int32 {
+ return p.type_
+}
+
+func (p *tApplicationException) Read(iprot TProtocol) (TApplicationException, error) {
+ _, err := iprot.ReadStructBegin()
+ if err != nil {
+ return nil, err
+ }
+
+ message := ""
+ type_ := int32(UNKNOWN_APPLICATION_EXCEPTION)
+
+ for {
+ _, ttype, id, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return nil, err
+ }
+ if ttype == STOP {
+ break
+ }
+ switch id {
+ case 1:
+ if ttype == STRING {
+ if message, err = iprot.ReadString(); err != nil {
+ return nil, err
+ }
+ } else {
+ if err = SkipDefaultDepth(iprot, ttype); err != nil {
+ return nil, err
+ }
+ }
+ case 2:
+ if ttype == I32 {
+ if type_, err = iprot.ReadI32(); err != nil {
+ return nil, err
+ }
+ } else {
+ if err = SkipDefaultDepth(iprot, ttype); err != nil {
+ return nil, err
+ }
+ }
+ default:
+ if err = SkipDefaultDepth(iprot, ttype); err != nil {
+ return nil, err
+ }
+ }
+ if err = iprot.ReadFieldEnd(); err != nil {
+ return nil, err
+ }
+ }
+ return NewTApplicationException(type_, message), iprot.ReadStructEnd()
+}
+
+func (p *tApplicationException) Write(oprot TProtocol) (err error) {
+ err = oprot.WriteStructBegin("TApplicationException")
+ if len(p.Error()) > 0 {
+ err = oprot.WriteFieldBegin("message", STRING, 1)
+ if err != nil {
+ return
+ }
+ err = oprot.WriteString(p.Error())
+ if err != nil {
+ return
+ }
+ err = oprot.WriteFieldEnd()
+ if err != nil {
+ return
+ }
+ }
+ err = oprot.WriteFieldBegin("type", I32, 2)
+ if err != nil {
+ return
+ }
+ err = oprot.WriteI32(p.type_)
+ if err != nil {
+ return
+ }
+ err = oprot.WriteFieldEnd()
+ if err != nil {
+ return
+ }
+ err = oprot.WriteFieldStop()
+ if err != nil {
+ return
+ }
+ err = oprot.WriteStructEnd()
+ return
+}
diff --git a/vendor/github.com/lightstep/thrift/lib/go/thrift/binary_protocol.go b/vendor/github.com/lightstep/thrift/lib/go/thrift/binary_protocol.go
new file mode 100644
index 000000000..09f94d4c7
--- /dev/null
+++ b/vendor/github.com/lightstep/thrift/lib/go/thrift/binary_protocol.go
@@ -0,0 +1,484 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+import (
+ "encoding/binary"
+ "errors"
+ "fmt"
+ "io"
+ "math"
+)
+
+type TBinaryProtocol struct {
+ trans TRichTransport
+ origTransport TTransport
+ reader io.Reader
+ writer io.Writer
+ strictRead bool
+ strictWrite bool
+ buffer [64]byte
+}
+
+type TBinaryProtocolFactory struct {
+ strictRead bool
+ strictWrite bool
+}
+
+func NewTBinaryProtocolTransport(t TTransport) *TBinaryProtocol {
+ return NewTBinaryProtocol(t, false, true)
+}
+
+func NewTBinaryProtocol(t TTransport, strictRead, strictWrite bool) *TBinaryProtocol {
+ p := &TBinaryProtocol{origTransport: t, strictRead: strictRead, strictWrite: strictWrite}
+ if et, ok := t.(TRichTransport); ok {
+ p.trans = et
+ } else {
+ p.trans = NewTRichTransport(t)
+ }
+ p.reader = p.trans
+ p.writer = p.trans
+ return p
+}
+
+func NewTBinaryProtocolFactoryDefault() *TBinaryProtocolFactory {
+ return NewTBinaryProtocolFactory(false, true)
+}
+
+func NewTBinaryProtocolFactory(strictRead, strictWrite bool) *TBinaryProtocolFactory {
+ return &TBinaryProtocolFactory{strictRead: strictRead, strictWrite: strictWrite}
+}
+
+func (p *TBinaryProtocolFactory) GetProtocol(t TTransport) TProtocol {
+ return NewTBinaryProtocol(t, p.strictRead, p.strictWrite)
+}
+
+/**
+ * Writing Methods
+ */
+
+func (p *TBinaryProtocol) WriteMessageBegin(name string, typeId TMessageType, seqId int32) error {
+ if p.strictWrite {
+ version := uint32(VERSION_1) | uint32(typeId)
+ e := p.WriteI32(int32(version))
+ if e != nil {
+ return e
+ }
+ e = p.WriteString(name)
+ if e != nil {
+ return e
+ }
+ e = p.WriteI32(seqId)
+ return e
+ } else {
+ e := p.WriteString(name)
+ if e != nil {
+ return e
+ }
+ e = p.WriteByte(byte(typeId))
+ if e != nil {
+ return e
+ }
+ e = p.WriteI32(seqId)
+ return e
+ }
+ return nil
+}
+
+func (p *TBinaryProtocol) WriteMessageEnd() error {
+ return nil
+}
+
+func (p *TBinaryProtocol) WriteStructBegin(name string) error {
+ return nil
+}
+
+func (p *TBinaryProtocol) WriteStructEnd() error {
+ return nil
+}
+
+func (p *TBinaryProtocol) WriteFieldBegin(name string, typeId TType, id int16) error {
+ e := p.WriteByte(byte(typeId))
+ if e != nil {
+ return e
+ }
+ e = p.WriteI16(id)
+ return e
+}
+
+func (p *TBinaryProtocol) WriteFieldEnd() error {
+ return nil
+}
+
+func (p *TBinaryProtocol) WriteFieldStop() error {
+ e := p.WriteByte(STOP)
+ return e
+}
+
+func (p *TBinaryProtocol) WriteMapBegin(keyType TType, valueType TType, size int) error {
+ e := p.WriteByte(byte(keyType))
+ if e != nil {
+ return e
+ }
+ e = p.WriteByte(byte(valueType))
+ if e != nil {
+ return e
+ }
+ e = p.WriteI32(int32(size))
+ return e
+}
+
+func (p *TBinaryProtocol) WriteMapEnd() error {
+ return nil
+}
+
+func (p *TBinaryProtocol) WriteListBegin(elemType TType, size int) error {
+ e := p.WriteByte(byte(elemType))
+ if e != nil {
+ return e
+ }
+ e = p.WriteI32(int32(size))
+ return e
+}
+
+func (p *TBinaryProtocol) WriteListEnd() error {
+ return nil
+}
+
+func (p *TBinaryProtocol) WriteSetBegin(elemType TType, size int) error {
+ e := p.WriteByte(byte(elemType))
+ if e != nil {
+ return e
+ }
+ e = p.WriteI32(int32(size))
+ return e
+}
+
+func (p *TBinaryProtocol) WriteSetEnd() error {
+ return nil
+}
+
+func (p *TBinaryProtocol) WriteBool(value bool) error {
+ if value {
+ return p.WriteByte(1)
+ }
+ return p.WriteByte(0)
+}
+
+func (p *TBinaryProtocol) WriteByte(value byte) error {
+ e := p.trans.WriteByte(value)
+ return NewTProtocolException(e)
+}
+
+func (p *TBinaryProtocol) WriteI16(value int16) error {
+ v := p.buffer[0:2]
+ binary.BigEndian.PutUint16(v, uint16(value))
+ _, e := p.writer.Write(v)
+ return NewTProtocolException(e)
+}
+
+func (p *TBinaryProtocol) WriteI32(value int32) error {
+ v := p.buffer[0:4]
+ binary.BigEndian.PutUint32(v, uint32(value))
+ _, e := p.writer.Write(v)
+ return NewTProtocolException(e)
+}
+
+func (p *TBinaryProtocol) WriteI64(value int64) error {
+ v := p.buffer[0:8]
+ binary.BigEndian.PutUint64(v, uint64(value))
+ _, err := p.writer.Write(v)
+ return NewTProtocolException(err)
+}
+
+func (p *TBinaryProtocol) WriteDouble(value float64) error {
+ return p.WriteI64(int64(math.Float64bits(value)))
+}
+
+func (p *TBinaryProtocol) WriteString(value string) error {
+ e := p.WriteI32(int32(len(value)))
+ if e != nil {
+ return e
+ }
+ _, err := p.trans.WriteString(value)
+ return NewTProtocolException(err)
+}
+
+func (p *TBinaryProtocol) WriteBinary(value []byte) error {
+ e := p.WriteI32(int32(len(value)))
+ if e != nil {
+ return e
+ }
+ _, err := p.writer.Write(value)
+ return NewTProtocolException(err)
+}
+
+/**
+ * Reading methods
+ */
+
+func (p *TBinaryProtocol) ReadMessageBegin() (name string, typeId TMessageType, seqId int32, err error) {
+ size, e := p.ReadI32()
+ if e != nil {
+ return "", typeId, 0, NewTProtocolException(e)
+ }
+ if size < 0 {
+ typeId = TMessageType(size & 0x0ff)
+ version := int64(int64(size) & VERSION_MASK)
+ if version != VERSION_1 {
+ return name, typeId, seqId, NewTProtocolExceptionWithType(BAD_VERSION, fmt.Errorf("Bad version in ReadMessageBegin"))
+ }
+ name, e = p.ReadString()
+ if e != nil {
+ return name, typeId, seqId, NewTProtocolException(e)
+ }
+ seqId, e = p.ReadI32()
+ if e != nil {
+ return name, typeId, seqId, NewTProtocolException(e)
+ }
+ return name, typeId, seqId, nil
+ }
+ if p.strictRead {
+ return name, typeId, seqId, NewTProtocolExceptionWithType(BAD_VERSION, fmt.Errorf("Missing version in ReadMessageBegin"))
+ }
+ name, e2 := p.readStringBody(int(size))
+ if e2 != nil {
+ return name, typeId, seqId, e2
+ }
+ b, e3 := p.ReadByte()
+ if e3 != nil {
+ return name, typeId, seqId, e3
+ }
+ typeId = TMessageType(b)
+ seqId, e4 := p.ReadI32()
+ if e4 != nil {
+ return name, typeId, seqId, e4
+ }
+ return name, typeId, seqId, nil
+}
+
+func (p *TBinaryProtocol) ReadMessageEnd() error {
+ return nil
+}
+
+func (p *TBinaryProtocol) ReadStructBegin() (name string, err error) {
+ return
+}
+
+func (p *TBinaryProtocol) ReadStructEnd() error {
+ return nil
+}
+
+func (p *TBinaryProtocol) ReadFieldBegin() (name string, typeId TType, seqId int16, err error) {
+ t, err := p.ReadByte()
+ typeId = TType(t)
+ if err != nil {
+ return name, typeId, seqId, err
+ }
+ if t != STOP {
+ seqId, err = p.ReadI16()
+ }
+ return name, typeId, seqId, err
+}
+
+func (p *TBinaryProtocol) ReadFieldEnd() error {
+ return nil
+}
+
+var invalidDataLength = NewTProtocolExceptionWithType(INVALID_DATA, errors.New("Invalid data length"))
+
+func (p *TBinaryProtocol) ReadMapBegin() (kType, vType TType, size int, err error) {
+ k, e := p.ReadByte()
+ if e != nil {
+ err = NewTProtocolException(e)
+ return
+ }
+ kType = TType(k)
+ v, e := p.ReadByte()
+ if e != nil {
+ err = NewTProtocolException(e)
+ return
+ }
+ vType = TType(v)
+ size32, e := p.ReadI32()
+ if e != nil {
+ err = NewTProtocolException(e)
+ return
+ }
+ if size32 < 0 {
+ err = invalidDataLength
+ return
+ }
+ size = int(size32)
+ return kType, vType, size, nil
+}
+
+func (p *TBinaryProtocol) ReadMapEnd() error {
+ return nil
+}
+
+func (p *TBinaryProtocol) ReadListBegin() (elemType TType, size int, err error) {
+ b, e := p.ReadByte()
+ if e != nil {
+ err = NewTProtocolException(e)
+ return
+ }
+ elemType = TType(b)
+ size32, e := p.ReadI32()
+ if e != nil {
+ err = NewTProtocolException(e)
+ return
+ }
+ if size32 < 0 {
+ err = invalidDataLength
+ return
+ }
+ size = int(size32)
+
+ return
+}
+
+func (p *TBinaryProtocol) ReadListEnd() error {
+ return nil
+}
+
+func (p *TBinaryProtocol) ReadSetBegin() (elemType TType, size int, err error) {
+ b, e := p.ReadByte()
+ if e != nil {
+ err = NewTProtocolException(e)
+ return
+ }
+ elemType = TType(b)
+ size32, e := p.ReadI32()
+ if e != nil {
+ err = NewTProtocolException(e)
+ return
+ }
+ if size32 < 0 {
+ err = invalidDataLength
+ return
+ }
+ size = int(size32)
+ return elemType, size, nil
+}
+
+func (p *TBinaryProtocol) ReadSetEnd() error {
+ return nil
+}
+
+func (p *TBinaryProtocol) ReadBool() (bool, error) {
+ b, e := p.ReadByte()
+ v := true
+ if b != 1 {
+ v = false
+ }
+ return v, e
+}
+
+func (p *TBinaryProtocol) ReadByte() (value byte, err error) {
+ return p.trans.ReadByte()
+}
+
+func (p *TBinaryProtocol) ReadI16() (value int16, err error) {
+ buf := p.buffer[0:2]
+ err = p.readAll(buf)
+ value = int16(binary.BigEndian.Uint16(buf))
+ return value, err
+}
+
+func (p *TBinaryProtocol) ReadI32() (value int32, err error) {
+ buf := p.buffer[0:4]
+ err = p.readAll(buf)
+ value = int32(binary.BigEndian.Uint32(buf))
+ return value, err
+}
+
+func (p *TBinaryProtocol) ReadI64() (value int64, err error) {
+ buf := p.buffer[0:8]
+ err = p.readAll(buf)
+ value = int64(binary.BigEndian.Uint64(buf))
+ return value, err
+}
+
+func (p *TBinaryProtocol) ReadDouble() (value float64, err error) {
+ buf := p.buffer[0:8]
+ err = p.readAll(buf)
+ value = math.Float64frombits(binary.BigEndian.Uint64(buf))
+ return value, err
+}
+
+func (p *TBinaryProtocol) ReadString() (value string, err error) {
+ size, e := p.ReadI32()
+ if e != nil {
+ return "", e
+ }
+ if size < 0 {
+ err = invalidDataLength
+ return
+ }
+
+ return p.readStringBody(int(size))
+}
+
+func (p *TBinaryProtocol) ReadBinary() ([]byte, error) {
+ size, e := p.ReadI32()
+ if e != nil {
+ return nil, e
+ }
+ if size < 0 {
+ return nil, invalidDataLength
+ }
+
+ isize := int(size)
+ buf := make([]byte, isize)
+ _, err := io.ReadFull(p.trans, buf)
+ return buf, NewTProtocolException(err)
+}
+
+func (p *TBinaryProtocol) Flush() (err error) {
+ return NewTProtocolException(p.trans.Flush())
+}
+
+func (p *TBinaryProtocol) Skip(fieldType TType) (err error) {
+ return SkipDefaultDepth(p, fieldType)
+}
+
+func (p *TBinaryProtocol) Transport() TTransport {
+ return p.origTransport
+}
+
+func (p *TBinaryProtocol) readAll(buf []byte) error {
+ _, err := io.ReadFull(p.reader, buf)
+ return NewTProtocolException(err)
+}
+
+func (p *TBinaryProtocol) readStringBody(size int) (value string, err error) {
+ if size < 0 {
+ return "", nil
+ }
+ var buf []byte
+ if size <= len(p.buffer) {
+ buf = p.buffer[0:size]
+ } else {
+ buf = make([]byte, size)
+ }
+ _, e := io.ReadFull(p.trans, buf)
+ return string(buf), NewTProtocolException(e)
+}
diff --git a/vendor/github.com/lightstep/thrift/lib/go/thrift/buffered_transport.go b/vendor/github.com/lightstep/thrift/lib/go/thrift/buffered_transport.go
new file mode 100644
index 000000000..d258b7000
--- /dev/null
+++ b/vendor/github.com/lightstep/thrift/lib/go/thrift/buffered_transport.go
@@ -0,0 +1,70 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+import (
+ "bufio"
+)
+
+type TBufferedTransportFactory struct {
+ size int
+}
+
+type TBufferedTransport struct {
+ bufio.ReadWriter
+ tp TTransport
+}
+
+func (p *TBufferedTransportFactory) GetTransport(trans TTransport) TTransport {
+ return NewTBufferedTransport(trans, p.size)
+}
+
+func NewTBufferedTransportFactory(bufferSize int) *TBufferedTransportFactory {
+ return &TBufferedTransportFactory{size: bufferSize}
+}
+
+func NewTBufferedTransport(trans TTransport, bufferSize int) *TBufferedTransport {
+ return &TBufferedTransport{
+ ReadWriter: bufio.ReadWriter{
+ Reader: bufio.NewReaderSize(trans, bufferSize),
+ Writer: bufio.NewWriterSize(trans, bufferSize),
+ },
+ tp: trans,
+ }
+}
+
+func (p *TBufferedTransport) IsOpen() bool {
+ return p.tp.IsOpen()
+}
+
+func (p *TBufferedTransport) Open() (err error) {
+ return p.tp.Open()
+}
+
+func (p *TBufferedTransport) Close() (err error) {
+ return p.tp.Close()
+}
+
+func (p *TBufferedTransport) Flush() error {
+ if err := p.ReadWriter.Flush(); err != nil {
+ return err
+ }
+ return p.tp.Flush()
+}
diff --git a/vendor/github.com/lightstep/thrift/lib/go/thrift/compact_protocol.go b/vendor/github.com/lightstep/thrift/lib/go/thrift/compact_protocol.go
new file mode 100644
index 000000000..0857a7a42
--- /dev/null
+++ b/vendor/github.com/lightstep/thrift/lib/go/thrift/compact_protocol.go
@@ -0,0 +1,797 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+import (
+ "encoding/binary"
+ "fmt"
+ "io"
+ "math"
+)
+
+const (
+ COMPACT_PROTOCOL_ID = 0x082
+ COMPACT_VERSION = 1
+ COMPACT_VERSION_MASK = 0x1f
+ COMPACT_TYPE_MASK = 0x0E0
+ COMPACT_TYPE_BITS = 0x07
+ COMPACT_TYPE_SHIFT_AMOUNT = 5
+)
+
+type tCompactType byte
+
+const (
+ COMPACT_BOOLEAN_TRUE = 0x01
+ COMPACT_BOOLEAN_FALSE = 0x02
+ COMPACT_BYTE = 0x03
+ COMPACT_I16 = 0x04
+ COMPACT_I32 = 0x05
+ COMPACT_I64 = 0x06
+ COMPACT_DOUBLE = 0x07
+ COMPACT_BINARY = 0x08
+ COMPACT_LIST = 0x09
+ COMPACT_SET = 0x0A
+ COMPACT_MAP = 0x0B
+ COMPACT_STRUCT = 0x0C
+)
+
+var (
+ ttypeToCompactType map[TType]tCompactType
+)
+
+func init() {
+ ttypeToCompactType = map[TType]tCompactType{
+ STOP: STOP,
+ BOOL: COMPACT_BOOLEAN_TRUE,
+ BYTE: COMPACT_BYTE,
+ I16: COMPACT_I16,
+ I32: COMPACT_I32,
+ I64: COMPACT_I64,
+ DOUBLE: COMPACT_DOUBLE,
+ STRING: COMPACT_BINARY,
+ LIST: COMPACT_LIST,
+ SET: COMPACT_SET,
+ MAP: COMPACT_MAP,
+ STRUCT: COMPACT_STRUCT,
+ }
+}
+
+type TCompactProtocolFactory struct{}
+
+func NewTCompactProtocolFactory() *TCompactProtocolFactory {
+ return &TCompactProtocolFactory{}
+}
+
+func (p *TCompactProtocolFactory) GetProtocol(trans TTransport) TProtocol {
+ return NewTCompactProtocol(trans)
+}
+
+type TCompactProtocol struct {
+ trans TRichTransport
+ origTransport TTransport
+
+ // Used to keep track of the last field for the current and previous structs,
+ // so we can do the delta stuff.
+ lastField []int
+ lastFieldId int
+
+ // If we encounter a boolean field begin, save the TField here so it can
+ // have the value incorporated.
+ booleanFieldName string
+ booleanFieldId int16
+ booleanFieldPending bool
+
+ // If we read a field header, and it's a boolean field, save the boolean
+ // value here so that readBool can use it.
+ boolValue bool
+ boolValueIsNotNull bool
+ buffer [64]byte
+}
+
+// Create a TCompactProtocol given a TTransport
+func NewTCompactProtocol(trans TTransport) *TCompactProtocol {
+ p := &TCompactProtocol{origTransport: trans, lastField: []int{}}
+ if et, ok := trans.(TRichTransport); ok {
+ p.trans = et
+ } else {
+ p.trans = NewTRichTransport(trans)
+ }
+
+ return p
+
+}
+
+//
+// Public Writing methods.
+//
+
+// Write a message header to the wire. Compact Protocol messages contain the
+// protocol version so we can migrate forwards in the future if need be.
+func (p *TCompactProtocol) WriteMessageBegin(name string, typeId TMessageType, seqid int32) error {
+ err := p.writeByteDirect(COMPACT_PROTOCOL_ID)
+ if err != nil {
+ return NewTProtocolException(err)
+ }
+ err = p.writeByteDirect((COMPACT_VERSION & COMPACT_VERSION_MASK) | ((byte(typeId) << COMPACT_TYPE_SHIFT_AMOUNT) & COMPACT_TYPE_MASK))
+ if err != nil {
+ return NewTProtocolException(err)
+ }
+ _, err = p.writeVarint32(seqid)
+ if err != nil {
+ return NewTProtocolException(err)
+ }
+ e := p.WriteString(name)
+ return e
+
+}
+
+func (p *TCompactProtocol) WriteMessageEnd() error { return nil }
+
+// Write a struct begin. This doesn't actually put anything on the wire. We
+// use it as an opportunity to put special placeholder markers on the field
+// stack so we can get the field id deltas correct.
+func (p *TCompactProtocol) WriteStructBegin(name string) error {
+ p.lastField = append(p.lastField, p.lastFieldId)
+ p.lastFieldId = 0
+ return nil
+}
+
+// Write a struct end. This doesn't actually put anything on the wire. We use
+// this as an opportunity to pop the last field from the current struct off
+// of the field stack.
+func (p *TCompactProtocol) WriteStructEnd() error {
+ p.lastFieldId = p.lastField[len(p.lastField)-1]
+ p.lastField = p.lastField[:len(p.lastField)-1]
+ return nil
+}
+
+func (p *TCompactProtocol) WriteFieldBegin(name string, typeId TType, id int16) error {
+ if typeId == BOOL {
+ // we want to possibly include the value, so we'll wait.
+ p.booleanFieldName, p.booleanFieldId, p.booleanFieldPending = name, id, true
+ return nil
+ }
+ _, err := p.writeFieldBeginInternal(name, typeId, id, 0xFF)
+ return NewTProtocolException(err)
+}
+
+// The workhorse of writeFieldBegin. It has the option of doing a
+// 'type override' of the type header. This is used specifically in the
+// boolean field case.
+func (p *TCompactProtocol) writeFieldBeginInternal(name string, typeId TType, id int16, typeOverride byte) (int, error) {
+ // short lastField = lastField_.pop();
+
+ // if there's a type override, use that.
+ var typeToWrite byte
+ if typeOverride == 0xFF {
+ typeToWrite = byte(p.getCompactType(typeId))
+ } else {
+ typeToWrite = typeOverride
+ }
+ // check if we can use delta encoding for the field id
+ fieldId := int(id)
+ written := 0
+ if fieldId > p.lastFieldId && fieldId-p.lastFieldId <= 15 {
+ // write them together
+ err := p.writeByteDirect(byte((fieldId-p.lastFieldId)<<4) | typeToWrite)
+ if err != nil {
+ return 0, err
+ }
+ } else {
+ // write them separate
+ err := p.writeByteDirect(typeToWrite)
+ if err != nil {
+ return 0, err
+ }
+ err = p.WriteI16(id)
+ written = 1 + 2
+ if err != nil {
+ return 0, err
+ }
+ }
+
+ p.lastFieldId = fieldId
+ // p.lastField.Push(field.id);
+ return written, nil
+}
+
+func (p *TCompactProtocol) WriteFieldEnd() error { return nil }
+
+func (p *TCompactProtocol) WriteFieldStop() error {
+ err := p.writeByteDirect(STOP)
+ return NewTProtocolException(err)
+}
+
+func (p *TCompactProtocol) WriteMapBegin(keyType TType, valueType TType, size int) error {
+ if size == 0 {
+ err := p.writeByteDirect(0)
+ return NewTProtocolException(err)
+ }
+ _, err := p.writeVarint32(int32(size))
+ if err != nil {
+ return NewTProtocolException(err)
+ }
+ err = p.writeByteDirect(byte(p.getCompactType(keyType))<<4 | byte(p.getCompactType(valueType)))
+ return NewTProtocolException(err)
+}
+
+func (p *TCompactProtocol) WriteMapEnd() error { return nil }
+
+// Write a list header.
+func (p *TCompactProtocol) WriteListBegin(elemType TType, size int) error {
+ _, err := p.writeCollectionBegin(elemType, size)
+ return NewTProtocolException(err)
+}
+
+func (p *TCompactProtocol) WriteListEnd() error { return nil }
+
+// Write a set header.
+func (p *TCompactProtocol) WriteSetBegin(elemType TType, size int) error {
+ _, err := p.writeCollectionBegin(elemType, size)
+ return NewTProtocolException(err)
+}
+
+func (p *TCompactProtocol) WriteSetEnd() error { return nil }
+
+func (p *TCompactProtocol) WriteBool(value bool) error {
+ v := byte(COMPACT_BOOLEAN_FALSE)
+ if value {
+ v = byte(COMPACT_BOOLEAN_TRUE)
+ }
+ if p.booleanFieldPending {
+ // we haven't written the field header yet
+ _, err := p.writeFieldBeginInternal(p.booleanFieldName, BOOL, p.booleanFieldId, v)
+ p.booleanFieldPending = false
+ return NewTProtocolException(err)
+ }
+ // we're not part of a field, so just write the value.
+ err := p.writeByteDirect(v)
+ return NewTProtocolException(err)
+}
+
+// Write a byte. Nothing to see here!
+func (p *TCompactProtocol) WriteByte(value byte) error {
+ err := p.writeByteDirect(value)
+ return NewTProtocolException(err)
+}
+
+// Write an I16 as a zigzag varint.
+func (p *TCompactProtocol) WriteI16(value int16) error {
+ _, err := p.writeVarint32(p.int32ToZigzag(int32(value)))
+ return NewTProtocolException(err)
+}
+
+// Write an i32 as a zigzag varint.
+func (p *TCompactProtocol) WriteI32(value int32) error {
+ _, err := p.writeVarint32(p.int32ToZigzag(value))
+ return NewTProtocolException(err)
+}
+
+// Write an i64 as a zigzag varint.
+func (p *TCompactProtocol) WriteI64(value int64) error {
+ _, err := p.writeVarint64(p.int64ToZigzag(value))
+ return NewTProtocolException(err)
+}
+
+// Write a double to the wire as 8 bytes.
+func (p *TCompactProtocol) WriteDouble(value float64) error {
+ buf := p.buffer[0:8]
+ binary.LittleEndian.PutUint64(buf, math.Float64bits(value))
+ _, err := p.trans.Write(buf)
+ return NewTProtocolException(err)
+}
+
+// Write a string to the wire with a varint size preceeding.
+func (p *TCompactProtocol) WriteString(value string) error {
+ _, e := p.writeVarint32(int32(len(value)))
+ if e != nil {
+ return NewTProtocolException(e)
+ }
+ if len(value) > 0 {
+ }
+ _, e = p.trans.WriteString(value)
+ return e
+}
+
+// Write a byte array, using a varint for the size.
+func (p *TCompactProtocol) WriteBinary(bin []byte) error {
+ _, e := p.writeVarint32(int32(len(bin)))
+ if e != nil {
+ return NewTProtocolException(e)
+ }
+ if len(bin) > 0 {
+ _, e = p.trans.Write(bin)
+ return NewTProtocolException(e)
+ }
+ return nil
+}
+
+//
+// Reading methods.
+//
+
+// Read a message header.
+func (p *TCompactProtocol) ReadMessageBegin() (name string, typeId TMessageType, seqId int32, err error) {
+ protocolId, err := p.ReadByte()
+ if protocolId != COMPACT_PROTOCOL_ID {
+ e := fmt.Errorf("Expected protocol id %02x but got %02x", COMPACT_PROTOCOL_ID, protocolId)
+ return "", typeId, seqId, NewTProtocolExceptionWithType(BAD_VERSION, e)
+ }
+ versionAndType, err := p.ReadByte()
+ version := versionAndType & COMPACT_VERSION_MASK
+ typeId = TMessageType((versionAndType >> COMPACT_TYPE_SHIFT_AMOUNT) & COMPACT_TYPE_BITS)
+ if err != nil {
+ return
+ }
+ if version != COMPACT_VERSION {
+ e := fmt.Errorf("Expected version %02x but got %02x", COMPACT_VERSION, version)
+ err = NewTProtocolExceptionWithType(BAD_VERSION, e)
+ return
+ }
+ seqId, e := p.readVarint32()
+ if e != nil {
+ err = NewTProtocolException(e)
+ return
+ }
+ name, err = p.ReadString()
+ return
+}
+
+func (p *TCompactProtocol) ReadMessageEnd() error { return nil }
+
+// Read a struct begin. There's nothing on the wire for this, but it is our
+// opportunity to push a new struct begin marker onto the field stack.
+func (p *TCompactProtocol) ReadStructBegin() (name string, err error) {
+ p.lastField = append(p.lastField, p.lastFieldId)
+ p.lastFieldId = 0
+ return
+}
+
+// Doesn't actually consume any wire data, just removes the last field for
+// this struct from the field stack.
+func (p *TCompactProtocol) ReadStructEnd() error {
+ // consume the last field we read off the wire.
+ p.lastFieldId = p.lastField[len(p.lastField)-1]
+ p.lastField = p.lastField[:len(p.lastField)-1]
+ return nil
+}
+
+// Read a field header off the wire.
+func (p *TCompactProtocol) ReadFieldBegin() (name string, typeId TType, id int16, err error) {
+ t, err := p.ReadByte()
+ if err != nil {
+ return
+ }
+
+ // if it's a stop, then we can return immediately, as the struct is over.
+ if (t & 0x0f) == STOP {
+ return "", STOP, 0, nil
+ }
+
+ // mask off the 4 MSB of the type header. it could contain a field id delta.
+ modifier := int16((t & 0xf0) >> 4)
+ if modifier == 0 {
+ // not a delta. look ahead for the zigzag varint field id.
+ id, err = p.ReadI16()
+ if err != nil {
+ return
+ }
+ } else {
+ // has a delta. add the delta to the last read field id.
+ id = int16(p.lastFieldId) + modifier
+ }
+ typeId, e := p.getTType(tCompactType(t & 0x0f))
+ if e != nil {
+ err = NewTProtocolException(e)
+ return
+ }
+
+ // if this happens to be a boolean field, the value is encoded in the type
+ if p.isBoolType(t) {
+ // save the boolean value in a special instance variable.
+ p.boolValue = (byte(t)&0x0f == COMPACT_BOOLEAN_TRUE)
+ p.boolValueIsNotNull = true
+ }
+
+ // push the new field onto the field stack so we can keep the deltas going.
+ p.lastFieldId = int(id)
+ return
+}
+
+func (p *TCompactProtocol) ReadFieldEnd() error { return nil }
+
+// Read a map header off the wire. If the size is zero, skip reading the key
+// and value type. This means that 0-length maps will yield TMaps without the
+// "correct" types.
+func (p *TCompactProtocol) ReadMapBegin() (keyType TType, valueType TType, size int, err error) {
+ size32, e := p.readVarint32()
+ if e != nil {
+ err = NewTProtocolException(e)
+ return
+ }
+ if size32 < 0 {
+ err = invalidDataLength
+ return
+ }
+ size = int(size32)
+
+ keyAndValueType := byte(STOP)
+ if size != 0 {
+ keyAndValueType, err = p.ReadByte()
+ if err != nil {
+ return
+ }
+ }
+ keyType, _ = p.getTType(tCompactType(keyAndValueType >> 4))
+ valueType, _ = p.getTType(tCompactType(keyAndValueType & 0xf))
+ return
+}
+
+func (p *TCompactProtocol) ReadMapEnd() error { return nil }
+
+// Read a list header off the wire. If the list size is 0-14, the size will
+// be packed into the element type header. If it's a longer list, the 4 MSB
+// of the element type header will be 0xF, and a varint will follow with the
+// true size.
+func (p *TCompactProtocol) ReadListBegin() (elemType TType, size int, err error) {
+ size_and_type, err := p.ReadByte()
+ if err != nil {
+ return
+ }
+ size = int((size_and_type >> 4) & 0x0f)
+ if size == 15 {
+ size2, e := p.readVarint32()
+ if e != nil {
+ err = NewTProtocolException(e)
+ return
+ }
+ if size2 < 0 {
+ err = invalidDataLength
+ return
+ }
+ size = int(size2)
+ }
+ elemType, e := p.getTType(tCompactType(size_and_type))
+ if e != nil {
+ err = NewTProtocolException(e)
+ return
+ }
+ return
+}
+
+func (p *TCompactProtocol) ReadListEnd() error { return nil }
+
+// Read a set header off the wire. If the set size is 0-14, the size will
+// be packed into the element type header. If it's a longer set, the 4 MSB
+// of the element type header will be 0xF, and a varint will follow with the
+// true size.
+func (p *TCompactProtocol) ReadSetBegin() (elemType TType, size int, err error) {
+ return p.ReadListBegin()
+}
+
+func (p *TCompactProtocol) ReadSetEnd() error { return nil }
+
+// Read a boolean off the wire. If this is a boolean field, the value should
+// already have been read during readFieldBegin, so we'll just consume the
+// pre-stored value. Otherwise, read a byte.
+func (p *TCompactProtocol) ReadBool() (value bool, err error) {
+ if p.boolValueIsNotNull {
+ p.boolValueIsNotNull = false
+ return p.boolValue, nil
+ }
+ v, err := p.ReadByte()
+ return v == COMPACT_BOOLEAN_TRUE, err
+}
+
+// Read a single byte off the wire. Nothing interesting here.
+func (p *TCompactProtocol) ReadByte() (value byte, err error) {
+ value, err = p.trans.ReadByte()
+ if err != nil {
+ return 0, NewTProtocolException(err)
+ }
+ return
+}
+
+// Read an i16 from the wire as a zigzag varint.
+func (p *TCompactProtocol) ReadI16() (value int16, err error) {
+ v, err := p.ReadI32()
+ return int16(v), err
+}
+
+// Read an i32 from the wire as a zigzag varint.
+func (p *TCompactProtocol) ReadI32() (value int32, err error) {
+ v, e := p.readVarint32()
+ if e != nil {
+ return 0, NewTProtocolException(e)
+ }
+ value = p.zigzagToInt32(v)
+ return value, nil
+}
+
+// Read an i64 from the wire as a zigzag varint.
+func (p *TCompactProtocol) ReadI64() (value int64, err error) {
+ v, e := p.readVarint64()
+ if e != nil {
+ return 0, NewTProtocolException(e)
+ }
+ value = p.zigzagToInt64(v)
+ return value, nil
+}
+
+// No magic here - just read a double off the wire.
+func (p *TCompactProtocol) ReadDouble() (value float64, err error) {
+ longBits := p.buffer[0:8]
+ _, e := io.ReadFull(p.trans, longBits)
+ if e != nil {
+ return 0.0, NewTProtocolException(e)
+ }
+ return math.Float64frombits(p.bytesToUint64(longBits)), nil
+}
+
+// Reads a []byte (via readBinary), and then UTF-8 decodes it.
+func (p *TCompactProtocol) ReadString() (value string, err error) {
+ length, e := p.readVarint32()
+ if e != nil {
+ return "", NewTProtocolException(e)
+ }
+ if length < 0 {
+ return "", invalidDataLength
+ }
+
+ if length == 0 {
+ return "", nil
+ }
+ var buf []byte
+ if length <= int32(len(p.buffer)) {
+ buf = p.buffer[0:length]
+ } else {
+ buf = make([]byte, length)
+ }
+ _, e = io.ReadFull(p.trans, buf)
+ return string(buf), NewTProtocolException(e)
+}
+
+// Read a []byte from the wire.
+func (p *TCompactProtocol) ReadBinary() (value []byte, err error) {
+ length, e := p.readVarint32()
+ if e != nil {
+ return nil, NewTProtocolException(e)
+ }
+ if length == 0 {
+ return []byte{}, nil
+ }
+ if length < 0 {
+ return nil, invalidDataLength
+ }
+
+ buf := make([]byte, length)
+ _, e = io.ReadFull(p.trans, buf)
+ return buf, NewTProtocolException(e)
+}
+
+func (p *TCompactProtocol) Flush() (err error) {
+ return NewTProtocolException(p.trans.Flush())
+}
+
+func (p *TCompactProtocol) Skip(fieldType TType) (err error) {
+ return SkipDefaultDepth(p, fieldType)
+}
+
+func (p *TCompactProtocol) Transport() TTransport {
+ return p.origTransport
+}
+
+//
+// Internal writing methods
+//
+
+// Abstract method for writing the start of lists and sets. List and sets on
+// the wire differ only by the type indicator.
+func (p *TCompactProtocol) writeCollectionBegin(elemType TType, size int) (int, error) {
+ if size <= 14 {
+ return 1, p.writeByteDirect(byte(int32(size<<4) | int32(p.getCompactType(elemType))))
+ }
+ err := p.writeByteDirect(0xf0 | byte(p.getCompactType(elemType)))
+ if err != nil {
+ return 0, err
+ }
+ m, err := p.writeVarint32(int32(size))
+ return 1 + m, err
+}
+
+// Write an i32 as a varint. Results in 1-5 bytes on the wire.
+// TODO(pomack): make a permanent buffer like writeVarint64?
+func (p *TCompactProtocol) writeVarint32(n int32) (int, error) {
+ i32buf := p.buffer[0:5]
+ idx := 0
+ for {
+ if (n & ^0x7F) == 0 {
+ i32buf[idx] = byte(n)
+ idx++
+ // p.writeByteDirect(byte(n));
+ break
+ // return;
+ } else {
+ i32buf[idx] = byte((n & 0x7F) | 0x80)
+ idx++
+ // p.writeByteDirect(byte(((n & 0x7F) | 0x80)));
+ u := uint32(n)
+ n = int32(u >> 7)
+ }
+ }
+ return p.trans.Write(i32buf[0:idx])
+}
+
+// Write an i64 as a varint. Results in 1-10 bytes on the wire.
+func (p *TCompactProtocol) writeVarint64(n int64) (int, error) {
+ varint64out := p.buffer[0:10]
+ idx := 0
+ for {
+ if (n & ^0x7F) == 0 {
+ varint64out[idx] = byte(n)
+ idx++
+ break
+ } else {
+ varint64out[idx] = byte((n & 0x7F) | 0x80)
+ idx++
+ u := uint64(n)
+ n = int64(u >> 7)
+ }
+ }
+ return p.trans.Write(varint64out[0:idx])
+}
+
+// Convert l into a zigzag long. This allows negative numbers to be
+// represented compactly as a varint.
+func (p *TCompactProtocol) int64ToZigzag(l int64) int64 {
+ return (l << 1) ^ (l >> 63)
+}
+
+// Convert l into a zigzag long. This allows negative numbers to be
+// represented compactly as a varint.
+func (p *TCompactProtocol) int32ToZigzag(n int32) int32 {
+ return (n << 1) ^ (n >> 31)
+}
+
+func (p *TCompactProtocol) fixedUint64ToBytes(n uint64, buf []byte) {
+ binary.LittleEndian.PutUint64(buf, n)
+}
+
+func (p *TCompactProtocol) fixedInt64ToBytes(n int64, buf []byte) {
+ binary.LittleEndian.PutUint64(buf, uint64(n))
+}
+
+// Writes a byte without any possiblity of all that field header nonsense.
+// Used internally by other writing methods that know they need to write a byte.
+func (p *TCompactProtocol) writeByteDirect(b byte) error {
+ return p.trans.WriteByte(b)
+}
+
+// Writes a byte without any possiblity of all that field header nonsense.
+func (p *TCompactProtocol) writeIntAsByteDirect(n int) (int, error) {
+ return 1, p.writeByteDirect(byte(n))
+}
+
+//
+// Internal reading methods
+//
+
+// Read an i32 from the wire as a varint. The MSB of each byte is set
+// if there is another byte to follow. This can read up to 5 bytes.
+func (p *TCompactProtocol) readVarint32() (int32, error) {
+ // if the wire contains the right stuff, this will just truncate the i64 we
+ // read and get us the right sign.
+ v, err := p.readVarint64()
+ return int32(v), err
+}
+
+// Read an i64 from the wire as a proper varint. The MSB of each byte is set
+// if there is another byte to follow. This can read up to 10 bytes.
+func (p *TCompactProtocol) readVarint64() (int64, error) {
+ shift := uint(0)
+ result := int64(0)
+ for {
+ b, err := p.ReadByte()
+ if err != nil {
+ return 0, err
+ }
+ result |= int64(b&0x7f) << shift
+ if (b & 0x80) != 0x80 {
+ break
+ }
+ shift += 7
+ }
+ return result, nil
+}
+
+//
+// encoding helpers
+//
+
+// Convert from zigzag int to int.
+func (p *TCompactProtocol) zigzagToInt32(n int32) int32 {
+ u := uint32(n)
+ return int32(u>>1) ^ -(n & 1)
+}
+
+// Convert from zigzag long to long.
+func (p *TCompactProtocol) zigzagToInt64(n int64) int64 {
+ u := uint64(n)
+ return int64(u>>1) ^ -(n & 1)
+}
+
+// Note that it's important that the mask bytes are long literals,
+// otherwise they'll default to ints, and when you shift an int left 56 bits,
+// you just get a messed up int.
+func (p *TCompactProtocol) bytesToInt64(b []byte) int64 {
+ return int64(binary.LittleEndian.Uint64(b))
+}
+
+// Note that it's important that the mask bytes are long literals,
+// otherwise they'll default to ints, and when you shift an int left 56 bits,
+// you just get a messed up int.
+func (p *TCompactProtocol) bytesToUint64(b []byte) uint64 {
+ return binary.LittleEndian.Uint64(b)
+}
+
+//
+// type testing and converting
+//
+
+func (p *TCompactProtocol) isBoolType(b byte) bool {
+ return (b&0x0f) == COMPACT_BOOLEAN_TRUE || (b&0x0f) == COMPACT_BOOLEAN_FALSE
+}
+
+// Given a tCompactType constant, convert it to its corresponding
+// TType value.
+func (p *TCompactProtocol) getTType(t tCompactType) (TType, error) {
+ switch byte(t) & 0x0f {
+ case STOP:
+ return STOP, nil
+ case COMPACT_BOOLEAN_FALSE, COMPACT_BOOLEAN_TRUE:
+ return BOOL, nil
+ case COMPACT_BYTE:
+ return BYTE, nil
+ case COMPACT_I16:
+ return I16, nil
+ case COMPACT_I32:
+ return I32, nil
+ case COMPACT_I64:
+ return I64, nil
+ case COMPACT_DOUBLE:
+ return DOUBLE, nil
+ case COMPACT_BINARY:
+ return STRING, nil
+ case COMPACT_LIST:
+ return LIST, nil
+ case COMPACT_SET:
+ return SET, nil
+ case COMPACT_MAP:
+ return MAP, nil
+ case COMPACT_STRUCT:
+ return STRUCT, nil
+ }
+ return STOP, TException(fmt.Errorf("don't know what type: %s", t&0x0f))
+}
+
+// Given a TType value, find the appropriate TCompactProtocol.Types constant.
+func (p *TCompactProtocol) getCompactType(t TType) tCompactType {
+ return ttypeToCompactType[t]
+}
diff --git a/vendor/github.com/lightstep/thrift/lib/go/thrift/debug_protocol.go b/vendor/github.com/lightstep/thrift/lib/go/thrift/debug_protocol.go
new file mode 100644
index 000000000..ee341b2f7
--- /dev/null
+++ b/vendor/github.com/lightstep/thrift/lib/go/thrift/debug_protocol.go
@@ -0,0 +1,269 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+import (
+ "log"
+)
+
+type TDebugProtocol struct {
+ Delegate TProtocol
+ LogPrefix string
+}
+
+type TDebugProtocolFactory struct {
+ Underlying TProtocolFactory
+ LogPrefix string
+}
+
+func NewTDebugProtocolFactory(underlying TProtocolFactory, logPrefix string) *TDebugProtocolFactory {
+ return &TDebugProtocolFactory{
+ Underlying: underlying,
+ LogPrefix: logPrefix,
+ }
+}
+
+func (t *TDebugProtocolFactory) GetProtocol(trans TTransport) TProtocol {
+ return &TDebugProtocol{
+ Delegate: t.Underlying.GetProtocol(trans),
+ LogPrefix: t.LogPrefix,
+ }
+}
+
+func (tdp *TDebugProtocol) WriteMessageBegin(name string, typeId TMessageType, seqid int32) error {
+ err := tdp.Delegate.WriteMessageBegin(name, typeId, seqid)
+ log.Printf("%sWriteMessageBegin(name=%#v, typeId=%#v, seqid=%#v) => %#v", tdp.LogPrefix, name, typeId, seqid, err)
+ return err
+}
+func (tdp *TDebugProtocol) WriteMessageEnd() error {
+ err := tdp.Delegate.WriteMessageEnd()
+ log.Printf("%sWriteMessageEnd() => %#v", tdp.LogPrefix, err)
+ return err
+}
+func (tdp *TDebugProtocol) WriteStructBegin(name string) error {
+ err := tdp.Delegate.WriteStructBegin(name)
+ log.Printf("%sWriteStructBegin(name=%#v) => %#v", tdp.LogPrefix, name, err)
+ return err
+}
+func (tdp *TDebugProtocol) WriteStructEnd() error {
+ err := tdp.Delegate.WriteStructEnd()
+ log.Printf("%sWriteStructEnd() => %#v", tdp.LogPrefix, err)
+ return err
+}
+func (tdp *TDebugProtocol) WriteFieldBegin(name string, typeId TType, id int16) error {
+ err := tdp.Delegate.WriteFieldBegin(name, typeId, id)
+ log.Printf("%sWriteFieldBegin(name=%#v, typeId=%#v, id%#v) => %#v", tdp.LogPrefix, name, typeId, id, err)
+ return err
+}
+func (tdp *TDebugProtocol) WriteFieldEnd() error {
+ err := tdp.Delegate.WriteFieldEnd()
+ log.Printf("%sWriteFieldEnd() => %#v", tdp.LogPrefix, err)
+ return err
+}
+func (tdp *TDebugProtocol) WriteFieldStop() error {
+ err := tdp.Delegate.WriteFieldStop()
+ log.Printf("%sWriteFieldStop() => %#v", tdp.LogPrefix, err)
+ return err
+}
+func (tdp *TDebugProtocol) WriteMapBegin(keyType TType, valueType TType, size int) error {
+ err := tdp.Delegate.WriteMapBegin(keyType, valueType, size)
+ log.Printf("%sWriteMapBegin(keyType=%#v, valueType=%#v, size=%#v) => %#v", tdp.LogPrefix, keyType, valueType, size, err)
+ return err
+}
+func (tdp *TDebugProtocol) WriteMapEnd() error {
+ err := tdp.Delegate.WriteMapEnd()
+ log.Printf("%sWriteMapEnd() => %#v", tdp.LogPrefix, err)
+ return err
+}
+func (tdp *TDebugProtocol) WriteListBegin(elemType TType, size int) error {
+ err := tdp.Delegate.WriteListBegin(elemType, size)
+ log.Printf("%sWriteListBegin(elemType=%#v, size=%#v) => %#v", tdp.LogPrefix, elemType, size, err)
+ return err
+}
+func (tdp *TDebugProtocol) WriteListEnd() error {
+ err := tdp.Delegate.WriteListEnd()
+ log.Printf("%sWriteListEnd() => %#v", tdp.LogPrefix, err)
+ return err
+}
+func (tdp *TDebugProtocol) WriteSetBegin(elemType TType, size int) error {
+ err := tdp.Delegate.WriteSetBegin(elemType, size)
+ log.Printf("%sWriteSetBegin(elemType=%#v, size=%#v) => %#v", tdp.LogPrefix, elemType, size, err)
+ return err
+}
+func (tdp *TDebugProtocol) WriteSetEnd() error {
+ err := tdp.Delegate.WriteSetEnd()
+ log.Printf("%sWriteSetEnd() => %#v", tdp.LogPrefix, err)
+ return err
+}
+func (tdp *TDebugProtocol) WriteBool(value bool) error {
+ err := tdp.Delegate.WriteBool(value)
+ log.Printf("%sWriteBool(value=%#v) => %#v", tdp.LogPrefix, value, err)
+ return err
+}
+func (tdp *TDebugProtocol) WriteByte(value byte) error {
+ err := tdp.Delegate.WriteByte(value)
+ log.Printf("%sWriteByte(value=%#v) => %#v", tdp.LogPrefix, value, err)
+ return err
+}
+func (tdp *TDebugProtocol) WriteI16(value int16) error {
+ err := tdp.Delegate.WriteI16(value)
+ log.Printf("%sWriteI16(value=%#v) => %#v", tdp.LogPrefix, value, err)
+ return err
+}
+func (tdp *TDebugProtocol) WriteI32(value int32) error {
+ err := tdp.Delegate.WriteI32(value)
+ log.Printf("%sWriteI32(value=%#v) => %#v", tdp.LogPrefix, value, err)
+ return err
+}
+func (tdp *TDebugProtocol) WriteI64(value int64) error {
+ err := tdp.Delegate.WriteI64(value)
+ log.Printf("%sWriteI64(value=%#v) => %#v", tdp.LogPrefix, value, err)
+ return err
+}
+func (tdp *TDebugProtocol) WriteDouble(value float64) error {
+ err := tdp.Delegate.WriteDouble(value)
+ log.Printf("%sWriteDouble(value=%#v) => %#v", tdp.LogPrefix, value, err)
+ return err
+}
+func (tdp *TDebugProtocol) WriteString(value string) error {
+ err := tdp.Delegate.WriteString(value)
+ log.Printf("%sWriteString(value=%#v) => %#v", tdp.LogPrefix, value, err)
+ return err
+}
+func (tdp *TDebugProtocol) WriteBinary(value []byte) error {
+ err := tdp.Delegate.WriteBinary(value)
+ log.Printf("%sWriteBinary(value=%#v) => %#v", tdp.LogPrefix, value, err)
+ return err
+}
+
+func (tdp *TDebugProtocol) ReadMessageBegin() (name string, typeId TMessageType, seqid int32, err error) {
+ name, typeId, seqid, err = tdp.Delegate.ReadMessageBegin()
+ log.Printf("%sReadMessageBegin() (name=%#v, typeId=%#v, seqid=%#v, err=%#v)", tdp.LogPrefix, name, typeId, seqid, err)
+ return
+}
+func (tdp *TDebugProtocol) ReadMessageEnd() (err error) {
+ err = tdp.Delegate.ReadMessageEnd()
+ log.Printf("%sReadMessageEnd() err=%#v", tdp.LogPrefix, err)
+ return
+}
+func (tdp *TDebugProtocol) ReadStructBegin() (name string, err error) {
+ name, err = tdp.Delegate.ReadStructBegin()
+ log.Printf("%sReadStructBegin() (name%#v, err=%#v)", tdp.LogPrefix, name, err)
+ return
+}
+func (tdp *TDebugProtocol) ReadStructEnd() (err error) {
+ err = tdp.Delegate.ReadStructEnd()
+ log.Printf("%sReadStructEnd() err=%#v", tdp.LogPrefix, err)
+ return
+}
+func (tdp *TDebugProtocol) ReadFieldBegin() (name string, typeId TType, id int16, err error) {
+ name, typeId, id, err = tdp.Delegate.ReadFieldBegin()
+ log.Printf("%sReadFieldBegin() (name=%#v, typeId=%#v, id=%#v, err=%#v)", tdp.LogPrefix, name, typeId, id, err)
+ return
+}
+func (tdp *TDebugProtocol) ReadFieldEnd() (err error) {
+ err = tdp.Delegate.ReadFieldEnd()
+ log.Printf("%sReadFieldEnd() err=%#v", tdp.LogPrefix, err)
+ return
+}
+func (tdp *TDebugProtocol) ReadMapBegin() (keyType TType, valueType TType, size int, err error) {
+ keyType, valueType, size, err = tdp.Delegate.ReadMapBegin()
+ log.Printf("%sReadMapBegin() (keyType=%#v, valueType=%#v, size=%#v, err=%#v)", tdp.LogPrefix, keyType, valueType, size, err)
+ return
+}
+func (tdp *TDebugProtocol) ReadMapEnd() (err error) {
+ err = tdp.Delegate.ReadMapEnd()
+ log.Printf("%sReadMapEnd() err=%#v", tdp.LogPrefix, err)
+ return
+}
+func (tdp *TDebugProtocol) ReadListBegin() (elemType TType, size int, err error) {
+ elemType, size, err = tdp.Delegate.ReadListBegin()
+ log.Printf("%sReadListBegin() (elemType=%#v, size=%#v, err=%#v)", tdp.LogPrefix, elemType, size, err)
+ return
+}
+func (tdp *TDebugProtocol) ReadListEnd() (err error) {
+ err = tdp.Delegate.ReadListEnd()
+ log.Printf("%sReadListEnd() err=%#v", tdp.LogPrefix, err)
+ return
+}
+func (tdp *TDebugProtocol) ReadSetBegin() (elemType TType, size int, err error) {
+ elemType, size, err = tdp.Delegate.ReadSetBegin()
+ log.Printf("%sReadSetBegin() (elemType=%#v, size=%#v, err=%#v)", tdp.LogPrefix, elemType, size, err)
+ return
+}
+func (tdp *TDebugProtocol) ReadSetEnd() (err error) {
+ err = tdp.Delegate.ReadSetEnd()
+ log.Printf("%sReadSetEnd() err=%#v", tdp.LogPrefix, err)
+ return
+}
+func (tdp *TDebugProtocol) ReadBool() (value bool, err error) {
+ value, err = tdp.Delegate.ReadBool()
+ log.Printf("%sReadBool() (value=%#v, err=%#v)", tdp.LogPrefix, value, err)
+ return
+}
+func (tdp *TDebugProtocol) ReadByte() (value byte, err error) {
+ value, err = tdp.Delegate.ReadByte()
+ log.Printf("%sReadByte() (value=%#v, err=%#v)", tdp.LogPrefix, value, err)
+ return
+}
+func (tdp *TDebugProtocol) ReadI16() (value int16, err error) {
+ value, err = tdp.Delegate.ReadI16()
+ log.Printf("%sReadI16() (value=%#v, err=%#v)", tdp.LogPrefix, value, err)
+ return
+}
+func (tdp *TDebugProtocol) ReadI32() (value int32, err error) {
+ value, err = tdp.Delegate.ReadI32()
+ log.Printf("%sReadI32() (value=%#v, err=%#v)", tdp.LogPrefix, value, err)
+ return
+}
+func (tdp *TDebugProtocol) ReadI64() (value int64, err error) {
+ value, err = tdp.Delegate.ReadI64()
+ log.Printf("%sReadI64() (value=%#v, err=%#v)", tdp.LogPrefix, value, err)
+ return
+}
+func (tdp *TDebugProtocol) ReadDouble() (value float64, err error) {
+ value, err = tdp.Delegate.ReadDouble()
+ log.Printf("%sReadDouble() (value=%#v, err=%#v)", tdp.LogPrefix, value, err)
+ return
+}
+func (tdp *TDebugProtocol) ReadString() (value string, err error) {
+ value, err = tdp.Delegate.ReadString()
+ log.Printf("%sReadString() (value=%#v, err=%#v)", tdp.LogPrefix, value, err)
+ return
+}
+func (tdp *TDebugProtocol) ReadBinary() (value []byte, err error) {
+ value, err = tdp.Delegate.ReadBinary()
+ log.Printf("%sReadBinary() (value=%#v, err=%#v)", tdp.LogPrefix, value, err)
+ return
+}
+func (tdp *TDebugProtocol) Skip(fieldType TType) (err error) {
+ err = tdp.Delegate.Skip(fieldType)
+ log.Printf("%sSkip(fieldType=%#v) (err=%#v)", tdp.LogPrefix, fieldType, err)
+ return
+}
+func (tdp *TDebugProtocol) Flush() (err error) {
+ err = tdp.Delegate.Flush()
+ log.Printf("%sFlush() (err=%#v)", tdp.LogPrefix, err)
+ return
+}
+
+func (tdp *TDebugProtocol) Transport() TTransport {
+ return tdp.Delegate.Transport()
+}
diff --git a/vendor/github.com/lightstep/thrift/lib/go/thrift/deserializer.go b/vendor/github.com/lightstep/thrift/lib/go/thrift/deserializer.go
new file mode 100644
index 000000000..91a0983a4
--- /dev/null
+++ b/vendor/github.com/lightstep/thrift/lib/go/thrift/deserializer.go
@@ -0,0 +1,58 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+type TDeserializer struct {
+ Transport TTransport
+ Protocol TProtocol
+}
+
+func NewTDeserializer() *TDeserializer {
+ var transport TTransport
+ transport = NewTMemoryBufferLen(1024)
+
+ protocol := NewTBinaryProtocolFactoryDefault().GetProtocol(transport)
+
+ return &TDeserializer{
+ transport,
+ protocol}
+}
+
+func (t *TDeserializer) ReadString(msg TStruct, s string) (err error) {
+ err = nil
+ if _, err = t.Transport.Write([]byte(s)); err != nil {
+ return
+ }
+ if err = msg.Read(t.Protocol); err != nil {
+ return
+ }
+ return
+}
+
+func (t *TDeserializer) Read(msg TStruct, b []byte) (err error) {
+ err = nil
+ if _, err = t.Transport.Write(b); err != nil {
+ return
+ }
+ if err = msg.Read(t.Protocol); err != nil {
+ return
+ }
+ return
+}
diff --git a/vendor/github.com/lightstep/thrift/lib/go/thrift/exception.go b/vendor/github.com/lightstep/thrift/lib/go/thrift/exception.go
new file mode 100644
index 000000000..e08ffc0c7
--- /dev/null
+++ b/vendor/github.com/lightstep/thrift/lib/go/thrift/exception.go
@@ -0,0 +1,25 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+// Generic Thrift exception
+type TException interface {
+ error
+}
diff --git a/vendor/github.com/lightstep/thrift/lib/go/thrift/field.go b/vendor/github.com/lightstep/thrift/lib/go/thrift/field.go
new file mode 100644
index 000000000..9d6652550
--- /dev/null
+++ b/vendor/github.com/lightstep/thrift/lib/go/thrift/field.go
@@ -0,0 +1,79 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+// Helper class that encapsulates field metadata.
+type field struct {
+ name string
+ typeId TType
+ id int
+}
+
+func newField(n string, t TType, i int) *field {
+ return &field{name: n, typeId: t, id: i}
+}
+
+func (p *field) Name() string {
+ if p == nil {
+ return ""
+ }
+ return p.name
+}
+
+func (p *field) TypeId() TType {
+ if p == nil {
+ return TType(VOID)
+ }
+ return p.typeId
+}
+
+func (p *field) Id() int {
+ if p == nil {
+ return -1
+ }
+ return p.id
+}
+
+func (p *field) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return "<TField name:'" + p.name + "' type:" + string(p.typeId) + " field-id:" + string(p.id) + ">"
+}
+
+var ANONYMOUS_FIELD *field
+
+type fieldSlice []field
+
+func (p fieldSlice) Len() int {
+ return len(p)
+}
+
+func (p fieldSlice) Less(i, j int) bool {
+ return p[i].Id() < p[j].Id()
+}
+
+func (p fieldSlice) Swap(i, j int) {
+ p[i], p[j] = p[j], p[i]
+}
+
+func init() {
+ ANONYMOUS_FIELD = newField("", STOP, 0)
+}
diff --git a/vendor/github.com/lightstep/thrift/lib/go/thrift/framed_transport.go b/vendor/github.com/lightstep/thrift/lib/go/thrift/framed_transport.go
new file mode 100644
index 000000000..bfecbe832
--- /dev/null
+++ b/vendor/github.com/lightstep/thrift/lib/go/thrift/framed_transport.go
@@ -0,0 +1,151 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+import (
+ "bufio"
+ "bytes"
+ "encoding/binary"
+ "fmt"
+ "io"
+)
+
+const DEFAULT_MAX_LENGTH = 16384000
+
+type TFramedTransport struct {
+ transport TTransport
+ buf bytes.Buffer
+ reader *bufio.Reader
+ frameSize int //Current remaining size of the frame. if ==0 read next frame header
+ buffer [4]byte
+ maxLength int
+}
+
+type tFramedTransportFactory struct {
+ factory TTransportFactory
+ maxLength int
+}
+
+func NewTFramedTransportFactory(factory TTransportFactory) TTransportFactory {
+ return &tFramedTransportFactory{factory: factory, maxLength: DEFAULT_MAX_LENGTH}
+}
+
+func (p *tFramedTransportFactory) GetTransport(base TTransport) TTransport {
+ return NewTFramedTransportMaxLength(p.factory.GetTransport(base), p.maxLength)
+}
+
+func NewTFramedTransport(transport TTransport) *TFramedTransport {
+ return &TFramedTransport{transport: transport, reader: bufio.NewReader(transport), maxLength: DEFAULT_MAX_LENGTH}
+}
+
+func NewTFramedTransportMaxLength(transport TTransport, maxLength int) *TFramedTransport {
+ return &TFramedTransport{transport: transport, reader: bufio.NewReader(transport), maxLength: maxLength}
+}
+
+func (p *TFramedTransport) Open() error {
+ return p.transport.Open()
+}
+
+func (p *TFramedTransport) IsOpen() bool {
+ return p.transport.IsOpen()
+}
+
+func (p *TFramedTransport) Close() error {
+ return p.transport.Close()
+}
+
+func (p *TFramedTransport) Read(buf []byte) (l int, err error) {
+ if p.frameSize == 0 {
+ p.frameSize, err = p.readFrameHeader()
+ if err != nil {
+ return
+ }
+ }
+ if p.frameSize < len(buf) {
+ return 0, NewTTransportExceptionFromError(fmt.Errorf("Not enought frame size %d to read %d bytes", p.frameSize, len(buf)))
+ }
+ got, err := p.reader.Read(buf)
+ p.frameSize = p.frameSize - got
+ //sanity check
+ if p.frameSize < 0 {
+ return 0, NewTTransportException(UNKNOWN_TRANSPORT_EXCEPTION, "Negative frame size")
+ }
+ return got, NewTTransportExceptionFromError(err)
+}
+
+func (p *TFramedTransport) ReadByte() (c byte, err error) {
+ if p.frameSize == 0 {
+ p.frameSize, err = p.readFrameHeader()
+ if err != nil {
+ return
+ }
+ }
+ if p.frameSize < 1 {
+ return 0, NewTTransportExceptionFromError(fmt.Errorf("Not enought frame size %d to read %d bytes", p.frameSize, 1))
+ }
+ c, err = p.reader.ReadByte()
+ if err == nil {
+ p.frameSize--
+ }
+ return
+}
+
+func (p *TFramedTransport) Write(buf []byte) (int, error) {
+ n, err := p.buf.Write(buf)
+ return n, NewTTransportExceptionFromError(err)
+}
+
+func (p *TFramedTransport) WriteByte(c byte) error {
+ return p.buf.WriteByte(c)
+}
+
+func (p *TFramedTransport) WriteString(s string) (n int, err error) {
+ return p.buf.WriteString(s)
+}
+
+func (p *TFramedTransport) Flush() error {
+ size := p.buf.Len()
+ buf := p.buffer[:4]
+ binary.BigEndian.PutUint32(buf, uint32(size))
+ _, err := p.transport.Write(buf)
+ if err != nil {
+ return NewTTransportExceptionFromError(err)
+ }
+ if size > 0 {
+ if n, err := p.buf.WriteTo(p.transport); err != nil {
+ print("Error while flushing write buffer of size ", size, " to transport, only wrote ", n, " bytes: ", err.Error(), "\n")
+ return NewTTransportExceptionFromError(err)
+ }
+ }
+ err = p.transport.Flush()
+ return NewTTransportExceptionFromError(err)
+}
+
+func (p *TFramedTransport) readFrameHeader() (int, error) {
+ buf := p.buffer[:4]
+ if _, err := io.ReadFull(p.reader, buf); err != nil {
+ return 0, err
+ }
+ size := int(binary.BigEndian.Uint32(buf))
+ if size < 0 || size > p.maxLength {
+ return 0, NewTTransportException(UNKNOWN_TRANSPORT_EXCEPTION, fmt.Sprintf("Incorrect frame size (%d)", size))
+ }
+ return size, nil
+}
diff --git a/vendor/github.com/lightstep/thrift/lib/go/thrift/http_client.go b/vendor/github.com/lightstep/thrift/lib/go/thrift/http_client.go
new file mode 100644
index 000000000..5806c1d0f
--- /dev/null
+++ b/vendor/github.com/lightstep/thrift/lib/go/thrift/http_client.go
@@ -0,0 +1,286 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+import (
+ "bytes"
+ "io"
+ "io/ioutil"
+ "net/http"
+ "net/url"
+ "strconv"
+ "sync"
+ "time"
+)
+
+type THttpClient struct {
+ // the most recent response, if any
+ responseBuffer *bytes.Buffer
+ url *url.URL
+ requestBuffer *bytes.Buffer
+ header http.Header
+ timeout time.Duration
+ // TODO what are these timeouts for?
+ nsecConnectTimeout int64
+ nsecReadTimeout int64
+ httpClient *http.Client
+}
+
+type THttpClientTransportFactory struct {
+ url string
+ isPost bool
+ timeout time.Duration
+}
+
+func (p *THttpClientTransportFactory) GetTransport(trans TTransport) TTransport {
+ if trans != nil {
+ t, ok := trans.(*THttpClient)
+ if ok && t.url != nil {
+ if t.requestBuffer != nil {
+ t2, _ := NewTHttpPostClient(t.url.String(), t.timeout)
+ return t2
+ }
+ t2, _ := NewTHttpClient(t.url.String(), t.timeout)
+ return t2
+ }
+ }
+ if p.isPost {
+ s, _ := NewTHttpPostClient(p.url, p.timeout)
+ return s
+ }
+ s, _ := NewTHttpClient(p.url, p.timeout)
+ return s
+}
+
+func NewTHttpClientTransportFactory(url string, timeout time.Duration) *THttpClientTransportFactory {
+ return &THttpClientTransportFactory{url: url, isPost: false, timeout: timeout}
+}
+
+func NewTHttpPostClientTransportFactory(url string, timeout time.Duration) *THttpClientTransportFactory {
+ return &THttpClientTransportFactory{url: url, isPost: true, timeout: timeout}
+}
+
+func newHttpClient(timeout time.Duration) *http.Client {
+ return &http.Client{
+ // Setting a non-nil Transport means that each client will get its own
+ // idle connection pool. This is way more stable than sharing a single
+ // pool for this entire server.
+ Transport: &http.Transport{}, // TODO set additional (TLS?) timeouts?
+ Timeout: timeout,
+ }
+}
+
+func NewTHttpClient(urlstr string, timeout time.Duration) (TTransport, error) {
+ parsedURL, err := url.Parse(urlstr)
+ if err != nil {
+ return nil, err
+ }
+ response, err := http.Get(urlstr)
+ if response != nil && response.Body != nil {
+ defer response.Body.Close()
+ }
+ if err != nil {
+ return nil, err
+ }
+ bs, err := ioutil.ReadAll(response.Body)
+ if err != nil {
+ return nil, err
+ }
+ buf := bytes.NewBuffer(bs)
+
+ return &THttpClient{
+ responseBuffer: buf,
+ url: parsedURL,
+ httpClient: newHttpClient(timeout),
+ timeout: timeout,
+ }, nil
+}
+
+// bufPool is a set of buffers used for the request bodies. Buffers should
+// be Reset() before they are added to the pool.
+var bufPool = sync.Pool{
+ New: func() interface{} {
+ return bytes.NewBuffer(make([]byte, 0, 1024))
+ },
+}
+
+func getBuffer() *bytes.Buffer {
+ buf := bufPool.Get().(*bytes.Buffer)
+ if buf == nil {
+ buf = bytes.NewBuffer(make([]byte, 0, 1024))
+ }
+ return buf
+}
+
+func NewTHttpPostClient(urlstr string, timeout time.Duration) (TTransport, error) {
+ parsedURL, err := url.Parse(urlstr)
+ if err != nil {
+ return nil, err
+ }
+ return &THttpClient{
+ url: parsedURL,
+ requestBuffer: getBuffer(),
+ header: http.Header{},
+ httpClient: newHttpClient(timeout),
+ }, nil
+}
+
+// Set the HTTP Header for this specific Thrift Transport
+// It is important that you first assert the TTransport as a THttpClient type
+// like so:
+//
+// httpTrans := trans.(THttpClient)
+// httpTrans.SetHeader("User-Agent","Thrift Client 1.0")
+func (p *THttpClient) SetHeader(key string, value string) {
+ p.header.Set(key, value)
+}
+
+// Get the HTTP Header represented by the supplied Header Key for this specific Thrift Transport
+// It is important that you first assert the TTransport as a THttpClient type
+// like so:
+//
+// httpTrans := trans.(THttpClient)
+// hdrValue := httpTrans.GetHeader("User-Agent")
+func (p *THttpClient) GetHeader(key string) string {
+ return p.header.Get(key)
+}
+
+// Deletes the HTTP Header given a Header Key for this specific Thrift Transport
+// It is important that you first assert the TTransport as a THttpClient type
+// like so:
+//
+// httpTrans := trans.(THttpClient)
+// httpTrans.DelHeader("User-Agent")
+func (p *THttpClient) DelHeader(key string) {
+ p.header.Del(key)
+}
+
+func (p *THttpClient) Open() error {
+ // do nothing
+ return nil
+}
+
+func (p *THttpClient) IsOpen() bool {
+ return p.responseBuffer != nil || p.requestBuffer != nil
+}
+
+func (p *THttpClient) Peek() bool {
+ return p.IsOpen()
+}
+
+func (p *THttpClient) Close() error {
+ if p.responseBuffer != nil {
+ p.responseBuffer = nil
+ }
+ if p.requestBuffer != nil {
+ // Note: We do not return the buffer to the pool,
+ // since there is a potential race here. It will be
+ // garbage collected.
+ p.requestBuffer = nil
+ }
+ return nil
+}
+
+func (p *THttpClient) Read(buf []byte) (int, error) {
+ if p.responseBuffer == nil {
+ return 0, NewTTransportException(NOT_OPEN, "Response buffer is empty, no request.")
+ }
+ n, err := p.responseBuffer.Read(buf)
+ if n > 0 && (err == nil || err == io.EOF) {
+ return n, nil
+ }
+ return n, NewTTransportExceptionFromError(err)
+}
+
+func (p *THttpClient) ReadByte() (c byte, err error) {
+ return readByte(p.responseBuffer)
+}
+
+func (p *THttpClient) Write(buf []byte) (int, error) {
+ n, err := p.requestBuffer.Write(buf)
+ return n, err
+}
+
+func (p *THttpClient) WriteByte(c byte) error {
+ return p.requestBuffer.WriteByte(c)
+}
+
+func (p *THttpClient) WriteString(s string) (n int, err error) {
+ return p.requestBuffer.WriteString(s)
+}
+
+// bufferCloser makes a bytes.Buffer into an io.Closer and returns unused
+// buffers to the pool.
+type bufferCloser struct {
+ sync.Once
+ *bytes.Buffer
+}
+
+// THttpClient reuses its buffer from one request to the next. If that
+// buffer is not reset, well, it'll just keep getting extended from
+// one request to the next. Make the bytes.Buffer into an io.Closer
+// and rely on the http transport to call Close() (and therefore
+// to call Reset() and return it to the pool).
+func (b *bufferCloser) Close() error {
+ b.Once.Do(func() {
+ b.Reset()
+ bufPool.Put(b.Buffer)
+ })
+ return nil
+}
+
+func (p *THttpClient) Flush() error {
+ req, err := http.NewRequest("POST", p.url.String(), &bufferCloser{Buffer: p.requestBuffer})
+ if err != nil {
+ return NewTTransportExceptionFromError(err)
+ }
+ // Reset the request/response state
+ p.requestBuffer = getBuffer()
+ p.responseBuffer = nil
+ // Do the call
+ req.Header = p.header
+ // http2 reads the header outside of the call to Do(), so make a new
+ // header for next time here.
+ p.header = make(http.Header, len(req.Header))
+ // Also, I'm not sure why the headers are reused from request to request,
+ // so make a copy of them in case anyone is expecting that.
+ for k, v := range req.Header {
+ p.header[k] = v
+ }
+ req.Header.Set("Content-Type", "application/x-thrift")
+ response, err := p.httpClient.Do(req)
+ if response != nil && response.Body != nil {
+ defer response.Body.Close()
+ }
+
+ if err != nil {
+ return NewTTransportExceptionFromError(err)
+ }
+ if response.StatusCode != http.StatusOK {
+ // TODO(pomack) log bad response
+ return NewTTransportException(UNKNOWN_TRANSPORT_EXCEPTION, "HTTP Response code: "+strconv.Itoa(response.StatusCode))
+ }
+ bs, err := ioutil.ReadAll(response.Body)
+ if err != nil {
+ return err
+ }
+ p.responseBuffer = bytes.NewBuffer(bs)
+ return nil
+}
diff --git a/vendor/github.com/lightstep/thrift/lib/go/thrift/iostream_transport.go b/vendor/github.com/lightstep/thrift/lib/go/thrift/iostream_transport.go
new file mode 100644
index 000000000..314eaa6ff
--- /dev/null
+++ b/vendor/github.com/lightstep/thrift/lib/go/thrift/iostream_transport.go
@@ -0,0 +1,205 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+import (
+ "bufio"
+ "io"
+)
+
+// StreamTransport is a Transport made of an io.Reader and/or an io.Writer
+type StreamTransport struct {
+ io.Reader
+ io.Writer
+ isReadWriter bool
+}
+
+type StreamTransportFactory struct {
+ Reader io.Reader
+ Writer io.Writer
+ isReadWriter bool
+}
+
+func (p *StreamTransportFactory) GetTransport(trans TTransport) TTransport {
+ if trans != nil {
+ t, ok := trans.(*StreamTransport)
+ if ok {
+ if t.isReadWriter {
+ return NewStreamTransportRW(t.Reader.(io.ReadWriter))
+ }
+ if t.Reader != nil && t.Writer != nil {
+ return NewStreamTransport(t.Reader, t.Writer)
+ }
+ if t.Reader != nil && t.Writer == nil {
+ return NewStreamTransportR(t.Reader)
+ }
+ if t.Reader == nil && t.Writer != nil {
+ return NewStreamTransportW(t.Writer)
+ }
+ return &StreamTransport{}
+ }
+ }
+ if p.isReadWriter {
+ return NewStreamTransportRW(p.Reader.(io.ReadWriter))
+ }
+ if p.Reader != nil && p.Writer != nil {
+ return NewStreamTransport(p.Reader, p.Writer)
+ }
+ if p.Reader != nil && p.Writer == nil {
+ return NewStreamTransportR(p.Reader)
+ }
+ if p.Reader == nil && p.Writer != nil {
+ return NewStreamTransportW(p.Writer)
+ }
+ return &StreamTransport{}
+}
+
+func NewStreamTransportFactory(reader io.Reader, writer io.Writer, isReadWriter bool) *StreamTransportFactory {
+ return &StreamTransportFactory{Reader: reader, Writer: writer, isReadWriter: isReadWriter}
+}
+
+func NewStreamTransport(r io.Reader, w io.Writer) *StreamTransport {
+ return &StreamTransport{Reader: bufio.NewReader(r), Writer: bufio.NewWriter(w)}
+}
+
+func NewStreamTransportR(r io.Reader) *StreamTransport {
+ return &StreamTransport{Reader: bufio.NewReader(r)}
+}
+
+func NewStreamTransportW(w io.Writer) *StreamTransport {
+ return &StreamTransport{Writer: bufio.NewWriter(w)}
+}
+
+func NewStreamTransportRW(rw io.ReadWriter) *StreamTransport {
+ bufrw := bufio.NewReadWriter(bufio.NewReader(rw), bufio.NewWriter(rw))
+ return &StreamTransport{Reader: bufrw, Writer: bufrw, isReadWriter: true}
+}
+
+// (The streams must already be open at construction time, so this should
+// always return true.)
+func (p *StreamTransport) IsOpen() bool {
+ return true
+}
+
+// (The streams must already be open. This method does nothing.)
+func (p *StreamTransport) Open() error {
+ return nil
+}
+
+// func (p *StreamTransport) Peek() bool {
+// return p.IsOpen()
+// }
+
+// Closes both the input and output streams.
+func (p *StreamTransport) Close() error {
+ closedReader := false
+ if p.Reader != nil {
+ c, ok := p.Reader.(io.Closer)
+ if ok {
+ e := c.Close()
+ closedReader = true
+ if e != nil {
+ return e
+ }
+ }
+ p.Reader = nil
+ }
+ if p.Writer != nil && (!closedReader || !p.isReadWriter) {
+ c, ok := p.Writer.(io.Closer)
+ if ok {
+ e := c.Close()
+ if e != nil {
+ return e
+ }
+ }
+ p.Writer = nil
+ }
+ return nil
+}
+
+// Flushes the underlying output stream if not null.
+func (p *StreamTransport) Flush() error {
+ if p.Writer == nil {
+ return NewTTransportException(NOT_OPEN, "Cannot flush null outputStream")
+ }
+ f, ok := p.Writer.(Flusher)
+ if ok {
+ err := f.Flush()
+ if err != nil {
+ return NewTTransportExceptionFromError(err)
+ }
+ }
+ return nil
+}
+
+func (p *StreamTransport) Read(c []byte) (n int, err error) {
+ n, err = p.Reader.Read(c)
+ if err != nil {
+ err = NewTTransportExceptionFromError(err)
+ }
+ return
+}
+
+func (p *StreamTransport) ReadByte() (c byte, err error) {
+ f, ok := p.Reader.(io.ByteReader)
+ if ok {
+ c, err = f.ReadByte()
+ } else {
+ c, err = readByte(p.Reader)
+ }
+ if err != nil {
+ err = NewTTransportExceptionFromError(err)
+ }
+ return
+}
+
+func (p *StreamTransport) Write(c []byte) (n int, err error) {
+ n, err = p.Writer.Write(c)
+ if err != nil {
+ err = NewTTransportExceptionFromError(err)
+ }
+ return
+}
+
+func (p *StreamTransport) WriteByte(c byte) (err error) {
+ f, ok := p.Writer.(io.ByteWriter)
+ if ok {
+ err = f.WriteByte(c)
+ } else {
+ err = writeByte(p.Writer, c)
+ }
+ if err != nil {
+ err = NewTTransportExceptionFromError(err)
+ }
+ return
+}
+
+func (p *StreamTransport) WriteString(s string) (n int, err error) {
+ f, ok := p.Writer.(stringWriter)
+ if ok {
+ n, err = f.WriteString(s)
+ } else {
+ n, err = p.Writer.Write([]byte(s))
+ }
+ if err != nil {
+ err = NewTTransportExceptionFromError(err)
+ }
+ return
+}
diff --git a/vendor/github.com/lightstep/thrift/lib/go/thrift/json_protocol.go b/vendor/github.com/lightstep/thrift/lib/go/thrift/json_protocol.go
new file mode 100644
index 000000000..6c82b7c75
--- /dev/null
+++ b/vendor/github.com/lightstep/thrift/lib/go/thrift/json_protocol.go
@@ -0,0 +1,552 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+import (
+ "encoding/base64"
+ "fmt"
+)
+
+const (
+ THRIFT_JSON_PROTOCOL_VERSION = 1
+)
+
+// for references to _ParseContext see tsimplejson_protocol.go
+
+// JSON protocol implementation for thrift.
+//
+// This protocol produces/consumes a simple output format
+// suitable for parsing by scripting languages. It should not be
+// confused with the full-featured TJSONProtocol.
+//
+type TJSONProtocol struct {
+ *TSimpleJSONProtocol
+}
+
+// Constructor
+func NewTJSONProtocol(t TTransport) *TJSONProtocol {
+ v := &TJSONProtocol{TSimpleJSONProtocol: NewTSimpleJSONProtocol(t)}
+ v.parseContextStack = append(v.parseContextStack, int(_CONTEXT_IN_TOPLEVEL))
+ v.dumpContext = append(v.dumpContext, int(_CONTEXT_IN_TOPLEVEL))
+ return v
+}
+
+// Factory
+type TJSONProtocolFactory struct{}
+
+func (p *TJSONProtocolFactory) GetProtocol(trans TTransport) TProtocol {
+ return NewTJSONProtocol(trans)
+}
+
+func NewTJSONProtocolFactory() *TJSONProtocolFactory {
+ return &TJSONProtocolFactory{}
+}
+
+func (p *TJSONProtocol) WriteMessageBegin(name string, typeId TMessageType, seqId int32) error {
+ if e := p.OutputListBegin(); e != nil {
+ return e
+ }
+ if e := p.WriteI32(THRIFT_JSON_PROTOCOL_VERSION); e != nil {
+ return e
+ }
+ if e := p.WriteString(name); e != nil {
+ return e
+ }
+ if e := p.WriteByte(byte(typeId)); e != nil {
+ return e
+ }
+ if e := p.WriteI32(seqId); e != nil {
+ return e
+ }
+ return nil
+}
+
+func (p *TJSONProtocol) WriteMessageEnd() error {
+ return p.OutputListEnd()
+}
+
+func (p *TJSONProtocol) WriteStructBegin(name string) error {
+ if e := p.OutputObjectBegin(); e != nil {
+ return e
+ }
+ return nil
+}
+
+func (p *TJSONProtocol) WriteStructEnd() error {
+ return p.OutputObjectEnd()
+}
+
+func (p *TJSONProtocol) WriteFieldBegin(name string, typeId TType, id int16) error {
+ if e := p.WriteI16(id); e != nil {
+ return e
+ }
+ if e := p.OutputObjectBegin(); e != nil {
+ return e
+ }
+ s, e1 := p.TypeIdToString(typeId)
+ if e1 != nil {
+ return e1
+ }
+ if e := p.WriteString(s); e != nil {
+ return e
+ }
+ return nil
+}
+
+func (p *TJSONProtocol) WriteFieldEnd() error {
+ return p.OutputObjectEnd()
+}
+
+func (p *TJSONProtocol) WriteFieldStop() error { return nil }
+
+func (p *TJSONProtocol) WriteMapBegin(keyType TType, valueType TType, size int) error {
+ if e := p.OutputListBegin(); e != nil {
+ return e
+ }
+ s, e1 := p.TypeIdToString(keyType)
+ if e1 != nil {
+ return e1
+ }
+ if e := p.WriteString(s); e != nil {
+ return e
+ }
+ s, e1 = p.TypeIdToString(valueType)
+ if e1 != nil {
+ return e1
+ }
+ if e := p.WriteString(s); e != nil {
+ return e
+ }
+ return p.WriteI64(int64(size))
+}
+
+func (p *TJSONProtocol) WriteMapEnd() error {
+ return p.OutputListEnd()
+}
+
+func (p *TJSONProtocol) WriteListBegin(elemType TType, size int) error {
+ return p.OutputElemListBegin(elemType, size)
+}
+
+func (p *TJSONProtocol) WriteListEnd() error {
+ return p.OutputListEnd()
+}
+
+func (p *TJSONProtocol) WriteSetBegin(elemType TType, size int) error {
+ return p.OutputElemListBegin(elemType, size)
+}
+
+func (p *TJSONProtocol) WriteSetEnd() error {
+ return p.OutputListEnd()
+}
+
+func (p *TJSONProtocol) WriteBool(b bool) error {
+ if b {
+ return p.WriteI32(1)
+ }
+ return p.WriteI32(0)
+}
+
+func (p *TJSONProtocol) WriteByte(b byte) error {
+ return p.WriteI32(int32(b))
+}
+
+func (p *TJSONProtocol) WriteI16(v int16) error {
+ return p.WriteI32(int32(v))
+}
+
+func (p *TJSONProtocol) WriteI32(v int32) error {
+ return p.OutputI64(int64(v))
+}
+
+func (p *TJSONProtocol) WriteI64(v int64) error {
+ return p.OutputI64(int64(v))
+}
+
+func (p *TJSONProtocol) WriteDouble(v float64) error {
+ return p.OutputF64(v)
+}
+
+func (p *TJSONProtocol) WriteString(v string) error {
+ return p.OutputString(v)
+}
+
+func (p *TJSONProtocol) WriteBinary(v []byte) error {
+ // JSON library only takes in a string,
+ // not an arbitrary byte array, to ensure bytes are transmitted
+ // efficiently we must convert this into a valid JSON string
+ // therefore we use base64 encoding to avoid excessive escaping/quoting
+ if e := p.OutputPreValue(); e != nil {
+ return e
+ }
+ p.writer.Write(JSON_QUOTE_BYTES)
+ writer := base64.NewEncoder(base64.StdEncoding, p.writer)
+ if _, e := writer.Write(v); e != nil {
+ return NewTProtocolException(e)
+ }
+ writer.Close()
+ p.writer.Write(JSON_QUOTE_BYTES)
+ return p.OutputPostValue()
+}
+
+// Reading methods.
+
+func (p *TJSONProtocol) ReadMessageBegin() (name string, typeId TMessageType, seqId int32, err error) {
+ if isNull, err := p.ParseListBegin(); isNull || err != nil {
+ return name, typeId, seqId, err
+ }
+ version, err := p.ReadI32()
+ if err != nil {
+ return name, typeId, seqId, err
+ }
+ if version != THRIFT_JSON_PROTOCOL_VERSION {
+ e := fmt.Errorf("Unknown Protocol version %d, expected version %d", version, THRIFT_JSON_PROTOCOL_VERSION)
+ return name, typeId, seqId, NewTProtocolExceptionWithType(INVALID_DATA, e)
+
+ }
+ if name, err = p.ReadString(); err != nil {
+ return name, typeId, seqId, err
+ }
+ bTypeId, err := p.ReadByte()
+ typeId = TMessageType(bTypeId)
+ if err != nil {
+ return name, typeId, seqId, err
+ }
+ if seqId, err = p.ReadI32(); err != nil {
+ return name, typeId, seqId, err
+ }
+ return name, typeId, seqId, nil
+}
+
+func (p *TJSONProtocol) ReadMessageEnd() error {
+ err := p.ParseListEnd()
+ return err
+}
+
+func (p *TJSONProtocol) ReadStructBegin() (name string, err error) {
+ _, err = p.ParseObjectStart()
+ return "", err
+}
+
+func (p *TJSONProtocol) ReadStructEnd() error {
+ return p.ParseObjectEnd()
+}
+
+func (p *TJSONProtocol) ReadFieldBegin() (string, TType, int16, error) {
+ if p.reader.Buffered() < 1 {
+ return "", STOP, -1, nil
+ }
+ b, _ := p.reader.Peek(1)
+ if len(b) < 1 || b[0] == JSON_RBRACE[0] || b[0] == JSON_RBRACKET[0] {
+ return "", STOP, -1, nil
+ }
+ fieldId, err := p.ReadI16()
+ if err != nil {
+ return "", STOP, fieldId, err
+ }
+ if _, err = p.ParseObjectStart(); err != nil {
+ return "", STOP, fieldId, err
+ }
+ sType, err := p.ReadString()
+ if err != nil {
+ return "", STOP, fieldId, err
+ }
+ fType, err := p.StringToTypeId(sType)
+ return "", fType, fieldId, err
+}
+
+func (p *TJSONProtocol) ReadFieldEnd() error {
+ return p.ParseObjectEnd()
+}
+
+func (p *TJSONProtocol) ReadMapBegin() (keyType TType, valueType TType, size int, e error) {
+ if isNull, e := p.ParseListBegin(); isNull || e != nil {
+ return VOID, VOID, 0, e
+ }
+
+ // read keyType
+ sKeyType, e := p.ReadString()
+ if e != nil {
+ return keyType, valueType, size, e
+ }
+ keyType, e = p.StringToTypeId(sKeyType)
+ if e != nil {
+ return keyType, valueType, size, e
+ }
+
+ // read valueType
+ sValueType, e := p.ReadString()
+ if e != nil {
+ return keyType, valueType, size, e
+ }
+ valueType, e = p.StringToTypeId(sValueType)
+ if e != nil {
+ return keyType, valueType, size, e
+ }
+
+ // read size
+ iSize, err := p.ReadI64()
+ size = int(iSize)
+ return keyType, valueType, size, err
+}
+
+func (p *TJSONProtocol) ReadMapEnd() error {
+ return p.ParseListEnd()
+}
+
+func (p *TJSONProtocol) ReadListBegin() (elemType TType, size int, e error) {
+ return p.ParseElemListBegin()
+}
+
+func (p *TJSONProtocol) ReadListEnd() error {
+ return p.ParseListEnd()
+}
+
+func (p *TJSONProtocol) ReadSetBegin() (elemType TType, size int, e error) {
+ return p.ParseElemListBegin()
+}
+
+func (p *TJSONProtocol) ReadSetEnd() error {
+ return p.ParseListEnd()
+}
+
+func (p *TJSONProtocol) ReadBool() (bool, error) {
+ value, err := p.ReadI32()
+ return (value != 0), err
+}
+
+func (p *TJSONProtocol) ReadByte() (byte, error) {
+ v, err := p.ReadI64()
+ return byte(v), err
+}
+
+func (p *TJSONProtocol) ReadI16() (int16, error) {
+ v, err := p.ReadI64()
+ return int16(v), err
+}
+
+func (p *TJSONProtocol) ReadI32() (int32, error) {
+ v, err := p.ReadI64()
+ return int32(v), err
+}
+
+func (p *TJSONProtocol) ReadI64() (int64, error) {
+ v, _, err := p.ParseI64()
+ return v, err
+}
+
+func (p *TJSONProtocol) ReadDouble() (float64, error) {
+ v, _, err := p.ParseF64()
+ return v, err
+}
+
+func (p *TJSONProtocol) ReadString() (string, error) {
+ var v string
+ if err := p.ParsePreValue(); err != nil {
+ return v, err
+ }
+ b, _ := p.reader.Peek(len(JSON_NULL))
+ if len(b) > 0 && b[0] == JSON_QUOTE {
+ p.reader.ReadByte()
+ value, err := p.ParseStringBody()
+ v = value
+ if err != nil {
+ return v, err
+ }
+ } else if len(b) >= len(JSON_NULL) && string(b[0:len(JSON_NULL)]) == string(JSON_NULL) {
+ _, err := p.reader.Read(b[0:len(JSON_NULL)])
+ if err != nil {
+ return v, NewTProtocolException(err)
+ }
+ } else {
+ e := fmt.Errorf("Expected a JSON string, found %s", string(b))
+ return v, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ return v, p.ParsePostValue()
+}
+
+func (p *TJSONProtocol) ReadBinary() ([]byte, error) {
+ var v []byte
+ if err := p.ParsePreValue(); err != nil {
+ return nil, err
+ }
+ b, _ := p.reader.Peek(len(JSON_NULL))
+ if len(b) > 0 && b[0] == JSON_QUOTE {
+ p.reader.ReadByte()
+ value, err := p.ParseBase64EncodedBody()
+ v = value
+ if err != nil {
+ return v, err
+ }
+ } else if len(b) >= len(JSON_NULL) && string(b[0:len(JSON_NULL)]) == string(JSON_NULL) {
+ _, err := p.reader.Read(b[0:len(JSON_NULL)])
+ if err != nil {
+ return v, NewTProtocolException(err)
+ }
+ } else {
+ e := fmt.Errorf("Expected a JSON string, found %s", string(b))
+ return v, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ return v, p.ParsePostValue()
+}
+
+func (p *TJSONProtocol) Flush() (err error) {
+ err = p.writer.Flush()
+ if err == nil {
+ err = p.trans.Flush()
+ }
+ return NewTProtocolException(err)
+}
+
+func (p *TJSONProtocol) Skip(fieldType TType) (err error) {
+ return SkipDefaultDepth(p, fieldType)
+}
+
+func (p *TJSONProtocol) Transport() TTransport {
+ return p.trans
+}
+
+func (p *TJSONProtocol) OutputElemListBegin(elemType TType, size int) error {
+ if e := p.OutputListBegin(); e != nil {
+ return e
+ }
+ s, e1 := p.TypeIdToString(elemType)
+ if e1 != nil {
+ return e1
+ }
+ if e := p.WriteString(s); e != nil {
+ return e
+ }
+ if e := p.WriteI64(int64(size)); e != nil {
+ return e
+ }
+ return nil
+}
+
+func (p *TJSONProtocol) ParseElemListBegin() (elemType TType, size int, e error) {
+ if isNull, e := p.ParseListBegin(); isNull || e != nil {
+ return VOID, 0, e
+ }
+ sElemType, err := p.ReadString()
+ if err != nil {
+ return VOID, size, err
+ }
+ elemType, err = p.StringToTypeId(sElemType)
+ if err != nil {
+ return elemType, size, err
+ }
+ nSize, err2 := p.ReadI64()
+ size = int(nSize)
+ return elemType, size, err2
+}
+
+func (p *TJSONProtocol) readElemListBegin() (elemType TType, size int, e error) {
+ if isNull, e := p.ParseListBegin(); isNull || e != nil {
+ return VOID, 0, e
+ }
+ sElemType, err := p.ReadString()
+ if err != nil {
+ return VOID, size, err
+ }
+ elemType, err = p.StringToTypeId(sElemType)
+ if err != nil {
+ return elemType, size, err
+ }
+ nSize, err2 := p.ReadI64()
+ size = int(nSize)
+ return elemType, size, err2
+}
+
+func (p *TJSONProtocol) writeElemListBegin(elemType TType, size int) error {
+ if e := p.OutputListBegin(); e != nil {
+ return e
+ }
+ s, e1 := p.TypeIdToString(elemType)
+ if e1 != nil {
+ return e1
+ }
+ if e := p.OutputString(s); e != nil {
+ return e
+ }
+ if e := p.OutputI64(int64(size)); e != nil {
+ return e
+ }
+ return nil
+}
+
+func (p *TJSONProtocol) TypeIdToString(fieldType TType) (string, error) {
+ switch byte(fieldType) {
+ case BOOL:
+ return "tf", nil
+ case BYTE:
+ return "i8", nil
+ case I16:
+ return "i16", nil
+ case I32:
+ return "i32", nil
+ case I64:
+ return "i64", nil
+ case DOUBLE:
+ return "dbl", nil
+ case STRING:
+ return "str", nil
+ case STRUCT:
+ return "rec", nil
+ case MAP:
+ return "map", nil
+ case SET:
+ return "set", nil
+ case LIST:
+ return "lst", nil
+ }
+
+ e := fmt.Errorf("Unknown fieldType: %d", int(fieldType))
+ return "", NewTProtocolExceptionWithType(INVALID_DATA, e)
+}
+
+func (p *TJSONProtocol) StringToTypeId(fieldType string) (TType, error) {
+ switch fieldType {
+ case "tf":
+ return TType(BOOL), nil
+ case "i8":
+ return TType(BYTE), nil
+ case "i16":
+ return TType(I16), nil
+ case "i32":
+ return TType(I32), nil
+ case "i64":
+ return TType(I64), nil
+ case "dbl":
+ return TType(DOUBLE), nil
+ case "str":
+ return TType(STRING), nil
+ case "rec":
+ return TType(STRUCT), nil
+ case "map":
+ return TType(MAP), nil
+ case "set":
+ return TType(SET), nil
+ case "lst":
+ return TType(LIST), nil
+ }
+
+ e := fmt.Errorf("Unknown type identifier: %s", fieldType)
+ return TType(STOP), NewTProtocolExceptionWithType(INVALID_DATA, e)
+}
diff --git a/vendor/github.com/lightstep/thrift/lib/go/thrift/memory_buffer.go b/vendor/github.com/lightstep/thrift/lib/go/thrift/memory_buffer.go
new file mode 100644
index 000000000..c48e08935
--- /dev/null
+++ b/vendor/github.com/lightstep/thrift/lib/go/thrift/memory_buffer.go
@@ -0,0 +1,79 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+import (
+ "bytes"
+)
+
+// Memory buffer-based implementation of the TTransport interface.
+type TMemoryBuffer struct {
+ *bytes.Buffer
+ size int
+}
+
+type TMemoryBufferTransportFactory struct {
+ size int
+}
+
+func (p *TMemoryBufferTransportFactory) GetTransport(trans TTransport) TTransport {
+ if trans != nil {
+ t, ok := trans.(*TMemoryBuffer)
+ if ok && t.size > 0 {
+ return NewTMemoryBufferLen(t.size)
+ }
+ }
+ return NewTMemoryBufferLen(p.size)
+}
+
+func NewTMemoryBufferTransportFactory(size int) *TMemoryBufferTransportFactory {
+ return &TMemoryBufferTransportFactory{size: size}
+}
+
+func NewTMemoryBuffer() *TMemoryBuffer {
+ return &TMemoryBuffer{Buffer: &bytes.Buffer{}, size: 0}
+}
+
+func NewTMemoryBufferLen(size int) *TMemoryBuffer {
+ buf := make([]byte, 0, size)
+ return &TMemoryBuffer{Buffer: bytes.NewBuffer(buf), size: size}
+}
+
+func (p *TMemoryBuffer) IsOpen() bool {
+ return true
+}
+
+func (p *TMemoryBuffer) Open() error {
+ return nil
+}
+
+func (p *TMemoryBuffer) Peek() bool {
+ return p.IsOpen()
+}
+
+func (p *TMemoryBuffer) Close() error {
+ p.Buffer.Reset()
+ return nil
+}
+
+// Flushing a memory buffer is a no-op
+func (p *TMemoryBuffer) Flush() error {
+ return nil
+}
diff --git a/vendor/github.com/lightstep/thrift/lib/go/thrift/messagetype.go b/vendor/github.com/lightstep/thrift/lib/go/thrift/messagetype.go
new file mode 100644
index 000000000..25ab2e98a
--- /dev/null
+++ b/vendor/github.com/lightstep/thrift/lib/go/thrift/messagetype.go
@@ -0,0 +1,31 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+// Message type constants in the Thrift protocol.
+type TMessageType int32
+
+const (
+ INVALID_TMESSAGE_TYPE TMessageType = 0
+ CALL TMessageType = 1
+ REPLY TMessageType = 2
+ EXCEPTION TMessageType = 3
+ ONEWAY TMessageType = 4
+)
diff --git a/vendor/github.com/lightstep/thrift/lib/go/thrift/multiplexed_protocol.go b/vendor/github.com/lightstep/thrift/lib/go/thrift/multiplexed_protocol.go
new file mode 100644
index 000000000..3157e0d5d
--- /dev/null
+++ b/vendor/github.com/lightstep/thrift/lib/go/thrift/multiplexed_protocol.go
@@ -0,0 +1,169 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+import (
+ "fmt"
+ "strings"
+)
+
+/*
+TMultiplexedProtocol is a protocol-independent concrete decorator
+that allows a Thrift client to communicate with a multiplexing Thrift server,
+by prepending the service name to the function name during function calls.
+
+NOTE: THIS IS NOT USED BY SERVERS. On the server, use TMultiplexedProcessor to handle request
+from a multiplexing client.
+
+This example uses a single socket transport to invoke two services:
+
+socket := thrift.NewTSocketFromAddrTimeout(addr, TIMEOUT)
+transport := thrift.NewTFramedTransport(socket)
+protocol := thrift.NewTBinaryProtocolTransport(transport)
+
+mp := thrift.NewTMultiplexedProtocol(protocol, "Calculator")
+service := Calculator.NewCalculatorClient(mp)
+
+mp2 := thrift.NewTMultiplexedProtocol(protocol, "WeatherReport")
+service2 := WeatherReport.NewWeatherReportClient(mp2)
+
+err := transport.Open()
+if err != nil {
+ t.Fatal("Unable to open client socket", err)
+}
+
+fmt.Println(service.Add(2,2))
+fmt.Println(service2.GetTemperature())
+*/
+
+type TMultiplexedProtocol struct {
+ TProtocol
+ serviceName string
+}
+
+const MULTIPLEXED_SEPARATOR = ":"
+
+func NewTMultiplexedProtocol(protocol TProtocol, serviceName string) *TMultiplexedProtocol {
+ return &TMultiplexedProtocol{
+ TProtocol: protocol,
+ serviceName: serviceName,
+ }
+}
+
+func (t *TMultiplexedProtocol) WriteMessageBegin(name string, typeId TMessageType, seqid int32) error {
+ if typeId == CALL || typeId == ONEWAY {
+ return t.TProtocol.WriteMessageBegin(t.serviceName+MULTIPLEXED_SEPARATOR+name, typeId, seqid)
+ } else {
+ return t.TProtocol.WriteMessageBegin(name, typeId, seqid)
+ }
+}
+
+/*
+TMultiplexedProcessor is a TProcessor allowing
+a single TServer to provide multiple services.
+
+To do so, you instantiate the processor and then register additional
+processors with it, as shown in the following example:
+
+var processor = thrift.NewTMultiplexedProcessor()
+
+firstProcessor :=
+processor.RegisterProcessor("FirstService", firstProcessor)
+
+processor.registerProcessor(
+ "Calculator",
+ Calculator.NewCalculatorProcessor(&CalculatorHandler{}),
+)
+
+processor.registerProcessor(
+ "WeatherReport",
+ WeatherReport.NewWeatherReportProcessor(&WeatherReportHandler{}),
+)
+
+serverTransport, err := thrift.NewTServerSocketTimeout(addr, TIMEOUT)
+if err != nil {
+ t.Fatal("Unable to create server socket", err)
+}
+server := thrift.NewTSimpleServer2(processor, serverTransport)
+server.Serve();
+*/
+
+type TMultiplexedProcessor struct {
+ serviceProcessorMap map[string]TProcessor
+ DefaultProcessor TProcessor
+}
+
+func NewTMultiplexedProcessor() *TMultiplexedProcessor {
+ return &TMultiplexedProcessor{
+ serviceProcessorMap: make(map[string]TProcessor),
+ }
+}
+
+func (t *TMultiplexedProcessor) RegisterDefault(processor TProcessor) {
+ t.DefaultProcessor = processor
+}
+
+func (t *TMultiplexedProcessor) RegisterProcessor(name string, processor TProcessor) {
+ if t.serviceProcessorMap == nil {
+ t.serviceProcessorMap = make(map[string]TProcessor)
+ }
+ t.serviceProcessorMap[name] = processor
+}
+
+func (t *TMultiplexedProcessor) Process(in, out TProtocol) (bool, TException) {
+ name, typeId, seqid, err := in.ReadMessageBegin()
+ if err != nil {
+ return false, err
+ }
+ if typeId != CALL && typeId != ONEWAY {
+ return false, fmt.Errorf("Unexpected message type %v", typeId)
+ }
+ //extract the service name
+ v := strings.SplitN(name, MULTIPLEXED_SEPARATOR, 2)
+ if len(v) != 2 {
+ if t.DefaultProcessor != nil {
+ smb := NewStoredMessageProtocol(in, name, typeId, seqid)
+ return t.DefaultProcessor.Process(smb, out)
+ }
+ return false, fmt.Errorf("Service name not found in message name: %s. Did you forget to use a TMultiplexProtocol in your client?", name)
+ }
+ actualProcessor, ok := t.serviceProcessorMap[v[0]]
+ if !ok {
+ return false, fmt.Errorf("Service name not found: %s. Did you forget to call registerProcessor()?", v[0])
+ }
+ smb := NewStoredMessageProtocol(in, v[1], typeId, seqid)
+ return actualProcessor.Process(smb, out)
+}
+
+//Protocol that use stored message for ReadMessageBegin
+type storedMessageProtocol struct {
+ TProtocol
+ name string
+ typeId TMessageType
+ seqid int32
+}
+
+func NewStoredMessageProtocol(protocol TProtocol, name string, typeId TMessageType, seqid int32) *storedMessageProtocol {
+ return &storedMessageProtocol{protocol, name, typeId, seqid}
+}
+
+func (s *storedMessageProtocol) ReadMessageBegin() (name string, typeId TMessageType, seqid int32, err error) {
+ return s.name, s.typeId, s.seqid, nil
+}
diff --git a/vendor/github.com/lightstep/thrift/lib/go/thrift/numeric.go b/vendor/github.com/lightstep/thrift/lib/go/thrift/numeric.go
new file mode 100644
index 000000000..aa8daa9b5
--- /dev/null
+++ b/vendor/github.com/lightstep/thrift/lib/go/thrift/numeric.go
@@ -0,0 +1,164 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+import (
+ "math"
+ "strconv"
+)
+
+type Numeric interface {
+ Int64() int64
+ Int32() int32
+ Int16() int16
+ Byte() byte
+ Int() int
+ Float64() float64
+ Float32() float32
+ String() string
+ isNull() bool
+}
+
+type numeric struct {
+ iValue int64
+ dValue float64
+ sValue string
+ isNil bool
+}
+
+var (
+ INFINITY Numeric
+ NEGATIVE_INFINITY Numeric
+ NAN Numeric
+ ZERO Numeric
+ NUMERIC_NULL Numeric
+)
+
+func NewNumericFromDouble(dValue float64) Numeric {
+ if math.IsInf(dValue, 1) {
+ return INFINITY
+ }
+ if math.IsInf(dValue, -1) {
+ return NEGATIVE_INFINITY
+ }
+ if math.IsNaN(dValue) {
+ return NAN
+ }
+ iValue := int64(dValue)
+ sValue := strconv.FormatFloat(dValue, 'g', 10, 64)
+ isNil := false
+ return &numeric{iValue: iValue, dValue: dValue, sValue: sValue, isNil: isNil}
+}
+
+func NewNumericFromI64(iValue int64) Numeric {
+ dValue := float64(iValue)
+ sValue := string(iValue)
+ isNil := false
+ return &numeric{iValue: iValue, dValue: dValue, sValue: sValue, isNil: isNil}
+}
+
+func NewNumericFromI32(iValue int32) Numeric {
+ dValue := float64(iValue)
+ sValue := string(iValue)
+ isNil := false
+ return &numeric{iValue: int64(iValue), dValue: dValue, sValue: sValue, isNil: isNil}
+}
+
+func NewNumericFromString(sValue string) Numeric {
+ if sValue == INFINITY.String() {
+ return INFINITY
+ }
+ if sValue == NEGATIVE_INFINITY.String() {
+ return NEGATIVE_INFINITY
+ }
+ if sValue == NAN.String() {
+ return NAN
+ }
+ iValue, _ := strconv.ParseInt(sValue, 10, 64)
+ dValue, _ := strconv.ParseFloat(sValue, 64)
+ isNil := len(sValue) == 0
+ return &numeric{iValue: iValue, dValue: dValue, sValue: sValue, isNil: isNil}
+}
+
+func NewNumericFromJSONString(sValue string, isNull bool) Numeric {
+ if isNull {
+ return NewNullNumeric()
+ }
+ if sValue == JSON_INFINITY {
+ return INFINITY
+ }
+ if sValue == JSON_NEGATIVE_INFINITY {
+ return NEGATIVE_INFINITY
+ }
+ if sValue == JSON_NAN {
+ return NAN
+ }
+ iValue, _ := strconv.ParseInt(sValue, 10, 64)
+ dValue, _ := strconv.ParseFloat(sValue, 64)
+ return &numeric{iValue: iValue, dValue: dValue, sValue: sValue, isNil: isNull}
+}
+
+func NewNullNumeric() Numeric {
+ return &numeric{iValue: 0, dValue: 0.0, sValue: "", isNil: true}
+}
+
+func (p *numeric) Int64() int64 {
+ return p.iValue
+}
+
+func (p *numeric) Int32() int32 {
+ return int32(p.iValue)
+}
+
+func (p *numeric) Int16() int16 {
+ return int16(p.iValue)
+}
+
+func (p *numeric) Byte() byte {
+ return byte(p.iValue)
+}
+
+func (p *numeric) Int() int {
+ return int(p.iValue)
+}
+
+func (p *numeric) Float64() float64 {
+ return p.dValue
+}
+
+func (p *numeric) Float32() float32 {
+ return float32(p.dValue)
+}
+
+func (p *numeric) String() string {
+ return p.sValue
+}
+
+func (p *numeric) isNull() bool {
+ return p.isNil
+}
+
+func init() {
+ INFINITY = &numeric{iValue: 0, dValue: math.Inf(1), sValue: "Infinity", isNil: false}
+ NEGATIVE_INFINITY = &numeric{iValue: 0, dValue: math.Inf(-1), sValue: "-Infinity", isNil: false}
+ NAN = &numeric{iValue: 0, dValue: math.NaN(), sValue: "NaN", isNil: false}
+ ZERO = &numeric{iValue: 0, dValue: 0, sValue: "0", isNil: false}
+ NUMERIC_NULL = &numeric{iValue: 0, dValue: 0, sValue: "0", isNil: true}
+}
diff --git a/vendor/github.com/lightstep/thrift/lib/go/thrift/pointerize.go b/vendor/github.com/lightstep/thrift/lib/go/thrift/pointerize.go
new file mode 100644
index 000000000..8d6b2c215
--- /dev/null
+++ b/vendor/github.com/lightstep/thrift/lib/go/thrift/pointerize.go
@@ -0,0 +1,50 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+///////////////////////////////////////////////////////////////////////////////
+// This file is home to helpers that convert from various base types to
+// respective pointer types. This is necessary because Go does not permit
+// references to constants, nor can a pointer type to base type be allocated
+// and initialized in a single expression.
+//
+// E.g., this is not allowed:
+//
+// var ip *int = &5
+//
+// But this *is* allowed:
+//
+// func IntPtr(i int) *int { return &i }
+// var ip *int = IntPtr(5)
+//
+// Since pointers to base types are commonplace as [optional] fields in
+// exported thrift structs, we factor such helpers here.
+///////////////////////////////////////////////////////////////////////////////
+
+func Float32Ptr(v float32) *float32 { return &v }
+func Float64Ptr(v float64) *float64 { return &v }
+func IntPtr(v int) *int { return &v }
+func Int32Ptr(v int32) *int32 { return &v }
+func Int64Ptr(v int64) *int64 { return &v }
+func StringPtr(v string) *string { return &v }
+func Uint32Ptr(v uint32) *uint32 { return &v }
+func Uint64Ptr(v uint64) *uint64 { return &v }
+func BoolPtr(v bool) *bool { return &v }
+func ByteSlicePtr(v []byte) *[]byte { return &v }
diff --git a/vendor/github.com/lightstep/thrift/lib/go/thrift/processor.go b/vendor/github.com/lightstep/thrift/lib/go/thrift/processor.go
new file mode 100644
index 000000000..ca0d3faf2
--- /dev/null
+++ b/vendor/github.com/lightstep/thrift/lib/go/thrift/processor.go
@@ -0,0 +1,30 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+// A processor is a generic object which operates upon an input stream and
+// writes to some output stream.
+type TProcessor interface {
+ Process(in, out TProtocol) (bool, TException)
+}
+
+type TProcessorFunction interface {
+ Process(seqId int32, in, out TProtocol) (bool, TException)
+}
diff --git a/vendor/github.com/lightstep/thrift/lib/go/thrift/processor_factory.go b/vendor/github.com/lightstep/thrift/lib/go/thrift/processor_factory.go
new file mode 100644
index 000000000..9d645df24
--- /dev/null
+++ b/vendor/github.com/lightstep/thrift/lib/go/thrift/processor_factory.go
@@ -0,0 +1,58 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+// The default processor factory just returns a singleton
+// instance.
+type TProcessorFactory interface {
+ GetProcessor(trans TTransport) TProcessor
+}
+
+type tProcessorFactory struct {
+ processor TProcessor
+}
+
+func NewTProcessorFactory(p TProcessor) TProcessorFactory {
+ return &tProcessorFactory{processor: p}
+}
+
+func (p *tProcessorFactory) GetProcessor(trans TTransport) TProcessor {
+ return p.processor
+}
+
+/**
+ * The default processor factory just returns a singleton
+ * instance.
+ */
+type TProcessorFunctionFactory interface {
+ GetProcessorFunction(trans TTransport) TProcessorFunction
+}
+
+type tProcessorFunctionFactory struct {
+ processor TProcessorFunction
+}
+
+func NewTProcessorFunctionFactory(p TProcessorFunction) TProcessorFunctionFactory {
+ return &tProcessorFunctionFactory{processor: p}
+}
+
+func (p *tProcessorFunctionFactory) GetProcessorFunction(trans TTransport) TProcessorFunction {
+ return p.processor
+}
diff --git a/vendor/github.com/lightstep/thrift/lib/go/thrift/protocol.go b/vendor/github.com/lightstep/thrift/lib/go/thrift/protocol.go
new file mode 100644
index 000000000..87ceaad20
--- /dev/null
+++ b/vendor/github.com/lightstep/thrift/lib/go/thrift/protocol.go
@@ -0,0 +1,154 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+const (
+ VERSION_MASK = 0xffff0000
+ VERSION_1 = 0x80010000
+)
+
+type TProtocol interface {
+ WriteMessageBegin(name string, typeId TMessageType, seqid int32) error
+ WriteMessageEnd() error
+ WriteStructBegin(name string) error
+ WriteStructEnd() error
+ WriteFieldBegin(name string, typeId TType, id int16) error
+ WriteFieldEnd() error
+ WriteFieldStop() error
+ WriteMapBegin(keyType TType, valueType TType, size int) error
+ WriteMapEnd() error
+ WriteListBegin(elemType TType, size int) error
+ WriteListEnd() error
+ WriteSetBegin(elemType TType, size int) error
+ WriteSetEnd() error
+ WriteBool(value bool) error
+ WriteByte(value byte) error
+ WriteI16(value int16) error
+ WriteI32(value int32) error
+ WriteI64(value int64) error
+ WriteDouble(value float64) error
+ WriteString(value string) error
+ WriteBinary(value []byte) error
+
+ ReadMessageBegin() (name string, typeId TMessageType, seqid int32, err error)
+ ReadMessageEnd() error
+ ReadStructBegin() (name string, err error)
+ ReadStructEnd() error
+ ReadFieldBegin() (name string, typeId TType, id int16, err error)
+ ReadFieldEnd() error
+ ReadMapBegin() (keyType TType, valueType TType, size int, err error)
+ ReadMapEnd() error
+ ReadListBegin() (elemType TType, size int, err error)
+ ReadListEnd() error
+ ReadSetBegin() (elemType TType, size int, err error)
+ ReadSetEnd() error
+ ReadBool() (value bool, err error)
+ ReadByte() (value byte, err error)
+ ReadI16() (value int16, err error)
+ ReadI32() (value int32, err error)
+ ReadI64() (value int64, err error)
+ ReadDouble() (value float64, err error)
+ ReadString() (value string, err error)
+ ReadBinary() (value []byte, err error)
+
+ Skip(fieldType TType) (err error)
+ Flush() (err error)
+
+ Transport() TTransport
+}
+
+// The maximum recursive depth the skip() function will traverse
+var MaxSkipDepth = 1<<31 - 1
+
+// Skips over the next data element from the provided input TProtocol object.
+func SkipDefaultDepth(prot TProtocol, typeId TType) (err error) {
+ return Skip(prot, typeId, MaxSkipDepth)
+}
+
+// Skips over the next data element from the provided input TProtocol object.
+func Skip(self TProtocol, fieldType TType, maxDepth int) (err error) {
+ switch fieldType {
+ case STOP:
+ return
+ case BOOL:
+ _, err = self.ReadBool()
+ return
+ case BYTE:
+ _, err = self.ReadByte()
+ return
+ case I16:
+ _, err = self.ReadI16()
+ return
+ case I32:
+ _, err = self.ReadI32()
+ return
+ case I64:
+ _, err = self.ReadI64()
+ return
+ case DOUBLE:
+ _, err = self.ReadDouble()
+ return
+ case STRING:
+ _, err = self.ReadString()
+ return
+ case STRUCT:
+ if _, err = self.ReadStructBegin(); err != nil {
+ return err
+ }
+ for {
+ _, typeId, _, _ := self.ReadFieldBegin()
+ if typeId == STOP {
+ break
+ }
+ Skip(self, typeId, maxDepth-1)
+ self.ReadFieldEnd()
+ }
+ return self.ReadStructEnd()
+ case MAP:
+ keyType, valueType, size, err := self.ReadMapBegin()
+ if err != nil {
+ return err
+ }
+ for i := 0; i < size; i++ {
+ Skip(self, keyType, maxDepth-1)
+ self.Skip(valueType)
+ }
+ return self.ReadMapEnd()
+ case SET:
+ elemType, size, err := self.ReadSetBegin()
+ if err != nil {
+ return err
+ }
+ for i := 0; i < size; i++ {
+ Skip(self, elemType, maxDepth-1)
+ }
+ return self.ReadSetEnd()
+ case LIST:
+ elemType, size, err := self.ReadListBegin()
+ if err != nil {
+ return err
+ }
+ for i := 0; i < size; i++ {
+ Skip(self, elemType, maxDepth-1)
+ }
+ return self.ReadListEnd()
+ }
+ return nil
+}
diff --git a/vendor/github.com/lightstep/thrift/lib/go/thrift/protocol_exception.go b/vendor/github.com/lightstep/thrift/lib/go/thrift/protocol_exception.go
new file mode 100644
index 000000000..29ab75d92
--- /dev/null
+++ b/vendor/github.com/lightstep/thrift/lib/go/thrift/protocol_exception.go
@@ -0,0 +1,77 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+import (
+ "encoding/base64"
+)
+
+// Thrift Protocol exception
+type TProtocolException interface {
+ TException
+ TypeId() int
+}
+
+const (
+ UNKNOWN_PROTOCOL_EXCEPTION = 0
+ INVALID_DATA = 1
+ NEGATIVE_SIZE = 2
+ SIZE_LIMIT = 3
+ BAD_VERSION = 4
+ NOT_IMPLEMENTED = 5
+ DEPTH_LIMIT = 6
+)
+
+type tProtocolException struct {
+ typeId int
+ message string
+}
+
+func (p *tProtocolException) TypeId() int {
+ return p.typeId
+}
+
+func (p *tProtocolException) String() string {
+ return p.message
+}
+
+func (p *tProtocolException) Error() string {
+ return p.message
+}
+
+func NewTProtocolException(err error) TProtocolException {
+ if err == nil {
+ return nil
+ }
+ if e, ok := err.(TProtocolException); ok {
+ return e
+ }
+ if _, ok := err.(base64.CorruptInputError); ok {
+ return &tProtocolException{INVALID_DATA, err.Error()}
+ }
+ return &tProtocolException{UNKNOWN_PROTOCOL_EXCEPTION, err.Error()}
+}
+
+func NewTProtocolExceptionWithType(errType int, err error) TProtocolException {
+ if err == nil {
+ return nil
+ }
+ return &tProtocolException{errType, err.Error()}
+}
diff --git a/vendor/github.com/lightstep/thrift/lib/go/thrift/protocol_factory.go b/vendor/github.com/lightstep/thrift/lib/go/thrift/protocol_factory.go
new file mode 100644
index 000000000..c40f796d8
--- /dev/null
+++ b/vendor/github.com/lightstep/thrift/lib/go/thrift/protocol_factory.go
@@ -0,0 +1,25 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+// Factory interface for constructing protocol instances.
+type TProtocolFactory interface {
+ GetProtocol(trans TTransport) TProtocol
+}
diff --git a/vendor/github.com/lightstep/thrift/lib/go/thrift/rich_transport.go b/vendor/github.com/lightstep/thrift/lib/go/thrift/rich_transport.go
new file mode 100644
index 000000000..d7268d99b
--- /dev/null
+++ b/vendor/github.com/lightstep/thrift/lib/go/thrift/rich_transport.go
@@ -0,0 +1,64 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+import "io"
+
+type RichTransport struct {
+ TTransport
+}
+
+// Wraps Transport to provide TRichTransport interface
+func NewTRichTransport(trans TTransport) *RichTransport {
+ return &RichTransport{trans}
+}
+
+func (r *RichTransport) ReadByte() (c byte, err error) {
+ return readByte(r.TTransport)
+}
+
+func (r *RichTransport) WriteByte(c byte) error {
+ return writeByte(r.TTransport, c)
+}
+
+func (r *RichTransport) WriteString(s string) (n int, err error) {
+ return r.Write([]byte(s))
+}
+
+func readByte(r io.Reader) (c byte, err error) {
+ v := [1]byte{0}
+ n, err := r.Read(v[0:1])
+ if n > 0 && (err == nil || err == io.EOF) {
+ return v[0], nil
+ }
+ if n > 0 && err != nil {
+ return v[0], err
+ }
+ if err != nil {
+ return 0, err
+ }
+ return v[0], nil
+}
+
+func writeByte(w io.Writer, c byte) error {
+ v := [1]byte{c}
+ _, err := w.Write(v[0:1])
+ return err
+}
diff --git a/vendor/github.com/lightstep/thrift/lib/go/thrift/serializer.go b/vendor/github.com/lightstep/thrift/lib/go/thrift/serializer.go
new file mode 100644
index 000000000..771222999
--- /dev/null
+++ b/vendor/github.com/lightstep/thrift/lib/go/thrift/serializer.go
@@ -0,0 +1,75 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+type TSerializer struct {
+ Transport *TMemoryBuffer
+ Protocol TProtocol
+}
+
+type TStruct interface {
+ Write(p TProtocol) error
+ Read(p TProtocol) error
+}
+
+func NewTSerializer() *TSerializer {
+ transport := NewTMemoryBufferLen(1024)
+ protocol := NewTBinaryProtocolFactoryDefault().GetProtocol(transport)
+
+ return &TSerializer{
+ transport,
+ protocol}
+}
+
+func (t *TSerializer) WriteString(msg TStruct) (s string, err error) {
+ t.Transport.Reset()
+
+ if err = msg.Write(t.Protocol); err != nil {
+ return
+ }
+
+ if err = t.Protocol.Flush(); err != nil {
+ return
+ }
+ if err = t.Transport.Flush(); err != nil {
+ return
+ }
+
+ return t.Transport.String(), nil
+}
+
+func (t *TSerializer) Write(msg TStruct) (b []byte, err error) {
+ t.Transport.Reset()
+
+ if err = msg.Write(t.Protocol); err != nil {
+ return
+ }
+
+ if err = t.Protocol.Flush(); err != nil {
+ return
+ }
+
+ if err = t.Transport.Flush(); err != nil {
+ return
+ }
+
+ b = append(b, t.Transport.Bytes()...)
+ return
+}
diff --git a/vendor/github.com/lightstep/thrift/lib/go/thrift/serializer_types.go b/vendor/github.com/lightstep/thrift/lib/go/thrift/serializer_types.go
new file mode 100644
index 000000000..efbcde899
--- /dev/null
+++ b/vendor/github.com/lightstep/thrift/lib/go/thrift/serializer_types.go
@@ -0,0 +1,595 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+// Autogenerated by Thrift Compiler (1.0.0-dev)
+// DO NOT EDIT UNLESS YOU ARE SURE THAT YOU KNOW WHAT YOU ARE DOING
+
+/* THE FOLLOWING THRIFT FILE WAS USED TO CREATE THIS
+
+enum TestEnum {
+ FIRST = 1,
+ SECOND = 2,
+ THIRD = 3,
+ FOURTH = 4,
+}
+
+struct TestStruct {
+ 1: bool on,
+ 2: byte b,
+ 3: i16 int16,
+ 4: i32 int32,
+ 5: i64 int64,
+ 6: double d,
+ 7: string st,
+ 8: binary bin,
+ 9: map<string, string> stringMap,
+ 10: list<string> stringList,
+ 11: set<string> stringSet,
+ 12: TestEnum e,
+}
+*/
+
+import (
+ "fmt"
+)
+
+// (needed to ensure safety because of naive import list construction.)
+var _ = ZERO
+var _ = fmt.Printf
+
+var GoUnusedProtection__ int
+
+type TestEnum int64
+
+const (
+ TestEnum_FIRST TestEnum = 1
+ TestEnum_SECOND TestEnum = 2
+ TestEnum_THIRD TestEnum = 3
+ TestEnum_FOURTH TestEnum = 4
+)
+
+func (p TestEnum) String() string {
+ switch p {
+ case TestEnum_FIRST:
+ return "TestEnum_FIRST"
+ case TestEnum_SECOND:
+ return "TestEnum_SECOND"
+ case TestEnum_THIRD:
+ return "TestEnum_THIRD"
+ case TestEnum_FOURTH:
+ return "TestEnum_FOURTH"
+ }
+ return "<UNSET>"
+}
+
+func TestEnumFromString(s string) (TestEnum, error) {
+ switch s {
+ case "TestEnum_FIRST":
+ return TestEnum_FIRST, nil
+ case "TestEnum_SECOND":
+ return TestEnum_SECOND, nil
+ case "TestEnum_THIRD":
+ return TestEnum_THIRD, nil
+ case "TestEnum_FOURTH":
+ return TestEnum_FOURTH, nil
+ }
+ return TestEnum(0), fmt.Errorf("not a valid TestEnum string")
+}
+
+func TestEnumPtr(v TestEnum) *TestEnum { return &v }
+
+type TestStruct struct {
+ On bool `thrift:"on,1"`
+ B int8 `thrift:"b,2"`
+ Int16 int16 `thrift:"int16,3"`
+ Int32 int32 `thrift:"int32,4"`
+ Int64 int64 `thrift:"int64,5"`
+ D float64 `thrift:"d,6"`
+ St string `thrift:"st,7"`
+ Bin []byte `thrift:"bin,8"`
+ StringMap map[string]string `thrift:"stringMap,9"`
+ StringList []string `thrift:"stringList,10"`
+ StringSet map[string]bool `thrift:"stringSet,11"`
+ E TestEnum `thrift:"e,12"`
+}
+
+func NewTestStruct() *TestStruct {
+ rval := &TestStruct{}
+ return rval
+}
+
+func (p *TestStruct) Read(iprot TProtocol) error {
+ if _, err := iprot.ReadStructBegin(); err != nil {
+ return fmt.Errorf("%T read error: %s", p, err)
+ }
+ for {
+ _, fieldTypeId, fieldId, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return fmt.Errorf("%T field %d read error: %s", p, fieldId, err)
+ }
+ if fieldTypeId == STOP {
+ break
+ }
+ switch fieldId {
+ case 1:
+ if err := p.readField1(iprot); err != nil {
+ return err
+ }
+ case 2:
+ if err := p.readField2(iprot); err != nil {
+ return err
+ }
+ case 3:
+ if err := p.readField3(iprot); err != nil {
+ return err
+ }
+ case 4:
+ if err := p.readField4(iprot); err != nil {
+ return err
+ }
+ case 5:
+ if err := p.readField5(iprot); err != nil {
+ return err
+ }
+ case 6:
+ if err := p.readField6(iprot); err != nil {
+ return err
+ }
+ case 7:
+ if err := p.readField7(iprot); err != nil {
+ return err
+ }
+ case 8:
+ if err := p.readField8(iprot); err != nil {
+ return err
+ }
+ case 9:
+ if err := p.readField9(iprot); err != nil {
+ return err
+ }
+ case 10:
+ if err := p.readField10(iprot); err != nil {
+ return err
+ }
+ case 11:
+ if err := p.readField11(iprot); err != nil {
+ return err
+ }
+ case 12:
+ if err := p.readField12(iprot); err != nil {
+ return err
+ }
+ default:
+ if err := iprot.Skip(fieldTypeId); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadFieldEnd(); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadStructEnd(); err != nil {
+ return fmt.Errorf("%T read struct end error: %s", p, err)
+ }
+ return nil
+}
+
+func (p *TestStruct) readField1(iprot TProtocol) error {
+ if v, err := iprot.ReadBool(); err != nil {
+ return fmt.Errorf("error reading field 1: %s", err)
+ } else {
+ p.On = v
+ }
+ return nil
+}
+
+func (p *TestStruct) readField2(iprot TProtocol) error {
+ if v, err := iprot.ReadByte(); err != nil {
+ return fmt.Errorf("error reading field 2: %s", err)
+ } else {
+ temp := int8(v)
+ p.B = temp
+ }
+ return nil
+}
+
+func (p *TestStruct) readField3(iprot TProtocol) error {
+ if v, err := iprot.ReadI16(); err != nil {
+ return fmt.Errorf("error reading field 3: %s", err)
+ } else {
+ p.Int16 = v
+ }
+ return nil
+}
+
+func (p *TestStruct) readField4(iprot TProtocol) error {
+ if v, err := iprot.ReadI32(); err != nil {
+ return fmt.Errorf("error reading field 4: %s", err)
+ } else {
+ p.Int32 = v
+ }
+ return nil
+}
+
+func (p *TestStruct) readField5(iprot TProtocol) error {
+ if v, err := iprot.ReadI64(); err != nil {
+ return fmt.Errorf("error reading field 5: %s", err)
+ } else {
+ p.Int64 = v
+ }
+ return nil
+}
+
+func (p *TestStruct) readField6(iprot TProtocol) error {
+ if v, err := iprot.ReadDouble(); err != nil {
+ return fmt.Errorf("error reading field 6: %s", err)
+ } else {
+ p.D = v
+ }
+ return nil
+}
+
+func (p *TestStruct) readField7(iprot TProtocol) error {
+ if v, err := iprot.ReadString(); err != nil {
+ return fmt.Errorf("error reading field 7: %s", err)
+ } else {
+ p.St = v
+ }
+ return nil
+}
+
+func (p *TestStruct) readField8(iprot TProtocol) error {
+ if v, err := iprot.ReadBinary(); err != nil {
+ return fmt.Errorf("error reading field 8: %s", err)
+ } else {
+ p.Bin = v
+ }
+ return nil
+}
+
+func (p *TestStruct) readField9(iprot TProtocol) error {
+ _, _, size, err := iprot.ReadMapBegin()
+ if err != nil {
+ return fmt.Errorf("error reading map begin: %s")
+ }
+ tMap := make(map[string]string, size)
+ p.StringMap = tMap
+ for i := 0; i < size; i++ {
+ var _key0 string
+ if v, err := iprot.ReadString(); err != nil {
+ return fmt.Errorf("error reading field 0: %s", err)
+ } else {
+ _key0 = v
+ }
+ var _val1 string
+ if v, err := iprot.ReadString(); err != nil {
+ return fmt.Errorf("error reading field 0: %s", err)
+ } else {
+ _val1 = v
+ }
+ p.StringMap[_key0] = _val1
+ }
+ if err := iprot.ReadMapEnd(); err != nil {
+ return fmt.Errorf("error reading map end: %s")
+ }
+ return nil
+}
+
+func (p *TestStruct) readField10(iprot TProtocol) error {
+ _, size, err := iprot.ReadListBegin()
+ if err != nil {
+ return fmt.Errorf("error reading list begin: %s")
+ }
+ tSlice := make([]string, 0, size)
+ p.StringList = tSlice
+ for i := 0; i < size; i++ {
+ var _elem2 string
+ if v, err := iprot.ReadString(); err != nil {
+ return fmt.Errorf("error reading field 0: %s", err)
+ } else {
+ _elem2 = v
+ }
+ p.StringList = append(p.StringList, _elem2)
+ }
+ if err := iprot.ReadListEnd(); err != nil {
+ return fmt.Errorf("error reading list end: %s")
+ }
+ return nil
+}
+
+func (p *TestStruct) readField11(iprot TProtocol) error {
+ _, size, err := iprot.ReadSetBegin()
+ if err != nil {
+ return fmt.Errorf("error reading set begin: %s")
+ }
+ tSet := make(map[string]bool, size)
+ p.StringSet = tSet
+ for i := 0; i < size; i++ {
+ var _elem3 string
+ if v, err := iprot.ReadString(); err != nil {
+ return fmt.Errorf("error reading field 0: %s", err)
+ } else {
+ _elem3 = v
+ }
+ p.StringSet[_elem3] = true
+ }
+ if err := iprot.ReadSetEnd(); err != nil {
+ return fmt.Errorf("error reading set end: %s")
+ }
+ return nil
+}
+
+func (p *TestStruct) readField12(iprot TProtocol) error {
+ if v, err := iprot.ReadI32(); err != nil {
+ return fmt.Errorf("error reading field 12: %s", err)
+ } else {
+ temp := TestEnum(v)
+ p.E = temp
+ }
+ return nil
+}
+
+func (p *TestStruct) Write(oprot TProtocol) error {
+ if err := oprot.WriteStructBegin("TestStruct"); err != nil {
+ return fmt.Errorf("%T write struct begin error: %s", p, err)
+ }
+ if err := p.writeField1(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField2(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField3(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField4(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField5(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField6(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField7(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField8(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField9(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField10(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField11(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField12(oprot); err != nil {
+ return err
+ }
+ if err := oprot.WriteFieldStop(); err != nil {
+ return fmt.Errorf("write field stop error: %s", err)
+ }
+ if err := oprot.WriteStructEnd(); err != nil {
+ return fmt.Errorf("write struct stop error: %s", err)
+ }
+ return nil
+}
+
+func (p *TestStruct) writeField1(oprot TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("on", BOOL, 1); err != nil {
+ return fmt.Errorf("%T write field begin error 1:on: %s", p, err)
+ }
+ if err := oprot.WriteBool(bool(p.On)); err != nil {
+ return fmt.Errorf("%T.on (1) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 1:on: %s", p, err)
+ }
+ return err
+}
+
+func (p *TestStruct) writeField2(oprot TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("b", BYTE, 2); err != nil {
+ return fmt.Errorf("%T write field begin error 2:b: %s", p, err)
+ }
+ if err := oprot.WriteByte(byte(p.B)); err != nil {
+ return fmt.Errorf("%T.b (2) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 2:b: %s", p, err)
+ }
+ return err
+}
+
+func (p *TestStruct) writeField3(oprot TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("int16", I16, 3); err != nil {
+ return fmt.Errorf("%T write field begin error 3:int16: %s", p, err)
+ }
+ if err := oprot.WriteI16(int16(p.Int16)); err != nil {
+ return fmt.Errorf("%T.int16 (3) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 3:int16: %s", p, err)
+ }
+ return err
+}
+
+func (p *TestStruct) writeField4(oprot TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("int32", I32, 4); err != nil {
+ return fmt.Errorf("%T write field begin error 4:int32: %s", p, err)
+ }
+ if err := oprot.WriteI32(int32(p.Int32)); err != nil {
+ return fmt.Errorf("%T.int32 (4) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 4:int32: %s", p, err)
+ }
+ return err
+}
+
+func (p *TestStruct) writeField5(oprot TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("int64", I64, 5); err != nil {
+ return fmt.Errorf("%T write field begin error 5:int64: %s", p, err)
+ }
+ if err := oprot.WriteI64(int64(p.Int64)); err != nil {
+ return fmt.Errorf("%T.int64 (5) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 5:int64: %s", p, err)
+ }
+ return err
+}
+
+func (p *TestStruct) writeField6(oprot TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("d", DOUBLE, 6); err != nil {
+ return fmt.Errorf("%T write field begin error 6:d: %s", p, err)
+ }
+ if err := oprot.WriteDouble(float64(p.D)); err != nil {
+ return fmt.Errorf("%T.d (6) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 6:d: %s", p, err)
+ }
+ return err
+}
+
+func (p *TestStruct) writeField7(oprot TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("st", STRING, 7); err != nil {
+ return fmt.Errorf("%T write field begin error 7:st: %s", p, err)
+ }
+ if err := oprot.WriteString(string(p.St)); err != nil {
+ return fmt.Errorf("%T.st (7) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 7:st: %s", p, err)
+ }
+ return err
+}
+
+func (p *TestStruct) writeField8(oprot TProtocol) (err error) {
+ if p.Bin != nil {
+ if err := oprot.WriteFieldBegin("bin", STRING, 8); err != nil {
+ return fmt.Errorf("%T write field begin error 8:bin: %s", p, err)
+ }
+ if err := oprot.WriteBinary(p.Bin); err != nil {
+ return fmt.Errorf("%T.bin (8) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 8:bin: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *TestStruct) writeField9(oprot TProtocol) (err error) {
+ if p.StringMap != nil {
+ if err := oprot.WriteFieldBegin("stringMap", MAP, 9); err != nil {
+ return fmt.Errorf("%T write field begin error 9:stringMap: %s", p, err)
+ }
+ if err := oprot.WriteMapBegin(STRING, STRING, len(p.StringMap)); err != nil {
+ return fmt.Errorf("error writing map begin: %s")
+ }
+ for k, v := range p.StringMap {
+ if err := oprot.WriteString(string(k)); err != nil {
+ return fmt.Errorf("%T. (0) field write error: %s", p, err)
+ }
+ if err := oprot.WriteString(string(v)); err != nil {
+ return fmt.Errorf("%T. (0) field write error: %s", p, err)
+ }
+ }
+ if err := oprot.WriteMapEnd(); err != nil {
+ return fmt.Errorf("error writing map end: %s")
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 9:stringMap: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *TestStruct) writeField10(oprot TProtocol) (err error) {
+ if p.StringList != nil {
+ if err := oprot.WriteFieldBegin("stringList", LIST, 10); err != nil {
+ return fmt.Errorf("%T write field begin error 10:stringList: %s", p, err)
+ }
+ if err := oprot.WriteListBegin(STRING, len(p.StringList)); err != nil {
+ return fmt.Errorf("error writing list begin: %s")
+ }
+ for _, v := range p.StringList {
+ if err := oprot.WriteString(string(v)); err != nil {
+ return fmt.Errorf("%T. (0) field write error: %s", p, err)
+ }
+ }
+ if err := oprot.WriteListEnd(); err != nil {
+ return fmt.Errorf("error writing list end: %s")
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 10:stringList: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *TestStruct) writeField11(oprot TProtocol) (err error) {
+ if p.StringSet != nil {
+ if err := oprot.WriteFieldBegin("stringSet", SET, 11); err != nil {
+ return fmt.Errorf("%T write field begin error 11:stringSet: %s", p, err)
+ }
+ if err := oprot.WriteSetBegin(STRING, len(p.StringSet)); err != nil {
+ return fmt.Errorf("error writing set begin: %s")
+ }
+ for v, _ := range p.StringSet {
+ if err := oprot.WriteString(string(v)); err != nil {
+ return fmt.Errorf("%T. (0) field write error: %s", p, err)
+ }
+ }
+ if err := oprot.WriteSetEnd(); err != nil {
+ return fmt.Errorf("error writing set end: %s")
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 11:stringSet: %s", p, err)
+ }
+ }
+ return err
+}
+
+func (p *TestStruct) writeField12(oprot TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("e", I32, 12); err != nil {
+ return fmt.Errorf("%T write field begin error 12:e: %s", p, err)
+ }
+ if err := oprot.WriteI32(int32(p.E)); err != nil {
+ return fmt.Errorf("%T.e (12) field write error: %s", p, err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return fmt.Errorf("%T write field end error 12:e: %s", p, err)
+ }
+ return err
+}
+
+func (p *TestStruct) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return fmt.Sprintf("TestStruct(%+v)", *p)
+}
diff --git a/vendor/github.com/lightstep/thrift/lib/go/thrift/server.go b/vendor/github.com/lightstep/thrift/lib/go/thrift/server.go
new file mode 100644
index 000000000..f813fa353
--- /dev/null
+++ b/vendor/github.com/lightstep/thrift/lib/go/thrift/server.go
@@ -0,0 +1,35 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+type TServer interface {
+ ProcessorFactory() TProcessorFactory
+ ServerTransport() TServerTransport
+ InputTransportFactory() TTransportFactory
+ OutputTransportFactory() TTransportFactory
+ InputProtocolFactory() TProtocolFactory
+ OutputProtocolFactory() TProtocolFactory
+
+ // Starts the server
+ Serve() error
+ // Stops the server. This is optional on a per-implementation basis. Not
+ // all servers are required to be cleanly stoppable.
+ Stop() error
+}
diff --git a/vendor/github.com/lightstep/thrift/lib/go/thrift/server_socket.go b/vendor/github.com/lightstep/thrift/lib/go/thrift/server_socket.go
new file mode 100644
index 000000000..936eb2e7d
--- /dev/null
+++ b/vendor/github.com/lightstep/thrift/lib/go/thrift/server_socket.go
@@ -0,0 +1,127 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+import (
+ "net"
+ "sync"
+ "time"
+)
+
+type TServerSocket struct {
+ listener net.Listener
+ addr net.Addr
+ clientTimeout time.Duration
+
+ // Protects the interrupted value to make it thread safe.
+ mu sync.RWMutex
+ interrupted bool
+
+ //Size of buffer to use for socket. Defaults to 1024.
+ //Set to 0 to disable bufferring server transport altogether.
+ BufferSize int
+}
+
+func NewTServerSocket(listenAddr string) (*TServerSocket, error) {
+ return NewTServerSocketTimeout(listenAddr, 0)
+}
+
+func NewTServerSocketTimeout(listenAddr string, clientTimeout time.Duration) (*TServerSocket, error) {
+ addr, err := net.ResolveTCPAddr("tcp", listenAddr)
+ if err != nil {
+ return nil, err
+ }
+ return &TServerSocket{addr: addr, clientTimeout: clientTimeout, BufferSize: 1024}, nil
+}
+
+func (p *TServerSocket) Listen() error {
+ if p.IsListening() {
+ return nil
+ }
+ l, err := net.Listen(p.addr.Network(), p.addr.String())
+ if err != nil {
+ return err
+ }
+ p.listener = l
+ return nil
+}
+
+func (p *TServerSocket) Accept() (TTransport, error) {
+ p.mu.RLock()
+ interrupted := p.interrupted
+ p.mu.RUnlock()
+
+ if interrupted {
+ return nil, errTransportInterrupted
+ }
+ if p.listener == nil {
+ return nil, NewTTransportException(NOT_OPEN, "No underlying server socket")
+ }
+ conn, err := p.listener.Accept()
+ if err != nil {
+ return nil, NewTTransportExceptionFromError(err)
+ }
+ var trans TTransport
+ trans = NewTSocketFromConnTimeout(conn, p.clientTimeout)
+ if p.BufferSize != 0 {
+ trans = NewTBufferedTransport(trans, p.BufferSize)
+ }
+ return trans, nil
+}
+
+// Checks whether the socket is listening.
+func (p *TServerSocket) IsListening() bool {
+ return p.listener != nil
+}
+
+// Connects the socket, creating a new socket object if necessary.
+func (p *TServerSocket) Open() error {
+ if p.IsListening() {
+ return NewTTransportException(ALREADY_OPEN, "Server socket already open")
+ }
+ if l, err := net.Listen(p.addr.Network(), p.addr.String()); err != nil {
+ return err
+ } else {
+ p.listener = l
+ }
+ return nil
+}
+
+func (p *TServerSocket) Addr() net.Addr {
+ return p.addr
+}
+
+func (p *TServerSocket) Close() error {
+ defer func() {
+ p.listener = nil
+ }()
+ if p.IsListening() {
+ return p.listener.Close()
+ }
+ return nil
+}
+
+func (p *TServerSocket) Interrupt() error {
+ p.mu.Lock()
+ p.interrupted = true
+ p.mu.Unlock()
+
+ return nil
+}
diff --git a/vendor/github.com/lightstep/thrift/lib/go/thrift/server_transport.go b/vendor/github.com/lightstep/thrift/lib/go/thrift/server_transport.go
new file mode 100644
index 000000000..51c40b64a
--- /dev/null
+++ b/vendor/github.com/lightstep/thrift/lib/go/thrift/server_transport.go
@@ -0,0 +1,34 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+// Server transport. Object which provides client transports.
+type TServerTransport interface {
+ Listen() error
+ Accept() (TTransport, error)
+ Close() error
+
+ // Optional method implementation. This signals to the server transport
+ // that it should break out of any accept() or listen() that it is currently
+ // blocked on. This method, if implemented, MUST be thread safe, as it may
+ // be called from a different thread context than the other TServerTransport
+ // methods.
+ Interrupt() error
+}
diff --git a/vendor/github.com/lightstep/thrift/lib/go/thrift/simple_json_protocol.go b/vendor/github.com/lightstep/thrift/lib/go/thrift/simple_json_protocol.go
new file mode 100644
index 000000000..7a1ed8877
--- /dev/null
+++ b/vendor/github.com/lightstep/thrift/lib/go/thrift/simple_json_protocol.go
@@ -0,0 +1,1250 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+import (
+ "bufio"
+ "bytes"
+ "encoding/base64"
+ "encoding/json"
+ "fmt"
+ "io"
+ "math"
+ "strconv"
+)
+
+type _ParseContext int
+
+const (
+ _CONTEXT_IN_TOPLEVEL _ParseContext = 1
+ _CONTEXT_IN_LIST_FIRST _ParseContext = 2
+ _CONTEXT_IN_LIST _ParseContext = 3
+ _CONTEXT_IN_OBJECT_FIRST _ParseContext = 4
+ _CONTEXT_IN_OBJECT_NEXT_KEY _ParseContext = 5
+ _CONTEXT_IN_OBJECT_NEXT_VALUE _ParseContext = 6
+)
+
+func (p _ParseContext) String() string {
+ switch p {
+ case _CONTEXT_IN_TOPLEVEL:
+ return "TOPLEVEL"
+ case _CONTEXT_IN_LIST_FIRST:
+ return "LIST-FIRST"
+ case _CONTEXT_IN_LIST:
+ return "LIST"
+ case _CONTEXT_IN_OBJECT_FIRST:
+ return "OBJECT-FIRST"
+ case _CONTEXT_IN_OBJECT_NEXT_KEY:
+ return "OBJECT-NEXT-KEY"
+ case _CONTEXT_IN_OBJECT_NEXT_VALUE:
+ return "OBJECT-NEXT-VALUE"
+ }
+ return "UNKNOWN-PARSE-CONTEXT"
+}
+
+// JSON protocol implementation for thrift.
+//
+// This protocol produces/consumes a simple output format
+// suitable for parsing by scripting languages. It should not be
+// confused with the full-featured TJSONProtocol.
+//
+type TSimpleJSONProtocol struct {
+ trans TTransport
+
+ parseContextStack []int
+ dumpContext []int
+
+ writer *bufio.Writer
+ reader *bufio.Reader
+}
+
+// Constructor
+func NewTSimpleJSONProtocol(t TTransport) *TSimpleJSONProtocol {
+ v := &TSimpleJSONProtocol{trans: t,
+ writer: bufio.NewWriter(t),
+ reader: bufio.NewReader(t),
+ }
+ v.parseContextStack = append(v.parseContextStack, int(_CONTEXT_IN_TOPLEVEL))
+ v.dumpContext = append(v.dumpContext, int(_CONTEXT_IN_TOPLEVEL))
+ return v
+}
+
+// Factory
+type TSimpleJSONProtocolFactory struct{}
+
+func (p *TSimpleJSONProtocolFactory) GetProtocol(trans TTransport) TProtocol {
+ return NewTSimpleJSONProtocol(trans)
+}
+
+func NewTSimpleJSONProtocolFactory() *TSimpleJSONProtocolFactory {
+ return &TSimpleJSONProtocolFactory{}
+}
+
+var (
+ JSON_COMMA []byte
+ JSON_COLON []byte
+ JSON_LBRACE []byte
+ JSON_RBRACE []byte
+ JSON_LBRACKET []byte
+ JSON_RBRACKET []byte
+ JSON_QUOTE byte
+ JSON_QUOTE_BYTES []byte
+ JSON_NULL []byte
+ JSON_TRUE []byte
+ JSON_FALSE []byte
+ JSON_INFINITY string
+ JSON_NEGATIVE_INFINITY string
+ JSON_NAN string
+ JSON_INFINITY_BYTES []byte
+ JSON_NEGATIVE_INFINITY_BYTES []byte
+ JSON_NAN_BYTES []byte
+ json_nonbase_map_elem_bytes []byte
+)
+
+func init() {
+ JSON_COMMA = []byte{','}
+ JSON_COLON = []byte{':'}
+ JSON_LBRACE = []byte{'{'}
+ JSON_RBRACE = []byte{'}'}
+ JSON_LBRACKET = []byte{'['}
+ JSON_RBRACKET = []byte{']'}
+ JSON_QUOTE = '"'
+ JSON_QUOTE_BYTES = []byte{'"'}
+ JSON_NULL = []byte{'n', 'u', 'l', 'l'}
+ JSON_TRUE = []byte{'t', 'r', 'u', 'e'}
+ JSON_FALSE = []byte{'f', 'a', 'l', 's', 'e'}
+ JSON_INFINITY = "Infinity"
+ JSON_NEGATIVE_INFINITY = "-Infinity"
+ JSON_NAN = "NaN"
+ JSON_INFINITY_BYTES = []byte{'I', 'n', 'f', 'i', 'n', 'i', 't', 'y'}
+ JSON_NEGATIVE_INFINITY_BYTES = []byte{'-', 'I', 'n', 'f', 'i', 'n', 'i', 't', 'y'}
+ JSON_NAN_BYTES = []byte{'N', 'a', 'N'}
+ json_nonbase_map_elem_bytes = []byte{']', ',', '['}
+}
+
+func jsonQuote(s string) string {
+ b, _ := json.Marshal(s)
+ s1 := string(b)
+ return s1
+}
+
+func jsonUnquote(s string) (string, bool) {
+ s1 := new(string)
+ err := json.Unmarshal([]byte(s), s1)
+ return *s1, err == nil
+}
+
+func mismatch(expected, actual string) error {
+ return fmt.Errorf("Expected '%s' but found '%s' while parsing JSON.", expected, actual)
+}
+
+func (p *TSimpleJSONProtocol) WriteMessageBegin(name string, typeId TMessageType, seqId int32) error {
+ if e := p.OutputListBegin(); e != nil {
+ return e
+ }
+ if e := p.WriteString(name); e != nil {
+ return e
+ }
+ if e := p.WriteByte(byte(typeId)); e != nil {
+ return e
+ }
+ if e := p.WriteI32(seqId); e != nil {
+ return e
+ }
+ return nil
+}
+
+func (p *TSimpleJSONProtocol) WriteMessageEnd() error {
+ return p.OutputListEnd()
+}
+
+func (p *TSimpleJSONProtocol) WriteStructBegin(name string) error {
+ if e := p.OutputObjectBegin(); e != nil {
+ return e
+ }
+ return nil
+}
+
+func (p *TSimpleJSONProtocol) WriteStructEnd() error {
+ return p.OutputObjectEnd()
+}
+
+func (p *TSimpleJSONProtocol) WriteFieldBegin(name string, typeId TType, id int16) error {
+ if e := p.WriteString(name); e != nil {
+ return e
+ }
+ return nil
+}
+
+func (p *TSimpleJSONProtocol) WriteFieldEnd() error {
+ //return p.OutputListEnd()
+ return nil
+}
+
+func (p *TSimpleJSONProtocol) WriteFieldStop() error { return nil }
+
+func (p *TSimpleJSONProtocol) WriteMapBegin(keyType TType, valueType TType, size int) error {
+ if e := p.OutputListBegin(); e != nil {
+ return e
+ }
+ if e := p.WriteByte(byte(keyType)); e != nil {
+ return e
+ }
+ if e := p.WriteByte(byte(valueType)); e != nil {
+ return e
+ }
+ return p.WriteI32(int32(size))
+}
+
+func (p *TSimpleJSONProtocol) WriteMapEnd() error {
+ return p.OutputListEnd()
+}
+
+func (p *TSimpleJSONProtocol) WriteListBegin(elemType TType, size int) error {
+ return p.OutputElemListBegin(elemType, size)
+}
+
+func (p *TSimpleJSONProtocol) WriteListEnd() error {
+ return p.OutputListEnd()
+}
+
+func (p *TSimpleJSONProtocol) WriteSetBegin(elemType TType, size int) error {
+ return p.OutputElemListBegin(elemType, size)
+}
+
+func (p *TSimpleJSONProtocol) WriteSetEnd() error {
+ return p.OutputListEnd()
+}
+
+func (p *TSimpleJSONProtocol) WriteBool(b bool) error {
+ return p.OutputBool(b)
+}
+
+func (p *TSimpleJSONProtocol) WriteByte(b byte) error {
+ return p.WriteI32(int32(b))
+}
+
+func (p *TSimpleJSONProtocol) WriteI16(v int16) error {
+ return p.WriteI32(int32(v))
+}
+
+func (p *TSimpleJSONProtocol) WriteI32(v int32) error {
+ return p.OutputI64(int64(v))
+}
+
+func (p *TSimpleJSONProtocol) WriteI64(v int64) error {
+ return p.OutputI64(int64(v))
+}
+
+func (p *TSimpleJSONProtocol) WriteDouble(v float64) error {
+ return p.OutputF64(v)
+}
+
+func (p *TSimpleJSONProtocol) WriteString(v string) error {
+ return p.OutputString(v)
+}
+
+func (p *TSimpleJSONProtocol) WriteBinary(v []byte) error {
+ // JSON library only takes in a string,
+ // not an arbitrary byte array, to ensure bytes are transmitted
+ // efficiently we must convert this into a valid JSON string
+ // therefore we use base64 encoding to avoid excessive escaping/quoting
+ if e := p.OutputPreValue(); e != nil {
+ return e
+ }
+ if _, e := p.writer.Write(JSON_QUOTE_BYTES); e != nil {
+ return NewTProtocolException(e)
+ }
+ writer := base64.NewEncoder(base64.StdEncoding, p.writer)
+ if _, e := writer.Write(v); e != nil {
+ return NewTProtocolException(e)
+ }
+ if e := writer.Close(); e != nil {
+ return NewTProtocolException(e)
+ }
+ if _, e := p.writer.Write(JSON_QUOTE_BYTES); e != nil {
+ return NewTProtocolException(e)
+ }
+ return p.OutputPostValue()
+}
+
+// Reading methods.
+
+func (p *TSimpleJSONProtocol) ReadMessageBegin() (name string, typeId TMessageType, seqId int32, err error) {
+ if isNull, err := p.ParseListBegin(); isNull || err != nil {
+ return name, typeId, seqId, err
+ }
+ if name, err = p.ReadString(); err != nil {
+ return name, typeId, seqId, err
+ }
+ bTypeId, err := p.ReadByte()
+ typeId = TMessageType(bTypeId)
+ if err != nil {
+ return name, typeId, seqId, err
+ }
+ if seqId, err = p.ReadI32(); err != nil {
+ return name, typeId, seqId, err
+ }
+ return name, typeId, seqId, nil
+}
+
+func (p *TSimpleJSONProtocol) ReadMessageEnd() error {
+ return p.ParseListEnd()
+}
+
+func (p *TSimpleJSONProtocol) ReadStructBegin() (name string, err error) {
+ _, err = p.ParseObjectStart()
+ return "", err
+}
+
+func (p *TSimpleJSONProtocol) ReadStructEnd() error {
+ return p.ParseObjectEnd()
+}
+
+func (p *TSimpleJSONProtocol) ReadFieldBegin() (string, TType, int16, error) {
+ if err := p.ParsePreValue(); err != nil {
+ return "", STOP, 0, err
+ }
+ b, _ := p.reader.Peek(1)
+ if len(b) > 0 {
+ switch b[0] {
+ case JSON_RBRACE[0]:
+ return "", STOP, 0, nil
+ case JSON_QUOTE:
+ p.reader.ReadByte()
+ name, err := p.ParseStringBody()
+ // simplejson is not meant to be read back into thrift
+ // - see http://wiki.apache.org/thrift/ThriftUsageJava
+ // - use JSON instead
+ if err != nil {
+ return name, STOP, 0, err
+ }
+ return name, STOP, -1, p.ParsePostValue()
+ /*
+ if err = p.ParsePostValue(); err != nil {
+ return name, STOP, 0, err
+ }
+ if isNull, err := p.ParseListBegin(); isNull || err != nil {
+ return name, STOP, 0, err
+ }
+ bType, err := p.ReadByte()
+ thetype := TType(bType)
+ if err != nil {
+ return name, thetype, 0, err
+ }
+ id, err := p.ReadI16()
+ return name, thetype, id, err
+ */
+ }
+ e := fmt.Errorf("Expected \"}\" or '\"', but found: '%s'", string(b))
+ return "", STOP, 0, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ return "", STOP, 0, NewTProtocolException(io.EOF)
+}
+
+func (p *TSimpleJSONProtocol) ReadFieldEnd() error {
+ return nil
+ //return p.ParseListEnd()
+}
+
+func (p *TSimpleJSONProtocol) ReadMapBegin() (keyType TType, valueType TType, size int, e error) {
+ if isNull, e := p.ParseListBegin(); isNull || e != nil {
+ return VOID, VOID, 0, e
+ }
+
+ // read keyType
+ bKeyType, e := p.ReadByte()
+ keyType = TType(bKeyType)
+ if e != nil {
+ return keyType, valueType, size, e
+ }
+
+ // read valueType
+ bValueType, e := p.ReadByte()
+ valueType = TType(bValueType)
+ if e != nil {
+ return keyType, valueType, size, e
+ }
+
+ // read size
+ iSize, err := p.ReadI64()
+ size = int(iSize)
+ return keyType, valueType, size, err
+}
+
+func (p *TSimpleJSONProtocol) ReadMapEnd() error {
+ return p.ParseListEnd()
+}
+
+func (p *TSimpleJSONProtocol) ReadListBegin() (elemType TType, size int, e error) {
+ return p.ParseElemListBegin()
+}
+
+func (p *TSimpleJSONProtocol) ReadListEnd() error {
+ return p.ParseListEnd()
+}
+
+func (p *TSimpleJSONProtocol) ReadSetBegin() (elemType TType, size int, e error) {
+ return p.ParseElemListBegin()
+}
+
+func (p *TSimpleJSONProtocol) ReadSetEnd() error {
+ return p.ParseListEnd()
+}
+
+func (p *TSimpleJSONProtocol) ReadBool() (bool, error) {
+ var value bool
+ if err := p.ParsePreValue(); err != nil {
+ return value, err
+ }
+ b, _ := p.reader.Peek(len(JSON_TRUE))
+ if len(b) > 0 {
+ switch b[0] {
+ case JSON_TRUE[0]:
+ if string(b) == string(JSON_TRUE) {
+ p.reader.Read(b[0:len(JSON_TRUE)])
+ value = true
+ } else {
+ e := fmt.Errorf("Expected \"true\" but found: %s", string(b))
+ return value, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ break
+ case JSON_FALSE[0]:
+ if string(b) == string(JSON_FALSE[:len(b)]) {
+ p.reader.Read(b[0:len(JSON_FALSE)])
+ value = false
+ } else {
+ e := fmt.Errorf("Expected \"false\" but found: %s", string(b))
+ return value, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ break
+ case JSON_NULL[0]:
+ if string(b) == string(JSON_NULL) {
+ p.reader.Read(b[0:len(JSON_NULL)])
+ value = false
+ } else {
+ e := fmt.Errorf("Expected \"null\" but found: %s", string(b))
+ return value, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ default:
+ e := fmt.Errorf("Expected \"true\", \"false\", or \"null\" but found: %s", string(b))
+ return value, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ }
+ return value, p.ParsePostValue()
+}
+
+func (p *TSimpleJSONProtocol) ReadByte() (byte, error) {
+ v, err := p.ReadI64()
+ return byte(v), err
+}
+
+func (p *TSimpleJSONProtocol) ReadI16() (int16, error) {
+ v, err := p.ReadI64()
+ return int16(v), err
+}
+
+func (p *TSimpleJSONProtocol) ReadI32() (int32, error) {
+ v, err := p.ReadI64()
+ return int32(v), err
+}
+
+func (p *TSimpleJSONProtocol) ReadI64() (int64, error) {
+ v, _, err := p.ParseI64()
+ return v, err
+}
+
+func (p *TSimpleJSONProtocol) ReadDouble() (float64, error) {
+ v, _, err := p.ParseF64()
+ return v, err
+}
+
+func (p *TSimpleJSONProtocol) ReadString() (string, error) {
+ var v string
+ if err := p.ParsePreValue(); err != nil {
+ return v, err
+ }
+ var b []byte
+ b, _ = p.reader.Peek(len(JSON_NULL))
+ if len(b) > 0 && b[0] == JSON_QUOTE {
+ p.reader.ReadByte()
+ value, err := p.ParseStringBody()
+ v = value
+ if err != nil {
+ return v, err
+ }
+ } else if len(b) >= len(JSON_NULL) && string(b[0:len(JSON_NULL)]) == string(JSON_NULL) {
+ _, err := p.reader.Read(b[0:len(JSON_NULL)])
+ if err != nil {
+ return v, NewTProtocolException(err)
+ }
+ } else {
+ e := fmt.Errorf("Expected a JSON string, found %s", string(b))
+ return v, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ return v, p.ParsePostValue()
+}
+
+func (p *TSimpleJSONProtocol) ReadBinary() ([]byte, error) {
+ var v []byte
+ if err := p.ParsePreValue(); err != nil {
+ return nil, err
+ }
+ b, _ := p.reader.Peek(len(JSON_NULL))
+ if len(b) > 0 && b[0] == JSON_QUOTE {
+ p.reader.ReadByte()
+ value, err := p.ParseBase64EncodedBody()
+ v = value
+ if err != nil {
+ return v, err
+ }
+ } else if len(b) >= len(JSON_NULL) && string(b[0:len(JSON_NULL)]) == string(JSON_NULL) {
+ _, err := p.reader.Read(b[0:len(JSON_NULL)])
+ if err != nil {
+ return v, NewTProtocolException(err)
+ }
+ } else {
+ e := fmt.Errorf("Expected a JSON string, found %s", string(b))
+ return v, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ return v, p.ParsePostValue()
+}
+
+func (p *TSimpleJSONProtocol) Flush() (err error) {
+ return NewTProtocolException(p.writer.Flush())
+}
+
+func (p *TSimpleJSONProtocol) Skip(fieldType TType) (err error) {
+ return SkipDefaultDepth(p, fieldType)
+}
+
+func (p *TSimpleJSONProtocol) Transport() TTransport {
+ return p.trans
+}
+
+func (p *TSimpleJSONProtocol) OutputPreValue() error {
+ cxt := _ParseContext(p.dumpContext[len(p.dumpContext)-1])
+ switch cxt {
+ case _CONTEXT_IN_LIST, _CONTEXT_IN_OBJECT_NEXT_KEY:
+ if _, e := p.writer.Write(JSON_COMMA); e != nil {
+ return NewTProtocolException(e)
+ }
+ break
+ case _CONTEXT_IN_OBJECT_NEXT_VALUE:
+ if _, e := p.writer.Write(JSON_COLON); e != nil {
+ return NewTProtocolException(e)
+ }
+ break
+ }
+ return nil
+}
+
+func (p *TSimpleJSONProtocol) OutputPostValue() error {
+ cxt := _ParseContext(p.dumpContext[len(p.dumpContext)-1])
+ switch cxt {
+ case _CONTEXT_IN_LIST_FIRST:
+ p.dumpContext = p.dumpContext[:len(p.dumpContext)-1]
+ p.dumpContext = append(p.dumpContext, int(_CONTEXT_IN_LIST))
+ break
+ case _CONTEXT_IN_OBJECT_FIRST:
+ p.dumpContext = p.dumpContext[:len(p.dumpContext)-1]
+ p.dumpContext = append(p.dumpContext, int(_CONTEXT_IN_OBJECT_NEXT_VALUE))
+ break
+ case _CONTEXT_IN_OBJECT_NEXT_KEY:
+ p.dumpContext = p.dumpContext[:len(p.dumpContext)-1]
+ p.dumpContext = append(p.dumpContext, int(_CONTEXT_IN_OBJECT_NEXT_VALUE))
+ break
+ case _CONTEXT_IN_OBJECT_NEXT_VALUE:
+ p.dumpContext = p.dumpContext[:len(p.dumpContext)-1]
+ p.dumpContext = append(p.dumpContext, int(_CONTEXT_IN_OBJECT_NEXT_KEY))
+ break
+ }
+ return nil
+}
+
+func (p *TSimpleJSONProtocol) OutputBool(value bool) error {
+ if e := p.OutputPreValue(); e != nil {
+ return e
+ }
+ var v string
+ if value {
+ v = string(JSON_TRUE)
+ } else {
+ v = string(JSON_FALSE)
+ }
+ switch _ParseContext(p.dumpContext[len(p.dumpContext)-1]) {
+ case _CONTEXT_IN_OBJECT_FIRST, _CONTEXT_IN_OBJECT_NEXT_KEY:
+ v = jsonQuote(v)
+ default:
+ }
+ if e := p.OutputStringData(v); e != nil {
+ return e
+ }
+ return p.OutputPostValue()
+}
+
+func (p *TSimpleJSONProtocol) OutputNull() error {
+ if e := p.OutputPreValue(); e != nil {
+ return e
+ }
+ if _, e := p.writer.Write(JSON_NULL); e != nil {
+ return NewTProtocolException(e)
+ }
+ return p.OutputPostValue()
+}
+
+func (p *TSimpleJSONProtocol) OutputF64(value float64) error {
+ if e := p.OutputPreValue(); e != nil {
+ return e
+ }
+ var v string
+ if math.IsNaN(value) {
+ v = string(JSON_QUOTE) + JSON_NAN + string(JSON_QUOTE)
+ } else if math.IsInf(value, 1) {
+ v = string(JSON_QUOTE) + JSON_INFINITY + string(JSON_QUOTE)
+ } else if math.IsInf(value, -1) {
+ v = string(JSON_QUOTE) + JSON_NEGATIVE_INFINITY + string(JSON_QUOTE)
+ } else {
+ v = strconv.FormatFloat(value, 'g', -1, 64)
+ switch _ParseContext(p.dumpContext[len(p.dumpContext)-1]) {
+ case _CONTEXT_IN_OBJECT_FIRST, _CONTEXT_IN_OBJECT_NEXT_KEY:
+ v = string(JSON_QUOTE) + v + string(JSON_QUOTE)
+ default:
+ }
+ }
+ if e := p.OutputStringData(v); e != nil {
+ return e
+ }
+ return p.OutputPostValue()
+}
+
+func (p *TSimpleJSONProtocol) OutputI64(value int64) error {
+ if e := p.OutputPreValue(); e != nil {
+ return e
+ }
+ v := strconv.FormatInt(value, 10)
+ switch _ParseContext(p.dumpContext[len(p.dumpContext)-1]) {
+ case _CONTEXT_IN_OBJECT_FIRST, _CONTEXT_IN_OBJECT_NEXT_KEY:
+ v = jsonQuote(v)
+ default:
+ }
+ if e := p.OutputStringData(v); e != nil {
+ return e
+ }
+ return p.OutputPostValue()
+}
+
+func (p *TSimpleJSONProtocol) OutputString(s string) error {
+ if e := p.OutputPreValue(); e != nil {
+ return e
+ }
+ if e := p.OutputStringData(jsonQuote(s)); e != nil {
+ return e
+ }
+ return p.OutputPostValue()
+}
+
+func (p *TSimpleJSONProtocol) OutputStringData(s string) error {
+ _, e := p.writer.Write([]byte(s))
+ return NewTProtocolException(e)
+}
+
+func (p *TSimpleJSONProtocol) OutputObjectBegin() error {
+ if e := p.OutputPreValue(); e != nil {
+ return e
+ }
+ if _, e := p.writer.Write(JSON_LBRACE); e != nil {
+ return NewTProtocolException(e)
+ }
+ p.dumpContext = append(p.dumpContext, int(_CONTEXT_IN_OBJECT_FIRST))
+ return nil
+}
+
+func (p *TSimpleJSONProtocol) OutputObjectEnd() error {
+ if _, e := p.writer.Write(JSON_RBRACE); e != nil {
+ return NewTProtocolException(e)
+ }
+ p.dumpContext = p.dumpContext[:len(p.dumpContext)-1]
+ if e := p.OutputPostValue(); e != nil {
+ return e
+ }
+ return nil
+}
+
+func (p *TSimpleJSONProtocol) OutputListBegin() error {
+ if e := p.OutputPreValue(); e != nil {
+ return e
+ }
+ if _, e := p.writer.Write(JSON_LBRACKET); e != nil {
+ return NewTProtocolException(e)
+ }
+ p.dumpContext = append(p.dumpContext, int(_CONTEXT_IN_LIST_FIRST))
+ return nil
+}
+
+func (p *TSimpleJSONProtocol) OutputListEnd() error {
+ if _, e := p.writer.Write(JSON_RBRACKET); e != nil {
+ return NewTProtocolException(e)
+ }
+ p.dumpContext = p.dumpContext[:len(p.dumpContext)-1]
+ if e := p.OutputPostValue(); e != nil {
+ return e
+ }
+ return nil
+}
+
+func (p *TSimpleJSONProtocol) OutputElemListBegin(elemType TType, size int) error {
+ if e := p.OutputListBegin(); e != nil {
+ return e
+ }
+ if e := p.WriteByte(byte(elemType)); e != nil {
+ return e
+ }
+ if e := p.WriteI64(int64(size)); e != nil {
+ return e
+ }
+ return nil
+}
+
+func (p *TSimpleJSONProtocol) ParsePreValue() error {
+ if e := p.readNonSignificantWhitespace(); e != nil {
+ return NewTProtocolException(e)
+ }
+ cxt := _ParseContext(p.parseContextStack[len(p.parseContextStack)-1])
+ b, _ := p.reader.Peek(1)
+ switch cxt {
+ case _CONTEXT_IN_LIST:
+ if len(b) > 0 {
+ switch b[0] {
+ case JSON_RBRACKET[0]:
+ return nil
+ case JSON_COMMA[0]:
+ p.reader.ReadByte()
+ if e := p.readNonSignificantWhitespace(); e != nil {
+ return NewTProtocolException(e)
+ }
+ return nil
+ default:
+ e := fmt.Errorf("Expected \"]\" or \",\" in list context, but found \"%s\"", string(b))
+ return NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ }
+ break
+ case _CONTEXT_IN_OBJECT_NEXT_KEY:
+ if len(b) > 0 {
+ switch b[0] {
+ case JSON_RBRACE[0]:
+ return nil
+ case JSON_COMMA[0]:
+ p.reader.ReadByte()
+ if e := p.readNonSignificantWhitespace(); e != nil {
+ return NewTProtocolException(e)
+ }
+ return nil
+ default:
+ e := fmt.Errorf("Expected \"}\" or \",\" in object context, but found \"%s\"", string(b))
+ return NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ }
+ break
+ case _CONTEXT_IN_OBJECT_NEXT_VALUE:
+ if len(b) > 0 {
+ switch b[0] {
+ case JSON_COLON[0]:
+ p.reader.ReadByte()
+ if e := p.readNonSignificantWhitespace(); e != nil {
+ return NewTProtocolException(e)
+ }
+ return nil
+ default:
+ e := fmt.Errorf("Expected \":\" in object context, but found \"%s\"", string(b))
+ return NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ }
+ break
+ }
+ return nil
+}
+
+func (p *TSimpleJSONProtocol) ParsePostValue() error {
+ if e := p.readNonSignificantWhitespace(); e != nil {
+ return NewTProtocolException(e)
+ }
+ cxt := _ParseContext(p.parseContextStack[len(p.parseContextStack)-1])
+ switch cxt {
+ case _CONTEXT_IN_LIST_FIRST:
+ p.parseContextStack = p.parseContextStack[:len(p.parseContextStack)-1]
+ p.parseContextStack = append(p.parseContextStack, int(_CONTEXT_IN_LIST))
+ break
+ case _CONTEXT_IN_OBJECT_FIRST, _CONTEXT_IN_OBJECT_NEXT_KEY:
+ p.parseContextStack = p.parseContextStack[:len(p.parseContextStack)-1]
+ p.parseContextStack = append(p.parseContextStack, int(_CONTEXT_IN_OBJECT_NEXT_VALUE))
+ break
+ case _CONTEXT_IN_OBJECT_NEXT_VALUE:
+ p.parseContextStack = p.parseContextStack[:len(p.parseContextStack)-1]
+ p.parseContextStack = append(p.parseContextStack, int(_CONTEXT_IN_OBJECT_NEXT_KEY))
+ break
+ }
+ return nil
+}
+
+func (p *TSimpleJSONProtocol) readNonSignificantWhitespace() error {
+ for {
+ b, _ := p.reader.Peek(1)
+ if len(b) < 1 {
+ return nil
+ }
+ switch b[0] {
+ case ' ', '\r', '\n', '\t':
+ p.reader.ReadByte()
+ continue
+ default:
+ break
+ }
+ break
+ }
+ return nil
+}
+
+func (p *TSimpleJSONProtocol) ParseStringBody() (string, error) {
+ var buf bytes.Buffer
+ buf.WriteByte(JSON_QUOTE)
+ for {
+ line, err := p.reader.ReadString(JSON_QUOTE)
+ if err != nil {
+ return "", NewTProtocolException(err)
+ }
+ buf.WriteString(line)
+ l := len(line)
+ // count number of escapes to see if we need to keep going
+ i := 1
+ for ; i < l; i++ {
+ if line[l-i-1] != '\\' {
+ break
+ }
+ }
+ if i&0x01 == 1 {
+ break
+ }
+ }
+ str := buf.String()
+ v, ok := jsonUnquote(str)
+ if !ok {
+ e := fmt.Errorf("Unable to parse as JSON string %s", str)
+ return "", NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ return v, nil
+}
+
+func (p *TSimpleJSONProtocol) ParseBase64EncodedBody() ([]byte, error) {
+ line, err := p.reader.ReadBytes(JSON_QUOTE)
+ if err != nil {
+ return line, NewTProtocolException(err)
+ }
+ line2 := line[0 : len(line)-1]
+ l := len(line2)
+ output := make([]byte, base64.StdEncoding.DecodedLen(l))
+ n, err := base64.StdEncoding.Decode(output, line2)
+ return output[0:n], NewTProtocolException(err)
+}
+
+func (p *TSimpleJSONProtocol) ParseI64() (int64, bool, error) {
+ if err := p.ParsePreValue(); err != nil {
+ return 0, false, err
+ }
+ var value int64
+ var isnull bool
+ b, _ := p.reader.Peek(len(JSON_NULL))
+ if len(b) >= len(JSON_NULL) && string(b) == string(JSON_NULL) {
+ p.reader.Read(b[0:len(JSON_NULL)])
+ isnull = true
+ } else {
+ num, err := p.readNumeric()
+ isnull = (num == nil)
+ if !isnull {
+ value = num.Int64()
+ }
+ if err != nil {
+ return value, isnull, err
+ }
+ }
+ return value, isnull, p.ParsePostValue()
+}
+
+func (p *TSimpleJSONProtocol) ParseF64() (float64, bool, error) {
+ if err := p.ParsePreValue(); err != nil {
+ return 0, false, err
+ }
+ var value float64
+ var isnull bool
+ b, _ := p.reader.Peek(len(JSON_NULL))
+ if len(b) >= len(JSON_NULL) && string(b) == string(JSON_NULL) {
+ p.reader.Read(b[0:len(JSON_NULL)])
+ isnull = true
+ } else {
+ num, err := p.readNumeric()
+ isnull = (num == nil)
+ if !isnull {
+ value = num.Float64()
+ }
+ if err != nil {
+ return value, isnull, err
+ }
+ }
+ return value, isnull, p.ParsePostValue()
+}
+
+func (p *TSimpleJSONProtocol) ParseObjectStart() (bool, error) {
+ if err := p.ParsePreValue(); err != nil {
+ return false, err
+ }
+ var b []byte
+ b, _ = p.reader.Peek(len(JSON_NULL))
+ if len(b) > 0 && b[0] == JSON_LBRACE[0] {
+ p.reader.ReadByte()
+ p.parseContextStack = append(p.parseContextStack, int(_CONTEXT_IN_OBJECT_FIRST))
+ return false, nil
+ } else if len(b) >= len(JSON_NULL) && string(b[0:len(JSON_NULL)]) == string(JSON_NULL) {
+ return true, nil
+ }
+ e := fmt.Errorf("Expected '{' or null, but found '%s'", string(b))
+ return false, NewTProtocolExceptionWithType(INVALID_DATA, e)
+}
+
+func (p *TSimpleJSONProtocol) ParseObjectEnd() error {
+ if isNull, err := p.readIfNull(); isNull || err != nil {
+ return err
+ }
+ cxt := _ParseContext(p.parseContextStack[len(p.parseContextStack)-1])
+ if cxt != _CONTEXT_IN_OBJECT_FIRST && cxt != _CONTEXT_IN_OBJECT_NEXT_KEY {
+ e := fmt.Errorf("Expected to be in the Object Context, but not in Object Context")
+ return NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ line, err := p.reader.ReadString(JSON_RBRACE[0])
+ if err != nil {
+ return NewTProtocolException(err)
+ }
+ for _, char := range line {
+ switch char {
+ default:
+ e := fmt.Errorf("Expecting end of object \"}\", but found: \"%s\"", line)
+ return NewTProtocolExceptionWithType(INVALID_DATA, e)
+ case ' ', '\n', '\r', '\t', '}':
+ break
+ }
+ }
+ p.parseContextStack = p.parseContextStack[:len(p.parseContextStack)-1]
+ return p.ParsePostValue()
+}
+
+func (p *TSimpleJSONProtocol) ParseListBegin() (isNull bool, err error) {
+ if e := p.ParsePreValue(); e != nil {
+ return false, e
+ }
+ var b []byte
+ b, err = p.reader.Peek(len(JSON_NULL))
+ if err != nil {
+ return false, err
+ }
+ if len(b) >= 1 && b[0] == JSON_LBRACKET[0] {
+ p.parseContextStack = append(p.parseContextStack, int(_CONTEXT_IN_LIST_FIRST))
+ p.reader.ReadByte()
+ isNull = false
+ } else if len(b) >= len(JSON_NULL) && string(b) == string(JSON_NULL) {
+ isNull = true
+ } else {
+ err = fmt.Errorf("Expected \"null\" or \"[\", received %q", b)
+ }
+ return isNull, NewTProtocolExceptionWithType(INVALID_DATA, err)
+}
+
+func (p *TSimpleJSONProtocol) ParseElemListBegin() (elemType TType, size int, e error) {
+ if isNull, e := p.ParseListBegin(); isNull || e != nil {
+ return VOID, 0, e
+ }
+ bElemType, err := p.ReadByte()
+ elemType = TType(bElemType)
+ if err != nil {
+ return elemType, size, err
+ }
+ nSize, err2 := p.ReadI64()
+ size = int(nSize)
+ return elemType, size, err2
+}
+
+func (p *TSimpleJSONProtocol) ParseListEnd() error {
+ if isNull, err := p.readIfNull(); isNull || err != nil {
+ return err
+ }
+ if _ParseContext(p.parseContextStack[len(p.parseContextStack)-1]) != _CONTEXT_IN_LIST {
+ e := fmt.Errorf("Expected to be in the List Context, but not in List Context")
+ return NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ line, err := p.reader.ReadString(JSON_RBRACKET[0])
+ if err != nil {
+ return NewTProtocolException(err)
+ }
+ for _, char := range line {
+ switch char {
+ default:
+ e := fmt.Errorf("Expecting end of list \"]\", but found: \"", line, "\"")
+ return NewTProtocolExceptionWithType(INVALID_DATA, e)
+ case ' ', '\n', '\r', '\t', rune(JSON_RBRACKET[0]):
+ break
+ }
+ }
+ p.parseContextStack = p.parseContextStack[:len(p.parseContextStack)-1]
+ return p.ParsePostValue()
+}
+
+func (p *TSimpleJSONProtocol) readSingleValue() (interface{}, TType, error) {
+ e := p.readNonSignificantWhitespace()
+ if e != nil {
+ return nil, VOID, NewTProtocolException(e)
+ }
+ b, e := p.reader.Peek(10)
+ if len(b) > 0 {
+ c := b[0]
+ switch c {
+ case JSON_NULL[0]:
+ buf := make([]byte, len(JSON_NULL))
+ _, e := p.reader.Read(buf)
+ if e != nil {
+ return nil, VOID, NewTProtocolException(e)
+ }
+ if string(JSON_NULL) != string(buf) {
+ e = mismatch(string(JSON_NULL), string(buf))
+ return nil, VOID, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ return nil, VOID, nil
+ case JSON_QUOTE:
+ p.reader.ReadByte()
+ v, e := p.ParseStringBody()
+ if e != nil {
+ return v, UTF8, NewTProtocolException(e)
+ }
+ if v == JSON_INFINITY {
+ return INFINITY, DOUBLE, nil
+ } else if v == JSON_NEGATIVE_INFINITY {
+ return NEGATIVE_INFINITY, DOUBLE, nil
+ } else if v == JSON_NAN {
+ return NAN, DOUBLE, nil
+ }
+ return v, UTF8, nil
+ case JSON_TRUE[0]:
+ buf := make([]byte, len(JSON_TRUE))
+ _, e := p.reader.Read(buf)
+ if e != nil {
+ return true, BOOL, NewTProtocolException(e)
+ }
+ if string(JSON_TRUE) != string(buf) {
+ e := mismatch(string(JSON_TRUE), string(buf))
+ return true, BOOL, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ return true, BOOL, nil
+ case JSON_FALSE[0]:
+ buf := make([]byte, len(JSON_FALSE))
+ _, e := p.reader.Read(buf)
+ if e != nil {
+ return false, BOOL, NewTProtocolException(e)
+ }
+ if string(JSON_FALSE) != string(buf) {
+ e := mismatch(string(JSON_FALSE), string(buf))
+ return false, BOOL, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ return false, BOOL, nil
+ case JSON_LBRACKET[0]:
+ _, e := p.reader.ReadByte()
+ return make([]interface{}, 0), LIST, NewTProtocolException(e)
+ case JSON_LBRACE[0]:
+ _, e := p.reader.ReadByte()
+ return make(map[string]interface{}), STRUCT, NewTProtocolException(e)
+ case '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'e', 'E', '.', '+', '-', JSON_INFINITY[0], JSON_NAN[0]:
+ // assume numeric
+ v, e := p.readNumeric()
+ return v, DOUBLE, e
+ default:
+ e := fmt.Errorf("Expected element in list but found '%s' while parsing JSON.", string(c))
+ return nil, VOID, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ }
+ e = fmt.Errorf("Cannot read a single element while parsing JSON.")
+ return nil, VOID, NewTProtocolExceptionWithType(INVALID_DATA, e)
+
+}
+
+func (p *TSimpleJSONProtocol) readIfNull() (bool, error) {
+ cont := true
+ for cont {
+ b, _ := p.reader.Peek(1)
+ if len(b) < 1 {
+ return false, nil
+ }
+ switch b[0] {
+ default:
+ return false, nil
+ case JSON_NULL[0]:
+ cont = false
+ break
+ case ' ', '\n', '\r', '\t':
+ p.reader.ReadByte()
+ break
+ }
+ }
+ b, _ := p.reader.Peek(len(JSON_NULL))
+ if string(b) == string(JSON_NULL) {
+ p.reader.Read(b[0:len(JSON_NULL)])
+ return true, nil
+ }
+ return false, nil
+}
+
+func (p *TSimpleJSONProtocol) readQuoteIfNext() {
+ b, _ := p.reader.Peek(1)
+ if len(b) > 0 && b[0] == JSON_QUOTE {
+ p.reader.ReadByte()
+ }
+}
+
+func (p *TSimpleJSONProtocol) readNumeric() (Numeric, error) {
+ isNull, err := p.readIfNull()
+ if isNull || err != nil {
+ return NUMERIC_NULL, err
+ }
+ hasDecimalPoint := false
+ nextCanBeSign := true
+ hasE := false
+ MAX_LEN := 40
+ buf := bytes.NewBuffer(make([]byte, 0, MAX_LEN))
+ continueFor := true
+ inQuotes := false
+ for continueFor {
+ c, err := p.reader.ReadByte()
+ if err != nil {
+ if err == io.EOF {
+ break
+ }
+ return NUMERIC_NULL, NewTProtocolException(err)
+ }
+ switch c {
+ case '0', '1', '2', '3', '4', '5', '6', '7', '8', '9':
+ buf.WriteByte(c)
+ nextCanBeSign = false
+ case '.':
+ if hasDecimalPoint {
+ e := fmt.Errorf("Unable to parse number with multiple decimal points '%s.'", buf.String())
+ return NUMERIC_NULL, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ if hasE {
+ e := fmt.Errorf("Unable to parse number with decimal points in the exponent '%s.'", buf.String())
+ return NUMERIC_NULL, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ buf.WriteByte(c)
+ hasDecimalPoint, nextCanBeSign = true, false
+ case 'e', 'E':
+ if hasE {
+ e := fmt.Errorf("Unable to parse number with multiple exponents '%s%c'", buf.String(), c)
+ return NUMERIC_NULL, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ buf.WriteByte(c)
+ hasE, nextCanBeSign = true, true
+ case '-', '+':
+ if !nextCanBeSign {
+ e := fmt.Errorf("Negative sign within number")
+ return NUMERIC_NULL, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ buf.WriteByte(c)
+ nextCanBeSign = false
+ case ' ', 0, '\t', '\n', '\r', JSON_RBRACE[0], JSON_RBRACKET[0], JSON_COMMA[0], JSON_COLON[0]:
+ p.reader.UnreadByte()
+ continueFor = false
+ case JSON_NAN[0]:
+ if buf.Len() == 0 {
+ buffer := make([]byte, len(JSON_NAN))
+ buffer[0] = c
+ _, e := p.reader.Read(buffer[1:])
+ if e != nil {
+ return NUMERIC_NULL, NewTProtocolException(e)
+ }
+ if JSON_NAN != string(buffer) {
+ e := mismatch(JSON_NAN, string(buffer))
+ return NUMERIC_NULL, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ if inQuotes {
+ p.readQuoteIfNext()
+ }
+ return NAN, nil
+ } else {
+ e := fmt.Errorf("Unable to parse number starting with character '%c'", c)
+ return NUMERIC_NULL, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ case JSON_INFINITY[0]:
+ if buf.Len() == 0 || (buf.Len() == 1 && buf.Bytes()[0] == '+') {
+ buffer := make([]byte, len(JSON_INFINITY))
+ buffer[0] = c
+ _, e := p.reader.Read(buffer[1:])
+ if e != nil {
+ return NUMERIC_NULL, NewTProtocolException(e)
+ }
+ if JSON_INFINITY != string(buffer) {
+ e := mismatch(JSON_INFINITY, string(buffer))
+ return NUMERIC_NULL, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ if inQuotes {
+ p.readQuoteIfNext()
+ }
+ return INFINITY, nil
+ } else if buf.Len() == 1 && buf.Bytes()[0] == JSON_NEGATIVE_INFINITY[0] {
+ buffer := make([]byte, len(JSON_NEGATIVE_INFINITY))
+ buffer[0] = JSON_NEGATIVE_INFINITY[0]
+ buffer[1] = c
+ _, e := p.reader.Read(buffer[2:])
+ if e != nil {
+ return NUMERIC_NULL, NewTProtocolException(e)
+ }
+ if JSON_NEGATIVE_INFINITY != string(buffer) {
+ e := mismatch(JSON_NEGATIVE_INFINITY, string(buffer))
+ return NUMERIC_NULL, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ if inQuotes {
+ p.readQuoteIfNext()
+ }
+ return NEGATIVE_INFINITY, nil
+ } else {
+ e := fmt.Errorf("Unable to parse number starting with character '%c' due to existing buffer %s", c, buf.String())
+ return NUMERIC_NULL, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ case JSON_QUOTE:
+ if !inQuotes {
+ inQuotes = true
+ } else {
+ break
+ }
+ default:
+ e := fmt.Errorf("Unable to parse number starting with character '%c'", c)
+ return NUMERIC_NULL, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ }
+ if buf.Len() == 0 {
+ e := fmt.Errorf("Unable to parse number from empty string ''")
+ return NUMERIC_NULL, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ return NewNumericFromJSONString(buf.String(), false), nil
+}
diff --git a/vendor/github.com/lightstep/thrift/lib/go/thrift/simple_server.go b/vendor/github.com/lightstep/thrift/lib/go/thrift/simple_server.go
new file mode 100644
index 000000000..2afdb0623
--- /dev/null
+++ b/vendor/github.com/lightstep/thrift/lib/go/thrift/simple_server.go
@@ -0,0 +1,188 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+import (
+ "log"
+ "runtime/debug"
+)
+
+// Simple, non-concurrent server for testing.
+type TSimpleServer struct {
+ quit chan struct{}
+
+ processorFactory TProcessorFactory
+ serverTransport TServerTransport
+ inputTransportFactory TTransportFactory
+ outputTransportFactory TTransportFactory
+ inputProtocolFactory TProtocolFactory
+ outputProtocolFactory TProtocolFactory
+}
+
+func NewTSimpleServer2(processor TProcessor, serverTransport TServerTransport) *TSimpleServer {
+ return NewTSimpleServerFactory2(NewTProcessorFactory(processor), serverTransport)
+}
+
+func NewTSimpleServer4(processor TProcessor, serverTransport TServerTransport, transportFactory TTransportFactory, protocolFactory TProtocolFactory) *TSimpleServer {
+ return NewTSimpleServerFactory4(NewTProcessorFactory(processor),
+ serverTransport,
+ transportFactory,
+ protocolFactory,
+ )
+}
+
+func NewTSimpleServer6(processor TProcessor, serverTransport TServerTransport, inputTransportFactory TTransportFactory, outputTransportFactory TTransportFactory, inputProtocolFactory TProtocolFactory, outputProtocolFactory TProtocolFactory) *TSimpleServer {
+ return NewTSimpleServerFactory6(NewTProcessorFactory(processor),
+ serverTransport,
+ inputTransportFactory,
+ outputTransportFactory,
+ inputProtocolFactory,
+ outputProtocolFactory,
+ )
+}
+
+func NewTSimpleServerFactory2(processorFactory TProcessorFactory, serverTransport TServerTransport) *TSimpleServer {
+ return NewTSimpleServerFactory6(processorFactory,
+ serverTransport,
+ NewTTransportFactory(),
+ NewTTransportFactory(),
+ NewTBinaryProtocolFactoryDefault(),
+ NewTBinaryProtocolFactoryDefault(),
+ )
+}
+
+func NewTSimpleServerFactory4(processorFactory TProcessorFactory, serverTransport TServerTransport, transportFactory TTransportFactory, protocolFactory TProtocolFactory) *TSimpleServer {
+ return NewTSimpleServerFactory6(processorFactory,
+ serverTransport,
+ transportFactory,
+ transportFactory,
+ protocolFactory,
+ protocolFactory,
+ )
+}
+
+func NewTSimpleServerFactory6(processorFactory TProcessorFactory, serverTransport TServerTransport, inputTransportFactory TTransportFactory, outputTransportFactory TTransportFactory, inputProtocolFactory TProtocolFactory, outputProtocolFactory TProtocolFactory) *TSimpleServer {
+ return &TSimpleServer{
+ processorFactory: processorFactory,
+ serverTransport: serverTransport,
+ inputTransportFactory: inputTransportFactory,
+ outputTransportFactory: outputTransportFactory,
+ inputProtocolFactory: inputProtocolFactory,
+ outputProtocolFactory: outputProtocolFactory,
+ quit: make(chan struct{}, 1),
+ }
+}
+
+func (p *TSimpleServer) ProcessorFactory() TProcessorFactory {
+ return p.processorFactory
+}
+
+func (p *TSimpleServer) ServerTransport() TServerTransport {
+ return p.serverTransport
+}
+
+func (p *TSimpleServer) InputTransportFactory() TTransportFactory {
+ return p.inputTransportFactory
+}
+
+func (p *TSimpleServer) OutputTransportFactory() TTransportFactory {
+ return p.outputTransportFactory
+}
+
+func (p *TSimpleServer) InputProtocolFactory() TProtocolFactory {
+ return p.inputProtocolFactory
+}
+
+func (p *TSimpleServer) OutputProtocolFactory() TProtocolFactory {
+ return p.outputProtocolFactory
+}
+
+func (p *TSimpleServer) Listen() error {
+ return p.serverTransport.Listen()
+}
+
+func (p *TSimpleServer) AcceptLoop() error {
+ for {
+ select {
+ case <-p.quit:
+ return nil
+ default:
+ }
+
+ client, err := p.serverTransport.Accept()
+ if err != nil {
+ log.Println("Accept err: ", err)
+ }
+ if client != nil {
+ go func() {
+ if err := p.processRequests(client); err != nil {
+ log.Println("error processing request:", err)
+ }
+ }()
+ }
+ }
+}
+
+func (p *TSimpleServer) Serve() error {
+ err := p.Listen()
+ if err != nil {
+ return err
+ }
+ p.AcceptLoop()
+ return nil
+}
+
+func (p *TSimpleServer) Stop() error {
+ p.quit <- struct{}{}
+ p.serverTransport.Interrupt()
+ return nil
+}
+
+func (p *TSimpleServer) processRequests(client TTransport) error {
+ processor := p.processorFactory.GetProcessor(client)
+ inputTransport := p.inputTransportFactory.GetTransport(client)
+ outputTransport := p.outputTransportFactory.GetTransport(client)
+ inputProtocol := p.inputProtocolFactory.GetProtocol(inputTransport)
+ outputProtocol := p.outputProtocolFactory.GetProtocol(outputTransport)
+ defer func() {
+ if e := recover(); e != nil {
+ log.Printf("panic in processor: %s: %s", e, debug.Stack())
+ }
+ }()
+ if inputTransport != nil {
+ defer inputTransport.Close()
+ }
+ if outputTransport != nil {
+ defer outputTransport.Close()
+ }
+ for {
+ ok, err := processor.Process(inputProtocol, outputProtocol)
+ if err, ok := err.(TTransportException); ok && err.TypeId() == END_OF_FILE {
+ return nil
+ } else if err != nil {
+ log.Printf("error processing request: %s", err)
+ return err
+ }
+ if !ok {
+ break
+ }
+ }
+ return nil
+}
diff --git a/vendor/github.com/lightstep/thrift/lib/go/thrift/socket.go b/vendor/github.com/lightstep/thrift/lib/go/thrift/socket.go
new file mode 100644
index 000000000..a381ea25a
--- /dev/null
+++ b/vendor/github.com/lightstep/thrift/lib/go/thrift/socket.go
@@ -0,0 +1,159 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+import (
+ "net"
+ "time"
+)
+
+type TSocket struct {
+ conn net.Conn
+ addr net.Addr
+ timeout time.Duration
+}
+
+// NewTSocket creates a net.Conn-backed TTransport, given a host and port
+//
+// Example:
+// trans, err := thrift.NewTSocket("localhost:9090")
+func NewTSocket(hostPort string) (*TSocket, error) {
+ return NewTSocketTimeout(hostPort, 0)
+}
+
+// NewTSocketTimeout creates a net.Conn-backed TTransport, given a host and port
+// it also accepts a timeout as a time.Duration
+func NewTSocketTimeout(hostPort string, timeout time.Duration) (*TSocket, error) {
+ //conn, err := net.DialTimeout(network, address, timeout)
+ addr, err := net.ResolveTCPAddr("tcp", hostPort)
+ if err != nil {
+ return nil, err
+ }
+ return NewTSocketFromAddrTimeout(addr, timeout), nil
+}
+
+// Creates a TSocket from a net.Addr
+func NewTSocketFromAddrTimeout(addr net.Addr, timeout time.Duration) *TSocket {
+ return &TSocket{addr: addr, timeout: timeout}
+}
+
+// Creates a TSocket from an existing net.Conn
+func NewTSocketFromConnTimeout(conn net.Conn, timeout time.Duration) *TSocket {
+ return &TSocket{conn: conn, addr: conn.RemoteAddr(), timeout: timeout}
+}
+
+// Sets the socket timeout
+func (p *TSocket) SetTimeout(timeout time.Duration) error {
+ p.timeout = timeout
+ return nil
+}
+
+func (p *TSocket) pushDeadline(read, write bool) {
+ var t time.Time
+ if p.timeout > 0 {
+ t = time.Now().Add(time.Duration(p.timeout))
+ }
+ if read && write {
+ p.conn.SetDeadline(t)
+ } else if read {
+ p.conn.SetReadDeadline(t)
+ } else if write {
+ p.conn.SetWriteDeadline(t)
+ }
+}
+
+// Connects the socket, creating a new socket object if necessary.
+func (p *TSocket) Open() error {
+ if p.IsOpen() {
+ return NewTTransportException(ALREADY_OPEN, "Socket already connected.")
+ }
+ if p.addr == nil {
+ return NewTTransportException(NOT_OPEN, "Cannot open nil address.")
+ }
+ if len(p.addr.Network()) == 0 {
+ return NewTTransportException(NOT_OPEN, "Cannot open bad network name.")
+ }
+ if len(p.addr.String()) == 0 {
+ return NewTTransportException(NOT_OPEN, "Cannot open bad address.")
+ }
+ var err error
+ if p.conn, err = net.DialTimeout(p.addr.Network(), p.addr.String(), p.timeout); err != nil {
+ return NewTTransportException(NOT_OPEN, err.Error())
+ }
+ return nil
+}
+
+// Retreive the underlying net.Conn
+func (p *TSocket) Conn() net.Conn {
+ return p.conn
+}
+
+// Returns true if the connection is open
+func (p *TSocket) IsOpen() bool {
+ if p.conn == nil {
+ return false
+ }
+ return true
+}
+
+// Closes the socket.
+func (p *TSocket) Close() error {
+ // Close the socket
+ if p.conn != nil {
+ err := p.conn.Close()
+ if err != nil {
+ return err
+ }
+ p.conn = nil
+ }
+ return nil
+}
+
+func (p *TSocket) Read(buf []byte) (int, error) {
+ if !p.IsOpen() {
+ return 0, NewTTransportException(NOT_OPEN, "Connection not open")
+ }
+ p.pushDeadline(true, false)
+ n, err := p.conn.Read(buf)
+ return n, NewTTransportExceptionFromError(err)
+}
+
+func (p *TSocket) Write(buf []byte) (int, error) {
+ if !p.IsOpen() {
+ return 0, NewTTransportException(NOT_OPEN, "Connection not open")
+ }
+ p.pushDeadline(false, true)
+ return p.conn.Write(buf)
+}
+
+func (p *TSocket) Peek() bool {
+ return p.IsOpen()
+}
+
+func (p *TSocket) Flush() error {
+ return nil
+}
+
+func (p *TSocket) Interrupt() error {
+ if !p.IsOpen() {
+ return nil
+ }
+ return p.conn.Close()
+}
diff --git a/vendor/github.com/lightstep/thrift/lib/go/thrift/ssl_server_socket.go b/vendor/github.com/lightstep/thrift/lib/go/thrift/ssl_server_socket.go
new file mode 100644
index 000000000..061552865
--- /dev/null
+++ b/vendor/github.com/lightstep/thrift/lib/go/thrift/ssl_server_socket.go
@@ -0,0 +1,109 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+import (
+ "crypto/tls"
+ "net"
+ "time"
+)
+
+type TSSLServerSocket struct {
+ listener net.Listener
+ addr net.Addr
+ clientTimeout time.Duration
+ interrupted bool
+ cfg *tls.Config
+}
+
+func NewTSSLServerSocket(listenAddr string, cfg *tls.Config) (*TSSLServerSocket, error) {
+ return NewTSSLServerSocketTimeout(listenAddr, cfg, 0)
+}
+
+func NewTSSLServerSocketTimeout(listenAddr string, cfg *tls.Config, clientTimeout time.Duration) (*TSSLServerSocket, error) {
+ addr, err := net.ResolveTCPAddr("tcp", listenAddr)
+ if err != nil {
+ return nil, err
+ }
+ return &TSSLServerSocket{addr: addr, clientTimeout: clientTimeout, cfg: cfg}, nil
+}
+
+func (p *TSSLServerSocket) Listen() error {
+ if p.IsListening() {
+ return nil
+ }
+ l, err := tls.Listen(p.addr.Network(), p.addr.String(), p.cfg)
+ if err != nil {
+ return err
+ }
+ p.listener = l
+ return nil
+}
+
+func (p *TSSLServerSocket) Accept() (TTransport, error) {
+ if p.interrupted {
+ return nil, errTransportInterrupted
+ }
+ if p.listener == nil {
+ return nil, NewTTransportException(NOT_OPEN, "No underlying server socket")
+ }
+ conn, err := p.listener.Accept()
+ if err != nil {
+ return nil, NewTTransportExceptionFromError(err)
+ }
+ return NewTSSLSocketFromConnTimeout(conn, p.cfg, p.clientTimeout), nil
+}
+
+// Checks whether the socket is listening.
+func (p *TSSLServerSocket) IsListening() bool {
+ return p.listener != nil
+}
+
+// Connects the socket, creating a new socket object if necessary.
+func (p *TSSLServerSocket) Open() error {
+ if p.IsListening() {
+ return NewTTransportException(ALREADY_OPEN, "Server socket already open")
+ }
+ if l, err := tls.Listen(p.addr.Network(), p.addr.String(), p.cfg); err != nil {
+ return err
+ } else {
+ p.listener = l
+ }
+ return nil
+}
+
+func (p *TSSLServerSocket) Addr() net.Addr {
+ return p.addr
+}
+
+func (p *TSSLServerSocket) Close() error {
+ defer func() {
+ p.listener = nil
+ }()
+ if p.IsListening() {
+ return p.listener.Close()
+ }
+ return nil
+}
+
+func (p *TSSLServerSocket) Interrupt() error {
+ p.interrupted = true
+ return nil
+}
diff --git a/vendor/github.com/lightstep/thrift/lib/go/thrift/ssl_socket.go b/vendor/github.com/lightstep/thrift/lib/go/thrift/ssl_socket.go
new file mode 100644
index 000000000..f831e1860
--- /dev/null
+++ b/vendor/github.com/lightstep/thrift/lib/go/thrift/ssl_socket.go
@@ -0,0 +1,161 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+import (
+ "crypto/tls"
+ "net"
+ "time"
+)
+
+type TSSLSocket struct {
+ conn net.Conn
+ addr net.Addr
+ timeout time.Duration
+ cfg *tls.Config
+}
+
+// NewTSSLSocket creates a net.Conn-backed TTransport, given a host and port and tls Configuration
+//
+// Example:
+// trans, err := thrift.NewTSocket("localhost:9090")
+func NewTSSLSocket(hostPort string, cfg *tls.Config) (*TSSLSocket, error) {
+ return NewTSSLSocketTimeout(hostPort, cfg, 0)
+}
+
+// NewTSSLSocketTimeout creates a net.Conn-backed TTransport, given a host and port
+// it also accepts a tls Configuration and a timeout as a time.Duration
+func NewTSSLSocketTimeout(hostPort string, cfg *tls.Config, timeout time.Duration) (*TSSLSocket, error) {
+ //conn, err := net.DialTimeout(network, address, timeout)
+ addr, err := net.ResolveTCPAddr("tcp", hostPort)
+ if err != nil {
+ return nil, err
+ }
+ return NewTSSLSocketFromAddrTimeout(addr, cfg, timeout), nil
+}
+
+// Creates a TSSLSocket from a net.Addr
+func NewTSSLSocketFromAddrTimeout(addr net.Addr, cfg *tls.Config, timeout time.Duration) *TSSLSocket {
+ return &TSSLSocket{addr: addr, timeout: timeout, cfg: cfg}
+}
+
+// Creates a TSSLSocket from an existing net.Conn
+func NewTSSLSocketFromConnTimeout(conn net.Conn, cfg *tls.Config, timeout time.Duration) *TSSLSocket {
+ return &TSSLSocket{conn: conn, addr: conn.RemoteAddr(), timeout: timeout, cfg: cfg}
+}
+
+// Sets the socket timeout
+func (p *TSSLSocket) SetTimeout(timeout time.Duration) error {
+ p.timeout = timeout
+ return nil
+}
+
+func (p *TSSLSocket) pushDeadline(read, write bool) {
+ var t time.Time
+ if p.timeout > 0 {
+ t = time.Now().Add(time.Duration(p.timeout))
+ }
+ if read && write {
+ p.conn.SetDeadline(t)
+ } else if read {
+ p.conn.SetReadDeadline(t)
+ } else if write {
+ p.conn.SetWriteDeadline(t)
+ }
+}
+
+// Connects the socket, creating a new socket object if necessary.
+func (p *TSSLSocket) Open() error {
+ if p.IsOpen() {
+ return NewTTransportException(ALREADY_OPEN, "Socket already connected.")
+ }
+ if p.addr == nil {
+ return NewTTransportException(NOT_OPEN, "Cannot open nil address.")
+ }
+ if len(p.addr.Network()) == 0 {
+ return NewTTransportException(NOT_OPEN, "Cannot open bad network name.")
+ }
+ if len(p.addr.String()) == 0 {
+ return NewTTransportException(NOT_OPEN, "Cannot open bad address.")
+ }
+ var err error
+ if p.conn, err = tls.Dial(p.addr.Network(), p.addr.String(), p.cfg); err != nil {
+ return NewTTransportException(NOT_OPEN, err.Error())
+ }
+ return nil
+}
+
+// Retreive the underlying net.Conn
+func (p *TSSLSocket) Conn() net.Conn {
+ return p.conn
+}
+
+// Returns true if the connection is open
+func (p *TSSLSocket) IsOpen() bool {
+ if p.conn == nil {
+ return false
+ }
+ return true
+}
+
+// Closes the socket.
+func (p *TSSLSocket) Close() error {
+ // Close the socket
+ if p.conn != nil {
+ err := p.conn.Close()
+ if err != nil {
+ return err
+ }
+ p.conn = nil
+ }
+ return nil
+}
+
+func (p *TSSLSocket) Read(buf []byte) (int, error) {
+ if !p.IsOpen() {
+ return 0, NewTTransportException(NOT_OPEN, "Connection not open")
+ }
+ p.pushDeadline(true, false)
+ n, err := p.conn.Read(buf)
+ return n, NewTTransportExceptionFromError(err)
+}
+
+func (p *TSSLSocket) Write(buf []byte) (int, error) {
+ if !p.IsOpen() {
+ return 0, NewTTransportException(NOT_OPEN, "Connection not open")
+ }
+ p.pushDeadline(false, true)
+ return p.conn.Write(buf)
+}
+
+func (p *TSSLSocket) Peek() bool {
+ return p.IsOpen()
+}
+
+func (p *TSSLSocket) Flush() error {
+ return nil
+}
+
+func (p *TSSLSocket) Interrupt() error {
+ if !p.IsOpen() {
+ return nil
+ }
+ return p.conn.Close()
+}
diff --git a/vendor/github.com/lightstep/thrift/lib/go/thrift/transport.go b/vendor/github.com/lightstep/thrift/lib/go/thrift/transport.go
new file mode 100644
index 000000000..8c0622db0
--- /dev/null
+++ b/vendor/github.com/lightstep/thrift/lib/go/thrift/transport.go
@@ -0,0 +1,59 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+import (
+ "errors"
+ "io"
+)
+
+var errTransportInterrupted = errors.New("Transport Interrupted")
+
+type Flusher interface {
+ Flush() (err error)
+}
+
+// Encapsulates the I/O layer
+type TTransport interface {
+ io.ReadWriteCloser
+ Flusher
+
+ // Opens the transport for communication
+ Open() error
+
+ // Returns true if the transport is open
+ IsOpen() bool
+}
+
+type stringWriter interface {
+ WriteString(s string) (n int, err error)
+}
+
+// This is "enchanced" transport with extra capabilities. You need to use one of these
+// to construct protocol.
+// Notably, TSocket does not implement this interface, and it is always a mistake to use
+// TSocket directly in protocol.
+type TRichTransport interface {
+ io.ReadWriter
+ io.ByteReader
+ io.ByteWriter
+ stringWriter
+ Flusher
+}
diff --git a/vendor/github.com/lightstep/thrift/lib/go/thrift/transport_exception.go b/vendor/github.com/lightstep/thrift/lib/go/thrift/transport_exception.go
new file mode 100644
index 000000000..9505b4461
--- /dev/null
+++ b/vendor/github.com/lightstep/thrift/lib/go/thrift/transport_exception.go
@@ -0,0 +1,90 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+import (
+ "errors"
+ "io"
+)
+
+type timeoutable interface {
+ Timeout() bool
+}
+
+// Thrift Transport exception
+type TTransportException interface {
+ TException
+ TypeId() int
+ Err() error
+}
+
+const (
+ UNKNOWN_TRANSPORT_EXCEPTION = 0
+ NOT_OPEN = 1
+ ALREADY_OPEN = 2
+ TIMED_OUT = 3
+ END_OF_FILE = 4
+)
+
+type tTransportException struct {
+ typeId int
+ err error
+}
+
+func (p *tTransportException) TypeId() int {
+ return p.typeId
+}
+
+func (p *tTransportException) Error() string {
+ return p.err.Error()
+}
+
+func (p *tTransportException) Err() error {
+ return p.err
+}
+
+func NewTTransportException(t int, e string) TTransportException {
+ return &tTransportException{typeId: t, err: errors.New(e)}
+}
+
+func NewTTransportExceptionFromError(e error) TTransportException {
+ if e == nil {
+ return nil
+ }
+
+ if t, ok := e.(TTransportException); ok {
+ return t
+ }
+
+ switch v := e.(type) {
+ case TTransportException:
+ return v
+ case timeoutable:
+ if v.Timeout() {
+ return &tTransportException{typeId: TIMED_OUT, err: e}
+ }
+ }
+
+ if e == io.EOF {
+ return &tTransportException{typeId: END_OF_FILE, err: e}
+ }
+
+ return &tTransportException{typeId: UNKNOWN_TRANSPORT_EXCEPTION, err: e}
+}
diff --git a/vendor/github.com/lightstep/thrift/lib/go/thrift/transport_factory.go b/vendor/github.com/lightstep/thrift/lib/go/thrift/transport_factory.go
new file mode 100644
index 000000000..533d1b437
--- /dev/null
+++ b/vendor/github.com/lightstep/thrift/lib/go/thrift/transport_factory.go
@@ -0,0 +1,39 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+// Factory class used to create wrapped instance of Transports.
+// This is used primarily in servers, which get Transports from
+// a ServerTransport and then may want to mutate them (i.e. create
+// a BufferedTransport from the underlying base transport)
+type TTransportFactory interface {
+ GetTransport(trans TTransport) TTransport
+}
+
+type tTransportFactory struct{}
+
+// Return a wrapped instance of the base Transport.
+func (p *tTransportFactory) GetTransport(trans TTransport) TTransport {
+ return trans
+}
+
+func NewTTransportFactory() TTransportFactory {
+ return &tTransportFactory{}
+}
diff --git a/vendor/github.com/lightstep/thrift/lib/go/thrift/type.go b/vendor/github.com/lightstep/thrift/lib/go/thrift/type.go
new file mode 100644
index 000000000..7c68c2b94
--- /dev/null
+++ b/vendor/github.com/lightstep/thrift/lib/go/thrift/type.go
@@ -0,0 +1,68 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+// Type constants in the Thrift protocol
+type TType byte
+
+const (
+ STOP = 0
+ VOID = 1
+ BOOL = 2
+ BYTE = 3
+ I08 = 3
+ DOUBLE = 4
+ I16 = 6
+ I32 = 8
+ I64 = 10
+ STRING = 11
+ UTF7 = 11
+ STRUCT = 12
+ MAP = 13
+ SET = 14
+ LIST = 15
+ UTF8 = 16
+ UTF16 = 17
+ BINARY = 18
+)
+
+var typeNames = map[int]string{
+ STOP: "STOP",
+ VOID: "VOID",
+ BOOL: "BOOL",
+ BYTE: "BYTE",
+ I16: "I16",
+ I32: "I32",
+ I64: "I64",
+ STRING: "STRING",
+ STRUCT: "STRUCT",
+ MAP: "MAP",
+ SET: "SET",
+ LIST: "LIST",
+ UTF8: "UTF8",
+ UTF16: "UTF16",
+}
+
+func (p TType) String() string {
+ if s, ok := typeNames[int(p)]; ok {
+ return s
+ }
+ return "Unknown"
+}
diff --git a/vendor/github.com/opentracing/opentracing-go/CHANGELOG.md b/vendor/github.com/opentracing/opentracing-go/CHANGELOG.md
new file mode 100644
index 000000000..1fc9fdf7f
--- /dev/null
+++ b/vendor/github.com/opentracing/opentracing-go/CHANGELOG.md
@@ -0,0 +1,14 @@
+Changes by Version
+==================
+
+1.1.0 (unreleased)
+-------------------
+
+- Deprecate InitGlobalTracer() in favor of SetGlobalTracer()
+
+
+1.0.0 (2016-09-26)
+-------------------
+
+- This release implements OpenTracing Specification 1.0 (http://opentracing.io/spec)
+
diff --git a/vendor/github.com/opentracing/opentracing-go/LICENSE b/vendor/github.com/opentracing/opentracing-go/LICENSE
new file mode 100644
index 000000000..f0027349e
--- /dev/null
+++ b/vendor/github.com/opentracing/opentracing-go/LICENSE
@@ -0,0 +1,201 @@
+ Apache License
+ Version 2.0, January 2004
+ http://www.apache.org/licenses/
+
+ TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
+
+ 1. Definitions.
+
+ "License" shall mean the terms and conditions for use, reproduction,
+ and distribution as defined by Sections 1 through 9 of this document.
+
+ "Licensor" shall mean the copyright owner or entity authorized by
+ the copyright owner that is granting the License.
+
+ "Legal Entity" shall mean the union of the acting entity and all
+ other entities that control, are controlled by, or are under common
+ control with that entity. For the purposes of this definition,
+ "control" means (i) the power, direct or indirect, to cause the
+ direction or management of such entity, whether by contract or
+ otherwise, or (ii) ownership of fifty percent (50%) or more of the
+ outstanding shares, or (iii) beneficial ownership of such entity.
+
+ "You" (or "Your") shall mean an individual or Legal Entity
+ exercising permissions granted by this License.
+
+ "Source" form shall mean the preferred form for making modifications,
+ including but not limited to software source code, documentation
+ source, and configuration files.
+
+ "Object" form shall mean any form resulting from mechanical
+ transformation or translation of a Source form, including but
+ not limited to compiled object code, generated documentation,
+ and conversions to other media types.
+
+ "Work" shall mean the work of authorship, whether in Source or
+ Object form, made available under the License, as indicated by a
+ copyright notice that is included in or attached to the work
+ (an example is provided in the Appendix below).
+
+ "Derivative Works" shall mean any work, whether in Source or Object
+ form, that is based on (or derived from) the Work and for which the
+ editorial revisions, annotations, elaborations, or other modifications
+ represent, as a whole, an original work of authorship. For the purposes
+ of this License, Derivative Works shall not include works that remain
+ separable from, or merely link (or bind by name) to the interfaces of,
+ the Work and Derivative Works thereof.
+
+ "Contribution" shall mean any work of authorship, including
+ the original version of the Work and any modifications or additions
+ to that Work or Derivative Works thereof, that is intentionally
+ submitted to Licensor for inclusion in the Work by the copyright owner
+ or by an individual or Legal Entity authorized to submit on behalf of
+ the copyright owner. For the purposes of this definition, "submitted"
+ means any form of electronic, verbal, or written communication sent
+ to the Licensor or its representatives, including but not limited to
+ communication on electronic mailing lists, source code control systems,
+ and issue tracking systems that are managed by, or on behalf of, the
+ Licensor for the purpose of discussing and improving the Work, but
+ excluding communication that is conspicuously marked or otherwise
+ designated in writing by the copyright owner as "Not a Contribution."
+
+ "Contributor" shall mean Licensor and any individual or Legal Entity
+ on behalf of whom a Contribution has been received by Licensor and
+ subsequently incorporated within the Work.
+
+ 2. Grant of Copyright License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ copyright license to reproduce, prepare Derivative Works of,
+ publicly display, publicly perform, sublicense, and distribute the
+ Work and such Derivative Works in Source or Object form.
+
+ 3. Grant of Patent License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ (except as stated in this section) patent license to make, have made,
+ use, offer to sell, sell, import, and otherwise transfer the Work,
+ where such license applies only to those patent claims licensable
+ by such Contributor that are necessarily infringed by their
+ Contribution(s) alone or by combination of their Contribution(s)
+ with the Work to which such Contribution(s) was submitted. If You
+ institute patent litigation against any entity (including a
+ cross-claim or counterclaim in a lawsuit) alleging that the Work
+ or a Contribution incorporated within the Work constitutes direct
+ or contributory patent infringement, then any patent licenses
+ granted to You under this License for that Work shall terminate
+ as of the date such litigation is filed.
+
+ 4. Redistribution. You may reproduce and distribute copies of the
+ Work or Derivative Works thereof in any medium, with or without
+ modifications, and in Source or Object form, provided that You
+ meet the following conditions:
+
+ (a) You must give any other recipients of the Work or
+ Derivative Works a copy of this License; and
+
+ (b) You must cause any modified files to carry prominent notices
+ stating that You changed the files; and
+
+ (c) You must retain, in the Source form of any Derivative Works
+ that You distribute, all copyright, patent, trademark, and
+ attribution notices from the Source form of the Work,
+ excluding those notices that do not pertain to any part of
+ the Derivative Works; and
+
+ (d) If the Work includes a "NOTICE" text file as part of its
+ distribution, then any Derivative Works that You distribute must
+ include a readable copy of the attribution notices contained
+ within such NOTICE file, excluding those notices that do not
+ pertain to any part of the Derivative Works, in at least one
+ of the following places: within a NOTICE text file distributed
+ as part of the Derivative Works; within the Source form or
+ documentation, if provided along with the Derivative Works; or,
+ within a display generated by the Derivative Works, if and
+ wherever such third-party notices normally appear. The contents
+ of the NOTICE file are for informational purposes only and
+ do not modify the License. You may add Your own attribution
+ notices within Derivative Works that You distribute, alongside
+ or as an addendum to the NOTICE text from the Work, provided
+ that such additional attribution notices cannot be construed
+ as modifying the License.
+
+ You may add Your own copyright statement to Your modifications and
+ may provide additional or different license terms and conditions
+ for use, reproduction, or distribution of Your modifications, or
+ for any such Derivative Works as a whole, provided Your use,
+ reproduction, and distribution of the Work otherwise complies with
+ the conditions stated in this License.
+
+ 5. Submission of Contributions. Unless You explicitly state otherwise,
+ any Contribution intentionally submitted for inclusion in the Work
+ by You to the Licensor shall be under the terms and conditions of
+ this License, without any additional terms or conditions.
+ Notwithstanding the above, nothing herein shall supersede or modify
+ the terms of any separate license agreement you may have executed
+ with Licensor regarding such Contributions.
+
+ 6. Trademarks. This License does not grant permission to use the trade
+ names, trademarks, service marks, or product names of the Licensor,
+ except as required for reasonable and customary use in describing the
+ origin of the Work and reproducing the content of the NOTICE file.
+
+ 7. Disclaimer of Warranty. Unless required by applicable law or
+ agreed to in writing, Licensor provides the Work (and each
+ Contributor provides its Contributions) on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
+ implied, including, without limitation, any warranties or conditions
+ of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
+ PARTICULAR PURPOSE. You are solely responsible for determining the
+ appropriateness of using or redistributing the Work and assume any
+ risks associated with Your exercise of permissions under this License.
+
+ 8. Limitation of Liability. In no event and under no legal theory,
+ whether in tort (including negligence), contract, or otherwise,
+ unless required by applicable law (such as deliberate and grossly
+ negligent acts) or agreed to in writing, shall any Contributor be
+ liable to You for damages, including any direct, indirect, special,
+ incidental, or consequential damages of any character arising as a
+ result of this License or out of the use or inability to use the
+ Work (including but not limited to damages for loss of goodwill,
+ work stoppage, computer failure or malfunction, or any and all
+ other commercial damages or losses), even if such Contributor
+ has been advised of the possibility of such damages.
+
+ 9. Accepting Warranty or Additional Liability. While redistributing
+ the Work or Derivative Works thereof, You may choose to offer,
+ and charge a fee for, acceptance of support, warranty, indemnity,
+ or other liability obligations and/or rights consistent with this
+ License. However, in accepting such obligations, You may act only
+ on Your own behalf and on Your sole responsibility, not on behalf
+ of any other Contributor, and only if You agree to indemnify,
+ defend, and hold each Contributor harmless for any liability
+ incurred by, or claims asserted against, such Contributor by reason
+ of your accepting any such warranty or additional liability.
+
+ END OF TERMS AND CONDITIONS
+
+ APPENDIX: How to apply the Apache License to your work.
+
+ To apply the Apache License to your work, attach the following
+ boilerplate notice, with the fields enclosed by brackets "{}"
+ replaced with your own identifying information. (Don't include
+ the brackets!) The text should be enclosed in the appropriate
+ comment syntax for the file format. We also recommend that a
+ file or class name and description of purpose be included on the
+ same "printed page" as the copyright notice for easier
+ identification within third-party archives.
+
+ Copyright 2016 The OpenTracing Authors
+
+ 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.
diff --git a/vendor/github.com/opentracing/opentracing-go/Makefile b/vendor/github.com/opentracing/opentracing-go/Makefile
new file mode 100644
index 000000000..d49a5c0d4
--- /dev/null
+++ b/vendor/github.com/opentracing/opentracing-go/Makefile
@@ -0,0 +1,32 @@
+PACKAGES := . ./mocktracer/... ./ext/...
+
+.DEFAULT_GOAL := test-and-lint
+
+.PHONE: test-and-lint
+
+test-and-lint: test lint
+
+.PHONY: test
+test:
+ go test -v -cover -race ./...
+
+cover:
+ @rm -rf cover-all.out
+ $(foreach pkg, $(PACKAGES), $(MAKE) cover-pkg PKG=$(pkg) || true;)
+ @grep mode: cover.out > coverage.out
+ @cat cover-all.out >> coverage.out
+ go tool cover -html=coverage.out -o cover.html
+ @rm -rf cover.out cover-all.out coverage.out
+
+cover-pkg:
+ go test -coverprofile cover.out $(PKG)
+ @grep -v mode: cover.out >> cover-all.out
+
+.PHONY: lint
+lint:
+ go fmt ./...
+ golint ./...
+ @# Run again with magic to exit non-zero if golint outputs anything.
+ @! (golint ./... | read dummy)
+ go vet ./...
+
diff --git a/vendor/github.com/opentracing/opentracing-go/README.md b/vendor/github.com/opentracing/opentracing-go/README.md
new file mode 100644
index 000000000..31cb35c17
--- /dev/null
+++ b/vendor/github.com/opentracing/opentracing-go/README.md
@@ -0,0 +1,171 @@
+[![Gitter chat](http://img.shields.io/badge/gitter-join%20chat%20%E2%86%92-brightgreen.svg)](https://gitter.im/opentracing/public) [![Build Status](https://travis-ci.org/opentracing/opentracing-go.svg?branch=master)](https://travis-ci.org/opentracing/opentracing-go) [![GoDoc](https://godoc.org/github.com/opentracing/opentracing-go?status.svg)](http://godoc.org/github.com/opentracing/opentracing-go)
+[![Sourcegraph Badge](https://sourcegraph.com/github.com/opentracing/opentracing-go/-/badge.svg)](https://sourcegraph.com/github.com/opentracing/opentracing-go?badge)
+
+# OpenTracing API for Go
+
+This package is a Go platform API for OpenTracing.
+
+## Required Reading
+
+In order to understand the Go platform API, one must first be familiar with the
+[OpenTracing project](http://opentracing.io) and
+[terminology](https://opentracing.io/specification/) more specifically.
+
+## API overview for those adding instrumentation
+
+Everyday consumers of this `opentracing` package really only need to worry
+about a couple of key abstractions: the `StartSpan` function, the `Span`
+interface, and binding a `Tracer` at `main()`-time. Here are code snippets
+demonstrating some important use cases.
+
+#### Singleton initialization
+
+The simplest starting point is `./default_tracer.go`. As early as possible, call
+
+```go
+ import "github.com/opentracing/opentracing-go"
+ import ".../some_tracing_impl"
+
+ func main() {
+ opentracing.SetGlobalTracer(
+ // tracing impl specific:
+ some_tracing_impl.New(...),
+ )
+ ...
+ }
+```
+
+#### Non-Singleton initialization
+
+If you prefer direct control to singletons, manage ownership of the
+`opentracing.Tracer` implementation explicitly.
+
+#### Creating a Span given an existing Go `context.Context`
+
+If you use `context.Context` in your application, OpenTracing's Go library will
+happily rely on it for `Span` propagation. To start a new (blocking child)
+`Span`, you can use `StartSpanFromContext`.
+
+```go
+ func xyz(ctx context.Context, ...) {
+ ...
+ span, ctx := opentracing.StartSpanFromContext(ctx, "operation_name")
+ defer span.Finish()
+ span.LogFields(
+ log.String("event", "soft error"),
+ log.String("type", "cache timeout"),
+ log.Int("waited.millis", 1500))
+ ...
+ }
+```
+
+#### Starting an empty trace by creating a "root span"
+
+It's always possible to create a "root" `Span` with no parent or other causal
+reference.
+
+```go
+ func xyz() {
+ ...
+ sp := opentracing.StartSpan("operation_name")
+ defer sp.Finish()
+ ...
+ }
+```
+
+#### Creating a (child) Span given an existing (parent) Span
+
+```go
+ func xyz(parentSpan opentracing.Span, ...) {
+ ...
+ sp := opentracing.StartSpan(
+ "operation_name",
+ opentracing.ChildOf(parentSpan.Context()))
+ defer sp.Finish()
+ ...
+ }
+```
+
+#### Serializing to the wire
+
+```go
+ func makeSomeRequest(ctx context.Context) ... {
+ if span := opentracing.SpanFromContext(ctx); span != nil {
+ httpClient := &http.Client{}
+ httpReq, _ := http.NewRequest("GET", "http://myservice/", nil)
+
+ // Transmit the span's TraceContext as HTTP headers on our
+ // outbound request.
+ opentracing.GlobalTracer().Inject(
+ span.Context(),
+ opentracing.HTTPHeaders,
+ opentracing.HTTPHeadersCarrier(httpReq.Header))
+
+ resp, err := httpClient.Do(httpReq)
+ ...
+ }
+ ...
+ }
+```
+
+#### Deserializing from the wire
+
+```go
+ http.HandleFunc("/", func(w http.ResponseWriter, req *http.Request) {
+ var serverSpan opentracing.Span
+ appSpecificOperationName := ...
+ wireContext, err := opentracing.GlobalTracer().Extract(
+ opentracing.HTTPHeaders,
+ opentracing.HTTPHeadersCarrier(req.Header))
+ if err != nil {
+ // Optionally record something about err here
+ }
+
+ // Create the span referring to the RPC client if available.
+ // If wireContext == nil, a root span will be created.
+ serverSpan = opentracing.StartSpan(
+ appSpecificOperationName,
+ ext.RPCServerOption(wireContext))
+
+ defer serverSpan.Finish()
+
+ ctx := opentracing.ContextWithSpan(context.Background(), serverSpan)
+ ...
+ }
+```
+
+#### Conditionally capture a field using `log.Noop`
+
+In some situations, you may want to dynamically decide whether or not
+to log a field. For example, you may want to capture additional data,
+such as a customer ID, in non-production environments:
+
+```go
+ func Customer(order *Order) log.Field {
+ if os.Getenv("ENVIRONMENT") == "dev" {
+ return log.String("customer", order.Customer.ID)
+ }
+ return log.Noop()
+ }
+```
+
+#### Goroutine-safety
+
+The entire public API is goroutine-safe and does not require external
+synchronization.
+
+## API pointers for those implementing a tracing system
+
+Tracing system implementors may be able to reuse or copy-paste-modify the `basictracer` package, found [here](https://github.com/opentracing/basictracer-go). In particular, see `basictracer.New(...)`.
+
+## API compatibility
+
+For the time being, "mild" backwards-incompatible changes may be made without changing the major version number. As OpenTracing and `opentracing-go` mature, backwards compatibility will become more of a priority.
+
+## Tracer test suite
+
+A test suite is available in the [harness](https://godoc.org/github.com/opentracing/opentracing-go/harness) package that can assist Tracer implementors to assert that their Tracer is working correctly.
+
+## Licensing
+
+[Apache 2.0 License](./LICENSE).
diff --git a/vendor/github.com/opentracing/opentracing-go/ext/tags.go b/vendor/github.com/opentracing/opentracing-go/ext/tags.go
new file mode 100644
index 000000000..8800129a2
--- /dev/null
+++ b/vendor/github.com/opentracing/opentracing-go/ext/tags.go
@@ -0,0 +1,210 @@
+package ext
+
+import opentracing "github.com/opentracing/opentracing-go"
+
+// These constants define common tag names recommended for better portability across
+// tracing systems and languages/platforms.
+//
+// The tag names are defined as typed strings, so that in addition to the usual use
+//
+// span.setTag(TagName, value)
+//
+// they also support value type validation via this additional syntax:
+//
+// TagName.Set(span, value)
+//
+var (
+ //////////////////////////////////////////////////////////////////////
+ // SpanKind (client/server or producer/consumer)
+ //////////////////////////////////////////////////////////////////////
+
+ // SpanKind hints at relationship between spans, e.g. client/server
+ SpanKind = spanKindTagName("span.kind")
+
+ // SpanKindRPCClient marks a span representing the client-side of an RPC
+ // or other remote call
+ SpanKindRPCClientEnum = SpanKindEnum("client")
+ SpanKindRPCClient = opentracing.Tag{Key: string(SpanKind), Value: SpanKindRPCClientEnum}
+
+ // SpanKindRPCServer marks a span representing the server-side of an RPC
+ // or other remote call
+ SpanKindRPCServerEnum = SpanKindEnum("server")
+ SpanKindRPCServer = opentracing.Tag{Key: string(SpanKind), Value: SpanKindRPCServerEnum}
+
+ // SpanKindProducer marks a span representing the producer-side of a
+ // message bus
+ SpanKindProducerEnum = SpanKindEnum("producer")
+ SpanKindProducer = opentracing.Tag{Key: string(SpanKind), Value: SpanKindProducerEnum}
+
+ // SpanKindConsumer marks a span representing the consumer-side of a
+ // message bus
+ SpanKindConsumerEnum = SpanKindEnum("consumer")
+ SpanKindConsumer = opentracing.Tag{Key: string(SpanKind), Value: SpanKindConsumerEnum}
+
+ //////////////////////////////////////////////////////////////////////
+ // Component name
+ //////////////////////////////////////////////////////////////////////
+
+ // Component is a low-cardinality identifier of the module, library,
+ // or package that is generating a span.
+ Component = stringTagName("component")
+
+ //////////////////////////////////////////////////////////////////////
+ // Sampling hint
+ //////////////////////////////////////////////////////////////////////
+
+ // SamplingPriority determines the priority of sampling this Span.
+ SamplingPriority = uint16TagName("sampling.priority")
+
+ //////////////////////////////////////////////////////////////////////
+ // Peer tags. These tags can be emitted by either client-side of
+ // server-side to describe the other side/service in a peer-to-peer
+ // communications, like an RPC call.
+ //////////////////////////////////////////////////////////////////////
+
+ // PeerService records the service name of the peer.
+ PeerService = stringTagName("peer.service")
+
+ // PeerAddress records the address name of the peer. This may be a "ip:port",
+ // a bare "hostname", a FQDN or even a database DSN substring
+ // like "mysql://username@127.0.0.1:3306/dbname"
+ PeerAddress = stringTagName("peer.address")
+
+ // PeerHostname records the host name of the peer
+ PeerHostname = stringTagName("peer.hostname")
+
+ // PeerHostIPv4 records IP v4 host address of the peer
+ PeerHostIPv4 = ipv4Tag("peer.ipv4")
+
+ // PeerHostIPv6 records IP v6 host address of the peer
+ PeerHostIPv6 = stringTagName("peer.ipv6")
+
+ // PeerPort records port number of the peer
+ PeerPort = uint16TagName("peer.port")
+
+ //////////////////////////////////////////////////////////////////////
+ // HTTP Tags
+ //////////////////////////////////////////////////////////////////////
+
+ // HTTPUrl should be the URL of the request being handled in this segment
+ // of the trace, in standard URI format. The protocol is optional.
+ HTTPUrl = stringTagName("http.url")
+
+ // HTTPMethod is the HTTP method of the request, and is case-insensitive.
+ HTTPMethod = stringTagName("http.method")
+
+ // HTTPStatusCode is the numeric HTTP status code (200, 404, etc) of the
+ // HTTP response.
+ HTTPStatusCode = uint16TagName("http.status_code")
+
+ //////////////////////////////////////////////////////////////////////
+ // DB Tags
+ //////////////////////////////////////////////////////////////////////
+
+ // DBInstance is database instance name.
+ DBInstance = stringTagName("db.instance")
+
+ // DBStatement is a database statement for the given database type.
+ // It can be a query or a prepared statement (i.e., before substitution).
+ DBStatement = stringTagName("db.statement")
+
+ // DBType is a database type. For any SQL database, "sql".
+ // For others, the lower-case database category, e.g. "redis"
+ DBType = stringTagName("db.type")
+
+ // DBUser is a username for accessing database.
+ DBUser = stringTagName("db.user")
+
+ //////////////////////////////////////////////////////////////////////
+ // Message Bus Tag
+ //////////////////////////////////////////////////////////////////////
+
+ // MessageBusDestination is an address at which messages can be exchanged
+ MessageBusDestination = stringTagName("message_bus.destination")
+
+ //////////////////////////////////////////////////////////////////////
+ // Error Tag
+ //////////////////////////////////////////////////////////////////////
+
+ // Error indicates that operation represented by the span resulted in an error.
+ Error = boolTagName("error")
+)
+
+// ---
+
+// SpanKindEnum represents common span types
+type SpanKindEnum string
+
+type spanKindTagName string
+
+// Set adds a string tag to the `span`
+func (tag spanKindTagName) Set(span opentracing.Span, value SpanKindEnum) {
+ span.SetTag(string(tag), value)
+}
+
+type rpcServerOption struct {
+ clientContext opentracing.SpanContext
+}
+
+func (r rpcServerOption) Apply(o *opentracing.StartSpanOptions) {
+ if r.clientContext != nil {
+ opentracing.ChildOf(r.clientContext).Apply(o)
+ }
+ SpanKindRPCServer.Apply(o)
+}
+
+// RPCServerOption returns a StartSpanOption appropriate for an RPC server span
+// with `client` representing the metadata for the remote peer Span if available.
+// In case client == nil, due to the client not being instrumented, this RPC
+// server span will be a root span.
+func RPCServerOption(client opentracing.SpanContext) opentracing.StartSpanOption {
+ return rpcServerOption{client}
+}
+
+// ---
+
+type stringTagName string
+
+// Set adds a string tag to the `span`
+func (tag stringTagName) Set(span opentracing.Span, value string) {
+ span.SetTag(string(tag), value)
+}
+
+// ---
+
+type uint32TagName string
+
+// Set adds a uint32 tag to the `span`
+func (tag uint32TagName) Set(span opentracing.Span, value uint32) {
+ span.SetTag(string(tag), value)
+}
+
+// ---
+
+type uint16TagName string
+
+// Set adds a uint16 tag to the `span`
+func (tag uint16TagName) Set(span opentracing.Span, value uint16) {
+ span.SetTag(string(tag), value)
+}
+
+// ---
+
+type boolTagName string
+
+// Add adds a bool tag to the `span`
+func (tag boolTagName) Set(span opentracing.Span, value bool) {
+ span.SetTag(string(tag), value)
+}
+
+type ipv4Tag string
+
+// Set adds IP v4 host address of the peer as an uint32 value to the `span`, keep this for backward and zipkin compatibility
+func (tag ipv4Tag) Set(span opentracing.Span, value uint32) {
+ span.SetTag(string(tag), value)
+}
+
+// SetString records IP v4 host address of the peer as a .-separated tuple to the `span`. E.g., "127.0.0.1"
+func (tag ipv4Tag) SetString(span opentracing.Span, value string) {
+ span.SetTag(string(tag), value)
+}
diff --git a/vendor/github.com/opentracing/opentracing-go/globaltracer.go b/vendor/github.com/opentracing/opentracing-go/globaltracer.go
new file mode 100644
index 000000000..8c8e793ff
--- /dev/null
+++ b/vendor/github.com/opentracing/opentracing-go/globaltracer.go
@@ -0,0 +1,32 @@
+package opentracing
+
+var (
+ globalTracer Tracer = NoopTracer{}
+)
+
+// SetGlobalTracer sets the [singleton] opentracing.Tracer returned by
+// GlobalTracer(). Those who use GlobalTracer (rather than directly manage an
+// opentracing.Tracer instance) should call SetGlobalTracer as early as
+// possible in main(), prior to calling the `StartSpan` global func below.
+// Prior to calling `SetGlobalTracer`, any Spans started via the `StartSpan`
+// (etc) globals are noops.
+func SetGlobalTracer(tracer Tracer) {
+ globalTracer = tracer
+}
+
+// GlobalTracer returns the global singleton `Tracer` implementation.
+// Before `SetGlobalTracer()` is called, the `GlobalTracer()` is a noop
+// implementation that drops all data handed to it.
+func GlobalTracer() Tracer {
+ return globalTracer
+}
+
+// StartSpan defers to `Tracer.StartSpan`. See `GlobalTracer()`.
+func StartSpan(operationName string, opts ...StartSpanOption) Span {
+ return globalTracer.StartSpan(operationName, opts...)
+}
+
+// InitGlobalTracer is deprecated. Please use SetGlobalTracer.
+func InitGlobalTracer(tracer Tracer) {
+ SetGlobalTracer(tracer)
+}
diff --git a/vendor/github.com/opentracing/opentracing-go/gocontext.go b/vendor/github.com/opentracing/opentracing-go/gocontext.go
new file mode 100644
index 000000000..05a62e70b
--- /dev/null
+++ b/vendor/github.com/opentracing/opentracing-go/gocontext.go
@@ -0,0 +1,54 @@
+package opentracing
+
+import "context"
+
+type contextKey struct{}
+
+var activeSpanKey = contextKey{}
+
+// ContextWithSpan returns a new `context.Context` that holds a reference to
+// `span`'s SpanContext.
+func ContextWithSpan(ctx context.Context, span Span) context.Context {
+ return context.WithValue(ctx, activeSpanKey, span)
+}
+
+// SpanFromContext returns the `Span` previously associated with `ctx`, or
+// `nil` if no such `Span` could be found.
+//
+// NOTE: context.Context != SpanContext: the former is Go's intra-process
+// context propagation mechanism, and the latter houses OpenTracing's per-Span
+// identity and baggage information.
+func SpanFromContext(ctx context.Context) Span {
+ val := ctx.Value(activeSpanKey)
+ if sp, ok := val.(Span); ok {
+ return sp
+ }
+ return nil
+}
+
+// StartSpanFromContext starts and returns a Span with `operationName`, using
+// any Span found within `ctx` as a ChildOfRef. If no such parent could be
+// found, StartSpanFromContext creates a root (parentless) Span.
+//
+// The second return value is a context.Context object built around the
+// returned Span.
+//
+// Example usage:
+//
+// SomeFunction(ctx context.Context, ...) {
+// sp, ctx := opentracing.StartSpanFromContext(ctx, "SomeFunction")
+// defer sp.Finish()
+// ...
+// }
+func StartSpanFromContext(ctx context.Context, operationName string, opts ...StartSpanOption) (Span, context.Context) {
+ return startSpanFromContextWithTracer(ctx, GlobalTracer(), operationName, opts...)
+}
+
+// startSpanFromContextWithTracer is factored out for testing purposes.
+func startSpanFromContextWithTracer(ctx context.Context, tracer Tracer, operationName string, opts ...StartSpanOption) (Span, context.Context) {
+ if parentSpan := SpanFromContext(ctx); parentSpan != nil {
+ opts = append(opts, ChildOf(parentSpan.Context()))
+ }
+ span := tracer.StartSpan(operationName, opts...)
+ return span, ContextWithSpan(ctx, span)
+}
diff --git a/vendor/github.com/opentracing/opentracing-go/log/field.go b/vendor/github.com/opentracing/opentracing-go/log/field.go
new file mode 100644
index 000000000..50feea341
--- /dev/null
+++ b/vendor/github.com/opentracing/opentracing-go/log/field.go
@@ -0,0 +1,269 @@
+package log
+
+import (
+ "fmt"
+ "math"
+)
+
+type fieldType int
+
+const (
+ stringType fieldType = iota
+ boolType
+ intType
+ int32Type
+ uint32Type
+ int64Type
+ uint64Type
+ float32Type
+ float64Type
+ errorType
+ objectType
+ lazyLoggerType
+ noopType
+)
+
+// Field instances are constructed via LogBool, LogString, and so on.
+// Tracing implementations may then handle them via the Field.Marshal
+// method.
+//
+// "heavily influenced by" (i.e., partially stolen from)
+// https://github.com/uber-go/zap
+type Field struct {
+ key string
+ fieldType fieldType
+ numericVal int64
+ stringVal string
+ interfaceVal interface{}
+}
+
+// String adds a string-valued key:value pair to a Span.LogFields() record
+func String(key, val string) Field {
+ return Field{
+ key: key,
+ fieldType: stringType,
+ stringVal: val,
+ }
+}
+
+// Bool adds a bool-valued key:value pair to a Span.LogFields() record
+func Bool(key string, val bool) Field {
+ var numericVal int64
+ if val {
+ numericVal = 1
+ }
+ return Field{
+ key: key,
+ fieldType: boolType,
+ numericVal: numericVal,
+ }
+}
+
+// Int adds an int-valued key:value pair to a Span.LogFields() record
+func Int(key string, val int) Field {
+ return Field{
+ key: key,
+ fieldType: intType,
+ numericVal: int64(val),
+ }
+}
+
+// Int32 adds an int32-valued key:value pair to a Span.LogFields() record
+func Int32(key string, val int32) Field {
+ return Field{
+ key: key,
+ fieldType: int32Type,
+ numericVal: int64(val),
+ }
+}
+
+// Int64 adds an int64-valued key:value pair to a Span.LogFields() record
+func Int64(key string, val int64) Field {
+ return Field{
+ key: key,
+ fieldType: int64Type,
+ numericVal: val,
+ }
+}
+
+// Uint32 adds a uint32-valued key:value pair to a Span.LogFields() record
+func Uint32(key string, val uint32) Field {
+ return Field{
+ key: key,
+ fieldType: uint32Type,
+ numericVal: int64(val),
+ }
+}
+
+// Uint64 adds a uint64-valued key:value pair to a Span.LogFields() record
+func Uint64(key string, val uint64) Field {
+ return Field{
+ key: key,
+ fieldType: uint64Type,
+ numericVal: int64(val),
+ }
+}
+
+// Float32 adds a float32-valued key:value pair to a Span.LogFields() record
+func Float32(key string, val float32) Field {
+ return Field{
+ key: key,
+ fieldType: float32Type,
+ numericVal: int64(math.Float32bits(val)),
+ }
+}
+
+// Float64 adds a float64-valued key:value pair to a Span.LogFields() record
+func Float64(key string, val float64) Field {
+ return Field{
+ key: key,
+ fieldType: float64Type,
+ numericVal: int64(math.Float64bits(val)),
+ }
+}
+
+// Error adds an error with the key "error" to a Span.LogFields() record
+func Error(err error) Field {
+ return Field{
+ key: "error",
+ fieldType: errorType,
+ interfaceVal: err,
+ }
+}
+
+// Object adds an object-valued key:value pair to a Span.LogFields() record
+func Object(key string, obj interface{}) Field {
+ return Field{
+ key: key,
+ fieldType: objectType,
+ interfaceVal: obj,
+ }
+}
+
+// LazyLogger allows for user-defined, late-bound logging of arbitrary data
+type LazyLogger func(fv Encoder)
+
+// Lazy adds a LazyLogger to a Span.LogFields() record; the tracing
+// implementation will call the LazyLogger function at an indefinite time in
+// the future (after Lazy() returns).
+func Lazy(ll LazyLogger) Field {
+ return Field{
+ fieldType: lazyLoggerType,
+ interfaceVal: ll,
+ }
+}
+
+// Noop creates a no-op log field that should be ignored by the tracer.
+// It can be used to capture optional fields, for example those that should
+// only be logged in non-production environment:
+//
+// func customerField(order *Order) log.Field {
+// if os.Getenv("ENVIRONMENT") == "dev" {
+// return log.String("customer", order.Customer.ID)
+// }
+// return log.Noop()
+// }
+//
+// span.LogFields(log.String("event", "purchase"), customerField(order))
+//
+func Noop() Field {
+ return Field{
+ fieldType: noopType,
+ }
+}
+
+// Encoder allows access to the contents of a Field (via a call to
+// Field.Marshal).
+//
+// Tracer implementations typically provide an implementation of Encoder;
+// OpenTracing callers typically do not need to concern themselves with it.
+type Encoder interface {
+ EmitString(key, value string)
+ EmitBool(key string, value bool)
+ EmitInt(key string, value int)
+ EmitInt32(key string, value int32)
+ EmitInt64(key string, value int64)
+ EmitUint32(key string, value uint32)
+ EmitUint64(key string, value uint64)
+ EmitFloat32(key string, value float32)
+ EmitFloat64(key string, value float64)
+ EmitObject(key string, value interface{})
+ EmitLazyLogger(value LazyLogger)
+}
+
+// Marshal passes a Field instance through to the appropriate
+// field-type-specific method of an Encoder.
+func (lf Field) Marshal(visitor Encoder) {
+ switch lf.fieldType {
+ case stringType:
+ visitor.EmitString(lf.key, lf.stringVal)
+ case boolType:
+ visitor.EmitBool(lf.key, lf.numericVal != 0)
+ case intType:
+ visitor.EmitInt(lf.key, int(lf.numericVal))
+ case int32Type:
+ visitor.EmitInt32(lf.key, int32(lf.numericVal))
+ case int64Type:
+ visitor.EmitInt64(lf.key, int64(lf.numericVal))
+ case uint32Type:
+ visitor.EmitUint32(lf.key, uint32(lf.numericVal))
+ case uint64Type:
+ visitor.EmitUint64(lf.key, uint64(lf.numericVal))
+ case float32Type:
+ visitor.EmitFloat32(lf.key, math.Float32frombits(uint32(lf.numericVal)))
+ case float64Type:
+ visitor.EmitFloat64(lf.key, math.Float64frombits(uint64(lf.numericVal)))
+ case errorType:
+ if err, ok := lf.interfaceVal.(error); ok {
+ visitor.EmitString(lf.key, err.Error())
+ } else {
+ visitor.EmitString(lf.key, "<nil>")
+ }
+ case objectType:
+ visitor.EmitObject(lf.key, lf.interfaceVal)
+ case lazyLoggerType:
+ visitor.EmitLazyLogger(lf.interfaceVal.(LazyLogger))
+ case noopType:
+ // intentionally left blank
+ }
+}
+
+// Key returns the field's key.
+func (lf Field) Key() string {
+ return lf.key
+}
+
+// Value returns the field's value as interface{}.
+func (lf Field) Value() interface{} {
+ switch lf.fieldType {
+ case stringType:
+ return lf.stringVal
+ case boolType:
+ return lf.numericVal != 0
+ case intType:
+ return int(lf.numericVal)
+ case int32Type:
+ return int32(lf.numericVal)
+ case int64Type:
+ return int64(lf.numericVal)
+ case uint32Type:
+ return uint32(lf.numericVal)
+ case uint64Type:
+ return uint64(lf.numericVal)
+ case float32Type:
+ return math.Float32frombits(uint32(lf.numericVal))
+ case float64Type:
+ return math.Float64frombits(uint64(lf.numericVal))
+ case errorType, objectType, lazyLoggerType:
+ return lf.interfaceVal
+ case noopType:
+ return nil
+ default:
+ return nil
+ }
+}
+
+// String returns a string representation of the key and value.
+func (lf Field) String() string {
+ return fmt.Sprint(lf.key, ":", lf.Value())
+}
diff --git a/vendor/github.com/opentracing/opentracing-go/log/util.go b/vendor/github.com/opentracing/opentracing-go/log/util.go
new file mode 100644
index 000000000..3832feb5c
--- /dev/null
+++ b/vendor/github.com/opentracing/opentracing-go/log/util.go
@@ -0,0 +1,54 @@
+package log
+
+import "fmt"
+
+// InterleavedKVToFields converts keyValues a la Span.LogKV() to a Field slice
+// a la Span.LogFields().
+func InterleavedKVToFields(keyValues ...interface{}) ([]Field, error) {
+ if len(keyValues)%2 != 0 {
+ return nil, fmt.Errorf("non-even keyValues len: %d", len(keyValues))
+ }
+ fields := make([]Field, len(keyValues)/2)
+ for i := 0; i*2 < len(keyValues); i++ {
+ key, ok := keyValues[i*2].(string)
+ if !ok {
+ return nil, fmt.Errorf(
+ "non-string key (pair #%d): %T",
+ i, keyValues[i*2])
+ }
+ switch typedVal := keyValues[i*2+1].(type) {
+ case bool:
+ fields[i] = Bool(key, typedVal)
+ case string:
+ fields[i] = String(key, typedVal)
+ case int:
+ fields[i] = Int(key, typedVal)
+ case int8:
+ fields[i] = Int32(key, int32(typedVal))
+ case int16:
+ fields[i] = Int32(key, int32(typedVal))
+ case int32:
+ fields[i] = Int32(key, typedVal)
+ case int64:
+ fields[i] = Int64(key, typedVal)
+ case uint:
+ fields[i] = Uint64(key, uint64(typedVal))
+ case uint64:
+ fields[i] = Uint64(key, typedVal)
+ case uint8:
+ fields[i] = Uint32(key, uint32(typedVal))
+ case uint16:
+ fields[i] = Uint32(key, uint32(typedVal))
+ case uint32:
+ fields[i] = Uint32(key, typedVal)
+ case float32:
+ fields[i] = Float32(key, typedVal)
+ case float64:
+ fields[i] = Float64(key, typedVal)
+ default:
+ // When in doubt, coerce to a string
+ fields[i] = String(key, fmt.Sprint(typedVal))
+ }
+ }
+ return fields, nil
+}
diff --git a/vendor/github.com/opentracing/opentracing-go/noop.go b/vendor/github.com/opentracing/opentracing-go/noop.go
new file mode 100644
index 000000000..0d32f692c
--- /dev/null
+++ b/vendor/github.com/opentracing/opentracing-go/noop.go
@@ -0,0 +1,64 @@
+package opentracing
+
+import "github.com/opentracing/opentracing-go/log"
+
+// A NoopTracer is a trivial, minimum overhead implementation of Tracer
+// for which all operations are no-ops.
+//
+// The primary use of this implementation is in libraries, such as RPC
+// frameworks, that make tracing an optional feature controlled by the
+// end user. A no-op implementation allows said libraries to use it
+// as the default Tracer and to write instrumentation that does
+// not need to keep checking if the tracer instance is nil.
+//
+// For the same reason, the NoopTracer is the default "global" tracer
+// (see GlobalTracer and SetGlobalTracer functions).
+//
+// WARNING: NoopTracer does not support baggage propagation.
+type NoopTracer struct{}
+
+type noopSpan struct{}
+type noopSpanContext struct{}
+
+var (
+ defaultNoopSpanContext = noopSpanContext{}
+ defaultNoopSpan = noopSpan{}
+ defaultNoopTracer = NoopTracer{}
+)
+
+const (
+ emptyString = ""
+)
+
+// noopSpanContext:
+func (n noopSpanContext) ForeachBaggageItem(handler func(k, v string) bool) {}
+
+// noopSpan:
+func (n noopSpan) Context() SpanContext { return defaultNoopSpanContext }
+func (n noopSpan) SetBaggageItem(key, val string) Span { return defaultNoopSpan }
+func (n noopSpan) BaggageItem(key string) string { return emptyString }
+func (n noopSpan) SetTag(key string, value interface{}) Span { return n }
+func (n noopSpan) LogFields(fields ...log.Field) {}
+func (n noopSpan) LogKV(keyVals ...interface{}) {}
+func (n noopSpan) Finish() {}
+func (n noopSpan) FinishWithOptions(opts FinishOptions) {}
+func (n noopSpan) SetOperationName(operationName string) Span { return n }
+func (n noopSpan) Tracer() Tracer { return defaultNoopTracer }
+func (n noopSpan) LogEvent(event string) {}
+func (n noopSpan) LogEventWithPayload(event string, payload interface{}) {}
+func (n noopSpan) Log(data LogData) {}
+
+// StartSpan belongs to the Tracer interface.
+func (n NoopTracer) StartSpan(operationName string, opts ...StartSpanOption) Span {
+ return defaultNoopSpan
+}
+
+// Inject belongs to the Tracer interface.
+func (n NoopTracer) Inject(sp SpanContext, format interface{}, carrier interface{}) error {
+ return nil
+}
+
+// Extract belongs to the Tracer interface.
+func (n NoopTracer) Extract(format interface{}, carrier interface{}) (SpanContext, error) {
+ return nil, ErrSpanContextNotFound
+}
diff --git a/vendor/github.com/opentracing/opentracing-go/propagation.go b/vendor/github.com/opentracing/opentracing-go/propagation.go
new file mode 100644
index 000000000..b0c275eb0
--- /dev/null
+++ b/vendor/github.com/opentracing/opentracing-go/propagation.go
@@ -0,0 +1,176 @@
+package opentracing
+
+import (
+ "errors"
+ "net/http"
+)
+
+///////////////////////////////////////////////////////////////////////////////
+// CORE PROPAGATION INTERFACES:
+///////////////////////////////////////////////////////////////////////////////
+
+var (
+ // ErrUnsupportedFormat occurs when the `format` passed to Tracer.Inject() or
+ // Tracer.Extract() is not recognized by the Tracer implementation.
+ ErrUnsupportedFormat = errors.New("opentracing: Unknown or unsupported Inject/Extract format")
+
+ // ErrSpanContextNotFound occurs when the `carrier` passed to
+ // Tracer.Extract() is valid and uncorrupted but has insufficient
+ // information to extract a SpanContext.
+ ErrSpanContextNotFound = errors.New("opentracing: SpanContext not found in Extract carrier")
+
+ // ErrInvalidSpanContext errors occur when Tracer.Inject() is asked to
+ // operate on a SpanContext which it is not prepared to handle (for
+ // example, since it was created by a different tracer implementation).
+ ErrInvalidSpanContext = errors.New("opentracing: SpanContext type incompatible with tracer")
+
+ // ErrInvalidCarrier errors occur when Tracer.Inject() or Tracer.Extract()
+ // implementations expect a different type of `carrier` than they are
+ // given.
+ ErrInvalidCarrier = errors.New("opentracing: Invalid Inject/Extract carrier")
+
+ // ErrSpanContextCorrupted occurs when the `carrier` passed to
+ // Tracer.Extract() is of the expected type but is corrupted.
+ ErrSpanContextCorrupted = errors.New("opentracing: SpanContext data corrupted in Extract carrier")
+)
+
+///////////////////////////////////////////////////////////////////////////////
+// BUILTIN PROPAGATION FORMATS:
+///////////////////////////////////////////////////////////////////////////////
+
+// BuiltinFormat is used to demarcate the values within package `opentracing`
+// that are intended for use with the Tracer.Inject() and Tracer.Extract()
+// methods.
+type BuiltinFormat byte
+
+const (
+ // Binary represents SpanContexts as opaque binary data.
+ //
+ // For Tracer.Inject(): the carrier must be an `io.Writer`.
+ //
+ // For Tracer.Extract(): the carrier must be an `io.Reader`.
+ Binary BuiltinFormat = iota
+
+ // TextMap represents SpanContexts as key:value string pairs.
+ //
+ // Unlike HTTPHeaders, the TextMap format does not restrict the key or
+ // value character sets in any way.
+ //
+ // For Tracer.Inject(): the carrier must be a `TextMapWriter`.
+ //
+ // For Tracer.Extract(): the carrier must be a `TextMapReader`.
+ TextMap
+
+ // HTTPHeaders represents SpanContexts as HTTP header string pairs.
+ //
+ // Unlike TextMap, the HTTPHeaders format requires that the keys and values
+ // be valid as HTTP headers as-is (i.e., character casing may be unstable
+ // and special characters are disallowed in keys, values should be
+ // URL-escaped, etc).
+ //
+ // For Tracer.Inject(): the carrier must be a `TextMapWriter`.
+ //
+ // For Tracer.Extract(): the carrier must be a `TextMapReader`.
+ //
+ // See HTTPHeadersCarrier for an implementation of both TextMapWriter
+ // and TextMapReader that defers to an http.Header instance for storage.
+ // For example, Inject():
+ //
+ // carrier := opentracing.HTTPHeadersCarrier(httpReq.Header)
+ // err := span.Tracer().Inject(
+ // span.Context(), opentracing.HTTPHeaders, carrier)
+ //
+ // Or Extract():
+ //
+ // carrier := opentracing.HTTPHeadersCarrier(httpReq.Header)
+ // clientContext, err := tracer.Extract(
+ // opentracing.HTTPHeaders, carrier)
+ //
+ HTTPHeaders
+)
+
+// TextMapWriter is the Inject() carrier for the TextMap builtin format. With
+// it, the caller can encode a SpanContext for propagation as entries in a map
+// of unicode strings.
+type TextMapWriter interface {
+ // Set a key:value pair to the carrier. Multiple calls to Set() for the
+ // same key leads to undefined behavior.
+ //
+ // NOTE: The backing store for the TextMapWriter may contain data unrelated
+ // to SpanContext. As such, Inject() and Extract() implementations that
+ // call the TextMapWriter and TextMapReader interfaces must agree on a
+ // prefix or other convention to distinguish their own key:value pairs.
+ Set(key, val string)
+}
+
+// TextMapReader is the Extract() carrier for the TextMap builtin format. With it,
+// the caller can decode a propagated SpanContext as entries in a map of
+// unicode strings.
+type TextMapReader interface {
+ // ForeachKey returns TextMap contents via repeated calls to the `handler`
+ // function. If any call to `handler` returns a non-nil error, ForeachKey
+ // terminates and returns that error.
+ //
+ // NOTE: The backing store for the TextMapReader may contain data unrelated
+ // to SpanContext. As such, Inject() and Extract() implementations that
+ // call the TextMapWriter and TextMapReader interfaces must agree on a
+ // prefix or other convention to distinguish their own key:value pairs.
+ //
+ // The "foreach" callback pattern reduces unnecessary copying in some cases
+ // and also allows implementations to hold locks while the map is read.
+ ForeachKey(handler func(key, val string) error) error
+}
+
+// TextMapCarrier allows the use of regular map[string]string
+// as both TextMapWriter and TextMapReader.
+type TextMapCarrier map[string]string
+
+// ForeachKey conforms to the TextMapReader interface.
+func (c TextMapCarrier) ForeachKey(handler func(key, val string) error) error {
+ for k, v := range c {
+ if err := handler(k, v); err != nil {
+ return err
+ }
+ }
+ return nil
+}
+
+// Set implements Set() of opentracing.TextMapWriter
+func (c TextMapCarrier) Set(key, val string) {
+ c[key] = val
+}
+
+// HTTPHeadersCarrier satisfies both TextMapWriter and TextMapReader.
+//
+// Example usage for server side:
+//
+// carrier := opentracing.HTTPHeadersCarrier(httpReq.Header)
+// clientContext, err := tracer.Extract(opentracing.HTTPHeaders, carrier)
+//
+// Example usage for client side:
+//
+// carrier := opentracing.HTTPHeadersCarrier(httpReq.Header)
+// err := tracer.Inject(
+// span.Context(),
+// opentracing.HTTPHeaders,
+// carrier)
+//
+type HTTPHeadersCarrier http.Header
+
+// Set conforms to the TextMapWriter interface.
+func (c HTTPHeadersCarrier) Set(key, val string) {
+ h := http.Header(c)
+ h.Set(key, val)
+}
+
+// ForeachKey conforms to the TextMapReader interface.
+func (c HTTPHeadersCarrier) ForeachKey(handler func(key, val string) error) error {
+ for k, vals := range c {
+ for _, v := range vals {
+ if err := handler(k, v); err != nil {
+ return err
+ }
+ }
+ }
+ return nil
+}
diff --git a/vendor/github.com/opentracing/opentracing-go/span.go b/vendor/github.com/opentracing/opentracing-go/span.go
new file mode 100644
index 000000000..0d3fb5341
--- /dev/null
+++ b/vendor/github.com/opentracing/opentracing-go/span.go
@@ -0,0 +1,189 @@
+package opentracing
+
+import (
+ "time"
+
+ "github.com/opentracing/opentracing-go/log"
+)
+
+// SpanContext represents Span state that must propagate to descendant Spans and across process
+// boundaries (e.g., a <trace_id, span_id, sampled> tuple).
+type SpanContext interface {
+ // ForeachBaggageItem grants access to all baggage items stored in the
+ // SpanContext.
+ // The handler function will be called for each baggage key/value pair.
+ // The ordering of items is not guaranteed.
+ //
+ // The bool return value indicates if the handler wants to continue iterating
+ // through the rest of the baggage items; for example if the handler is trying to
+ // find some baggage item by pattern matching the name, it can return false
+ // as soon as the item is found to stop further iterations.
+ ForeachBaggageItem(handler func(k, v string) bool)
+}
+
+// Span represents an active, un-finished span in the OpenTracing system.
+//
+// Spans are created by the Tracer interface.
+type Span interface {
+ // Sets the end timestamp and finalizes Span state.
+ //
+ // With the exception of calls to Context() (which are always allowed),
+ // Finish() must be the last call made to any span instance, and to do
+ // otherwise leads to undefined behavior.
+ Finish()
+ // FinishWithOptions is like Finish() but with explicit control over
+ // timestamps and log data.
+ FinishWithOptions(opts FinishOptions)
+
+ // Context() yields the SpanContext for this Span. Note that the return
+ // value of Context() is still valid after a call to Span.Finish(), as is
+ // a call to Span.Context() after a call to Span.Finish().
+ Context() SpanContext
+
+ // Sets or changes the operation name.
+ //
+ // Returns a reference to this Span for chaining.
+ SetOperationName(operationName string) Span
+
+ // Adds a tag to the span.
+ //
+ // If there is a pre-existing tag set for `key`, it is overwritten.
+ //
+ // Tag values can be numeric types, strings, or bools. The behavior of
+ // other tag value types is undefined at the OpenTracing level. If a
+ // tracing system does not know how to handle a particular value type, it
+ // may ignore the tag, but shall not panic.
+ //
+ // Returns a reference to this Span for chaining.
+ SetTag(key string, value interface{}) Span
+
+ // LogFields is an efficient and type-checked way to record key:value
+ // logging data about a Span, though the programming interface is a little
+ // more verbose than LogKV(). Here's an example:
+ //
+ // span.LogFields(
+ // log.String("event", "soft error"),
+ // log.String("type", "cache timeout"),
+ // log.Int("waited.millis", 1500))
+ //
+ // Also see Span.FinishWithOptions() and FinishOptions.BulkLogData.
+ LogFields(fields ...log.Field)
+
+ // LogKV is a concise, readable way to record key:value logging data about
+ // a Span, though unfortunately this also makes it less efficient and less
+ // type-safe than LogFields(). Here's an example:
+ //
+ // span.LogKV(
+ // "event", "soft error",
+ // "type", "cache timeout",
+ // "waited.millis", 1500)
+ //
+ // For LogKV (as opposed to LogFields()), the parameters must appear as
+ // key-value pairs, like
+ //
+ // span.LogKV(key1, val1, key2, val2, key3, val3, ...)
+ //
+ // The keys must all be strings. The values may be strings, numeric types,
+ // bools, Go error instances, or arbitrary structs.
+ //
+ // (Note to implementors: consider the log.InterleavedKVToFields() helper)
+ LogKV(alternatingKeyValues ...interface{})
+
+ // SetBaggageItem sets a key:value pair on this Span and its SpanContext
+ // that also propagates to descendants of this Span.
+ //
+ // SetBaggageItem() enables powerful functionality given a full-stack
+ // opentracing integration (e.g., arbitrary application data from a mobile
+ // app can make it, transparently, all the way into the depths of a storage
+ // system), and with it some powerful costs: use this feature with care.
+ //
+ // IMPORTANT NOTE #1: SetBaggageItem() will only propagate baggage items to
+ // *future* causal descendants of the associated Span.
+ //
+ // IMPORTANT NOTE #2: Use this thoughtfully and with care. Every key and
+ // value is copied into every local *and remote* child of the associated
+ // Span, and that can add up to a lot of network and cpu overhead.
+ //
+ // Returns a reference to this Span for chaining.
+ SetBaggageItem(restrictedKey, value string) Span
+
+ // Gets the value for a baggage item given its key. Returns the empty string
+ // if the value isn't found in this Span.
+ BaggageItem(restrictedKey string) string
+
+ // Provides access to the Tracer that created this Span.
+ Tracer() Tracer
+
+ // Deprecated: use LogFields or LogKV
+ LogEvent(event string)
+ // Deprecated: use LogFields or LogKV
+ LogEventWithPayload(event string, payload interface{})
+ // Deprecated: use LogFields or LogKV
+ Log(data LogData)
+}
+
+// LogRecord is data associated with a single Span log. Every LogRecord
+// instance must specify at least one Field.
+type LogRecord struct {
+ Timestamp time.Time
+ Fields []log.Field
+}
+
+// FinishOptions allows Span.FinishWithOptions callers to override the finish
+// timestamp and provide log data via a bulk interface.
+type FinishOptions struct {
+ // FinishTime overrides the Span's finish time, or implicitly becomes
+ // time.Now() if FinishTime.IsZero().
+ //
+ // FinishTime must resolve to a timestamp that's >= the Span's StartTime
+ // (per StartSpanOptions).
+ FinishTime time.Time
+
+ // LogRecords allows the caller to specify the contents of many LogFields()
+ // calls with a single slice. May be nil.
+ //
+ // None of the LogRecord.Timestamp values may be .IsZero() (i.e., they must
+ // be set explicitly). Also, they must be >= the Span's start timestamp and
+ // <= the FinishTime (or time.Now() if FinishTime.IsZero()). Otherwise the
+ // behavior of FinishWithOptions() is undefined.
+ //
+ // If specified, the caller hands off ownership of LogRecords at
+ // FinishWithOptions() invocation time.
+ //
+ // If specified, the (deprecated) BulkLogData must be nil or empty.
+ LogRecords []LogRecord
+
+ // BulkLogData is DEPRECATED.
+ BulkLogData []LogData
+}
+
+// LogData is DEPRECATED
+type LogData struct {
+ Timestamp time.Time
+ Event string
+ Payload interface{}
+}
+
+// ToLogRecord converts a deprecated LogData to a non-deprecated LogRecord
+func (ld *LogData) ToLogRecord() LogRecord {
+ var literalTimestamp time.Time
+ if ld.Timestamp.IsZero() {
+ literalTimestamp = time.Now()
+ } else {
+ literalTimestamp = ld.Timestamp
+ }
+ rval := LogRecord{
+ Timestamp: literalTimestamp,
+ }
+ if ld.Payload == nil {
+ rval.Fields = []log.Field{
+ log.String("event", ld.Event),
+ }
+ } else {
+ rval.Fields = []log.Field{
+ log.String("event", ld.Event),
+ log.Object("payload", ld.Payload),
+ }
+ }
+ return rval
+}
diff --git a/vendor/github.com/opentracing/opentracing-go/tracer.go b/vendor/github.com/opentracing/opentracing-go/tracer.go
new file mode 100644
index 000000000..7bca1f736
--- /dev/null
+++ b/vendor/github.com/opentracing/opentracing-go/tracer.go
@@ -0,0 +1,305 @@
+package opentracing
+
+import "time"
+
+// Tracer is a simple, thin interface for Span creation and SpanContext
+// propagation.
+type Tracer interface {
+
+ // Create, start, and return a new Span with the given `operationName` and
+ // incorporate the given StartSpanOption `opts`. (Note that `opts` borrows
+ // from the "functional options" pattern, per
+ // http://dave.cheney.net/2014/10/17/functional-options-for-friendly-apis)
+ //
+ // A Span with no SpanReference options (e.g., opentracing.ChildOf() or
+ // opentracing.FollowsFrom()) becomes the root of its own trace.
+ //
+ // Examples:
+ //
+ // var tracer opentracing.Tracer = ...
+ //
+ // // The root-span case:
+ // sp := tracer.StartSpan("GetFeed")
+ //
+ // // The vanilla child span case:
+ // sp := tracer.StartSpan(
+ // "GetFeed",
+ // opentracing.ChildOf(parentSpan.Context()))
+ //
+ // // All the bells and whistles:
+ // sp := tracer.StartSpan(
+ // "GetFeed",
+ // opentracing.ChildOf(parentSpan.Context()),
+ // opentracing.Tag{"user_agent", loggedReq.UserAgent},
+ // opentracing.StartTime(loggedReq.Timestamp),
+ // )
+ //
+ StartSpan(operationName string, opts ...StartSpanOption) Span
+
+ // Inject() takes the `sm` SpanContext instance and injects it for
+ // propagation within `carrier`. The actual type of `carrier` depends on
+ // the value of `format`.
+ //
+ // OpenTracing defines a common set of `format` values (see BuiltinFormat),
+ // and each has an expected carrier type.
+ //
+ // Other packages may declare their own `format` values, much like the keys
+ // used by `context.Context` (see
+ // https://godoc.org/golang.org/x/net/context#WithValue).
+ //
+ // Example usage (sans error handling):
+ //
+ // carrier := opentracing.HTTPHeadersCarrier(httpReq.Header)
+ // err := tracer.Inject(
+ // span.Context(),
+ // opentracing.HTTPHeaders,
+ // carrier)
+ //
+ // NOTE: All opentracing.Tracer implementations MUST support all
+ // BuiltinFormats.
+ //
+ // Implementations may return opentracing.ErrUnsupportedFormat if `format`
+ // is not supported by (or not known by) the implementation.
+ //
+ // Implementations may return opentracing.ErrInvalidCarrier or any other
+ // implementation-specific error if the format is supported but injection
+ // fails anyway.
+ //
+ // See Tracer.Extract().
+ Inject(sm SpanContext, format interface{}, carrier interface{}) error
+
+ // Extract() returns a SpanContext instance given `format` and `carrier`.
+ //
+ // OpenTracing defines a common set of `format` values (see BuiltinFormat),
+ // and each has an expected carrier type.
+ //
+ // Other packages may declare their own `format` values, much like the keys
+ // used by `context.Context` (see
+ // https://godoc.org/golang.org/x/net/context#WithValue).
+ //
+ // Example usage (with StartSpan):
+ //
+ //
+ // carrier := opentracing.HTTPHeadersCarrier(httpReq.Header)
+ // clientContext, err := tracer.Extract(opentracing.HTTPHeaders, carrier)
+ //
+ // // ... assuming the ultimate goal here is to resume the trace with a
+ // // server-side Span:
+ // var serverSpan opentracing.Span
+ // if err == nil {
+ // span = tracer.StartSpan(
+ // rpcMethodName, ext.RPCServerOption(clientContext))
+ // } else {
+ // span = tracer.StartSpan(rpcMethodName)
+ // }
+ //
+ //
+ // NOTE: All opentracing.Tracer implementations MUST support all
+ // BuiltinFormats.
+ //
+ // Return values:
+ // - A successful Extract returns a SpanContext instance and a nil error
+ // - If there was simply no SpanContext to extract in `carrier`, Extract()
+ // returns (nil, opentracing.ErrSpanContextNotFound)
+ // - If `format` is unsupported or unrecognized, Extract() returns (nil,
+ // opentracing.ErrUnsupportedFormat)
+ // - If there are more fundamental problems with the `carrier` object,
+ // Extract() may return opentracing.ErrInvalidCarrier,
+ // opentracing.ErrSpanContextCorrupted, or implementation-specific
+ // errors.
+ //
+ // See Tracer.Inject().
+ Extract(format interface{}, carrier interface{}) (SpanContext, error)
+}
+
+// StartSpanOptions allows Tracer.StartSpan() callers and implementors a
+// mechanism to override the start timestamp, specify Span References, and make
+// a single Tag or multiple Tags available at Span start time.
+//
+// StartSpan() callers should look at the StartSpanOption interface and
+// implementations available in this package.
+//
+// Tracer implementations can convert a slice of `StartSpanOption` instances
+// into a `StartSpanOptions` struct like so:
+//
+// func StartSpan(opName string, opts ...opentracing.StartSpanOption) {
+// sso := opentracing.StartSpanOptions{}
+// for _, o := range opts {
+// o.Apply(&sso)
+// }
+// ...
+// }
+//
+type StartSpanOptions struct {
+ // Zero or more causal references to other Spans (via their SpanContext).
+ // If empty, start a "root" Span (i.e., start a new trace).
+ References []SpanReference
+
+ // StartTime overrides the Span's start time, or implicitly becomes
+ // time.Now() if StartTime.IsZero().
+ StartTime time.Time
+
+ // Tags may have zero or more entries; the restrictions on map values are
+ // identical to those for Span.SetTag(). May be nil.
+ //
+ // If specified, the caller hands off ownership of Tags at
+ // StartSpan() invocation time.
+ Tags map[string]interface{}
+}
+
+// StartSpanOption instances (zero or more) may be passed to Tracer.StartSpan.
+//
+// StartSpanOption borrows from the "functional options" pattern, per
+// http://dave.cheney.net/2014/10/17/functional-options-for-friendly-apis
+type StartSpanOption interface {
+ Apply(*StartSpanOptions)
+}
+
+// SpanReferenceType is an enum type describing different categories of
+// relationships between two Spans. If Span-2 refers to Span-1, the
+// SpanReferenceType describes Span-1 from Span-2's perspective. For example,
+// ChildOfRef means that Span-1 created Span-2.
+//
+// NOTE: Span-1 and Span-2 do *not* necessarily depend on each other for
+// completion; e.g., Span-2 may be part of a background job enqueued by Span-1,
+// or Span-2 may be sitting in a distributed queue behind Span-1.
+type SpanReferenceType int
+
+const (
+ // ChildOfRef refers to a parent Span that caused *and* somehow depends
+ // upon the new child Span. Often (but not always), the parent Span cannot
+ // finish until the child Span does.
+ //
+ // An timing diagram for a ChildOfRef that's blocked on the new Span:
+ //
+ // [-Parent Span---------]
+ // [-Child Span----]
+ //
+ // See http://opentracing.io/spec/
+ //
+ // See opentracing.ChildOf()
+ ChildOfRef SpanReferenceType = iota
+
+ // FollowsFromRef refers to a parent Span that does not depend in any way
+ // on the result of the new child Span. For instance, one might use
+ // FollowsFromRefs to describe pipeline stages separated by queues,
+ // or a fire-and-forget cache insert at the tail end of a web request.
+ //
+ // A FollowsFromRef Span is part of the same logical trace as the new Span:
+ // i.e., the new Span is somehow caused by the work of its FollowsFromRef.
+ //
+ // All of the following could be valid timing diagrams for children that
+ // "FollowFrom" a parent.
+ //
+ // [-Parent Span-] [-Child Span-]
+ //
+ //
+ // [-Parent Span--]
+ // [-Child Span-]
+ //
+ //
+ // [-Parent Span-]
+ // [-Child Span-]
+ //
+ // See http://opentracing.io/spec/
+ //
+ // See opentracing.FollowsFrom()
+ FollowsFromRef
+)
+
+// SpanReference is a StartSpanOption that pairs a SpanReferenceType and a
+// referenced SpanContext. See the SpanReferenceType documentation for
+// supported relationships. If SpanReference is created with
+// ReferencedContext==nil, it has no effect. Thus it allows for a more concise
+// syntax for starting spans:
+//
+// sc, _ := tracer.Extract(someFormat, someCarrier)
+// span := tracer.StartSpan("operation", opentracing.ChildOf(sc))
+//
+// The `ChildOf(sc)` option above will not panic if sc == nil, it will just
+// not add the parent span reference to the options.
+type SpanReference struct {
+ Type SpanReferenceType
+ ReferencedContext SpanContext
+}
+
+// Apply satisfies the StartSpanOption interface.
+func (r SpanReference) Apply(o *StartSpanOptions) {
+ if r.ReferencedContext != nil {
+ o.References = append(o.References, r)
+ }
+}
+
+// ChildOf returns a StartSpanOption pointing to a dependent parent span.
+// If sc == nil, the option has no effect.
+//
+// See ChildOfRef, SpanReference
+func ChildOf(sc SpanContext) SpanReference {
+ return SpanReference{
+ Type: ChildOfRef,
+ ReferencedContext: sc,
+ }
+}
+
+// FollowsFrom returns a StartSpanOption pointing to a parent Span that caused
+// the child Span but does not directly depend on its result in any way.
+// If sc == nil, the option has no effect.
+//
+// See FollowsFromRef, SpanReference
+func FollowsFrom(sc SpanContext) SpanReference {
+ return SpanReference{
+ Type: FollowsFromRef,
+ ReferencedContext: sc,
+ }
+}
+
+// StartTime is a StartSpanOption that sets an explicit start timestamp for the
+// new Span.
+type StartTime time.Time
+
+// Apply satisfies the StartSpanOption interface.
+func (t StartTime) Apply(o *StartSpanOptions) {
+ o.StartTime = time.Time(t)
+}
+
+// Tags are a generic map from an arbitrary string key to an opaque value type.
+// The underlying tracing system is responsible for interpreting and
+// serializing the values.
+type Tags map[string]interface{}
+
+// Apply satisfies the StartSpanOption interface.
+func (t Tags) Apply(o *StartSpanOptions) {
+ if o.Tags == nil {
+ o.Tags = make(map[string]interface{})
+ }
+ for k, v := range t {
+ o.Tags[k] = v
+ }
+}
+
+// Tag may be passed as a StartSpanOption to add a tag to new spans,
+// or its Set method may be used to apply the tag to an existing Span,
+// for example:
+//
+// tracer.StartSpan("opName", Tag{"Key", value})
+//
+// or
+//
+// Tag{"key", value}.Set(span)
+type Tag struct {
+ Key string
+ Value interface{}
+}
+
+// Apply satisfies the StartSpanOption interface.
+func (t Tag) Apply(o *StartSpanOptions) {
+ if o.Tags == nil {
+ o.Tags = make(map[string]interface{})
+ }
+ o.Tags[t.Key] = t.Value
+}
+
+// Set applies the tag to an existing Span.
+func (t Tag) Set(s Span) {
+ s.SetTag(t.Key, t.Value)
+}
diff --git a/vendor/github.com/philhofer/fwd/LICENSE.md b/vendor/github.com/philhofer/fwd/LICENSE.md
new file mode 100644
index 000000000..1ac6a81f6
--- /dev/null
+++ b/vendor/github.com/philhofer/fwd/LICENSE.md
@@ -0,0 +1,7 @@
+Copyright (c) 2014-2015, Philip Hofer
+
+Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. \ No newline at end of file
diff --git a/vendor/github.com/philhofer/fwd/README.md b/vendor/github.com/philhofer/fwd/README.md
new file mode 100644
index 000000000..38349af34
--- /dev/null
+++ b/vendor/github.com/philhofer/fwd/README.md
@@ -0,0 +1,315 @@
+
+# fwd
+ import "github.com/philhofer/fwd"
+
+The `fwd` package provides a buffered reader
+and writer. Each has methods that help improve
+the encoding/decoding performance of some binary
+protocols.
+
+The `fwd.Writer` and `fwd.Reader` type provide similar
+functionality to their counterparts in `bufio`, plus
+a few extra utility methods that simplify read-ahead
+and write-ahead. I wrote this package to improve serialization
+performance for <a href="http://github.com/tinylib/msgp">http://github.com/tinylib/msgp</a>,
+where it provided about a 2x speedup over `bufio` for certain
+workloads. However, care must be taken to understand the semantics of the
+extra methods provided by this package, as they allow
+the user to access and manipulate the buffer memory
+directly.
+
+The extra methods for `fwd.Reader` are `Peek`, `Skip`
+and `Next`. `(*fwd.Reader).Peek`, unlike `(*bufio.Reader).Peek`,
+will re-allocate the read buffer in order to accommodate arbitrarily
+large read-ahead. `(*fwd.Reader).Skip` skips the next `n` bytes
+in the stream, and uses the `io.Seeker` interface if the underlying
+stream implements it. `(*fwd.Reader).Next` returns a slice pointing
+to the next `n` bytes in the read buffer (like `Peek`), but also
+increments the read position. This allows users to process streams
+in arbitrary block sizes without having to manage appropriately-sized
+slices. Additionally, obviating the need to copy the data from the
+buffer to another location in memory can improve performance dramatically
+in CPU-bound applications.
+
+`fwd.Writer` only has one extra method, which is `(*fwd.Writer).Next`, which
+returns a slice pointing to the next `n` bytes of the writer, and increments
+the write position by the length of the returned slice. This allows users
+to write directly to the end of the buffer.
+
+
+
+
+## Constants
+``` go
+const (
+ // DefaultReaderSize is the default size of the read buffer
+ DefaultReaderSize = 2048
+)
+```
+``` go
+const (
+ // DefaultWriterSize is the
+ // default write buffer size.
+ DefaultWriterSize = 2048
+)
+```
+
+
+
+## type Reader
+``` go
+type Reader struct {
+ // contains filtered or unexported fields
+}
+```
+Reader is a buffered look-ahead reader
+
+
+
+
+
+
+
+
+
+### func NewReader
+``` go
+func NewReader(r io.Reader) *Reader
+```
+NewReader returns a new *Reader that reads from 'r'
+
+
+### func NewReaderSize
+``` go
+func NewReaderSize(r io.Reader, n int) *Reader
+```
+NewReaderSize returns a new *Reader that
+reads from 'r' and has a buffer size 'n'
+
+
+
+
+### func (\*Reader) BufferSize
+``` go
+func (r *Reader) BufferSize() int
+```
+BufferSize returns the total size of the buffer
+
+
+
+### func (\*Reader) Buffered
+``` go
+func (r *Reader) Buffered() int
+```
+Buffered returns the number of bytes currently in the buffer
+
+
+
+### func (\*Reader) Next
+``` go
+func (r *Reader) Next(n int) ([]byte, error)
+```
+Next returns the next 'n' bytes in the stream.
+Unlike Peek, Next advances the reader position.
+The returned bytes point to the same
+data as the buffer, so the slice is
+only valid until the next reader method call.
+An EOF is considered an unexpected error.
+If an the returned slice is less than the
+length asked for, an error will be returned,
+and the reader position will not be incremented.
+
+
+
+### func (\*Reader) Peek
+``` go
+func (r *Reader) Peek(n int) ([]byte, error)
+```
+Peek returns the next 'n' buffered bytes,
+reading from the underlying reader if necessary.
+It will only return a slice shorter than 'n' bytes
+if it also returns an error. Peek does not advance
+the reader. EOF errors are *not* returned as
+io.ErrUnexpectedEOF.
+
+
+
+### func (\*Reader) Read
+``` go
+func (r *Reader) Read(b []byte) (int, error)
+```
+Read implements `io.Reader`
+
+
+
+### func (\*Reader) ReadByte
+``` go
+func (r *Reader) ReadByte() (byte, error)
+```
+ReadByte implements `io.ByteReader`
+
+
+
+### func (\*Reader) ReadFull
+``` go
+func (r *Reader) ReadFull(b []byte) (int, error)
+```
+ReadFull attempts to read len(b) bytes into
+'b'. It returns the number of bytes read into
+'b', and an error if it does not return len(b).
+EOF is considered an unexpected error.
+
+
+
+### func (\*Reader) Reset
+``` go
+func (r *Reader) Reset(rd io.Reader)
+```
+Reset resets the underlying reader
+and the read buffer.
+
+
+
+### func (\*Reader) Skip
+``` go
+func (r *Reader) Skip(n int) (int, error)
+```
+Skip moves the reader forward 'n' bytes.
+Returns the number of bytes skipped and any
+errors encountered. It is analogous to Seek(n, 1).
+If the underlying reader implements io.Seeker, then
+that method will be used to skip forward.
+
+If the reader encounters
+an EOF before skipping 'n' bytes, it
+returns io.ErrUnexpectedEOF. If the
+underlying reader implements io.Seeker, then
+those rules apply instead. (Many implementations
+will not return `io.EOF` until the next call
+to Read.)
+
+
+
+### func (\*Reader) WriteTo
+``` go
+func (r *Reader) WriteTo(w io.Writer) (int64, error)
+```
+WriteTo implements `io.WriterTo`
+
+
+
+## type Writer
+``` go
+type Writer struct {
+ // contains filtered or unexported fields
+}
+```
+Writer is a buffered writer
+
+
+
+
+
+
+
+
+
+### func NewWriter
+``` go
+func NewWriter(w io.Writer) *Writer
+```
+NewWriter returns a new writer
+that writes to 'w' and has a buffer
+that is `DefaultWriterSize` bytes.
+
+
+### func NewWriterSize
+``` go
+func NewWriterSize(w io.Writer, size int) *Writer
+```
+NewWriterSize returns a new writer
+that writes to 'w' and has a buffer
+that is 'size' bytes.
+
+
+
+
+### func (\*Writer) BufferSize
+``` go
+func (w *Writer) BufferSize() int
+```
+BufferSize returns the maximum size of the buffer.
+
+
+
+### func (\*Writer) Buffered
+``` go
+func (w *Writer) Buffered() int
+```
+Buffered returns the number of buffered bytes
+in the reader.
+
+
+
+### func (\*Writer) Flush
+``` go
+func (w *Writer) Flush() error
+```
+Flush flushes any buffered bytes
+to the underlying writer.
+
+
+
+### func (\*Writer) Next
+``` go
+func (w *Writer) Next(n int) ([]byte, error)
+```
+Next returns the next 'n' free bytes
+in the write buffer, flushing the writer
+as necessary. Next will return `io.ErrShortBuffer`
+if 'n' is greater than the size of the write buffer.
+Calls to 'next' increment the write position by
+the size of the returned buffer.
+
+
+
+### func (\*Writer) ReadFrom
+``` go
+func (w *Writer) ReadFrom(r io.Reader) (int64, error)
+```
+ReadFrom implements `io.ReaderFrom`
+
+
+
+### func (\*Writer) Write
+``` go
+func (w *Writer) Write(p []byte) (int, error)
+```
+Write implements `io.Writer`
+
+
+
+### func (\*Writer) WriteByte
+``` go
+func (w *Writer) WriteByte(b byte) error
+```
+WriteByte implements `io.ByteWriter`
+
+
+
+### func (\*Writer) WriteString
+``` go
+func (w *Writer) WriteString(s string) (int, error)
+```
+WriteString is analogous to Write, but it takes a string.
+
+
+
+
+
+
+
+
+
+- - -
+Generated by [godoc2md](http://godoc.org/github.com/davecheney/godoc2md) \ No newline at end of file
diff --git a/vendor/github.com/philhofer/fwd/reader.go b/vendor/github.com/philhofer/fwd/reader.go
new file mode 100644
index 000000000..75be62ab0
--- /dev/null
+++ b/vendor/github.com/philhofer/fwd/reader.go
@@ -0,0 +1,383 @@
+// The `fwd` package provides a buffered reader
+// and writer. Each has methods that help improve
+// the encoding/decoding performance of some binary
+// protocols.
+//
+// The `fwd.Writer` and `fwd.Reader` type provide similar
+// functionality to their counterparts in `bufio`, plus
+// a few extra utility methods that simplify read-ahead
+// and write-ahead. I wrote this package to improve serialization
+// performance for http://github.com/tinylib/msgp,
+// where it provided about a 2x speedup over `bufio` for certain
+// workloads. However, care must be taken to understand the semantics of the
+// extra methods provided by this package, as they allow
+// the user to access and manipulate the buffer memory
+// directly.
+//
+// The extra methods for `fwd.Reader` are `Peek`, `Skip`
+// and `Next`. `(*fwd.Reader).Peek`, unlike `(*bufio.Reader).Peek`,
+// will re-allocate the read buffer in order to accommodate arbitrarily
+// large read-ahead. `(*fwd.Reader).Skip` skips the next `n` bytes
+// in the stream, and uses the `io.Seeker` interface if the underlying
+// stream implements it. `(*fwd.Reader).Next` returns a slice pointing
+// to the next `n` bytes in the read buffer (like `Peek`), but also
+// increments the read position. This allows users to process streams
+// in arbitrary block sizes without having to manage appropriately-sized
+// slices. Additionally, obviating the need to copy the data from the
+// buffer to another location in memory can improve performance dramatically
+// in CPU-bound applications.
+//
+// `fwd.Writer` only has one extra method, which is `(*fwd.Writer).Next`, which
+// returns a slice pointing to the next `n` bytes of the writer, and increments
+// the write position by the length of the returned slice. This allows users
+// to write directly to the end of the buffer.
+//
+package fwd
+
+import "io"
+
+const (
+ // DefaultReaderSize is the default size of the read buffer
+ DefaultReaderSize = 2048
+
+ // minimum read buffer; straight from bufio
+ minReaderSize = 16
+)
+
+// NewReader returns a new *Reader that reads from 'r'
+func NewReader(r io.Reader) *Reader {
+ return NewReaderSize(r, DefaultReaderSize)
+}
+
+// NewReaderSize returns a new *Reader that
+// reads from 'r' and has a buffer size 'n'
+func NewReaderSize(r io.Reader, n int) *Reader {
+ rd := &Reader{
+ r: r,
+ data: make([]byte, 0, max(minReaderSize, n)),
+ }
+ if s, ok := r.(io.Seeker); ok {
+ rd.rs = s
+ }
+ return rd
+}
+
+// Reader is a buffered look-ahead reader
+type Reader struct {
+ r io.Reader // underlying reader
+
+ // data[n:len(data)] is buffered data; data[len(data):cap(data)] is free buffer space
+ data []byte // data
+ n int // read offset
+ state error // last read error
+
+ // if the reader past to NewReader was
+ // also an io.Seeker, this is non-nil
+ rs io.Seeker
+}
+
+// Reset resets the underlying reader
+// and the read buffer.
+func (r *Reader) Reset(rd io.Reader) {
+ r.r = rd
+ r.data = r.data[0:0]
+ r.n = 0
+ r.state = nil
+ if s, ok := rd.(io.Seeker); ok {
+ r.rs = s
+ } else {
+ r.rs = nil
+ }
+}
+
+// more() does one read on the underlying reader
+func (r *Reader) more() {
+ // move data backwards so that
+ // the read offset is 0; this way
+ // we can supply the maximum number of
+ // bytes to the reader
+ if r.n != 0 {
+ if r.n < len(r.data) {
+ r.data = r.data[:copy(r.data[0:], r.data[r.n:])]
+ } else {
+ r.data = r.data[:0]
+ }
+ r.n = 0
+ }
+ var a int
+ a, r.state = r.r.Read(r.data[len(r.data):cap(r.data)])
+ if a == 0 && r.state == nil {
+ r.state = io.ErrNoProgress
+ return
+ } else if a > 0 && r.state == io.EOF {
+ // discard the io.EOF if we read more than 0 bytes.
+ // the next call to Read should return io.EOF again.
+ r.state = nil
+ }
+ r.data = r.data[:len(r.data)+a]
+}
+
+// pop error
+func (r *Reader) err() (e error) {
+ e, r.state = r.state, nil
+ return
+}
+
+// pop error; EOF -> io.ErrUnexpectedEOF
+func (r *Reader) noEOF() (e error) {
+ e, r.state = r.state, nil
+ if e == io.EOF {
+ e = io.ErrUnexpectedEOF
+ }
+ return
+}
+
+// buffered bytes
+func (r *Reader) buffered() int { return len(r.data) - r.n }
+
+// Buffered returns the number of bytes currently in the buffer
+func (r *Reader) Buffered() int { return len(r.data) - r.n }
+
+// BufferSize returns the total size of the buffer
+func (r *Reader) BufferSize() int { return cap(r.data) }
+
+// Peek returns the next 'n' buffered bytes,
+// reading from the underlying reader if necessary.
+// It will only return a slice shorter than 'n' bytes
+// if it also returns an error. Peek does not advance
+// the reader. EOF errors are *not* returned as
+// io.ErrUnexpectedEOF.
+func (r *Reader) Peek(n int) ([]byte, error) {
+ // in the degenerate case,
+ // we may need to realloc
+ // (the caller asked for more
+ // bytes than the size of the buffer)
+ if cap(r.data) < n {
+ old := r.data[r.n:]
+ r.data = make([]byte, n+r.buffered())
+ r.data = r.data[:copy(r.data, old)]
+ r.n = 0
+ }
+
+ // keep filling until
+ // we hit an error or
+ // read enough bytes
+ for r.buffered() < n && r.state == nil {
+ r.more()
+ }
+
+ // we must have hit an error
+ if r.buffered() < n {
+ return r.data[r.n:], r.err()
+ }
+
+ return r.data[r.n : r.n+n], nil
+}
+
+// Skip moves the reader forward 'n' bytes.
+// Returns the number of bytes skipped and any
+// errors encountered. It is analogous to Seek(n, 1).
+// If the underlying reader implements io.Seeker, then
+// that method will be used to skip forward.
+//
+// If the reader encounters
+// an EOF before skipping 'n' bytes, it
+// returns io.ErrUnexpectedEOF. If the
+// underlying reader implements io.Seeker, then
+// those rules apply instead. (Many implementations
+// will not return `io.EOF` until the next call
+// to Read.)
+func (r *Reader) Skip(n int) (int, error) {
+
+ // fast path
+ if r.buffered() >= n {
+ r.n += n
+ return n, nil
+ }
+
+ // use seeker implementation
+ // if we can
+ if r.rs != nil {
+ return r.skipSeek(n)
+ }
+
+ // loop on filling
+ // and then erasing
+ o := n
+ for r.buffered() < n && r.state == nil {
+ r.more()
+ // we can skip forward
+ // up to r.buffered() bytes
+ step := min(r.buffered(), n)
+ r.n += step
+ n -= step
+ }
+ // at this point, n should be
+ // 0 if everything went smoothly
+ return o - n, r.noEOF()
+}
+
+// Next returns the next 'n' bytes in the stream.
+// Unlike Peek, Next advances the reader position.
+// The returned bytes point to the same
+// data as the buffer, so the slice is
+// only valid until the next reader method call.
+// An EOF is considered an unexpected error.
+// If an the returned slice is less than the
+// length asked for, an error will be returned,
+// and the reader position will not be incremented.
+func (r *Reader) Next(n int) ([]byte, error) {
+
+ // in case the buffer is too small
+ if cap(r.data) < n {
+ old := r.data[r.n:]
+ r.data = make([]byte, n+r.buffered())
+ r.data = r.data[:copy(r.data, old)]
+ r.n = 0
+ }
+
+ // fill at least 'n' bytes
+ for r.buffered() < n && r.state == nil {
+ r.more()
+ }
+
+ if r.buffered() < n {
+ return r.data[r.n:], r.noEOF()
+ }
+ out := r.data[r.n : r.n+n]
+ r.n += n
+ return out, nil
+}
+
+// skipSeek uses the io.Seeker to seek forward.
+// only call this function when n > r.buffered()
+func (r *Reader) skipSeek(n int) (int, error) {
+ o := r.buffered()
+ // first, clear buffer
+ n -= o
+ r.n = 0
+ r.data = r.data[:0]
+
+ // then seek forward remaning bytes
+ i, err := r.rs.Seek(int64(n), 1)
+ return int(i) + o, err
+}
+
+// Read implements `io.Reader`
+func (r *Reader) Read(b []byte) (int, error) {
+ // if we have data in the buffer, just
+ // return that.
+ if r.buffered() != 0 {
+ x := copy(b, r.data[r.n:])
+ r.n += x
+ return x, nil
+ }
+ var n int
+ // we have no buffered data; determine
+ // whether or not to buffer or call
+ // the underlying reader directly
+ if len(b) >= cap(r.data) {
+ n, r.state = r.r.Read(b)
+ } else {
+ r.more()
+ n = copy(b, r.data)
+ r.n = n
+ }
+ if n == 0 {
+ return 0, r.err()
+ }
+ return n, nil
+}
+
+// ReadFull attempts to read len(b) bytes into
+// 'b'. It returns the number of bytes read into
+// 'b', and an error if it does not return len(b).
+// EOF is considered an unexpected error.
+func (r *Reader) ReadFull(b []byte) (int, error) {
+ var n int // read into b
+ var nn int // scratch
+ l := len(b)
+ // either read buffered data,
+ // or read directly for the underlying
+ // buffer, or fetch more buffered data.
+ for n < l && r.state == nil {
+ if r.buffered() != 0 {
+ nn = copy(b[n:], r.data[r.n:])
+ n += nn
+ r.n += nn
+ } else if l-n > cap(r.data) {
+ nn, r.state = r.r.Read(b[n:])
+ n += nn
+ } else {
+ r.more()
+ }
+ }
+ if n < l {
+ return n, r.noEOF()
+ }
+ return n, nil
+}
+
+// ReadByte implements `io.ByteReader`
+func (r *Reader) ReadByte() (byte, error) {
+ for r.buffered() < 1 && r.state == nil {
+ r.more()
+ }
+ if r.buffered() < 1 {
+ return 0, r.err()
+ }
+ b := r.data[r.n]
+ r.n++
+ return b, nil
+}
+
+// WriteTo implements `io.WriterTo`
+func (r *Reader) WriteTo(w io.Writer) (int64, error) {
+ var (
+ i int64
+ ii int
+ err error
+ )
+ // first, clear buffer
+ if r.buffered() > 0 {
+ ii, err = w.Write(r.data[r.n:])
+ i += int64(ii)
+ if err != nil {
+ return i, err
+ }
+ r.data = r.data[0:0]
+ r.n = 0
+ }
+ for r.state == nil {
+ // here we just do
+ // 1:1 reads and writes
+ r.more()
+ if r.buffered() > 0 {
+ ii, err = w.Write(r.data)
+ i += int64(ii)
+ if err != nil {
+ return i, err
+ }
+ r.data = r.data[0:0]
+ r.n = 0
+ }
+ }
+ if r.state != io.EOF {
+ return i, r.err()
+ }
+ return i, nil
+}
+
+func min(a int, b int) int {
+ if a < b {
+ return a
+ }
+ return b
+}
+
+func max(a int, b int) int {
+ if a < b {
+ return b
+ }
+ return a
+}
diff --git a/vendor/github.com/philhofer/fwd/writer.go b/vendor/github.com/philhofer/fwd/writer.go
new file mode 100644
index 000000000..2dc392a91
--- /dev/null
+++ b/vendor/github.com/philhofer/fwd/writer.go
@@ -0,0 +1,224 @@
+package fwd
+
+import "io"
+
+const (
+ // DefaultWriterSize is the
+ // default write buffer size.
+ DefaultWriterSize = 2048
+
+ minWriterSize = minReaderSize
+)
+
+// Writer is a buffered writer
+type Writer struct {
+ w io.Writer // writer
+ buf []byte // 0:len(buf) is bufered data
+}
+
+// NewWriter returns a new writer
+// that writes to 'w' and has a buffer
+// that is `DefaultWriterSize` bytes.
+func NewWriter(w io.Writer) *Writer {
+ if wr, ok := w.(*Writer); ok {
+ return wr
+ }
+ return &Writer{
+ w: w,
+ buf: make([]byte, 0, DefaultWriterSize),
+ }
+}
+
+// NewWriterSize returns a new writer
+// that writes to 'w' and has a buffer
+// that is 'size' bytes.
+func NewWriterSize(w io.Writer, size int) *Writer {
+ if wr, ok := w.(*Writer); ok && cap(wr.buf) >= size {
+ return wr
+ }
+ return &Writer{
+ w: w,
+ buf: make([]byte, 0, max(size, minWriterSize)),
+ }
+}
+
+// Buffered returns the number of buffered bytes
+// in the reader.
+func (w *Writer) Buffered() int { return len(w.buf) }
+
+// BufferSize returns the maximum size of the buffer.
+func (w *Writer) BufferSize() int { return cap(w.buf) }
+
+// Flush flushes any buffered bytes
+// to the underlying writer.
+func (w *Writer) Flush() error {
+ l := len(w.buf)
+ if l > 0 {
+ n, err := w.w.Write(w.buf)
+
+ // if we didn't write the whole
+ // thing, copy the unwritten
+ // bytes to the beginnning of the
+ // buffer.
+ if n < l && n > 0 {
+ w.pushback(n)
+ if err == nil {
+ err = io.ErrShortWrite
+ }
+ }
+ if err != nil {
+ return err
+ }
+ w.buf = w.buf[:0]
+ return nil
+ }
+ return nil
+}
+
+// Write implements `io.Writer`
+func (w *Writer) Write(p []byte) (int, error) {
+ c, l, ln := cap(w.buf), len(w.buf), len(p)
+ avail := c - l
+
+ // requires flush
+ if avail < ln {
+ if err := w.Flush(); err != nil {
+ return 0, err
+ }
+ l = len(w.buf)
+ }
+ // too big to fit in buffer;
+ // write directly to w.w
+ if c < ln {
+ return w.w.Write(p)
+ }
+
+ // grow buf slice; copy; return
+ w.buf = w.buf[:l+ln]
+ return copy(w.buf[l:], p), nil
+}
+
+// WriteString is analogous to Write, but it takes a string.
+func (w *Writer) WriteString(s string) (int, error) {
+ c, l, ln := cap(w.buf), len(w.buf), len(s)
+ avail := c - l
+
+ // requires flush
+ if avail < ln {
+ if err := w.Flush(); err != nil {
+ return 0, err
+ }
+ l = len(w.buf)
+ }
+ // too big to fit in buffer;
+ // write directly to w.w
+ //
+ // yes, this is unsafe. *but*
+ // io.Writer is not allowed
+ // to mutate its input or
+ // maintain a reference to it,
+ // per the spec in package io.
+ //
+ // plus, if the string is really
+ // too big to fit in the buffer, then
+ // creating a copy to write it is
+ // expensive (and, strictly speaking,
+ // unnecessary)
+ if c < ln {
+ return w.w.Write(unsafestr(s))
+ }
+
+ // grow buf slice; copy; return
+ w.buf = w.buf[:l+ln]
+ return copy(w.buf[l:], s), nil
+}
+
+// WriteByte implements `io.ByteWriter`
+func (w *Writer) WriteByte(b byte) error {
+ if len(w.buf) == cap(w.buf) {
+ if err := w.Flush(); err != nil {
+ return err
+ }
+ }
+ w.buf = append(w.buf, b)
+ return nil
+}
+
+// Next returns the next 'n' free bytes
+// in the write buffer, flushing the writer
+// as necessary. Next will return `io.ErrShortBuffer`
+// if 'n' is greater than the size of the write buffer.
+// Calls to 'next' increment the write position by
+// the size of the returned buffer.
+func (w *Writer) Next(n int) ([]byte, error) {
+ c, l := cap(w.buf), len(w.buf)
+ if n > c {
+ return nil, io.ErrShortBuffer
+ }
+ avail := c - l
+ if avail < n {
+ if err := w.Flush(); err != nil {
+ return nil, err
+ }
+ l = len(w.buf)
+ }
+ w.buf = w.buf[:l+n]
+ return w.buf[l:], nil
+}
+
+// take the bytes from w.buf[n:len(w.buf)]
+// and put them at the beginning of w.buf,
+// and resize to the length of the copied segment.
+func (w *Writer) pushback(n int) {
+ w.buf = w.buf[:copy(w.buf, w.buf[n:])]
+}
+
+// ReadFrom implements `io.ReaderFrom`
+func (w *Writer) ReadFrom(r io.Reader) (int64, error) {
+ // anticipatory flush
+ if err := w.Flush(); err != nil {
+ return 0, err
+ }
+
+ w.buf = w.buf[0:cap(w.buf)] // expand buffer
+
+ var nn int64 // written
+ var err error // error
+ var x int // read
+
+ // 1:1 reads and writes
+ for err == nil {
+ x, err = r.Read(w.buf)
+ if x > 0 {
+ n, werr := w.w.Write(w.buf[:x])
+ nn += int64(n)
+
+ if err != nil {
+ if n < x && n > 0 {
+ w.pushback(n - x)
+ }
+ return nn, werr
+ }
+ if n < x {
+ w.pushback(n - x)
+ return nn, io.ErrShortWrite
+ }
+ } else if err == nil {
+ err = io.ErrNoProgress
+ break
+ }
+ }
+ if err != io.EOF {
+ return nn, err
+ }
+
+ // we only clear here
+ // because we are sure
+ // the writes have
+ // succeeded. otherwise,
+ // we retain the data in case
+ // future writes succeed.
+ w.buf = w.buf[0:0]
+
+ return nn, nil
+}
diff --git a/vendor/github.com/philhofer/fwd/writer_appengine.go b/vendor/github.com/philhofer/fwd/writer_appengine.go
new file mode 100644
index 000000000..e367f3931
--- /dev/null
+++ b/vendor/github.com/philhofer/fwd/writer_appengine.go
@@ -0,0 +1,5 @@
+// +build appengine
+
+package fwd
+
+func unsafestr(s string) []byte { return []byte(s) }
diff --git a/vendor/github.com/philhofer/fwd/writer_unsafe.go b/vendor/github.com/philhofer/fwd/writer_unsafe.go
new file mode 100644
index 000000000..a0bf453b3
--- /dev/null
+++ b/vendor/github.com/philhofer/fwd/writer_unsafe.go
@@ -0,0 +1,18 @@
+// +build !appengine
+
+package fwd
+
+import (
+ "reflect"
+ "unsafe"
+)
+
+// unsafe cast string as []byte
+func unsafestr(b string) []byte {
+ l := len(b)
+ return *(*[]byte)(unsafe.Pointer(&reflect.SliceHeader{
+ Len: l,
+ Cap: l,
+ Data: (*reflect.StringHeader)(unsafe.Pointer(&b)).Data,
+ }))
+}
diff --git a/vendor/github.com/tinylib/msgp/LICENSE b/vendor/github.com/tinylib/msgp/LICENSE
new file mode 100644
index 000000000..14d60424e
--- /dev/null
+++ b/vendor/github.com/tinylib/msgp/LICENSE
@@ -0,0 +1,8 @@
+Copyright (c) 2014 Philip Hofer
+Portions Copyright (c) 2009 The Go Authors (license at http://golang.org) where indicated
+
+Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. \ No newline at end of file
diff --git a/vendor/github.com/tinylib/msgp/msgp/advise_linux.go b/vendor/github.com/tinylib/msgp/msgp/advise_linux.go
new file mode 100644
index 000000000..6c6bb37a5
--- /dev/null
+++ b/vendor/github.com/tinylib/msgp/msgp/advise_linux.go
@@ -0,0 +1,24 @@
+// +build linux,!appengine
+
+package msgp
+
+import (
+ "os"
+ "syscall"
+)
+
+func adviseRead(mem []byte) {
+ syscall.Madvise(mem, syscall.MADV_SEQUENTIAL|syscall.MADV_WILLNEED)
+}
+
+func adviseWrite(mem []byte) {
+ syscall.Madvise(mem, syscall.MADV_SEQUENTIAL)
+}
+
+func fallocate(f *os.File, sz int64) error {
+ err := syscall.Fallocate(int(f.Fd()), 0, 0, sz)
+ if err == syscall.ENOTSUP {
+ return f.Truncate(sz)
+ }
+ return err
+}
diff --git a/vendor/github.com/tinylib/msgp/msgp/advise_other.go b/vendor/github.com/tinylib/msgp/msgp/advise_other.go
new file mode 100644
index 000000000..da65ea541
--- /dev/null
+++ b/vendor/github.com/tinylib/msgp/msgp/advise_other.go
@@ -0,0 +1,17 @@
+// +build !linux appengine
+
+package msgp
+
+import (
+ "os"
+)
+
+// TODO: darwin, BSD support
+
+func adviseRead(mem []byte) {}
+
+func adviseWrite(mem []byte) {}
+
+func fallocate(f *os.File, sz int64) error {
+ return f.Truncate(sz)
+}
diff --git a/vendor/github.com/tinylib/msgp/msgp/circular.go b/vendor/github.com/tinylib/msgp/msgp/circular.go
new file mode 100644
index 000000000..a0434c7ea
--- /dev/null
+++ b/vendor/github.com/tinylib/msgp/msgp/circular.go
@@ -0,0 +1,39 @@
+package msgp
+
+type timer interface {
+ StartTimer()
+ StopTimer()
+}
+
+// EndlessReader is an io.Reader
+// that loops over the same data
+// endlessly. It is used for benchmarking.
+type EndlessReader struct {
+ tb timer
+ data []byte
+ offset int
+}
+
+// NewEndlessReader returns a new endless reader
+func NewEndlessReader(b []byte, tb timer) *EndlessReader {
+ return &EndlessReader{tb: tb, data: b, offset: 0}
+}
+
+// Read implements io.Reader. In practice, it
+// always returns (len(p), nil), although it
+// fills the supplied slice while the benchmark
+// timer is stopped.
+func (c *EndlessReader) Read(p []byte) (int, error) {
+ c.tb.StopTimer()
+ var n int
+ l := len(p)
+ m := len(c.data)
+ for n < l {
+ nn := copy(p[n:], c.data[c.offset:])
+ n += nn
+ c.offset += nn
+ c.offset %= m
+ }
+ c.tb.StartTimer()
+ return n, nil
+}
diff --git a/vendor/github.com/tinylib/msgp/msgp/defs.go b/vendor/github.com/tinylib/msgp/msgp/defs.go
new file mode 100644
index 000000000..c634eef1d
--- /dev/null
+++ b/vendor/github.com/tinylib/msgp/msgp/defs.go
@@ -0,0 +1,142 @@
+// This package is the support library for the msgp code generator (http://github.com/tinylib/msgp).
+//
+// This package defines the utilites used by the msgp code generator for encoding and decoding MessagePack
+// from []byte and io.Reader/io.Writer types. Much of this package is devoted to helping the msgp code
+// generator implement the Marshaler/Unmarshaler and Encodable/Decodable interfaces.
+//
+// This package defines four "families" of functions:
+// - AppendXxxx() appends an object to a []byte in MessagePack encoding.
+// - ReadXxxxBytes() reads an object from a []byte and returns the remaining bytes.
+// - (*Writer).WriteXxxx() writes an object to the buffered *Writer type.
+// - (*Reader).ReadXxxx() reads an object from a buffered *Reader type.
+//
+// Once a type has satisfied the `Encodable` and `Decodable` interfaces,
+// it can be written and read from arbitrary `io.Writer`s and `io.Reader`s using
+// msgp.Encode(io.Writer, msgp.Encodable)
+// and
+// msgp.Decode(io.Reader, msgp.Decodable)
+//
+// There are also methods for converting MessagePack to JSON without
+// an explicit de-serialization step.
+//
+// For additional tips, tricks, and gotchas, please visit
+// the wiki at http://github.com/tinylib/msgp
+package msgp
+
+const last4 = 0x0f
+const first4 = 0xf0
+const last5 = 0x1f
+const first3 = 0xe0
+const last7 = 0x7f
+
+func isfixint(b byte) bool {
+ return b>>7 == 0
+}
+
+func isnfixint(b byte) bool {
+ return b&first3 == mnfixint
+}
+
+func isfixmap(b byte) bool {
+ return b&first4 == mfixmap
+}
+
+func isfixarray(b byte) bool {
+ return b&first4 == mfixarray
+}
+
+func isfixstr(b byte) bool {
+ return b&first3 == mfixstr
+}
+
+func wfixint(u uint8) byte {
+ return u & last7
+}
+
+func rfixint(b byte) uint8 {
+ return b
+}
+
+func wnfixint(i int8) byte {
+ return byte(i) | mnfixint
+}
+
+func rnfixint(b byte) int8 {
+ return int8(b)
+}
+
+func rfixmap(b byte) uint8 {
+ return b & last4
+}
+
+func wfixmap(u uint8) byte {
+ return mfixmap | (u & last4)
+}
+
+func rfixstr(b byte) uint8 {
+ return b & last5
+}
+
+func wfixstr(u uint8) byte {
+ return (u & last5) | mfixstr
+}
+
+func rfixarray(b byte) uint8 {
+ return (b & last4)
+}
+
+func wfixarray(u uint8) byte {
+ return (u & last4) | mfixarray
+}
+
+// These are all the byte
+// prefixes defined by the
+// msgpack standard
+const (
+ // 0XXXXXXX
+ mfixint uint8 = 0x00
+
+ // 111XXXXX
+ mnfixint uint8 = 0xe0
+
+ // 1000XXXX
+ mfixmap uint8 = 0x80
+
+ // 1001XXXX
+ mfixarray uint8 = 0x90
+
+ // 101XXXXX
+ mfixstr uint8 = 0xa0
+
+ mnil uint8 = 0xc0
+ mfalse uint8 = 0xc2
+ mtrue uint8 = 0xc3
+ mbin8 uint8 = 0xc4
+ mbin16 uint8 = 0xc5
+ mbin32 uint8 = 0xc6
+ mext8 uint8 = 0xc7
+ mext16 uint8 = 0xc8
+ mext32 uint8 = 0xc9
+ mfloat32 uint8 = 0xca
+ mfloat64 uint8 = 0xcb
+ muint8 uint8 = 0xcc
+ muint16 uint8 = 0xcd
+ muint32 uint8 = 0xce
+ muint64 uint8 = 0xcf
+ mint8 uint8 = 0xd0
+ mint16 uint8 = 0xd1
+ mint32 uint8 = 0xd2
+ mint64 uint8 = 0xd3
+ mfixext1 uint8 = 0xd4
+ mfixext2 uint8 = 0xd5
+ mfixext4 uint8 = 0xd6
+ mfixext8 uint8 = 0xd7
+ mfixext16 uint8 = 0xd8
+ mstr8 uint8 = 0xd9
+ mstr16 uint8 = 0xda
+ mstr32 uint8 = 0xdb
+ marray16 uint8 = 0xdc
+ marray32 uint8 = 0xdd
+ mmap16 uint8 = 0xde
+ mmap32 uint8 = 0xdf
+)
diff --git a/vendor/github.com/tinylib/msgp/msgp/edit.go b/vendor/github.com/tinylib/msgp/msgp/edit.go
new file mode 100644
index 000000000..b473a6f66
--- /dev/null
+++ b/vendor/github.com/tinylib/msgp/msgp/edit.go
@@ -0,0 +1,242 @@
+package msgp
+
+import (
+ "math"
+)
+
+// Locate returns a []byte pointing to the field
+// in a messagepack map with the provided key. (The returned []byte
+// points to a sub-slice of 'raw'; Locate does no allocations.) If the
+// key doesn't exist in the map, a zero-length []byte will be returned.
+func Locate(key string, raw []byte) []byte {
+ s, n := locate(raw, key)
+ return raw[s:n]
+}
+
+// Replace takes a key ("key") in a messagepack map ("raw")
+// and replaces its value with the one provided and returns
+// the new []byte. The returned []byte may point to the same
+// memory as "raw". Replace makes no effort to evaluate the validity
+// of the contents of 'val'. It may use up to the full capacity of 'raw.'
+// Replace returns 'nil' if the field doesn't exist or if the object in 'raw'
+// is not a map.
+func Replace(key string, raw []byte, val []byte) []byte {
+ start, end := locate(raw, key)
+ if start == end {
+ return nil
+ }
+ return replace(raw, start, end, val, true)
+}
+
+// CopyReplace works similarly to Replace except that the returned
+// byte slice does not point to the same memory as 'raw'. CopyReplace
+// returns 'nil' if the field doesn't exist or 'raw' isn't a map.
+func CopyReplace(key string, raw []byte, val []byte) []byte {
+ start, end := locate(raw, key)
+ if start == end {
+ return nil
+ }
+ return replace(raw, start, end, val, false)
+}
+
+// Remove removes a key-value pair from 'raw'. It returns
+// 'raw' unchanged if the key didn't exist.
+func Remove(key string, raw []byte) []byte {
+ start, end := locateKV(raw, key)
+ if start == end {
+ return raw
+ }
+ raw = raw[:start+copy(raw[start:], raw[end:])]
+ return resizeMap(raw, -1)
+}
+
+// HasKey returns whether the map in 'raw' has
+// a field with key 'key'
+func HasKey(key string, raw []byte) bool {
+ sz, bts, err := ReadMapHeaderBytes(raw)
+ if err != nil {
+ return false
+ }
+ var field []byte
+ for i := uint32(0); i < sz; i++ {
+ field, bts, err = ReadStringZC(bts)
+ if err != nil {
+ return false
+ }
+ if UnsafeString(field) == key {
+ return true
+ }
+ }
+ return false
+}
+
+func replace(raw []byte, start int, end int, val []byte, inplace bool) []byte {
+ ll := end - start // length of segment to replace
+ lv := len(val)
+
+ if inplace {
+ extra := lv - ll
+
+ // fastest case: we're doing
+ // a 1:1 replacement
+ if extra == 0 {
+ copy(raw[start:], val)
+ return raw
+
+ } else if extra < 0 {
+ // 'val' smaller than replaced value
+ // copy in place and shift back
+
+ x := copy(raw[start:], val)
+ y := copy(raw[start+x:], raw[end:])
+ return raw[:start+x+y]
+
+ } else if extra < cap(raw)-len(raw) {
+ // 'val' less than (cap-len) extra bytes
+ // copy in place and shift forward
+ raw = raw[0 : len(raw)+extra]
+ // shift end forward
+ copy(raw[end+extra:], raw[end:])
+ copy(raw[start:], val)
+ return raw
+ }
+ }
+
+ // we have to allocate new space
+ out := make([]byte, len(raw)+len(val)-ll)
+ x := copy(out, raw[:start])
+ y := copy(out[x:], val)
+ copy(out[x+y:], raw[end:])
+ return out
+}
+
+// locate does a naive O(n) search for the map key; returns start, end
+// (returns 0,0 on error)
+func locate(raw []byte, key string) (start int, end int) {
+ var (
+ sz uint32
+ bts []byte
+ field []byte
+ err error
+ )
+ sz, bts, err = ReadMapHeaderBytes(raw)
+ if err != nil {
+ return
+ }
+
+ // loop and locate field
+ for i := uint32(0); i < sz; i++ {
+ field, bts, err = ReadStringZC(bts)
+ if err != nil {
+ return 0, 0
+ }
+ if UnsafeString(field) == key {
+ // start location
+ l := len(raw)
+ start = l - len(bts)
+ bts, err = Skip(bts)
+ if err != nil {
+ return 0, 0
+ }
+ end = l - len(bts)
+ return
+ }
+ bts, err = Skip(bts)
+ if err != nil {
+ return 0, 0
+ }
+ }
+ return 0, 0
+}
+
+// locate key AND value
+func locateKV(raw []byte, key string) (start int, end int) {
+ var (
+ sz uint32
+ bts []byte
+ field []byte
+ err error
+ )
+ sz, bts, err = ReadMapHeaderBytes(raw)
+ if err != nil {
+ return 0, 0
+ }
+
+ for i := uint32(0); i < sz; i++ {
+ tmp := len(bts)
+ field, bts, err = ReadStringZC(bts)
+ if err != nil {
+ return 0, 0
+ }
+ if UnsafeString(field) == key {
+ start = len(raw) - tmp
+ bts, err = Skip(bts)
+ if err != nil {
+ return 0, 0
+ }
+ end = len(raw) - len(bts)
+ return
+ }
+ bts, err = Skip(bts)
+ if err != nil {
+ return 0, 0
+ }
+ }
+ return 0, 0
+}
+
+// delta is delta on map size
+func resizeMap(raw []byte, delta int64) []byte {
+ var sz int64
+ switch raw[0] {
+ case mmap16:
+ sz = int64(big.Uint16(raw[1:]))
+ if sz+delta <= math.MaxUint16 {
+ big.PutUint16(raw[1:], uint16(sz+delta))
+ return raw
+ }
+ if cap(raw)-len(raw) >= 2 {
+ raw = raw[0 : len(raw)+2]
+ copy(raw[5:], raw[3:])
+ raw[0] = mmap32
+ big.PutUint32(raw[1:], uint32(sz+delta))
+ return raw
+ }
+ n := make([]byte, 0, len(raw)+5)
+ n = AppendMapHeader(n, uint32(sz+delta))
+ return append(n, raw[3:]...)
+
+ case mmap32:
+ sz = int64(big.Uint32(raw[1:]))
+ big.PutUint32(raw[1:], uint32(sz+delta))
+ return raw
+
+ default:
+ sz = int64(rfixmap(raw[0]))
+ if sz+delta < 16 {
+ raw[0] = wfixmap(uint8(sz + delta))
+ return raw
+ } else if sz+delta <= math.MaxUint16 {
+ if cap(raw)-len(raw) >= 2 {
+ raw = raw[0 : len(raw)+2]
+ copy(raw[3:], raw[1:])
+ raw[0] = mmap16
+ big.PutUint16(raw[1:], uint16(sz+delta))
+ return raw
+ }
+ n := make([]byte, 0, len(raw)+5)
+ n = AppendMapHeader(n, uint32(sz+delta))
+ return append(n, raw[1:]...)
+ }
+ if cap(raw)-len(raw) >= 4 {
+ raw = raw[0 : len(raw)+4]
+ copy(raw[5:], raw[1:])
+ raw[0] = mmap32
+ big.PutUint32(raw[1:], uint32(sz+delta))
+ return raw
+ }
+ n := make([]byte, 0, len(raw)+5)
+ n = AppendMapHeader(n, uint32(sz+delta))
+ return append(n, raw[1:]...)
+ }
+}
diff --git a/vendor/github.com/tinylib/msgp/msgp/elsize.go b/vendor/github.com/tinylib/msgp/msgp/elsize.go
new file mode 100644
index 000000000..95762e7ee
--- /dev/null
+++ b/vendor/github.com/tinylib/msgp/msgp/elsize.go
@@ -0,0 +1,99 @@
+package msgp
+
+// size of every object on the wire,
+// plus type information. gives us
+// constant-time type information
+// for traversing composite objects.
+//
+var sizes = [256]bytespec{
+ mnil: {size: 1, extra: constsize, typ: NilType},
+ mfalse: {size: 1, extra: constsize, typ: BoolType},
+ mtrue: {size: 1, extra: constsize, typ: BoolType},
+ mbin8: {size: 2, extra: extra8, typ: BinType},
+ mbin16: {size: 3, extra: extra16, typ: BinType},
+ mbin32: {size: 5, extra: extra32, typ: BinType},
+ mext8: {size: 3, extra: extra8, typ: ExtensionType},
+ mext16: {size: 4, extra: extra16, typ: ExtensionType},
+ mext32: {size: 6, extra: extra32, typ: ExtensionType},
+ mfloat32: {size: 5, extra: constsize, typ: Float32Type},
+ mfloat64: {size: 9, extra: constsize, typ: Float64Type},
+ muint8: {size: 2, extra: constsize, typ: UintType},
+ muint16: {size: 3, extra: constsize, typ: UintType},
+ muint32: {size: 5, extra: constsize, typ: UintType},
+ muint64: {size: 9, extra: constsize, typ: UintType},
+ mint8: {size: 2, extra: constsize, typ: IntType},
+ mint16: {size: 3, extra: constsize, typ: IntType},
+ mint32: {size: 5, extra: constsize, typ: IntType},
+ mint64: {size: 9, extra: constsize, typ: IntType},
+ mfixext1: {size: 3, extra: constsize, typ: ExtensionType},
+ mfixext2: {size: 4, extra: constsize, typ: ExtensionType},
+ mfixext4: {size: 6, extra: constsize, typ: ExtensionType},
+ mfixext8: {size: 10, extra: constsize, typ: ExtensionType},
+ mfixext16: {size: 18, extra: constsize, typ: ExtensionType},
+ mstr8: {size: 2, extra: extra8, typ: StrType},
+ mstr16: {size: 3, extra: extra16, typ: StrType},
+ mstr32: {size: 5, extra: extra32, typ: StrType},
+ marray16: {size: 3, extra: array16v, typ: ArrayType},
+ marray32: {size: 5, extra: array32v, typ: ArrayType},
+ mmap16: {size: 3, extra: map16v, typ: MapType},
+ mmap32: {size: 5, extra: map32v, typ: MapType},
+}
+
+func init() {
+ // set up fixed fields
+
+ // fixint
+ for i := mfixint; i < 0x80; i++ {
+ sizes[i] = bytespec{size: 1, extra: constsize, typ: IntType}
+ }
+
+ // nfixint
+ for i := uint16(mnfixint); i < 0x100; i++ {
+ sizes[uint8(i)] = bytespec{size: 1, extra: constsize, typ: IntType}
+ }
+
+ // fixstr gets constsize,
+ // since the prefix yields the size
+ for i := mfixstr; i < 0xc0; i++ {
+ sizes[i] = bytespec{size: 1 + rfixstr(i), extra: constsize, typ: StrType}
+ }
+
+ // fixmap
+ for i := mfixmap; i < 0x90; i++ {
+ sizes[i] = bytespec{size: 1, extra: varmode(2 * rfixmap(i)), typ: MapType}
+ }
+
+ // fixarray
+ for i := mfixarray; i < 0xa0; i++ {
+ sizes[i] = bytespec{size: 1, extra: varmode(rfixarray(i)), typ: ArrayType}
+ }
+}
+
+// a valid bytespsec has
+// non-zero 'size' and
+// non-zero 'typ'
+type bytespec struct {
+ size uint8 // prefix size information
+ extra varmode // extra size information
+ typ Type // type
+ _ byte // makes bytespec 4 bytes (yes, this matters)
+}
+
+// size mode
+// if positive, # elements for composites
+type varmode int8
+
+const (
+ constsize varmode = 0 // constant size (size bytes + uint8(varmode) objects)
+ extra8 = -1 // has uint8(p[1]) extra bytes
+ extra16 = -2 // has be16(p[1:]) extra bytes
+ extra32 = -3 // has be32(p[1:]) extra bytes
+ map16v = -4 // use map16
+ map32v = -5 // use map32
+ array16v = -6 // use array16
+ array32v = -7 // use array32
+)
+
+func getType(v byte) Type {
+ return sizes[v].typ
+}
diff --git a/vendor/github.com/tinylib/msgp/msgp/errors.go b/vendor/github.com/tinylib/msgp/msgp/errors.go
new file mode 100644
index 000000000..cc78a980c
--- /dev/null
+++ b/vendor/github.com/tinylib/msgp/msgp/errors.go
@@ -0,0 +1,314 @@
+package msgp
+
+import (
+ "fmt"
+ "reflect"
+)
+
+const resumableDefault = false
+
+var (
+ // ErrShortBytes is returned when the
+ // slice being decoded is too short to
+ // contain the contents of the message
+ ErrShortBytes error = errShort{}
+
+ // this error is only returned
+ // if we reach code that should
+ // be unreachable
+ fatal error = errFatal{}
+)
+
+// Error is the interface satisfied
+// by all of the errors that originate
+// from this package.
+type Error interface {
+ error
+
+ // Resumable returns whether
+ // or not the error means that
+ // the stream of data is malformed
+ // and the information is unrecoverable.
+ Resumable() bool
+}
+
+// contextError allows msgp Error instances to be enhanced with additional
+// context about their origin.
+type contextError interface {
+ Error
+
+ // withContext must not modify the error instance - it must clone and
+ // return a new error with the context added.
+ withContext(ctx string) error
+}
+
+// Cause returns the underlying cause of an error that has been wrapped
+// with additional context.
+func Cause(e error) error {
+ out := e
+ if e, ok := e.(errWrapped); ok && e.cause != nil {
+ out = e.cause
+ }
+ return out
+}
+
+// Resumable returns whether or not the error means that the stream of data is
+// malformed and the information is unrecoverable.
+func Resumable(e error) bool {
+ if e, ok := e.(Error); ok {
+ return e.Resumable()
+ }
+ return resumableDefault
+}
+
+// WrapError wraps an error with additional context that allows the part of the
+// serialized type that caused the problem to be identified. Underlying errors
+// can be retrieved using Cause()
+//
+// The input error is not modified - a new error should be returned.
+//
+// ErrShortBytes is not wrapped with any context due to backward compatibility
+// issues with the public API.
+//
+func WrapError(err error, ctx ...interface{}) error {
+ switch e := err.(type) {
+ case errShort:
+ return e
+ case contextError:
+ return e.withContext(ctxString(ctx))
+ default:
+ return errWrapped{cause: err, ctx: ctxString(ctx)}
+ }
+}
+
+// ctxString converts the incoming interface{} slice into a single string.
+func ctxString(ctx []interface{}) string {
+ out := ""
+ for idx, cv := range ctx {
+ if idx > 0 {
+ out += "/"
+ }
+ out += fmt.Sprintf("%v", cv)
+ }
+ return out
+}
+
+func addCtx(ctx, add string) string {
+ if ctx != "" {
+ return add + "/" + ctx
+ } else {
+ return add
+ }
+}
+
+// errWrapped allows arbitrary errors passed to WrapError to be enhanced with
+// context and unwrapped with Cause()
+type errWrapped struct {
+ cause error
+ ctx string
+}
+
+func (e errWrapped) Error() string {
+ if e.ctx != "" {
+ return fmt.Sprintf("%s at %s", e.cause, e.ctx)
+ } else {
+ return e.cause.Error()
+ }
+}
+
+func (e errWrapped) Resumable() bool {
+ if e, ok := e.cause.(Error); ok {
+ return e.Resumable()
+ }
+ return resumableDefault
+}
+
+type errShort struct{}
+
+func (e errShort) Error() string { return "msgp: too few bytes left to read object" }
+func (e errShort) Resumable() bool { return false }
+
+type errFatal struct {
+ ctx string
+}
+
+func (f errFatal) Error() string {
+ out := "msgp: fatal decoding error (unreachable code)"
+ if f.ctx != "" {
+ out += " at " + f.ctx
+ }
+ return out
+}
+
+func (f errFatal) Resumable() bool { return false }
+
+func (f errFatal) withContext(ctx string) error { f.ctx = addCtx(f.ctx, ctx); return f }
+
+// ArrayError is an error returned
+// when decoding a fix-sized array
+// of the wrong size
+type ArrayError struct {
+ Wanted uint32
+ Got uint32
+ ctx string
+}
+
+// Error implements the error interface
+func (a ArrayError) Error() string {
+ out := fmt.Sprintf("msgp: wanted array of size %d; got %d", a.Wanted, a.Got)
+ if a.ctx != "" {
+ out += " at " + a.ctx
+ }
+ return out
+}
+
+// Resumable is always 'true' for ArrayErrors
+func (a ArrayError) Resumable() bool { return true }
+
+func (a ArrayError) withContext(ctx string) error { a.ctx = addCtx(a.ctx, ctx); return a }
+
+// IntOverflow is returned when a call
+// would downcast an integer to a type
+// with too few bits to hold its value.
+type IntOverflow struct {
+ Value int64 // the value of the integer
+ FailedBitsize int // the bit size that the int64 could not fit into
+ ctx string
+}
+
+// Error implements the error interface
+func (i IntOverflow) Error() string {
+ str := fmt.Sprintf("msgp: %d overflows int%d", i.Value, i.FailedBitsize)
+ if i.ctx != "" {
+ str += " at " + i.ctx
+ }
+ return str
+}
+
+// Resumable is always 'true' for overflows
+func (i IntOverflow) Resumable() bool { return true }
+
+func (i IntOverflow) withContext(ctx string) error { i.ctx = addCtx(i.ctx, ctx); return i }
+
+// UintOverflow is returned when a call
+// would downcast an unsigned integer to a type
+// with too few bits to hold its value
+type UintOverflow struct {
+ Value uint64 // value of the uint
+ FailedBitsize int // the bit size that couldn't fit the value
+ ctx string
+}
+
+// Error implements the error interface
+func (u UintOverflow) Error() string {
+ str := fmt.Sprintf("msgp: %d overflows uint%d", u.Value, u.FailedBitsize)
+ if u.ctx != "" {
+ str += " at " + u.ctx
+ }
+ return str
+}
+
+// Resumable is always 'true' for overflows
+func (u UintOverflow) Resumable() bool { return true }
+
+func (u UintOverflow) withContext(ctx string) error { u.ctx = addCtx(u.ctx, ctx); return u }
+
+// UintBelowZero is returned when a call
+// would cast a signed integer below zero
+// to an unsigned integer.
+type UintBelowZero struct {
+ Value int64 // value of the incoming int
+ ctx string
+}
+
+// Error implements the error interface
+func (u UintBelowZero) Error() string {
+ str := fmt.Sprintf("msgp: attempted to cast int %d to unsigned", u.Value)
+ if u.ctx != "" {
+ str += " at " + u.ctx
+ }
+ return str
+}
+
+// Resumable is always 'true' for overflows
+func (u UintBelowZero) Resumable() bool { return true }
+
+func (u UintBelowZero) withContext(ctx string) error {
+ u.ctx = ctx
+ return u
+}
+
+// A TypeError is returned when a particular
+// decoding method is unsuitable for decoding
+// a particular MessagePack value.
+type TypeError struct {
+ Method Type // Type expected by method
+ Encoded Type // Type actually encoded
+
+ ctx string
+}
+
+// Error implements the error interface
+func (t TypeError) Error() string {
+ out := fmt.Sprintf("msgp: attempted to decode type %q with method for %q", t.Encoded, t.Method)
+ if t.ctx != "" {
+ out += " at " + t.ctx
+ }
+ return out
+}
+
+// Resumable returns 'true' for TypeErrors
+func (t TypeError) Resumable() bool { return true }
+
+func (t TypeError) withContext(ctx string) error { t.ctx = addCtx(t.ctx, ctx); return t }
+
+// returns either InvalidPrefixError or
+// TypeError depending on whether or not
+// the prefix is recognized
+func badPrefix(want Type, lead byte) error {
+ t := sizes[lead].typ
+ if t == InvalidType {
+ return InvalidPrefixError(lead)
+ }
+ return TypeError{Method: want, Encoded: t}
+}
+
+// InvalidPrefixError is returned when a bad encoding
+// uses a prefix that is not recognized in the MessagePack standard.
+// This kind of error is unrecoverable.
+type InvalidPrefixError byte
+
+// Error implements the error interface
+func (i InvalidPrefixError) Error() string {
+ return fmt.Sprintf("msgp: unrecognized type prefix 0x%x", byte(i))
+}
+
+// Resumable returns 'false' for InvalidPrefixErrors
+func (i InvalidPrefixError) Resumable() bool { return false }
+
+// ErrUnsupportedType is returned
+// when a bad argument is supplied
+// to a function that takes `interface{}`.
+type ErrUnsupportedType struct {
+ T reflect.Type
+
+ ctx string
+}
+
+// Error implements error
+func (e *ErrUnsupportedType) Error() string {
+ out := fmt.Sprintf("msgp: type %q not supported", e.T)
+ if e.ctx != "" {
+ out += " at " + e.ctx
+ }
+ return out
+}
+
+// Resumable returns 'true' for ErrUnsupportedType
+func (e *ErrUnsupportedType) Resumable() bool { return true }
+
+func (e *ErrUnsupportedType) withContext(ctx string) error {
+ o := *e
+ o.ctx = addCtx(o.ctx, ctx)
+ return &o
+}
diff --git a/vendor/github.com/tinylib/msgp/msgp/extension.go b/vendor/github.com/tinylib/msgp/msgp/extension.go
new file mode 100644
index 000000000..0b31dcdb7
--- /dev/null
+++ b/vendor/github.com/tinylib/msgp/msgp/extension.go
@@ -0,0 +1,549 @@
+package msgp
+
+import (
+ "fmt"
+ "math"
+)
+
+const (
+ // Complex64Extension is the extension number used for complex64
+ Complex64Extension = 3
+
+ // Complex128Extension is the extension number used for complex128
+ Complex128Extension = 4
+
+ // TimeExtension is the extension number used for time.Time
+ TimeExtension = 5
+)
+
+// our extensions live here
+var extensionReg = make(map[int8]func() Extension)
+
+// RegisterExtension registers extensions so that they
+// can be initialized and returned by methods that
+// decode `interface{}` values. This should only
+// be called during initialization. f() should return
+// a newly-initialized zero value of the extension. Keep in
+// mind that extensions 3, 4, and 5 are reserved for
+// complex64, complex128, and time.Time, respectively,
+// and that MessagePack reserves extension types from -127 to -1.
+//
+// For example, if you wanted to register a user-defined struct:
+//
+// msgp.RegisterExtension(10, func() msgp.Extension { &MyExtension{} })
+//
+// RegisterExtension will panic if you call it multiple times
+// with the same 'typ' argument, or if you use a reserved
+// type (3, 4, or 5).
+func RegisterExtension(typ int8, f func() Extension) {
+ switch typ {
+ case Complex64Extension, Complex128Extension, TimeExtension:
+ panic(fmt.Sprint("msgp: forbidden extension type:", typ))
+ }
+ if _, ok := extensionReg[typ]; ok {
+ panic(fmt.Sprint("msgp: RegisterExtension() called with typ", typ, "more than once"))
+ }
+ extensionReg[typ] = f
+}
+
+// ExtensionTypeError is an error type returned
+// when there is a mis-match between an extension type
+// and the type encoded on the wire
+type ExtensionTypeError struct {
+ Got int8
+ Want int8
+}
+
+// Error implements the error interface
+func (e ExtensionTypeError) Error() string {
+ return fmt.Sprintf("msgp: error decoding extension: wanted type %d; got type %d", e.Want, e.Got)
+}
+
+// Resumable returns 'true' for ExtensionTypeErrors
+func (e ExtensionTypeError) Resumable() bool { return true }
+
+func errExt(got int8, wanted int8) error {
+ return ExtensionTypeError{Got: got, Want: wanted}
+}
+
+// Extension is the interface fulfilled
+// by types that want to define their
+// own binary encoding.
+type Extension interface {
+ // ExtensionType should return
+ // a int8 that identifies the concrete
+ // type of the extension. (Types <0 are
+ // officially reserved by the MessagePack
+ // specifications.)
+ ExtensionType() int8
+
+ // Len should return the length
+ // of the data to be encoded
+ Len() int
+
+ // MarshalBinaryTo should copy
+ // the data into the supplied slice,
+ // assuming that the slice has length Len()
+ MarshalBinaryTo([]byte) error
+
+ UnmarshalBinary([]byte) error
+}
+
+// RawExtension implements the Extension interface
+type RawExtension struct {
+ Data []byte
+ Type int8
+}
+
+// ExtensionType implements Extension.ExtensionType, and returns r.Type
+func (r *RawExtension) ExtensionType() int8 { return r.Type }
+
+// Len implements Extension.Len, and returns len(r.Data)
+func (r *RawExtension) Len() int { return len(r.Data) }
+
+// MarshalBinaryTo implements Extension.MarshalBinaryTo,
+// and returns a copy of r.Data
+func (r *RawExtension) MarshalBinaryTo(d []byte) error {
+ copy(d, r.Data)
+ return nil
+}
+
+// UnmarshalBinary implements Extension.UnmarshalBinary,
+// and sets r.Data to the contents of the provided slice
+func (r *RawExtension) UnmarshalBinary(b []byte) error {
+ if cap(r.Data) >= len(b) {
+ r.Data = r.Data[0:len(b)]
+ } else {
+ r.Data = make([]byte, len(b))
+ }
+ copy(r.Data, b)
+ return nil
+}
+
+// WriteExtension writes an extension type to the writer
+func (mw *Writer) WriteExtension(e Extension) error {
+ l := e.Len()
+ var err error
+ switch l {
+ case 0:
+ o, err := mw.require(3)
+ if err != nil {
+ return err
+ }
+ mw.buf[o] = mext8
+ mw.buf[o+1] = 0
+ mw.buf[o+2] = byte(e.ExtensionType())
+ case 1:
+ o, err := mw.require(2)
+ if err != nil {
+ return err
+ }
+ mw.buf[o] = mfixext1
+ mw.buf[o+1] = byte(e.ExtensionType())
+ case 2:
+ o, err := mw.require(2)
+ if err != nil {
+ return err
+ }
+ mw.buf[o] = mfixext2
+ mw.buf[o+1] = byte(e.ExtensionType())
+ case 4:
+ o, err := mw.require(2)
+ if err != nil {
+ return err
+ }
+ mw.buf[o] = mfixext4
+ mw.buf[o+1] = byte(e.ExtensionType())
+ case 8:
+ o, err := mw.require(2)
+ if err != nil {
+ return err
+ }
+ mw.buf[o] = mfixext8
+ mw.buf[o+1] = byte(e.ExtensionType())
+ case 16:
+ o, err := mw.require(2)
+ if err != nil {
+ return err
+ }
+ mw.buf[o] = mfixext16
+ mw.buf[o+1] = byte(e.ExtensionType())
+ default:
+ switch {
+ case l < math.MaxUint8:
+ o, err := mw.require(3)
+ if err != nil {
+ return err
+ }
+ mw.buf[o] = mext8
+ mw.buf[o+1] = byte(uint8(l))
+ mw.buf[o+2] = byte(e.ExtensionType())
+ case l < math.MaxUint16:
+ o, err := mw.require(4)
+ if err != nil {
+ return err
+ }
+ mw.buf[o] = mext16
+ big.PutUint16(mw.buf[o+1:], uint16(l))
+ mw.buf[o+3] = byte(e.ExtensionType())
+ default:
+ o, err := mw.require(6)
+ if err != nil {
+ return err
+ }
+ mw.buf[o] = mext32
+ big.PutUint32(mw.buf[o+1:], uint32(l))
+ mw.buf[o+5] = byte(e.ExtensionType())
+ }
+ }
+ // we can only write directly to the
+ // buffer if we're sure that it
+ // fits the object
+ if l <= mw.bufsize() {
+ o, err := mw.require(l)
+ if err != nil {
+ return err
+ }
+ return e.MarshalBinaryTo(mw.buf[o:])
+ }
+ // here we create a new buffer
+ // just large enough for the body
+ // and save it as the write buffer
+ err = mw.flush()
+ if err != nil {
+ return err
+ }
+ buf := make([]byte, l)
+ err = e.MarshalBinaryTo(buf)
+ if err != nil {
+ return err
+ }
+ mw.buf = buf
+ mw.wloc = l
+ return nil
+}
+
+// peek at the extension type, assuming the next
+// kind to be read is Extension
+func (m *Reader) peekExtensionType() (int8, error) {
+ p, err := m.R.Peek(2)
+ if err != nil {
+ return 0, err
+ }
+ spec := sizes[p[0]]
+ if spec.typ != ExtensionType {
+ return 0, badPrefix(ExtensionType, p[0])
+ }
+ if spec.extra == constsize {
+ return int8(p[1]), nil
+ }
+ size := spec.size
+ p, err = m.R.Peek(int(size))
+ if err != nil {
+ return 0, err
+ }
+ return int8(p[size-1]), nil
+}
+
+// peekExtension peeks at the extension encoding type
+// (must guarantee at least 1 byte in 'b')
+func peekExtension(b []byte) (int8, error) {
+ spec := sizes[b[0]]
+ size := spec.size
+ if spec.typ != ExtensionType {
+ return 0, badPrefix(ExtensionType, b[0])
+ }
+ if len(b) < int(size) {
+ return 0, ErrShortBytes
+ }
+ // for fixed extensions,
+ // the type information is in
+ // the second byte
+ if spec.extra == constsize {
+ return int8(b[1]), nil
+ }
+ // otherwise, it's in the last
+ // part of the prefix
+ return int8(b[size-1]), nil
+}
+
+// ReadExtension reads the next object from the reader
+// as an extension. ReadExtension will fail if the next
+// object in the stream is not an extension, or if
+// e.Type() is not the same as the wire type.
+func (m *Reader) ReadExtension(e Extension) (err error) {
+ var p []byte
+ p, err = m.R.Peek(2)
+ if err != nil {
+ return
+ }
+ lead := p[0]
+ var read int
+ var off int
+ switch lead {
+ case mfixext1:
+ if int8(p[1]) != e.ExtensionType() {
+ err = errExt(int8(p[1]), e.ExtensionType())
+ return
+ }
+ p, err = m.R.Peek(3)
+ if err != nil {
+ return
+ }
+ err = e.UnmarshalBinary(p[2:])
+ if err == nil {
+ _, err = m.R.Skip(3)
+ }
+ return
+
+ case mfixext2:
+ if int8(p[1]) != e.ExtensionType() {
+ err = errExt(int8(p[1]), e.ExtensionType())
+ return
+ }
+ p, err = m.R.Peek(4)
+ if err != nil {
+ return
+ }
+ err = e.UnmarshalBinary(p[2:])
+ if err == nil {
+ _, err = m.R.Skip(4)
+ }
+ return
+
+ case mfixext4:
+ if int8(p[1]) != e.ExtensionType() {
+ err = errExt(int8(p[1]), e.ExtensionType())
+ return
+ }
+ p, err = m.R.Peek(6)
+ if err != nil {
+ return
+ }
+ err = e.UnmarshalBinary(p[2:])
+ if err == nil {
+ _, err = m.R.Skip(6)
+ }
+ return
+
+ case mfixext8:
+ if int8(p[1]) != e.ExtensionType() {
+ err = errExt(int8(p[1]), e.ExtensionType())
+ return
+ }
+ p, err = m.R.Peek(10)
+ if err != nil {
+ return
+ }
+ err = e.UnmarshalBinary(p[2:])
+ if err == nil {
+ _, err = m.R.Skip(10)
+ }
+ return
+
+ case mfixext16:
+ if int8(p[1]) != e.ExtensionType() {
+ err = errExt(int8(p[1]), e.ExtensionType())
+ return
+ }
+ p, err = m.R.Peek(18)
+ if err != nil {
+ return
+ }
+ err = e.UnmarshalBinary(p[2:])
+ if err == nil {
+ _, err = m.R.Skip(18)
+ }
+ return
+
+ case mext8:
+ p, err = m.R.Peek(3)
+ if err != nil {
+ return
+ }
+ if int8(p[2]) != e.ExtensionType() {
+ err = errExt(int8(p[2]), e.ExtensionType())
+ return
+ }
+ read = int(uint8(p[1]))
+ off = 3
+
+ case mext16:
+ p, err = m.R.Peek(4)
+ if err != nil {
+ return
+ }
+ if int8(p[3]) != e.ExtensionType() {
+ err = errExt(int8(p[3]), e.ExtensionType())
+ return
+ }
+ read = int(big.Uint16(p[1:]))
+ off = 4
+
+ case mext32:
+ p, err = m.R.Peek(6)
+ if err != nil {
+ return
+ }
+ if int8(p[5]) != e.ExtensionType() {
+ err = errExt(int8(p[5]), e.ExtensionType())
+ return
+ }
+ read = int(big.Uint32(p[1:]))
+ off = 6
+
+ default:
+ err = badPrefix(ExtensionType, lead)
+ return
+ }
+
+ p, err = m.R.Peek(read + off)
+ if err != nil {
+ return
+ }
+ err = e.UnmarshalBinary(p[off:])
+ if err == nil {
+ _, err = m.R.Skip(read + off)
+ }
+ return
+}
+
+// AppendExtension appends a MessagePack extension to the provided slice
+func AppendExtension(b []byte, e Extension) ([]byte, error) {
+ l := e.Len()
+ var o []byte
+ var n int
+ switch l {
+ case 0:
+ o, n = ensure(b, 3)
+ o[n] = mext8
+ o[n+1] = 0
+ o[n+2] = byte(e.ExtensionType())
+ return o[:n+3], nil
+ case 1:
+ o, n = ensure(b, 3)
+ o[n] = mfixext1
+ o[n+1] = byte(e.ExtensionType())
+ n += 2
+ case 2:
+ o, n = ensure(b, 4)
+ o[n] = mfixext2
+ o[n+1] = byte(e.ExtensionType())
+ n += 2
+ case 4:
+ o, n = ensure(b, 6)
+ o[n] = mfixext4
+ o[n+1] = byte(e.ExtensionType())
+ n += 2
+ case 8:
+ o, n = ensure(b, 10)
+ o[n] = mfixext8
+ o[n+1] = byte(e.ExtensionType())
+ n += 2
+ case 16:
+ o, n = ensure(b, 18)
+ o[n] = mfixext16
+ o[n+1] = byte(e.ExtensionType())
+ n += 2
+ default:
+ switch {
+ case l < math.MaxUint8:
+ o, n = ensure(b, l+3)
+ o[n] = mext8
+ o[n+1] = byte(uint8(l))
+ o[n+2] = byte(e.ExtensionType())
+ n += 3
+ case l < math.MaxUint16:
+ o, n = ensure(b, l+4)
+ o[n] = mext16
+ big.PutUint16(o[n+1:], uint16(l))
+ o[n+3] = byte(e.ExtensionType())
+ n += 4
+ default:
+ o, n = ensure(b, l+6)
+ o[n] = mext32
+ big.PutUint32(o[n+1:], uint32(l))
+ o[n+5] = byte(e.ExtensionType())
+ n += 6
+ }
+ }
+ return o, e.MarshalBinaryTo(o[n:])
+}
+
+// ReadExtensionBytes reads an extension from 'b' into 'e'
+// and returns any remaining bytes.
+// Possible errors:
+// - ErrShortBytes ('b' not long enough)
+// - ExtensionTypeErorr{} (wire type not the same as e.Type())
+// - TypeErorr{} (next object not an extension)
+// - InvalidPrefixError
+// - An umarshal error returned from e.UnmarshalBinary
+func ReadExtensionBytes(b []byte, e Extension) ([]byte, error) {
+ l := len(b)
+ if l < 3 {
+ return b, ErrShortBytes
+ }
+ lead := b[0]
+ var (
+ sz int // size of 'data'
+ off int // offset of 'data'
+ typ int8
+ )
+ switch lead {
+ case mfixext1:
+ typ = int8(b[1])
+ sz = 1
+ off = 2
+ case mfixext2:
+ typ = int8(b[1])
+ sz = 2
+ off = 2
+ case mfixext4:
+ typ = int8(b[1])
+ sz = 4
+ off = 2
+ case mfixext8:
+ typ = int8(b[1])
+ sz = 8
+ off = 2
+ case mfixext16:
+ typ = int8(b[1])
+ sz = 16
+ off = 2
+ case mext8:
+ sz = int(uint8(b[1]))
+ typ = int8(b[2])
+ off = 3
+ if sz == 0 {
+ return b[3:], e.UnmarshalBinary(b[3:3])
+ }
+ case mext16:
+ if l < 4 {
+ return b, ErrShortBytes
+ }
+ sz = int(big.Uint16(b[1:]))
+ typ = int8(b[3])
+ off = 4
+ case mext32:
+ if l < 6 {
+ return b, ErrShortBytes
+ }
+ sz = int(big.Uint32(b[1:]))
+ typ = int8(b[5])
+ off = 6
+ default:
+ return b, badPrefix(ExtensionType, lead)
+ }
+
+ if typ != e.ExtensionType() {
+ return b, errExt(typ, e.ExtensionType())
+ }
+
+ // the data of the extension starts
+ // at 'off' and is 'sz' bytes long
+ if len(b[off:]) < sz {
+ return b, ErrShortBytes
+ }
+ tot := off + sz
+ return b[tot:], e.UnmarshalBinary(b[off:tot])
+}
diff --git a/vendor/github.com/tinylib/msgp/msgp/file.go b/vendor/github.com/tinylib/msgp/msgp/file.go
new file mode 100644
index 000000000..8e7370ebc
--- /dev/null
+++ b/vendor/github.com/tinylib/msgp/msgp/file.go
@@ -0,0 +1,92 @@
+// +build linux darwin dragonfly freebsd netbsd openbsd
+// +build !appengine
+
+package msgp
+
+import (
+ "os"
+ "syscall"
+)
+
+// ReadFile reads a file into 'dst' using
+// a read-only memory mapping. Consequently,
+// the file must be mmap-able, and the
+// Unmarshaler should never write to
+// the source memory. (Methods generated
+// by the msgp tool obey that constraint, but
+// user-defined implementations may not.)
+//
+// Reading and writing through file mappings
+// is only efficient for large files; small
+// files are best read and written using
+// the ordinary streaming interfaces.
+//
+func ReadFile(dst Unmarshaler, file *os.File) error {
+ stat, err := file.Stat()
+ if err != nil {
+ return err
+ }
+ data, err := syscall.Mmap(int(file.Fd()), 0, int(stat.Size()), syscall.PROT_READ, syscall.MAP_SHARED)
+ if err != nil {
+ return err
+ }
+ adviseRead(data)
+ _, err = dst.UnmarshalMsg(data)
+ uerr := syscall.Munmap(data)
+ if err == nil {
+ err = uerr
+ }
+ return err
+}
+
+// MarshalSizer is the combination
+// of the Marshaler and Sizer
+// interfaces.
+type MarshalSizer interface {
+ Marshaler
+ Sizer
+}
+
+// WriteFile writes a file from 'src' using
+// memory mapping. It overwrites the entire
+// contents of the previous file.
+// The mapping size is calculated
+// using the `Msgsize()` method
+// of 'src', so it must produce a result
+// equal to or greater than the actual encoded
+// size of the object. Otherwise,
+// a fault (SIGBUS) will occur.
+//
+// Reading and writing through file mappings
+// is only efficient for large files; small
+// files are best read and written using
+// the ordinary streaming interfaces.
+//
+// NOTE: The performance of this call
+// is highly OS- and filesystem-dependent.
+// Users should take care to test that this
+// performs as expected in a production environment.
+// (Linux users should run a kernel and filesystem
+// that support fallocate(2) for the best results.)
+func WriteFile(src MarshalSizer, file *os.File) error {
+ sz := src.Msgsize()
+ err := fallocate(file, int64(sz))
+ if err != nil {
+ return err
+ }
+ data, err := syscall.Mmap(int(file.Fd()), 0, sz, syscall.PROT_READ|syscall.PROT_WRITE, syscall.MAP_SHARED)
+ if err != nil {
+ return err
+ }
+ adviseWrite(data)
+ chunk := data[:0]
+ chunk, err = src.MarshalMsg(chunk)
+ if err != nil {
+ return err
+ }
+ uerr := syscall.Munmap(data)
+ if uerr != nil {
+ return uerr
+ }
+ return file.Truncate(int64(len(chunk)))
+}
diff --git a/vendor/github.com/tinylib/msgp/msgp/file_port.go b/vendor/github.com/tinylib/msgp/msgp/file_port.go
new file mode 100644
index 000000000..6e654dbdc
--- /dev/null
+++ b/vendor/github.com/tinylib/msgp/msgp/file_port.go
@@ -0,0 +1,47 @@
+// +build windows appengine
+
+package msgp
+
+import (
+ "io/ioutil"
+ "os"
+)
+
+// MarshalSizer is the combination
+// of the Marshaler and Sizer
+// interfaces.
+type MarshalSizer interface {
+ Marshaler
+ Sizer
+}
+
+func ReadFile(dst Unmarshaler, file *os.File) error {
+ if u, ok := dst.(Decodable); ok {
+ return u.DecodeMsg(NewReader(file))
+ }
+
+ data, err := ioutil.ReadAll(file)
+ if err != nil {
+ return err
+ }
+ _, err = dst.UnmarshalMsg(data)
+ return err
+}
+
+func WriteFile(src MarshalSizer, file *os.File) error {
+ if e, ok := src.(Encodable); ok {
+ w := NewWriter(file)
+ err := e.EncodeMsg(w)
+ if err == nil {
+ err = w.Flush()
+ }
+ return err
+ }
+
+ raw, err := src.MarshalMsg(nil)
+ if err != nil {
+ return err
+ }
+ _, err = file.Write(raw)
+ return err
+}
diff --git a/vendor/github.com/tinylib/msgp/msgp/integers.go b/vendor/github.com/tinylib/msgp/msgp/integers.go
new file mode 100644
index 000000000..f817d7759
--- /dev/null
+++ b/vendor/github.com/tinylib/msgp/msgp/integers.go
@@ -0,0 +1,174 @@
+package msgp
+
+/* ----------------------------------
+ integer encoding utilities
+ (inline-able)
+
+ TODO(tinylib): there are faster,
+ albeit non-portable solutions
+ to the code below. implement
+ byteswap?
+ ---------------------------------- */
+
+func putMint64(b []byte, i int64) {
+ b[0] = mint64
+ b[1] = byte(i >> 56)
+ b[2] = byte(i >> 48)
+ b[3] = byte(i >> 40)
+ b[4] = byte(i >> 32)
+ b[5] = byte(i >> 24)
+ b[6] = byte(i >> 16)
+ b[7] = byte(i >> 8)
+ b[8] = byte(i)
+}
+
+func getMint64(b []byte) int64 {
+ return (int64(b[1]) << 56) | (int64(b[2]) << 48) |
+ (int64(b[3]) << 40) | (int64(b[4]) << 32) |
+ (int64(b[5]) << 24) | (int64(b[6]) << 16) |
+ (int64(b[7]) << 8) | (int64(b[8]))
+}
+
+func putMint32(b []byte, i int32) {
+ b[0] = mint32
+ b[1] = byte(i >> 24)
+ b[2] = byte(i >> 16)
+ b[3] = byte(i >> 8)
+ b[4] = byte(i)
+}
+
+func getMint32(b []byte) int32 {
+ return (int32(b[1]) << 24) | (int32(b[2]) << 16) | (int32(b[3]) << 8) | (int32(b[4]))
+}
+
+func putMint16(b []byte, i int16) {
+ b[0] = mint16
+ b[1] = byte(i >> 8)
+ b[2] = byte(i)
+}
+
+func getMint16(b []byte) (i int16) {
+ return (int16(b[1]) << 8) | int16(b[2])
+}
+
+func putMint8(b []byte, i int8) {
+ b[0] = mint8
+ b[1] = byte(i)
+}
+
+func getMint8(b []byte) (i int8) {
+ return int8(b[1])
+}
+
+func putMuint64(b []byte, u uint64) {
+ b[0] = muint64
+ b[1] = byte(u >> 56)
+ b[2] = byte(u >> 48)
+ b[3] = byte(u >> 40)
+ b[4] = byte(u >> 32)
+ b[5] = byte(u >> 24)
+ b[6] = byte(u >> 16)
+ b[7] = byte(u >> 8)
+ b[8] = byte(u)
+}
+
+func getMuint64(b []byte) uint64 {
+ return (uint64(b[1]) << 56) | (uint64(b[2]) << 48) |
+ (uint64(b[3]) << 40) | (uint64(b[4]) << 32) |
+ (uint64(b[5]) << 24) | (uint64(b[6]) << 16) |
+ (uint64(b[7]) << 8) | (uint64(b[8]))
+}
+
+func putMuint32(b []byte, u uint32) {
+ b[0] = muint32
+ b[1] = byte(u >> 24)
+ b[2] = byte(u >> 16)
+ b[3] = byte(u >> 8)
+ b[4] = byte(u)
+}
+
+func getMuint32(b []byte) uint32 {
+ return (uint32(b[1]) << 24) | (uint32(b[2]) << 16) | (uint32(b[3]) << 8) | (uint32(b[4]))
+}
+
+func putMuint16(b []byte, u uint16) {
+ b[0] = muint16
+ b[1] = byte(u >> 8)
+ b[2] = byte(u)
+}
+
+func getMuint16(b []byte) uint16 {
+ return (uint16(b[1]) << 8) | uint16(b[2])
+}
+
+func putMuint8(b []byte, u uint8) {
+ b[0] = muint8
+ b[1] = byte(u)
+}
+
+func getMuint8(b []byte) uint8 {
+ return uint8(b[1])
+}
+
+func getUnix(b []byte) (sec int64, nsec int32) {
+ sec = (int64(b[0]) << 56) | (int64(b[1]) << 48) |
+ (int64(b[2]) << 40) | (int64(b[3]) << 32) |
+ (int64(b[4]) << 24) | (int64(b[5]) << 16) |
+ (int64(b[6]) << 8) | (int64(b[7]))
+
+ nsec = (int32(b[8]) << 24) | (int32(b[9]) << 16) | (int32(b[10]) << 8) | (int32(b[11]))
+ return
+}
+
+func putUnix(b []byte, sec int64, nsec int32) {
+ b[0] = byte(sec >> 56)
+ b[1] = byte(sec >> 48)
+ b[2] = byte(sec >> 40)
+ b[3] = byte(sec >> 32)
+ b[4] = byte(sec >> 24)
+ b[5] = byte(sec >> 16)
+ b[6] = byte(sec >> 8)
+ b[7] = byte(sec)
+ b[8] = byte(nsec >> 24)
+ b[9] = byte(nsec >> 16)
+ b[10] = byte(nsec >> 8)
+ b[11] = byte(nsec)
+}
+
+/* -----------------------------
+ prefix utilities
+ ----------------------------- */
+
+// write prefix and uint8
+func prefixu8(b []byte, pre byte, sz uint8) {
+ b[0] = pre
+ b[1] = byte(sz)
+}
+
+// write prefix and big-endian uint16
+func prefixu16(b []byte, pre byte, sz uint16) {
+ b[0] = pre
+ b[1] = byte(sz >> 8)
+ b[2] = byte(sz)
+}
+
+// write prefix and big-endian uint32
+func prefixu32(b []byte, pre byte, sz uint32) {
+ b[0] = pre
+ b[1] = byte(sz >> 24)
+ b[2] = byte(sz >> 16)
+ b[3] = byte(sz >> 8)
+ b[4] = byte(sz)
+}
+
+func prefixu64(b []byte, pre byte, sz uint64) {
+ b[0] = pre
+ b[1] = byte(sz >> 56)
+ b[2] = byte(sz >> 48)
+ b[3] = byte(sz >> 40)
+ b[4] = byte(sz >> 32)
+ b[5] = byte(sz >> 24)
+ b[6] = byte(sz >> 16)
+ b[7] = byte(sz >> 8)
+ b[8] = byte(sz)
+}
diff --git a/vendor/github.com/tinylib/msgp/msgp/json.go b/vendor/github.com/tinylib/msgp/msgp/json.go
new file mode 100644
index 000000000..4325860ad
--- /dev/null
+++ b/vendor/github.com/tinylib/msgp/msgp/json.go
@@ -0,0 +1,542 @@
+package msgp
+
+import (
+ "bufio"
+ "encoding/base64"
+ "encoding/json"
+ "io"
+ "strconv"
+ "unicode/utf8"
+)
+
+var (
+ null = []byte("null")
+ hex = []byte("0123456789abcdef")
+)
+
+var defuns [_maxtype]func(jsWriter, *Reader) (int, error)
+
+// note: there is an initialization loop if
+// this isn't set up during init()
+func init() {
+ // since none of these functions are inline-able,
+ // there is not much of a penalty to the indirect
+ // call. however, this is best expressed as a jump-table...
+ defuns = [_maxtype]func(jsWriter, *Reader) (int, error){
+ StrType: rwString,
+ BinType: rwBytes,
+ MapType: rwMap,
+ ArrayType: rwArray,
+ Float64Type: rwFloat64,
+ Float32Type: rwFloat32,
+ BoolType: rwBool,
+ IntType: rwInt,
+ UintType: rwUint,
+ NilType: rwNil,
+ ExtensionType: rwExtension,
+ Complex64Type: rwExtension,
+ Complex128Type: rwExtension,
+ TimeType: rwTime,
+ }
+}
+
+// this is the interface
+// used to write json
+type jsWriter interface {
+ io.Writer
+ io.ByteWriter
+ WriteString(string) (int, error)
+}
+
+// CopyToJSON reads MessagePack from 'src' and copies it
+// as JSON to 'dst' until EOF.
+func CopyToJSON(dst io.Writer, src io.Reader) (n int64, err error) {
+ r := NewReader(src)
+ n, err = r.WriteToJSON(dst)
+ freeR(r)
+ return
+}
+
+// WriteToJSON translates MessagePack from 'r' and writes it as
+// JSON to 'w' until the underlying reader returns io.EOF. It returns
+// the number of bytes written, and an error if it stopped before EOF.
+func (r *Reader) WriteToJSON(w io.Writer) (n int64, err error) {
+ var j jsWriter
+ var bf *bufio.Writer
+ if jsw, ok := w.(jsWriter); ok {
+ j = jsw
+ } else {
+ bf = bufio.NewWriter(w)
+ j = bf
+ }
+ var nn int
+ for err == nil {
+ nn, err = rwNext(j, r)
+ n += int64(nn)
+ }
+ if err != io.EOF {
+ if bf != nil {
+ bf.Flush()
+ }
+ return
+ }
+ err = nil
+ if bf != nil {
+ err = bf.Flush()
+ }
+ return
+}
+
+func rwNext(w jsWriter, src *Reader) (int, error) {
+ t, err := src.NextType()
+ if err != nil {
+ return 0, err
+ }
+ return defuns[t](w, src)
+}
+
+func rwMap(dst jsWriter, src *Reader) (n int, err error) {
+ var comma bool
+ var sz uint32
+ var field []byte
+
+ sz, err = src.ReadMapHeader()
+ if err != nil {
+ return
+ }
+
+ if sz == 0 {
+ return dst.WriteString("{}")
+ }
+
+ err = dst.WriteByte('{')
+ if err != nil {
+ return
+ }
+ n++
+ var nn int
+ for i := uint32(0); i < sz; i++ {
+ if comma {
+ err = dst.WriteByte(',')
+ if err != nil {
+ return
+ }
+ n++
+ }
+
+ field, err = src.ReadMapKeyPtr()
+ if err != nil {
+ return
+ }
+ nn, err = rwquoted(dst, field)
+ n += nn
+ if err != nil {
+ return
+ }
+
+ err = dst.WriteByte(':')
+ if err != nil {
+ return
+ }
+ n++
+ nn, err = rwNext(dst, src)
+ n += nn
+ if err != nil {
+ return
+ }
+ if !comma {
+ comma = true
+ }
+ }
+
+ err = dst.WriteByte('}')
+ if err != nil {
+ return
+ }
+ n++
+ return
+}
+
+func rwArray(dst jsWriter, src *Reader) (n int, err error) {
+ err = dst.WriteByte('[')
+ if err != nil {
+ return
+ }
+ var sz uint32
+ var nn int
+ sz, err = src.ReadArrayHeader()
+ if err != nil {
+ return
+ }
+ comma := false
+ for i := uint32(0); i < sz; i++ {
+ if comma {
+ err = dst.WriteByte(',')
+ if err != nil {
+ return
+ }
+ n++
+ }
+ nn, err = rwNext(dst, src)
+ n += nn
+ if err != nil {
+ return
+ }
+ comma = true
+ }
+
+ err = dst.WriteByte(']')
+ if err != nil {
+ return
+ }
+ n++
+ return
+}
+
+func rwNil(dst jsWriter, src *Reader) (int, error) {
+ err := src.ReadNil()
+ if err != nil {
+ return 0, err
+ }
+ return dst.Write(null)
+}
+
+func rwFloat32(dst jsWriter, src *Reader) (int, error) {
+ f, err := src.ReadFloat32()
+ if err != nil {
+ return 0, err
+ }
+ src.scratch = strconv.AppendFloat(src.scratch[:0], float64(f), 'f', -1, 64)
+ return dst.Write(src.scratch)
+}
+
+func rwFloat64(dst jsWriter, src *Reader) (int, error) {
+ f, err := src.ReadFloat64()
+ if err != nil {
+ return 0, err
+ }
+ src.scratch = strconv.AppendFloat(src.scratch[:0], f, 'f', -1, 32)
+ return dst.Write(src.scratch)
+}
+
+func rwInt(dst jsWriter, src *Reader) (int, error) {
+ i, err := src.ReadInt64()
+ if err != nil {
+ return 0, err
+ }
+ src.scratch = strconv.AppendInt(src.scratch[:0], i, 10)
+ return dst.Write(src.scratch)
+}
+
+func rwUint(dst jsWriter, src *Reader) (int, error) {
+ u, err := src.ReadUint64()
+ if err != nil {
+ return 0, err
+ }
+ src.scratch = strconv.AppendUint(src.scratch[:0], u, 10)
+ return dst.Write(src.scratch)
+}
+
+func rwBool(dst jsWriter, src *Reader) (int, error) {
+ b, err := src.ReadBool()
+ if err != nil {
+ return 0, err
+ }
+ if b {
+ return dst.WriteString("true")
+ }
+ return dst.WriteString("false")
+}
+
+func rwTime(dst jsWriter, src *Reader) (int, error) {
+ t, err := src.ReadTime()
+ if err != nil {
+ return 0, err
+ }
+ bts, err := t.MarshalJSON()
+ if err != nil {
+ return 0, err
+ }
+ return dst.Write(bts)
+}
+
+func rwExtension(dst jsWriter, src *Reader) (n int, err error) {
+ et, err := src.peekExtensionType()
+ if err != nil {
+ return 0, err
+ }
+
+ // registered extensions can override
+ // the JSON encoding
+ if j, ok := extensionReg[et]; ok {
+ var bts []byte
+ e := j()
+ err = src.ReadExtension(e)
+ if err != nil {
+ return
+ }
+ bts, err = json.Marshal(e)
+ if err != nil {
+ return
+ }
+ return dst.Write(bts)
+ }
+
+ e := RawExtension{}
+ e.Type = et
+ err = src.ReadExtension(&e)
+ if err != nil {
+ return
+ }
+
+ var nn int
+ err = dst.WriteByte('{')
+ if err != nil {
+ return
+ }
+ n++
+
+ nn, err = dst.WriteString(`"type:"`)
+ n += nn
+ if err != nil {
+ return
+ }
+
+ src.scratch = strconv.AppendInt(src.scratch[0:0], int64(e.Type), 10)
+ nn, err = dst.Write(src.scratch)
+ n += nn
+ if err != nil {
+ return
+ }
+
+ nn, err = dst.WriteString(`,"data":"`)
+ n += nn
+ if err != nil {
+ return
+ }
+
+ enc := base64.NewEncoder(base64.StdEncoding, dst)
+
+ nn, err = enc.Write(e.Data)
+ n += nn
+ if err != nil {
+ return
+ }
+ err = enc.Close()
+ if err != nil {
+ return
+ }
+ nn, err = dst.WriteString(`"}`)
+ n += nn
+ return
+}
+
+func rwString(dst jsWriter, src *Reader) (n int, err error) {
+ var p []byte
+ p, err = src.R.Peek(1)
+ if err != nil {
+ return
+ }
+ lead := p[0]
+ var read int
+
+ if isfixstr(lead) {
+ read = int(rfixstr(lead))
+ src.R.Skip(1)
+ goto write
+ }
+
+ switch lead {
+ case mstr8:
+ p, err = src.R.Next(2)
+ if err != nil {
+ return
+ }
+ read = int(uint8(p[1]))
+ case mstr16:
+ p, err = src.R.Next(3)
+ if err != nil {
+ return
+ }
+ read = int(big.Uint16(p[1:]))
+ case mstr32:
+ p, err = src.R.Next(5)
+ if err != nil {
+ return
+ }
+ read = int(big.Uint32(p[1:]))
+ default:
+ err = badPrefix(StrType, lead)
+ return
+ }
+write:
+ p, err = src.R.Next(read)
+ if err != nil {
+ return
+ }
+ n, err = rwquoted(dst, p)
+ return
+}
+
+func rwBytes(dst jsWriter, src *Reader) (n int, err error) {
+ var nn int
+ err = dst.WriteByte('"')
+ if err != nil {
+ return
+ }
+ n++
+ src.scratch, err = src.ReadBytes(src.scratch[:0])
+ if err != nil {
+ return
+ }
+ enc := base64.NewEncoder(base64.StdEncoding, dst)
+ nn, err = enc.Write(src.scratch)
+ n += nn
+ if err != nil {
+ return
+ }
+ err = enc.Close()
+ if err != nil {
+ return
+ }
+ err = dst.WriteByte('"')
+ if err != nil {
+ return
+ }
+ n++
+ return
+}
+
+// Below (c) The Go Authors, 2009-2014
+// Subject to the BSD-style license found at http://golang.org
+//
+// see: encoding/json/encode.go:(*encodeState).stringbytes()
+func rwquoted(dst jsWriter, s []byte) (n int, err error) {
+ var nn int
+ err = dst.WriteByte('"')
+ if err != nil {
+ return
+ }
+ n++
+ start := 0
+ for i := 0; i < len(s); {
+ if b := s[i]; b < utf8.RuneSelf {
+ if 0x20 <= b && b != '\\' && b != '"' && b != '<' && b != '>' && b != '&' {
+ i++
+ continue
+ }
+ if start < i {
+ nn, err = dst.Write(s[start:i])
+ n += nn
+ if err != nil {
+ return
+ }
+ }
+ switch b {
+ case '\\', '"':
+ err = dst.WriteByte('\\')
+ if err != nil {
+ return
+ }
+ n++
+ err = dst.WriteByte(b)
+ if err != nil {
+ return
+ }
+ n++
+ case '\n':
+ err = dst.WriteByte('\\')
+ if err != nil {
+ return
+ }
+ n++
+ err = dst.WriteByte('n')
+ if err != nil {
+ return
+ }
+ n++
+ case '\r':
+ err = dst.WriteByte('\\')
+ if err != nil {
+ return
+ }
+ n++
+ err = dst.WriteByte('r')
+ if err != nil {
+ return
+ }
+ n++
+ default:
+ nn, err = dst.WriteString(`\u00`)
+ n += nn
+ if err != nil {
+ return
+ }
+ err = dst.WriteByte(hex[b>>4])
+ if err != nil {
+ return
+ }
+ n++
+ err = dst.WriteByte(hex[b&0xF])
+ if err != nil {
+ return
+ }
+ n++
+ }
+ i++
+ start = i
+ continue
+ }
+ c, size := utf8.DecodeRune(s[i:])
+ if c == utf8.RuneError && size == 1 {
+ if start < i {
+ nn, err = dst.Write(s[start:i])
+ n += nn
+ if err != nil {
+ return
+ }
+ nn, err = dst.WriteString(`\ufffd`)
+ n += nn
+ if err != nil {
+ return
+ }
+ i += size
+ start = i
+ continue
+ }
+ }
+ if c == '\u2028' || c == '\u2029' {
+ if start < i {
+ nn, err = dst.Write(s[start:i])
+ n += nn
+ if err != nil {
+ return
+ }
+ nn, err = dst.WriteString(`\u202`)
+ n += nn
+ if err != nil {
+ return
+ }
+ err = dst.WriteByte(hex[c&0xF])
+ if err != nil {
+ return
+ }
+ n++
+ }
+ }
+ i += size
+ }
+ if start < len(s) {
+ nn, err = dst.Write(s[start:])
+ n += nn
+ if err != nil {
+ return
+ }
+ }
+ err = dst.WriteByte('"')
+ if err != nil {
+ return
+ }
+ n++
+ return
+}
diff --git a/vendor/github.com/tinylib/msgp/msgp/json_bytes.go b/vendor/github.com/tinylib/msgp/msgp/json_bytes.go
new file mode 100644
index 000000000..438caf539
--- /dev/null
+++ b/vendor/github.com/tinylib/msgp/msgp/json_bytes.go
@@ -0,0 +1,363 @@
+package msgp
+
+import (
+ "bufio"
+ "encoding/base64"
+ "encoding/json"
+ "io"
+ "strconv"
+ "time"
+)
+
+var unfuns [_maxtype]func(jsWriter, []byte, []byte) ([]byte, []byte, error)
+
+func init() {
+
+ // NOTE(pmh): this is best expressed as a jump table,
+ // but gc doesn't do that yet. revisit post-go1.5.
+ unfuns = [_maxtype]func(jsWriter, []byte, []byte) ([]byte, []byte, error){
+ StrType: rwStringBytes,
+ BinType: rwBytesBytes,
+ MapType: rwMapBytes,
+ ArrayType: rwArrayBytes,
+ Float64Type: rwFloat64Bytes,
+ Float32Type: rwFloat32Bytes,
+ BoolType: rwBoolBytes,
+ IntType: rwIntBytes,
+ UintType: rwUintBytes,
+ NilType: rwNullBytes,
+ ExtensionType: rwExtensionBytes,
+ Complex64Type: rwExtensionBytes,
+ Complex128Type: rwExtensionBytes,
+ TimeType: rwTimeBytes,
+ }
+}
+
+// UnmarshalAsJSON takes raw messagepack and writes
+// it as JSON to 'w'. If an error is returned, the
+// bytes not translated will also be returned. If
+// no errors are encountered, the length of the returned
+// slice will be zero.
+func UnmarshalAsJSON(w io.Writer, msg []byte) ([]byte, error) {
+ var (
+ scratch []byte
+ cast bool
+ dst jsWriter
+ err error
+ )
+ if jsw, ok := w.(jsWriter); ok {
+ dst = jsw
+ cast = true
+ } else {
+ dst = bufio.NewWriterSize(w, 512)
+ }
+ for len(msg) > 0 && err == nil {
+ msg, scratch, err = writeNext(dst, msg, scratch)
+ }
+ if !cast && err == nil {
+ err = dst.(*bufio.Writer).Flush()
+ }
+ return msg, err
+}
+
+func writeNext(w jsWriter, msg []byte, scratch []byte) ([]byte, []byte, error) {
+ if len(msg) < 1 {
+ return msg, scratch, ErrShortBytes
+ }
+ t := getType(msg[0])
+ if t == InvalidType {
+ return msg, scratch, InvalidPrefixError(msg[0])
+ }
+ if t == ExtensionType {
+ et, err := peekExtension(msg)
+ if err != nil {
+ return nil, scratch, err
+ }
+ if et == TimeExtension {
+ t = TimeType
+ }
+ }
+ return unfuns[t](w, msg, scratch)
+}
+
+func rwArrayBytes(w jsWriter, msg []byte, scratch []byte) ([]byte, []byte, error) {
+ sz, msg, err := ReadArrayHeaderBytes(msg)
+ if err != nil {
+ return msg, scratch, err
+ }
+ err = w.WriteByte('[')
+ if err != nil {
+ return msg, scratch, err
+ }
+ for i := uint32(0); i < sz; i++ {
+ if i != 0 {
+ err = w.WriteByte(',')
+ if err != nil {
+ return msg, scratch, err
+ }
+ }
+ msg, scratch, err = writeNext(w, msg, scratch)
+ if err != nil {
+ return msg, scratch, err
+ }
+ }
+ err = w.WriteByte(']')
+ return msg, scratch, err
+}
+
+func rwMapBytes(w jsWriter, msg []byte, scratch []byte) ([]byte, []byte, error) {
+ sz, msg, err := ReadMapHeaderBytes(msg)
+ if err != nil {
+ return msg, scratch, err
+ }
+ err = w.WriteByte('{')
+ if err != nil {
+ return msg, scratch, err
+ }
+ for i := uint32(0); i < sz; i++ {
+ if i != 0 {
+ err = w.WriteByte(',')
+ if err != nil {
+ return msg, scratch, err
+ }
+ }
+ msg, scratch, err = rwMapKeyBytes(w, msg, scratch)
+ if err != nil {
+ return msg, scratch, err
+ }
+ err = w.WriteByte(':')
+ if err != nil {
+ return msg, scratch, err
+ }
+ msg, scratch, err = writeNext(w, msg, scratch)
+ if err != nil {
+ return msg, scratch, err
+ }
+ }
+ err = w.WriteByte('}')
+ return msg, scratch, err
+}
+
+func rwMapKeyBytes(w jsWriter, msg []byte, scratch []byte) ([]byte, []byte, error) {
+ msg, scratch, err := rwStringBytes(w, msg, scratch)
+ if err != nil {
+ if tperr, ok := err.(TypeError); ok && tperr.Encoded == BinType {
+ return rwBytesBytes(w, msg, scratch)
+ }
+ }
+ return msg, scratch, err
+}
+
+func rwStringBytes(w jsWriter, msg []byte, scratch []byte) ([]byte, []byte, error) {
+ str, msg, err := ReadStringZC(msg)
+ if err != nil {
+ return msg, scratch, err
+ }
+ _, err = rwquoted(w, str)
+ return msg, scratch, err
+}
+
+func rwBytesBytes(w jsWriter, msg []byte, scratch []byte) ([]byte, []byte, error) {
+ bts, msg, err := ReadBytesZC(msg)
+ if err != nil {
+ return msg, scratch, err
+ }
+ l := base64.StdEncoding.EncodedLen(len(bts))
+ if cap(scratch) >= l {
+ scratch = scratch[0:l]
+ } else {
+ scratch = make([]byte, l)
+ }
+ base64.StdEncoding.Encode(scratch, bts)
+ err = w.WriteByte('"')
+ if err != nil {
+ return msg, scratch, err
+ }
+ _, err = w.Write(scratch)
+ if err != nil {
+ return msg, scratch, err
+ }
+ err = w.WriteByte('"')
+ return msg, scratch, err
+}
+
+func rwNullBytes(w jsWriter, msg []byte, scratch []byte) ([]byte, []byte, error) {
+ msg, err := ReadNilBytes(msg)
+ if err != nil {
+ return msg, scratch, err
+ }
+ _, err = w.Write(null)
+ return msg, scratch, err
+}
+
+func rwBoolBytes(w jsWriter, msg []byte, scratch []byte) ([]byte, []byte, error) {
+ b, msg, err := ReadBoolBytes(msg)
+ if err != nil {
+ return msg, scratch, err
+ }
+ if b {
+ _, err = w.WriteString("true")
+ return msg, scratch, err
+ }
+ _, err = w.WriteString("false")
+ return msg, scratch, err
+}
+
+func rwIntBytes(w jsWriter, msg []byte, scratch []byte) ([]byte, []byte, error) {
+ i, msg, err := ReadInt64Bytes(msg)
+ if err != nil {
+ return msg, scratch, err
+ }
+ scratch = strconv.AppendInt(scratch[0:0], i, 10)
+ _, err = w.Write(scratch)
+ return msg, scratch, err
+}
+
+func rwUintBytes(w jsWriter, msg []byte, scratch []byte) ([]byte, []byte, error) {
+ u, msg, err := ReadUint64Bytes(msg)
+ if err != nil {
+ return msg, scratch, err
+ }
+ scratch = strconv.AppendUint(scratch[0:0], u, 10)
+ _, err = w.Write(scratch)
+ return msg, scratch, err
+}
+
+func rwFloatBytes(w jsWriter, msg []byte, f64 bool, scratch []byte) ([]byte, []byte, error) {
+ var f float64
+ var err error
+ var sz int
+ if f64 {
+ sz = 64
+ f, msg, err = ReadFloat64Bytes(msg)
+ } else {
+ sz = 32
+ var v float32
+ v, msg, err = ReadFloat32Bytes(msg)
+ f = float64(v)
+ }
+ if err != nil {
+ return msg, scratch, err
+ }
+ scratch = strconv.AppendFloat(scratch, f, 'f', -1, sz)
+ _, err = w.Write(scratch)
+ return msg, scratch, err
+}
+
+func rwFloat32Bytes(w jsWriter, msg []byte, scratch []byte) ([]byte, []byte, error) {
+ var f float32
+ var err error
+ f, msg, err = ReadFloat32Bytes(msg)
+ if err != nil {
+ return msg, scratch, err
+ }
+ scratch = strconv.AppendFloat(scratch[:0], float64(f), 'f', -1, 32)
+ _, err = w.Write(scratch)
+ return msg, scratch, err
+}
+
+func rwFloat64Bytes(w jsWriter, msg []byte, scratch []byte) ([]byte, []byte, error) {
+ var f float64
+ var err error
+ f, msg, err = ReadFloat64Bytes(msg)
+ if err != nil {
+ return msg, scratch, err
+ }
+ scratch = strconv.AppendFloat(scratch[:0], f, 'f', -1, 64)
+ _, err = w.Write(scratch)
+ return msg, scratch, err
+}
+
+func rwTimeBytes(w jsWriter, msg []byte, scratch []byte) ([]byte, []byte, error) {
+ var t time.Time
+ var err error
+ t, msg, err = ReadTimeBytes(msg)
+ if err != nil {
+ return msg, scratch, err
+ }
+ bts, err := t.MarshalJSON()
+ if err != nil {
+ return msg, scratch, err
+ }
+ _, err = w.Write(bts)
+ return msg, scratch, err
+}
+
+func rwExtensionBytes(w jsWriter, msg []byte, scratch []byte) ([]byte, []byte, error) {
+ var err error
+ var et int8
+ et, err = peekExtension(msg)
+ if err != nil {
+ return msg, scratch, err
+ }
+
+ // if it's time.Time
+ if et == TimeExtension {
+ var tm time.Time
+ tm, msg, err = ReadTimeBytes(msg)
+ if err != nil {
+ return msg, scratch, err
+ }
+ bts, err := tm.MarshalJSON()
+ if err != nil {
+ return msg, scratch, err
+ }
+ _, err = w.Write(bts)
+ return msg, scratch, err
+ }
+
+ // if the extension is registered,
+ // use its canonical JSON form
+ if f, ok := extensionReg[et]; ok {
+ e := f()
+ msg, err = ReadExtensionBytes(msg, e)
+ if err != nil {
+ return msg, scratch, err
+ }
+ bts, err := json.Marshal(e)
+ if err != nil {
+ return msg, scratch, err
+ }
+ _, err = w.Write(bts)
+ return msg, scratch, err
+ }
+
+ // otherwise, write `{"type": <num>, "data": "<base64data>"}`
+ r := RawExtension{}
+ r.Type = et
+ msg, err = ReadExtensionBytes(msg, &r)
+ if err != nil {
+ return msg, scratch, err
+ }
+ scratch, err = writeExt(w, r, scratch)
+ return msg, scratch, err
+}
+
+func writeExt(w jsWriter, r RawExtension, scratch []byte) ([]byte, error) {
+ _, err := w.WriteString(`{"type":`)
+ if err != nil {
+ return scratch, err
+ }
+ scratch = strconv.AppendInt(scratch[0:0], int64(r.Type), 10)
+ _, err = w.Write(scratch)
+ if err != nil {
+ return scratch, err
+ }
+ _, err = w.WriteString(`,"data":"`)
+ if err != nil {
+ return scratch, err
+ }
+ l := base64.StdEncoding.EncodedLen(len(r.Data))
+ if cap(scratch) >= l {
+ scratch = scratch[0:l]
+ } else {
+ scratch = make([]byte, l)
+ }
+ base64.StdEncoding.Encode(scratch, r.Data)
+ _, err = w.Write(scratch)
+ if err != nil {
+ return scratch, err
+ }
+ _, err = w.WriteString(`"}`)
+ return scratch, err
+}
diff --git a/vendor/github.com/tinylib/msgp/msgp/number.go b/vendor/github.com/tinylib/msgp/msgp/number.go
new file mode 100644
index 000000000..ad07ef995
--- /dev/null
+++ b/vendor/github.com/tinylib/msgp/msgp/number.go
@@ -0,0 +1,267 @@
+package msgp
+
+import (
+ "math"
+ "strconv"
+)
+
+// The portable parts of the Number implementation
+
+// Number can be
+// an int64, uint64, float32,
+// or float64 internally.
+// It can decode itself
+// from any of the native
+// messagepack number types.
+// The zero-value of Number
+// is Int(0). Using the equality
+// operator with Number compares
+// both the type and the value
+// of the number.
+type Number struct {
+ // internally, this
+ // is just a tagged union.
+ // the raw bits of the number
+ // are stored the same way regardless.
+ bits uint64
+ typ Type
+}
+
+// AsInt sets the number to an int64.
+func (n *Number) AsInt(i int64) {
+
+ // we always store int(0)
+ // as {0, InvalidType} in
+ // order to preserve
+ // the behavior of the == operator
+ if i == 0 {
+ n.typ = InvalidType
+ n.bits = 0
+ return
+ }
+
+ n.typ = IntType
+ n.bits = uint64(i)
+}
+
+// AsUint sets the number to a uint64.
+func (n *Number) AsUint(u uint64) {
+ n.typ = UintType
+ n.bits = u
+}
+
+// AsFloat32 sets the value of the number
+// to a float32.
+func (n *Number) AsFloat32(f float32) {
+ n.typ = Float32Type
+ n.bits = uint64(math.Float32bits(f))
+}
+
+// AsFloat64 sets the value of the
+// number to a float64.
+func (n *Number) AsFloat64(f float64) {
+ n.typ = Float64Type
+ n.bits = math.Float64bits(f)
+}
+
+// Int casts the number as an int64, and
+// returns whether or not that was the
+// underlying type.
+func (n *Number) Int() (int64, bool) {
+ return int64(n.bits), n.typ == IntType || n.typ == InvalidType
+}
+
+// Uint casts the number as a uint64, and returns
+// whether or not that was the underlying type.
+func (n *Number) Uint() (uint64, bool) {
+ return n.bits, n.typ == UintType
+}
+
+// Float casts the number to a float64, and
+// returns whether or not that was the underlying
+// type (either a float64 or a float32).
+func (n *Number) Float() (float64, bool) {
+ switch n.typ {
+ case Float32Type:
+ return float64(math.Float32frombits(uint32(n.bits))), true
+ case Float64Type:
+ return math.Float64frombits(n.bits), true
+ default:
+ return 0.0, false
+ }
+}
+
+// Type will return one of:
+// Float64Type, Float32Type, UintType, or IntType.
+func (n *Number) Type() Type {
+ if n.typ == InvalidType {
+ return IntType
+ }
+ return n.typ
+}
+
+// DecodeMsg implements msgp.Decodable
+func (n *Number) DecodeMsg(r *Reader) error {
+ typ, err := r.NextType()
+ if err != nil {
+ return err
+ }
+ switch typ {
+ case Float32Type:
+ f, err := r.ReadFloat32()
+ if err != nil {
+ return err
+ }
+ n.AsFloat32(f)
+ return nil
+ case Float64Type:
+ f, err := r.ReadFloat64()
+ if err != nil {
+ return err
+ }
+ n.AsFloat64(f)
+ return nil
+ case IntType:
+ i, err := r.ReadInt64()
+ if err != nil {
+ return err
+ }
+ n.AsInt(i)
+ return nil
+ case UintType:
+ u, err := r.ReadUint64()
+ if err != nil {
+ return err
+ }
+ n.AsUint(u)
+ return nil
+ default:
+ return TypeError{Encoded: typ, Method: IntType}
+ }
+}
+
+// UnmarshalMsg implements msgp.Unmarshaler
+func (n *Number) UnmarshalMsg(b []byte) ([]byte, error) {
+ typ := NextType(b)
+ switch typ {
+ case IntType:
+ i, o, err := ReadInt64Bytes(b)
+ if err != nil {
+ return b, err
+ }
+ n.AsInt(i)
+ return o, nil
+ case UintType:
+ u, o, err := ReadUint64Bytes(b)
+ if err != nil {
+ return b, err
+ }
+ n.AsUint(u)
+ return o, nil
+ case Float64Type:
+ f, o, err := ReadFloat64Bytes(b)
+ if err != nil {
+ return b, err
+ }
+ n.AsFloat64(f)
+ return o, nil
+ case Float32Type:
+ f, o, err := ReadFloat32Bytes(b)
+ if err != nil {
+ return b, err
+ }
+ n.AsFloat32(f)
+ return o, nil
+ default:
+ return b, TypeError{Method: IntType, Encoded: typ}
+ }
+}
+
+// MarshalMsg implements msgp.Marshaler
+func (n *Number) MarshalMsg(b []byte) ([]byte, error) {
+ switch n.typ {
+ case IntType:
+ return AppendInt64(b, int64(n.bits)), nil
+ case UintType:
+ return AppendUint64(b, uint64(n.bits)), nil
+ case Float64Type:
+ return AppendFloat64(b, math.Float64frombits(n.bits)), nil
+ case Float32Type:
+ return AppendFloat32(b, math.Float32frombits(uint32(n.bits))), nil
+ default:
+ return AppendInt64(b, 0), nil
+ }
+}
+
+// EncodeMsg implements msgp.Encodable
+func (n *Number) EncodeMsg(w *Writer) error {
+ switch n.typ {
+ case IntType:
+ return w.WriteInt64(int64(n.bits))
+ case UintType:
+ return w.WriteUint64(n.bits)
+ case Float64Type:
+ return w.WriteFloat64(math.Float64frombits(n.bits))
+ case Float32Type:
+ return w.WriteFloat32(math.Float32frombits(uint32(n.bits)))
+ default:
+ return w.WriteInt64(0)
+ }
+}
+
+// Msgsize implements msgp.Sizer
+func (n *Number) Msgsize() int {
+ switch n.typ {
+ case Float32Type:
+ return Float32Size
+ case Float64Type:
+ return Float64Size
+ case IntType:
+ return Int64Size
+ case UintType:
+ return Uint64Size
+ default:
+ return 1 // fixint(0)
+ }
+}
+
+// MarshalJSON implements json.Marshaler
+func (n *Number) MarshalJSON() ([]byte, error) {
+ t := n.Type()
+ if t == InvalidType {
+ return []byte{'0'}, nil
+ }
+ out := make([]byte, 0, 32)
+ switch t {
+ case Float32Type, Float64Type:
+ f, _ := n.Float()
+ return strconv.AppendFloat(out, f, 'f', -1, 64), nil
+ case IntType:
+ i, _ := n.Int()
+ return strconv.AppendInt(out, i, 10), nil
+ case UintType:
+ u, _ := n.Uint()
+ return strconv.AppendUint(out, u, 10), nil
+ default:
+ panic("(*Number).typ is invalid")
+ }
+}
+
+// String implements fmt.Stringer
+func (n *Number) String() string {
+ switch n.typ {
+ case InvalidType:
+ return "0"
+ case Float32Type, Float64Type:
+ f, _ := n.Float()
+ return strconv.FormatFloat(f, 'f', -1, 64)
+ case IntType:
+ i, _ := n.Int()
+ return strconv.FormatInt(i, 10)
+ case UintType:
+ u, _ := n.Uint()
+ return strconv.FormatUint(u, 10)
+ default:
+ panic("(*Number).typ is invalid")
+ }
+}
diff --git a/vendor/github.com/tinylib/msgp/msgp/purego.go b/vendor/github.com/tinylib/msgp/msgp/purego.go
new file mode 100644
index 000000000..c828f7eca
--- /dev/null
+++ b/vendor/github.com/tinylib/msgp/msgp/purego.go
@@ -0,0 +1,15 @@
+// +build purego appengine
+
+package msgp
+
+// let's just assume appengine
+// uses 64-bit hardware...
+const smallint = false
+
+func UnsafeString(b []byte) string {
+ return string(b)
+}
+
+func UnsafeBytes(s string) []byte {
+ return []byte(s)
+}
diff --git a/vendor/github.com/tinylib/msgp/msgp/read.go b/vendor/github.com/tinylib/msgp/msgp/read.go
new file mode 100644
index 000000000..aa668c573
--- /dev/null
+++ b/vendor/github.com/tinylib/msgp/msgp/read.go
@@ -0,0 +1,1358 @@
+package msgp
+
+import (
+ "io"
+ "math"
+ "sync"
+ "time"
+
+ "github.com/philhofer/fwd"
+)
+
+// where we keep old *Readers
+var readerPool = sync.Pool{New: func() interface{} { return &Reader{} }}
+
+// Type is a MessagePack wire type,
+// including this package's built-in
+// extension types.
+type Type byte
+
+// MessagePack Types
+//
+// The zero value of Type
+// is InvalidType.
+const (
+ InvalidType Type = iota
+
+ // MessagePack built-in types
+
+ StrType
+ BinType
+ MapType
+ ArrayType
+ Float64Type
+ Float32Type
+ BoolType
+ IntType
+ UintType
+ NilType
+ ExtensionType
+
+ // pseudo-types provided
+ // by extensions
+
+ Complex64Type
+ Complex128Type
+ TimeType
+
+ _maxtype
+)
+
+// String implements fmt.Stringer
+func (t Type) String() string {
+ switch t {
+ case StrType:
+ return "str"
+ case BinType:
+ return "bin"
+ case MapType:
+ return "map"
+ case ArrayType:
+ return "array"
+ case Float64Type:
+ return "float64"
+ case Float32Type:
+ return "float32"
+ case BoolType:
+ return "bool"
+ case UintType:
+ return "uint"
+ case IntType:
+ return "int"
+ case ExtensionType:
+ return "ext"
+ case NilType:
+ return "nil"
+ default:
+ return "<invalid>"
+ }
+}
+
+func freeR(m *Reader) {
+ readerPool.Put(m)
+}
+
+// Unmarshaler is the interface fulfilled
+// by objects that know how to unmarshal
+// themselves from MessagePack.
+// UnmarshalMsg unmarshals the object
+// from binary, returing any leftover
+// bytes and any errors encountered.
+type Unmarshaler interface {
+ UnmarshalMsg([]byte) ([]byte, error)
+}
+
+// Decodable is the interface fulfilled
+// by objects that know how to read
+// themselves from a *Reader.
+type Decodable interface {
+ DecodeMsg(*Reader) error
+}
+
+// Decode decodes 'd' from 'r'.
+func Decode(r io.Reader, d Decodable) error {
+ rd := NewReader(r)
+ err := d.DecodeMsg(rd)
+ freeR(rd)
+ return err
+}
+
+// NewReader returns a *Reader that
+// reads from the provided reader. The
+// reader will be buffered.
+func NewReader(r io.Reader) *Reader {
+ p := readerPool.Get().(*Reader)
+ if p.R == nil {
+ p.R = fwd.NewReader(r)
+ } else {
+ p.R.Reset(r)
+ }
+ return p
+}
+
+// NewReaderSize returns a *Reader with a buffer of the given size.
+// (This is vastly preferable to passing the decoder a reader that is already buffered.)
+func NewReaderSize(r io.Reader, sz int) *Reader {
+ return &Reader{R: fwd.NewReaderSize(r, sz)}
+}
+
+// Reader wraps an io.Reader and provides
+// methods to read MessagePack-encoded values
+// from it. Readers are buffered.
+type Reader struct {
+ // R is the buffered reader
+ // that the Reader uses
+ // to decode MessagePack.
+ // The Reader itself
+ // is stateless; all the
+ // buffering is done
+ // within R.
+ R *fwd.Reader
+ scratch []byte
+}
+
+// Read implements `io.Reader`
+func (m *Reader) Read(p []byte) (int, error) {
+ return m.R.Read(p)
+}
+
+// CopyNext reads the next object from m without decoding it and writes it to w.
+// It avoids unnecessary copies internally.
+func (m *Reader) CopyNext(w io.Writer) (int64, error) {
+ sz, o, err := getNextSize(m.R)
+ if err != nil {
+ return 0, err
+ }
+
+ var n int64
+ // Opportunistic optimization: if we can fit the whole thing in the m.R
+ // buffer, then just get a pointer to that, and pass it to w.Write,
+ // avoiding an allocation.
+ if int(sz) <= m.R.BufferSize() {
+ var nn int
+ var buf []byte
+ buf, err = m.R.Next(int(sz))
+ if err != nil {
+ if err == io.ErrUnexpectedEOF {
+ err = ErrShortBytes
+ }
+ return 0, err
+ }
+ nn, err = w.Write(buf)
+ n += int64(nn)
+ } else {
+ // Fall back to io.CopyN.
+ // May avoid allocating if w is a ReaderFrom (e.g. bytes.Buffer)
+ n, err = io.CopyN(w, m.R, int64(sz))
+ if err == io.ErrUnexpectedEOF {
+ err = ErrShortBytes
+ }
+ }
+ if err != nil {
+ return n, err
+ } else if n < int64(sz) {
+ return n, io.ErrShortWrite
+ }
+
+ // for maps and slices, read elements
+ for x := uintptr(0); x < o; x++ {
+ var n2 int64
+ n2, err = m.CopyNext(w)
+ if err != nil {
+ return n, err
+ }
+ n += n2
+ }
+ return n, nil
+}
+
+// ReadFull implements `io.ReadFull`
+func (m *Reader) ReadFull(p []byte) (int, error) {
+ return m.R.ReadFull(p)
+}
+
+// Reset resets the underlying reader.
+func (m *Reader) Reset(r io.Reader) { m.R.Reset(r) }
+
+// Buffered returns the number of bytes currently in the read buffer.
+func (m *Reader) Buffered() int { return m.R.Buffered() }
+
+// BufferSize returns the capacity of the read buffer.
+func (m *Reader) BufferSize() int { return m.R.BufferSize() }
+
+// NextType returns the next object type to be decoded.
+func (m *Reader) NextType() (Type, error) {
+ p, err := m.R.Peek(1)
+ if err != nil {
+ return InvalidType, err
+ }
+ t := getType(p[0])
+ if t == InvalidType {
+ return t, InvalidPrefixError(p[0])
+ }
+ if t == ExtensionType {
+ v, err := m.peekExtensionType()
+ if err != nil {
+ return InvalidType, err
+ }
+ switch v {
+ case Complex64Extension:
+ return Complex64Type, nil
+ case Complex128Extension:
+ return Complex128Type, nil
+ case TimeExtension:
+ return TimeType, nil
+ }
+ }
+ return t, nil
+}
+
+// IsNil returns whether or not
+// the next byte is a null messagepack byte
+func (m *Reader) IsNil() bool {
+ p, err := m.R.Peek(1)
+ return err == nil && p[0] == mnil
+}
+
+// getNextSize returns the size of the next object on the wire.
+// returns (obj size, obj elements, error)
+// only maps and arrays have non-zero obj elements
+// for maps and arrays, obj size does not include elements
+//
+// use uintptr b/c it's guaranteed to be large enough
+// to hold whatever we can fit in memory.
+func getNextSize(r *fwd.Reader) (uintptr, uintptr, error) {
+ b, err := r.Peek(1)
+ if err != nil {
+ return 0, 0, err
+ }
+ lead := b[0]
+ spec := &sizes[lead]
+ size, mode := spec.size, spec.extra
+ if size == 0 {
+ return 0, 0, InvalidPrefixError(lead)
+ }
+ if mode >= 0 {
+ return uintptr(size), uintptr(mode), nil
+ }
+ b, err = r.Peek(int(size))
+ if err != nil {
+ return 0, 0, err
+ }
+ switch mode {
+ case extra8:
+ return uintptr(size) + uintptr(b[1]), 0, nil
+ case extra16:
+ return uintptr(size) + uintptr(big.Uint16(b[1:])), 0, nil
+ case extra32:
+ return uintptr(size) + uintptr(big.Uint32(b[1:])), 0, nil
+ case map16v:
+ return uintptr(size), 2 * uintptr(big.Uint16(b[1:])), nil
+ case map32v:
+ return uintptr(size), 2 * uintptr(big.Uint32(b[1:])), nil
+ case array16v:
+ return uintptr(size), uintptr(big.Uint16(b[1:])), nil
+ case array32v:
+ return uintptr(size), uintptr(big.Uint32(b[1:])), nil
+ default:
+ return 0, 0, fatal
+ }
+}
+
+// Skip skips over the next object, regardless of
+// its type. If it is an array or map, the whole array
+// or map will be skipped.
+func (m *Reader) Skip() error {
+ var (
+ v uintptr // bytes
+ o uintptr // objects
+ err error
+ p []byte
+ )
+
+ // we can use the faster
+ // method if we have enough
+ // buffered data
+ if m.R.Buffered() >= 5 {
+ p, err = m.R.Peek(5)
+ if err != nil {
+ return err
+ }
+ v, o, err = getSize(p)
+ if err != nil {
+ return err
+ }
+ } else {
+ v, o, err = getNextSize(m.R)
+ if err != nil {
+ return err
+ }
+ }
+
+ // 'v' is always non-zero
+ // if err == nil
+ _, err = m.R.Skip(int(v))
+ if err != nil {
+ return err
+ }
+
+ // for maps and slices, skip elements
+ for x := uintptr(0); x < o; x++ {
+ err = m.Skip()
+ if err != nil {
+ return err
+ }
+ }
+ return nil
+}
+
+// ReadMapHeader reads the next object
+// as a map header and returns the size
+// of the map and the number of bytes written.
+// It will return a TypeError{} if the next
+// object is not a map.
+func (m *Reader) ReadMapHeader() (sz uint32, err error) {
+ var p []byte
+ var lead byte
+ p, err = m.R.Peek(1)
+ if err != nil {
+ return
+ }
+ lead = p[0]
+ if isfixmap(lead) {
+ sz = uint32(rfixmap(lead))
+ _, err = m.R.Skip(1)
+ return
+ }
+ switch lead {
+ case mmap16:
+ p, err = m.R.Next(3)
+ if err != nil {
+ return
+ }
+ sz = uint32(big.Uint16(p[1:]))
+ return
+ case mmap32:
+ p, err = m.R.Next(5)
+ if err != nil {
+ return
+ }
+ sz = big.Uint32(p[1:])
+ return
+ default:
+ err = badPrefix(MapType, lead)
+ return
+ }
+}
+
+// ReadMapKey reads either a 'str' or 'bin' field from
+// the reader and returns the value as a []byte. It uses
+// scratch for storage if it is large enough.
+func (m *Reader) ReadMapKey(scratch []byte) ([]byte, error) {
+ out, err := m.ReadStringAsBytes(scratch)
+ if err != nil {
+ if tperr, ok := err.(TypeError); ok && tperr.Encoded == BinType {
+ return m.ReadBytes(scratch)
+ }
+ return nil, err
+ }
+ return out, nil
+}
+
+// MapKeyPtr returns a []byte pointing to the contents
+// of a valid map key. The key cannot be empty, and it
+// must be shorter than the total buffer size of the
+// *Reader. Additionally, the returned slice is only
+// valid until the next *Reader method call. Users
+// should exercise extreme care when using this
+// method; writing into the returned slice may
+// corrupt future reads.
+func (m *Reader) ReadMapKeyPtr() ([]byte, error) {
+ p, err := m.R.Peek(1)
+ if err != nil {
+ return nil, err
+ }
+ lead := p[0]
+ var read int
+ if isfixstr(lead) {
+ read = int(rfixstr(lead))
+ m.R.Skip(1)
+ goto fill
+ }
+ switch lead {
+ case mstr8, mbin8:
+ p, err = m.R.Next(2)
+ if err != nil {
+ return nil, err
+ }
+ read = int(p[1])
+ case mstr16, mbin16:
+ p, err = m.R.Next(3)
+ if err != nil {
+ return nil, err
+ }
+ read = int(big.Uint16(p[1:]))
+ case mstr32, mbin32:
+ p, err = m.R.Next(5)
+ if err != nil {
+ return nil, err
+ }
+ read = int(big.Uint32(p[1:]))
+ default:
+ return nil, badPrefix(StrType, lead)
+ }
+fill:
+ if read == 0 {
+ return nil, ErrShortBytes
+ }
+ return m.R.Next(read)
+}
+
+// ReadArrayHeader reads the next object as an
+// array header and returns the size of the array
+// and the number of bytes read.
+func (m *Reader) ReadArrayHeader() (sz uint32, err error) {
+ var lead byte
+ var p []byte
+ p, err = m.R.Peek(1)
+ if err != nil {
+ return
+ }
+ lead = p[0]
+ if isfixarray(lead) {
+ sz = uint32(rfixarray(lead))
+ _, err = m.R.Skip(1)
+ return
+ }
+ switch lead {
+ case marray16:
+ p, err = m.R.Next(3)
+ if err != nil {
+ return
+ }
+ sz = uint32(big.Uint16(p[1:]))
+ return
+
+ case marray32:
+ p, err = m.R.Next(5)
+ if err != nil {
+ return
+ }
+ sz = big.Uint32(p[1:])
+ return
+
+ default:
+ err = badPrefix(ArrayType, lead)
+ return
+ }
+}
+
+// ReadNil reads a 'nil' MessagePack byte from the reader
+func (m *Reader) ReadNil() error {
+ p, err := m.R.Peek(1)
+ if err != nil {
+ return err
+ }
+ if p[0] != mnil {
+ return badPrefix(NilType, p[0])
+ }
+ _, err = m.R.Skip(1)
+ return err
+}
+
+// ReadFloat64 reads a float64 from the reader.
+// (If the value on the wire is encoded as a float32,
+// it will be up-cast to a float64.)
+func (m *Reader) ReadFloat64() (f float64, err error) {
+ var p []byte
+ p, err = m.R.Peek(9)
+ if err != nil {
+ // we'll allow a coversion from float32 to float64,
+ // since we don't lose any precision
+ if err == io.EOF && len(p) > 0 && p[0] == mfloat32 {
+ ef, err := m.ReadFloat32()
+ return float64(ef), err
+ }
+ return
+ }
+ if p[0] != mfloat64 {
+ // see above
+ if p[0] == mfloat32 {
+ ef, err := m.ReadFloat32()
+ return float64(ef), err
+ }
+ err = badPrefix(Float64Type, p[0])
+ return
+ }
+ f = math.Float64frombits(getMuint64(p))
+ _, err = m.R.Skip(9)
+ return
+}
+
+// ReadFloat32 reads a float32 from the reader
+func (m *Reader) ReadFloat32() (f float32, err error) {
+ var p []byte
+ p, err = m.R.Peek(5)
+ if err != nil {
+ return
+ }
+ if p[0] != mfloat32 {
+ err = badPrefix(Float32Type, p[0])
+ return
+ }
+ f = math.Float32frombits(getMuint32(p))
+ _, err = m.R.Skip(5)
+ return
+}
+
+// ReadBool reads a bool from the reader
+func (m *Reader) ReadBool() (b bool, err error) {
+ var p []byte
+ p, err = m.R.Peek(1)
+ if err != nil {
+ return
+ }
+ switch p[0] {
+ case mtrue:
+ b = true
+ case mfalse:
+ default:
+ err = badPrefix(BoolType, p[0])
+ return
+ }
+ _, err = m.R.Skip(1)
+ return
+}
+
+// ReadInt64 reads an int64 from the reader
+func (m *Reader) ReadInt64() (i int64, err error) {
+ var p []byte
+ var lead byte
+ p, err = m.R.Peek(1)
+ if err != nil {
+ return
+ }
+ lead = p[0]
+
+ if isfixint(lead) {
+ i = int64(rfixint(lead))
+ _, err = m.R.Skip(1)
+ return
+ } else if isnfixint(lead) {
+ i = int64(rnfixint(lead))
+ _, err = m.R.Skip(1)
+ return
+ }
+
+ switch lead {
+ case mint8:
+ p, err = m.R.Next(2)
+ if err != nil {
+ return
+ }
+ i = int64(getMint8(p))
+ return
+
+ case muint8:
+ p, err = m.R.Next(2)
+ if err != nil {
+ return
+ }
+ i = int64(getMuint8(p))
+ return
+
+ case mint16:
+ p, err = m.R.Next(3)
+ if err != nil {
+ return
+ }
+ i = int64(getMint16(p))
+ return
+
+ case muint16:
+ p, err = m.R.Next(3)
+ if err != nil {
+ return
+ }
+ i = int64(getMuint16(p))
+ return
+
+ case mint32:
+ p, err = m.R.Next(5)
+ if err != nil {
+ return
+ }
+ i = int64(getMint32(p))
+ return
+
+ case muint32:
+ p, err = m.R.Next(5)
+ if err != nil {
+ return
+ }
+ i = int64(getMuint32(p))
+ return
+
+ case mint64:
+ p, err = m.R.Next(9)
+ if err != nil {
+ return
+ }
+ i = getMint64(p)
+ return
+
+ case muint64:
+ p, err = m.R.Next(9)
+ if err != nil {
+ return
+ }
+ u := getMuint64(p)
+ if u > math.MaxInt64 {
+ err = UintOverflow{Value: u, FailedBitsize: 64}
+ return
+ }
+ i = int64(u)
+ return
+
+ default:
+ err = badPrefix(IntType, lead)
+ return
+ }
+}
+
+// ReadInt32 reads an int32 from the reader
+func (m *Reader) ReadInt32() (i int32, err error) {
+ var in int64
+ in, err = m.ReadInt64()
+ if in > math.MaxInt32 || in < math.MinInt32 {
+ err = IntOverflow{Value: in, FailedBitsize: 32}
+ return
+ }
+ i = int32(in)
+ return
+}
+
+// ReadInt16 reads an int16 from the reader
+func (m *Reader) ReadInt16() (i int16, err error) {
+ var in int64
+ in, err = m.ReadInt64()
+ if in > math.MaxInt16 || in < math.MinInt16 {
+ err = IntOverflow{Value: in, FailedBitsize: 16}
+ return
+ }
+ i = int16(in)
+ return
+}
+
+// ReadInt8 reads an int8 from the reader
+func (m *Reader) ReadInt8() (i int8, err error) {
+ var in int64
+ in, err = m.ReadInt64()
+ if in > math.MaxInt8 || in < math.MinInt8 {
+ err = IntOverflow{Value: in, FailedBitsize: 8}
+ return
+ }
+ i = int8(in)
+ return
+}
+
+// ReadInt reads an int from the reader
+func (m *Reader) ReadInt() (i int, err error) {
+ if smallint {
+ var in int32
+ in, err = m.ReadInt32()
+ i = int(in)
+ return
+ }
+ var in int64
+ in, err = m.ReadInt64()
+ i = int(in)
+ return
+}
+
+// ReadUint64 reads a uint64 from the reader
+func (m *Reader) ReadUint64() (u uint64, err error) {
+ var p []byte
+ var lead byte
+ p, err = m.R.Peek(1)
+ if err != nil {
+ return
+ }
+ lead = p[0]
+ if isfixint(lead) {
+ u = uint64(rfixint(lead))
+ _, err = m.R.Skip(1)
+ return
+ }
+ switch lead {
+ case mint8:
+ p, err = m.R.Next(2)
+ if err != nil {
+ return
+ }
+ v := int64(getMint8(p))
+ if v < 0 {
+ err = UintBelowZero{Value: v}
+ return
+ }
+ u = uint64(v)
+ return
+
+ case muint8:
+ p, err = m.R.Next(2)
+ if err != nil {
+ return
+ }
+ u = uint64(getMuint8(p))
+ return
+
+ case mint16:
+ p, err = m.R.Next(3)
+ if err != nil {
+ return
+ }
+ v := int64(getMint16(p))
+ if v < 0 {
+ err = UintBelowZero{Value: v}
+ return
+ }
+ u = uint64(v)
+ return
+
+ case muint16:
+ p, err = m.R.Next(3)
+ if err != nil {
+ return
+ }
+ u = uint64(getMuint16(p))
+ return
+
+ case mint32:
+ p, err = m.R.Next(5)
+ if err != nil {
+ return
+ }
+ v := int64(getMint32(p))
+ if v < 0 {
+ err = UintBelowZero{Value: v}
+ return
+ }
+ u = uint64(v)
+ return
+
+ case muint32:
+ p, err = m.R.Next(5)
+ if err != nil {
+ return
+ }
+ u = uint64(getMuint32(p))
+ return
+
+ case mint64:
+ p, err = m.R.Next(9)
+ if err != nil {
+ return
+ }
+ v := int64(getMint64(p))
+ if v < 0 {
+ err = UintBelowZero{Value: v}
+ return
+ }
+ u = uint64(v)
+ return
+
+ case muint64:
+ p, err = m.R.Next(9)
+ if err != nil {
+ return
+ }
+ u = getMuint64(p)
+ return
+
+ default:
+ if isnfixint(lead) {
+ err = UintBelowZero{Value: int64(rnfixint(lead))}
+ } else {
+ err = badPrefix(UintType, lead)
+ }
+ return
+
+ }
+}
+
+// ReadUint32 reads a uint32 from the reader
+func (m *Reader) ReadUint32() (u uint32, err error) {
+ var in uint64
+ in, err = m.ReadUint64()
+ if in > math.MaxUint32 {
+ err = UintOverflow{Value: in, FailedBitsize: 32}
+ return
+ }
+ u = uint32(in)
+ return
+}
+
+// ReadUint16 reads a uint16 from the reader
+func (m *Reader) ReadUint16() (u uint16, err error) {
+ var in uint64
+ in, err = m.ReadUint64()
+ if in > math.MaxUint16 {
+ err = UintOverflow{Value: in, FailedBitsize: 16}
+ return
+ }
+ u = uint16(in)
+ return
+}
+
+// ReadUint8 reads a uint8 from the reader
+func (m *Reader) ReadUint8() (u uint8, err error) {
+ var in uint64
+ in, err = m.ReadUint64()
+ if in > math.MaxUint8 {
+ err = UintOverflow{Value: in, FailedBitsize: 8}
+ return
+ }
+ u = uint8(in)
+ return
+}
+
+// ReadUint reads a uint from the reader
+func (m *Reader) ReadUint() (u uint, err error) {
+ if smallint {
+ var un uint32
+ un, err = m.ReadUint32()
+ u = uint(un)
+ return
+ }
+ var un uint64
+ un, err = m.ReadUint64()
+ u = uint(un)
+ return
+}
+
+// ReadByte is analogous to ReadUint8.
+//
+// NOTE: this is *not* an implementation
+// of io.ByteReader.
+func (m *Reader) ReadByte() (b byte, err error) {
+ var in uint64
+ in, err = m.ReadUint64()
+ if in > math.MaxUint8 {
+ err = UintOverflow{Value: in, FailedBitsize: 8}
+ return
+ }
+ b = byte(in)
+ return
+}
+
+// ReadBytes reads a MessagePack 'bin' object
+// from the reader and returns its value. It may
+// use 'scratch' for storage if it is non-nil.
+func (m *Reader) ReadBytes(scratch []byte) (b []byte, err error) {
+ var p []byte
+ var lead byte
+ p, err = m.R.Peek(2)
+ if err != nil {
+ return
+ }
+ lead = p[0]
+ var read int64
+ switch lead {
+ case mbin8:
+ read = int64(p[1])
+ m.R.Skip(2)
+ case mbin16:
+ p, err = m.R.Next(3)
+ if err != nil {
+ return
+ }
+ read = int64(big.Uint16(p[1:]))
+ case mbin32:
+ p, err = m.R.Next(5)
+ if err != nil {
+ return
+ }
+ read = int64(big.Uint32(p[1:]))
+ default:
+ err = badPrefix(BinType, lead)
+ return
+ }
+ if int64(cap(scratch)) < read {
+ b = make([]byte, read)
+ } else {
+ b = scratch[0:read]
+ }
+ _, err = m.R.ReadFull(b)
+ return
+}
+
+// ReadBytesHeader reads the size header
+// of a MessagePack 'bin' object. The user
+// is responsible for dealing with the next
+// 'sz' bytes from the reader in an application-specific
+// way.
+func (m *Reader) ReadBytesHeader() (sz uint32, err error) {
+ var p []byte
+ p, err = m.R.Peek(1)
+ if err != nil {
+ return
+ }
+ switch p[0] {
+ case mbin8:
+ p, err = m.R.Next(2)
+ if err != nil {
+ return
+ }
+ sz = uint32(p[1])
+ return
+ case mbin16:
+ p, err = m.R.Next(3)
+ if err != nil {
+ return
+ }
+ sz = uint32(big.Uint16(p[1:]))
+ return
+ case mbin32:
+ p, err = m.R.Next(5)
+ if err != nil {
+ return
+ }
+ sz = uint32(big.Uint32(p[1:]))
+ return
+ default:
+ err = badPrefix(BinType, p[0])
+ return
+ }
+}
+
+// ReadExactBytes reads a MessagePack 'bin'-encoded
+// object off of the wire into the provided slice. An
+// ArrayError will be returned if the object is not
+// exactly the length of the input slice.
+func (m *Reader) ReadExactBytes(into []byte) error {
+ p, err := m.R.Peek(2)
+ if err != nil {
+ return err
+ }
+ lead := p[0]
+ var read int64 // bytes to read
+ var skip int // prefix size to skip
+ switch lead {
+ case mbin8:
+ read = int64(p[1])
+ skip = 2
+ case mbin16:
+ p, err = m.R.Peek(3)
+ if err != nil {
+ return err
+ }
+ read = int64(big.Uint16(p[1:]))
+ skip = 3
+ case mbin32:
+ p, err = m.R.Peek(5)
+ if err != nil {
+ return err
+ }
+ read = int64(big.Uint32(p[1:]))
+ skip = 5
+ default:
+ return badPrefix(BinType, lead)
+ }
+ if read != int64(len(into)) {
+ return ArrayError{Wanted: uint32(len(into)), Got: uint32(read)}
+ }
+ m.R.Skip(skip)
+ _, err = m.R.ReadFull(into)
+ return err
+}
+
+// ReadStringAsBytes reads a MessagePack 'str' (utf-8) string
+// and returns its value as bytes. It may use 'scratch' for storage
+// if it is non-nil.
+func (m *Reader) ReadStringAsBytes(scratch []byte) (b []byte, err error) {
+ var p []byte
+ var lead byte
+ p, err = m.R.Peek(1)
+ if err != nil {
+ return
+ }
+ lead = p[0]
+ var read int64
+
+ if isfixstr(lead) {
+ read = int64(rfixstr(lead))
+ m.R.Skip(1)
+ goto fill
+ }
+
+ switch lead {
+ case mstr8:
+ p, err = m.R.Next(2)
+ if err != nil {
+ return
+ }
+ read = int64(uint8(p[1]))
+ case mstr16:
+ p, err = m.R.Next(3)
+ if err != nil {
+ return
+ }
+ read = int64(big.Uint16(p[1:]))
+ case mstr32:
+ p, err = m.R.Next(5)
+ if err != nil {
+ return
+ }
+ read = int64(big.Uint32(p[1:]))
+ default:
+ err = badPrefix(StrType, lead)
+ return
+ }
+fill:
+ if int64(cap(scratch)) < read {
+ b = make([]byte, read)
+ } else {
+ b = scratch[0:read]
+ }
+ _, err = m.R.ReadFull(b)
+ return
+}
+
+// ReadStringHeader reads a string header
+// off of the wire. The user is then responsible
+// for dealing with the next 'sz' bytes from
+// the reader in an application-specific manner.
+func (m *Reader) ReadStringHeader() (sz uint32, err error) {
+ var p []byte
+ p, err = m.R.Peek(1)
+ if err != nil {
+ return
+ }
+ lead := p[0]
+ if isfixstr(lead) {
+ sz = uint32(rfixstr(lead))
+ m.R.Skip(1)
+ return
+ }
+ switch lead {
+ case mstr8:
+ p, err = m.R.Next(2)
+ if err != nil {
+ return
+ }
+ sz = uint32(p[1])
+ return
+ case mstr16:
+ p, err = m.R.Next(3)
+ if err != nil {
+ return
+ }
+ sz = uint32(big.Uint16(p[1:]))
+ return
+ case mstr32:
+ p, err = m.R.Next(5)
+ if err != nil {
+ return
+ }
+ sz = big.Uint32(p[1:])
+ return
+ default:
+ err = badPrefix(StrType, lead)
+ return
+ }
+}
+
+// ReadString reads a utf-8 string from the reader
+func (m *Reader) ReadString() (s string, err error) {
+ var p []byte
+ var lead byte
+ var read int64
+ p, err = m.R.Peek(1)
+ if err != nil {
+ return
+ }
+ lead = p[0]
+
+ if isfixstr(lead) {
+ read = int64(rfixstr(lead))
+ m.R.Skip(1)
+ goto fill
+ }
+
+ switch lead {
+ case mstr8:
+ p, err = m.R.Next(2)
+ if err != nil {
+ return
+ }
+ read = int64(uint8(p[1]))
+ case mstr16:
+ p, err = m.R.Next(3)
+ if err != nil {
+ return
+ }
+ read = int64(big.Uint16(p[1:]))
+ case mstr32:
+ p, err = m.R.Next(5)
+ if err != nil {
+ return
+ }
+ read = int64(big.Uint32(p[1:]))
+ default:
+ err = badPrefix(StrType, lead)
+ return
+ }
+fill:
+ if read == 0 {
+ s, err = "", nil
+ return
+ }
+ // reading into the memory
+ // that will become the string
+ // itself has vastly superior
+ // worst-case performance, because
+ // the reader buffer doesn't have
+ // to be large enough to hold the string.
+ // the idea here is to make it more
+ // difficult for someone malicious
+ // to cause the system to run out of
+ // memory by sending very large strings.
+ //
+ // NOTE: this works because the argument
+ // passed to (*fwd.Reader).ReadFull escapes
+ // to the heap; its argument may, in turn,
+ // be passed to the underlying reader, and
+ // thus escape analysis *must* conclude that
+ // 'out' escapes.
+ out := make([]byte, read)
+ _, err = m.R.ReadFull(out)
+ if err != nil {
+ return
+ }
+ s = UnsafeString(out)
+ return
+}
+
+// ReadComplex64 reads a complex64 from the reader
+func (m *Reader) ReadComplex64() (f complex64, err error) {
+ var p []byte
+ p, err = m.R.Peek(10)
+ if err != nil {
+ return
+ }
+ if p[0] != mfixext8 {
+ err = badPrefix(Complex64Type, p[0])
+ return
+ }
+ if int8(p[1]) != Complex64Extension {
+ err = errExt(int8(p[1]), Complex64Extension)
+ return
+ }
+ f = complex(math.Float32frombits(big.Uint32(p[2:])),
+ math.Float32frombits(big.Uint32(p[6:])))
+ _, err = m.R.Skip(10)
+ return
+}
+
+// ReadComplex128 reads a complex128 from the reader
+func (m *Reader) ReadComplex128() (f complex128, err error) {
+ var p []byte
+ p, err = m.R.Peek(18)
+ if err != nil {
+ return
+ }
+ if p[0] != mfixext16 {
+ err = badPrefix(Complex128Type, p[0])
+ return
+ }
+ if int8(p[1]) != Complex128Extension {
+ err = errExt(int8(p[1]), Complex128Extension)
+ return
+ }
+ f = complex(math.Float64frombits(big.Uint64(p[2:])),
+ math.Float64frombits(big.Uint64(p[10:])))
+ _, err = m.R.Skip(18)
+ return
+}
+
+// ReadMapStrIntf reads a MessagePack map into a map[string]interface{}.
+// (You must pass a non-nil map into the function.)
+func (m *Reader) ReadMapStrIntf(mp map[string]interface{}) (err error) {
+ var sz uint32
+ sz, err = m.ReadMapHeader()
+ if err != nil {
+ return
+ }
+ for key := range mp {
+ delete(mp, key)
+ }
+ for i := uint32(0); i < sz; i++ {
+ var key string
+ var val interface{}
+ key, err = m.ReadString()
+ if err != nil {
+ return
+ }
+ val, err = m.ReadIntf()
+ if err != nil {
+ return
+ }
+ mp[key] = val
+ }
+ return
+}
+
+// ReadTime reads a time.Time object from the reader.
+// The returned time's location will be set to time.Local.
+func (m *Reader) ReadTime() (t time.Time, err error) {
+ var p []byte
+ p, err = m.R.Peek(15)
+ if err != nil {
+ return
+ }
+ if p[0] != mext8 || p[1] != 12 {
+ err = badPrefix(TimeType, p[0])
+ return
+ }
+ if int8(p[2]) != TimeExtension {
+ err = errExt(int8(p[2]), TimeExtension)
+ return
+ }
+ sec, nsec := getUnix(p[3:])
+ t = time.Unix(sec, int64(nsec)).Local()
+ _, err = m.R.Skip(15)
+ return
+}
+
+// ReadIntf reads out the next object as a raw interface{}.
+// Arrays are decoded as []interface{}, and maps are decoded
+// as map[string]interface{}. Integers are decoded as int64
+// and unsigned integers are decoded as uint64.
+func (m *Reader) ReadIntf() (i interface{}, err error) {
+ var t Type
+ t, err = m.NextType()
+ if err != nil {
+ return
+ }
+ switch t {
+ case BoolType:
+ i, err = m.ReadBool()
+ return
+
+ case IntType:
+ i, err = m.ReadInt64()
+ return
+
+ case UintType:
+ i, err = m.ReadUint64()
+ return
+
+ case BinType:
+ i, err = m.ReadBytes(nil)
+ return
+
+ case StrType:
+ i, err = m.ReadString()
+ return
+
+ case Complex64Type:
+ i, err = m.ReadComplex64()
+ return
+
+ case Complex128Type:
+ i, err = m.ReadComplex128()
+ return
+
+ case TimeType:
+ i, err = m.ReadTime()
+ return
+
+ case ExtensionType:
+ var t int8
+ t, err = m.peekExtensionType()
+ if err != nil {
+ return
+ }
+ f, ok := extensionReg[t]
+ if ok {
+ e := f()
+ err = m.ReadExtension(e)
+ i = e
+ return
+ }
+ var e RawExtension
+ e.Type = t
+ err = m.ReadExtension(&e)
+ i = &e
+ return
+
+ case MapType:
+ mp := make(map[string]interface{})
+ err = m.ReadMapStrIntf(mp)
+ i = mp
+ return
+
+ case NilType:
+ err = m.ReadNil()
+ i = nil
+ return
+
+ case Float32Type:
+ i, err = m.ReadFloat32()
+ return
+
+ case Float64Type:
+ i, err = m.ReadFloat64()
+ return
+
+ case ArrayType:
+ var sz uint32
+ sz, err = m.ReadArrayHeader()
+
+ if err != nil {
+ return
+ }
+ out := make([]interface{}, int(sz))
+ for j := range out {
+ out[j], err = m.ReadIntf()
+ if err != nil {
+ return
+ }
+ }
+ i = out
+ return
+
+ default:
+ return nil, fatal // unreachable
+ }
+}
diff --git a/vendor/github.com/tinylib/msgp/msgp/read_bytes.go b/vendor/github.com/tinylib/msgp/msgp/read_bytes.go
new file mode 100644
index 000000000..f53f84d01
--- /dev/null
+++ b/vendor/github.com/tinylib/msgp/msgp/read_bytes.go
@@ -0,0 +1,1197 @@
+package msgp
+
+import (
+ "bytes"
+ "encoding/binary"
+ "math"
+ "time"
+)
+
+var big = binary.BigEndian
+
+// NextType returns the type of the next
+// object in the slice. If the length
+// of the input is zero, it returns
+// InvalidType.
+func NextType(b []byte) Type {
+ if len(b) == 0 {
+ return InvalidType
+ }
+ spec := sizes[b[0]]
+ t := spec.typ
+ if t == ExtensionType && len(b) > int(spec.size) {
+ var tp int8
+ if spec.extra == constsize {
+ tp = int8(b[1])
+ } else {
+ tp = int8(b[spec.size-1])
+ }
+ switch tp {
+ case TimeExtension:
+ return TimeType
+ case Complex128Extension:
+ return Complex128Type
+ case Complex64Extension:
+ return Complex64Type
+ default:
+ return ExtensionType
+ }
+ }
+ return t
+}
+
+// IsNil returns true if len(b)>0 and
+// the leading byte is a 'nil' MessagePack
+// byte; false otherwise
+func IsNil(b []byte) bool {
+ if len(b) != 0 && b[0] == mnil {
+ return true
+ }
+ return false
+}
+
+// Raw is raw MessagePack.
+// Raw allows you to read and write
+// data without interpreting its contents.
+type Raw []byte
+
+// MarshalMsg implements msgp.Marshaler.
+// It appends the raw contents of 'raw'
+// to the provided byte slice. If 'raw'
+// is 0 bytes, 'nil' will be appended instead.
+func (r Raw) MarshalMsg(b []byte) ([]byte, error) {
+ i := len(r)
+ if i == 0 {
+ return AppendNil(b), nil
+ }
+ o, l := ensure(b, i)
+ copy(o[l:], []byte(r))
+ return o, nil
+}
+
+// UnmarshalMsg implements msgp.Unmarshaler.
+// It sets the contents of *Raw to be the next
+// object in the provided byte slice.
+func (r *Raw) UnmarshalMsg(b []byte) ([]byte, error) {
+ l := len(b)
+ out, err := Skip(b)
+ if err != nil {
+ return b, err
+ }
+ rlen := l - len(out)
+ if IsNil(b[:rlen]) {
+ rlen = 0
+ }
+ if cap(*r) < rlen {
+ *r = make(Raw, rlen)
+ } else {
+ *r = (*r)[0:rlen]
+ }
+ copy(*r, b[:rlen])
+ return out, nil
+}
+
+// EncodeMsg implements msgp.Encodable.
+// It writes the raw bytes to the writer.
+// If r is empty, it writes 'nil' instead.
+func (r Raw) EncodeMsg(w *Writer) error {
+ if len(r) == 0 {
+ return w.WriteNil()
+ }
+ _, err := w.Write([]byte(r))
+ return err
+}
+
+// DecodeMsg implements msgp.Decodable.
+// It sets the value of *Raw to be the
+// next object on the wire.
+func (r *Raw) DecodeMsg(f *Reader) error {
+ *r = (*r)[:0]
+ err := appendNext(f, (*[]byte)(r))
+ if IsNil(*r) {
+ *r = (*r)[:0]
+ }
+ return err
+}
+
+// Msgsize implements msgp.Sizer
+func (r Raw) Msgsize() int {
+ l := len(r)
+ if l == 0 {
+ return 1 // for 'nil'
+ }
+ return l
+}
+
+func appendNext(f *Reader, d *[]byte) error {
+ amt, o, err := getNextSize(f.R)
+ if err != nil {
+ return err
+ }
+ var i int
+ *d, i = ensure(*d, int(amt))
+ _, err = f.R.ReadFull((*d)[i:])
+ if err != nil {
+ return err
+ }
+ for o > 0 {
+ err = appendNext(f, d)
+ if err != nil {
+ return err
+ }
+ o--
+ }
+ return nil
+}
+
+// MarshalJSON implements json.Marshaler
+func (r *Raw) MarshalJSON() ([]byte, error) {
+ var buf bytes.Buffer
+ _, err := UnmarshalAsJSON(&buf, []byte(*r))
+ return buf.Bytes(), err
+}
+
+// ReadMapHeaderBytes reads a map header size
+// from 'b' and returns the remaining bytes.
+// Possible errors:
+// - ErrShortBytes (too few bytes)
+// - TypeError{} (not a map)
+func ReadMapHeaderBytes(b []byte) (sz uint32, o []byte, err error) {
+ l := len(b)
+ if l < 1 {
+ err = ErrShortBytes
+ return
+ }
+
+ lead := b[0]
+ if isfixmap(lead) {
+ sz = uint32(rfixmap(lead))
+ o = b[1:]
+ return
+ }
+
+ switch lead {
+ case mmap16:
+ if l < 3 {
+ err = ErrShortBytes
+ return
+ }
+ sz = uint32(big.Uint16(b[1:]))
+ o = b[3:]
+ return
+
+ case mmap32:
+ if l < 5 {
+ err = ErrShortBytes
+ return
+ }
+ sz = big.Uint32(b[1:])
+ o = b[5:]
+ return
+
+ default:
+ err = badPrefix(MapType, lead)
+ return
+ }
+}
+
+// ReadMapKeyZC attempts to read a map key
+// from 'b' and returns the key bytes and the remaining bytes
+// Possible errors:
+// - ErrShortBytes (too few bytes)
+// - TypeError{} (not a str or bin)
+func ReadMapKeyZC(b []byte) ([]byte, []byte, error) {
+ o, b, err := ReadStringZC(b)
+ if err != nil {
+ if tperr, ok := err.(TypeError); ok && tperr.Encoded == BinType {
+ return ReadBytesZC(b)
+ }
+ return nil, b, err
+ }
+ return o, b, nil
+}
+
+// ReadArrayHeaderBytes attempts to read
+// the array header size off of 'b' and return
+// the size and remaining bytes.
+// Possible errors:
+// - ErrShortBytes (too few bytes)
+// - TypeError{} (not an array)
+func ReadArrayHeaderBytes(b []byte) (sz uint32, o []byte, err error) {
+ if len(b) < 1 {
+ return 0, nil, ErrShortBytes
+ }
+ lead := b[0]
+ if isfixarray(lead) {
+ sz = uint32(rfixarray(lead))
+ o = b[1:]
+ return
+ }
+
+ switch lead {
+ case marray16:
+ if len(b) < 3 {
+ err = ErrShortBytes
+ return
+ }
+ sz = uint32(big.Uint16(b[1:]))
+ o = b[3:]
+ return
+
+ case marray32:
+ if len(b) < 5 {
+ err = ErrShortBytes
+ return
+ }
+ sz = big.Uint32(b[1:])
+ o = b[5:]
+ return
+
+ default:
+ err = badPrefix(ArrayType, lead)
+ return
+ }
+}
+
+// ReadNilBytes tries to read a "nil" byte
+// off of 'b' and return the remaining bytes.
+// Possible errors:
+// - ErrShortBytes (too few bytes)
+// - TypeError{} (not a 'nil')
+// - InvalidPrefixError
+func ReadNilBytes(b []byte) ([]byte, error) {
+ if len(b) < 1 {
+ return nil, ErrShortBytes
+ }
+ if b[0] != mnil {
+ return b, badPrefix(NilType, b[0])
+ }
+ return b[1:], nil
+}
+
+// ReadFloat64Bytes tries to read a float64
+// from 'b' and return the value and the remaining bytes.
+// Possible errors:
+// - ErrShortBytes (too few bytes)
+// - TypeError{} (not a float64)
+func ReadFloat64Bytes(b []byte) (f float64, o []byte, err error) {
+ if len(b) < 9 {
+ if len(b) >= 5 && b[0] == mfloat32 {
+ var tf float32
+ tf, o, err = ReadFloat32Bytes(b)
+ f = float64(tf)
+ return
+ }
+ err = ErrShortBytes
+ return
+ }
+
+ if b[0] != mfloat64 {
+ if b[0] == mfloat32 {
+ var tf float32
+ tf, o, err = ReadFloat32Bytes(b)
+ f = float64(tf)
+ return
+ }
+ err = badPrefix(Float64Type, b[0])
+ return
+ }
+
+ f = math.Float64frombits(getMuint64(b))
+ o = b[9:]
+ return
+}
+
+// ReadFloat32Bytes tries to read a float64
+// from 'b' and return the value and the remaining bytes.
+// Possible errors:
+// - ErrShortBytes (too few bytes)
+// - TypeError{} (not a float32)
+func ReadFloat32Bytes(b []byte) (f float32, o []byte, err error) {
+ if len(b) < 5 {
+ err = ErrShortBytes
+ return
+ }
+
+ if b[0] != mfloat32 {
+ err = TypeError{Method: Float32Type, Encoded: getType(b[0])}
+ return
+ }
+
+ f = math.Float32frombits(getMuint32(b))
+ o = b[5:]
+ return
+}
+
+// ReadBoolBytes tries to read a float64
+// from 'b' and return the value and the remaining bytes.
+// Possible errors:
+// - ErrShortBytes (too few bytes)
+// - TypeError{} (not a bool)
+func ReadBoolBytes(b []byte) (bool, []byte, error) {
+ if len(b) < 1 {
+ return false, b, ErrShortBytes
+ }
+ switch b[0] {
+ case mtrue:
+ return true, b[1:], nil
+ case mfalse:
+ return false, b[1:], nil
+ default:
+ return false, b, badPrefix(BoolType, b[0])
+ }
+}
+
+// ReadInt64Bytes tries to read an int64
+// from 'b' and return the value and the remaining bytes.
+// Possible errors:
+// - ErrShortBytes (too few bytes)
+// - TypeError (not a int)
+func ReadInt64Bytes(b []byte) (i int64, o []byte, err error) {
+ l := len(b)
+ if l < 1 {
+ return 0, nil, ErrShortBytes
+ }
+
+ lead := b[0]
+ if isfixint(lead) {
+ i = int64(rfixint(lead))
+ o = b[1:]
+ return
+ }
+ if isnfixint(lead) {
+ i = int64(rnfixint(lead))
+ o = b[1:]
+ return
+ }
+
+ switch lead {
+ case mint8:
+ if l < 2 {
+ err = ErrShortBytes
+ return
+ }
+ i = int64(getMint8(b))
+ o = b[2:]
+ return
+
+ case muint8:
+ if l < 2 {
+ err = ErrShortBytes
+ return
+ }
+ i = int64(getMuint8(b))
+ o = b[2:]
+ return
+
+ case mint16:
+ if l < 3 {
+ err = ErrShortBytes
+ return
+ }
+ i = int64(getMint16(b))
+ o = b[3:]
+ return
+
+ case muint16:
+ if l < 3 {
+ err = ErrShortBytes
+ return
+ }
+ i = int64(getMuint16(b))
+ o = b[3:]
+ return
+
+ case mint32:
+ if l < 5 {
+ err = ErrShortBytes
+ return
+ }
+ i = int64(getMint32(b))
+ o = b[5:]
+ return
+
+ case muint32:
+ if l < 5 {
+ err = ErrShortBytes
+ return
+ }
+ i = int64(getMuint32(b))
+ o = b[5:]
+ return
+
+ case mint64:
+ if l < 9 {
+ err = ErrShortBytes
+ return
+ }
+ i = int64(getMint64(b))
+ o = b[9:]
+ return
+
+ case muint64:
+ if l < 9 {
+ err = ErrShortBytes
+ return
+ }
+ u := getMuint64(b)
+ if u > math.MaxInt64 {
+ err = UintOverflow{Value: u, FailedBitsize: 64}
+ return
+ }
+ i = int64(u)
+ o = b[9:]
+ return
+
+ default:
+ err = badPrefix(IntType, lead)
+ return
+ }
+}
+
+// ReadInt32Bytes tries to read an int32
+// from 'b' and return the value and the remaining bytes.
+// Possible errors:
+// - ErrShortBytes (too few bytes)
+// - TypeError{} (not a int)
+// - IntOverflow{} (value doesn't fit in int32)
+func ReadInt32Bytes(b []byte) (int32, []byte, error) {
+ i, o, err := ReadInt64Bytes(b)
+ if i > math.MaxInt32 || i < math.MinInt32 {
+ return 0, o, IntOverflow{Value: i, FailedBitsize: 32}
+ }
+ return int32(i), o, err
+}
+
+// ReadInt16Bytes tries to read an int16
+// from 'b' and return the value and the remaining bytes.
+// Possible errors:
+// - ErrShortBytes (too few bytes)
+// - TypeError{} (not a int)
+// - IntOverflow{} (value doesn't fit in int16)
+func ReadInt16Bytes(b []byte) (int16, []byte, error) {
+ i, o, err := ReadInt64Bytes(b)
+ if i > math.MaxInt16 || i < math.MinInt16 {
+ return 0, o, IntOverflow{Value: i, FailedBitsize: 16}
+ }
+ return int16(i), o, err
+}
+
+// ReadInt8Bytes tries to read an int16
+// from 'b' and return the value and the remaining bytes.
+// Possible errors:
+// - ErrShortBytes (too few bytes)
+// - TypeError{} (not a int)
+// - IntOverflow{} (value doesn't fit in int8)
+func ReadInt8Bytes(b []byte) (int8, []byte, error) {
+ i, o, err := ReadInt64Bytes(b)
+ if i > math.MaxInt8 || i < math.MinInt8 {
+ return 0, o, IntOverflow{Value: i, FailedBitsize: 8}
+ }
+ return int8(i), o, err
+}
+
+// ReadIntBytes tries to read an int
+// from 'b' and return the value and the remaining bytes.
+// Possible errors:
+// - ErrShortBytes (too few bytes)
+// - TypeError{} (not a int)
+// - IntOverflow{} (value doesn't fit in int; 32-bit platforms only)
+func ReadIntBytes(b []byte) (int, []byte, error) {
+ if smallint {
+ i, b, err := ReadInt32Bytes(b)
+ return int(i), b, err
+ }
+ i, b, err := ReadInt64Bytes(b)
+ return int(i), b, err
+}
+
+// ReadUint64Bytes tries to read a uint64
+// from 'b' and return the value and the remaining bytes.
+// Possible errors:
+// - ErrShortBytes (too few bytes)
+// - TypeError{} (not a uint)
+func ReadUint64Bytes(b []byte) (u uint64, o []byte, err error) {
+ l := len(b)
+ if l < 1 {
+ return 0, nil, ErrShortBytes
+ }
+
+ lead := b[0]
+ if isfixint(lead) {
+ u = uint64(rfixint(lead))
+ o = b[1:]
+ return
+ }
+
+ switch lead {
+ case mint8:
+ if l < 2 {
+ err = ErrShortBytes
+ return
+ }
+ v := int64(getMint8(b))
+ if v < 0 {
+ err = UintBelowZero{Value: v}
+ return
+ }
+ u = uint64(v)
+ o = b[2:]
+ return
+
+ case muint8:
+ if l < 2 {
+ err = ErrShortBytes
+ return
+ }
+ u = uint64(getMuint8(b))
+ o = b[2:]
+ return
+
+ case mint16:
+ if l < 3 {
+ err = ErrShortBytes
+ return
+ }
+ v := int64(getMint16(b))
+ if v < 0 {
+ err = UintBelowZero{Value: v}
+ return
+ }
+ u = uint64(v)
+ o = b[3:]
+ return
+
+ case muint16:
+ if l < 3 {
+ err = ErrShortBytes
+ return
+ }
+ u = uint64(getMuint16(b))
+ o = b[3:]
+ return
+
+ case mint32:
+ if l < 5 {
+ err = ErrShortBytes
+ return
+ }
+ v := int64(getMint32(b))
+ if v < 0 {
+ err = UintBelowZero{Value: v}
+ return
+ }
+ u = uint64(v)
+ o = b[5:]
+ return
+
+ case muint32:
+ if l < 5 {
+ err = ErrShortBytes
+ return
+ }
+ u = uint64(getMuint32(b))
+ o = b[5:]
+ return
+
+ case mint64:
+ if l < 9 {
+ err = ErrShortBytes
+ return
+ }
+ v := int64(getMint64(b))
+ if v < 0 {
+ err = UintBelowZero{Value: v}
+ return
+ }
+ u = uint64(v)
+ o = b[9:]
+ return
+
+ case muint64:
+ if l < 9 {
+ err = ErrShortBytes
+ return
+ }
+ u = getMuint64(b)
+ o = b[9:]
+ return
+
+ default:
+ if isnfixint(lead) {
+ err = UintBelowZero{Value: int64(rnfixint(lead))}
+ } else {
+ err = badPrefix(UintType, lead)
+ }
+ return
+ }
+}
+
+// ReadUint32Bytes tries to read a uint32
+// from 'b' and return the value and the remaining bytes.
+// Possible errors:
+// - ErrShortBytes (too few bytes)
+// - TypeError{} (not a uint)
+// - UintOverflow{} (value too large for uint32)
+func ReadUint32Bytes(b []byte) (uint32, []byte, error) {
+ v, o, err := ReadUint64Bytes(b)
+ if v > math.MaxUint32 {
+ return 0, nil, UintOverflow{Value: v, FailedBitsize: 32}
+ }
+ return uint32(v), o, err
+}
+
+// ReadUint16Bytes tries to read a uint16
+// from 'b' and return the value and the remaining bytes.
+// Possible errors:
+// - ErrShortBytes (too few bytes)
+// - TypeError{} (not a uint)
+// - UintOverflow{} (value too large for uint16)
+func ReadUint16Bytes(b []byte) (uint16, []byte, error) {
+ v, o, err := ReadUint64Bytes(b)
+ if v > math.MaxUint16 {
+ return 0, nil, UintOverflow{Value: v, FailedBitsize: 16}
+ }
+ return uint16(v), o, err
+}
+
+// ReadUint8Bytes tries to read a uint8
+// from 'b' and return the value and the remaining bytes.
+// Possible errors:
+// - ErrShortBytes (too few bytes)
+// - TypeError{} (not a uint)
+// - UintOverflow{} (value too large for uint8)
+func ReadUint8Bytes(b []byte) (uint8, []byte, error) {
+ v, o, err := ReadUint64Bytes(b)
+ if v > math.MaxUint8 {
+ return 0, nil, UintOverflow{Value: v, FailedBitsize: 8}
+ }
+ return uint8(v), o, err
+}
+
+// ReadUintBytes tries to read a uint
+// from 'b' and return the value and the remaining bytes.
+// Possible errors:
+// - ErrShortBytes (too few bytes)
+// - TypeError{} (not a uint)
+// - UintOverflow{} (value too large for uint; 32-bit platforms only)
+func ReadUintBytes(b []byte) (uint, []byte, error) {
+ if smallint {
+ u, b, err := ReadUint32Bytes(b)
+ return uint(u), b, err
+ }
+ u, b, err := ReadUint64Bytes(b)
+ return uint(u), b, err
+}
+
+// ReadByteBytes is analogous to ReadUint8Bytes
+func ReadByteBytes(b []byte) (byte, []byte, error) {
+ return ReadUint8Bytes(b)
+}
+
+// ReadBytesBytes reads a 'bin' object
+// from 'b' and returns its vaue and
+// the remaining bytes in 'b'.
+// Possible errors:
+// - ErrShortBytes (too few bytes)
+// - TypeError{} (not a 'bin' object)
+func ReadBytesBytes(b []byte, scratch []byte) (v []byte, o []byte, err error) {
+ return readBytesBytes(b, scratch, false)
+}
+
+func readBytesBytes(b []byte, scratch []byte, zc bool) (v []byte, o []byte, err error) {
+ l := len(b)
+ if l < 1 {
+ return nil, nil, ErrShortBytes
+ }
+
+ lead := b[0]
+ var read int
+ switch lead {
+ case mbin8:
+ if l < 2 {
+ err = ErrShortBytes
+ return
+ }
+
+ read = int(b[1])
+ b = b[2:]
+
+ case mbin16:
+ if l < 3 {
+ err = ErrShortBytes
+ return
+ }
+ read = int(big.Uint16(b[1:]))
+ b = b[3:]
+
+ case mbin32:
+ if l < 5 {
+ err = ErrShortBytes
+ return
+ }
+ read = int(big.Uint32(b[1:]))
+ b = b[5:]
+
+ default:
+ err = badPrefix(BinType, lead)
+ return
+ }
+
+ if len(b) < read {
+ err = ErrShortBytes
+ return
+ }
+
+ // zero-copy
+ if zc {
+ v = b[0:read]
+ o = b[read:]
+ return
+ }
+
+ if cap(scratch) >= read {
+ v = scratch[0:read]
+ } else {
+ v = make([]byte, read)
+ }
+
+ o = b[copy(v, b):]
+ return
+}
+
+// ReadBytesZC extracts the messagepack-encoded
+// binary field without copying. The returned []byte
+// points to the same memory as the input slice.
+// Possible errors:
+// - ErrShortBytes (b not long enough)
+// - TypeError{} (object not 'bin')
+func ReadBytesZC(b []byte) (v []byte, o []byte, err error) {
+ return readBytesBytes(b, nil, true)
+}
+
+func ReadExactBytes(b []byte, into []byte) (o []byte, err error) {
+ l := len(b)
+ if l < 1 {
+ err = ErrShortBytes
+ return
+ }
+
+ lead := b[0]
+ var read uint32
+ var skip int
+ switch lead {
+ case mbin8:
+ if l < 2 {
+ err = ErrShortBytes
+ return
+ }
+
+ read = uint32(b[1])
+ skip = 2
+
+ case mbin16:
+ if l < 3 {
+ err = ErrShortBytes
+ return
+ }
+ read = uint32(big.Uint16(b[1:]))
+ skip = 3
+
+ case mbin32:
+ if l < 5 {
+ err = ErrShortBytes
+ return
+ }
+ read = uint32(big.Uint32(b[1:]))
+ skip = 5
+
+ default:
+ err = badPrefix(BinType, lead)
+ return
+ }
+
+ if read != uint32(len(into)) {
+ err = ArrayError{Wanted: uint32(len(into)), Got: read}
+ return
+ }
+
+ o = b[skip+copy(into, b[skip:]):]
+ return
+}
+
+// ReadStringZC reads a messagepack string field
+// without copying. The returned []byte points
+// to the same memory as the input slice.
+// Possible errors:
+// - ErrShortBytes (b not long enough)
+// - TypeError{} (object not 'str')
+func ReadStringZC(b []byte) (v []byte, o []byte, err error) {
+ l := len(b)
+ if l < 1 {
+ return nil, nil, ErrShortBytes
+ }
+
+ lead := b[0]
+ var read int
+
+ if isfixstr(lead) {
+ read = int(rfixstr(lead))
+ b = b[1:]
+ } else {
+ switch lead {
+ case mstr8:
+ if l < 2 {
+ err = ErrShortBytes
+ return
+ }
+ read = int(b[1])
+ b = b[2:]
+
+ case mstr16:
+ if l < 3 {
+ err = ErrShortBytes
+ return
+ }
+ read = int(big.Uint16(b[1:]))
+ b = b[3:]
+
+ case mstr32:
+ if l < 5 {
+ err = ErrShortBytes
+ return
+ }
+ read = int(big.Uint32(b[1:]))
+ b = b[5:]
+
+ default:
+ err = TypeError{Method: StrType, Encoded: getType(lead)}
+ return
+ }
+ }
+
+ if len(b) < read {
+ err = ErrShortBytes
+ return
+ }
+
+ v = b[0:read]
+ o = b[read:]
+ return
+}
+
+// ReadStringBytes reads a 'str' object
+// from 'b' and returns its value and the
+// remaining bytes in 'b'.
+// Possible errors:
+// - ErrShortBytes (b not long enough)
+// - TypeError{} (not 'str' type)
+// - InvalidPrefixError
+func ReadStringBytes(b []byte) (string, []byte, error) {
+ v, o, err := ReadStringZC(b)
+ return string(v), o, err
+}
+
+// ReadStringAsBytes reads a 'str' object
+// into a slice of bytes. 'v' is the value of
+// the 'str' object, which may reside in memory
+// pointed to by 'scratch.' 'o' is the remaining bytes
+// in 'b.''
+// Possible errors:
+// - ErrShortBytes (b not long enough)
+// - TypeError{} (not 'str' type)
+// - InvalidPrefixError (unknown type marker)
+func ReadStringAsBytes(b []byte, scratch []byte) (v []byte, o []byte, err error) {
+ var tmp []byte
+ tmp, o, err = ReadStringZC(b)
+ v = append(scratch[:0], tmp...)
+ return
+}
+
+// ReadComplex128Bytes reads a complex128
+// extension object from 'b' and returns the
+// remaining bytes.
+// Possible errors:
+// - ErrShortBytes (not enough bytes in 'b')
+// - TypeError{} (object not a complex128)
+// - InvalidPrefixError
+// - ExtensionTypeError{} (object an extension of the correct size, but not a complex128)
+func ReadComplex128Bytes(b []byte) (c complex128, o []byte, err error) {
+ if len(b) < 18 {
+ err = ErrShortBytes
+ return
+ }
+ if b[0] != mfixext16 {
+ err = badPrefix(Complex128Type, b[0])
+ return
+ }
+ if int8(b[1]) != Complex128Extension {
+ err = errExt(int8(b[1]), Complex128Extension)
+ return
+ }
+ c = complex(math.Float64frombits(big.Uint64(b[2:])),
+ math.Float64frombits(big.Uint64(b[10:])))
+ o = b[18:]
+ return
+}
+
+// ReadComplex64Bytes reads a complex64
+// extension object from 'b' and returns the
+// remaining bytes.
+// Possible errors:
+// - ErrShortBytes (not enough bytes in 'b')
+// - TypeError{} (object not a complex64)
+// - ExtensionTypeError{} (object an extension of the correct size, but not a complex64)
+func ReadComplex64Bytes(b []byte) (c complex64, o []byte, err error) {
+ if len(b) < 10 {
+ err = ErrShortBytes
+ return
+ }
+ if b[0] != mfixext8 {
+ err = badPrefix(Complex64Type, b[0])
+ return
+ }
+ if b[1] != Complex64Extension {
+ err = errExt(int8(b[1]), Complex64Extension)
+ return
+ }
+ c = complex(math.Float32frombits(big.Uint32(b[2:])),
+ math.Float32frombits(big.Uint32(b[6:])))
+ o = b[10:]
+ return
+}
+
+// ReadTimeBytes reads a time.Time
+// extension object from 'b' and returns the
+// remaining bytes.
+// Possible errors:
+// - ErrShortBytes (not enough bytes in 'b')
+// - TypeError{} (object not a complex64)
+// - ExtensionTypeError{} (object an extension of the correct size, but not a time.Time)
+func ReadTimeBytes(b []byte) (t time.Time, o []byte, err error) {
+ if len(b) < 15 {
+ err = ErrShortBytes
+ return
+ }
+ if b[0] != mext8 || b[1] != 12 {
+ err = badPrefix(TimeType, b[0])
+ return
+ }
+ if int8(b[2]) != TimeExtension {
+ err = errExt(int8(b[2]), TimeExtension)
+ return
+ }
+ sec, nsec := getUnix(b[3:])
+ t = time.Unix(sec, int64(nsec)).Local()
+ o = b[15:]
+ return
+}
+
+// ReadMapStrIntfBytes reads a map[string]interface{}
+// out of 'b' and returns the map and remaining bytes.
+// If 'old' is non-nil, the values will be read into that map.
+func ReadMapStrIntfBytes(b []byte, old map[string]interface{}) (v map[string]interface{}, o []byte, err error) {
+ var sz uint32
+ o = b
+ sz, o, err = ReadMapHeaderBytes(o)
+
+ if err != nil {
+ return
+ }
+
+ if old != nil {
+ for key := range old {
+ delete(old, key)
+ }
+ v = old
+ } else {
+ v = make(map[string]interface{}, int(sz))
+ }
+
+ for z := uint32(0); z < sz; z++ {
+ if len(o) < 1 {
+ err = ErrShortBytes
+ return
+ }
+ var key []byte
+ key, o, err = ReadMapKeyZC(o)
+ if err != nil {
+ return
+ }
+ var val interface{}
+ val, o, err = ReadIntfBytes(o)
+ if err != nil {
+ return
+ }
+ v[string(key)] = val
+ }
+ return
+}
+
+// ReadIntfBytes attempts to read
+// the next object out of 'b' as a raw interface{} and
+// return the remaining bytes.
+func ReadIntfBytes(b []byte) (i interface{}, o []byte, err error) {
+ if len(b) < 1 {
+ err = ErrShortBytes
+ return
+ }
+
+ k := NextType(b)
+
+ switch k {
+ case MapType:
+ i, o, err = ReadMapStrIntfBytes(b, nil)
+ return
+
+ case ArrayType:
+ var sz uint32
+ sz, o, err = ReadArrayHeaderBytes(b)
+ if err != nil {
+ return
+ }
+ j := make([]interface{}, int(sz))
+ i = j
+ for d := range j {
+ j[d], o, err = ReadIntfBytes(o)
+ if err != nil {
+ return
+ }
+ }
+ return
+
+ case Float32Type:
+ i, o, err = ReadFloat32Bytes(b)
+ return
+
+ case Float64Type:
+ i, o, err = ReadFloat64Bytes(b)
+ return
+
+ case IntType:
+ i, o, err = ReadInt64Bytes(b)
+ return
+
+ case UintType:
+ i, o, err = ReadUint64Bytes(b)
+ return
+
+ case BoolType:
+ i, o, err = ReadBoolBytes(b)
+ return
+
+ case TimeType:
+ i, o, err = ReadTimeBytes(b)
+ return
+
+ case Complex64Type:
+ i, o, err = ReadComplex64Bytes(b)
+ return
+
+ case Complex128Type:
+ i, o, err = ReadComplex128Bytes(b)
+ return
+
+ case ExtensionType:
+ var t int8
+ t, err = peekExtension(b)
+ if err != nil {
+ return
+ }
+ // use a user-defined extension,
+ // if it's been registered
+ f, ok := extensionReg[t]
+ if ok {
+ e := f()
+ o, err = ReadExtensionBytes(b, e)
+ i = e
+ return
+ }
+ // last resort is a raw extension
+ e := RawExtension{}
+ e.Type = int8(t)
+ o, err = ReadExtensionBytes(b, &e)
+ i = &e
+ return
+
+ case NilType:
+ o, err = ReadNilBytes(b)
+ return
+
+ case BinType:
+ i, o, err = ReadBytesBytes(b, nil)
+ return
+
+ case StrType:
+ i, o, err = ReadStringBytes(b)
+ return
+
+ default:
+ err = InvalidPrefixError(b[0])
+ return
+ }
+}
+
+// Skip skips the next object in 'b' and
+// returns the remaining bytes. If the object
+// is a map or array, all of its elements
+// will be skipped.
+// Possible Errors:
+// - ErrShortBytes (not enough bytes in b)
+// - InvalidPrefixError (bad encoding)
+func Skip(b []byte) ([]byte, error) {
+ sz, asz, err := getSize(b)
+ if err != nil {
+ return b, err
+ }
+ if uintptr(len(b)) < sz {
+ return b, ErrShortBytes
+ }
+ b = b[sz:]
+ for asz > 0 {
+ b, err = Skip(b)
+ if err != nil {
+ return b, err
+ }
+ asz--
+ }
+ return b, nil
+}
+
+// returns (skip N bytes, skip M objects, error)
+func getSize(b []byte) (uintptr, uintptr, error) {
+ l := len(b)
+ if l == 0 {
+ return 0, 0, ErrShortBytes
+ }
+ lead := b[0]
+ spec := &sizes[lead] // get type information
+ size, mode := spec.size, spec.extra
+ if size == 0 {
+ return 0, 0, InvalidPrefixError(lead)
+ }
+ if mode >= 0 { // fixed composites
+ return uintptr(size), uintptr(mode), nil
+ }
+ if l < int(size) {
+ return 0, 0, ErrShortBytes
+ }
+ switch mode {
+ case extra8:
+ return uintptr(size) + uintptr(b[1]), 0, nil
+ case extra16:
+ return uintptr(size) + uintptr(big.Uint16(b[1:])), 0, nil
+ case extra32:
+ return uintptr(size) + uintptr(big.Uint32(b[1:])), 0, nil
+ case map16v:
+ return uintptr(size), 2 * uintptr(big.Uint16(b[1:])), nil
+ case map32v:
+ return uintptr(size), 2 * uintptr(big.Uint32(b[1:])), nil
+ case array16v:
+ return uintptr(size), uintptr(big.Uint16(b[1:])), nil
+ case array32v:
+ return uintptr(size), uintptr(big.Uint32(b[1:])), nil
+ default:
+ return 0, 0, fatal
+ }
+}
diff --git a/vendor/github.com/tinylib/msgp/msgp/size.go b/vendor/github.com/tinylib/msgp/msgp/size.go
new file mode 100644
index 000000000..ce2f8b16f
--- /dev/null
+++ b/vendor/github.com/tinylib/msgp/msgp/size.go
@@ -0,0 +1,38 @@
+package msgp
+
+// The sizes provided
+// are the worst-case
+// encoded sizes for
+// each type. For variable-
+// length types ([]byte, string),
+// the total encoded size is
+// the prefix size plus the
+// length of the object.
+const (
+ Int64Size = 9
+ IntSize = Int64Size
+ UintSize = Int64Size
+ Int8Size = 2
+ Int16Size = 3
+ Int32Size = 5
+ Uint8Size = 2
+ ByteSize = Uint8Size
+ Uint16Size = 3
+ Uint32Size = 5
+ Uint64Size = Int64Size
+ Float64Size = 9
+ Float32Size = 5
+ Complex64Size = 10
+ Complex128Size = 18
+
+ TimeSize = 15
+ BoolSize = 1
+ NilSize = 1
+
+ MapHeaderSize = 5
+ ArrayHeaderSize = 5
+
+ BytesPrefixSize = 5
+ StringPrefixSize = 5
+ ExtensionPrefixSize = 6
+)
diff --git a/vendor/github.com/tinylib/msgp/msgp/unsafe.go b/vendor/github.com/tinylib/msgp/msgp/unsafe.go
new file mode 100644
index 000000000..3978b6ff6
--- /dev/null
+++ b/vendor/github.com/tinylib/msgp/msgp/unsafe.go
@@ -0,0 +1,41 @@
+// +build !purego,!appengine
+
+package msgp
+
+import (
+ "reflect"
+ "unsafe"
+)
+
+// NOTE:
+// all of the definition in this file
+// should be repeated in appengine.go,
+// but without using unsafe
+
+const (
+ // spec says int and uint are always
+ // the same size, but that int/uint
+ // size may not be machine word size
+ smallint = unsafe.Sizeof(int(0)) == 4
+)
+
+// UnsafeString returns the byte slice as a volatile string
+// THIS SHOULD ONLY BE USED BY THE CODE GENERATOR.
+// THIS IS EVIL CODE.
+// YOU HAVE BEEN WARNED.
+func UnsafeString(b []byte) string {
+ sh := (*reflect.SliceHeader)(unsafe.Pointer(&b))
+ return *(*string)(unsafe.Pointer(&reflect.StringHeader{Data: sh.Data, Len: sh.Len}))
+}
+
+// UnsafeBytes returns the string as a byte slice
+// THIS SHOULD ONLY BE USED BY THE CODE GENERATOR.
+// THIS IS EVIL CODE.
+// YOU HAVE BEEN WARNED.
+func UnsafeBytes(s string) []byte {
+ return *(*[]byte)(unsafe.Pointer(&reflect.SliceHeader{
+ Len: len(s),
+ Cap: len(s),
+ Data: (*(*reflect.StringHeader)(unsafe.Pointer(&s))).Data,
+ }))
+}
diff --git a/vendor/github.com/tinylib/msgp/msgp/write.go b/vendor/github.com/tinylib/msgp/msgp/write.go
new file mode 100644
index 000000000..fb1947c57
--- /dev/null
+++ b/vendor/github.com/tinylib/msgp/msgp/write.go
@@ -0,0 +1,845 @@
+package msgp
+
+import (
+ "errors"
+ "fmt"
+ "io"
+ "math"
+ "reflect"
+ "sync"
+ "time"
+)
+
+// Sizer is an interface implemented
+// by types that can estimate their
+// size when MessagePack encoded.
+// This interface is optional, but
+// encoding/marshaling implementations
+// may use this as a way to pre-allocate
+// memory for serialization.
+type Sizer interface {
+ Msgsize() int
+}
+
+var (
+ // Nowhere is an io.Writer to nowhere
+ Nowhere io.Writer = nwhere{}
+
+ btsType = reflect.TypeOf(([]byte)(nil))
+ writerPool = sync.Pool{
+ New: func() interface{} {
+ return &Writer{buf: make([]byte, 2048)}
+ },
+ }
+)
+
+func popWriter(w io.Writer) *Writer {
+ wr := writerPool.Get().(*Writer)
+ wr.Reset(w)
+ return wr
+}
+
+func pushWriter(wr *Writer) {
+ wr.w = nil
+ wr.wloc = 0
+ writerPool.Put(wr)
+}
+
+// freeW frees a writer for use
+// by other processes. It is not necessary
+// to call freeW on a writer. However, maintaining
+// a reference to a *Writer after calling freeW on
+// it will cause undefined behavior.
+func freeW(w *Writer) { pushWriter(w) }
+
+// Require ensures that cap(old)-len(old) >= extra.
+func Require(old []byte, extra int) []byte {
+ l := len(old)
+ c := cap(old)
+ r := l + extra
+ if c >= r {
+ return old
+ } else if l == 0 {
+ return make([]byte, 0, extra)
+ }
+ // the new size is the greater
+ // of double the old capacity
+ // and the sum of the old length
+ // and the number of new bytes
+ // necessary.
+ c <<= 1
+ if c < r {
+ c = r
+ }
+ n := make([]byte, l, c)
+ copy(n, old)
+ return n
+}
+
+// nowhere writer
+type nwhere struct{}
+
+func (n nwhere) Write(p []byte) (int, error) { return len(p), nil }
+
+// Marshaler is the interface implemented
+// by types that know how to marshal themselves
+// as MessagePack. MarshalMsg appends the marshalled
+// form of the object to the provided
+// byte slice, returning the extended
+// slice and any errors encountered.
+type Marshaler interface {
+ MarshalMsg([]byte) ([]byte, error)
+}
+
+// Encodable is the interface implemented
+// by types that know how to write themselves
+// as MessagePack using a *msgp.Writer.
+type Encodable interface {
+ EncodeMsg(*Writer) error
+}
+
+// Writer is a buffered writer
+// that can be used to write
+// MessagePack objects to an io.Writer.
+// You must call *Writer.Flush() in order
+// to flush all of the buffered data
+// to the underlying writer.
+type Writer struct {
+ w io.Writer
+ buf []byte
+ wloc int
+}
+
+// NewWriter returns a new *Writer.
+func NewWriter(w io.Writer) *Writer {
+ if wr, ok := w.(*Writer); ok {
+ return wr
+ }
+ return popWriter(w)
+}
+
+// NewWriterSize returns a writer with a custom buffer size.
+func NewWriterSize(w io.Writer, sz int) *Writer {
+ // we must be able to require() 18
+ // contiguous bytes, so that is the
+ // practical minimum buffer size
+ if sz < 18 {
+ sz = 18
+ }
+
+ return &Writer{
+ w: w,
+ buf: make([]byte, sz),
+ }
+}
+
+// Encode encodes an Encodable to an io.Writer.
+func Encode(w io.Writer, e Encodable) error {
+ wr := NewWriter(w)
+ err := e.EncodeMsg(wr)
+ if err == nil {
+ err = wr.Flush()
+ }
+ freeW(wr)
+ return err
+}
+
+func (mw *Writer) flush() error {
+ if mw.wloc == 0 {
+ return nil
+ }
+ n, err := mw.w.Write(mw.buf[:mw.wloc])
+ if err != nil {
+ if n > 0 {
+ mw.wloc = copy(mw.buf, mw.buf[n:mw.wloc])
+ }
+ return err
+ }
+ mw.wloc = 0
+ return nil
+}
+
+// Flush flushes all of the buffered
+// data to the underlying writer.
+func (mw *Writer) Flush() error { return mw.flush() }
+
+// Buffered returns the number bytes in the write buffer
+func (mw *Writer) Buffered() int { return len(mw.buf) - mw.wloc }
+
+func (mw *Writer) avail() int { return len(mw.buf) - mw.wloc }
+
+func (mw *Writer) bufsize() int { return len(mw.buf) }
+
+// NOTE: this should only be called with
+// a number that is guaranteed to be less than
+// len(mw.buf). typically, it is called with a constant.
+//
+// NOTE: this is a hot code path
+func (mw *Writer) require(n int) (int, error) {
+ c := len(mw.buf)
+ wl := mw.wloc
+ if c-wl < n {
+ if err := mw.flush(); err != nil {
+ return 0, err
+ }
+ wl = mw.wloc
+ }
+ mw.wloc += n
+ return wl, nil
+}
+
+func (mw *Writer) Append(b ...byte) error {
+ if mw.avail() < len(b) {
+ err := mw.flush()
+ if err != nil {
+ return err
+ }
+ }
+ mw.wloc += copy(mw.buf[mw.wloc:], b)
+ return nil
+}
+
+// push one byte onto the buffer
+//
+// NOTE: this is a hot code path
+func (mw *Writer) push(b byte) error {
+ if mw.wloc == len(mw.buf) {
+ if err := mw.flush(); err != nil {
+ return err
+ }
+ }
+ mw.buf[mw.wloc] = b
+ mw.wloc++
+ return nil
+}
+
+func (mw *Writer) prefix8(b byte, u uint8) error {
+ const need = 2
+ if len(mw.buf)-mw.wloc < need {
+ if err := mw.flush(); err != nil {
+ return err
+ }
+ }
+ prefixu8(mw.buf[mw.wloc:], b, u)
+ mw.wloc += need
+ return nil
+}
+
+func (mw *Writer) prefix16(b byte, u uint16) error {
+ const need = 3
+ if len(mw.buf)-mw.wloc < need {
+ if err := mw.flush(); err != nil {
+ return err
+ }
+ }
+ prefixu16(mw.buf[mw.wloc:], b, u)
+ mw.wloc += need
+ return nil
+}
+
+func (mw *Writer) prefix32(b byte, u uint32) error {
+ const need = 5
+ if len(mw.buf)-mw.wloc < need {
+ if err := mw.flush(); err != nil {
+ return err
+ }
+ }
+ prefixu32(mw.buf[mw.wloc:], b, u)
+ mw.wloc += need
+ return nil
+}
+
+func (mw *Writer) prefix64(b byte, u uint64) error {
+ const need = 9
+ if len(mw.buf)-mw.wloc < need {
+ if err := mw.flush(); err != nil {
+ return err
+ }
+ }
+ prefixu64(mw.buf[mw.wloc:], b, u)
+ mw.wloc += need
+ return nil
+}
+
+// Write implements io.Writer, and writes
+// data directly to the buffer.
+func (mw *Writer) Write(p []byte) (int, error) {
+ l := len(p)
+ if mw.avail() < l {
+ if err := mw.flush(); err != nil {
+ return 0, err
+ }
+ if l > len(mw.buf) {
+ return mw.w.Write(p)
+ }
+ }
+ mw.wloc += copy(mw.buf[mw.wloc:], p)
+ return l, nil
+}
+
+// implements io.WriteString
+func (mw *Writer) writeString(s string) error {
+ l := len(s)
+ if mw.avail() < l {
+ if err := mw.flush(); err != nil {
+ return err
+ }
+ if l > len(mw.buf) {
+ _, err := io.WriteString(mw.w, s)
+ return err
+ }
+ }
+ mw.wloc += copy(mw.buf[mw.wloc:], s)
+ return nil
+}
+
+// Reset changes the underlying writer used by the Writer
+func (mw *Writer) Reset(w io.Writer) {
+ mw.buf = mw.buf[:cap(mw.buf)]
+ mw.w = w
+ mw.wloc = 0
+}
+
+// WriteMapHeader writes a map header of the given
+// size to the writer
+func (mw *Writer) WriteMapHeader(sz uint32) error {
+ switch {
+ case sz <= 15:
+ return mw.push(wfixmap(uint8(sz)))
+ case sz <= math.MaxUint16:
+ return mw.prefix16(mmap16, uint16(sz))
+ default:
+ return mw.prefix32(mmap32, sz)
+ }
+}
+
+// WriteArrayHeader writes an array header of the
+// given size to the writer
+func (mw *Writer) WriteArrayHeader(sz uint32) error {
+ switch {
+ case sz <= 15:
+ return mw.push(wfixarray(uint8(sz)))
+ case sz <= math.MaxUint16:
+ return mw.prefix16(marray16, uint16(sz))
+ default:
+ return mw.prefix32(marray32, sz)
+ }
+}
+
+// WriteNil writes a nil byte to the buffer
+func (mw *Writer) WriteNil() error {
+ return mw.push(mnil)
+}
+
+// WriteFloat64 writes a float64 to the writer
+func (mw *Writer) WriteFloat64(f float64) error {
+ return mw.prefix64(mfloat64, math.Float64bits(f))
+}
+
+// WriteFloat32 writes a float32 to the writer
+func (mw *Writer) WriteFloat32(f float32) error {
+ return mw.prefix32(mfloat32, math.Float32bits(f))
+}
+
+// WriteInt64 writes an int64 to the writer
+func (mw *Writer) WriteInt64(i int64) error {
+ if i >= 0 {
+ switch {
+ case i <= math.MaxInt8:
+ return mw.push(wfixint(uint8(i)))
+ case i <= math.MaxInt16:
+ return mw.prefix16(mint16, uint16(i))
+ case i <= math.MaxInt32:
+ return mw.prefix32(mint32, uint32(i))
+ default:
+ return mw.prefix64(mint64, uint64(i))
+ }
+ }
+ switch {
+ case i >= -32:
+ return mw.push(wnfixint(int8(i)))
+ case i >= math.MinInt8:
+ return mw.prefix8(mint8, uint8(i))
+ case i >= math.MinInt16:
+ return mw.prefix16(mint16, uint16(i))
+ case i >= math.MinInt32:
+ return mw.prefix32(mint32, uint32(i))
+ default:
+ return mw.prefix64(mint64, uint64(i))
+ }
+}
+
+// WriteInt8 writes an int8 to the writer
+func (mw *Writer) WriteInt8(i int8) error { return mw.WriteInt64(int64(i)) }
+
+// WriteInt16 writes an int16 to the writer
+func (mw *Writer) WriteInt16(i int16) error { return mw.WriteInt64(int64(i)) }
+
+// WriteInt32 writes an int32 to the writer
+func (mw *Writer) WriteInt32(i int32) error { return mw.WriteInt64(int64(i)) }
+
+// WriteInt writes an int to the writer
+func (mw *Writer) WriteInt(i int) error { return mw.WriteInt64(int64(i)) }
+
+// WriteUint64 writes a uint64 to the writer
+func (mw *Writer) WriteUint64(u uint64) error {
+ switch {
+ case u <= (1<<7)-1:
+ return mw.push(wfixint(uint8(u)))
+ case u <= math.MaxUint8:
+ return mw.prefix8(muint8, uint8(u))
+ case u <= math.MaxUint16:
+ return mw.prefix16(muint16, uint16(u))
+ case u <= math.MaxUint32:
+ return mw.prefix32(muint32, uint32(u))
+ default:
+ return mw.prefix64(muint64, u)
+ }
+}
+
+// WriteByte is analogous to WriteUint8
+func (mw *Writer) WriteByte(u byte) error { return mw.WriteUint8(uint8(u)) }
+
+// WriteUint8 writes a uint8 to the writer
+func (mw *Writer) WriteUint8(u uint8) error { return mw.WriteUint64(uint64(u)) }
+
+// WriteUint16 writes a uint16 to the writer
+func (mw *Writer) WriteUint16(u uint16) error { return mw.WriteUint64(uint64(u)) }
+
+// WriteUint32 writes a uint32 to the writer
+func (mw *Writer) WriteUint32(u uint32) error { return mw.WriteUint64(uint64(u)) }
+
+// WriteUint writes a uint to the writer
+func (mw *Writer) WriteUint(u uint) error { return mw.WriteUint64(uint64(u)) }
+
+// WriteBytes writes binary as 'bin' to the writer
+func (mw *Writer) WriteBytes(b []byte) error {
+ sz := uint32(len(b))
+ var err error
+ switch {
+ case sz <= math.MaxUint8:
+ err = mw.prefix8(mbin8, uint8(sz))
+ case sz <= math.MaxUint16:
+ err = mw.prefix16(mbin16, uint16(sz))
+ default:
+ err = mw.prefix32(mbin32, sz)
+ }
+ if err != nil {
+ return err
+ }
+ _, err = mw.Write(b)
+ return err
+}
+
+// WriteBytesHeader writes just the size header
+// of a MessagePack 'bin' object. The user is responsible
+// for then writing 'sz' more bytes into the stream.
+func (mw *Writer) WriteBytesHeader(sz uint32) error {
+ switch {
+ case sz <= math.MaxUint8:
+ return mw.prefix8(mbin8, uint8(sz))
+ case sz <= math.MaxUint16:
+ return mw.prefix16(mbin16, uint16(sz))
+ default:
+ return mw.prefix32(mbin32, sz)
+ }
+}
+
+// WriteBool writes a bool to the writer
+func (mw *Writer) WriteBool(b bool) error {
+ if b {
+ return mw.push(mtrue)
+ }
+ return mw.push(mfalse)
+}
+
+// WriteString writes a messagepack string to the writer.
+// (This is NOT an implementation of io.StringWriter)
+func (mw *Writer) WriteString(s string) error {
+ sz := uint32(len(s))
+ var err error
+ switch {
+ case sz <= 31:
+ err = mw.push(wfixstr(uint8(sz)))
+ case sz <= math.MaxUint8:
+ err = mw.prefix8(mstr8, uint8(sz))
+ case sz <= math.MaxUint16:
+ err = mw.prefix16(mstr16, uint16(sz))
+ default:
+ err = mw.prefix32(mstr32, sz)
+ }
+ if err != nil {
+ return err
+ }
+ return mw.writeString(s)
+}
+
+// WriteStringHeader writes just the string size
+// header of a MessagePack 'str' object. The user
+// is responsible for writing 'sz' more valid UTF-8
+// bytes to the stream.
+func (mw *Writer) WriteStringHeader(sz uint32) error {
+ switch {
+ case sz <= 31:
+ return mw.push(wfixstr(uint8(sz)))
+ case sz <= math.MaxUint8:
+ return mw.prefix8(mstr8, uint8(sz))
+ case sz <= math.MaxUint16:
+ return mw.prefix16(mstr16, uint16(sz))
+ default:
+ return mw.prefix32(mstr32, sz)
+ }
+}
+
+// WriteStringFromBytes writes a 'str' object
+// from a []byte.
+func (mw *Writer) WriteStringFromBytes(str []byte) error {
+ sz := uint32(len(str))
+ var err error
+ switch {
+ case sz <= 31:
+ err = mw.push(wfixstr(uint8(sz)))
+ case sz <= math.MaxUint8:
+ err = mw.prefix8(mstr8, uint8(sz))
+ case sz <= math.MaxUint16:
+ err = mw.prefix16(mstr16, uint16(sz))
+ default:
+ err = mw.prefix32(mstr32, sz)
+ }
+ if err != nil {
+ return err
+ }
+ _, err = mw.Write(str)
+ return err
+}
+
+// WriteComplex64 writes a complex64 to the writer
+func (mw *Writer) WriteComplex64(f complex64) error {
+ o, err := mw.require(10)
+ if err != nil {
+ return err
+ }
+ mw.buf[o] = mfixext8
+ mw.buf[o+1] = Complex64Extension
+ big.PutUint32(mw.buf[o+2:], math.Float32bits(real(f)))
+ big.PutUint32(mw.buf[o+6:], math.Float32bits(imag(f)))
+ return nil
+}
+
+// WriteComplex128 writes a complex128 to the writer
+func (mw *Writer) WriteComplex128(f complex128) error {
+ o, err := mw.require(18)
+ if err != nil {
+ return err
+ }
+ mw.buf[o] = mfixext16
+ mw.buf[o+1] = Complex128Extension
+ big.PutUint64(mw.buf[o+2:], math.Float64bits(real(f)))
+ big.PutUint64(mw.buf[o+10:], math.Float64bits(imag(f)))
+ return nil
+}
+
+// WriteMapStrStr writes a map[string]string to the writer
+func (mw *Writer) WriteMapStrStr(mp map[string]string) (err error) {
+ err = mw.WriteMapHeader(uint32(len(mp)))
+ if err != nil {
+ return
+ }
+ for key, val := range mp {
+ err = mw.WriteString(key)
+ if err != nil {
+ return
+ }
+ err = mw.WriteString(val)
+ if err != nil {
+ return
+ }
+ }
+ return nil
+}
+
+// WriteMapStrIntf writes a map[string]interface to the writer
+func (mw *Writer) WriteMapStrIntf(mp map[string]interface{}) (err error) {
+ err = mw.WriteMapHeader(uint32(len(mp)))
+ if err != nil {
+ return
+ }
+ for key, val := range mp {
+ err = mw.WriteString(key)
+ if err != nil {
+ return
+ }
+ err = mw.WriteIntf(val)
+ if err != nil {
+ return
+ }
+ }
+ return
+}
+
+// WriteTime writes a time.Time object to the wire.
+//
+// Time is encoded as Unix time, which means that
+// location (time zone) data is removed from the object.
+// The encoded object itself is 12 bytes: 8 bytes for
+// a big-endian 64-bit integer denoting seconds
+// elapsed since "zero" Unix time, followed by 4 bytes
+// for a big-endian 32-bit signed integer denoting
+// the nanosecond offset of the time. This encoding
+// is intended to ease portability across languages.
+// (Note that this is *not* the standard time.Time
+// binary encoding, because its implementation relies
+// heavily on the internal representation used by the
+// time package.)
+func (mw *Writer) WriteTime(t time.Time) error {
+ t = t.UTC()
+ o, err := mw.require(15)
+ if err != nil {
+ return err
+ }
+ mw.buf[o] = mext8
+ mw.buf[o+1] = 12
+ mw.buf[o+2] = TimeExtension
+ putUnix(mw.buf[o+3:], t.Unix(), int32(t.Nanosecond()))
+ return nil
+}
+
+// WriteIntf writes the concrete type of 'v'.
+// WriteIntf will error if 'v' is not one of the following:
+// - A bool, float, string, []byte, int, uint, or complex
+// - A map of supported types (with string keys)
+// - An array or slice of supported types
+// - A pointer to a supported type
+// - A type that satisfies the msgp.Encodable interface
+// - A type that satisfies the msgp.Extension interface
+func (mw *Writer) WriteIntf(v interface{}) error {
+ if v == nil {
+ return mw.WriteNil()
+ }
+ switch v := v.(type) {
+
+ // preferred interfaces
+
+ case Encodable:
+ return v.EncodeMsg(mw)
+ case Extension:
+ return mw.WriteExtension(v)
+
+ // concrete types
+
+ case bool:
+ return mw.WriteBool(v)
+ case float32:
+ return mw.WriteFloat32(v)
+ case float64:
+ return mw.WriteFloat64(v)
+ case complex64:
+ return mw.WriteComplex64(v)
+ case complex128:
+ return mw.WriteComplex128(v)
+ case uint8:
+ return mw.WriteUint8(v)
+ case uint16:
+ return mw.WriteUint16(v)
+ case uint32:
+ return mw.WriteUint32(v)
+ case uint64:
+ return mw.WriteUint64(v)
+ case uint:
+ return mw.WriteUint(v)
+ case int8:
+ return mw.WriteInt8(v)
+ case int16:
+ return mw.WriteInt16(v)
+ case int32:
+ return mw.WriteInt32(v)
+ case int64:
+ return mw.WriteInt64(v)
+ case int:
+ return mw.WriteInt(v)
+ case string:
+ return mw.WriteString(v)
+ case []byte:
+ return mw.WriteBytes(v)
+ case map[string]string:
+ return mw.WriteMapStrStr(v)
+ case map[string]interface{}:
+ return mw.WriteMapStrIntf(v)
+ case time.Time:
+ return mw.WriteTime(v)
+ }
+
+ val := reflect.ValueOf(v)
+ if !isSupported(val.Kind()) || !val.IsValid() {
+ return fmt.Errorf("msgp: type %s not supported", val)
+ }
+
+ switch val.Kind() {
+ case reflect.Ptr:
+ if val.IsNil() {
+ return mw.WriteNil()
+ }
+ return mw.WriteIntf(val.Elem().Interface())
+ case reflect.Slice:
+ return mw.writeSlice(val)
+ case reflect.Map:
+ return mw.writeMap(val)
+ }
+ return &ErrUnsupportedType{T: val.Type()}
+}
+
+func (mw *Writer) writeMap(v reflect.Value) (err error) {
+ if v.Type().Key().Kind() != reflect.String {
+ return errors.New("msgp: map keys must be strings")
+ }
+ ks := v.MapKeys()
+ err = mw.WriteMapHeader(uint32(len(ks)))
+ if err != nil {
+ return
+ }
+ for _, key := range ks {
+ val := v.MapIndex(key)
+ err = mw.WriteString(key.String())
+ if err != nil {
+ return
+ }
+ err = mw.WriteIntf(val.Interface())
+ if err != nil {
+ return
+ }
+ }
+ return
+}
+
+func (mw *Writer) writeSlice(v reflect.Value) (err error) {
+ // is []byte
+ if v.Type().ConvertibleTo(btsType) {
+ return mw.WriteBytes(v.Bytes())
+ }
+
+ sz := uint32(v.Len())
+ err = mw.WriteArrayHeader(sz)
+ if err != nil {
+ return
+ }
+ for i := uint32(0); i < sz; i++ {
+ err = mw.WriteIntf(v.Index(int(i)).Interface())
+ if err != nil {
+ return
+ }
+ }
+ return
+}
+
+func (mw *Writer) writeStruct(v reflect.Value) error {
+ if enc, ok := v.Interface().(Encodable); ok {
+ return enc.EncodeMsg(mw)
+ }
+ return fmt.Errorf("msgp: unsupported type: %s", v.Type())
+}
+
+func (mw *Writer) writeVal(v reflect.Value) error {
+ if !isSupported(v.Kind()) {
+ return fmt.Errorf("msgp: msgp/enc: type %q not supported", v.Type())
+ }
+
+ // shortcut for nil values
+ if v.IsNil() {
+ return mw.WriteNil()
+ }
+ switch v.Kind() {
+ case reflect.Bool:
+ return mw.WriteBool(v.Bool())
+
+ case reflect.Float32, reflect.Float64:
+ return mw.WriteFloat64(v.Float())
+
+ case reflect.Complex64, reflect.Complex128:
+ return mw.WriteComplex128(v.Complex())
+
+ case reflect.Int, reflect.Int16, reflect.Int32, reflect.Int64, reflect.Int8:
+ return mw.WriteInt64(v.Int())
+
+ case reflect.Interface, reflect.Ptr:
+ if v.IsNil() {
+ mw.WriteNil()
+ }
+ return mw.writeVal(v.Elem())
+
+ case reflect.Map:
+ return mw.writeMap(v)
+
+ case reflect.Uint, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Uint8:
+ return mw.WriteUint64(v.Uint())
+
+ case reflect.String:
+ return mw.WriteString(v.String())
+
+ case reflect.Slice, reflect.Array:
+ return mw.writeSlice(v)
+
+ case reflect.Struct:
+ return mw.writeStruct(v)
+
+ }
+ return fmt.Errorf("msgp: msgp/enc: type %q not supported", v.Type())
+}
+
+// is the reflect.Kind encodable?
+func isSupported(k reflect.Kind) bool {
+ switch k {
+ case reflect.Func, reflect.Chan, reflect.Invalid, reflect.UnsafePointer:
+ return false
+ default:
+ return true
+ }
+}
+
+// GuessSize guesses the size of the underlying
+// value of 'i'. If the underlying value is not
+// a simple builtin (or []byte), GuessSize defaults
+// to 512.
+func GuessSize(i interface{}) int {
+ if i == nil {
+ return NilSize
+ }
+
+ switch i := i.(type) {
+ case Sizer:
+ return i.Msgsize()
+ case Extension:
+ return ExtensionPrefixSize + i.Len()
+ case float64:
+ return Float64Size
+ case float32:
+ return Float32Size
+ case uint8, uint16, uint32, uint64, uint:
+ return UintSize
+ case int8, int16, int32, int64, int:
+ return IntSize
+ case []byte:
+ return BytesPrefixSize + len(i)
+ case string:
+ return StringPrefixSize + len(i)
+ case complex64:
+ return Complex64Size
+ case complex128:
+ return Complex128Size
+ case bool:
+ return BoolSize
+ case map[string]interface{}:
+ s := MapHeaderSize
+ for key, val := range i {
+ s += StringPrefixSize + len(key) + GuessSize(val)
+ }
+ return s
+ case map[string]string:
+ s := MapHeaderSize
+ for key, val := range i {
+ s += 2*StringPrefixSize + len(key) + len(val)
+ }
+ return s
+ default:
+ return 512
+ }
+}
diff --git a/vendor/github.com/tinylib/msgp/msgp/write_bytes.go b/vendor/github.com/tinylib/msgp/msgp/write_bytes.go
new file mode 100644
index 000000000..eaa03c46e
--- /dev/null
+++ b/vendor/github.com/tinylib/msgp/msgp/write_bytes.go
@@ -0,0 +1,411 @@
+package msgp
+
+import (
+ "math"
+ "reflect"
+ "time"
+)
+
+// ensure 'sz' extra bytes in 'b' btw len(b) and cap(b)
+func ensure(b []byte, sz int) ([]byte, int) {
+ l := len(b)
+ c := cap(b)
+ if c-l < sz {
+ o := make([]byte, (2*c)+sz) // exponential growth
+ n := copy(o, b)
+ return o[:n+sz], n
+ }
+ return b[:l+sz], l
+}
+
+// AppendMapHeader appends a map header with the
+// given size to the slice
+func AppendMapHeader(b []byte, sz uint32) []byte {
+ switch {
+ case sz <= 15:
+ return append(b, wfixmap(uint8(sz)))
+
+ case sz <= math.MaxUint16:
+ o, n := ensure(b, 3)
+ prefixu16(o[n:], mmap16, uint16(sz))
+ return o
+
+ default:
+ o, n := ensure(b, 5)
+ prefixu32(o[n:], mmap32, sz)
+ return o
+ }
+}
+
+// AppendArrayHeader appends an array header with
+// the given size to the slice
+func AppendArrayHeader(b []byte, sz uint32) []byte {
+ switch {
+ case sz <= 15:
+ return append(b, wfixarray(uint8(sz)))
+
+ case sz <= math.MaxUint16:
+ o, n := ensure(b, 3)
+ prefixu16(o[n:], marray16, uint16(sz))
+ return o
+
+ default:
+ o, n := ensure(b, 5)
+ prefixu32(o[n:], marray32, sz)
+ return o
+ }
+}
+
+// AppendNil appends a 'nil' byte to the slice
+func AppendNil(b []byte) []byte { return append(b, mnil) }
+
+// AppendFloat64 appends a float64 to the slice
+func AppendFloat64(b []byte, f float64) []byte {
+ o, n := ensure(b, Float64Size)
+ prefixu64(o[n:], mfloat64, math.Float64bits(f))
+ return o
+}
+
+// AppendFloat32 appends a float32 to the slice
+func AppendFloat32(b []byte, f float32) []byte {
+ o, n := ensure(b, Float32Size)
+ prefixu32(o[n:], mfloat32, math.Float32bits(f))
+ return o
+}
+
+// AppendInt64 appends an int64 to the slice
+func AppendInt64(b []byte, i int64) []byte {
+ if i >= 0 {
+ switch {
+ case i <= math.MaxInt8:
+ return append(b, wfixint(uint8(i)))
+ case i <= math.MaxInt16:
+ o, n := ensure(b, 3)
+ putMint16(o[n:], int16(i))
+ return o
+ case i <= math.MaxInt32:
+ o, n := ensure(b, 5)
+ putMint32(o[n:], int32(i))
+ return o
+ default:
+ o, n := ensure(b, 9)
+ putMint64(o[n:], i)
+ return o
+ }
+ }
+ switch {
+ case i >= -32:
+ return append(b, wnfixint(int8(i)))
+ case i >= math.MinInt8:
+ o, n := ensure(b, 2)
+ putMint8(o[n:], int8(i))
+ return o
+ case i >= math.MinInt16:
+ o, n := ensure(b, 3)
+ putMint16(o[n:], int16(i))
+ return o
+ case i >= math.MinInt32:
+ o, n := ensure(b, 5)
+ putMint32(o[n:], int32(i))
+ return o
+ default:
+ o, n := ensure(b, 9)
+ putMint64(o[n:], i)
+ return o
+ }
+}
+
+// AppendInt appends an int to the slice
+func AppendInt(b []byte, i int) []byte { return AppendInt64(b, int64(i)) }
+
+// AppendInt8 appends an int8 to the slice
+func AppendInt8(b []byte, i int8) []byte { return AppendInt64(b, int64(i)) }
+
+// AppendInt16 appends an int16 to the slice
+func AppendInt16(b []byte, i int16) []byte { return AppendInt64(b, int64(i)) }
+
+// AppendInt32 appends an int32 to the slice
+func AppendInt32(b []byte, i int32) []byte { return AppendInt64(b, int64(i)) }
+
+// AppendUint64 appends a uint64 to the slice
+func AppendUint64(b []byte, u uint64) []byte {
+ switch {
+ case u <= (1<<7)-1:
+ return append(b, wfixint(uint8(u)))
+
+ case u <= math.MaxUint8:
+ o, n := ensure(b, 2)
+ putMuint8(o[n:], uint8(u))
+ return o
+
+ case u <= math.MaxUint16:
+ o, n := ensure(b, 3)
+ putMuint16(o[n:], uint16(u))
+ return o
+
+ case u <= math.MaxUint32:
+ o, n := ensure(b, 5)
+ putMuint32(o[n:], uint32(u))
+ return o
+
+ default:
+ o, n := ensure(b, 9)
+ putMuint64(o[n:], u)
+ return o
+
+ }
+}
+
+// AppendUint appends a uint to the slice
+func AppendUint(b []byte, u uint) []byte { return AppendUint64(b, uint64(u)) }
+
+// AppendUint8 appends a uint8 to the slice
+func AppendUint8(b []byte, u uint8) []byte { return AppendUint64(b, uint64(u)) }
+
+// AppendByte is analogous to AppendUint8
+func AppendByte(b []byte, u byte) []byte { return AppendUint8(b, uint8(u)) }
+
+// AppendUint16 appends a uint16 to the slice
+func AppendUint16(b []byte, u uint16) []byte { return AppendUint64(b, uint64(u)) }
+
+// AppendUint32 appends a uint32 to the slice
+func AppendUint32(b []byte, u uint32) []byte { return AppendUint64(b, uint64(u)) }
+
+// AppendBytes appends bytes to the slice as MessagePack 'bin' data
+func AppendBytes(b []byte, bts []byte) []byte {
+ sz := len(bts)
+ var o []byte
+ var n int
+ switch {
+ case sz <= math.MaxUint8:
+ o, n = ensure(b, 2+sz)
+ prefixu8(o[n:], mbin8, uint8(sz))
+ n += 2
+ case sz <= math.MaxUint16:
+ o, n = ensure(b, 3+sz)
+ prefixu16(o[n:], mbin16, uint16(sz))
+ n += 3
+ default:
+ o, n = ensure(b, 5+sz)
+ prefixu32(o[n:], mbin32, uint32(sz))
+ n += 5
+ }
+ return o[:n+copy(o[n:], bts)]
+}
+
+// AppendBool appends a bool to the slice
+func AppendBool(b []byte, t bool) []byte {
+ if t {
+ return append(b, mtrue)
+ }
+ return append(b, mfalse)
+}
+
+// AppendString appends a string as a MessagePack 'str' to the slice
+func AppendString(b []byte, s string) []byte {
+ sz := len(s)
+ var n int
+ var o []byte
+ switch {
+ case sz <= 31:
+ o, n = ensure(b, 1+sz)
+ o[n] = wfixstr(uint8(sz))
+ n++
+ case sz <= math.MaxUint8:
+ o, n = ensure(b, 2+sz)
+ prefixu8(o[n:], mstr8, uint8(sz))
+ n += 2
+ case sz <= math.MaxUint16:
+ o, n = ensure(b, 3+sz)
+ prefixu16(o[n:], mstr16, uint16(sz))
+ n += 3
+ default:
+ o, n = ensure(b, 5+sz)
+ prefixu32(o[n:], mstr32, uint32(sz))
+ n += 5
+ }
+ return o[:n+copy(o[n:], s)]
+}
+
+// AppendStringFromBytes appends a []byte
+// as a MessagePack 'str' to the slice 'b.'
+func AppendStringFromBytes(b []byte, str []byte) []byte {
+ sz := len(str)
+ var n int
+ var o []byte
+ switch {
+ case sz <= 31:
+ o, n = ensure(b, 1+sz)
+ o[n] = wfixstr(uint8(sz))
+ n++
+ case sz <= math.MaxUint8:
+ o, n = ensure(b, 2+sz)
+ prefixu8(o[n:], mstr8, uint8(sz))
+ n += 2
+ case sz <= math.MaxUint16:
+ o, n = ensure(b, 3+sz)
+ prefixu16(o[n:], mstr16, uint16(sz))
+ n += 3
+ default:
+ o, n = ensure(b, 5+sz)
+ prefixu32(o[n:], mstr32, uint32(sz))
+ n += 5
+ }
+ return o[:n+copy(o[n:], str)]
+}
+
+// AppendComplex64 appends a complex64 to the slice as a MessagePack extension
+func AppendComplex64(b []byte, c complex64) []byte {
+ o, n := ensure(b, Complex64Size)
+ o[n] = mfixext8
+ o[n+1] = Complex64Extension
+ big.PutUint32(o[n+2:], math.Float32bits(real(c)))
+ big.PutUint32(o[n+6:], math.Float32bits(imag(c)))
+ return o
+}
+
+// AppendComplex128 appends a complex128 to the slice as a MessagePack extension
+func AppendComplex128(b []byte, c complex128) []byte {
+ o, n := ensure(b, Complex128Size)
+ o[n] = mfixext16
+ o[n+1] = Complex128Extension
+ big.PutUint64(o[n+2:], math.Float64bits(real(c)))
+ big.PutUint64(o[n+10:], math.Float64bits(imag(c)))
+ return o
+}
+
+// AppendTime appends a time.Time to the slice as a MessagePack extension
+func AppendTime(b []byte, t time.Time) []byte {
+ o, n := ensure(b, TimeSize)
+ t = t.UTC()
+ o[n] = mext8
+ o[n+1] = 12
+ o[n+2] = TimeExtension
+ putUnix(o[n+3:], t.Unix(), int32(t.Nanosecond()))
+ return o
+}
+
+// AppendMapStrStr appends a map[string]string to the slice
+// as a MessagePack map with 'str'-type keys and values
+func AppendMapStrStr(b []byte, m map[string]string) []byte {
+ sz := uint32(len(m))
+ b = AppendMapHeader(b, sz)
+ for key, val := range m {
+ b = AppendString(b, key)
+ b = AppendString(b, val)
+ }
+ return b
+}
+
+// AppendMapStrIntf appends a map[string]interface{} to the slice
+// as a MessagePack map with 'str'-type keys.
+func AppendMapStrIntf(b []byte, m map[string]interface{}) ([]byte, error) {
+ sz := uint32(len(m))
+ b = AppendMapHeader(b, sz)
+ var err error
+ for key, val := range m {
+ b = AppendString(b, key)
+ b, err = AppendIntf(b, val)
+ if err != nil {
+ return b, err
+ }
+ }
+ return b, nil
+}
+
+// AppendIntf appends the concrete type of 'i' to the
+// provided []byte. 'i' must be one of the following:
+// - 'nil'
+// - A bool, float, string, []byte, int, uint, or complex
+// - A map[string]interface{} or map[string]string
+// - A []T, where T is another supported type
+// - A *T, where T is another supported type
+// - A type that satisfieds the msgp.Marshaler interface
+// - A type that satisfies the msgp.Extension interface
+func AppendIntf(b []byte, i interface{}) ([]byte, error) {
+ if i == nil {
+ return AppendNil(b), nil
+ }
+
+ // all the concrete types
+ // for which we have methods
+ switch i := i.(type) {
+ case Marshaler:
+ return i.MarshalMsg(b)
+ case Extension:
+ return AppendExtension(b, i)
+ case bool:
+ return AppendBool(b, i), nil
+ case float32:
+ return AppendFloat32(b, i), nil
+ case float64:
+ return AppendFloat64(b, i), nil
+ case complex64:
+ return AppendComplex64(b, i), nil
+ case complex128:
+ return AppendComplex128(b, i), nil
+ case string:
+ return AppendString(b, i), nil
+ case []byte:
+ return AppendBytes(b, i), nil
+ case int8:
+ return AppendInt8(b, i), nil
+ case int16:
+ return AppendInt16(b, i), nil
+ case int32:
+ return AppendInt32(b, i), nil
+ case int64:
+ return AppendInt64(b, i), nil
+ case int:
+ return AppendInt64(b, int64(i)), nil
+ case uint:
+ return AppendUint64(b, uint64(i)), nil
+ case uint8:
+ return AppendUint8(b, i), nil
+ case uint16:
+ return AppendUint16(b, i), nil
+ case uint32:
+ return AppendUint32(b, i), nil
+ case uint64:
+ return AppendUint64(b, i), nil
+ case time.Time:
+ return AppendTime(b, i), nil
+ case map[string]interface{}:
+ return AppendMapStrIntf(b, i)
+ case map[string]string:
+ return AppendMapStrStr(b, i), nil
+ case []interface{}:
+ b = AppendArrayHeader(b, uint32(len(i)))
+ var err error
+ for _, k := range i {
+ b, err = AppendIntf(b, k)
+ if err != nil {
+ return b, err
+ }
+ }
+ return b, nil
+ }
+
+ var err error
+ v := reflect.ValueOf(i)
+ switch v.Kind() {
+ case reflect.Array, reflect.Slice:
+ l := v.Len()
+ b = AppendArrayHeader(b, uint32(l))
+ for i := 0; i < l; i++ {
+ b, err = AppendIntf(b, v.Index(i).Interface())
+ if err != nil {
+ return b, err
+ }
+ }
+ return b, nil
+ case reflect.Ptr:
+ if v.IsNil() {
+ return AppendNil(b), err
+ }
+ b, err = AppendIntf(b, v.Elem().Interface())
+ return b, err
+ default:
+ return b, &ErrUnsupportedType{T: v.Type()}
+ }
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/CHANGELOG.md b/vendor/github.com/uber/jaeger-client-go/CHANGELOG.md
new file mode 100644
index 000000000..4b3568ac1
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/CHANGELOG.md
@@ -0,0 +1,197 @@
+Changes by Version
+==================
+
+2.15.1 (unreleased)
+-------------------
+
+- nothing yet
+
+
+2.15.0 (2018-10-10)
+-------------------
+
+- Fix FollowsFrom spans ignoring baggage/debug header from dummy parent context (#313) <Zvi Cahana>
+- Make maximum annotation length configurable in tracer options (#318) <Eric Chang>
+- Support more environment variables in configuration (#323) <Daneyon Hansen>
+- Print error on Sampler Query failure (#328) <Goutham Veeramachaneni>
+- Add an HTTPOption to support custom http.RoundTripper (#333) <Michael Puncel>
+- Return an error when an HTTP error code is seen in zipkin HTTP transport (#331) <Michael Puncel>
+
+
+2.14.0 (2018-04-30)
+-------------------
+
+- Support throttling for debug traces (#274) <Isaac Hier>
+- Remove dependency on Apache Thrift (#303) <Yuri Shkuro>
+- Remove dependency on tchannel (#295) (#294) <Yuri Shkuro>
+- Test with Go 1.9 (#298) <Yuri Shkuro>
+
+
+2.13.0 (2018-04-15)
+-------------------
+
+- Use value receiver for config.NewTracer() (#283) <Yuri Shkuro>
+- Lock span during jaeger thrift conversion (#273) <Won Jun Jang>
+- Fix the RemotelyControlledSampler so that it terminates go-routine on Close() (#260) <Scott Kidder> <Yuri Shkuro>
+- Added support for client configuration via env vars (#275) <Juraci Paixão Kröhling>
+- Allow overriding sampler in the Config (#270) <Mike Kabischev>
+
+
+2.12.0 (2018-03-14)
+-------------------
+
+- Use lock when retrieving span.Context() (#268)
+- Add Configuration support for custom Injector and Extractor (#263) <Martin Liu>
+
+
+2.11.2 (2018-01-12)
+-------------------
+
+- Add Gopkg.toml to allow using the lib with `dep`
+
+
+2.11.1 (2018-01-03)
+-------------------
+
+- Do not enqueue spans after Reporter is closed (#235, #245)
+- Change default flush interval to 1sec (#243)
+
+
+2.11.0 (2017-11-27)
+-------------------
+
+- Normalize metric names and tags to be compatible with Prometheus (#222)
+
+
+2.10.0 (2017-11-14)
+-------------------
+
+- Support custom tracing headers (#176)
+- Add BaggageRestrictionManager (#178) and RemoteBaggageRestrictionManager (#182)
+- Do not coerce baggage keys to lower case (#196)
+- Log span name when span cannot be reported (#198)
+- Add option to enable gen128Bit for tracer (#193) and allow custom generator for high bits of trace ID (#219)
+
+
+2.9.0 (2017-07-29)
+------------------
+
+- Pin thrift <= 0.10 (#179)
+- Introduce a parallel interface ContribObserver (#159)
+
+
+2.8.0 (2017-07-05)
+------------------
+
+- Drop `jaeger.` prefix from `jaeger.hostname` process-level tag
+- Add options to set tracer tags
+
+
+2.7.0 (2017-06-21)
+------------------
+
+- Fix rate limiter balance [#135](https://github.com/uber/jaeger-client-go/pull/135) [#140](https://github.com/uber/jaeger-client-go/pull/140)
+- Default client to send Jaeger.thrift [#147](https://github.com/uber/jaeger-client-go/pull/147)
+- Save baggage in span [#153](https://github.com/uber/jaeger-client-go/pull/153)
+- Move reporter.queueLength to the top of the struct to guarantee 64bit alignment [#158](https://github.com/uber/jaeger-client-go/pull/158)
+- Support HTTP transport with jaeger.thrift [#161](https://github.com/uber/jaeger-client-go/pull/161)
+
+
+2.6.0 (2017-03-28)
+------------------
+
+- Add config option to initialize RPC Metrics feature
+
+
+2.5.0 (2017-03-23)
+------------------
+
+- Split request latency metric by success/failure [#123](https://github.com/uber/jaeger-client-go/pull/123)
+- Add mutex to adaptive sampler and fix race condition [#124](https://github.com/uber/jaeger-client-go/pull/124)
+- Fix rate limiter panic [#125](https://github.com/uber/jaeger-client-go/pull/125)
+
+
+2.4.0 (2017-03-21)
+------------------
+
+- Remove `_ms` suffix from request latency metric name [#121](https://github.com/uber/jaeger-client-go/pull/121)
+- Rename all metrics to "request" and "http_request" and use tags for other dimensions [#121](https://github.com/uber/jaeger-client-go/pull/121)
+
+
+2.3.0 (2017-03-20)
+------------------
+
+- Make Span type public to allow access to non-std methods for testing [#117](https://github.com/uber/jaeger-client-go/pull/117)
+- Add a structured way to extract traces for logging with zap [#118](https://github.com/uber/jaeger-client-go/pull/118)
+
+
+2.2.1 (2017-03-14)
+------------------
+
+- Fix panic caused by updating the remote sampler from adaptive sampler to any other sampler type (https://github.com/uber/jaeger-client-go/pull/111)
+
+
+2.2.0 (2017-03-10)
+------------------
+
+- Introduce Observer and SpanObserver (https://github.com/uber/jaeger-client-go/pull/94)
+- Add RPC metrics emitter as Observer/SpanObserver (https://github.com/uber/jaeger-client-go/pull/103)
+
+
+2.1.2 (2017-02-27)
+-------------------
+
+- Fix leaky bucket bug (https://github.com/uber/jaeger-client-go/pull/99)
+- Fix zap logger Infof (https://github.com/uber/jaeger-client-go/pull/100)
+- Add tracer initialization godoc examples
+
+
+2.1.1 (2017-02-21)
+-------------------
+
+- Fix inefficient usage of zap.Logger
+
+
+2.1.0 (2017-02-17)
+-------------------
+
+- Add adapter for zap.Logger (https://github.com/uber-go/zap)
+- Move logging API to ./log/ package
+
+
+2.0.0 (2017-02-08)
+-------------------
+
+- Support Adaptive Sampling
+- Support 128bit Trace IDs
+- Change trace/span IDs from uint64 to strong types TraceID and SpanID
+- Add Zipkin HTTP B3 Propagation format support #72
+- Rip out existing metrics and use github.com/uber/jaeger-lib/metrics
+- Change API for tracer, reporter, sampler initialization
+
+
+1.6.0 (2016-10-14)
+-------------------
+
+- Add Zipkin HTTP transport
+- Support external baggage via jaeger-baggage header
+- Unpin Thrift version, keep to master
+
+
+1.5.1 (2016-09-27)
+-------------------
+
+- Relax dependency on opentracing to ^1
+
+
+1.5.0 (2016-09-27)
+-------------------
+
+- Upgrade to opentracing-go 1.0
+- Support KV logging for Spans
+
+
+1.4.0 (2016-09-14)
+-------------------
+
+- Support debug traces via HTTP header "jaeger-debug-id"
diff --git a/vendor/github.com/uber/jaeger-client-go/CONTRIBUTING.md b/vendor/github.com/uber/jaeger-client-go/CONTRIBUTING.md
new file mode 100644
index 000000000..7cf014a51
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/CONTRIBUTING.md
@@ -0,0 +1,170 @@
+# How to Contribute to Jaeger
+
+We'd love your help!
+
+Jaeger is [Apache 2.0 licensed](LICENSE) and accepts contributions via GitHub
+pull requests. This document outlines some of the conventions on development
+workflow, commit message formatting, contact points and other resources to make
+it easier to get your contribution accepted.
+
+We gratefully welcome improvements to documentation as well as to code.
+
+# Certificate of Origin
+
+By contributing to this project you agree to the [Developer Certificate of
+Origin](https://developercertificate.org/) (DCO). This document was created
+by the Linux Kernel community and is a simple statement that you, as a
+contributor, have the legal right to make the contribution. See the [DCO](DCO)
+file for details.
+
+## Getting Started
+
+This library uses [glide](https://github.com/Masterminds/glide) to manage dependencies.
+
+To get started, make sure you clone the Git repository into the correct location
+`github.com/uber/jaeger-client-go` relative to `$GOPATH`:
+
+```
+mkdir -p $GOPATH/src/github.com/uber
+cd $GOPATH/src/github.com/uber
+git clone git@github.com:jaegertracing/jaeger-client-go.git jaeger-client-go
+cd jaeger-client-go
+```
+
+Then install dependencies and run the tests:
+
+```
+git submodule update --init --recursive
+glide install
+make test
+```
+
+## Imports grouping
+
+This projects follows the following pattern for grouping imports in Go files:
+ * imports from standard library
+ * imports from other projects
+ * imports from `jaeger-client-go` project
+
+For example:
+
+```go
+import (
+ "fmt"
+
+ "github.com/uber/jaeger-lib/metrics"
+ "go.uber.org/zap"
+
+ "github.com/uber/jaeger-client-go/config"
+)
+```
+
+## Making A Change
+
+*Before making any significant changes, please [open an
+issue](https://github.com/jaegertracing/jaeger-client-go/issues).* Discussing your proposed
+changes ahead of time will make the contribution process smooth for everyone.
+
+Once we've discussed your changes and you've got your code ready, make sure
+that tests are passing (`make test` or `make cover`) and open your PR. Your
+pull request is most likely to be accepted if it:
+
+* Includes tests for new functionality.
+* Follows the guidelines in [Effective
+ Go](https://golang.org/doc/effective_go.html) and the [Go team's common code
+ review comments](https://github.com/golang/go/wiki/CodeReviewComments).
+* Has a [good commit message](https://chris.beams.io/posts/git-commit/):
+ * Separate subject from body with a blank line
+ * Limit the subject line to 50 characters
+ * Capitalize the subject line
+ * Do not end the subject line with a period
+ * Use the imperative mood in the subject line
+ * Wrap the body at 72 characters
+ * Use the body to explain _what_ and _why_ instead of _how_
+* Each commit must be signed by the author ([see below](#sign-your-work)).
+
+## License
+
+By contributing your code, you agree to license your contribution under the terms
+of the [Apache License](LICENSE).
+
+If you are adding a new file it should have a header like below. The easiest
+way to add such header is to run `make fmt`.
+
+```
+// Copyright (c) 2017 The Jaeger Authors.
+//
+// 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.
+```
+
+## Sign your work
+
+The sign-off is a simple line at the end of the explanation for the
+patch, which certifies that you wrote it or otherwise have the right to
+pass it on as an open-source patch. The rules are pretty simple: if you
+can certify the below (from
+[developercertificate.org](http://developercertificate.org/)):
+
+```
+Developer Certificate of Origin
+Version 1.1
+
+Copyright (C) 2004, 2006 The Linux Foundation and its contributors.
+660 York Street, Suite 102,
+San Francisco, CA 94110 USA
+
+Everyone is permitted to copy and distribute verbatim copies of this
+license document, but changing it is not allowed.
+
+
+Developer's Certificate of Origin 1.1
+
+By making a contribution to this project, I certify that:
+
+(a) The contribution was created in whole or in part by me and I
+ have the right to submit it under the open source license
+ indicated in the file; or
+
+(b) The contribution is based upon previous work that, to the best
+ of my knowledge, is covered under an appropriate open source
+ license and I have the right under that license to submit that
+ work with modifications, whether created in whole or in part
+ by me, under the same open source license (unless I am
+ permitted to submit under a different license), as indicated
+ in the file; or
+
+(c) The contribution was provided directly to me by some other
+ person who certified (a), (b) or (c) and I have not modified
+ it.
+
+(d) I understand and agree that this project and the contribution
+ are public and that a record of the contribution (including all
+ personal information I submit with it, including my sign-off) is
+ maintained indefinitely and may be redistributed consistent with
+ this project or the open source license(s) involved.
+```
+
+then you just add a line to every git commit message:
+
+ Signed-off-by: Joe Smith <joe@gmail.com>
+
+using your real name (sorry, no pseudonyms or anonymous contributions.)
+
+You can add the sign off when creating the git commit via `git commit -s`.
+
+If you want this to be automatic you can set up some aliases:
+
+```
+git config --add alias.amend "commit -s --amend"
+git config --add alias.c "commit -s"
+```
diff --git a/vendor/github.com/uber/jaeger-client-go/DCO b/vendor/github.com/uber/jaeger-client-go/DCO
new file mode 100644
index 000000000..068953d4b
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/DCO
@@ -0,0 +1,37 @@
+Developer Certificate of Origin
+Version 1.1
+
+Copyright (C) 2004, 2006 The Linux Foundation and its contributors.
+660 York Street, Suite 102,
+San Francisco, CA 94110 USA
+
+Everyone is permitted to copy and distribute verbatim copies of this
+license document, but changing it is not allowed.
+
+
+Developer's Certificate of Origin 1.1
+
+By making a contribution to this project, I certify that:
+
+(a) The contribution was created in whole or in part by me and I
+ have the right to submit it under the open source license
+ indicated in the file; or
+
+(b) The contribution is based upon previous work that, to the best
+ of my knowledge, is covered under an appropriate open source
+ license and I have the right under that license to submit that
+ work with modifications, whether created in whole or in part
+ by me, under the same open source license (unless I am
+ permitted to submit under a different license), as indicated
+ in the file; or
+
+(c) The contribution was provided directly to me by some other
+ person who certified (a), (b) or (c) and I have not modified
+ it.
+
+(d) I understand and agree that this project and the contribution
+ are public and that a record of the contribution (including all
+ personal information I submit with it, including my sign-off) is
+ maintained indefinitely and may be redistributed consistent with
+ this project or the open source license(s) involved.
+
diff --git a/vendor/github.com/uber/jaeger-client-go/Gopkg.lock b/vendor/github.com/uber/jaeger-client-go/Gopkg.lock
new file mode 100644
index 000000000..ec054c6ed
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/Gopkg.lock
@@ -0,0 +1,164 @@
+# This file is autogenerated, do not edit; changes may be undone by the next 'dep ensure'.
+
+
+[[projects]]
+ branch = "master"
+ name = "github.com/beorn7/perks"
+ packages = ["quantile"]
+ revision = "3a771d992973f24aa725d07868b467d1ddfceafb"
+
+[[projects]]
+ branch = "master"
+ name = "github.com/codahale/hdrhistogram"
+ packages = ["."]
+ revision = "3a0bb77429bd3a61596f5e8a3172445844342120"
+
+[[projects]]
+ branch = "master"
+ name = "github.com/crossdock/crossdock-go"
+ packages = [
+ ".",
+ "assert",
+ "require"
+ ]
+ revision = "049aabb0122b03bc9bd30cab8f3f91fb60166361"
+
+[[projects]]
+ name = "github.com/davecgh/go-spew"
+ packages = ["spew"]
+ revision = "346938d642f2ec3594ed81d874461961cd0faa76"
+ version = "v1.1.0"
+
+[[projects]]
+ name = "github.com/golang/protobuf"
+ packages = ["proto"]
+ revision = "925541529c1fa6821df4e44ce2723319eb2be768"
+ version = "v1.0.0"
+
+[[projects]]
+ name = "github.com/matttproud/golang_protobuf_extensions"
+ packages = ["pbutil"]
+ revision = "3247c84500bff8d9fb6d579d800f20b3e091582c"
+ version = "v1.0.0"
+
+[[projects]]
+ name = "github.com/opentracing/opentracing-go"
+ packages = [
+ ".",
+ "ext",
+ "log"
+ ]
+ revision = "1949ddbfd147afd4d964a9f00b24eb291e0e7c38"
+ version = "v1.0.2"
+
+[[projects]]
+ name = "github.com/pkg/errors"
+ packages = ["."]
+ revision = "645ef00459ed84a119197bfb8d8205042c6df63d"
+ version = "v0.8.0"
+
+[[projects]]
+ name = "github.com/pmezard/go-difflib"
+ packages = ["difflib"]
+ revision = "792786c7400a136282c1664665ae0a8db921c6c2"
+ version = "v1.0.0"
+
+[[projects]]
+ name = "github.com/prometheus/client_golang"
+ packages = ["prometheus"]
+ revision = "c5b7fccd204277076155f10851dad72b76a49317"
+ version = "v0.8.0"
+
+[[projects]]
+ branch = "master"
+ name = "github.com/prometheus/client_model"
+ packages = ["go"]
+ revision = "99fa1f4be8e564e8a6b613da7fa6f46c9edafc6c"
+
+[[projects]]
+ branch = "master"
+ name = "github.com/prometheus/common"
+ packages = [
+ "expfmt",
+ "internal/bitbucket.org/ww/goautoneg",
+ "model"
+ ]
+ revision = "d811d2e9bf898806ecfb6ef6296774b13ffc314c"
+
+[[projects]]
+ branch = "master"
+ name = "github.com/prometheus/procfs"
+ packages = [
+ ".",
+ "internal/util",
+ "nfs",
+ "xfs"
+ ]
+ revision = "8b1c2da0d56deffdbb9e48d4414b4e674bd8083e"
+
+[[projects]]
+ name = "github.com/stretchr/testify"
+ packages = [
+ "assert",
+ "require",
+ "suite"
+ ]
+ revision = "12b6f73e6084dad08a7c6e575284b177ecafbc71"
+ version = "v1.2.1"
+
+[[projects]]
+ name = "github.com/uber-go/atomic"
+ packages = ["."]
+ revision = "8474b86a5a6f79c443ce4b2992817ff32cf208b8"
+ version = "v1.3.1"
+
+[[projects]]
+ name = "github.com/uber/jaeger-lib"
+ packages = [
+ "metrics",
+ "metrics/prometheus",
+ "metrics/testutils"
+ ]
+ revision = "4267858c0679cd4e47cefed8d7f70fd386cfb567"
+ version = "v1.4.0"
+
+[[projects]]
+ name = "go.uber.org/atomic"
+ packages = ["."]
+ revision = "54f72d32435d760d5604f17a82e2435b28dc4ba5"
+ version = "v1.3.0"
+
+[[projects]]
+ name = "go.uber.org/multierr"
+ packages = ["."]
+ revision = "3c4937480c32f4c13a875a1829af76c98ca3d40a"
+ version = "v1.1.0"
+
+[[projects]]
+ name = "go.uber.org/zap"
+ packages = [
+ ".",
+ "buffer",
+ "internal/bufferpool",
+ "internal/color",
+ "internal/exit",
+ "zapcore"
+ ]
+ revision = "eeedf312bc6c57391d84767a4cd413f02a917974"
+ version = "v1.8.0"
+
+[[projects]]
+ branch = "master"
+ name = "golang.org/x/net"
+ packages = [
+ "context",
+ "context/ctxhttp"
+ ]
+ revision = "5f9ae10d9af5b1c89ae6904293b14b064d4ada23"
+
+[solve-meta]
+ analyzer-name = "dep"
+ analyzer-version = 1
+ inputs-digest = "f9dcfaf37a785c5dac1e20c29605eda29a83ba9c6f8842e92960dc94c8c4ff80"
+ solver-name = "gps-cdcl"
+ solver-version = 1
diff --git a/vendor/github.com/uber/jaeger-client-go/Gopkg.toml b/vendor/github.com/uber/jaeger-client-go/Gopkg.toml
new file mode 100644
index 000000000..baf7a6bdf
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/Gopkg.toml
@@ -0,0 +1,27 @@
+[[constraint]]
+ name = "github.com/crossdock/crossdock-go"
+ branch = "master"
+
+[[constraint]]
+ name = "github.com/opentracing/opentracing-go"
+ version = "^1"
+
+[[constraint]]
+ name = "github.com/prometheus/client_golang"
+ version = "0.8.0"
+
+[[constraint]]
+ name = "github.com/stretchr/testify"
+ version = "^1.1.3"
+
+[[constraint]]
+ name = "github.com/uber-go/atomic"
+ version = "^1"
+
+[[constraint]]
+ name = "github.com/uber/jaeger-lib"
+ version = "^1.3"
+
+[[constraint]]
+ name = "go.uber.org/zap"
+ version = "^1"
diff --git a/vendor/github.com/uber/jaeger-client-go/LICENSE b/vendor/github.com/uber/jaeger-client-go/LICENSE
new file mode 100644
index 000000000..261eeb9e9
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/LICENSE
@@ -0,0 +1,201 @@
+ Apache License
+ Version 2.0, January 2004
+ http://www.apache.org/licenses/
+
+ TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
+
+ 1. Definitions.
+
+ "License" shall mean the terms and conditions for use, reproduction,
+ and distribution as defined by Sections 1 through 9 of this document.
+
+ "Licensor" shall mean the copyright owner or entity authorized by
+ the copyright owner that is granting the License.
+
+ "Legal Entity" shall mean the union of the acting entity and all
+ other entities that control, are controlled by, or are under common
+ control with that entity. For the purposes of this definition,
+ "control" means (i) the power, direct or indirect, to cause the
+ direction or management of such entity, whether by contract or
+ otherwise, or (ii) ownership of fifty percent (50%) or more of the
+ outstanding shares, or (iii) beneficial ownership of such entity.
+
+ "You" (or "Your") shall mean an individual or Legal Entity
+ exercising permissions granted by this License.
+
+ "Source" form shall mean the preferred form for making modifications,
+ including but not limited to software source code, documentation
+ source, and configuration files.
+
+ "Object" form shall mean any form resulting from mechanical
+ transformation or translation of a Source form, including but
+ not limited to compiled object code, generated documentation,
+ and conversions to other media types.
+
+ "Work" shall mean the work of authorship, whether in Source or
+ Object form, made available under the License, as indicated by a
+ copyright notice that is included in or attached to the work
+ (an example is provided in the Appendix below).
+
+ "Derivative Works" shall mean any work, whether in Source or Object
+ form, that is based on (or derived from) the Work and for which the
+ editorial revisions, annotations, elaborations, or other modifications
+ represent, as a whole, an original work of authorship. For the purposes
+ of this License, Derivative Works shall not include works that remain
+ separable from, or merely link (or bind by name) to the interfaces of,
+ the Work and Derivative Works thereof.
+
+ "Contribution" shall mean any work of authorship, including
+ the original version of the Work and any modifications or additions
+ to that Work or Derivative Works thereof, that is intentionally
+ submitted to Licensor for inclusion in the Work by the copyright owner
+ or by an individual or Legal Entity authorized to submit on behalf of
+ the copyright owner. For the purposes of this definition, "submitted"
+ means any form of electronic, verbal, or written communication sent
+ to the Licensor or its representatives, including but not limited to
+ communication on electronic mailing lists, source code control systems,
+ and issue tracking systems that are managed by, or on behalf of, the
+ Licensor for the purpose of discussing and improving the Work, but
+ excluding communication that is conspicuously marked or otherwise
+ designated in writing by the copyright owner as "Not a Contribution."
+
+ "Contributor" shall mean Licensor and any individual or Legal Entity
+ on behalf of whom a Contribution has been received by Licensor and
+ subsequently incorporated within the Work.
+
+ 2. Grant of Copyright License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ copyright license to reproduce, prepare Derivative Works of,
+ publicly display, publicly perform, sublicense, and distribute the
+ Work and such Derivative Works in Source or Object form.
+
+ 3. Grant of Patent License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ (except as stated in this section) patent license to make, have made,
+ use, offer to sell, sell, import, and otherwise transfer the Work,
+ where such license applies only to those patent claims licensable
+ by such Contributor that are necessarily infringed by their
+ Contribution(s) alone or by combination of their Contribution(s)
+ with the Work to which such Contribution(s) was submitted. If You
+ institute patent litigation against any entity (including a
+ cross-claim or counterclaim in a lawsuit) alleging that the Work
+ or a Contribution incorporated within the Work constitutes direct
+ or contributory patent infringement, then any patent licenses
+ granted to You under this License for that Work shall terminate
+ as of the date such litigation is filed.
+
+ 4. Redistribution. You may reproduce and distribute copies of the
+ Work or Derivative Works thereof in any medium, with or without
+ modifications, and in Source or Object form, provided that You
+ meet the following conditions:
+
+ (a) You must give any other recipients of the Work or
+ Derivative Works a copy of this License; and
+
+ (b) You must cause any modified files to carry prominent notices
+ stating that You changed the files; and
+
+ (c) You must retain, in the Source form of any Derivative Works
+ that You distribute, all copyright, patent, trademark, and
+ attribution notices from the Source form of the Work,
+ excluding those notices that do not pertain to any part of
+ the Derivative Works; and
+
+ (d) If the Work includes a "NOTICE" text file as part of its
+ distribution, then any Derivative Works that You distribute must
+ include a readable copy of the attribution notices contained
+ within such NOTICE file, excluding those notices that do not
+ pertain to any part of the Derivative Works, in at least one
+ of the following places: within a NOTICE text file distributed
+ as part of the Derivative Works; within the Source form or
+ documentation, if provided along with the Derivative Works; or,
+ within a display generated by the Derivative Works, if and
+ wherever such third-party notices normally appear. The contents
+ of the NOTICE file are for informational purposes only and
+ do not modify the License. You may add Your own attribution
+ notices within Derivative Works that You distribute, alongside
+ or as an addendum to the NOTICE text from the Work, provided
+ that such additional attribution notices cannot be construed
+ as modifying the License.
+
+ You may add Your own copyright statement to Your modifications and
+ may provide additional or different license terms and conditions
+ for use, reproduction, or distribution of Your modifications, or
+ for any such Derivative Works as a whole, provided Your use,
+ reproduction, and distribution of the Work otherwise complies with
+ the conditions stated in this License.
+
+ 5. Submission of Contributions. Unless You explicitly state otherwise,
+ any Contribution intentionally submitted for inclusion in the Work
+ by You to the Licensor shall be under the terms and conditions of
+ this License, without any additional terms or conditions.
+ Notwithstanding the above, nothing herein shall supersede or modify
+ the terms of any separate license agreement you may have executed
+ with Licensor regarding such Contributions.
+
+ 6. Trademarks. This License does not grant permission to use the trade
+ names, trademarks, service marks, or product names of the Licensor,
+ except as required for reasonable and customary use in describing the
+ origin of the Work and reproducing the content of the NOTICE file.
+
+ 7. Disclaimer of Warranty. Unless required by applicable law or
+ agreed to in writing, Licensor provides the Work (and each
+ Contributor provides its Contributions) on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
+ implied, including, without limitation, any warranties or conditions
+ of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
+ PARTICULAR PURPOSE. You are solely responsible for determining the
+ appropriateness of using or redistributing the Work and assume any
+ risks associated with Your exercise of permissions under this License.
+
+ 8. Limitation of Liability. In no event and under no legal theory,
+ whether in tort (including negligence), contract, or otherwise,
+ unless required by applicable law (such as deliberate and grossly
+ negligent acts) or agreed to in writing, shall any Contributor be
+ liable to You for damages, including any direct, indirect, special,
+ incidental, or consequential damages of any character arising as a
+ result of this License or out of the use or inability to use the
+ Work (including but not limited to damages for loss of goodwill,
+ work stoppage, computer failure or malfunction, or any and all
+ other commercial damages or losses), even if such Contributor
+ has been advised of the possibility of such damages.
+
+ 9. Accepting Warranty or Additional Liability. While redistributing
+ the Work or Derivative Works thereof, You may choose to offer,
+ and charge a fee for, acceptance of support, warranty, indemnity,
+ or other liability obligations and/or rights consistent with this
+ License. However, in accepting such obligations, You may act only
+ on Your own behalf and on Your sole responsibility, not on behalf
+ of any other Contributor, and only if You agree to indemnify,
+ defend, and hold each Contributor harmless for any liability
+ incurred by, or claims asserted against, such Contributor by reason
+ of your accepting any such warranty or additional liability.
+
+ END OF TERMS AND CONDITIONS
+
+ APPENDIX: How to apply the Apache License to your work.
+
+ To apply the Apache License to your work, attach the following
+ boilerplate notice, with the fields enclosed by brackets "[]"
+ replaced with your own identifying information. (Don't include
+ the brackets!) The text should be enclosed in the appropriate
+ comment syntax for the file format. We also recommend that a
+ file or class name and description of purpose be included on the
+ same "printed page" as the copyright notice for easier
+ identification within third-party archives.
+
+ Copyright [yyyy] [name of copyright owner]
+
+ 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.
diff --git a/vendor/github.com/uber/jaeger-client-go/Makefile b/vendor/github.com/uber/jaeger-client-go/Makefile
new file mode 100644
index 000000000..cbcc1faf4
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/Makefile
@@ -0,0 +1,117 @@
+PROJECT_ROOT=github.com/uber/jaeger-client-go
+PACKAGES := $(shell glide novendor | grep -v -e ./thrift-gen/... -e ./thrift/...)
+# all .go files that don't exist in hidden directories
+ALL_SRC := $(shell find . -name "*.go" | grep -v -e vendor -e thrift-gen -e ./thrift/ \
+ -e ".*/\..*" \
+ -e ".*/_.*" \
+ -e ".*/mocks.*")
+
+-include crossdock/rules.mk
+
+export GO15VENDOREXPERIMENT=1
+
+RACE=-race
+GOTEST=go test -v $(RACE)
+GOLINT=golint
+GOVET=go vet
+GOFMT=gofmt
+FMT_LOG=fmt.log
+LINT_LOG=lint.log
+
+THRIFT_VER=0.9.3
+THRIFT_IMG=thrift:$(THRIFT_VER)
+THRIFT=docker run -v "${PWD}:/data" $(THRIFT_IMG) thrift
+THRIFT_GO_ARGS=thrift_import="github.com/apache/thrift/lib/go/thrift"
+THRIFT_GEN_DIR=thrift-gen
+
+PASS=$(shell printf "\033[32mPASS\033[0m")
+FAIL=$(shell printf "\033[31mFAIL\033[0m")
+COLORIZE=sed ''/PASS/s//$(PASS)/'' | sed ''/FAIL/s//$(FAIL)/''
+
+.DEFAULT_GOAL := test-and-lint
+
+.PHONY: test-and-lint
+test-and-lint: test fmt lint
+
+.PHONY: test
+test:
+ bash -c "set -e; set -o pipefail; $(GOTEST) $(PACKAGES) | $(COLORIZE)"
+
+.PHONY: fmt
+fmt:
+ $(GOFMT) -e -s -l -w $(ALL_SRC)
+ ./scripts/updateLicenses.sh
+
+.PHONY: lint
+lint:
+ $(GOVET) $(PACKAGES)
+ @cat /dev/null > $(LINT_LOG)
+ @$(foreach pkg, $(PACKAGES), $(GOLINT) $(pkg) | grep -v crossdock/thrift >> $(LINT_LOG) || true;)
+ @[ ! -s "$(LINT_LOG)" ] || (echo "Lint Failures" | cat - $(LINT_LOG) && false)
+ @$(GOFMT) -e -s -l $(ALL_SRC) > $(FMT_LOG)
+ ./scripts/updateLicenses.sh >> $(FMT_LOG)
+ @[ ! -s "$(FMT_LOG)" ] || (echo "go fmt or license check failures, run 'make fmt'" | cat - $(FMT_LOG) && false)
+
+
+.PHONY: install
+install:
+ glide --version || go get github.com/Masterminds/glide
+ifeq ($(USE_DEP),true)
+ dep ensure
+else
+ glide install
+endif
+
+
+.PHONY: cover
+cover:
+ ./scripts/cover.sh $(shell go list $(PACKAGES))
+ go tool cover -html=cover.out -o cover.html
+
+
+# This is not part of the regular test target because we don't want to slow it
+# down.
+.PHONY: test-examples
+test-examples:
+ make -C examples
+
+# TODO at the moment we're not generating tchan_*.go files
+thrift: idl-submodule thrift-image
+ $(THRIFT) -o /data --gen go:$(THRIFT_GO_ARGS) --out /data/$(THRIFT_GEN_DIR) /data/idl/thrift/agent.thrift
+ $(THRIFT) -o /data --gen go:$(THRIFT_GO_ARGS) --out /data/$(THRIFT_GEN_DIR) /data/idl/thrift/sampling.thrift
+ $(THRIFT) -o /data --gen go:$(THRIFT_GO_ARGS) --out /data/$(THRIFT_GEN_DIR) /data/idl/thrift/jaeger.thrift
+ $(THRIFT) -o /data --gen go:$(THRIFT_GO_ARGS) --out /data/$(THRIFT_GEN_DIR) /data/idl/thrift/zipkincore.thrift
+ $(THRIFT) -o /data --gen go:$(THRIFT_GO_ARGS) --out /data/$(THRIFT_GEN_DIR) /data/idl/thrift/baggage.thrift
+ $(THRIFT) -o /data --gen go:$(THRIFT_GO_ARGS) --out /data/crossdock/thrift/ /data/idl/thrift/crossdock/tracetest.thrift
+ sed -i '' 's|"zipkincore"|"$(PROJECT_ROOT)/thrift-gen/zipkincore"|g' $(THRIFT_GEN_DIR)/agent/*.go
+ sed -i '' 's|"jaeger"|"$(PROJECT_ROOT)/thrift-gen/jaeger"|g' $(THRIFT_GEN_DIR)/agent/*.go
+ sed -i '' 's|"github.com/apache/thrift/lib/go/thrift"|"github.com/uber/jaeger-client-go/thrift"|g' \
+ $(THRIFT_GEN_DIR)/*/*.go crossdock/thrift/tracetest/*.go
+ rm -rf thrift-gen/*/*-remote
+ rm -rf crossdock/thrift/*/*-remote
+ rm -rf thrift-gen/jaeger/collector.go
+
+idl-submodule:
+ git submodule init
+ git submodule update
+
+thrift-image:
+ $(THRIFT) -version
+
+.PHONY: install-dep-ci
+install-dep-ci:
+ - curl -L -s https://github.com/golang/dep/releases/download/v0.3.2/dep-linux-amd64 -o $$GOPATH/bin/dep
+ - chmod +x $$GOPATH/bin/dep
+
+.PHONY: install-ci
+install-ci: install-dep-ci install
+ go get github.com/wadey/gocovmerge
+ go get github.com/mattn/goveralls
+ go get golang.org/x/tools/cmd/cover
+ go get golang.org/x/lint/golint
+
+.PHONY: test-ci
+test-ci:
+ @./scripts/cover.sh $(shell go list $(PACKAGES))
+ make lint
+
diff --git a/vendor/github.com/uber/jaeger-client-go/README.md b/vendor/github.com/uber/jaeger-client-go/README.md
new file mode 100644
index 000000000..6d9546e5b
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/README.md
@@ -0,0 +1,270 @@
+[![GoDoc][doc-img]][doc] [![Build Status][ci-img]][ci] [![Coverage Status][cov-img]][cov] [![OpenTracing 1.0 Enabled][ot-img]][ot-url]
+
+# Jaeger Bindings for Go OpenTracing API
+
+Instrumentation library that implements an
+[OpenTracing](http://opentracing.io) Tracer for Jaeger (https://jaegertracing.io).
+
+**IMPORTANT**: The library's import path is based on its original location under `github.com/uber`. Do not try to import it as `github.com/jaegertracing`, it will not compile. We might revisit this in the next major release.
+ * :white_check_mark: `import "github.com/uber/jaeger-client-go"`
+ * :x: `import "github.com/jaegertracing/jaeger-client-go"`
+
+## How to Contribute
+
+Please see [CONTRIBUTING.md](CONTRIBUTING.md).
+
+## Installation
+
+We recommended using a dependency manager like [glide](https://github.com/Masterminds/glide)
+and [semantic versioning](http://semver.org/) when including this library into an application.
+For example, Jaeger backend imports this library like this:
+
+```yaml
+- package: github.com/uber/jaeger-client-go
+ version: ^2.7.0
+```
+
+If you instead want to use the latest version in `master`, you can pull it via `go get`.
+Note that during `go get` you may see build errors due to incompatible dependencies, which is why
+we recommend using semantic versions for dependencies. The error may be fixed by running
+`make install` (it will install `glide` if you don't have it):
+
+```shell
+go get -u github.com/uber/jaeger-client-go/
+cd $GOPATH/src/github.com/uber/jaeger-client-go/
+git submodule update --init --recursive
+make install
+```
+
+## Initialization
+
+See tracer initialization examples in [godoc](https://godoc.org/github.com/uber/jaeger-client-go/config#pkg-examples)
+and [config/example_test.go](./config/example_test.go).
+
+### Environment variables
+
+The tracer can be initialized with values coming from environment variables. None of the env vars are required
+and all of them can be overriden via direct setting of the property on the configuration object.
+
+Property| Description
+--- | ---
+JAEGER_SERVICE_NAME | The service name
+JAEGER_AGENT_HOST | The hostname for communicating with agent via UDP
+JAEGER_AGENT_PORT | The port for communicating with agent via UDP
+JAEGER_ENDPOINT | The HTTP endpoint for sending spans directly to a collector, i.e. http://jaeger-collector:14268/api/traces
+JAEGER_USER | Username to send as part of "Basic" authentication to the collector endpoint
+JAEGER_PASSWORD | Password to send as part of "Basic" authentication to the collector endpoint
+JAEGER_REPORTER_LOG_SPANS | Whether the reporter should also log the spans
+JAEGER_REPORTER_MAX_QUEUE_SIZE | The reporter's maximum queue size
+JAEGER_REPORTER_FLUSH_INTERVAL | The reporter's flush interval, with units, e.g. "500ms" or "2s" ([valid units][timeunits])
+JAEGER_SAMPLER_TYPE | The sampler type
+JAEGER_SAMPLER_PARAM | The sampler parameter (number)
+JAEGER_SAMPLER_MANAGER_HOST_PORT | The HTTP endpoint when using the remote sampler, i.e. http://jaeger-agent:5778/sampling
+JAEGER_SAMPLER_MAX_OPERATIONS | The maximum number of operations that the sampler will keep track of
+JAEGER_SAMPLER_REFRESH_INTERVAL | How often the remotely controlled sampler will poll jaeger-agent for the appropriate sampling strategy, with units, e.g. "1m" or "30s" ([valid units][timeunits])
+JAEGER_TAGS | A comma separated list of `name = value` tracer level tags, which get added to all reported spans. The value can also refer to an environment variable using the format `${envVarName:default}`, where the `:default` is optional, and identifies a value to be used if the environment variable cannot be found
+JAEGER_DISABLED | Whether the tracer is disabled or not. If true, the default `opentracing.NoopTracer` is used.
+JAEGER_RPC_METRICS | Whether to store RPC metrics
+
+By default, the client sends traces via UDP to the agent at `localhost:6831`. Use `JAEGER_AGENT_HOST` and
+`JAEGER_AGENT_PORT` to send UDP traces to a different `host:port`. If `JAEGER_ENDPOINT` is set, the client sends traces
+to the endpoint via `HTTP`, making the `JAEGER_AGENT_HOST` and `JAEGER_AGENT_PORT` unused. If `JAEGER_ENDPOINT` is
+secured, HTTP basic authentication can be performed by setting the `JAEGER_USER` and `JAEGER_PASSWORD` environment
+variables.
+
+### Closing the tracer via `io.Closer`
+
+The constructor function for Jaeger Tracer returns the tracer itself and an `io.Closer` instance.
+It is recommended to structure your `main()` so that it calls the `Close()` function on the closer
+before exiting, e.g.
+
+```go
+tracer, closer, err := cfg.NewTracer(...)
+defer closer.Close()
+```
+
+This is especially useful for command-line tools that enable tracing, as well as
+for the long-running apps that support graceful shutdown. For example, if your deployment
+system sends SIGTERM instead of killing the process and you trap that signal to do a graceful
+exit, then having `defer closer.Closer()` ensures that all buffered spans are flushed.
+
+### Metrics & Monitoring
+
+The tracer emits a number of different metrics, defined in
+[metrics.go](metrics.go). The monitoring backend is expected to support
+tag-based metric names, e.g. instead of `statsd`-style string names
+like `counters.my-service.jaeger.spans.started.sampled`, the metrics
+are defined by a short name and a collection of key/value tags, for
+example: `name:jaeger.traces, state:started, sampled:y`. See [metrics.go](./metrics.go)
+file for the full list and descriptions of emitted metrics.
+
+The monitoring backend is represented by the `metrics.Factory` interface from package
+[`"github.com/uber/jaeger-lib/metrics"`](https://github.com/jaegertracing/jaeger-lib/tree/master/metrics). An implementation
+of that interface can be passed as an option to either the Configuration object or the Tracer
+constructor, for example:
+
+```go
+import (
+ "github.com/uber/jaeger-client-go/config"
+ "github.com/uber/jaeger-lib/metrics/prometheus"
+)
+
+ metricsFactory := prometheus.New()
+ tracer, closer, err := config.Configuration{
+ ServiceName: "your-service-name",
+ }.NewTracer(
+ config.Metrics(metricsFactory),
+ )
+```
+
+By default, a no-op `metrics.NullFactory` is used.
+
+### Logging
+
+The tracer can be configured with an optional logger, which will be
+used to log communication errors, or log spans if a logging reporter
+option is specified in the configuration. The logging API is abstracted
+by the [Logger](logger.go) interface. A logger instance implementing
+this interface can be set on the `Config` object before calling the
+`New` method.
+
+Besides the [zap](https://github.com/uber-go/zap) implementation
+bundled with this package there is also a [go-kit](https://github.com/go-kit/kit)
+one in the [jaeger-lib](https://github.com/jaegertracing/jaeger-lib) repository.
+
+## Instrumentation for Tracing
+
+Since this tracer is fully compliant with OpenTracing API 1.0,
+all code instrumentation should only use the API itself, as described
+in the [opentracing-go](https://github.com/opentracing/opentracing-go) documentation.
+
+## Features
+
+### Reporters
+
+A "reporter" is a component that receives the finished spans and reports
+them to somewhere. Under normal circumstances, the Tracer
+should use the default `RemoteReporter`, which sends the spans out of
+process via configurable "transport". For testing purposes, one can
+use an `InMemoryReporter` that accumulates spans in a buffer and
+allows to retrieve them for later verification. Also available are
+`NullReporter`, a no-op reporter that does nothing, a `LoggingReporter`
+which logs all finished spans using their `String()` method, and a
+`CompositeReporter` that can be used to combine more than one reporter
+into one, e.g. to attach a logging reporter to the main remote reporter.
+
+### Span Reporting Transports
+
+The remote reporter uses "transports" to actually send the spans out
+of process. Currently the supported transports include:
+ * [Jaeger Thrift](https://github.com/jaegertracing/jaeger-idl/blob/master/thrift/agent.thrift) over UDP or HTTP,
+ * [Zipkin Thrift](https://github.com/jaegertracing/jaeger-idl/blob/master/thrift/zipkincore.thrift) over HTTP.
+
+### Sampling
+
+The tracer does not record all spans, but only those that have the
+sampling bit set in the `flags`. When a new trace is started and a new
+unique ID is generated, a sampling decision is made whether this trace
+should be sampled. The sampling decision is propagated to all downstream
+calls via the `flags` field of the trace context. The following samplers
+are available:
+ 1. `RemotelyControlledSampler` uses one of the other simpler samplers
+ and periodically updates it by polling an external server. This
+ allows dynamic control of the sampling strategies.
+ 1. `ConstSampler` always makes the same sampling decision for all
+ trace IDs. it can be configured to either sample all traces, or
+ to sample none.
+ 1. `ProbabilisticSampler` uses a fixed sampling rate as a probability
+ for a given trace to be sampled. The actual decision is made by
+ comparing the trace ID with a random number multiplied by the
+ sampling rate.
+ 1. `RateLimitingSampler` can be used to allow only a certain fixed
+ number of traces to be sampled per second.
+
+### Baggage Injection
+
+The OpenTracing spec allows for [baggage][baggage], which are key value pairs that are added
+to the span context and propagated throughout the trace. An external process can inject baggage
+by setting the special HTTP Header `jaeger-baggage` on a request:
+
+```sh
+curl -H "jaeger-baggage: key1=value1, key2=value2" http://myhost.com
+```
+
+Baggage can also be programatically set inside your service:
+
+```go
+if span := opentracing.SpanFromContext(ctx); span != nil {
+ span.SetBaggageItem("key", "value")
+}
+```
+
+Another service downstream of that can retrieve the baggage in a similar way:
+
+```go
+if span := opentracing.SpanFromContext(ctx); span != nil {
+ val := span.BaggageItem("key")
+ println(val)
+}
+```
+
+### Debug Traces (Forced Sampling)
+
+#### Programmatically
+
+The OpenTracing API defines a `sampling.priority` standard tag that
+can be used to affect the sampling of a span and its children:
+
+```go
+import (
+ "github.com/opentracing/opentracing-go"
+ "github.com/opentracing/opentracing-go/ext"
+)
+
+span := opentracing.SpanFromContext(ctx)
+ext.SamplingPriority.Set(span, 1)
+```
+
+#### Via HTTP Headers
+
+Jaeger Tracer also understands a special HTTP Header `jaeger-debug-id`,
+which can be set in the incoming request, e.g.
+
+```sh
+curl -H "jaeger-debug-id: some-correlation-id" http://myhost.com
+```
+
+When Jaeger sees this header in the request that otherwise has no
+tracing context, it ensures that the new trace started for this
+request will be sampled in the "debug" mode (meaning it should survive
+all downsampling that might happen in the collection pipeline), and the
+root span will have a tag as if this statement was executed:
+
+```go
+span.SetTag("jaeger-debug-id", "some-correlation-id")
+```
+
+This allows using Jaeger UI to find the trace by this tag.
+
+### Zipkin HTTP B3 compatible header propagation
+
+Jaeger Tracer supports Zipkin B3 Propagation HTTP headers, which are used
+by a lot of Zipkin tracers. This means that you can use Jaeger in conjunction with e.g. [these OpenZipkin tracers](https://github.com/openzipkin).
+
+However it is not the default propagation format, see [here](zipkin/README.md#NewZipkinB3HTTPHeaderPropagator) how to set it up.
+
+## License
+
+[Apache 2.0 License](LICENSE).
+
+
+[doc-img]: https://godoc.org/github.com/uber/jaeger-client-go?status.svg
+[doc]: https://godoc.org/github.com/uber/jaeger-client-go
+[ci-img]: https://travis-ci.org/jaegertracing/jaeger-client-go.svg?branch=master
+[ci]: https://travis-ci.org/jaegertracing/jaeger-client-go
+[cov-img]: https://codecov.io/gh/jaegertracing/jaeger-client-go/branch/master/graph/badge.svg
+[cov]: https://codecov.io/gh/jaegertracing/jaeger-client-go
+[ot-img]: https://img.shields.io/badge/OpenTracing--1.0-enabled-blue.svg
+[ot-url]: http://opentracing.io
+[baggage]: https://github.com/opentracing/specification/blob/master/specification.md#set-a-baggage-item
+[timeunits]: https://golang.org/pkg/time/#ParseDuration
diff --git a/vendor/github.com/uber/jaeger-client-go/RELEASE.md b/vendor/github.com/uber/jaeger-client-go/RELEASE.md
new file mode 100644
index 000000000..115e49ab8
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/RELEASE.md
@@ -0,0 +1,11 @@
+# Release Process
+
+1. Create a PR "Preparing for release X.Y.Z" against master branch
+ * Alter CHANGELOG.md from `<placeholder_version> (unreleased)` to `<X.Y.Z> (YYYY-MM-DD)`
+ * Update `JaegerClientVersion` in constants.go to `Go-X.Y.Z`
+2. Create a release "Release X.Y.Z" on Github
+ * Create Tag `vX.Y.Z`
+ * Copy CHANGELOG.md into the release notes
+3. Create a PR "Back to development" against master branch
+ * Add `<next_version> (unreleased)` to CHANGELOG.md
+ * Update `JaegerClientVersion` in constants.go to `Go-<next_version>dev`
diff --git a/vendor/github.com/uber/jaeger-client-go/baggage_setter.go b/vendor/github.com/uber/jaeger-client-go/baggage_setter.go
new file mode 100644
index 000000000..1037ca0e8
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/baggage_setter.go
@@ -0,0 +1,77 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package jaeger
+
+import (
+ "github.com/opentracing/opentracing-go/log"
+
+ "github.com/uber/jaeger-client-go/internal/baggage"
+)
+
+// baggageSetter is an actor that can set a baggage value on a Span given certain
+// restrictions (eg. maxValueLength).
+type baggageSetter struct {
+ restrictionManager baggage.RestrictionManager
+ metrics *Metrics
+}
+
+func newBaggageSetter(restrictionManager baggage.RestrictionManager, metrics *Metrics) *baggageSetter {
+ return &baggageSetter{
+ restrictionManager: restrictionManager,
+ metrics: metrics,
+ }
+}
+
+// (NB) span should hold the lock before making this call
+func (s *baggageSetter) setBaggage(span *Span, key, value string) {
+ var truncated bool
+ var prevItem string
+ restriction := s.restrictionManager.GetRestriction(span.serviceName(), key)
+ if !restriction.KeyAllowed() {
+ s.logFields(span, key, value, prevItem, truncated, restriction.KeyAllowed())
+ s.metrics.BaggageUpdateFailure.Inc(1)
+ return
+ }
+ if len(value) > restriction.MaxValueLength() {
+ truncated = true
+ value = value[:restriction.MaxValueLength()]
+ s.metrics.BaggageTruncate.Inc(1)
+ }
+ prevItem = span.context.baggage[key]
+ s.logFields(span, key, value, prevItem, truncated, restriction.KeyAllowed())
+ span.context = span.context.WithBaggageItem(key, value)
+ s.metrics.BaggageUpdateSuccess.Inc(1)
+}
+
+func (s *baggageSetter) logFields(span *Span, key, value, prevItem string, truncated, valid bool) {
+ if !span.context.IsSampled() {
+ return
+ }
+ fields := []log.Field{
+ log.String("event", "baggage"),
+ log.String("key", key),
+ log.String("value", value),
+ }
+ if prevItem != "" {
+ fields = append(fields, log.String("override", "true"))
+ }
+ if truncated {
+ fields = append(fields, log.String("truncated", "true"))
+ }
+ if !valid {
+ fields = append(fields, log.String("invalid", "true"))
+ }
+ span.logFieldsNoLocking(fields...)
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/config/config.go b/vendor/github.com/uber/jaeger-client-go/config/config.go
new file mode 100644
index 000000000..6cb546002
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/config/config.go
@@ -0,0 +1,394 @@
+// Copyright (c) 2017-2018 Uber Technologies, Inc.
+//
+// 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.
+
+package config
+
+import (
+ "errors"
+ "fmt"
+ "io"
+ "strings"
+ "time"
+
+ "github.com/opentracing/opentracing-go"
+
+ "github.com/uber/jaeger-client-go"
+ "github.com/uber/jaeger-client-go/internal/baggage/remote"
+ throttler "github.com/uber/jaeger-client-go/internal/throttler/remote"
+ "github.com/uber/jaeger-client-go/rpcmetrics"
+ "github.com/uber/jaeger-client-go/transport"
+)
+
+const defaultSamplingProbability = 0.001
+
+// Configuration configures and creates Jaeger Tracer
+type Configuration struct {
+ // ServiceName specifies the service name to use on the tracer.
+ // Can be provided via environment variable named JAEGER_SERVICE_NAME
+ ServiceName string `yaml:"serviceName"`
+
+ // Disabled can be provided via environment variable named JAEGER_DISABLED
+ Disabled bool `yaml:"disabled"`
+
+ // RPCMetrics can be provided via environment variable named JAEGER_RPC_METRICS
+ RPCMetrics bool `yaml:"rpc_metrics"`
+
+ // Tags can be provided via environment variable named JAEGER_TAGS
+ Tags []opentracing.Tag `yaml:"tags"`
+
+ Sampler *SamplerConfig `yaml:"sampler"`
+ Reporter *ReporterConfig `yaml:"reporter"`
+ Headers *jaeger.HeadersConfig `yaml:"headers"`
+ BaggageRestrictions *BaggageRestrictionsConfig `yaml:"baggage_restrictions"`
+ Throttler *ThrottlerConfig `yaml:"throttler"`
+}
+
+// SamplerConfig allows initializing a non-default sampler. All fields are optional.
+type SamplerConfig struct {
+ // Type specifies the type of the sampler: const, probabilistic, rateLimiting, or remote
+ // Can be set by exporting an environment variable named JAEGER_SAMPLER_TYPE
+ Type string `yaml:"type"`
+
+ // Param is a value passed to the sampler.
+ // Valid values for Param field are:
+ // - for "const" sampler, 0 or 1 for always false/true respectively
+ // - for "probabilistic" sampler, a probability between 0 and 1
+ // - for "rateLimiting" sampler, the number of spans per second
+ // - for "remote" sampler, param is the same as for "probabilistic"
+ // and indicates the initial sampling rate before the actual one
+ // is received from the mothership.
+ // Can be set by exporting an environment variable named JAEGER_SAMPLER_PARAM
+ Param float64 `yaml:"param"`
+
+ // SamplingServerURL is the address of jaeger-agent's HTTP sampling server
+ // Can be set by exporting an environment variable named JAEGER_SAMPLER_MANAGER_HOST_PORT
+ SamplingServerURL string `yaml:"samplingServerURL"`
+
+ // MaxOperations is the maximum number of operations that the sampler
+ // will keep track of. If an operation is not tracked, a default probabilistic
+ // sampler will be used rather than the per operation specific sampler.
+ // Can be set by exporting an environment variable named JAEGER_SAMPLER_MAX_OPERATIONS
+ MaxOperations int `yaml:"maxOperations"`
+
+ // SamplingRefreshInterval controls how often the remotely controlled sampler will poll
+ // jaeger-agent for the appropriate sampling strategy.
+ // Can be set by exporting an environment variable named JAEGER_SAMPLER_REFRESH_INTERVAL
+ SamplingRefreshInterval time.Duration `yaml:"samplingRefreshInterval"`
+}
+
+// ReporterConfig configures the reporter. All fields are optional.
+type ReporterConfig struct {
+ // QueueSize controls how many spans the reporter can keep in memory before it starts dropping
+ // new spans. The queue is continuously drained by a background go-routine, as fast as spans
+ // can be sent out of process.
+ // Can be set by exporting an environment variable named JAEGER_REPORTER_MAX_QUEUE_SIZE
+ QueueSize int `yaml:"queueSize"`
+
+ // BufferFlushInterval controls how often the buffer is force-flushed, even if it's not full.
+ // It is generally not useful, as it only matters for very low traffic services.
+ // Can be set by exporting an environment variable named JAEGER_REPORTER_FLUSH_INTERVAL
+ BufferFlushInterval time.Duration
+
+ // LogSpans, when true, enables LoggingReporter that runs in parallel with the main reporter
+ // and logs all submitted spans. Main Configuration.Logger must be initialized in the code
+ // for this option to have any effect.
+ // Can be set by exporting an environment variable named JAEGER_REPORTER_LOG_SPANS
+ LogSpans bool `yaml:"logSpans"`
+
+ // LocalAgentHostPort instructs reporter to send spans to jaeger-agent at this address
+ // Can be set by exporting an environment variable named JAEGER_AGENT_HOST / JAEGER_AGENT_PORT
+ LocalAgentHostPort string `yaml:"localAgentHostPort"`
+
+ // CollectorEndpoint instructs reporter to send spans to jaeger-collector at this URL
+ // Can be set by exporting an environment variable named JAEGER_ENDPOINT
+ CollectorEndpoint string `yaml:"collectorEndpoint"`
+
+ // User instructs reporter to include a user for basic http authentication when sending spans to jaeger-collector.
+ // Can be set by exporting an environment variable named JAEGER_USER
+ User string `yaml:"user"`
+
+ // Password instructs reporter to include a password for basic http authentication when sending spans to
+ // jaeger-collector. Can be set by exporting an environment variable named JAEGER_PASSWORD
+ Password string `yaml:"password"`
+}
+
+// BaggageRestrictionsConfig configures the baggage restrictions manager which can be used to whitelist
+// certain baggage keys. All fields are optional.
+type BaggageRestrictionsConfig struct {
+ // DenyBaggageOnInitializationFailure controls the startup failure mode of the baggage restriction
+ // manager. If true, the manager will not allow any baggage to be written until baggage restrictions have
+ // been retrieved from jaeger-agent. If false, the manager wil allow any baggage to be written until baggage
+ // restrictions have been retrieved from jaeger-agent.
+ DenyBaggageOnInitializationFailure bool `yaml:"denyBaggageOnInitializationFailure"`
+
+ // HostPort is the hostPort of jaeger-agent's baggage restrictions server
+ HostPort string `yaml:"hostPort"`
+
+ // RefreshInterval controls how often the baggage restriction manager will poll
+ // jaeger-agent for the most recent baggage restrictions.
+ RefreshInterval time.Duration `yaml:"refreshInterval"`
+}
+
+// ThrottlerConfig configures the throttler which can be used to throttle the
+// rate at which the client may send debug requests.
+type ThrottlerConfig struct {
+ // HostPort of jaeger-agent's credit server.
+ HostPort string `yaml:"hostPort"`
+
+ // RefreshInterval controls how often the throttler will poll jaeger-agent
+ // for more throttling credits.
+ RefreshInterval time.Duration `yaml:"refreshInterval"`
+
+ // SynchronousInitialization determines whether or not the throttler should
+ // synchronously fetch credits from the agent when an operation is seen for
+ // the first time. This should be set to true if the client will be used by
+ // a short lived service that needs to ensure that credits are fetched
+ // upfront such that sampling or throttling occurs.
+ SynchronousInitialization bool `yaml:"synchronousInitialization"`
+}
+
+type nullCloser struct{}
+
+func (*nullCloser) Close() error { return nil }
+
+// New creates a new Jaeger Tracer, and a closer func that can be used to flush buffers
+// before shutdown.
+//
+// Deprecated: use NewTracer() function
+func (c Configuration) New(
+ serviceName string,
+ options ...Option,
+) (opentracing.Tracer, io.Closer, error) {
+ if serviceName != "" {
+ c.ServiceName = serviceName
+ }
+
+ return c.NewTracer(options...)
+}
+
+// NewTracer returns a new tracer based on the current configuration, using the given options,
+// and a closer func that can be used to flush buffers before shutdown.
+func (c Configuration) NewTracer(options ...Option) (opentracing.Tracer, io.Closer, error) {
+ if c.ServiceName == "" {
+ return nil, nil, errors.New("no service name provided")
+ }
+
+ if c.Disabled {
+ return &opentracing.NoopTracer{}, &nullCloser{}, nil
+ }
+ opts := applyOptions(options...)
+ tracerMetrics := jaeger.NewMetrics(opts.metrics, nil)
+ if c.RPCMetrics {
+ Observer(
+ rpcmetrics.NewObserver(
+ opts.metrics.Namespace("jaeger-rpc", map[string]string{"component": "jaeger"}),
+ rpcmetrics.DefaultNameNormalizer,
+ ),
+ )(&opts) // adds to c.observers
+ }
+ if c.Sampler == nil {
+ c.Sampler = &SamplerConfig{
+ Type: jaeger.SamplerTypeRemote,
+ Param: defaultSamplingProbability,
+ }
+ }
+ if c.Reporter == nil {
+ c.Reporter = &ReporterConfig{}
+ }
+
+ sampler := opts.sampler
+ if sampler == nil {
+ s, err := c.Sampler.NewSampler(c.ServiceName, tracerMetrics)
+ if err != nil {
+ return nil, nil, err
+ }
+ sampler = s
+ }
+
+ reporter := opts.reporter
+ if reporter == nil {
+ r, err := c.Reporter.NewReporter(c.ServiceName, tracerMetrics, opts.logger)
+ if err != nil {
+ return nil, nil, err
+ }
+ reporter = r
+ }
+
+ tracerOptions := []jaeger.TracerOption{
+ jaeger.TracerOptions.Metrics(tracerMetrics),
+ jaeger.TracerOptions.Logger(opts.logger),
+ jaeger.TracerOptions.CustomHeaderKeys(c.Headers),
+ jaeger.TracerOptions.Gen128Bit(opts.gen128Bit),
+ jaeger.TracerOptions.ZipkinSharedRPCSpan(opts.zipkinSharedRPCSpan),
+ jaeger.TracerOptions.MaxTagValueLength(opts.maxTagValueLength),
+ }
+
+ for _, tag := range opts.tags {
+ tracerOptions = append(tracerOptions, jaeger.TracerOptions.Tag(tag.Key, tag.Value))
+ }
+
+ for _, tag := range c.Tags {
+ tracerOptions = append(tracerOptions, jaeger.TracerOptions.Tag(tag.Key, tag.Value))
+ }
+
+ for _, obs := range opts.observers {
+ tracerOptions = append(tracerOptions, jaeger.TracerOptions.Observer(obs))
+ }
+
+ for _, cobs := range opts.contribObservers {
+ tracerOptions = append(tracerOptions, jaeger.TracerOptions.ContribObserver(cobs))
+ }
+
+ for format, injector := range opts.injectors {
+ tracerOptions = append(tracerOptions, jaeger.TracerOptions.Injector(format, injector))
+ }
+
+ for format, extractor := range opts.extractors {
+ tracerOptions = append(tracerOptions, jaeger.TracerOptions.Extractor(format, extractor))
+ }
+
+ if c.BaggageRestrictions != nil {
+ mgr := remote.NewRestrictionManager(
+ c.ServiceName,
+ remote.Options.Metrics(tracerMetrics),
+ remote.Options.Logger(opts.logger),
+ remote.Options.HostPort(c.BaggageRestrictions.HostPort),
+ remote.Options.RefreshInterval(c.BaggageRestrictions.RefreshInterval),
+ remote.Options.DenyBaggageOnInitializationFailure(
+ c.BaggageRestrictions.DenyBaggageOnInitializationFailure,
+ ),
+ )
+ tracerOptions = append(tracerOptions, jaeger.TracerOptions.BaggageRestrictionManager(mgr))
+ }
+
+ if c.Throttler != nil {
+ debugThrottler := throttler.NewThrottler(
+ c.ServiceName,
+ throttler.Options.Metrics(tracerMetrics),
+ throttler.Options.Logger(opts.logger),
+ throttler.Options.HostPort(c.Throttler.HostPort),
+ throttler.Options.RefreshInterval(c.Throttler.RefreshInterval),
+ throttler.Options.SynchronousInitialization(
+ c.Throttler.SynchronousInitialization,
+ ),
+ )
+
+ tracerOptions = append(tracerOptions, jaeger.TracerOptions.DebugThrottler(debugThrottler))
+ }
+
+ tracer, closer := jaeger.NewTracer(
+ c.ServiceName,
+ sampler,
+ reporter,
+ tracerOptions...,
+ )
+
+ return tracer, closer, nil
+}
+
+// InitGlobalTracer creates a new Jaeger Tracer, and sets it as global OpenTracing Tracer.
+// It returns a closer func that can be used to flush buffers before shutdown.
+func (c Configuration) InitGlobalTracer(
+ serviceName string,
+ options ...Option,
+) (io.Closer, error) {
+ if c.Disabled {
+ return &nullCloser{}, nil
+ }
+ tracer, closer, err := c.New(serviceName, options...)
+ if err != nil {
+ return nil, err
+ }
+ opentracing.SetGlobalTracer(tracer)
+ return closer, nil
+}
+
+// NewSampler creates a new sampler based on the configuration
+func (sc *SamplerConfig) NewSampler(
+ serviceName string,
+ metrics *jaeger.Metrics,
+) (jaeger.Sampler, error) {
+ samplerType := strings.ToLower(sc.Type)
+ if samplerType == jaeger.SamplerTypeConst {
+ return jaeger.NewConstSampler(sc.Param != 0), nil
+ }
+ if samplerType == jaeger.SamplerTypeProbabilistic {
+ if sc.Param >= 0 && sc.Param <= 1.0 {
+ return jaeger.NewProbabilisticSampler(sc.Param)
+ }
+ return nil, fmt.Errorf(
+ "Invalid Param for probabilistic sampler: %v. Expecting value between 0 and 1",
+ sc.Param,
+ )
+ }
+ if samplerType == jaeger.SamplerTypeRateLimiting {
+ return jaeger.NewRateLimitingSampler(sc.Param), nil
+ }
+ if samplerType == jaeger.SamplerTypeRemote || sc.Type == "" {
+ sc2 := *sc
+ sc2.Type = jaeger.SamplerTypeProbabilistic
+ initSampler, err := sc2.NewSampler(serviceName, nil)
+ if err != nil {
+ return nil, err
+ }
+ options := []jaeger.SamplerOption{
+ jaeger.SamplerOptions.Metrics(metrics),
+ jaeger.SamplerOptions.InitialSampler(initSampler),
+ jaeger.SamplerOptions.SamplingServerURL(sc.SamplingServerURL),
+ }
+ if sc.MaxOperations != 0 {
+ options = append(options, jaeger.SamplerOptions.MaxOperations(sc.MaxOperations))
+ }
+ if sc.SamplingRefreshInterval != 0 {
+ options = append(options, jaeger.SamplerOptions.SamplingRefreshInterval(sc.SamplingRefreshInterval))
+ }
+ return jaeger.NewRemotelyControlledSampler(serviceName, options...), nil
+ }
+ return nil, fmt.Errorf("Unknown sampler type %v", sc.Type)
+}
+
+// NewReporter instantiates a new reporter that submits spans to the collector
+func (rc *ReporterConfig) NewReporter(
+ serviceName string,
+ metrics *jaeger.Metrics,
+ logger jaeger.Logger,
+) (jaeger.Reporter, error) {
+ sender, err := rc.newTransport()
+ if err != nil {
+ return nil, err
+ }
+ reporter := jaeger.NewRemoteReporter(
+ sender,
+ jaeger.ReporterOptions.QueueSize(rc.QueueSize),
+ jaeger.ReporterOptions.BufferFlushInterval(rc.BufferFlushInterval),
+ jaeger.ReporterOptions.Logger(logger),
+ jaeger.ReporterOptions.Metrics(metrics))
+ if rc.LogSpans && logger != nil {
+ logger.Infof("Initializing logging reporter\n")
+ reporter = jaeger.NewCompositeReporter(jaeger.NewLoggingReporter(logger), reporter)
+ }
+ return reporter, err
+}
+
+func (rc *ReporterConfig) newTransport() (jaeger.Transport, error) {
+ switch {
+ case rc.CollectorEndpoint != "" && rc.User != "" && rc.Password != "":
+ return transport.NewHTTPTransport(rc.CollectorEndpoint, transport.HTTPBatchSize(1),
+ transport.HTTPBasicAuth(rc.User, rc.Password)), nil
+ case rc.CollectorEndpoint != "":
+ return transport.NewHTTPTransport(rc.CollectorEndpoint, transport.HTTPBatchSize(1)), nil
+ default:
+ return jaeger.NewUDPTransport(rc.LocalAgentHostPort, 0)
+ }
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/config/config_env.go b/vendor/github.com/uber/jaeger-client-go/config/config_env.go
new file mode 100644
index 000000000..ff70ae12c
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/config/config_env.go
@@ -0,0 +1,221 @@
+// Copyright (c) 2018 The Jaeger Authors.
+//
+// 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.
+
+package config
+
+import (
+ "fmt"
+ "net/url"
+ "os"
+ "strconv"
+ "strings"
+ "time"
+
+ "github.com/opentracing/opentracing-go"
+ "github.com/pkg/errors"
+
+ "github.com/uber/jaeger-client-go"
+)
+
+const (
+ // environment variable names
+ envServiceName = "JAEGER_SERVICE_NAME"
+ envDisabled = "JAEGER_DISABLED"
+ envRPCMetrics = "JAEGER_RPC_METRICS"
+ envTags = "JAEGER_TAGS"
+ envSamplerType = "JAEGER_SAMPLER_TYPE"
+ envSamplerParam = "JAEGER_SAMPLER_PARAM"
+ envSamplerManagerHostPort = "JAEGER_SAMPLER_MANAGER_HOST_PORT"
+ envSamplerMaxOperations = "JAEGER_SAMPLER_MAX_OPERATIONS"
+ envSamplerRefreshInterval = "JAEGER_SAMPLER_REFRESH_INTERVAL"
+ envReporterMaxQueueSize = "JAEGER_REPORTER_MAX_QUEUE_SIZE"
+ envReporterFlushInterval = "JAEGER_REPORTER_FLUSH_INTERVAL"
+ envReporterLogSpans = "JAEGER_REPORTER_LOG_SPANS"
+ envEndpoint = "JAEGER_ENDPOINT"
+ envUser = "JAEGER_USER"
+ envPassword = "JAEGER_PASSWORD"
+ envAgentHost = "JAEGER_AGENT_HOST"
+ envAgentPort = "JAEGER_AGENT_PORT"
+)
+
+// FromEnv uses environment variables to set the tracer's Configuration
+func FromEnv() (*Configuration, error) {
+ c := &Configuration{}
+
+ if e := os.Getenv(envServiceName); e != "" {
+ c.ServiceName = e
+ }
+
+ if e := os.Getenv(envRPCMetrics); e != "" {
+ if value, err := strconv.ParseBool(e); err == nil {
+ c.RPCMetrics = value
+ } else {
+ return nil, errors.Wrapf(err, "cannot parse env var %s=%s", envRPCMetrics, e)
+ }
+ }
+
+ if e := os.Getenv(envDisabled); e != "" {
+ if value, err := strconv.ParseBool(e); err == nil {
+ c.Disabled = value
+ } else {
+ return nil, errors.Wrapf(err, "cannot parse env var %s=%s", envDisabled, e)
+ }
+ }
+
+ if e := os.Getenv(envTags); e != "" {
+ c.Tags = parseTags(e)
+ }
+
+ if s, err := samplerConfigFromEnv(); err == nil {
+ c.Sampler = s
+ } else {
+ return nil, errors.Wrap(err, "cannot obtain sampler config from env")
+ }
+
+ if r, err := reporterConfigFromEnv(); err == nil {
+ c.Reporter = r
+ } else {
+ return nil, errors.Wrap(err, "cannot obtain reporter config from env")
+ }
+
+ return c, nil
+}
+
+// samplerConfigFromEnv creates a new SamplerConfig based on the environment variables
+func samplerConfigFromEnv() (*SamplerConfig, error) {
+ sc := &SamplerConfig{}
+
+ if e := os.Getenv(envSamplerType); e != "" {
+ sc.Type = e
+ }
+
+ if e := os.Getenv(envSamplerParam); e != "" {
+ if value, err := strconv.ParseFloat(e, 64); err == nil {
+ sc.Param = value
+ } else {
+ return nil, errors.Wrapf(err, "cannot parse env var %s=%s", envSamplerParam, e)
+ }
+ }
+
+ if e := os.Getenv(envSamplerManagerHostPort); e != "" {
+ sc.SamplingServerURL = e
+ }
+
+ if e := os.Getenv(envSamplerMaxOperations); e != "" {
+ if value, err := strconv.ParseInt(e, 10, 0); err == nil {
+ sc.MaxOperations = int(value)
+ } else {
+ return nil, errors.Wrapf(err, "cannot parse env var %s=%s", envSamplerMaxOperations, e)
+ }
+ }
+
+ if e := os.Getenv(envSamplerRefreshInterval); e != "" {
+ if value, err := time.ParseDuration(e); err == nil {
+ sc.SamplingRefreshInterval = value
+ } else {
+ return nil, errors.Wrapf(err, "cannot parse env var %s=%s", envSamplerRefreshInterval, e)
+ }
+ }
+
+ return sc, nil
+}
+
+// reporterConfigFromEnv creates a new ReporterConfig based on the environment variables
+func reporterConfigFromEnv() (*ReporterConfig, error) {
+ rc := &ReporterConfig{}
+
+ if e := os.Getenv(envReporterMaxQueueSize); e != "" {
+ if value, err := strconv.ParseInt(e, 10, 0); err == nil {
+ rc.QueueSize = int(value)
+ } else {
+ return nil, errors.Wrapf(err, "cannot parse env var %s=%s", envReporterMaxQueueSize, e)
+ }
+ }
+
+ if e := os.Getenv(envReporterFlushInterval); e != "" {
+ if value, err := time.ParseDuration(e); err == nil {
+ rc.BufferFlushInterval = value
+ } else {
+ return nil, errors.Wrapf(err, "cannot parse env var %s=%s", envReporterFlushInterval, e)
+ }
+ }
+
+ if e := os.Getenv(envReporterLogSpans); e != "" {
+ if value, err := strconv.ParseBool(e); err == nil {
+ rc.LogSpans = value
+ } else {
+ return nil, errors.Wrapf(err, "cannot parse env var %s=%s", envReporterLogSpans, e)
+ }
+ }
+
+ if e := os.Getenv(envEndpoint); e != "" {
+ u, err := url.ParseRequestURI(e)
+ if err != nil {
+ return nil, errors.Wrapf(err, "cannot parse env var %s=%s", envEndpoint, e)
+ }
+ rc.CollectorEndpoint = u.String()
+ user := os.Getenv(envUser)
+ pswd := os.Getenv(envPassword)
+ if user != "" && pswd == "" || user == "" && pswd != "" {
+ return nil, errors.Errorf("you must set %s and %s env vars together", envUser, envPassword)
+ }
+ rc.User = user
+ rc.Password = pswd
+ } else {
+ host := jaeger.DefaultUDPSpanServerHost
+ if e := os.Getenv(envAgentHost); e != "" {
+ host = e
+ }
+
+ port := jaeger.DefaultUDPSpanServerPort
+ if e := os.Getenv(envAgentPort); e != "" {
+ if value, err := strconv.ParseInt(e, 10, 0); err == nil {
+ port = int(value)
+ } else {
+ return nil, errors.Wrapf(err, "cannot parse env var %s=%s", envAgentPort, e)
+ }
+ }
+ rc.LocalAgentHostPort = fmt.Sprintf("%s:%d", host, port)
+ }
+
+ return rc, nil
+}
+
+// parseTags parses the given string into a collection of Tags.
+// Spec for this value:
+// - comma separated list of key=value
+// - value can be specified using the notation ${envVar:defaultValue}, where `envVar`
+// is an environment variable and `defaultValue` is the value to use in case the env var is not set
+func parseTags(sTags string) []opentracing.Tag {
+ pairs := strings.Split(sTags, ",")
+ tags := make([]opentracing.Tag, 0)
+ for _, p := range pairs {
+ kv := strings.SplitN(p, "=", 2)
+ k, v := strings.TrimSpace(kv[0]), strings.TrimSpace(kv[1])
+
+ if strings.HasPrefix(v, "${") && strings.HasSuffix(v, "}") {
+ ed := strings.SplitN(v[2:len(v)-1], ":", 2)
+ e, d := ed[0], ed[1]
+ v = os.Getenv(e)
+ if v == "" && d != "" {
+ v = d
+ }
+ }
+
+ tag := opentracing.Tag{Key: k, Value: v}
+ tags = append(tags, tag)
+ }
+
+ return tags
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/config/options.go b/vendor/github.com/uber/jaeger-client-go/config/options.go
new file mode 100644
index 000000000..d14f1f8a9
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/config/options.go
@@ -0,0 +1,148 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package config
+
+import (
+ opentracing "github.com/opentracing/opentracing-go"
+ "github.com/uber/jaeger-lib/metrics"
+
+ "github.com/uber/jaeger-client-go"
+)
+
+// Option is a function that sets some option on the client.
+type Option func(c *Options)
+
+// Options control behavior of the client.
+type Options struct {
+ metrics metrics.Factory
+ logger jaeger.Logger
+ reporter jaeger.Reporter
+ sampler jaeger.Sampler
+ contribObservers []jaeger.ContribObserver
+ observers []jaeger.Observer
+ gen128Bit bool
+ zipkinSharedRPCSpan bool
+ maxTagValueLength int
+ tags []opentracing.Tag
+ injectors map[interface{}]jaeger.Injector
+ extractors map[interface{}]jaeger.Extractor
+}
+
+// Metrics creates an Option that initializes Metrics in the tracer,
+// which is used to emit statistics about spans.
+func Metrics(factory metrics.Factory) Option {
+ return func(c *Options) {
+ c.metrics = factory
+ }
+}
+
+// Logger can be provided to log Reporter errors, as well as to log spans
+// if Reporter.LogSpans is set to true.
+func Logger(logger jaeger.Logger) Option {
+ return func(c *Options) {
+ c.logger = logger
+ }
+}
+
+// Reporter can be provided explicitly to override the configuration.
+// Useful for testing, e.g. by passing InMemoryReporter.
+func Reporter(reporter jaeger.Reporter) Option {
+ return func(c *Options) {
+ c.reporter = reporter
+ }
+}
+
+// Sampler can be provided explicitly to override the configuration.
+func Sampler(sampler jaeger.Sampler) Option {
+ return func(c *Options) {
+ c.sampler = sampler
+ }
+}
+
+// Observer can be registered with the Tracer to receive notifications about new Spans.
+func Observer(observer jaeger.Observer) Option {
+ return func(c *Options) {
+ c.observers = append(c.observers, observer)
+ }
+}
+
+// ContribObserver can be registered with the Tracer to recieve notifications
+// about new spans.
+func ContribObserver(observer jaeger.ContribObserver) Option {
+ return func(c *Options) {
+ c.contribObservers = append(c.contribObservers, observer)
+ }
+}
+
+// Gen128Bit specifies whether to generate 128bit trace IDs.
+func Gen128Bit(gen128Bit bool) Option {
+ return func(c *Options) {
+ c.gen128Bit = gen128Bit
+ }
+}
+
+// ZipkinSharedRPCSpan creates an option that enables sharing span ID between client
+// and server spans a la zipkin. If false, client and server spans will be assigned
+// different IDs.
+func ZipkinSharedRPCSpan(zipkinSharedRPCSpan bool) Option {
+ return func(c *Options) {
+ c.zipkinSharedRPCSpan = zipkinSharedRPCSpan
+ }
+}
+
+// MaxTagValueLength can be provided to override the default max tag value length.
+func MaxTagValueLength(maxTagValueLength int) Option {
+ return func(c *Options) {
+ c.maxTagValueLength = maxTagValueLength
+ }
+}
+
+// Tag creates an option that adds a tracer-level tag.
+func Tag(key string, value interface{}) Option {
+ return func(c *Options) {
+ c.tags = append(c.tags, opentracing.Tag{Key: key, Value: value})
+ }
+}
+
+// Injector registers an Injector with the given format.
+func Injector(format interface{}, injector jaeger.Injector) Option {
+ return func(c *Options) {
+ c.injectors[format] = injector
+ }
+}
+
+// Extractor registers an Extractor with the given format.
+func Extractor(format interface{}, extractor jaeger.Extractor) Option {
+ return func(c *Options) {
+ c.extractors[format] = extractor
+ }
+}
+
+func applyOptions(options ...Option) Options {
+ opts := Options{
+ injectors: make(map[interface{}]jaeger.Injector),
+ extractors: make(map[interface{}]jaeger.Extractor),
+ }
+ for _, option := range options {
+ option(&opts)
+ }
+ if opts.metrics == nil {
+ opts.metrics = metrics.NullFactory
+ }
+ if opts.logger == nil {
+ opts.logger = jaeger.NullLogger
+ }
+ return opts
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/constants.go b/vendor/github.com/uber/jaeger-client-go/constants.go
new file mode 100644
index 000000000..5a4e18752
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/constants.go
@@ -0,0 +1,88 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package jaeger
+
+const (
+ // JaegerClientVersion is the version of the client library reported as Span tag.
+ JaegerClientVersion = "Go-2.15.1dev"
+
+ // JaegerClientVersionTagKey is the name of the tag used to report client version.
+ JaegerClientVersionTagKey = "jaeger.version"
+
+ // JaegerDebugHeader is the name of HTTP header or a TextMap carrier key which,
+ // if found in the carrier, forces the trace to be sampled as "debug" trace.
+ // The value of the header is recorded as the tag on the root span, so that the
+ // trace can be found in the UI using this value as a correlation ID.
+ JaegerDebugHeader = "jaeger-debug-id"
+
+ // JaegerBaggageHeader is the name of the HTTP header that is used to submit baggage.
+ // It differs from TraceBaggageHeaderPrefix in that it can be used only in cases where
+ // a root span does not exist.
+ JaegerBaggageHeader = "jaeger-baggage"
+
+ // TracerHostnameTagKey used to report host name of the process.
+ TracerHostnameTagKey = "hostname"
+
+ // TracerIPTagKey used to report ip of the process.
+ TracerIPTagKey = "ip"
+
+ // TracerUUIDTagKey used to report UUID of the client process.
+ TracerUUIDTagKey = "client-uuid"
+
+ // SamplerTypeTagKey reports which sampler was used on the root span.
+ SamplerTypeTagKey = "sampler.type"
+
+ // SamplerParamTagKey reports the parameter of the sampler, like sampling probability.
+ SamplerParamTagKey = "sampler.param"
+
+ // TraceContextHeaderName is the http header name used to propagate tracing context.
+ // This must be in lower-case to avoid mismatches when decoding incoming headers.
+ TraceContextHeaderName = "uber-trace-id"
+
+ // TracerStateHeaderName is deprecated.
+ // Deprecated: use TraceContextHeaderName
+ TracerStateHeaderName = TraceContextHeaderName
+
+ // TraceBaggageHeaderPrefix is the prefix for http headers used to propagate baggage.
+ // This must be in lower-case to avoid mismatches when decoding incoming headers.
+ TraceBaggageHeaderPrefix = "uberctx-"
+
+ // SamplerTypeConst is the type of sampler that always makes the same decision.
+ SamplerTypeConst = "const"
+
+ // SamplerTypeRemote is the type of sampler that polls Jaeger agent for sampling strategy.
+ SamplerTypeRemote = "remote"
+
+ // SamplerTypeProbabilistic is the type of sampler that samples traces
+ // with a certain fixed probability.
+ SamplerTypeProbabilistic = "probabilistic"
+
+ // SamplerTypeRateLimiting is the type of sampler that samples
+ // only up to a fixed number of traces per second.
+ SamplerTypeRateLimiting = "ratelimiting"
+
+ // SamplerTypeLowerBound is the type of sampler that samples
+ // at least a fixed number of traces per second.
+ SamplerTypeLowerBound = "lowerbound"
+
+ // DefaultUDPSpanServerHost is the default host to send the spans to, via UDP
+ DefaultUDPSpanServerHost = "localhost"
+
+ // DefaultUDPSpanServerPort is the default port to send the spans to, via UDP
+ DefaultUDPSpanServerPort = 6831
+
+ // DefaultMaxTagValueLength is the default max length of byte array or string allowed in the tag value.
+ DefaultMaxTagValueLength = 256
+)
diff --git a/vendor/github.com/uber/jaeger-client-go/context.go b/vendor/github.com/uber/jaeger-client-go/context.go
new file mode 100644
index 000000000..8b06173d9
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/context.go
@@ -0,0 +1,258 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package jaeger
+
+import (
+ "errors"
+ "fmt"
+ "strconv"
+ "strings"
+)
+
+const (
+ flagSampled = byte(1)
+ flagDebug = byte(2)
+)
+
+var (
+ errEmptyTracerStateString = errors.New("Cannot convert empty string to tracer state")
+ errMalformedTracerStateString = errors.New("String does not match tracer state format")
+
+ emptyContext = SpanContext{}
+)
+
+// TraceID represents unique 128bit identifier of a trace
+type TraceID struct {
+ High, Low uint64
+}
+
+// SpanID represents unique 64bit identifier of a span
+type SpanID uint64
+
+// SpanContext represents propagated span identity and state
+type SpanContext struct {
+ // traceID represents globally unique ID of the trace.
+ // Usually generated as a random number.
+ traceID TraceID
+
+ // spanID represents span ID that must be unique within its trace,
+ // but does not have to be globally unique.
+ spanID SpanID
+
+ // parentID refers to the ID of the parent span.
+ // Should be 0 if the current span is a root span.
+ parentID SpanID
+
+ // flags is a bitmap containing such bits as 'sampled' and 'debug'.
+ flags byte
+
+ // Distributed Context baggage. The is a snapshot in time.
+ baggage map[string]string
+
+ // debugID can be set to some correlation ID when the context is being
+ // extracted from a TextMap carrier.
+ //
+ // See JaegerDebugHeader in constants.go
+ debugID string
+}
+
+// ForeachBaggageItem implements ForeachBaggageItem() of opentracing.SpanContext
+func (c SpanContext) ForeachBaggageItem(handler func(k, v string) bool) {
+ for k, v := range c.baggage {
+ if !handler(k, v) {
+ break
+ }
+ }
+}
+
+// IsSampled returns whether this trace was chosen for permanent storage
+// by the sampling mechanism of the tracer.
+func (c SpanContext) IsSampled() bool {
+ return (c.flags & flagSampled) == flagSampled
+}
+
+// IsDebug indicates whether sampling was explicitly requested by the service.
+func (c SpanContext) IsDebug() bool {
+ return (c.flags & flagDebug) == flagDebug
+}
+
+// IsValid indicates whether this context actually represents a valid trace.
+func (c SpanContext) IsValid() bool {
+ return c.traceID.IsValid() && c.spanID != 0
+}
+
+func (c SpanContext) String() string {
+ if c.traceID.High == 0 {
+ return fmt.Sprintf("%x:%x:%x:%x", c.traceID.Low, uint64(c.spanID), uint64(c.parentID), c.flags)
+ }
+ return fmt.Sprintf("%x%016x:%x:%x:%x", c.traceID.High, c.traceID.Low, uint64(c.spanID), uint64(c.parentID), c.flags)
+}
+
+// ContextFromString reconstructs the Context encoded in a string
+func ContextFromString(value string) (SpanContext, error) {
+ var context SpanContext
+ if value == "" {
+ return emptyContext, errEmptyTracerStateString
+ }
+ parts := strings.Split(value, ":")
+ if len(parts) != 4 {
+ return emptyContext, errMalformedTracerStateString
+ }
+ var err error
+ if context.traceID, err = TraceIDFromString(parts[0]); err != nil {
+ return emptyContext, err
+ }
+ if context.spanID, err = SpanIDFromString(parts[1]); err != nil {
+ return emptyContext, err
+ }
+ if context.parentID, err = SpanIDFromString(parts[2]); err != nil {
+ return emptyContext, err
+ }
+ flags, err := strconv.ParseUint(parts[3], 10, 8)
+ if err != nil {
+ return emptyContext, err
+ }
+ context.flags = byte(flags)
+ return context, nil
+}
+
+// TraceID returns the trace ID of this span context
+func (c SpanContext) TraceID() TraceID {
+ return c.traceID
+}
+
+// SpanID returns the span ID of this span context
+func (c SpanContext) SpanID() SpanID {
+ return c.spanID
+}
+
+// ParentID returns the parent span ID of this span context
+func (c SpanContext) ParentID() SpanID {
+ return c.parentID
+}
+
+// NewSpanContext creates a new instance of SpanContext
+func NewSpanContext(traceID TraceID, spanID, parentID SpanID, sampled bool, baggage map[string]string) SpanContext {
+ flags := byte(0)
+ if sampled {
+ flags = flagSampled
+ }
+ return SpanContext{
+ traceID: traceID,
+ spanID: spanID,
+ parentID: parentID,
+ flags: flags,
+ baggage: baggage}
+}
+
+// CopyFrom copies data from ctx into this context, including span identity and baggage.
+// TODO This is only used by interop.go. Remove once TChannel Go supports OpenTracing.
+func (c *SpanContext) CopyFrom(ctx *SpanContext) {
+ c.traceID = ctx.traceID
+ c.spanID = ctx.spanID
+ c.parentID = ctx.parentID
+ c.flags = ctx.flags
+ if l := len(ctx.baggage); l > 0 {
+ c.baggage = make(map[string]string, l)
+ for k, v := range ctx.baggage {
+ c.baggage[k] = v
+ }
+ } else {
+ c.baggage = nil
+ }
+}
+
+// WithBaggageItem creates a new context with an extra baggage item.
+func (c SpanContext) WithBaggageItem(key, value string) SpanContext {
+ var newBaggage map[string]string
+ if c.baggage == nil {
+ newBaggage = map[string]string{key: value}
+ } else {
+ newBaggage = make(map[string]string, len(c.baggage)+1)
+ for k, v := range c.baggage {
+ newBaggage[k] = v
+ }
+ newBaggage[key] = value
+ }
+ // Use positional parameters so the compiler will help catch new fields.
+ return SpanContext{c.traceID, c.spanID, c.parentID, c.flags, newBaggage, ""}
+}
+
+// isDebugIDContainerOnly returns true when the instance of the context is only
+// used to return the debug/correlation ID from extract() method. This happens
+// in the situation when "jaeger-debug-id" header is passed in the carrier to
+// the extract() method, but the request otherwise has no span context in it.
+// Previously this would've returned opentracing.ErrSpanContextNotFound from the
+// extract method, but now it returns a dummy context with only debugID filled in.
+//
+// See JaegerDebugHeader in constants.go
+// See textMapPropagator#Extract
+func (c *SpanContext) isDebugIDContainerOnly() bool {
+ return !c.traceID.IsValid() && c.debugID != ""
+}
+
+// ------- TraceID -------
+
+func (t TraceID) String() string {
+ if t.High == 0 {
+ return fmt.Sprintf("%x", t.Low)
+ }
+ return fmt.Sprintf("%x%016x", t.High, t.Low)
+}
+
+// TraceIDFromString creates a TraceID from a hexadecimal string
+func TraceIDFromString(s string) (TraceID, error) {
+ var hi, lo uint64
+ var err error
+ if len(s) > 32 {
+ return TraceID{}, fmt.Errorf("TraceID cannot be longer than 32 hex characters: %s", s)
+ } else if len(s) > 16 {
+ hiLen := len(s) - 16
+ if hi, err = strconv.ParseUint(s[0:hiLen], 16, 64); err != nil {
+ return TraceID{}, err
+ }
+ if lo, err = strconv.ParseUint(s[hiLen:], 16, 64); err != nil {
+ return TraceID{}, err
+ }
+ } else {
+ if lo, err = strconv.ParseUint(s, 16, 64); err != nil {
+ return TraceID{}, err
+ }
+ }
+ return TraceID{High: hi, Low: lo}, nil
+}
+
+// IsValid checks if the trace ID is valid, i.e. not zero.
+func (t TraceID) IsValid() bool {
+ return t.High != 0 || t.Low != 0
+}
+
+// ------- SpanID -------
+
+func (s SpanID) String() string {
+ return fmt.Sprintf("%x", uint64(s))
+}
+
+// SpanIDFromString creates a SpanID from a hexadecimal string
+func SpanIDFromString(s string) (SpanID, error) {
+ if len(s) > 16 {
+ return SpanID(0), fmt.Errorf("SpanID cannot be longer than 16 hex characters: %s", s)
+ }
+ id, err := strconv.ParseUint(s, 16, 64)
+ if err != nil {
+ return SpanID(0), err
+ }
+ return SpanID(id), nil
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/contrib_observer.go b/vendor/github.com/uber/jaeger-client-go/contrib_observer.go
new file mode 100644
index 000000000..4ce1881f3
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/contrib_observer.go
@@ -0,0 +1,56 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package jaeger
+
+import (
+ opentracing "github.com/opentracing/opentracing-go"
+)
+
+// ContribObserver can be registered with the Tracer to receive notifications
+// about new Spans. Modelled after github.com/opentracing-contrib/go-observer.
+type ContribObserver interface {
+ // Create and return a span observer. Called when a span starts.
+ // If the Observer is not interested in the given span, it must return (nil, false).
+ // E.g :
+ // func StartSpan(opName string, opts ...opentracing.StartSpanOption) {
+ // var sp opentracing.Span
+ // sso := opentracing.StartSpanOptions{}
+ // if spanObserver, ok := Observer.OnStartSpan(span, opName, sso); ok {
+ // // we have a valid SpanObserver
+ // }
+ // ...
+ // }
+ OnStartSpan(sp opentracing.Span, operationName string, options opentracing.StartSpanOptions) (ContribSpanObserver, bool)
+}
+
+// ContribSpanObserver is created by the Observer and receives notifications
+// about other Span events. This interface is meant to match
+// github.com/opentracing-contrib/go-observer, via duck typing, without
+// directly importing the go-observer package.
+type ContribSpanObserver interface {
+ OnSetOperationName(operationName string)
+ OnSetTag(key string, value interface{})
+ OnFinish(options opentracing.FinishOptions)
+}
+
+// wrapper observer for the old observers (see observer.go)
+type oldObserver struct {
+ obs Observer
+}
+
+func (o *oldObserver) OnStartSpan(sp opentracing.Span, operationName string, options opentracing.StartSpanOptions) (ContribSpanObserver, bool) {
+ spanObserver := o.obs.OnStartSpan(operationName, options)
+ return spanObserver, spanObserver != nil
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/doc.go b/vendor/github.com/uber/jaeger-client-go/doc.go
new file mode 100644
index 000000000..4f5549033
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/doc.go
@@ -0,0 +1,24 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+/*
+Package jaeger implements an OpenTracing (http://opentracing.io) Tracer.
+It is currently using Zipkin-compatible data model and can be directly
+itegrated with Zipkin backend (http://zipkin.io).
+
+For integration instructions please refer to the README:
+
+https://github.com/uber/jaeger-client-go/blob/master/README.md
+*/
+package jaeger
diff --git a/vendor/github.com/uber/jaeger-client-go/glide.lock b/vendor/github.com/uber/jaeger-client-go/glide.lock
new file mode 100644
index 000000000..d76b15361
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/glide.lock
@@ -0,0 +1,89 @@
+hash: 3accf84f97bff4a91162736104c0e9b9790820712bd86db6fec5e665f7196a82
+updated: 2018-04-30T11:46:43.804556-04:00
+imports:
+- name: github.com/beorn7/perks
+ version: 3a771d992973f24aa725d07868b467d1ddfceafb
+ subpackages:
+ - quantile
+- name: github.com/codahale/hdrhistogram
+ version: 3a0bb77429bd3a61596f5e8a3172445844342120
+- name: github.com/crossdock/crossdock-go
+ version: 049aabb0122b03bc9bd30cab8f3f91fb60166361
+ subpackages:
+ - assert
+ - require
+- name: github.com/davecgh/go-spew
+ version: 8991bc29aa16c548c550c7ff78260e27b9ab7c73
+ subpackages:
+ - spew
+- name: github.com/golang/protobuf
+ version: bbd03ef6da3a115852eaf24c8a1c46aeb39aa175
+ subpackages:
+ - proto
+- name: github.com/matttproud/golang_protobuf_extensions
+ version: c12348ce28de40eed0136aa2b644d0ee0650e56c
+ subpackages:
+ - pbutil
+- name: github.com/opentracing/opentracing-go
+ version: 1949ddbfd147afd4d964a9f00b24eb291e0e7c38
+ subpackages:
+ - ext
+ - log
+- name: github.com/pkg/errors
+ version: 645ef00459ed84a119197bfb8d8205042c6df63d
+- name: github.com/pmezard/go-difflib
+ version: 792786c7400a136282c1664665ae0a8db921c6c2
+ subpackages:
+ - difflib
+- name: github.com/prometheus/client_golang
+ version: c5b7fccd204277076155f10851dad72b76a49317
+ subpackages:
+ - prometheus
+- name: github.com/prometheus/client_model
+ version: 99fa1f4be8e564e8a6b613da7fa6f46c9edafc6c
+ subpackages:
+ - go
+- name: github.com/prometheus/common
+ version: 38c53a9f4bfcd932d1b00bfc65e256a7fba6b37a
+ subpackages:
+ - expfmt
+ - internal/bitbucket.org/ww/goautoneg
+ - model
+- name: github.com/prometheus/procfs
+ version: 780932d4fbbe0e69b84c34c20f5c8d0981e109ea
+ subpackages:
+ - internal/util
+ - nfs
+ - xfs
+- name: github.com/stretchr/testify
+ version: 12b6f73e6084dad08a7c6e575284b177ecafbc71
+ subpackages:
+ - assert
+ - require
+ - suite
+- name: github.com/uber/jaeger-lib
+ version: 4267858c0679cd4e47cefed8d7f70fd386cfb567
+ subpackages:
+ - metrics
+ - metrics/prometheus
+ - metrics/testutils
+- name: go.uber.org/atomic
+ version: 8474b86a5a6f79c443ce4b2992817ff32cf208b8
+- name: go.uber.org/multierr
+ version: 3c4937480c32f4c13a875a1829af76c98ca3d40a
+- name: go.uber.org/zap
+ version: eeedf312bc6c57391d84767a4cd413f02a917974
+ subpackages:
+ - buffer
+ - internal/bufferpool
+ - internal/color
+ - internal/exit
+ - zapcore
+- name: golang.org/x/net
+ version: 6078986fec03a1dcc236c34816c71b0e05018fda
+ subpackages:
+ - context
+ - context/ctxhttp
+testImports:
+- name: github.com/uber-go/atomic
+ version: 8474b86a5a6f79c443ce4b2992817ff32cf208b8
diff --git a/vendor/github.com/uber/jaeger-client-go/glide.yaml b/vendor/github.com/uber/jaeger-client-go/glide.yaml
new file mode 100644
index 000000000..6637da215
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/glide.yaml
@@ -0,0 +1,22 @@
+package: github.com/uber/jaeger-client-go
+import:
+- package: github.com/opentracing/opentracing-go
+ version: ^1
+ subpackages:
+ - ext
+ - log
+- package: github.com/crossdock/crossdock-go
+- package: github.com/uber/jaeger-lib
+ version: ^1.2.1
+ subpackages:
+ - metrics
+- package: github.com/pkg/errors
+ version: ~0.8.0
+testImport:
+- package: github.com/stretchr/testify
+ subpackages:
+ - assert
+ - require
+ - suite
+- package: github.com/prometheus/client_golang
+ version: v0.8.0
diff --git a/vendor/github.com/uber/jaeger-client-go/header.go b/vendor/github.com/uber/jaeger-client-go/header.go
new file mode 100644
index 000000000..19c2c055b
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/header.go
@@ -0,0 +1,64 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package jaeger
+
+// HeadersConfig contains the values for the header keys that Jaeger will use.
+// These values may be either custom or default depending on whether custom
+// values were provided via a configuration.
+type HeadersConfig struct {
+ // JaegerDebugHeader is the name of HTTP header or a TextMap carrier key which,
+ // if found in the carrier, forces the trace to be sampled as "debug" trace.
+ // The value of the header is recorded as the tag on the root span, so that the
+ // trace can be found in the UI using this value as a correlation ID.
+ JaegerDebugHeader string `yaml:"jaegerDebugHeader"`
+
+ // JaegerBaggageHeader is the name of the HTTP header that is used to submit baggage.
+ // It differs from TraceBaggageHeaderPrefix in that it can be used only in cases where
+ // a root span does not exist.
+ JaegerBaggageHeader string `yaml:"jaegerBaggageHeader"`
+
+ // TraceContextHeaderName is the http header name used to propagate tracing context.
+ // This must be in lower-case to avoid mismatches when decoding incoming headers.
+ TraceContextHeaderName string `yaml:"TraceContextHeaderName"`
+
+ // TraceBaggageHeaderPrefix is the prefix for http headers used to propagate baggage.
+ // This must be in lower-case to avoid mismatches when decoding incoming headers.
+ TraceBaggageHeaderPrefix string `yaml:"traceBaggageHeaderPrefix"`
+}
+
+func (c *HeadersConfig) applyDefaults() *HeadersConfig {
+ if c.JaegerBaggageHeader == "" {
+ c.JaegerBaggageHeader = JaegerBaggageHeader
+ }
+ if c.JaegerDebugHeader == "" {
+ c.JaegerDebugHeader = JaegerDebugHeader
+ }
+ if c.TraceBaggageHeaderPrefix == "" {
+ c.TraceBaggageHeaderPrefix = TraceBaggageHeaderPrefix
+ }
+ if c.TraceContextHeaderName == "" {
+ c.TraceContextHeaderName = TraceContextHeaderName
+ }
+ return c
+}
+
+func getDefaultHeadersConfig() *HeadersConfig {
+ return &HeadersConfig{
+ JaegerDebugHeader: JaegerDebugHeader,
+ JaegerBaggageHeader: JaegerBaggageHeader,
+ TraceContextHeaderName: TraceContextHeaderName,
+ TraceBaggageHeaderPrefix: TraceBaggageHeaderPrefix,
+ }
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/internal/baggage/remote/options.go b/vendor/github.com/uber/jaeger-client-go/internal/baggage/remote/options.go
new file mode 100644
index 000000000..745729319
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/internal/baggage/remote/options.go
@@ -0,0 +1,101 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package remote
+
+import (
+ "time"
+
+ "github.com/uber/jaeger-client-go"
+)
+
+const (
+ defaultMaxValueLength = 2048
+ defaultRefreshInterval = time.Minute
+ defaultHostPort = "localhost:5778"
+)
+
+// Option is a function that sets some option on the RestrictionManager
+type Option func(options *options)
+
+// Options is a factory for all available options
+var Options options
+
+type options struct {
+ denyBaggageOnInitializationFailure bool
+ metrics *jaeger.Metrics
+ logger jaeger.Logger
+ hostPort string
+ refreshInterval time.Duration
+}
+
+// DenyBaggageOnInitializationFailure creates an Option that determines the startup failure mode of RestrictionManager.
+// If DenyBaggageOnInitializationFailure is true, RestrictionManager will not allow any baggage to be written until baggage
+// restrictions have been retrieved from agent.
+// If DenyBaggageOnInitializationFailure is false, RestrictionManager will allow any baggage to be written until baggage
+// restrictions have been retrieved from agent.
+func (options) DenyBaggageOnInitializationFailure(b bool) Option {
+ return func(o *options) {
+ o.denyBaggageOnInitializationFailure = b
+ }
+}
+
+// Metrics creates an Option that initializes Metrics on the RestrictionManager, which is used to emit statistics.
+func (options) Metrics(m *jaeger.Metrics) Option {
+ return func(o *options) {
+ o.metrics = m
+ }
+}
+
+// Logger creates an Option that sets the logger used by the RestrictionManager.
+func (options) Logger(logger jaeger.Logger) Option {
+ return func(o *options) {
+ o.logger = logger
+ }
+}
+
+// HostPort creates an Option that sets the hostPort of the local agent that contains the baggage restrictions.
+func (options) HostPort(hostPort string) Option {
+ return func(o *options) {
+ o.hostPort = hostPort
+ }
+}
+
+// RefreshInterval creates an Option that sets how often the RestrictionManager will poll local agent for
+// the baggage restrictions.
+func (options) RefreshInterval(refreshInterval time.Duration) Option {
+ return func(o *options) {
+ o.refreshInterval = refreshInterval
+ }
+}
+
+func applyOptions(o ...Option) options {
+ opts := options{}
+ for _, option := range o {
+ option(&opts)
+ }
+ if opts.metrics == nil {
+ opts.metrics = jaeger.NewNullMetrics()
+ }
+ if opts.logger == nil {
+ opts.logger = jaeger.NullLogger
+ }
+ if opts.hostPort == "" {
+ opts.hostPort = defaultHostPort
+ }
+ if opts.refreshInterval == 0 {
+ opts.refreshInterval = defaultRefreshInterval
+ }
+ return opts
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/internal/baggage/remote/restriction_manager.go b/vendor/github.com/uber/jaeger-client-go/internal/baggage/remote/restriction_manager.go
new file mode 100644
index 000000000..a56515aca
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/internal/baggage/remote/restriction_manager.go
@@ -0,0 +1,157 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package remote
+
+import (
+ "fmt"
+ "net/url"
+ "sync"
+ "time"
+
+ "github.com/uber/jaeger-client-go/internal/baggage"
+ thrift "github.com/uber/jaeger-client-go/thrift-gen/baggage"
+ "github.com/uber/jaeger-client-go/utils"
+)
+
+type httpBaggageRestrictionManagerProxy struct {
+ url string
+}
+
+func newHTTPBaggageRestrictionManagerProxy(hostPort, serviceName string) *httpBaggageRestrictionManagerProxy {
+ v := url.Values{}
+ v.Set("service", serviceName)
+ return &httpBaggageRestrictionManagerProxy{
+ url: fmt.Sprintf("http://%s/baggageRestrictions?%s", hostPort, v.Encode()),
+ }
+}
+
+func (s *httpBaggageRestrictionManagerProxy) GetBaggageRestrictions(serviceName string) ([]*thrift.BaggageRestriction, error) {
+ var out []*thrift.BaggageRestriction
+ if err := utils.GetJSON(s.url, &out); err != nil {
+ return nil, err
+ }
+ return out, nil
+}
+
+// RestrictionManager manages baggage restrictions by retrieving baggage restrictions from agent
+type RestrictionManager struct {
+ options
+
+ mux sync.RWMutex
+ serviceName string
+ restrictions map[string]*baggage.Restriction
+ thriftProxy thrift.BaggageRestrictionManager
+ pollStopped sync.WaitGroup
+ stopPoll chan struct{}
+ invalidRestriction *baggage.Restriction
+ validRestriction *baggage.Restriction
+
+ // Determines if the manager has successfully retrieved baggage restrictions from agent
+ initialized bool
+}
+
+// NewRestrictionManager returns a BaggageRestrictionManager that polls the agent for the latest
+// baggage restrictions.
+func NewRestrictionManager(serviceName string, options ...Option) *RestrictionManager {
+ // TODO there is a developing use case where a single tracer can generate traces on behalf of many services.
+ // restrictionsMap will need to exist per service
+ opts := applyOptions(options...)
+ m := &RestrictionManager{
+ serviceName: serviceName,
+ options: opts,
+ restrictions: make(map[string]*baggage.Restriction),
+ thriftProxy: newHTTPBaggageRestrictionManagerProxy(opts.hostPort, serviceName),
+ stopPoll: make(chan struct{}),
+ invalidRestriction: baggage.NewRestriction(false, 0),
+ validRestriction: baggage.NewRestriction(true, defaultMaxValueLength),
+ }
+ m.pollStopped.Add(1)
+ go m.pollManager()
+ return m
+}
+
+// isReady returns true if the manager has retrieved baggage restrictions from the remote source.
+func (m *RestrictionManager) isReady() bool {
+ m.mux.RLock()
+ defer m.mux.RUnlock()
+ return m.initialized
+}
+
+// GetRestriction implements RestrictionManager#GetRestriction.
+func (m *RestrictionManager) GetRestriction(service, key string) *baggage.Restriction {
+ m.mux.RLock()
+ defer m.mux.RUnlock()
+ if !m.initialized {
+ if m.denyBaggageOnInitializationFailure {
+ return m.invalidRestriction
+ }
+ return m.validRestriction
+ }
+ if restriction, ok := m.restrictions[key]; ok {
+ return restriction
+ }
+ return m.invalidRestriction
+}
+
+// Close stops remote polling and closes the RemoteRestrictionManager.
+func (m *RestrictionManager) Close() error {
+ close(m.stopPoll)
+ m.pollStopped.Wait()
+ return nil
+}
+
+func (m *RestrictionManager) pollManager() {
+ defer m.pollStopped.Done()
+ // attempt to initialize baggage restrictions
+ if err := m.updateRestrictions(); err != nil {
+ m.logger.Error(fmt.Sprintf("Failed to initialize baggage restrictions: %s", err.Error()))
+ }
+ ticker := time.NewTicker(m.refreshInterval)
+ defer ticker.Stop()
+
+ for {
+ select {
+ case <-ticker.C:
+ if err := m.updateRestrictions(); err != nil {
+ m.logger.Error(fmt.Sprintf("Failed to update baggage restrictions: %s", err.Error()))
+ }
+ case <-m.stopPoll:
+ return
+ }
+ }
+}
+
+func (m *RestrictionManager) updateRestrictions() error {
+ restrictions, err := m.thriftProxy.GetBaggageRestrictions(m.serviceName)
+ if err != nil {
+ m.metrics.BaggageRestrictionsUpdateFailure.Inc(1)
+ return err
+ }
+ newRestrictions := m.parseRestrictions(restrictions)
+ m.metrics.BaggageRestrictionsUpdateSuccess.Inc(1)
+ m.mux.Lock()
+ defer m.mux.Unlock()
+ m.initialized = true
+ m.restrictions = newRestrictions
+ return nil
+}
+
+func (m *RestrictionManager) parseRestrictions(restrictions []*thrift.BaggageRestriction) map[string]*baggage.Restriction {
+ setters := make(map[string]*baggage.Restriction, len(restrictions))
+ for _, restriction := range restrictions {
+ setters[restriction.BaggageKey] = baggage.NewRestriction(true, int(restriction.MaxValueLength))
+ }
+ return setters
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/internal/baggage/restriction_manager.go b/vendor/github.com/uber/jaeger-client-go/internal/baggage/restriction_manager.go
new file mode 100644
index 000000000..c16a5c566
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/internal/baggage/restriction_manager.go
@@ -0,0 +1,71 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package baggage
+
+const (
+ defaultMaxValueLength = 2048
+)
+
+// Restriction determines whether a baggage key is allowed and contains any restrictions on the baggage value.
+type Restriction struct {
+ keyAllowed bool
+ maxValueLength int
+}
+
+// NewRestriction returns a new Restriction.
+func NewRestriction(keyAllowed bool, maxValueLength int) *Restriction {
+ return &Restriction{
+ keyAllowed: keyAllowed,
+ maxValueLength: maxValueLength,
+ }
+}
+
+// KeyAllowed returns whether the baggage key for this restriction is allowed.
+func (r *Restriction) KeyAllowed() bool {
+ return r.keyAllowed
+}
+
+// MaxValueLength returns the max length for the baggage value.
+func (r *Restriction) MaxValueLength() int {
+ return r.maxValueLength
+}
+
+// RestrictionManager keeps track of valid baggage keys and their restrictions. The manager
+// will return a Restriction for a specific baggage key which will determine whether the baggage
+// key is allowed for the current service and any other applicable restrictions on the baggage
+// value.
+type RestrictionManager interface {
+ GetRestriction(service, key string) *Restriction
+}
+
+// DefaultRestrictionManager allows any baggage key.
+type DefaultRestrictionManager struct {
+ defaultRestriction *Restriction
+}
+
+// NewDefaultRestrictionManager returns a DefaultRestrictionManager.
+func NewDefaultRestrictionManager(maxValueLength int) *DefaultRestrictionManager {
+ if maxValueLength == 0 {
+ maxValueLength = defaultMaxValueLength
+ }
+ return &DefaultRestrictionManager{
+ defaultRestriction: &Restriction{keyAllowed: true, maxValueLength: maxValueLength},
+ }
+}
+
+// GetRestriction implements RestrictionManager#GetRestriction.
+func (m *DefaultRestrictionManager) GetRestriction(service, key string) *Restriction {
+ return m.defaultRestriction
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/internal/spanlog/json.go b/vendor/github.com/uber/jaeger-client-go/internal/spanlog/json.go
new file mode 100644
index 000000000..0e10b8a5a
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/internal/spanlog/json.go
@@ -0,0 +1,81 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package spanlog
+
+import (
+ "encoding/json"
+ "fmt"
+
+ "github.com/opentracing/opentracing-go/log"
+)
+
+type fieldsAsMap map[string]string
+
+// MaterializeWithJSON converts log Fields into JSON string
+// TODO refactor into pluggable materializer
+func MaterializeWithJSON(logFields []log.Field) ([]byte, error) {
+ fields := fieldsAsMap(make(map[string]string, len(logFields)))
+ for _, field := range logFields {
+ field.Marshal(fields)
+ }
+ if event, ok := fields["event"]; ok && len(fields) == 1 {
+ return []byte(event), nil
+ }
+ return json.Marshal(fields)
+}
+
+func (ml fieldsAsMap) EmitString(key, value string) {
+ ml[key] = value
+}
+
+func (ml fieldsAsMap) EmitBool(key string, value bool) {
+ ml[key] = fmt.Sprintf("%t", value)
+}
+
+func (ml fieldsAsMap) EmitInt(key string, value int) {
+ ml[key] = fmt.Sprintf("%d", value)
+}
+
+func (ml fieldsAsMap) EmitInt32(key string, value int32) {
+ ml[key] = fmt.Sprintf("%d", value)
+}
+
+func (ml fieldsAsMap) EmitInt64(key string, value int64) {
+ ml[key] = fmt.Sprintf("%d", value)
+}
+
+func (ml fieldsAsMap) EmitUint32(key string, value uint32) {
+ ml[key] = fmt.Sprintf("%d", value)
+}
+
+func (ml fieldsAsMap) EmitUint64(key string, value uint64) {
+ ml[key] = fmt.Sprintf("%d", value)
+}
+
+func (ml fieldsAsMap) EmitFloat32(key string, value float32) {
+ ml[key] = fmt.Sprintf("%f", value)
+}
+
+func (ml fieldsAsMap) EmitFloat64(key string, value float64) {
+ ml[key] = fmt.Sprintf("%f", value)
+}
+
+func (ml fieldsAsMap) EmitObject(key string, value interface{}) {
+ ml[key] = fmt.Sprintf("%+v", value)
+}
+
+func (ml fieldsAsMap) EmitLazyLogger(value log.LazyLogger) {
+ value(ml)
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/internal/throttler/remote/options.go b/vendor/github.com/uber/jaeger-client-go/internal/throttler/remote/options.go
new file mode 100644
index 000000000..f52c322fb
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/internal/throttler/remote/options.go
@@ -0,0 +1,99 @@
+// Copyright (c) 2018 The Jaeger Authors.
+//
+// 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.
+
+package remote
+
+import (
+ "time"
+
+ "github.com/uber/jaeger-client-go"
+)
+
+const (
+ defaultHostPort = "localhost:5778"
+ defaultRefreshInterval = time.Second * 5
+)
+
+// Option is a function that sets some option on the Throttler
+type Option func(options *options)
+
+// Options is a factory for all available options
+var Options options
+
+type options struct {
+ metrics *jaeger.Metrics
+ logger jaeger.Logger
+ hostPort string
+ refreshInterval time.Duration
+ synchronousInitialization bool
+}
+
+// Metrics creates an Option that initializes Metrics on the Throttler, which is used to emit statistics.
+func (options) Metrics(m *jaeger.Metrics) Option {
+ return func(o *options) {
+ o.metrics = m
+ }
+}
+
+// Logger creates an Option that sets the logger used by the Throttler.
+func (options) Logger(logger jaeger.Logger) Option {
+ return func(o *options) {
+ o.logger = logger
+ }
+}
+
+// HostPort creates an Option that sets the hostPort of the local agent that keeps track of credits.
+func (options) HostPort(hostPort string) Option {
+ return func(o *options) {
+ o.hostPort = hostPort
+ }
+}
+
+// RefreshInterval creates an Option that sets how often the Throttler will poll local agent for
+// credits.
+func (options) RefreshInterval(refreshInterval time.Duration) Option {
+ return func(o *options) {
+ o.refreshInterval = refreshInterval
+ }
+}
+
+// SynchronousInitialization creates an Option that determines whether the throttler should synchronously
+// fetch credits from the agent when an operation is seen for the first time. This should be set to true
+// if the client will be used by a short lived service that needs to ensure that credits are fetched upfront
+// such that sampling or throttling occurs.
+func (options) SynchronousInitialization(b bool) Option {
+ return func(o *options) {
+ o.synchronousInitialization = b
+ }
+}
+
+func applyOptions(o ...Option) options {
+ opts := options{}
+ for _, option := range o {
+ option(&opts)
+ }
+ if opts.metrics == nil {
+ opts.metrics = jaeger.NewNullMetrics()
+ }
+ if opts.logger == nil {
+ opts.logger = jaeger.NullLogger
+ }
+ if opts.hostPort == "" {
+ opts.hostPort = defaultHostPort
+ }
+ if opts.refreshInterval == 0 {
+ opts.refreshInterval = defaultRefreshInterval
+ }
+ return opts
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/internal/throttler/remote/throttler.go b/vendor/github.com/uber/jaeger-client-go/internal/throttler/remote/throttler.go
new file mode 100644
index 000000000..20f434fe4
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/internal/throttler/remote/throttler.go
@@ -0,0 +1,216 @@
+// Copyright (c) 2018 The Jaeger Authors.
+//
+// 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.
+
+package remote
+
+import (
+ "fmt"
+ "net/url"
+ "sync"
+ "sync/atomic"
+ "time"
+
+ "github.com/pkg/errors"
+
+ "github.com/uber/jaeger-client-go"
+ "github.com/uber/jaeger-client-go/utils"
+)
+
+const (
+ // minimumCredits is the minimum amount of credits necessary to not be throttled.
+ // i.e. if currentCredits > minimumCredits, then the operation will not be throttled.
+ minimumCredits = 1.0
+)
+
+var (
+ errorUUIDNotSet = errors.New("Throttler UUID must be set")
+)
+
+type operationBalance struct {
+ Operation string `json:"operation"`
+ Balance float64 `json:"balance"`
+}
+
+type creditResponse struct {
+ Balances []operationBalance `json:"balances"`
+}
+
+type httpCreditManagerProxy struct {
+ hostPort string
+}
+
+func newHTTPCreditManagerProxy(hostPort string) *httpCreditManagerProxy {
+ return &httpCreditManagerProxy{
+ hostPort: hostPort,
+ }
+}
+
+// N.B. Operations list must not be empty.
+func (m *httpCreditManagerProxy) FetchCredits(uuid, serviceName string, operations []string) (*creditResponse, error) {
+ params := url.Values{}
+ params.Set("service", serviceName)
+ params.Set("uuid", uuid)
+ for _, op := range operations {
+ params.Add("operations", op)
+ }
+ var resp creditResponse
+ if err := utils.GetJSON(fmt.Sprintf("http://%s/credits?%s", m.hostPort, params.Encode()), &resp); err != nil {
+ return nil, errors.Wrap(err, "Failed to receive credits from agent")
+ }
+ return &resp, nil
+}
+
+// Throttler retrieves credits from agent and uses it to throttle operations.
+type Throttler struct {
+ options
+
+ mux sync.RWMutex
+ service string
+ uuid atomic.Value
+ creditManager *httpCreditManagerProxy
+ credits map[string]float64 // map of operation->credits
+ close chan struct{}
+ stopped sync.WaitGroup
+}
+
+// NewThrottler returns a Throttler that polls agent for credits and uses them to throttle
+// the service.
+func NewThrottler(service string, options ...Option) *Throttler {
+ opts := applyOptions(options...)
+ creditManager := newHTTPCreditManagerProxy(opts.hostPort)
+ t := &Throttler{
+ options: opts,
+ creditManager: creditManager,
+ service: service,
+ credits: make(map[string]float64),
+ close: make(chan struct{}),
+ }
+ t.stopped.Add(1)
+ go t.pollManager()
+ return t
+}
+
+// IsAllowed implements Throttler#IsAllowed.
+func (t *Throttler) IsAllowed(operation string) bool {
+ t.mux.Lock()
+ defer t.mux.Unlock()
+ value, ok := t.credits[operation]
+ if !ok || value == 0 {
+ if !ok {
+ // NOTE: This appears to be a no-op at first glance, but it stores
+ // the operation key in the map. Necessary for functionality of
+ // Throttler#operations method.
+ t.credits[operation] = 0
+ }
+ if !t.synchronousInitialization {
+ t.metrics.ThrottledDebugSpans.Inc(1)
+ return false
+ }
+ // If it is the first time this operation is being checked, synchronously fetch
+ // the credits.
+ credits, err := t.fetchCredits([]string{operation})
+ if err != nil {
+ // Failed to receive credits from agent, try again next time
+ t.logger.Error("Failed to fetch credits: " + err.Error())
+ return false
+ }
+ if len(credits.Balances) == 0 {
+ // This shouldn't happen but just in case
+ return false
+ }
+ for _, opBalance := range credits.Balances {
+ t.credits[opBalance.Operation] += opBalance.Balance
+ }
+ }
+ return t.isAllowed(operation)
+}
+
+// Close stops the throttler from fetching credits from remote.
+func (t *Throttler) Close() error {
+ close(t.close)
+ t.stopped.Wait()
+ return nil
+}
+
+// SetProcess implements ProcessSetter#SetProcess. It's imperative that the UUID is set before any remote
+// requests are made.
+func (t *Throttler) SetProcess(process jaeger.Process) {
+ if process.UUID != "" {
+ t.uuid.Store(process.UUID)
+ }
+}
+
+// N.B. This function must be called with the Write Lock
+func (t *Throttler) isAllowed(operation string) bool {
+ credits := t.credits[operation]
+ if credits < minimumCredits {
+ t.metrics.ThrottledDebugSpans.Inc(1)
+ return false
+ }
+ t.credits[operation] = credits - minimumCredits
+ return true
+}
+
+func (t *Throttler) pollManager() {
+ defer t.stopped.Done()
+ ticker := time.NewTicker(t.refreshInterval)
+ defer ticker.Stop()
+ for {
+ select {
+ case <-ticker.C:
+ t.refreshCredits()
+ case <-t.close:
+ return
+ }
+ }
+}
+
+func (t *Throttler) operations() []string {
+ t.mux.RLock()
+ defer t.mux.RUnlock()
+ operations := make([]string, 0, len(t.credits))
+ for op := range t.credits {
+ operations = append(operations, op)
+ }
+ return operations
+}
+
+func (t *Throttler) refreshCredits() {
+ operations := t.operations()
+ if len(operations) == 0 {
+ return
+ }
+ newCredits, err := t.fetchCredits(operations)
+ if err != nil {
+ t.metrics.ThrottlerUpdateFailure.Inc(1)
+ t.logger.Error("Failed to fetch credits: " + err.Error())
+ return
+ }
+ t.metrics.ThrottlerUpdateSuccess.Inc(1)
+
+ t.mux.Lock()
+ defer t.mux.Unlock()
+ for _, opBalance := range newCredits.Balances {
+ t.credits[opBalance.Operation] += opBalance.Balance
+ }
+}
+
+func (t *Throttler) fetchCredits(operations []string) (*creditResponse, error) {
+ uuid := t.uuid.Load()
+ uuidStr, _ := uuid.(string)
+ if uuid == nil || uuidStr == "" {
+ return nil, errorUUIDNotSet
+ }
+ return t.creditManager.FetchCredits(uuidStr, t.service, operations)
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/internal/throttler/throttler.go b/vendor/github.com/uber/jaeger-client-go/internal/throttler/throttler.go
new file mode 100644
index 000000000..196ed69ca
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/internal/throttler/throttler.go
@@ -0,0 +1,32 @@
+// Copyright (c) 2018 The Jaeger Authors.
+//
+// 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.
+
+package throttler
+
+// Throttler is used to rate limits operations. For example, given how debug spans
+// are always sampled, a throttler can be enabled per client to rate limit the amount
+// of debug spans a client can start.
+type Throttler interface {
+ // IsAllowed determines whether the operation should be allowed and not be
+ // throttled.
+ IsAllowed(operation string) bool
+}
+
+// DefaultThrottler doesn't throttle at all.
+type DefaultThrottler struct{}
+
+// IsAllowed implements Throttler#IsAllowed.
+func (t DefaultThrottler) IsAllowed(operation string) bool {
+ return true
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/interop.go b/vendor/github.com/uber/jaeger-client-go/interop.go
new file mode 100644
index 000000000..8402d087c
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/interop.go
@@ -0,0 +1,55 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package jaeger
+
+import (
+ "github.com/opentracing/opentracing-go"
+)
+
+// TODO this file should not be needed after TChannel PR.
+
+type formatKey int
+
+// SpanContextFormat is a constant used as OpenTracing Format.
+// Requires *SpanContext as carrier.
+// This format is intended for interop with TChannel or other Zipkin-like tracers.
+const SpanContextFormat formatKey = iota
+
+type jaegerTraceContextPropagator struct {
+ tracer *Tracer
+}
+
+func (p *jaegerTraceContextPropagator) Inject(
+ ctx SpanContext,
+ abstractCarrier interface{},
+) error {
+ carrier, ok := abstractCarrier.(*SpanContext)
+ if !ok {
+ return opentracing.ErrInvalidCarrier
+ }
+
+ carrier.CopyFrom(&ctx)
+ return nil
+}
+
+func (p *jaegerTraceContextPropagator) Extract(abstractCarrier interface{}) (SpanContext, error) {
+ carrier, ok := abstractCarrier.(*SpanContext)
+ if !ok {
+ return emptyContext, opentracing.ErrInvalidCarrier
+ }
+ ctx := new(SpanContext)
+ ctx.CopyFrom(carrier)
+ return *ctx, nil
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/jaeger_tag.go b/vendor/github.com/uber/jaeger-client-go/jaeger_tag.go
new file mode 100644
index 000000000..868b2a5b5
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/jaeger_tag.go
@@ -0,0 +1,84 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package jaeger
+
+import (
+ "fmt"
+
+ "github.com/opentracing/opentracing-go/log"
+
+ j "github.com/uber/jaeger-client-go/thrift-gen/jaeger"
+)
+
+type tags []*j.Tag
+
+// ConvertLogsToJaegerTags converts log Fields into jaeger tags.
+func ConvertLogsToJaegerTags(logFields []log.Field) []*j.Tag {
+ fields := tags(make([]*j.Tag, 0, len(logFields)))
+ for _, field := range logFields {
+ field.Marshal(&fields)
+ }
+ return fields
+}
+
+func (t *tags) EmitString(key, value string) {
+ *t = append(*t, &j.Tag{Key: key, VType: j.TagType_STRING, VStr: &value})
+}
+
+func (t *tags) EmitBool(key string, value bool) {
+ *t = append(*t, &j.Tag{Key: key, VType: j.TagType_BOOL, VBool: &value})
+}
+
+func (t *tags) EmitInt(key string, value int) {
+ vLong := int64(value)
+ *t = append(*t, &j.Tag{Key: key, VType: j.TagType_LONG, VLong: &vLong})
+}
+
+func (t *tags) EmitInt32(key string, value int32) {
+ vLong := int64(value)
+ *t = append(*t, &j.Tag{Key: key, VType: j.TagType_LONG, VLong: &vLong})
+}
+
+func (t *tags) EmitInt64(key string, value int64) {
+ *t = append(*t, &j.Tag{Key: key, VType: j.TagType_LONG, VLong: &value})
+}
+
+func (t *tags) EmitUint32(key string, value uint32) {
+ vLong := int64(value)
+ *t = append(*t, &j.Tag{Key: key, VType: j.TagType_LONG, VLong: &vLong})
+}
+
+func (t *tags) EmitUint64(key string, value uint64) {
+ vLong := int64(value)
+ *t = append(*t, &j.Tag{Key: key, VType: j.TagType_LONG, VLong: &vLong})
+}
+
+func (t *tags) EmitFloat32(key string, value float32) {
+ vDouble := float64(value)
+ *t = append(*t, &j.Tag{Key: key, VType: j.TagType_DOUBLE, VDouble: &vDouble})
+}
+
+func (t *tags) EmitFloat64(key string, value float64) {
+ *t = append(*t, &j.Tag{Key: key, VType: j.TagType_DOUBLE, VDouble: &value})
+}
+
+func (t *tags) EmitObject(key string, value interface{}) {
+ vStr := fmt.Sprintf("%+v", value)
+ *t = append(*t, &j.Tag{Key: key, VType: j.TagType_STRING, VStr: &vStr})
+}
+
+func (t *tags) EmitLazyLogger(value log.LazyLogger) {
+ value(t)
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/jaeger_thrift_span.go b/vendor/github.com/uber/jaeger-client-go/jaeger_thrift_span.go
new file mode 100644
index 000000000..6ce1caf87
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/jaeger_thrift_span.go
@@ -0,0 +1,179 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package jaeger
+
+import (
+ "time"
+
+ "github.com/opentracing/opentracing-go"
+
+ j "github.com/uber/jaeger-client-go/thrift-gen/jaeger"
+ "github.com/uber/jaeger-client-go/utils"
+)
+
+// BuildJaegerThrift builds jaeger span based on internal span.
+func BuildJaegerThrift(span *Span) *j.Span {
+ span.Lock()
+ defer span.Unlock()
+ startTime := utils.TimeToMicrosecondsSinceEpochInt64(span.startTime)
+ duration := span.duration.Nanoseconds() / int64(time.Microsecond)
+ jaegerSpan := &j.Span{
+ TraceIdLow: int64(span.context.traceID.Low),
+ TraceIdHigh: int64(span.context.traceID.High),
+ SpanId: int64(span.context.spanID),
+ ParentSpanId: int64(span.context.parentID),
+ OperationName: span.operationName,
+ Flags: int32(span.context.flags),
+ StartTime: startTime,
+ Duration: duration,
+ Tags: buildTags(span.tags, span.tracer.options.maxTagValueLength),
+ Logs: buildLogs(span.logs),
+ References: buildReferences(span.references),
+ }
+ return jaegerSpan
+}
+
+// BuildJaegerProcessThrift creates a thrift Process type.
+func BuildJaegerProcessThrift(span *Span) *j.Process {
+ span.Lock()
+ defer span.Unlock()
+ return buildJaegerProcessThrift(span.tracer)
+}
+
+func buildJaegerProcessThrift(tracer *Tracer) *j.Process {
+ process := &j.Process{
+ ServiceName: tracer.serviceName,
+ Tags: buildTags(tracer.tags, tracer.options.maxTagValueLength),
+ }
+ if tracer.process.UUID != "" {
+ process.Tags = append(process.Tags, &j.Tag{Key: TracerUUIDTagKey, VStr: &tracer.process.UUID, VType: j.TagType_STRING})
+ }
+ return process
+}
+
+func buildTags(tags []Tag, maxTagValueLength int) []*j.Tag {
+ jTags := make([]*j.Tag, 0, len(tags))
+ for _, tag := range tags {
+ jTag := buildTag(&tag, maxTagValueLength)
+ jTags = append(jTags, jTag)
+ }
+ return jTags
+}
+
+func buildLogs(logs []opentracing.LogRecord) []*j.Log {
+ jLogs := make([]*j.Log, 0, len(logs))
+ for _, log := range logs {
+ jLog := &j.Log{
+ Timestamp: utils.TimeToMicrosecondsSinceEpochInt64(log.Timestamp),
+ Fields: ConvertLogsToJaegerTags(log.Fields),
+ }
+ jLogs = append(jLogs, jLog)
+ }
+ return jLogs
+}
+
+func buildTag(tag *Tag, maxTagValueLength int) *j.Tag {
+ jTag := &j.Tag{Key: tag.key}
+ switch value := tag.value.(type) {
+ case string:
+ vStr := truncateString(value, maxTagValueLength)
+ jTag.VStr = &vStr
+ jTag.VType = j.TagType_STRING
+ case []byte:
+ if len(value) > maxTagValueLength {
+ value = value[:maxTagValueLength]
+ }
+ jTag.VBinary = value
+ jTag.VType = j.TagType_BINARY
+ case int:
+ vLong := int64(value)
+ jTag.VLong = &vLong
+ jTag.VType = j.TagType_LONG
+ case uint:
+ vLong := int64(value)
+ jTag.VLong = &vLong
+ jTag.VType = j.TagType_LONG
+ case int8:
+ vLong := int64(value)
+ jTag.VLong = &vLong
+ jTag.VType = j.TagType_LONG
+ case uint8:
+ vLong := int64(value)
+ jTag.VLong = &vLong
+ jTag.VType = j.TagType_LONG
+ case int16:
+ vLong := int64(value)
+ jTag.VLong = &vLong
+ jTag.VType = j.TagType_LONG
+ case uint16:
+ vLong := int64(value)
+ jTag.VLong = &vLong
+ jTag.VType = j.TagType_LONG
+ case int32:
+ vLong := int64(value)
+ jTag.VLong = &vLong
+ jTag.VType = j.TagType_LONG
+ case uint32:
+ vLong := int64(value)
+ jTag.VLong = &vLong
+ jTag.VType = j.TagType_LONG
+ case int64:
+ vLong := int64(value)
+ jTag.VLong = &vLong
+ jTag.VType = j.TagType_LONG
+ case uint64:
+ vLong := int64(value)
+ jTag.VLong = &vLong
+ jTag.VType = j.TagType_LONG
+ case float32:
+ vDouble := float64(value)
+ jTag.VDouble = &vDouble
+ jTag.VType = j.TagType_DOUBLE
+ case float64:
+ vDouble := float64(value)
+ jTag.VDouble = &vDouble
+ jTag.VType = j.TagType_DOUBLE
+ case bool:
+ vBool := value
+ jTag.VBool = &vBool
+ jTag.VType = j.TagType_BOOL
+ default:
+ vStr := truncateString(stringify(value), maxTagValueLength)
+ jTag.VStr = &vStr
+ jTag.VType = j.TagType_STRING
+ }
+ return jTag
+}
+
+func buildReferences(references []Reference) []*j.SpanRef {
+ retMe := make([]*j.SpanRef, 0, len(references))
+ for _, ref := range references {
+ if ref.Type == opentracing.ChildOfRef {
+ retMe = append(retMe, spanRef(ref.Context, j.SpanRefType_CHILD_OF))
+ } else if ref.Type == opentracing.FollowsFromRef {
+ retMe = append(retMe, spanRef(ref.Context, j.SpanRefType_FOLLOWS_FROM))
+ }
+ }
+ return retMe
+}
+
+func spanRef(ctx SpanContext, refType j.SpanRefType) *j.SpanRef {
+ return &j.SpanRef{
+ RefType: refType,
+ TraceIdLow: int64(ctx.traceID.Low),
+ TraceIdHigh: int64(ctx.traceID.High),
+ SpanId: int64(ctx.spanID),
+ }
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/log/logger.go b/vendor/github.com/uber/jaeger-client-go/log/logger.go
new file mode 100644
index 000000000..894bb3dbf
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/log/logger.go
@@ -0,0 +1,90 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package log
+
+import (
+ "bytes"
+ "fmt"
+ "log"
+ "sync"
+)
+
+// Logger provides an abstract interface for logging from Reporters.
+// Applications can provide their own implementation of this interface to adapt
+// reporters logging to whatever logging library they prefer (stdlib log,
+// logrus, go-logging, etc).
+type Logger interface {
+ // Error logs a message at error priority
+ Error(msg string)
+
+ // Infof logs a message at info priority
+ Infof(msg string, args ...interface{})
+}
+
+// StdLogger is implementation of the Logger interface that delegates to default `log` package
+var StdLogger = &stdLogger{}
+
+type stdLogger struct{}
+
+func (l *stdLogger) Error(msg string) {
+ log.Printf("ERROR: %s", msg)
+}
+
+// Infof logs a message at info priority
+func (l *stdLogger) Infof(msg string, args ...interface{}) {
+ log.Printf(msg, args...)
+}
+
+// NullLogger is implementation of the Logger interface that is no-op
+var NullLogger = &nullLogger{}
+
+type nullLogger struct{}
+
+func (l *nullLogger) Error(msg string) {}
+func (l *nullLogger) Infof(msg string, args ...interface{}) {}
+
+// BytesBufferLogger implements Logger backed by a bytes.Buffer.
+type BytesBufferLogger struct {
+ mux sync.Mutex
+ buf bytes.Buffer
+}
+
+// Error implements Logger.
+func (l *BytesBufferLogger) Error(msg string) {
+ l.mux.Lock()
+ l.buf.WriteString(fmt.Sprintf("ERROR: %s\n", msg))
+ l.mux.Unlock()
+}
+
+// Infof implements Logger.
+func (l *BytesBufferLogger) Infof(msg string, args ...interface{}) {
+ l.mux.Lock()
+ l.buf.WriteString("INFO: " + fmt.Sprintf(msg, args...) + "\n")
+ l.mux.Unlock()
+}
+
+// String returns string representation of the underlying buffer.
+func (l *BytesBufferLogger) String() string {
+ l.mux.Lock()
+ defer l.mux.Unlock()
+ return l.buf.String()
+}
+
+// Flush empties the underlying buffer.
+func (l *BytesBufferLogger) Flush() {
+ l.mux.Lock()
+ defer l.mux.Unlock()
+ l.buf.Reset()
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/logger.go b/vendor/github.com/uber/jaeger-client-go/logger.go
new file mode 100644
index 000000000..d4f0b5019
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/logger.go
@@ -0,0 +1,53 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package jaeger
+
+import "log"
+
+// NB This will be deprecated in 3.0.0, please use jaeger-client-go/log/logger instead.
+
+// Logger provides an abstract interface for logging from Reporters.
+// Applications can provide their own implementation of this interface to adapt
+// reporters logging to whatever logging library they prefer (stdlib log,
+// logrus, go-logging, etc).
+type Logger interface {
+ // Error logs a message at error priority
+ Error(msg string)
+
+ // Infof logs a message at info priority
+ Infof(msg string, args ...interface{})
+}
+
+// StdLogger is implementation of the Logger interface that delegates to default `log` package
+var StdLogger = &stdLogger{}
+
+type stdLogger struct{}
+
+func (l *stdLogger) Error(msg string) {
+ log.Printf("ERROR: %s", msg)
+}
+
+// Infof logs a message at info priority
+func (l *stdLogger) Infof(msg string, args ...interface{}) {
+ log.Printf(msg, args...)
+}
+
+// NullLogger is implementation of the Logger interface that delegates to default `log` package
+var NullLogger = &nullLogger{}
+
+type nullLogger struct{}
+
+func (l *nullLogger) Error(msg string) {}
+func (l *nullLogger) Infof(msg string, args ...interface{}) {}
diff --git a/vendor/github.com/uber/jaeger-client-go/metrics.go b/vendor/github.com/uber/jaeger-client-go/metrics.go
new file mode 100644
index 000000000..cadb2b9c0
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/metrics.go
@@ -0,0 +1,107 @@
+// Copyright (c) 2017-2018 Uber Technologies, Inc.
+//
+// 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.
+
+package jaeger
+
+import (
+ "github.com/uber/jaeger-lib/metrics"
+)
+
+// Metrics is a container of all stats emitted by Jaeger tracer.
+type Metrics struct {
+ // Number of traces started by this tracer as sampled
+ TracesStartedSampled metrics.Counter `metric:"traces" tags:"state=started,sampled=y"`
+
+ // Number of traces started by this tracer as not sampled
+ TracesStartedNotSampled metrics.Counter `metric:"traces" tags:"state=started,sampled=n"`
+
+ // Number of externally started sampled traces this tracer joined
+ TracesJoinedSampled metrics.Counter `metric:"traces" tags:"state=joined,sampled=y"`
+
+ // Number of externally started not-sampled traces this tracer joined
+ TracesJoinedNotSampled metrics.Counter `metric:"traces" tags:"state=joined,sampled=n"`
+
+ // Number of sampled spans started by this tracer
+ SpansStartedSampled metrics.Counter `metric:"started_spans" tags:"sampled=y"`
+
+ // Number of unsampled spans started by this tracer
+ SpansStartedNotSampled metrics.Counter `metric:"started_spans" tags:"sampled=n"`
+
+ // Number of spans finished by this tracer
+ SpansFinished metrics.Counter `metric:"finished_spans"`
+
+ // Number of errors decoding tracing context
+ DecodingErrors metrics.Counter `metric:"span_context_decoding_errors"`
+
+ // Number of spans successfully reported
+ ReporterSuccess metrics.Counter `metric:"reporter_spans" tags:"result=ok"`
+
+ // Number of spans not reported due to a Sender failure
+ ReporterFailure metrics.Counter `metric:"reporter_spans" tags:"result=err"`
+
+ // Number of spans dropped due to internal queue overflow
+ ReporterDropped metrics.Counter `metric:"reporter_spans" tags:"result=dropped"`
+
+ // Current number of spans in the reporter queue
+ ReporterQueueLength metrics.Gauge `metric:"reporter_queue_length"`
+
+ // Number of times the Sampler succeeded to retrieve sampling strategy
+ SamplerRetrieved metrics.Counter `metric:"sampler_queries" tags:"result=ok"`
+
+ // Number of times the Sampler failed to retrieve sampling strategy
+ SamplerQueryFailure metrics.Counter `metric:"sampler_queries" tags:"result=err"`
+
+ // Number of times the Sampler succeeded to retrieve and update sampling strategy
+ SamplerUpdated metrics.Counter `metric:"sampler_updates" tags:"result=ok"`
+
+ // Number of times the Sampler failed to update sampling strategy
+ SamplerUpdateFailure metrics.Counter `metric:"sampler_updates" tags:"result=err"`
+
+ // Number of times baggage was successfully written or updated on spans.
+ BaggageUpdateSuccess metrics.Counter `metric:"baggage_updates" tags:"result=ok"`
+
+ // Number of times baggage failed to write or update on spans.
+ BaggageUpdateFailure metrics.Counter `metric:"baggage_updates" tags:"result=err"`
+
+ // Number of times baggage was truncated as per baggage restrictions.
+ BaggageTruncate metrics.Counter `metric:"baggage_truncations"`
+
+ // Number of times baggage restrictions were successfully updated.
+ BaggageRestrictionsUpdateSuccess metrics.Counter `metric:"baggage_restrictions_updates" tags:"result=ok"`
+
+ // Number of times baggage restrictions failed to update.
+ BaggageRestrictionsUpdateFailure metrics.Counter `metric:"baggage_restrictions_updates" tags:"result=err"`
+
+ // Number of times debug spans were throttled.
+ ThrottledDebugSpans metrics.Counter `metric:"throttled_debug_spans"`
+
+ // Number of times throttler successfully updated.
+ ThrottlerUpdateSuccess metrics.Counter `metric:"throttler_updates" tags:"result=ok"`
+
+ // Number of times throttler failed to update.
+ ThrottlerUpdateFailure metrics.Counter `metric:"throttler_updates" tags:"result=err"`
+}
+
+// NewMetrics creates a new Metrics struct and initializes it.
+func NewMetrics(factory metrics.Factory, globalTags map[string]string) *Metrics {
+ m := &Metrics{}
+ // TODO the namespace "jaeger" should be configurable (e.g. in all-in-one "jaeger-client" would make more sense)
+ metrics.Init(m, factory.Namespace("jaeger", nil), globalTags)
+ return m
+}
+
+// NewNullMetrics creates a new Metrics struct that won't report any metrics.
+func NewNullMetrics() *Metrics {
+ return NewMetrics(metrics.NullFactory, nil)
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/observer.go b/vendor/github.com/uber/jaeger-client-go/observer.go
new file mode 100644
index 000000000..7bbd02889
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/observer.go
@@ -0,0 +1,88 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package jaeger
+
+import opentracing "github.com/opentracing/opentracing-go"
+
+// Observer can be registered with the Tracer to receive notifications about
+// new Spans.
+//
+// Deprecated: use jaeger.ContribObserver instead.
+type Observer interface {
+ OnStartSpan(operationName string, options opentracing.StartSpanOptions) SpanObserver
+}
+
+// SpanObserver is created by the Observer and receives notifications about
+// other Span events.
+//
+// Deprecated: use jaeger.ContribSpanObserver instead.
+type SpanObserver interface {
+ OnSetOperationName(operationName string)
+ OnSetTag(key string, value interface{})
+ OnFinish(options opentracing.FinishOptions)
+}
+
+// compositeObserver is a dispatcher to other observers
+type compositeObserver struct {
+ observers []ContribObserver
+}
+
+// compositeSpanObserver is a dispatcher to other span observers
+type compositeSpanObserver struct {
+ observers []ContribSpanObserver
+}
+
+// noopSpanObserver is used when there are no observers registered
+// on the Tracer or none of them returns span observers from OnStartSpan.
+var noopSpanObserver = &compositeSpanObserver{}
+
+func (o *compositeObserver) append(contribObserver ContribObserver) {
+ o.observers = append(o.observers, contribObserver)
+}
+
+func (o *compositeObserver) OnStartSpan(sp opentracing.Span, operationName string, options opentracing.StartSpanOptions) ContribSpanObserver {
+ var spanObservers []ContribSpanObserver
+ for _, obs := range o.observers {
+ spanObs, ok := obs.OnStartSpan(sp, operationName, options)
+ if ok {
+ if spanObservers == nil {
+ spanObservers = make([]ContribSpanObserver, 0, len(o.observers))
+ }
+ spanObservers = append(spanObservers, spanObs)
+ }
+ }
+ if len(spanObservers) == 0 {
+ return noopSpanObserver
+ }
+ return &compositeSpanObserver{observers: spanObservers}
+}
+
+func (o *compositeSpanObserver) OnSetOperationName(operationName string) {
+ for _, obs := range o.observers {
+ obs.OnSetOperationName(operationName)
+ }
+}
+
+func (o *compositeSpanObserver) OnSetTag(key string, value interface{}) {
+ for _, obs := range o.observers {
+ obs.OnSetTag(key, value)
+ }
+}
+
+func (o *compositeSpanObserver) OnFinish(options opentracing.FinishOptions) {
+ for _, obs := range o.observers {
+ obs.OnFinish(options)
+ }
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/process.go b/vendor/github.com/uber/jaeger-client-go/process.go
new file mode 100644
index 000000000..30cbf9962
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/process.go
@@ -0,0 +1,29 @@
+// Copyright (c) 2018 The Jaeger Authors.
+//
+// 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.
+
+package jaeger
+
+// Process holds process specific metadata that's relevant to this client.
+type Process struct {
+ Service string
+ UUID string
+ Tags []Tag
+}
+
+// ProcessSetter sets a process. This can be used by any class that requires
+// the process to be set as part of initialization.
+// See internal/throttler/remote/throttler.go for an example.
+type ProcessSetter interface {
+ SetProcess(process Process)
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/propagation.go b/vendor/github.com/uber/jaeger-client-go/propagation.go
new file mode 100644
index 000000000..abca67a3c
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/propagation.go
@@ -0,0 +1,300 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package jaeger
+
+import (
+ "bytes"
+ "encoding/binary"
+ "fmt"
+ "io"
+ "log"
+ "net/url"
+ "strings"
+ "sync"
+
+ opentracing "github.com/opentracing/opentracing-go"
+)
+
+// Injector is responsible for injecting SpanContext instances in a manner suitable
+// for propagation via a format-specific "carrier" object. Typically the
+// injection will take place across an RPC boundary, but message queues and
+// other IPC mechanisms are also reasonable places to use an Injector.
+type Injector interface {
+ // Inject takes `SpanContext` and injects it into `carrier`. The actual type
+ // of `carrier` depends on the `format` passed to `Tracer.Inject()`.
+ //
+ // Implementations may return opentracing.ErrInvalidCarrier or any other
+ // implementation-specific error if injection fails.
+ Inject(ctx SpanContext, carrier interface{}) error
+}
+
+// Extractor is responsible for extracting SpanContext instances from a
+// format-specific "carrier" object. Typically the extraction will take place
+// on the server side of an RPC boundary, but message queues and other IPC
+// mechanisms are also reasonable places to use an Extractor.
+type Extractor interface {
+ // Extract decodes a SpanContext instance from the given `carrier`,
+ // or (nil, opentracing.ErrSpanContextNotFound) if no context could
+ // be found in the `carrier`.
+ Extract(carrier interface{}) (SpanContext, error)
+}
+
+type textMapPropagator struct {
+ headerKeys *HeadersConfig
+ metrics Metrics
+ encodeValue func(string) string
+ decodeValue func(string) string
+}
+
+func newTextMapPropagator(headerKeys *HeadersConfig, metrics Metrics) *textMapPropagator {
+ return &textMapPropagator{
+ headerKeys: headerKeys,
+ metrics: metrics,
+ encodeValue: func(val string) string {
+ return val
+ },
+ decodeValue: func(val string) string {
+ return val
+ },
+ }
+}
+
+func newHTTPHeaderPropagator(headerKeys *HeadersConfig, metrics Metrics) *textMapPropagator {
+ return &textMapPropagator{
+ headerKeys: headerKeys,
+ metrics: metrics,
+ encodeValue: func(val string) string {
+ return url.QueryEscape(val)
+ },
+ decodeValue: func(val string) string {
+ // ignore decoding errors, cannot do anything about them
+ if v, err := url.QueryUnescape(val); err == nil {
+ return v
+ }
+ return val
+ },
+ }
+}
+
+type binaryPropagator struct {
+ tracer *Tracer
+ buffers sync.Pool
+}
+
+func newBinaryPropagator(tracer *Tracer) *binaryPropagator {
+ return &binaryPropagator{
+ tracer: tracer,
+ buffers: sync.Pool{New: func() interface{} { return &bytes.Buffer{} }},
+ }
+}
+
+func (p *textMapPropagator) Inject(
+ sc SpanContext,
+ abstractCarrier interface{},
+) error {
+ textMapWriter, ok := abstractCarrier.(opentracing.TextMapWriter)
+ if !ok {
+ return opentracing.ErrInvalidCarrier
+ }
+
+ // Do not encode the string with trace context to avoid accidental double-encoding
+ // if people are using opentracing < 0.10.0. Our colon-separated representation
+ // of the trace context is already safe for HTTP headers.
+ textMapWriter.Set(p.headerKeys.TraceContextHeaderName, sc.String())
+ for k, v := range sc.baggage {
+ safeKey := p.addBaggageKeyPrefix(k)
+ safeVal := p.encodeValue(v)
+ textMapWriter.Set(safeKey, safeVal)
+ }
+ return nil
+}
+
+func (p *textMapPropagator) Extract(abstractCarrier interface{}) (SpanContext, error) {
+ textMapReader, ok := abstractCarrier.(opentracing.TextMapReader)
+ if !ok {
+ return emptyContext, opentracing.ErrInvalidCarrier
+ }
+ var ctx SpanContext
+ var baggage map[string]string
+ err := textMapReader.ForeachKey(func(rawKey, value string) error {
+ key := strings.ToLower(rawKey) // TODO not necessary for plain TextMap
+ if key == p.headerKeys.TraceContextHeaderName {
+ var err error
+ safeVal := p.decodeValue(value)
+ if ctx, err = ContextFromString(safeVal); err != nil {
+ return err
+ }
+ } else if key == p.headerKeys.JaegerDebugHeader {
+ ctx.debugID = p.decodeValue(value)
+ } else if key == p.headerKeys.JaegerBaggageHeader {
+ if baggage == nil {
+ baggage = make(map[string]string)
+ }
+ for k, v := range p.parseCommaSeparatedMap(value) {
+ baggage[k] = v
+ }
+ } else if strings.HasPrefix(key, p.headerKeys.TraceBaggageHeaderPrefix) {
+ if baggage == nil {
+ baggage = make(map[string]string)
+ }
+ safeKey := p.removeBaggageKeyPrefix(key)
+ safeVal := p.decodeValue(value)
+ baggage[safeKey] = safeVal
+ }
+ return nil
+ })
+ if err != nil {
+ p.metrics.DecodingErrors.Inc(1)
+ return emptyContext, err
+ }
+ if !ctx.traceID.IsValid() && ctx.debugID == "" && len(baggage) == 0 {
+ return emptyContext, opentracing.ErrSpanContextNotFound
+ }
+ ctx.baggage = baggage
+ return ctx, nil
+}
+
+func (p *binaryPropagator) Inject(
+ sc SpanContext,
+ abstractCarrier interface{},
+) error {
+ carrier, ok := abstractCarrier.(io.Writer)
+ if !ok {
+ return opentracing.ErrInvalidCarrier
+ }
+
+ // Handle the tracer context
+ if err := binary.Write(carrier, binary.BigEndian, sc.traceID); err != nil {
+ return err
+ }
+ if err := binary.Write(carrier, binary.BigEndian, sc.spanID); err != nil {
+ return err
+ }
+ if err := binary.Write(carrier, binary.BigEndian, sc.parentID); err != nil {
+ return err
+ }
+ if err := binary.Write(carrier, binary.BigEndian, sc.flags); err != nil {
+ return err
+ }
+
+ // Handle the baggage items
+ if err := binary.Write(carrier, binary.BigEndian, int32(len(sc.baggage))); err != nil {
+ return err
+ }
+ for k, v := range sc.baggage {
+ if err := binary.Write(carrier, binary.BigEndian, int32(len(k))); err != nil {
+ return err
+ }
+ io.WriteString(carrier, k)
+ if err := binary.Write(carrier, binary.BigEndian, int32(len(v))); err != nil {
+ return err
+ }
+ io.WriteString(carrier, v)
+ }
+
+ return nil
+}
+
+func (p *binaryPropagator) Extract(abstractCarrier interface{}) (SpanContext, error) {
+ carrier, ok := abstractCarrier.(io.Reader)
+ if !ok {
+ return emptyContext, opentracing.ErrInvalidCarrier
+ }
+ var ctx SpanContext
+
+ if err := binary.Read(carrier, binary.BigEndian, &ctx.traceID); err != nil {
+ return emptyContext, opentracing.ErrSpanContextCorrupted
+ }
+ if err := binary.Read(carrier, binary.BigEndian, &ctx.spanID); err != nil {
+ return emptyContext, opentracing.ErrSpanContextCorrupted
+ }
+ if err := binary.Read(carrier, binary.BigEndian, &ctx.parentID); err != nil {
+ return emptyContext, opentracing.ErrSpanContextCorrupted
+ }
+ if err := binary.Read(carrier, binary.BigEndian, &ctx.flags); err != nil {
+ return emptyContext, opentracing.ErrSpanContextCorrupted
+ }
+
+ // Handle the baggage items
+ var numBaggage int32
+ if err := binary.Read(carrier, binary.BigEndian, &numBaggage); err != nil {
+ return emptyContext, opentracing.ErrSpanContextCorrupted
+ }
+ if iNumBaggage := int(numBaggage); iNumBaggage > 0 {
+ ctx.baggage = make(map[string]string, iNumBaggage)
+ buf := p.buffers.Get().(*bytes.Buffer)
+ defer p.buffers.Put(buf)
+
+ var keyLen, valLen int32
+ for i := 0; i < iNumBaggage; i++ {
+ if err := binary.Read(carrier, binary.BigEndian, &keyLen); err != nil {
+ return emptyContext, opentracing.ErrSpanContextCorrupted
+ }
+ buf.Reset()
+ buf.Grow(int(keyLen))
+ if n, err := io.CopyN(buf, carrier, int64(keyLen)); err != nil || int32(n) != keyLen {
+ return emptyContext, opentracing.ErrSpanContextCorrupted
+ }
+ key := buf.String()
+
+ if err := binary.Read(carrier, binary.BigEndian, &valLen); err != nil {
+ return emptyContext, opentracing.ErrSpanContextCorrupted
+ }
+ buf.Reset()
+ buf.Grow(int(valLen))
+ if n, err := io.CopyN(buf, carrier, int64(valLen)); err != nil || int32(n) != valLen {
+ return emptyContext, opentracing.ErrSpanContextCorrupted
+ }
+ ctx.baggage[key] = buf.String()
+ }
+ }
+
+ return ctx, nil
+}
+
+// Converts a comma separated key value pair list into a map
+// e.g. key1=value1, key2=value2, key3 = value3
+// is converted to map[string]string { "key1" : "value1",
+// "key2" : "value2",
+// "key3" : "value3" }
+func (p *textMapPropagator) parseCommaSeparatedMap(value string) map[string]string {
+ baggage := make(map[string]string)
+ value, err := url.QueryUnescape(value)
+ if err != nil {
+ log.Printf("Unable to unescape %s, %v", value, err)
+ return baggage
+ }
+ for _, kvpair := range strings.Split(value, ",") {
+ kv := strings.Split(strings.TrimSpace(kvpair), "=")
+ if len(kv) == 2 {
+ baggage[kv[0]] = kv[1]
+ } else {
+ log.Printf("Malformed value passed in for %s", p.headerKeys.JaegerBaggageHeader)
+ }
+ }
+ return baggage
+}
+
+// Converts a baggage item key into an http header format,
+// by prepending TraceBaggageHeaderPrefix and encoding the key string
+func (p *textMapPropagator) addBaggageKeyPrefix(key string) string {
+ // TODO encodeBaggageKeyAsHeader add caching and escaping
+ return fmt.Sprintf("%v%v", p.headerKeys.TraceBaggageHeaderPrefix, key)
+}
+
+func (p *textMapPropagator) removeBaggageKeyPrefix(key string) string {
+ // TODO decodeBaggageHeaderKey add caching and escaping
+ return key[len(p.headerKeys.TraceBaggageHeaderPrefix):]
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/reference.go b/vendor/github.com/uber/jaeger-client-go/reference.go
new file mode 100644
index 000000000..5646e78bb
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/reference.go
@@ -0,0 +1,23 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package jaeger
+
+import "github.com/opentracing/opentracing-go"
+
+// Reference represents a causal reference to other Spans (via their SpanContext).
+type Reference struct {
+ Type opentracing.SpanReferenceType
+ Context SpanContext
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/reporter.go b/vendor/github.com/uber/jaeger-client-go/reporter.go
new file mode 100644
index 000000000..fe6288c4b
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/reporter.go
@@ -0,0 +1,289 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package jaeger
+
+import (
+ "fmt"
+ "sync"
+ "sync/atomic"
+ "time"
+
+ "github.com/opentracing/opentracing-go"
+
+ "github.com/uber/jaeger-client-go/log"
+)
+
+// Reporter is called by the tracer when a span is completed to report the span to the tracing collector.
+type Reporter interface {
+ // Report submits a new span to collectors, possibly asynchronously and/or with buffering.
+ Report(span *Span)
+
+ // Close does a clean shutdown of the reporter, flushing any traces that may be buffered in memory.
+ Close()
+}
+
+// ------------------------------
+
+type nullReporter struct{}
+
+// NewNullReporter creates a no-op reporter that ignores all reported spans.
+func NewNullReporter() Reporter {
+ return &nullReporter{}
+}
+
+// Report implements Report() method of Reporter by doing nothing.
+func (r *nullReporter) Report(span *Span) {
+ // no-op
+}
+
+// Close implements Close() method of Reporter by doing nothing.
+func (r *nullReporter) Close() {
+ // no-op
+}
+
+// ------------------------------
+
+type loggingReporter struct {
+ logger Logger
+}
+
+// NewLoggingReporter creates a reporter that logs all reported spans to provided logger.
+func NewLoggingReporter(logger Logger) Reporter {
+ return &loggingReporter{logger}
+}
+
+// Report implements Report() method of Reporter by logging the span to the logger.
+func (r *loggingReporter) Report(span *Span) {
+ r.logger.Infof("Reporting span %+v", span)
+}
+
+// Close implements Close() method of Reporter by doing nothing.
+func (r *loggingReporter) Close() {
+ // no-op
+}
+
+// ------------------------------
+
+// InMemoryReporter is used for testing, and simply collects spans in memory.
+type InMemoryReporter struct {
+ spans []opentracing.Span
+ lock sync.Mutex
+}
+
+// NewInMemoryReporter creates a reporter that stores spans in memory.
+// NOTE: the Tracer should be created with options.PoolSpans = false.
+func NewInMemoryReporter() *InMemoryReporter {
+ return &InMemoryReporter{
+ spans: make([]opentracing.Span, 0, 10),
+ }
+}
+
+// Report implements Report() method of Reporter by storing the span in the buffer.
+func (r *InMemoryReporter) Report(span *Span) {
+ r.lock.Lock()
+ r.spans = append(r.spans, span)
+ r.lock.Unlock()
+}
+
+// Close implements Close() method of Reporter by doing nothing.
+func (r *InMemoryReporter) Close() {
+ // no-op
+}
+
+// SpansSubmitted returns the number of spans accumulated in the buffer.
+func (r *InMemoryReporter) SpansSubmitted() int {
+ r.lock.Lock()
+ defer r.lock.Unlock()
+ return len(r.spans)
+}
+
+// GetSpans returns accumulated spans as a copy of the buffer.
+func (r *InMemoryReporter) GetSpans() []opentracing.Span {
+ r.lock.Lock()
+ defer r.lock.Unlock()
+ copied := make([]opentracing.Span, len(r.spans))
+ copy(copied, r.spans)
+ return copied
+}
+
+// Reset clears all accumulated spans.
+func (r *InMemoryReporter) Reset() {
+ r.lock.Lock()
+ defer r.lock.Unlock()
+ r.spans = nil
+}
+
+// ------------------------------
+
+type compositeReporter struct {
+ reporters []Reporter
+}
+
+// NewCompositeReporter creates a reporter that ignores all reported spans.
+func NewCompositeReporter(reporters ...Reporter) Reporter {
+ return &compositeReporter{reporters: reporters}
+}
+
+// Report implements Report() method of Reporter by delegating to each underlying reporter.
+func (r *compositeReporter) Report(span *Span) {
+ for _, reporter := range r.reporters {
+ reporter.Report(span)
+ }
+}
+
+// Close implements Close() method of Reporter by closing each underlying reporter.
+func (r *compositeReporter) Close() {
+ for _, reporter := range r.reporters {
+ reporter.Close()
+ }
+}
+
+// ------------- REMOTE REPORTER -----------------
+
+type reporterQueueItemType int
+
+const (
+ defaultQueueSize = 100
+ defaultBufferFlushInterval = 1 * time.Second
+
+ reporterQueueItemSpan reporterQueueItemType = iota
+ reporterQueueItemClose
+)
+
+type reporterQueueItem struct {
+ itemType reporterQueueItemType
+ span *Span
+ close *sync.WaitGroup
+}
+
+type remoteReporter struct {
+ // These fields must be first in the struct because `sync/atomic` expects 64-bit alignment.
+ // Cf. https://github.com/uber/jaeger-client-go/issues/155, https://goo.gl/zW7dgq
+ queueLength int64
+ closed int64 // 0 - not closed, 1 - closed
+
+ reporterOptions
+
+ sender Transport
+ queue chan reporterQueueItem
+}
+
+// NewRemoteReporter creates a new reporter that sends spans out of process by means of Sender.
+// Calls to Report(Span) return immediately (side effect: if internal buffer is full the span is dropped).
+// Periodically the transport buffer is flushed even if it hasn't reached max packet size.
+// Calls to Close() block until all spans reported prior to the call to Close are flushed.
+func NewRemoteReporter(sender Transport, opts ...ReporterOption) Reporter {
+ options := reporterOptions{}
+ for _, option := range opts {
+ option(&options)
+ }
+ if options.bufferFlushInterval <= 0 {
+ options.bufferFlushInterval = defaultBufferFlushInterval
+ }
+ if options.logger == nil {
+ options.logger = log.NullLogger
+ }
+ if options.metrics == nil {
+ options.metrics = NewNullMetrics()
+ }
+ if options.queueSize <= 0 {
+ options.queueSize = defaultQueueSize
+ }
+ reporter := &remoteReporter{
+ reporterOptions: options,
+ sender: sender,
+ queue: make(chan reporterQueueItem, options.queueSize),
+ }
+ go reporter.processQueue()
+ return reporter
+}
+
+// Report implements Report() method of Reporter.
+// It passes the span to a background go-routine for submission to Jaeger backend.
+// If the internal queue is full, the span is dropped and metrics.ReporterDropped counter is incremented.
+// If Report() is called after the reporter has been Close()-ed, the additional spans will not be
+// sent to the backend, but the metrics.ReporterDropped counter may not reflect them correctly,
+// because some of them may still be successfully added to the queue.
+func (r *remoteReporter) Report(span *Span) {
+ select {
+ case r.queue <- reporterQueueItem{itemType: reporterQueueItemSpan, span: span}:
+ atomic.AddInt64(&r.queueLength, 1)
+ default:
+ r.metrics.ReporterDropped.Inc(1)
+ }
+}
+
+// Close implements Close() method of Reporter by waiting for the queue to be drained.
+func (r *remoteReporter) Close() {
+ if swapped := atomic.CompareAndSwapInt64(&r.closed, 0, 1); !swapped {
+ r.logger.Error("Repeated attempt to close the reporter is ignored")
+ return
+ }
+ r.sendCloseEvent()
+ r.sender.Close()
+}
+
+func (r *remoteReporter) sendCloseEvent() {
+ wg := &sync.WaitGroup{}
+ wg.Add(1)
+ item := reporterQueueItem{itemType: reporterQueueItemClose, close: wg}
+
+ r.queue <- item // if the queue is full we will block until there is space
+ atomic.AddInt64(&r.queueLength, 1)
+ wg.Wait()
+}
+
+// processQueue reads spans from the queue, converts them to Thrift, and stores them in an internal buffer.
+// When the buffer length reaches batchSize, it is flushed by submitting the accumulated spans to Jaeger.
+// Buffer also gets flushed automatically every batchFlushInterval seconds, just in case the tracer stopped
+// reporting new spans.
+func (r *remoteReporter) processQueue() {
+ // flush causes the Sender to flush its accumulated spans and clear the buffer
+ flush := func() {
+ if flushed, err := r.sender.Flush(); err != nil {
+ r.metrics.ReporterFailure.Inc(int64(flushed))
+ r.logger.Error(fmt.Sprintf("error when flushing the buffer: %s", err.Error()))
+ } else if flushed > 0 {
+ r.metrics.ReporterSuccess.Inc(int64(flushed))
+ }
+ }
+
+ timer := time.NewTicker(r.bufferFlushInterval)
+ for {
+ select {
+ case <-timer.C:
+ flush()
+ case item := <-r.queue:
+ atomic.AddInt64(&r.queueLength, -1)
+ switch item.itemType {
+ case reporterQueueItemSpan:
+ span := item.span
+ if flushed, err := r.sender.Append(span); err != nil {
+ r.metrics.ReporterFailure.Inc(int64(flushed))
+ r.logger.Error(fmt.Sprintf("error reporting span %q: %s", span.OperationName(), err.Error()))
+ } else if flushed > 0 {
+ r.metrics.ReporterSuccess.Inc(int64(flushed))
+ // to reduce the number of gauge stats, we only emit queue length on flush
+ r.metrics.ReporterQueueLength.Update(atomic.LoadInt64(&r.queueLength))
+ }
+ case reporterQueueItemClose:
+ timer.Stop()
+ flush()
+ item.close.Done()
+ return
+ }
+ }
+ }
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/reporter_options.go b/vendor/github.com/uber/jaeger-client-go/reporter_options.go
new file mode 100644
index 000000000..65012d701
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/reporter_options.go
@@ -0,0 +1,69 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package jaeger
+
+import (
+ "time"
+)
+
+// ReporterOption is a function that sets some option on the reporter.
+type ReporterOption func(c *reporterOptions)
+
+// ReporterOptions is a factory for all available ReporterOption's
+var ReporterOptions reporterOptions
+
+// reporterOptions control behavior of the reporter.
+type reporterOptions struct {
+ // queueSize is the size of internal queue where reported spans are stored before they are processed in the background
+ queueSize int
+ // bufferFlushInterval is how often the buffer is force-flushed, even if it's not full
+ bufferFlushInterval time.Duration
+ // logger is used to log errors of span submissions
+ logger Logger
+ // metrics is used to record runtime stats
+ metrics *Metrics
+}
+
+// QueueSize creates a ReporterOption that sets the size of the internal queue where
+// spans are stored before they are processed.
+func (reporterOptions) QueueSize(queueSize int) ReporterOption {
+ return func(r *reporterOptions) {
+ r.queueSize = queueSize
+ }
+}
+
+// Metrics creates a ReporterOption that initializes Metrics in the reporter,
+// which is used to record runtime statistics.
+func (reporterOptions) Metrics(metrics *Metrics) ReporterOption {
+ return func(r *reporterOptions) {
+ r.metrics = metrics
+ }
+}
+
+// BufferFlushInterval creates a ReporterOption that sets how often the queue
+// is force-flushed.
+func (reporterOptions) BufferFlushInterval(bufferFlushInterval time.Duration) ReporterOption {
+ return func(r *reporterOptions) {
+ r.bufferFlushInterval = bufferFlushInterval
+ }
+}
+
+// Logger creates a ReporterOption that initializes the logger used to log
+// errors of span submissions.
+func (reporterOptions) Logger(logger Logger) ReporterOption {
+ return func(r *reporterOptions) {
+ r.logger = logger
+ }
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/rpcmetrics/README.md b/vendor/github.com/uber/jaeger-client-go/rpcmetrics/README.md
new file mode 100644
index 000000000..879948e9c
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/rpcmetrics/README.md
@@ -0,0 +1,5 @@
+An Observer that can be used to emit RPC metrics
+================================================
+
+It can be attached to the tracer during tracer construction.
+See `ExampleObserver` function in [observer_test.go](./observer_test.go).
diff --git a/vendor/github.com/uber/jaeger-client-go/rpcmetrics/doc.go b/vendor/github.com/uber/jaeger-client-go/rpcmetrics/doc.go
new file mode 100644
index 000000000..51aa11b35
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/rpcmetrics/doc.go
@@ -0,0 +1,16 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+// Package rpcmetrics implements an Observer that can be used to emit RPC metrics.
+package rpcmetrics
diff --git a/vendor/github.com/uber/jaeger-client-go/rpcmetrics/endpoints.go b/vendor/github.com/uber/jaeger-client-go/rpcmetrics/endpoints.go
new file mode 100644
index 000000000..30555243d
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/rpcmetrics/endpoints.go
@@ -0,0 +1,63 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package rpcmetrics
+
+import "sync"
+
+// normalizedEndpoints is a cache for endpointName -> safeName mappings.
+type normalizedEndpoints struct {
+ names map[string]string
+ maxSize int
+ defaultName string
+ normalizer NameNormalizer
+ mux sync.RWMutex
+}
+
+func newNormalizedEndpoints(maxSize int, normalizer NameNormalizer) *normalizedEndpoints {
+ return &normalizedEndpoints{
+ maxSize: maxSize,
+ normalizer: normalizer,
+ names: make(map[string]string, maxSize),
+ }
+}
+
+// normalize looks up the name in the cache, if not found it uses normalizer
+// to convert the name to a safe name. If called with more than maxSize unique
+// names it returns "" for all other names beyond those already cached.
+func (n *normalizedEndpoints) normalize(name string) string {
+ n.mux.RLock()
+ norm, ok := n.names[name]
+ l := len(n.names)
+ n.mux.RUnlock()
+ if ok {
+ return norm
+ }
+ if l >= n.maxSize {
+ return ""
+ }
+ return n.normalizeWithLock(name)
+}
+
+func (n *normalizedEndpoints) normalizeWithLock(name string) string {
+ norm := n.normalizer.Normalize(name)
+ n.mux.Lock()
+ defer n.mux.Unlock()
+ // cache may have grown while we were not holding the lock
+ if len(n.names) >= n.maxSize {
+ return ""
+ }
+ n.names[name] = norm
+ return norm
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/rpcmetrics/metrics.go b/vendor/github.com/uber/jaeger-client-go/rpcmetrics/metrics.go
new file mode 100644
index 000000000..ab8d74c29
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/rpcmetrics/metrics.go
@@ -0,0 +1,124 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package rpcmetrics
+
+import (
+ "sync"
+
+ "github.com/uber/jaeger-lib/metrics"
+)
+
+const (
+ otherEndpointsPlaceholder = "other"
+ endpointNameMetricTag = "endpoint"
+)
+
+// Metrics is a collection of metrics for an endpoint describing
+// throughput, success, errors, and performance.
+type Metrics struct {
+ // RequestCountSuccess is a counter of the total number of successes.
+ RequestCountSuccess metrics.Counter `metric:"requests" tags:"error=false"`
+
+ // RequestCountFailures is a counter of the number of times any failure has been observed.
+ RequestCountFailures metrics.Counter `metric:"requests" tags:"error=true"`
+
+ // RequestLatencySuccess is a latency histogram of succesful requests.
+ RequestLatencySuccess metrics.Timer `metric:"request_latency" tags:"error=false"`
+
+ // RequestLatencyFailures is a latency histogram of failed requests.
+ RequestLatencyFailures metrics.Timer `metric:"request_latency" tags:"error=true"`
+
+ // HTTPStatusCode2xx is a counter of the total number of requests with HTTP status code 200-299
+ HTTPStatusCode2xx metrics.Counter `metric:"http_requests" tags:"status_code=2xx"`
+
+ // HTTPStatusCode3xx is a counter of the total number of requests with HTTP status code 300-399
+ HTTPStatusCode3xx metrics.Counter `metric:"http_requests" tags:"status_code=3xx"`
+
+ // HTTPStatusCode4xx is a counter of the total number of requests with HTTP status code 400-499
+ HTTPStatusCode4xx metrics.Counter `metric:"http_requests" tags:"status_code=4xx"`
+
+ // HTTPStatusCode5xx is a counter of the total number of requests with HTTP status code 500-599
+ HTTPStatusCode5xx metrics.Counter `metric:"http_requests" tags:"status_code=5xx"`
+}
+
+func (m *Metrics) recordHTTPStatusCode(statusCode uint16) {
+ if statusCode >= 200 && statusCode < 300 {
+ m.HTTPStatusCode2xx.Inc(1)
+ } else if statusCode >= 300 && statusCode < 400 {
+ m.HTTPStatusCode3xx.Inc(1)
+ } else if statusCode >= 400 && statusCode < 500 {
+ m.HTTPStatusCode4xx.Inc(1)
+ } else if statusCode >= 500 && statusCode < 600 {
+ m.HTTPStatusCode5xx.Inc(1)
+ }
+}
+
+// MetricsByEndpoint is a registry/cache of metrics for each unique endpoint name.
+// Only maxNumberOfEndpoints Metrics are stored, all other endpoint names are mapped
+// to a generic endpoint name "other".
+type MetricsByEndpoint struct {
+ metricsFactory metrics.Factory
+ endpoints *normalizedEndpoints
+ metricsByEndpoint map[string]*Metrics
+ mux sync.RWMutex
+}
+
+func newMetricsByEndpoint(
+ metricsFactory metrics.Factory,
+ normalizer NameNormalizer,
+ maxNumberOfEndpoints int,
+) *MetricsByEndpoint {
+ return &MetricsByEndpoint{
+ metricsFactory: metricsFactory,
+ endpoints: newNormalizedEndpoints(maxNumberOfEndpoints, normalizer),
+ metricsByEndpoint: make(map[string]*Metrics, maxNumberOfEndpoints+1), // +1 for "other"
+ }
+}
+
+func (m *MetricsByEndpoint) get(endpoint string) *Metrics {
+ safeName := m.endpoints.normalize(endpoint)
+ if safeName == "" {
+ safeName = otherEndpointsPlaceholder
+ }
+ m.mux.RLock()
+ met := m.metricsByEndpoint[safeName]
+ m.mux.RUnlock()
+ if met != nil {
+ return met
+ }
+
+ return m.getWithWriteLock(safeName)
+}
+
+// split to make easier to test
+func (m *MetricsByEndpoint) getWithWriteLock(safeName string) *Metrics {
+ m.mux.Lock()
+ defer m.mux.Unlock()
+
+ // it is possible that the name has been already registered after we released
+ // the read lock and before we grabbed the write lock, so check for that.
+ if met, ok := m.metricsByEndpoint[safeName]; ok {
+ return met
+ }
+
+ // it would be nice to create the struct before locking, since Init() is somewhat
+ // expensive, however some metrics backends (e.g. expvar) may not like duplicate metrics.
+ met := &Metrics{}
+ tags := map[string]string{endpointNameMetricTag: safeName}
+ metrics.Init(met, m.metricsFactory, tags)
+
+ m.metricsByEndpoint[safeName] = met
+ return met
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/rpcmetrics/normalizer.go b/vendor/github.com/uber/jaeger-client-go/rpcmetrics/normalizer.go
new file mode 100644
index 000000000..148d84b3a
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/rpcmetrics/normalizer.go
@@ -0,0 +1,101 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package rpcmetrics
+
+// NameNormalizer is used to convert the endpoint names to strings
+// that can be safely used as tags in the metrics.
+type NameNormalizer interface {
+ Normalize(name string) string
+}
+
+// DefaultNameNormalizer converts endpoint names so that they contain only characters
+// from the safe charset [a-zA-Z0-9-./_]. All other characters are replaced with '-'.
+var DefaultNameNormalizer = &SimpleNameNormalizer{
+ SafeSets: []SafeCharacterSet{
+ &Range{From: 'a', To: 'z'},
+ &Range{From: 'A', To: 'Z'},
+ &Range{From: '0', To: '9'},
+ &Char{'-'},
+ &Char{'_'},
+ &Char{'/'},
+ &Char{'.'},
+ },
+ Replacement: '-',
+}
+
+// SimpleNameNormalizer uses a set of safe character sets.
+type SimpleNameNormalizer struct {
+ SafeSets []SafeCharacterSet
+ Replacement byte
+}
+
+// SafeCharacterSet determines if the given character is "safe"
+type SafeCharacterSet interface {
+ IsSafe(c byte) bool
+}
+
+// Range implements SafeCharacterSet
+type Range struct {
+ From, To byte
+}
+
+// IsSafe implements SafeCharacterSet
+func (r *Range) IsSafe(c byte) bool {
+ return c >= r.From && c <= r.To
+}
+
+// Char implements SafeCharacterSet
+type Char struct {
+ Val byte
+}
+
+// IsSafe implements SafeCharacterSet
+func (ch *Char) IsSafe(c byte) bool {
+ return c == ch.Val
+}
+
+// Normalize checks each character in the string against SafeSets,
+// and if it's not safe substitutes it with Replacement.
+func (n *SimpleNameNormalizer) Normalize(name string) string {
+ var retMe []byte
+ nameBytes := []byte(name)
+ for i, b := range nameBytes {
+ if n.safeByte(b) {
+ if retMe != nil {
+ retMe[i] = b
+ }
+ } else {
+ if retMe == nil {
+ retMe = make([]byte, len(nameBytes))
+ copy(retMe[0:i], nameBytes[0:i])
+ }
+ retMe[i] = n.Replacement
+ }
+ }
+ if retMe == nil {
+ return name
+ }
+ return string(retMe)
+}
+
+// safeByte checks if b against all safe charsets.
+func (n *SimpleNameNormalizer) safeByte(b byte) bool {
+ for i := range n.SafeSets {
+ if n.SafeSets[i].IsSafe(b) {
+ return true
+ }
+ }
+ return false
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/rpcmetrics/observer.go b/vendor/github.com/uber/jaeger-client-go/rpcmetrics/observer.go
new file mode 100644
index 000000000..eca5ff6f3
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/rpcmetrics/observer.go
@@ -0,0 +1,171 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package rpcmetrics
+
+import (
+ "strconv"
+ "sync"
+ "time"
+
+ "github.com/opentracing/opentracing-go"
+ "github.com/opentracing/opentracing-go/ext"
+ "github.com/uber/jaeger-lib/metrics"
+
+ jaeger "github.com/uber/jaeger-client-go"
+)
+
+const defaultMaxNumberOfEndpoints = 200
+
+// Observer is an observer that can emit RPC metrics.
+type Observer struct {
+ metricsByEndpoint *MetricsByEndpoint
+}
+
+// NewObserver creates a new observer that can emit RPC metrics.
+func NewObserver(metricsFactory metrics.Factory, normalizer NameNormalizer) *Observer {
+ return &Observer{
+ metricsByEndpoint: newMetricsByEndpoint(
+ metricsFactory,
+ normalizer,
+ defaultMaxNumberOfEndpoints,
+ ),
+ }
+}
+
+// OnStartSpan creates a new Observer for the span.
+func (o *Observer) OnStartSpan(
+ operationName string,
+ options opentracing.StartSpanOptions,
+) jaeger.SpanObserver {
+ return NewSpanObserver(o.metricsByEndpoint, operationName, options)
+}
+
+// SpanKind identifies the span as inboud, outbound, or internal
+type SpanKind int
+
+const (
+ // Local span kind
+ Local SpanKind = iota
+ // Inbound span kind
+ Inbound
+ // Outbound span kind
+ Outbound
+)
+
+// SpanObserver collects RPC metrics
+type SpanObserver struct {
+ metricsByEndpoint *MetricsByEndpoint
+ operationName string
+ startTime time.Time
+ mux sync.Mutex
+ kind SpanKind
+ httpStatusCode uint16
+ err bool
+}
+
+// NewSpanObserver creates a new SpanObserver that can emit RPC metrics.
+func NewSpanObserver(
+ metricsByEndpoint *MetricsByEndpoint,
+ operationName string,
+ options opentracing.StartSpanOptions,
+) *SpanObserver {
+ so := &SpanObserver{
+ metricsByEndpoint: metricsByEndpoint,
+ operationName: operationName,
+ startTime: options.StartTime,
+ }
+ for k, v := range options.Tags {
+ so.handleTagInLock(k, v)
+ }
+ return so
+}
+
+// handleTags watches for special tags
+// - SpanKind
+// - HttpStatusCode
+// - Error
+func (so *SpanObserver) handleTagInLock(key string, value interface{}) {
+ if key == string(ext.SpanKind) {
+ if v, ok := value.(ext.SpanKindEnum); ok {
+ value = string(v)
+ }
+ if v, ok := value.(string); ok {
+ if v == string(ext.SpanKindRPCClientEnum) {
+ so.kind = Outbound
+ } else if v == string(ext.SpanKindRPCServerEnum) {
+ so.kind = Inbound
+ }
+ }
+ return
+ }
+ if key == string(ext.HTTPStatusCode) {
+ if v, ok := value.(uint16); ok {
+ so.httpStatusCode = v
+ } else if v, ok := value.(int); ok {
+ so.httpStatusCode = uint16(v)
+ } else if v, ok := value.(string); ok {
+ if vv, err := strconv.Atoi(v); err == nil {
+ so.httpStatusCode = uint16(vv)
+ }
+ }
+ return
+ }
+ if key == string(ext.Error) {
+ if v, ok := value.(bool); ok {
+ so.err = v
+ } else if v, ok := value.(string); ok {
+ if vv, err := strconv.ParseBool(v); err == nil {
+ so.err = vv
+ }
+ }
+ return
+ }
+}
+
+// OnFinish emits the RPC metrics. It only has an effect when operation name
+// is not blank, and the span kind is an RPC server.
+func (so *SpanObserver) OnFinish(options opentracing.FinishOptions) {
+ so.mux.Lock()
+ defer so.mux.Unlock()
+
+ if so.operationName == "" || so.kind != Inbound {
+ return
+ }
+
+ mets := so.metricsByEndpoint.get(so.operationName)
+ latency := options.FinishTime.Sub(so.startTime)
+ if so.err {
+ mets.RequestCountFailures.Inc(1)
+ mets.RequestLatencyFailures.Record(latency)
+ } else {
+ mets.RequestCountSuccess.Inc(1)
+ mets.RequestLatencySuccess.Record(latency)
+ }
+ mets.recordHTTPStatusCode(so.httpStatusCode)
+}
+
+// OnSetOperationName records new operation name.
+func (so *SpanObserver) OnSetOperationName(operationName string) {
+ so.mux.Lock()
+ so.operationName = operationName
+ so.mux.Unlock()
+}
+
+// OnSetTag implements SpanObserver
+func (so *SpanObserver) OnSetTag(key string, value interface{}) {
+ so.mux.Lock()
+ so.handleTagInLock(key, value)
+ so.mux.Unlock()
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/sampler.go b/vendor/github.com/uber/jaeger-client-go/sampler.go
new file mode 100644
index 000000000..3e1630953
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/sampler.go
@@ -0,0 +1,557 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package jaeger
+
+import (
+ "fmt"
+ "math"
+ "net/url"
+ "sync"
+ "sync/atomic"
+ "time"
+
+ "github.com/uber/jaeger-client-go/log"
+ "github.com/uber/jaeger-client-go/thrift-gen/sampling"
+ "github.com/uber/jaeger-client-go/utils"
+)
+
+const (
+ defaultSamplingServerURL = "http://localhost:5778/sampling"
+ defaultSamplingRefreshInterval = time.Minute
+ defaultMaxOperations = 2000
+)
+
+// Sampler decides whether a new trace should be sampled or not.
+type Sampler interface {
+ // IsSampled decides whether a trace with given `id` and `operation`
+ // should be sampled. This function will also return the tags that
+ // can be used to identify the type of sampling that was applied to
+ // the root span. Most simple samplers would return two tags,
+ // sampler.type and sampler.param, similar to those used in the Configuration
+ IsSampled(id TraceID, operation string) (sampled bool, tags []Tag)
+
+ // Close does a clean shutdown of the sampler, stopping any background
+ // go-routines it may have started.
+ Close()
+
+ // Equal checks if the `other` sampler is functionally equivalent
+ // to this sampler.
+ // TODO remove this function. This function is used to determine if 2 samplers are equivalent
+ // which does not bode well with the adaptive sampler which has to create all the composite samplers
+ // for the comparison to occur. This is expensive to do if only one sampler has changed.
+ Equal(other Sampler) bool
+}
+
+// -----------------------
+
+// ConstSampler is a sampler that always makes the same decision.
+type ConstSampler struct {
+ Decision bool
+ tags []Tag
+}
+
+// NewConstSampler creates a ConstSampler.
+func NewConstSampler(sample bool) Sampler {
+ tags := []Tag{
+ {key: SamplerTypeTagKey, value: SamplerTypeConst},
+ {key: SamplerParamTagKey, value: sample},
+ }
+ return &ConstSampler{Decision: sample, tags: tags}
+}
+
+// IsSampled implements IsSampled() of Sampler.
+func (s *ConstSampler) IsSampled(id TraceID, operation string) (bool, []Tag) {
+ return s.Decision, s.tags
+}
+
+// Close implements Close() of Sampler.
+func (s *ConstSampler) Close() {
+ // nothing to do
+}
+
+// Equal implements Equal() of Sampler.
+func (s *ConstSampler) Equal(other Sampler) bool {
+ if o, ok := other.(*ConstSampler); ok {
+ return s.Decision == o.Decision
+ }
+ return false
+}
+
+// -----------------------
+
+// ProbabilisticSampler is a sampler that randomly samples a certain percentage
+// of traces.
+type ProbabilisticSampler struct {
+ samplingRate float64
+ samplingBoundary uint64
+ tags []Tag
+}
+
+const maxRandomNumber = ^(uint64(1) << 63) // i.e. 0x7fffffffffffffff
+
+// NewProbabilisticSampler creates a sampler that randomly samples a certain percentage of traces specified by the
+// samplingRate, in the range between 0.0 and 1.0.
+//
+// It relies on the fact that new trace IDs are 63bit random numbers themselves, thus making the sampling decision
+// without generating a new random number, but simply calculating if traceID < (samplingRate * 2^63).
+// TODO remove the error from this function for next major release
+func NewProbabilisticSampler(samplingRate float64) (*ProbabilisticSampler, error) {
+ if samplingRate < 0.0 || samplingRate > 1.0 {
+ return nil, fmt.Errorf("Sampling Rate must be between 0.0 and 1.0, received %f", samplingRate)
+ }
+ return newProbabilisticSampler(samplingRate), nil
+}
+
+func newProbabilisticSampler(samplingRate float64) *ProbabilisticSampler {
+ samplingRate = math.Max(0.0, math.Min(samplingRate, 1.0))
+ tags := []Tag{
+ {key: SamplerTypeTagKey, value: SamplerTypeProbabilistic},
+ {key: SamplerParamTagKey, value: samplingRate},
+ }
+ return &ProbabilisticSampler{
+ samplingRate: samplingRate,
+ samplingBoundary: uint64(float64(maxRandomNumber) * samplingRate),
+ tags: tags,
+ }
+}
+
+// SamplingRate returns the sampling probability this sampled was constructed with.
+func (s *ProbabilisticSampler) SamplingRate() float64 {
+ return s.samplingRate
+}
+
+// IsSampled implements IsSampled() of Sampler.
+func (s *ProbabilisticSampler) IsSampled(id TraceID, operation string) (bool, []Tag) {
+ return s.samplingBoundary >= id.Low, s.tags
+}
+
+// Close implements Close() of Sampler.
+func (s *ProbabilisticSampler) Close() {
+ // nothing to do
+}
+
+// Equal implements Equal() of Sampler.
+func (s *ProbabilisticSampler) Equal(other Sampler) bool {
+ if o, ok := other.(*ProbabilisticSampler); ok {
+ return s.samplingBoundary == o.samplingBoundary
+ }
+ return false
+}
+
+// -----------------------
+
+type rateLimitingSampler struct {
+ maxTracesPerSecond float64
+ rateLimiter utils.RateLimiter
+ tags []Tag
+}
+
+// NewRateLimitingSampler creates a sampler that samples at most maxTracesPerSecond. The distribution of sampled
+// traces follows burstiness of the service, i.e. a service with uniformly distributed requests will have those
+// requests sampled uniformly as well, but if requests are bursty, especially sub-second, then a number of
+// sequential requests can be sampled each second.
+func NewRateLimitingSampler(maxTracesPerSecond float64) Sampler {
+ tags := []Tag{
+ {key: SamplerTypeTagKey, value: SamplerTypeRateLimiting},
+ {key: SamplerParamTagKey, value: maxTracesPerSecond},
+ }
+ return &rateLimitingSampler{
+ maxTracesPerSecond: maxTracesPerSecond,
+ rateLimiter: utils.NewRateLimiter(maxTracesPerSecond, math.Max(maxTracesPerSecond, 1.0)),
+ tags: tags,
+ }
+}
+
+// IsSampled implements IsSampled() of Sampler.
+func (s *rateLimitingSampler) IsSampled(id TraceID, operation string) (bool, []Tag) {
+ return s.rateLimiter.CheckCredit(1.0), s.tags
+}
+
+func (s *rateLimitingSampler) Close() {
+ // nothing to do
+}
+
+func (s *rateLimitingSampler) Equal(other Sampler) bool {
+ if o, ok := other.(*rateLimitingSampler); ok {
+ return s.maxTracesPerSecond == o.maxTracesPerSecond
+ }
+ return false
+}
+
+// -----------------------
+
+// GuaranteedThroughputProbabilisticSampler is a sampler that leverages both probabilisticSampler and
+// rateLimitingSampler. The rateLimitingSampler is used as a guaranteed lower bound sampler such that
+// every operation is sampled at least once in a time interval defined by the lowerBound. ie a lowerBound
+// of 1.0 / (60 * 10) will sample an operation at least once every 10 minutes.
+//
+// The probabilisticSampler is given higher priority when tags are emitted, ie. if IsSampled() for both
+// samplers return true, the tags for probabilisticSampler will be used.
+type GuaranteedThroughputProbabilisticSampler struct {
+ probabilisticSampler *ProbabilisticSampler
+ lowerBoundSampler Sampler
+ tags []Tag
+ samplingRate float64
+ lowerBound float64
+}
+
+// NewGuaranteedThroughputProbabilisticSampler returns a delegating sampler that applies both
+// probabilisticSampler and rateLimitingSampler.
+func NewGuaranteedThroughputProbabilisticSampler(
+ lowerBound, samplingRate float64,
+) (*GuaranteedThroughputProbabilisticSampler, error) {
+ return newGuaranteedThroughputProbabilisticSampler(lowerBound, samplingRate), nil
+}
+
+func newGuaranteedThroughputProbabilisticSampler(lowerBound, samplingRate float64) *GuaranteedThroughputProbabilisticSampler {
+ s := &GuaranteedThroughputProbabilisticSampler{
+ lowerBoundSampler: NewRateLimitingSampler(lowerBound),
+ lowerBound: lowerBound,
+ }
+ s.setProbabilisticSampler(samplingRate)
+ return s
+}
+
+func (s *GuaranteedThroughputProbabilisticSampler) setProbabilisticSampler(samplingRate float64) {
+ if s.probabilisticSampler == nil || s.samplingRate != samplingRate {
+ s.probabilisticSampler = newProbabilisticSampler(samplingRate)
+ s.samplingRate = s.probabilisticSampler.SamplingRate()
+ s.tags = []Tag{
+ {key: SamplerTypeTagKey, value: SamplerTypeLowerBound},
+ {key: SamplerParamTagKey, value: s.samplingRate},
+ }
+ }
+}
+
+// IsSampled implements IsSampled() of Sampler.
+func (s *GuaranteedThroughputProbabilisticSampler) IsSampled(id TraceID, operation string) (bool, []Tag) {
+ if sampled, tags := s.probabilisticSampler.IsSampled(id, operation); sampled {
+ s.lowerBoundSampler.IsSampled(id, operation)
+ return true, tags
+ }
+ sampled, _ := s.lowerBoundSampler.IsSampled(id, operation)
+ return sampled, s.tags
+}
+
+// Close implements Close() of Sampler.
+func (s *GuaranteedThroughputProbabilisticSampler) Close() {
+ s.probabilisticSampler.Close()
+ s.lowerBoundSampler.Close()
+}
+
+// Equal implements Equal() of Sampler.
+func (s *GuaranteedThroughputProbabilisticSampler) Equal(other Sampler) bool {
+ // NB The Equal() function is expensive and will be removed. See adaptiveSampler.Equal() for
+ // more information.
+ return false
+}
+
+// this function should only be called while holding a Write lock
+func (s *GuaranteedThroughputProbabilisticSampler) update(lowerBound, samplingRate float64) {
+ s.setProbabilisticSampler(samplingRate)
+ if s.lowerBound != lowerBound {
+ s.lowerBoundSampler = NewRateLimitingSampler(lowerBound)
+ s.lowerBound = lowerBound
+ }
+}
+
+// -----------------------
+
+type adaptiveSampler struct {
+ sync.RWMutex
+
+ samplers map[string]*GuaranteedThroughputProbabilisticSampler
+ defaultSampler *ProbabilisticSampler
+ lowerBound float64
+ maxOperations int
+}
+
+// NewAdaptiveSampler returns a delegating sampler that applies both probabilisticSampler and
+// rateLimitingSampler via the guaranteedThroughputProbabilisticSampler. This sampler keeps track of all
+// operations and delegates calls to the respective guaranteedThroughputProbabilisticSampler.
+func NewAdaptiveSampler(strategies *sampling.PerOperationSamplingStrategies, maxOperations int) (Sampler, error) {
+ return newAdaptiveSampler(strategies, maxOperations), nil
+}
+
+func newAdaptiveSampler(strategies *sampling.PerOperationSamplingStrategies, maxOperations int) Sampler {
+ samplers := make(map[string]*GuaranteedThroughputProbabilisticSampler)
+ for _, strategy := range strategies.PerOperationStrategies {
+ sampler := newGuaranteedThroughputProbabilisticSampler(
+ strategies.DefaultLowerBoundTracesPerSecond,
+ strategy.ProbabilisticSampling.SamplingRate,
+ )
+ samplers[strategy.Operation] = sampler
+ }
+ return &adaptiveSampler{
+ samplers: samplers,
+ defaultSampler: newProbabilisticSampler(strategies.DefaultSamplingProbability),
+ lowerBound: strategies.DefaultLowerBoundTracesPerSecond,
+ maxOperations: maxOperations,
+ }
+}
+
+func (s *adaptiveSampler) IsSampled(id TraceID, operation string) (bool, []Tag) {
+ s.RLock()
+ sampler, ok := s.samplers[operation]
+ if ok {
+ defer s.RUnlock()
+ return sampler.IsSampled(id, operation)
+ }
+ s.RUnlock()
+ s.Lock()
+ defer s.Unlock()
+
+ // Check if sampler has already been created
+ sampler, ok = s.samplers[operation]
+ if ok {
+ return sampler.IsSampled(id, operation)
+ }
+ // Store only up to maxOperations of unique ops.
+ if len(s.samplers) >= s.maxOperations {
+ return s.defaultSampler.IsSampled(id, operation)
+ }
+ newSampler := newGuaranteedThroughputProbabilisticSampler(s.lowerBound, s.defaultSampler.SamplingRate())
+ s.samplers[operation] = newSampler
+ return newSampler.IsSampled(id, operation)
+}
+
+func (s *adaptiveSampler) Close() {
+ s.Lock()
+ defer s.Unlock()
+ for _, sampler := range s.samplers {
+ sampler.Close()
+ }
+ s.defaultSampler.Close()
+}
+
+func (s *adaptiveSampler) Equal(other Sampler) bool {
+ // NB The Equal() function is overly expensive for adaptiveSampler since it's composed of multiple
+ // samplers which all need to be initialized before this function can be called for a comparison.
+ // Therefore, adaptiveSampler uses the update() function to only alter the samplers that need
+ // changing. Hence this function always returns false so that the update function can be called.
+ // Once the Equal() function is removed from the Sampler API, this will no longer be needed.
+ return false
+}
+
+func (s *adaptiveSampler) update(strategies *sampling.PerOperationSamplingStrategies) {
+ s.Lock()
+ defer s.Unlock()
+ for _, strategy := range strategies.PerOperationStrategies {
+ operation := strategy.Operation
+ samplingRate := strategy.ProbabilisticSampling.SamplingRate
+ lowerBound := strategies.DefaultLowerBoundTracesPerSecond
+ if sampler, ok := s.samplers[operation]; ok {
+ sampler.update(lowerBound, samplingRate)
+ } else {
+ sampler := newGuaranteedThroughputProbabilisticSampler(
+ lowerBound,
+ samplingRate,
+ )
+ s.samplers[operation] = sampler
+ }
+ }
+ s.lowerBound = strategies.DefaultLowerBoundTracesPerSecond
+ if s.defaultSampler.SamplingRate() != strategies.DefaultSamplingProbability {
+ s.defaultSampler = newProbabilisticSampler(strategies.DefaultSamplingProbability)
+ }
+}
+
+// -----------------------
+
+// RemotelyControlledSampler is a delegating sampler that polls a remote server
+// for the appropriate sampling strategy, constructs a corresponding sampler and
+// delegates to it for sampling decisions.
+type RemotelyControlledSampler struct {
+ // These fields must be first in the struct because `sync/atomic` expects 64-bit alignment.
+ // Cf. https://github.com/uber/jaeger-client-go/issues/155, https://goo.gl/zW7dgq
+ closed int64 // 0 - not closed, 1 - closed
+
+ sync.RWMutex
+ samplerOptions
+
+ serviceName string
+ manager sampling.SamplingManager
+ doneChan chan *sync.WaitGroup
+}
+
+type httpSamplingManager struct {
+ serverURL string
+}
+
+func (s *httpSamplingManager) GetSamplingStrategy(serviceName string) (*sampling.SamplingStrategyResponse, error) {
+ var out sampling.SamplingStrategyResponse
+ v := url.Values{}
+ v.Set("service", serviceName)
+ if err := utils.GetJSON(s.serverURL+"?"+v.Encode(), &out); err != nil {
+ return nil, err
+ }
+ return &out, nil
+}
+
+// NewRemotelyControlledSampler creates a sampler that periodically pulls
+// the sampling strategy from an HTTP sampling server (e.g. jaeger-agent).
+func NewRemotelyControlledSampler(
+ serviceName string,
+ opts ...SamplerOption,
+) *RemotelyControlledSampler {
+ options := applySamplerOptions(opts...)
+ sampler := &RemotelyControlledSampler{
+ samplerOptions: options,
+ serviceName: serviceName,
+ manager: &httpSamplingManager{serverURL: options.samplingServerURL},
+ doneChan: make(chan *sync.WaitGroup),
+ }
+ go sampler.pollController()
+ return sampler
+}
+
+func applySamplerOptions(opts ...SamplerOption) samplerOptions {
+ options := samplerOptions{}
+ for _, option := range opts {
+ option(&options)
+ }
+ if options.sampler == nil {
+ options.sampler = newProbabilisticSampler(0.001)
+ }
+ if options.logger == nil {
+ options.logger = log.NullLogger
+ }
+ if options.maxOperations <= 0 {
+ options.maxOperations = defaultMaxOperations
+ }
+ if options.samplingServerURL == "" {
+ options.samplingServerURL = defaultSamplingServerURL
+ }
+ if options.metrics == nil {
+ options.metrics = NewNullMetrics()
+ }
+ if options.samplingRefreshInterval <= 0 {
+ options.samplingRefreshInterval = defaultSamplingRefreshInterval
+ }
+ return options
+}
+
+// IsSampled implements IsSampled() of Sampler.
+func (s *RemotelyControlledSampler) IsSampled(id TraceID, operation string) (bool, []Tag) {
+ s.RLock()
+ defer s.RUnlock()
+ return s.sampler.IsSampled(id, operation)
+}
+
+// Close implements Close() of Sampler.
+func (s *RemotelyControlledSampler) Close() {
+ if swapped := atomic.CompareAndSwapInt64(&s.closed, 0, 1); !swapped {
+ s.logger.Error("Repeated attempt to close the sampler is ignored")
+ return
+ }
+
+ var wg sync.WaitGroup
+ wg.Add(1)
+ s.doneChan <- &wg
+ wg.Wait()
+}
+
+// Equal implements Equal() of Sampler.
+func (s *RemotelyControlledSampler) Equal(other Sampler) bool {
+ // NB The Equal() function is expensive and will be removed. See adaptiveSampler.Equal() for
+ // more information.
+ if o, ok := other.(*RemotelyControlledSampler); ok {
+ s.RLock()
+ o.RLock()
+ defer s.RUnlock()
+ defer o.RUnlock()
+ return s.sampler.Equal(o.sampler)
+ }
+ return false
+}
+
+func (s *RemotelyControlledSampler) pollController() {
+ ticker := time.NewTicker(s.samplingRefreshInterval)
+ defer ticker.Stop()
+ s.pollControllerWithTicker(ticker)
+}
+
+func (s *RemotelyControlledSampler) pollControllerWithTicker(ticker *time.Ticker) {
+ for {
+ select {
+ case <-ticker.C:
+ s.updateSampler()
+ case wg := <-s.doneChan:
+ wg.Done()
+ return
+ }
+ }
+}
+
+func (s *RemotelyControlledSampler) getSampler() Sampler {
+ s.Lock()
+ defer s.Unlock()
+ return s.sampler
+}
+
+func (s *RemotelyControlledSampler) setSampler(sampler Sampler) {
+ s.Lock()
+ defer s.Unlock()
+ s.sampler = sampler
+}
+
+func (s *RemotelyControlledSampler) updateSampler() {
+ res, err := s.manager.GetSamplingStrategy(s.serviceName)
+ if err != nil {
+ s.metrics.SamplerQueryFailure.Inc(1)
+ s.logger.Infof("Unable to query sampling strategy: %v", err)
+ return
+ }
+ s.Lock()
+ defer s.Unlock()
+
+ s.metrics.SamplerRetrieved.Inc(1)
+ if strategies := res.GetOperationSampling(); strategies != nil {
+ s.updateAdaptiveSampler(strategies)
+ } else {
+ err = s.updateRateLimitingOrProbabilisticSampler(res)
+ }
+ if err != nil {
+ s.metrics.SamplerUpdateFailure.Inc(1)
+ s.logger.Infof("Unable to handle sampling strategy response %+v. Got error: %v", res, err)
+ return
+ }
+ s.metrics.SamplerUpdated.Inc(1)
+}
+
+// NB: this function should only be called while holding a Write lock
+func (s *RemotelyControlledSampler) updateAdaptiveSampler(strategies *sampling.PerOperationSamplingStrategies) {
+ if adaptiveSampler, ok := s.sampler.(*adaptiveSampler); ok {
+ adaptiveSampler.update(strategies)
+ } else {
+ s.sampler = newAdaptiveSampler(strategies, s.maxOperations)
+ }
+}
+
+// NB: this function should only be called while holding a Write lock
+func (s *RemotelyControlledSampler) updateRateLimitingOrProbabilisticSampler(res *sampling.SamplingStrategyResponse) error {
+ var newSampler Sampler
+ if probabilistic := res.GetProbabilisticSampling(); probabilistic != nil {
+ newSampler = newProbabilisticSampler(probabilistic.SamplingRate)
+ } else if rateLimiting := res.GetRateLimitingSampling(); rateLimiting != nil {
+ newSampler = NewRateLimitingSampler(float64(rateLimiting.MaxTracesPerSecond))
+ } else {
+ return fmt.Errorf("Unsupported sampling strategy type %v", res.GetStrategyType())
+ }
+ if !s.sampler.Equal(newSampler) {
+ s.sampler = newSampler
+ }
+ return nil
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/sampler_options.go b/vendor/github.com/uber/jaeger-client-go/sampler_options.go
new file mode 100644
index 000000000..75d28a561
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/sampler_options.go
@@ -0,0 +1,81 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package jaeger
+
+import (
+ "time"
+)
+
+// SamplerOption is a function that sets some option on the sampler
+type SamplerOption func(options *samplerOptions)
+
+// SamplerOptions is a factory for all available SamplerOption's
+var SamplerOptions samplerOptions
+
+type samplerOptions struct {
+ metrics *Metrics
+ maxOperations int
+ sampler Sampler
+ logger Logger
+ samplingServerURL string
+ samplingRefreshInterval time.Duration
+}
+
+// Metrics creates a SamplerOption that initializes Metrics on the sampler,
+// which is used to emit statistics.
+func (samplerOptions) Metrics(m *Metrics) SamplerOption {
+ return func(o *samplerOptions) {
+ o.metrics = m
+ }
+}
+
+// MaxOperations creates a SamplerOption that sets the maximum number of
+// operations the sampler will keep track of.
+func (samplerOptions) MaxOperations(maxOperations int) SamplerOption {
+ return func(o *samplerOptions) {
+ o.maxOperations = maxOperations
+ }
+}
+
+// InitialSampler creates a SamplerOption that sets the initial sampler
+// to use before a remote sampler is created and used.
+func (samplerOptions) InitialSampler(sampler Sampler) SamplerOption {
+ return func(o *samplerOptions) {
+ o.sampler = sampler
+ }
+}
+
+// Logger creates a SamplerOption that sets the logger used by the sampler.
+func (samplerOptions) Logger(logger Logger) SamplerOption {
+ return func(o *samplerOptions) {
+ o.logger = logger
+ }
+}
+
+// SamplingServerURL creates a SamplerOption that sets the sampling server url
+// of the local agent that contains the sampling strategies.
+func (samplerOptions) SamplingServerURL(samplingServerURL string) SamplerOption {
+ return func(o *samplerOptions) {
+ o.samplingServerURL = samplingServerURL
+ }
+}
+
+// SamplingRefreshInterval creates a SamplerOption that sets how often the
+// sampler will poll local agent for the appropriate sampling strategy.
+func (samplerOptions) SamplingRefreshInterval(samplingRefreshInterval time.Duration) SamplerOption {
+ return func(o *samplerOptions) {
+ o.samplingRefreshInterval = samplingRefreshInterval
+ }
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/span.go b/vendor/github.com/uber/jaeger-client-go/span.go
new file mode 100644
index 000000000..f0b497a90
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/span.go
@@ -0,0 +1,249 @@
+// Copyright (c) 2017-2018 Uber Technologies, Inc.
+//
+// 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.
+
+package jaeger
+
+import (
+ "sync"
+ "time"
+
+ "github.com/opentracing/opentracing-go"
+ "github.com/opentracing/opentracing-go/ext"
+ "github.com/opentracing/opentracing-go/log"
+)
+
+// Span implements opentracing.Span
+type Span struct {
+ sync.RWMutex
+
+ tracer *Tracer
+
+ context SpanContext
+
+ // The name of the "operation" this span is an instance of.
+ // Known as a "span name" in some implementations.
+ operationName string
+
+ // firstInProcess, if true, indicates that this span is the root of the (sub)tree
+ // of spans in the current process. In other words it's true for the root spans,
+ // and the ingress spans when the process joins another trace.
+ firstInProcess bool
+
+ // startTime is the timestamp indicating when the span began, with microseconds precision.
+ startTime time.Time
+
+ // duration returns duration of the span with microseconds precision.
+ // Zero value means duration is unknown.
+ duration time.Duration
+
+ // tags attached to this span
+ tags []Tag
+
+ // The span's "micro-log"
+ logs []opentracing.LogRecord
+
+ // references for this span
+ references []Reference
+
+ observer ContribSpanObserver
+}
+
+// Tag is a simple key value wrapper.
+// TODO deprecate in the next major release, use opentracing.Tag instead.
+type Tag struct {
+ key string
+ value interface{}
+}
+
+// SetOperationName sets or changes the operation name.
+func (s *Span) SetOperationName(operationName string) opentracing.Span {
+ s.Lock()
+ defer s.Unlock()
+ if s.context.IsSampled() {
+ s.operationName = operationName
+ }
+ s.observer.OnSetOperationName(operationName)
+ return s
+}
+
+// SetTag implements SetTag() of opentracing.Span
+func (s *Span) SetTag(key string, value interface{}) opentracing.Span {
+ s.observer.OnSetTag(key, value)
+ if key == string(ext.SamplingPriority) && !setSamplingPriority(s, value) {
+ return s
+ }
+ s.Lock()
+ defer s.Unlock()
+ if s.context.IsSampled() {
+ s.setTagNoLocking(key, value)
+ }
+ return s
+}
+
+func (s *Span) setTagNoLocking(key string, value interface{}) {
+ s.tags = append(s.tags, Tag{key: key, value: value})
+}
+
+// LogFields implements opentracing.Span API
+func (s *Span) LogFields(fields ...log.Field) {
+ s.Lock()
+ defer s.Unlock()
+ if !s.context.IsSampled() {
+ return
+ }
+ s.logFieldsNoLocking(fields...)
+}
+
+// this function should only be called while holding a Write lock
+func (s *Span) logFieldsNoLocking(fields ...log.Field) {
+ lr := opentracing.LogRecord{
+ Fields: fields,
+ Timestamp: time.Now(),
+ }
+ s.appendLog(lr)
+}
+
+// LogKV implements opentracing.Span API
+func (s *Span) LogKV(alternatingKeyValues ...interface{}) {
+ s.RLock()
+ sampled := s.context.IsSampled()
+ s.RUnlock()
+ if !sampled {
+ return
+ }
+ fields, err := log.InterleavedKVToFields(alternatingKeyValues...)
+ if err != nil {
+ s.LogFields(log.Error(err), log.String("function", "LogKV"))
+ return
+ }
+ s.LogFields(fields...)
+}
+
+// LogEvent implements opentracing.Span API
+func (s *Span) LogEvent(event string) {
+ s.Log(opentracing.LogData{Event: event})
+}
+
+// LogEventWithPayload implements opentracing.Span API
+func (s *Span) LogEventWithPayload(event string, payload interface{}) {
+ s.Log(opentracing.LogData{Event: event, Payload: payload})
+}
+
+// Log implements opentracing.Span API
+func (s *Span) Log(ld opentracing.LogData) {
+ s.Lock()
+ defer s.Unlock()
+ if s.context.IsSampled() {
+ if ld.Timestamp.IsZero() {
+ ld.Timestamp = s.tracer.timeNow()
+ }
+ s.appendLog(ld.ToLogRecord())
+ }
+}
+
+// this function should only be called while holding a Write lock
+func (s *Span) appendLog(lr opentracing.LogRecord) {
+ // TODO add logic to limit number of logs per span (issue #46)
+ s.logs = append(s.logs, lr)
+}
+
+// SetBaggageItem implements SetBaggageItem() of opentracing.SpanContext
+func (s *Span) SetBaggageItem(key, value string) opentracing.Span {
+ s.Lock()
+ defer s.Unlock()
+ s.tracer.setBaggage(s, key, value)
+ return s
+}
+
+// BaggageItem implements BaggageItem() of opentracing.SpanContext
+func (s *Span) BaggageItem(key string) string {
+ s.RLock()
+ defer s.RUnlock()
+ return s.context.baggage[key]
+}
+
+// Finish implements opentracing.Span API
+func (s *Span) Finish() {
+ s.FinishWithOptions(opentracing.FinishOptions{})
+}
+
+// FinishWithOptions implements opentracing.Span API
+func (s *Span) FinishWithOptions(options opentracing.FinishOptions) {
+ if options.FinishTime.IsZero() {
+ options.FinishTime = s.tracer.timeNow()
+ }
+ s.observer.OnFinish(options)
+ s.Lock()
+ if s.context.IsSampled() {
+ s.duration = options.FinishTime.Sub(s.startTime)
+ // Note: bulk logs are not subject to maxLogsPerSpan limit
+ if options.LogRecords != nil {
+ s.logs = append(s.logs, options.LogRecords...)
+ }
+ for _, ld := range options.BulkLogData {
+ s.logs = append(s.logs, ld.ToLogRecord())
+ }
+ }
+ s.Unlock()
+ // call reportSpan even for non-sampled traces, to return span to the pool
+ s.tracer.reportSpan(s)
+}
+
+// Context implements opentracing.Span API
+func (s *Span) Context() opentracing.SpanContext {
+ s.Lock()
+ defer s.Unlock()
+ return s.context
+}
+
+// Tracer implements opentracing.Span API
+func (s *Span) Tracer() opentracing.Tracer {
+ return s.tracer
+}
+
+func (s *Span) String() string {
+ s.RLock()
+ defer s.RUnlock()
+ return s.context.String()
+}
+
+// OperationName allows retrieving current operation name.
+func (s *Span) OperationName() string {
+ s.RLock()
+ defer s.RUnlock()
+ return s.operationName
+}
+
+func (s *Span) serviceName() string {
+ return s.tracer.serviceName
+}
+
+// setSamplingPriority returns true if the flag was updated successfully, false otherwise.
+func setSamplingPriority(s *Span, value interface{}) bool {
+ s.Lock()
+ defer s.Unlock()
+ val, ok := value.(uint16)
+ if !ok {
+ return false
+ }
+ if val == 0 {
+ s.context.flags = s.context.flags & (^flagSampled)
+ return true
+ }
+ if s.tracer.isDebugAllowed(s.operationName) {
+ s.context.flags = s.context.flags | flagDebug | flagSampled
+ return true
+ }
+ return false
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/thrift-gen/agent/agent.go b/vendor/github.com/uber/jaeger-client-go/thrift-gen/agent/agent.go
new file mode 100644
index 000000000..e48811c50
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/thrift-gen/agent/agent.go
@@ -0,0 +1,411 @@
+// Autogenerated by Thrift Compiler (0.9.3)
+// DO NOT EDIT UNLESS YOU ARE SURE THAT YOU KNOW WHAT YOU ARE DOING
+
+package agent
+
+import (
+ "bytes"
+ "fmt"
+ "github.com/uber/jaeger-client-go/thrift"
+ "github.com/uber/jaeger-client-go/thrift-gen/jaeger"
+ "github.com/uber/jaeger-client-go/thrift-gen/zipkincore"
+)
+
+// (needed to ensure safety because of naive import list construction.)
+var _ = thrift.ZERO
+var _ = fmt.Printf
+var _ = bytes.Equal
+
+var _ = jaeger.GoUnusedProtection__
+var _ = zipkincore.GoUnusedProtection__
+
+type Agent interface {
+ // Parameters:
+ // - Spans
+ EmitZipkinBatch(spans []*zipkincore.Span) (err error)
+ // Parameters:
+ // - Batch
+ EmitBatch(batch *jaeger.Batch) (err error)
+}
+
+type AgentClient struct {
+ Transport thrift.TTransport
+ ProtocolFactory thrift.TProtocolFactory
+ InputProtocol thrift.TProtocol
+ OutputProtocol thrift.TProtocol
+ SeqId int32
+}
+
+func NewAgentClientFactory(t thrift.TTransport, f thrift.TProtocolFactory) *AgentClient {
+ return &AgentClient{Transport: t,
+ ProtocolFactory: f,
+ InputProtocol: f.GetProtocol(t),
+ OutputProtocol: f.GetProtocol(t),
+ SeqId: 0,
+ }
+}
+
+func NewAgentClientProtocol(t thrift.TTransport, iprot thrift.TProtocol, oprot thrift.TProtocol) *AgentClient {
+ return &AgentClient{Transport: t,
+ ProtocolFactory: nil,
+ InputProtocol: iprot,
+ OutputProtocol: oprot,
+ SeqId: 0,
+ }
+}
+
+// Parameters:
+// - Spans
+func (p *AgentClient) EmitZipkinBatch(spans []*zipkincore.Span) (err error) {
+ if err = p.sendEmitZipkinBatch(spans); err != nil {
+ return
+ }
+ return
+}
+
+func (p *AgentClient) sendEmitZipkinBatch(spans []*zipkincore.Span) (err error) {
+ oprot := p.OutputProtocol
+ if oprot == nil {
+ oprot = p.ProtocolFactory.GetProtocol(p.Transport)
+ p.OutputProtocol = oprot
+ }
+ p.SeqId++
+ if err = oprot.WriteMessageBegin("emitZipkinBatch", thrift.ONEWAY, p.SeqId); err != nil {
+ return
+ }
+ args := AgentEmitZipkinBatchArgs{
+ Spans: spans,
+ }
+ if err = args.Write(oprot); err != nil {
+ return
+ }
+ if err = oprot.WriteMessageEnd(); err != nil {
+ return
+ }
+ return oprot.Flush()
+}
+
+// Parameters:
+// - Batch
+func (p *AgentClient) EmitBatch(batch *jaeger.Batch) (err error) {
+ if err = p.sendEmitBatch(batch); err != nil {
+ return
+ }
+ return
+}
+
+func (p *AgentClient) sendEmitBatch(batch *jaeger.Batch) (err error) {
+ oprot := p.OutputProtocol
+ if oprot == nil {
+ oprot = p.ProtocolFactory.GetProtocol(p.Transport)
+ p.OutputProtocol = oprot
+ }
+ p.SeqId++
+ if err = oprot.WriteMessageBegin("emitBatch", thrift.ONEWAY, p.SeqId); err != nil {
+ return
+ }
+ args := AgentEmitBatchArgs{
+ Batch: batch,
+ }
+ if err = args.Write(oprot); err != nil {
+ return
+ }
+ if err = oprot.WriteMessageEnd(); err != nil {
+ return
+ }
+ return oprot.Flush()
+}
+
+type AgentProcessor struct {
+ processorMap map[string]thrift.TProcessorFunction
+ handler Agent
+}
+
+func (p *AgentProcessor) AddToProcessorMap(key string, processor thrift.TProcessorFunction) {
+ p.processorMap[key] = processor
+}
+
+func (p *AgentProcessor) GetProcessorFunction(key string) (processor thrift.TProcessorFunction, ok bool) {
+ processor, ok = p.processorMap[key]
+ return processor, ok
+}
+
+func (p *AgentProcessor) ProcessorMap() map[string]thrift.TProcessorFunction {
+ return p.processorMap
+}
+
+func NewAgentProcessor(handler Agent) *AgentProcessor {
+
+ self0 := &AgentProcessor{handler: handler, processorMap: make(map[string]thrift.TProcessorFunction)}
+ self0.processorMap["emitZipkinBatch"] = &agentProcessorEmitZipkinBatch{handler: handler}
+ self0.processorMap["emitBatch"] = &agentProcessorEmitBatch{handler: handler}
+ return self0
+}
+
+func (p *AgentProcessor) Process(iprot, oprot thrift.TProtocol) (success bool, err thrift.TException) {
+ name, _, seqId, err := iprot.ReadMessageBegin()
+ if err != nil {
+ return false, err
+ }
+ if processor, ok := p.GetProcessorFunction(name); ok {
+ return processor.Process(seqId, iprot, oprot)
+ }
+ iprot.Skip(thrift.STRUCT)
+ iprot.ReadMessageEnd()
+ x1 := thrift.NewTApplicationException(thrift.UNKNOWN_METHOD, "Unknown function "+name)
+ oprot.WriteMessageBegin(name, thrift.EXCEPTION, seqId)
+ x1.Write(oprot)
+ oprot.WriteMessageEnd()
+ oprot.Flush()
+ return false, x1
+
+}
+
+type agentProcessorEmitZipkinBatch struct {
+ handler Agent
+}
+
+func (p *agentProcessorEmitZipkinBatch) Process(seqId int32, iprot, oprot thrift.TProtocol) (success bool, err thrift.TException) {
+ args := AgentEmitZipkinBatchArgs{}
+ if err = args.Read(iprot); err != nil {
+ iprot.ReadMessageEnd()
+ return false, err
+ }
+
+ iprot.ReadMessageEnd()
+ var err2 error
+ if err2 = p.handler.EmitZipkinBatch(args.Spans); err2 != nil {
+ return true, err2
+ }
+ return true, nil
+}
+
+type agentProcessorEmitBatch struct {
+ handler Agent
+}
+
+func (p *agentProcessorEmitBatch) Process(seqId int32, iprot, oprot thrift.TProtocol) (success bool, err thrift.TException) {
+ args := AgentEmitBatchArgs{}
+ if err = args.Read(iprot); err != nil {
+ iprot.ReadMessageEnd()
+ return false, err
+ }
+
+ iprot.ReadMessageEnd()
+ var err2 error
+ if err2 = p.handler.EmitBatch(args.Batch); err2 != nil {
+ return true, err2
+ }
+ return true, nil
+}
+
+// HELPER FUNCTIONS AND STRUCTURES
+
+// Attributes:
+// - Spans
+type AgentEmitZipkinBatchArgs struct {
+ Spans []*zipkincore.Span `thrift:"spans,1" json:"spans"`
+}
+
+func NewAgentEmitZipkinBatchArgs() *AgentEmitZipkinBatchArgs {
+ return &AgentEmitZipkinBatchArgs{}
+}
+
+func (p *AgentEmitZipkinBatchArgs) GetSpans() []*zipkincore.Span {
+ return p.Spans
+}
+func (p *AgentEmitZipkinBatchArgs) Read(iprot thrift.TProtocol) error {
+ if _, err := iprot.ReadStructBegin(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read error: ", p), err)
+ }
+
+ for {
+ _, fieldTypeId, fieldId, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T field %d read error: ", p, fieldId), err)
+ }
+ if fieldTypeId == thrift.STOP {
+ break
+ }
+ switch fieldId {
+ case 1:
+ if err := p.readField1(iprot); err != nil {
+ return err
+ }
+ default:
+ if err := iprot.Skip(fieldTypeId); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadFieldEnd(); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadStructEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read struct end error: ", p), err)
+ }
+ return nil
+}
+
+func (p *AgentEmitZipkinBatchArgs) readField1(iprot thrift.TProtocol) error {
+ _, size, err := iprot.ReadListBegin()
+ if err != nil {
+ return thrift.PrependError("error reading list begin: ", err)
+ }
+ tSlice := make([]*zipkincore.Span, 0, size)
+ p.Spans = tSlice
+ for i := 0; i < size; i++ {
+ _elem2 := &zipkincore.Span{}
+ if err := _elem2.Read(iprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error reading struct: ", _elem2), err)
+ }
+ p.Spans = append(p.Spans, _elem2)
+ }
+ if err := iprot.ReadListEnd(); err != nil {
+ return thrift.PrependError("error reading list end: ", err)
+ }
+ return nil
+}
+
+func (p *AgentEmitZipkinBatchArgs) Write(oprot thrift.TProtocol) error {
+ if err := oprot.WriteStructBegin("emitZipkinBatch_args"); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write struct begin error: ", p), err)
+ }
+ if err := p.writeField1(oprot); err != nil {
+ return err
+ }
+ if err := oprot.WriteFieldStop(); err != nil {
+ return thrift.PrependError("write field stop error: ", err)
+ }
+ if err := oprot.WriteStructEnd(); err != nil {
+ return thrift.PrependError("write struct stop error: ", err)
+ }
+ return nil
+}
+
+func (p *AgentEmitZipkinBatchArgs) writeField1(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("spans", thrift.LIST, 1); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 1:spans: ", p), err)
+ }
+ if err := oprot.WriteListBegin(thrift.STRUCT, len(p.Spans)); err != nil {
+ return thrift.PrependError("error writing list begin: ", err)
+ }
+ for _, v := range p.Spans {
+ if err := v.Write(oprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error writing struct: ", v), err)
+ }
+ }
+ if err := oprot.WriteListEnd(); err != nil {
+ return thrift.PrependError("error writing list end: ", err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 1:spans: ", p), err)
+ }
+ return err
+}
+
+func (p *AgentEmitZipkinBatchArgs) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return fmt.Sprintf("AgentEmitZipkinBatchArgs(%+v)", *p)
+}
+
+// Attributes:
+// - Batch
+type AgentEmitBatchArgs struct {
+ Batch *jaeger.Batch `thrift:"batch,1" json:"batch"`
+}
+
+func NewAgentEmitBatchArgs() *AgentEmitBatchArgs {
+ return &AgentEmitBatchArgs{}
+}
+
+var AgentEmitBatchArgs_Batch_DEFAULT *jaeger.Batch
+
+func (p *AgentEmitBatchArgs) GetBatch() *jaeger.Batch {
+ if !p.IsSetBatch() {
+ return AgentEmitBatchArgs_Batch_DEFAULT
+ }
+ return p.Batch
+}
+func (p *AgentEmitBatchArgs) IsSetBatch() bool {
+ return p.Batch != nil
+}
+
+func (p *AgentEmitBatchArgs) Read(iprot thrift.TProtocol) error {
+ if _, err := iprot.ReadStructBegin(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read error: ", p), err)
+ }
+
+ for {
+ _, fieldTypeId, fieldId, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T field %d read error: ", p, fieldId), err)
+ }
+ if fieldTypeId == thrift.STOP {
+ break
+ }
+ switch fieldId {
+ case 1:
+ if err := p.readField1(iprot); err != nil {
+ return err
+ }
+ default:
+ if err := iprot.Skip(fieldTypeId); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadFieldEnd(); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadStructEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read struct end error: ", p), err)
+ }
+ return nil
+}
+
+func (p *AgentEmitBatchArgs) readField1(iprot thrift.TProtocol) error {
+ p.Batch = &jaeger.Batch{}
+ if err := p.Batch.Read(iprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error reading struct: ", p.Batch), err)
+ }
+ return nil
+}
+
+func (p *AgentEmitBatchArgs) Write(oprot thrift.TProtocol) error {
+ if err := oprot.WriteStructBegin("emitBatch_args"); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write struct begin error: ", p), err)
+ }
+ if err := p.writeField1(oprot); err != nil {
+ return err
+ }
+ if err := oprot.WriteFieldStop(); err != nil {
+ return thrift.PrependError("write field stop error: ", err)
+ }
+ if err := oprot.WriteStructEnd(); err != nil {
+ return thrift.PrependError("write struct stop error: ", err)
+ }
+ return nil
+}
+
+func (p *AgentEmitBatchArgs) writeField1(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("batch", thrift.STRUCT, 1); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 1:batch: ", p), err)
+ }
+ if err := p.Batch.Write(oprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error writing struct: ", p.Batch), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 1:batch: ", p), err)
+ }
+ return err
+}
+
+func (p *AgentEmitBatchArgs) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return fmt.Sprintf("AgentEmitBatchArgs(%+v)", *p)
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/thrift-gen/agent/constants.go b/vendor/github.com/uber/jaeger-client-go/thrift-gen/agent/constants.go
new file mode 100644
index 000000000..aa9857bb8
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/thrift-gen/agent/constants.go
@@ -0,0 +1,23 @@
+// Autogenerated by Thrift Compiler (0.9.3)
+// DO NOT EDIT UNLESS YOU ARE SURE THAT YOU KNOW WHAT YOU ARE DOING
+
+package agent
+
+import (
+ "bytes"
+ "fmt"
+ "github.com/uber/jaeger-client-go/thrift"
+ "github.com/uber/jaeger-client-go/thrift-gen/jaeger"
+ "github.com/uber/jaeger-client-go/thrift-gen/zipkincore"
+)
+
+// (needed to ensure safety because of naive import list construction.)
+var _ = thrift.ZERO
+var _ = fmt.Printf
+var _ = bytes.Equal
+
+var _ = jaeger.GoUnusedProtection__
+var _ = zipkincore.GoUnusedProtection__
+
+func init() {
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/thrift-gen/agent/ttypes.go b/vendor/github.com/uber/jaeger-client-go/thrift-gen/agent/ttypes.go
new file mode 100644
index 000000000..9c28f11c1
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/thrift-gen/agent/ttypes.go
@@ -0,0 +1,21 @@
+// Autogenerated by Thrift Compiler (0.9.3)
+// DO NOT EDIT UNLESS YOU ARE SURE THAT YOU KNOW WHAT YOU ARE DOING
+
+package agent
+
+import (
+ "bytes"
+ "fmt"
+ "github.com/uber/jaeger-client-go/thrift"
+ "github.com/uber/jaeger-client-go/thrift-gen/jaeger"
+ "github.com/uber/jaeger-client-go/thrift-gen/zipkincore"
+)
+
+// (needed to ensure safety because of naive import list construction.)
+var _ = thrift.ZERO
+var _ = fmt.Printf
+var _ = bytes.Equal
+
+var _ = jaeger.GoUnusedProtection__
+var _ = zipkincore.GoUnusedProtection__
+var GoUnusedProtection__ int
diff --git a/vendor/github.com/uber/jaeger-client-go/thrift-gen/baggage/baggagerestrictionmanager.go b/vendor/github.com/uber/jaeger-client-go/thrift-gen/baggage/baggagerestrictionmanager.go
new file mode 100644
index 000000000..1f79c1255
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/thrift-gen/baggage/baggagerestrictionmanager.go
@@ -0,0 +1,435 @@
+// Autogenerated by Thrift Compiler (0.9.3)
+// DO NOT EDIT UNLESS YOU ARE SURE THAT YOU KNOW WHAT YOU ARE DOING
+
+package baggage
+
+import (
+ "bytes"
+ "fmt"
+ "github.com/uber/jaeger-client-go/thrift"
+)
+
+// (needed to ensure safety because of naive import list construction.)
+var _ = thrift.ZERO
+var _ = fmt.Printf
+var _ = bytes.Equal
+
+type BaggageRestrictionManager interface {
+ // getBaggageRestrictions retrieves the baggage restrictions for a specific service.
+ // Usually, baggageRestrictions apply to all services however there may be situations
+ // where a baggageKey might only be allowed to be set by a specific service.
+ //
+ // Parameters:
+ // - ServiceName
+ GetBaggageRestrictions(serviceName string) (r []*BaggageRestriction, err error)
+}
+
+type BaggageRestrictionManagerClient struct {
+ Transport thrift.TTransport
+ ProtocolFactory thrift.TProtocolFactory
+ InputProtocol thrift.TProtocol
+ OutputProtocol thrift.TProtocol
+ SeqId int32
+}
+
+func NewBaggageRestrictionManagerClientFactory(t thrift.TTransport, f thrift.TProtocolFactory) *BaggageRestrictionManagerClient {
+ return &BaggageRestrictionManagerClient{Transport: t,
+ ProtocolFactory: f,
+ InputProtocol: f.GetProtocol(t),
+ OutputProtocol: f.GetProtocol(t),
+ SeqId: 0,
+ }
+}
+
+func NewBaggageRestrictionManagerClientProtocol(t thrift.TTransport, iprot thrift.TProtocol, oprot thrift.TProtocol) *BaggageRestrictionManagerClient {
+ return &BaggageRestrictionManagerClient{Transport: t,
+ ProtocolFactory: nil,
+ InputProtocol: iprot,
+ OutputProtocol: oprot,
+ SeqId: 0,
+ }
+}
+
+// getBaggageRestrictions retrieves the baggage restrictions for a specific service.
+// Usually, baggageRestrictions apply to all services however there may be situations
+// where a baggageKey might only be allowed to be set by a specific service.
+//
+// Parameters:
+// - ServiceName
+func (p *BaggageRestrictionManagerClient) GetBaggageRestrictions(serviceName string) (r []*BaggageRestriction, err error) {
+ if err = p.sendGetBaggageRestrictions(serviceName); err != nil {
+ return
+ }
+ return p.recvGetBaggageRestrictions()
+}
+
+func (p *BaggageRestrictionManagerClient) sendGetBaggageRestrictions(serviceName string) (err error) {
+ oprot := p.OutputProtocol
+ if oprot == nil {
+ oprot = p.ProtocolFactory.GetProtocol(p.Transport)
+ p.OutputProtocol = oprot
+ }
+ p.SeqId++
+ if err = oprot.WriteMessageBegin("getBaggageRestrictions", thrift.CALL, p.SeqId); err != nil {
+ return
+ }
+ args := BaggageRestrictionManagerGetBaggageRestrictionsArgs{
+ ServiceName: serviceName,
+ }
+ if err = args.Write(oprot); err != nil {
+ return
+ }
+ if err = oprot.WriteMessageEnd(); err != nil {
+ return
+ }
+ return oprot.Flush()
+}
+
+func (p *BaggageRestrictionManagerClient) recvGetBaggageRestrictions() (value []*BaggageRestriction, err error) {
+ iprot := p.InputProtocol
+ if iprot == nil {
+ iprot = p.ProtocolFactory.GetProtocol(p.Transport)
+ p.InputProtocol = iprot
+ }
+ method, mTypeId, seqId, err := iprot.ReadMessageBegin()
+ if err != nil {
+ return
+ }
+ if method != "getBaggageRestrictions" {
+ err = thrift.NewTApplicationException(thrift.WRONG_METHOD_NAME, "getBaggageRestrictions failed: wrong method name")
+ return
+ }
+ if p.SeqId != seqId {
+ err = thrift.NewTApplicationException(thrift.BAD_SEQUENCE_ID, "getBaggageRestrictions failed: out of sequence response")
+ return
+ }
+ if mTypeId == thrift.EXCEPTION {
+ error0 := thrift.NewTApplicationException(thrift.UNKNOWN_APPLICATION_EXCEPTION, "Unknown Exception")
+ var error1 error
+ error1, err = error0.Read(iprot)
+ if err != nil {
+ return
+ }
+ if err = iprot.ReadMessageEnd(); err != nil {
+ return
+ }
+ err = error1
+ return
+ }
+ if mTypeId != thrift.REPLY {
+ err = thrift.NewTApplicationException(thrift.INVALID_MESSAGE_TYPE_EXCEPTION, "getBaggageRestrictions failed: invalid message type")
+ return
+ }
+ result := BaggageRestrictionManagerGetBaggageRestrictionsResult{}
+ if err = result.Read(iprot); err != nil {
+ return
+ }
+ if err = iprot.ReadMessageEnd(); err != nil {
+ return
+ }
+ value = result.GetSuccess()
+ return
+}
+
+type BaggageRestrictionManagerProcessor struct {
+ processorMap map[string]thrift.TProcessorFunction
+ handler BaggageRestrictionManager
+}
+
+func (p *BaggageRestrictionManagerProcessor) AddToProcessorMap(key string, processor thrift.TProcessorFunction) {
+ p.processorMap[key] = processor
+}
+
+func (p *BaggageRestrictionManagerProcessor) GetProcessorFunction(key string) (processor thrift.TProcessorFunction, ok bool) {
+ processor, ok = p.processorMap[key]
+ return processor, ok
+}
+
+func (p *BaggageRestrictionManagerProcessor) ProcessorMap() map[string]thrift.TProcessorFunction {
+ return p.processorMap
+}
+
+func NewBaggageRestrictionManagerProcessor(handler BaggageRestrictionManager) *BaggageRestrictionManagerProcessor {
+
+ self2 := &BaggageRestrictionManagerProcessor{handler: handler, processorMap: make(map[string]thrift.TProcessorFunction)}
+ self2.processorMap["getBaggageRestrictions"] = &baggageRestrictionManagerProcessorGetBaggageRestrictions{handler: handler}
+ return self2
+}
+
+func (p *BaggageRestrictionManagerProcessor) Process(iprot, oprot thrift.TProtocol) (success bool, err thrift.TException) {
+ name, _, seqId, err := iprot.ReadMessageBegin()
+ if err != nil {
+ return false, err
+ }
+ if processor, ok := p.GetProcessorFunction(name); ok {
+ return processor.Process(seqId, iprot, oprot)
+ }
+ iprot.Skip(thrift.STRUCT)
+ iprot.ReadMessageEnd()
+ x3 := thrift.NewTApplicationException(thrift.UNKNOWN_METHOD, "Unknown function "+name)
+ oprot.WriteMessageBegin(name, thrift.EXCEPTION, seqId)
+ x3.Write(oprot)
+ oprot.WriteMessageEnd()
+ oprot.Flush()
+ return false, x3
+
+}
+
+type baggageRestrictionManagerProcessorGetBaggageRestrictions struct {
+ handler BaggageRestrictionManager
+}
+
+func (p *baggageRestrictionManagerProcessorGetBaggageRestrictions) Process(seqId int32, iprot, oprot thrift.TProtocol) (success bool, err thrift.TException) {
+ args := BaggageRestrictionManagerGetBaggageRestrictionsArgs{}
+ if err = args.Read(iprot); err != nil {
+ iprot.ReadMessageEnd()
+ x := thrift.NewTApplicationException(thrift.PROTOCOL_ERROR, err.Error())
+ oprot.WriteMessageBegin("getBaggageRestrictions", thrift.EXCEPTION, seqId)
+ x.Write(oprot)
+ oprot.WriteMessageEnd()
+ oprot.Flush()
+ return false, err
+ }
+
+ iprot.ReadMessageEnd()
+ result := BaggageRestrictionManagerGetBaggageRestrictionsResult{}
+ var retval []*BaggageRestriction
+ var err2 error
+ if retval, err2 = p.handler.GetBaggageRestrictions(args.ServiceName); err2 != nil {
+ x := thrift.NewTApplicationException(thrift.INTERNAL_ERROR, "Internal error processing getBaggageRestrictions: "+err2.Error())
+ oprot.WriteMessageBegin("getBaggageRestrictions", thrift.EXCEPTION, seqId)
+ x.Write(oprot)
+ oprot.WriteMessageEnd()
+ oprot.Flush()
+ return true, err2
+ } else {
+ result.Success = retval
+ }
+ if err2 = oprot.WriteMessageBegin("getBaggageRestrictions", thrift.REPLY, seqId); err2 != nil {
+ err = err2
+ }
+ if err2 = result.Write(oprot); err == nil && err2 != nil {
+ err = err2
+ }
+ if err2 = oprot.WriteMessageEnd(); err == nil && err2 != nil {
+ err = err2
+ }
+ if err2 = oprot.Flush(); err == nil && err2 != nil {
+ err = err2
+ }
+ if err != nil {
+ return
+ }
+ return true, err
+}
+
+// HELPER FUNCTIONS AND STRUCTURES
+
+// Attributes:
+// - ServiceName
+type BaggageRestrictionManagerGetBaggageRestrictionsArgs struct {
+ ServiceName string `thrift:"serviceName,1" json:"serviceName"`
+}
+
+func NewBaggageRestrictionManagerGetBaggageRestrictionsArgs() *BaggageRestrictionManagerGetBaggageRestrictionsArgs {
+ return &BaggageRestrictionManagerGetBaggageRestrictionsArgs{}
+}
+
+func (p *BaggageRestrictionManagerGetBaggageRestrictionsArgs) GetServiceName() string {
+ return p.ServiceName
+}
+func (p *BaggageRestrictionManagerGetBaggageRestrictionsArgs) Read(iprot thrift.TProtocol) error {
+ if _, err := iprot.ReadStructBegin(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read error: ", p), err)
+ }
+
+ for {
+ _, fieldTypeId, fieldId, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T field %d read error: ", p, fieldId), err)
+ }
+ if fieldTypeId == thrift.STOP {
+ break
+ }
+ switch fieldId {
+ case 1:
+ if err := p.readField1(iprot); err != nil {
+ return err
+ }
+ default:
+ if err := iprot.Skip(fieldTypeId); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadFieldEnd(); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadStructEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read struct end error: ", p), err)
+ }
+ return nil
+}
+
+func (p *BaggageRestrictionManagerGetBaggageRestrictionsArgs) readField1(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadString(); err != nil {
+ return thrift.PrependError("error reading field 1: ", err)
+ } else {
+ p.ServiceName = v
+ }
+ return nil
+}
+
+func (p *BaggageRestrictionManagerGetBaggageRestrictionsArgs) Write(oprot thrift.TProtocol) error {
+ if err := oprot.WriteStructBegin("getBaggageRestrictions_args"); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write struct begin error: ", p), err)
+ }
+ if err := p.writeField1(oprot); err != nil {
+ return err
+ }
+ if err := oprot.WriteFieldStop(); err != nil {
+ return thrift.PrependError("write field stop error: ", err)
+ }
+ if err := oprot.WriteStructEnd(); err != nil {
+ return thrift.PrependError("write struct stop error: ", err)
+ }
+ return nil
+}
+
+func (p *BaggageRestrictionManagerGetBaggageRestrictionsArgs) writeField1(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("serviceName", thrift.STRING, 1); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 1:serviceName: ", p), err)
+ }
+ if err := oprot.WriteString(string(p.ServiceName)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.serviceName (1) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 1:serviceName: ", p), err)
+ }
+ return err
+}
+
+func (p *BaggageRestrictionManagerGetBaggageRestrictionsArgs) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return fmt.Sprintf("BaggageRestrictionManagerGetBaggageRestrictionsArgs(%+v)", *p)
+}
+
+// Attributes:
+// - Success
+type BaggageRestrictionManagerGetBaggageRestrictionsResult struct {
+ Success []*BaggageRestriction `thrift:"success,0" json:"success,omitempty"`
+}
+
+func NewBaggageRestrictionManagerGetBaggageRestrictionsResult() *BaggageRestrictionManagerGetBaggageRestrictionsResult {
+ return &BaggageRestrictionManagerGetBaggageRestrictionsResult{}
+}
+
+var BaggageRestrictionManagerGetBaggageRestrictionsResult_Success_DEFAULT []*BaggageRestriction
+
+func (p *BaggageRestrictionManagerGetBaggageRestrictionsResult) GetSuccess() []*BaggageRestriction {
+ return p.Success
+}
+func (p *BaggageRestrictionManagerGetBaggageRestrictionsResult) IsSetSuccess() bool {
+ return p.Success != nil
+}
+
+func (p *BaggageRestrictionManagerGetBaggageRestrictionsResult) Read(iprot thrift.TProtocol) error {
+ if _, err := iprot.ReadStructBegin(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read error: ", p), err)
+ }
+
+ for {
+ _, fieldTypeId, fieldId, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T field %d read error: ", p, fieldId), err)
+ }
+ if fieldTypeId == thrift.STOP {
+ break
+ }
+ switch fieldId {
+ case 0:
+ if err := p.readField0(iprot); err != nil {
+ return err
+ }
+ default:
+ if err := iprot.Skip(fieldTypeId); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadFieldEnd(); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadStructEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read struct end error: ", p), err)
+ }
+ return nil
+}
+
+func (p *BaggageRestrictionManagerGetBaggageRestrictionsResult) readField0(iprot thrift.TProtocol) error {
+ _, size, err := iprot.ReadListBegin()
+ if err != nil {
+ return thrift.PrependError("error reading list begin: ", err)
+ }
+ tSlice := make([]*BaggageRestriction, 0, size)
+ p.Success = tSlice
+ for i := 0; i < size; i++ {
+ _elem4 := &BaggageRestriction{}
+ if err := _elem4.Read(iprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error reading struct: ", _elem4), err)
+ }
+ p.Success = append(p.Success, _elem4)
+ }
+ if err := iprot.ReadListEnd(); err != nil {
+ return thrift.PrependError("error reading list end: ", err)
+ }
+ return nil
+}
+
+func (p *BaggageRestrictionManagerGetBaggageRestrictionsResult) Write(oprot thrift.TProtocol) error {
+ if err := oprot.WriteStructBegin("getBaggageRestrictions_result"); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write struct begin error: ", p), err)
+ }
+ if err := p.writeField0(oprot); err != nil {
+ return err
+ }
+ if err := oprot.WriteFieldStop(); err != nil {
+ return thrift.PrependError("write field stop error: ", err)
+ }
+ if err := oprot.WriteStructEnd(); err != nil {
+ return thrift.PrependError("write struct stop error: ", err)
+ }
+ return nil
+}
+
+func (p *BaggageRestrictionManagerGetBaggageRestrictionsResult) writeField0(oprot thrift.TProtocol) (err error) {
+ if p.IsSetSuccess() {
+ if err := oprot.WriteFieldBegin("success", thrift.LIST, 0); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 0:success: ", p), err)
+ }
+ if err := oprot.WriteListBegin(thrift.STRUCT, len(p.Success)); err != nil {
+ return thrift.PrependError("error writing list begin: ", err)
+ }
+ for _, v := range p.Success {
+ if err := v.Write(oprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error writing struct: ", v), err)
+ }
+ }
+ if err := oprot.WriteListEnd(); err != nil {
+ return thrift.PrependError("error writing list end: ", err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 0:success: ", p), err)
+ }
+ }
+ return err
+}
+
+func (p *BaggageRestrictionManagerGetBaggageRestrictionsResult) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return fmt.Sprintf("BaggageRestrictionManagerGetBaggageRestrictionsResult(%+v)", *p)
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/thrift-gen/baggage/constants.go b/vendor/github.com/uber/jaeger-client-go/thrift-gen/baggage/constants.go
new file mode 100644
index 000000000..ed35ce9ab
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/thrift-gen/baggage/constants.go
@@ -0,0 +1,18 @@
+// Autogenerated by Thrift Compiler (0.9.3)
+// DO NOT EDIT UNLESS YOU ARE SURE THAT YOU KNOW WHAT YOU ARE DOING
+
+package baggage
+
+import (
+ "bytes"
+ "fmt"
+ "github.com/uber/jaeger-client-go/thrift"
+)
+
+// (needed to ensure safety because of naive import list construction.)
+var _ = thrift.ZERO
+var _ = fmt.Printf
+var _ = bytes.Equal
+
+func init() {
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/thrift-gen/baggage/ttypes.go b/vendor/github.com/uber/jaeger-client-go/thrift-gen/baggage/ttypes.go
new file mode 100644
index 000000000..7888892f6
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/thrift-gen/baggage/ttypes.go
@@ -0,0 +1,154 @@
+// Autogenerated by Thrift Compiler (0.9.3)
+// DO NOT EDIT UNLESS YOU ARE SURE THAT YOU KNOW WHAT YOU ARE DOING
+
+package baggage
+
+import (
+ "bytes"
+ "fmt"
+ "github.com/uber/jaeger-client-go/thrift"
+)
+
+// (needed to ensure safety because of naive import list construction.)
+var _ = thrift.ZERO
+var _ = fmt.Printf
+var _ = bytes.Equal
+
+var GoUnusedProtection__ int
+
+// Attributes:
+// - BaggageKey
+// - MaxValueLength
+type BaggageRestriction struct {
+ BaggageKey string `thrift:"baggageKey,1,required" json:"baggageKey"`
+ MaxValueLength int32 `thrift:"maxValueLength,2,required" json:"maxValueLength"`
+}
+
+func NewBaggageRestriction() *BaggageRestriction {
+ return &BaggageRestriction{}
+}
+
+func (p *BaggageRestriction) GetBaggageKey() string {
+ return p.BaggageKey
+}
+
+func (p *BaggageRestriction) GetMaxValueLength() int32 {
+ return p.MaxValueLength
+}
+func (p *BaggageRestriction) Read(iprot thrift.TProtocol) error {
+ if _, err := iprot.ReadStructBegin(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read error: ", p), err)
+ }
+
+ var issetBaggageKey bool = false
+ var issetMaxValueLength bool = false
+
+ for {
+ _, fieldTypeId, fieldId, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T field %d read error: ", p, fieldId), err)
+ }
+ if fieldTypeId == thrift.STOP {
+ break
+ }
+ switch fieldId {
+ case 1:
+ if err := p.readField1(iprot); err != nil {
+ return err
+ }
+ issetBaggageKey = true
+ case 2:
+ if err := p.readField2(iprot); err != nil {
+ return err
+ }
+ issetMaxValueLength = true
+ default:
+ if err := iprot.Skip(fieldTypeId); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadFieldEnd(); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadStructEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read struct end error: ", p), err)
+ }
+ if !issetBaggageKey {
+ return thrift.NewTProtocolExceptionWithType(thrift.INVALID_DATA, fmt.Errorf("Required field BaggageKey is not set"))
+ }
+ if !issetMaxValueLength {
+ return thrift.NewTProtocolExceptionWithType(thrift.INVALID_DATA, fmt.Errorf("Required field MaxValueLength is not set"))
+ }
+ return nil
+}
+
+func (p *BaggageRestriction) readField1(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadString(); err != nil {
+ return thrift.PrependError("error reading field 1: ", err)
+ } else {
+ p.BaggageKey = v
+ }
+ return nil
+}
+
+func (p *BaggageRestriction) readField2(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadI32(); err != nil {
+ return thrift.PrependError("error reading field 2: ", err)
+ } else {
+ p.MaxValueLength = v
+ }
+ return nil
+}
+
+func (p *BaggageRestriction) Write(oprot thrift.TProtocol) error {
+ if err := oprot.WriteStructBegin("BaggageRestriction"); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write struct begin error: ", p), err)
+ }
+ if err := p.writeField1(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField2(oprot); err != nil {
+ return err
+ }
+ if err := oprot.WriteFieldStop(); err != nil {
+ return thrift.PrependError("write field stop error: ", err)
+ }
+ if err := oprot.WriteStructEnd(); err != nil {
+ return thrift.PrependError("write struct stop error: ", err)
+ }
+ return nil
+}
+
+func (p *BaggageRestriction) writeField1(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("baggageKey", thrift.STRING, 1); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 1:baggageKey: ", p), err)
+ }
+ if err := oprot.WriteString(string(p.BaggageKey)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.baggageKey (1) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 1:baggageKey: ", p), err)
+ }
+ return err
+}
+
+func (p *BaggageRestriction) writeField2(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("maxValueLength", thrift.I32, 2); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 2:maxValueLength: ", p), err)
+ }
+ if err := oprot.WriteI32(int32(p.MaxValueLength)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.maxValueLength (2) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 2:maxValueLength: ", p), err)
+ }
+ return err
+}
+
+func (p *BaggageRestriction) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return fmt.Sprintf("BaggageRestriction(%+v)", *p)
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/thrift-gen/jaeger/agent.go b/vendor/github.com/uber/jaeger-client-go/thrift-gen/jaeger/agent.go
new file mode 100644
index 000000000..b32c37dd2
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/thrift-gen/jaeger/agent.go
@@ -0,0 +1,242 @@
+// Autogenerated by Thrift Compiler (0.9.3)
+// DO NOT EDIT UNLESS YOU ARE SURE THAT YOU KNOW WHAT YOU ARE DOING
+
+package jaeger
+
+import (
+ "bytes"
+ "fmt"
+ "github.com/uber/jaeger-client-go/thrift"
+)
+
+// (needed to ensure safety because of naive import list construction.)
+var _ = thrift.ZERO
+var _ = fmt.Printf
+var _ = bytes.Equal
+
+type Agent interface {
+ // Parameters:
+ // - Batch
+ EmitBatch(batch *Batch) (err error)
+}
+
+type AgentClient struct {
+ Transport thrift.TTransport
+ ProtocolFactory thrift.TProtocolFactory
+ InputProtocol thrift.TProtocol
+ OutputProtocol thrift.TProtocol
+ SeqId int32
+}
+
+func NewAgentClientFactory(t thrift.TTransport, f thrift.TProtocolFactory) *AgentClient {
+ return &AgentClient{Transport: t,
+ ProtocolFactory: f,
+ InputProtocol: f.GetProtocol(t),
+ OutputProtocol: f.GetProtocol(t),
+ SeqId: 0,
+ }
+}
+
+func NewAgentClientProtocol(t thrift.TTransport, iprot thrift.TProtocol, oprot thrift.TProtocol) *AgentClient {
+ return &AgentClient{Transport: t,
+ ProtocolFactory: nil,
+ InputProtocol: iprot,
+ OutputProtocol: oprot,
+ SeqId: 0,
+ }
+}
+
+// Parameters:
+// - Batch
+func (p *AgentClient) EmitBatch(batch *Batch) (err error) {
+ if err = p.sendEmitBatch(batch); err != nil {
+ return
+ }
+ return
+}
+
+func (p *AgentClient) sendEmitBatch(batch *Batch) (err error) {
+ oprot := p.OutputProtocol
+ if oprot == nil {
+ oprot = p.ProtocolFactory.GetProtocol(p.Transport)
+ p.OutputProtocol = oprot
+ }
+ p.SeqId++
+ if err = oprot.WriteMessageBegin("emitBatch", thrift.ONEWAY, p.SeqId); err != nil {
+ return
+ }
+ args := AgentEmitBatchArgs{
+ Batch: batch,
+ }
+ if err = args.Write(oprot); err != nil {
+ return
+ }
+ if err = oprot.WriteMessageEnd(); err != nil {
+ return
+ }
+ return oprot.Flush()
+}
+
+type AgentProcessor struct {
+ processorMap map[string]thrift.TProcessorFunction
+ handler Agent
+}
+
+func (p *AgentProcessor) AddToProcessorMap(key string, processor thrift.TProcessorFunction) {
+ p.processorMap[key] = processor
+}
+
+func (p *AgentProcessor) GetProcessorFunction(key string) (processor thrift.TProcessorFunction, ok bool) {
+ processor, ok = p.processorMap[key]
+ return processor, ok
+}
+
+func (p *AgentProcessor) ProcessorMap() map[string]thrift.TProcessorFunction {
+ return p.processorMap
+}
+
+func NewAgentProcessor(handler Agent) *AgentProcessor {
+
+ self6 := &AgentProcessor{handler: handler, processorMap: make(map[string]thrift.TProcessorFunction)}
+ self6.processorMap["emitBatch"] = &agentProcessorEmitBatch{handler: handler}
+ return self6
+}
+
+func (p *AgentProcessor) Process(iprot, oprot thrift.TProtocol) (success bool, err thrift.TException) {
+ name, _, seqId, err := iprot.ReadMessageBegin()
+ if err != nil {
+ return false, err
+ }
+ if processor, ok := p.GetProcessorFunction(name); ok {
+ return processor.Process(seqId, iprot, oprot)
+ }
+ iprot.Skip(thrift.STRUCT)
+ iprot.ReadMessageEnd()
+ x7 := thrift.NewTApplicationException(thrift.UNKNOWN_METHOD, "Unknown function "+name)
+ oprot.WriteMessageBegin(name, thrift.EXCEPTION, seqId)
+ x7.Write(oprot)
+ oprot.WriteMessageEnd()
+ oprot.Flush()
+ return false, x7
+
+}
+
+type agentProcessorEmitBatch struct {
+ handler Agent
+}
+
+func (p *agentProcessorEmitBatch) Process(seqId int32, iprot, oprot thrift.TProtocol) (success bool, err thrift.TException) {
+ args := AgentEmitBatchArgs{}
+ if err = args.Read(iprot); err != nil {
+ iprot.ReadMessageEnd()
+ return false, err
+ }
+
+ iprot.ReadMessageEnd()
+ var err2 error
+ if err2 = p.handler.EmitBatch(args.Batch); err2 != nil {
+ return true, err2
+ }
+ return true, nil
+}
+
+// HELPER FUNCTIONS AND STRUCTURES
+
+// Attributes:
+// - Batch
+type AgentEmitBatchArgs struct {
+ Batch *Batch `thrift:"batch,1" json:"batch"`
+}
+
+func NewAgentEmitBatchArgs() *AgentEmitBatchArgs {
+ return &AgentEmitBatchArgs{}
+}
+
+var AgentEmitBatchArgs_Batch_DEFAULT *Batch
+
+func (p *AgentEmitBatchArgs) GetBatch() *Batch {
+ if !p.IsSetBatch() {
+ return AgentEmitBatchArgs_Batch_DEFAULT
+ }
+ return p.Batch
+}
+func (p *AgentEmitBatchArgs) IsSetBatch() bool {
+ return p.Batch != nil
+}
+
+func (p *AgentEmitBatchArgs) Read(iprot thrift.TProtocol) error {
+ if _, err := iprot.ReadStructBegin(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read error: ", p), err)
+ }
+
+ for {
+ _, fieldTypeId, fieldId, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T field %d read error: ", p, fieldId), err)
+ }
+ if fieldTypeId == thrift.STOP {
+ break
+ }
+ switch fieldId {
+ case 1:
+ if err := p.readField1(iprot); err != nil {
+ return err
+ }
+ default:
+ if err := iprot.Skip(fieldTypeId); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadFieldEnd(); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadStructEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read struct end error: ", p), err)
+ }
+ return nil
+}
+
+func (p *AgentEmitBatchArgs) readField1(iprot thrift.TProtocol) error {
+ p.Batch = &Batch{}
+ if err := p.Batch.Read(iprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error reading struct: ", p.Batch), err)
+ }
+ return nil
+}
+
+func (p *AgentEmitBatchArgs) Write(oprot thrift.TProtocol) error {
+ if err := oprot.WriteStructBegin("emitBatch_args"); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write struct begin error: ", p), err)
+ }
+ if err := p.writeField1(oprot); err != nil {
+ return err
+ }
+ if err := oprot.WriteFieldStop(); err != nil {
+ return thrift.PrependError("write field stop error: ", err)
+ }
+ if err := oprot.WriteStructEnd(); err != nil {
+ return thrift.PrependError("write struct stop error: ", err)
+ }
+ return nil
+}
+
+func (p *AgentEmitBatchArgs) writeField1(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("batch", thrift.STRUCT, 1); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 1:batch: ", p), err)
+ }
+ if err := p.Batch.Write(oprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error writing struct: ", p.Batch), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 1:batch: ", p), err)
+ }
+ return err
+}
+
+func (p *AgentEmitBatchArgs) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return fmt.Sprintf("AgentEmitBatchArgs(%+v)", *p)
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/thrift-gen/jaeger/constants.go b/vendor/github.com/uber/jaeger-client-go/thrift-gen/jaeger/constants.go
new file mode 100644
index 000000000..621b8b1c2
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/thrift-gen/jaeger/constants.go
@@ -0,0 +1,18 @@
+// Autogenerated by Thrift Compiler (0.9.3)
+// DO NOT EDIT UNLESS YOU ARE SURE THAT YOU KNOW WHAT YOU ARE DOING
+
+package jaeger
+
+import (
+ "bytes"
+ "fmt"
+ "github.com/uber/jaeger-client-go/thrift"
+)
+
+// (needed to ensure safety because of naive import list construction.)
+var _ = thrift.ZERO
+var _ = fmt.Printf
+var _ = bytes.Equal
+
+func init() {
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/thrift-gen/jaeger/ttypes.go b/vendor/github.com/uber/jaeger-client-go/thrift-gen/jaeger/ttypes.go
new file mode 100644
index 000000000..d23ed2fc2
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/thrift-gen/jaeger/ttypes.go
@@ -0,0 +1,1838 @@
+// Autogenerated by Thrift Compiler (0.9.3)
+// DO NOT EDIT UNLESS YOU ARE SURE THAT YOU KNOW WHAT YOU ARE DOING
+
+package jaeger
+
+import (
+ "bytes"
+ "fmt"
+ "github.com/uber/jaeger-client-go/thrift"
+)
+
+// (needed to ensure safety because of naive import list construction.)
+var _ = thrift.ZERO
+var _ = fmt.Printf
+var _ = bytes.Equal
+
+var GoUnusedProtection__ int
+
+type TagType int64
+
+const (
+ TagType_STRING TagType = 0
+ TagType_DOUBLE TagType = 1
+ TagType_BOOL TagType = 2
+ TagType_LONG TagType = 3
+ TagType_BINARY TagType = 4
+)
+
+func (p TagType) String() string {
+ switch p {
+ case TagType_STRING:
+ return "STRING"
+ case TagType_DOUBLE:
+ return "DOUBLE"
+ case TagType_BOOL:
+ return "BOOL"
+ case TagType_LONG:
+ return "LONG"
+ case TagType_BINARY:
+ return "BINARY"
+ }
+ return "<UNSET>"
+}
+
+func TagTypeFromString(s string) (TagType, error) {
+ switch s {
+ case "STRING":
+ return TagType_STRING, nil
+ case "DOUBLE":
+ return TagType_DOUBLE, nil
+ case "BOOL":
+ return TagType_BOOL, nil
+ case "LONG":
+ return TagType_LONG, nil
+ case "BINARY":
+ return TagType_BINARY, nil
+ }
+ return TagType(0), fmt.Errorf("not a valid TagType string")
+}
+
+func TagTypePtr(v TagType) *TagType { return &v }
+
+func (p TagType) MarshalText() ([]byte, error) {
+ return []byte(p.String()), nil
+}
+
+func (p *TagType) UnmarshalText(text []byte) error {
+ q, err := TagTypeFromString(string(text))
+ if err != nil {
+ return err
+ }
+ *p = q
+ return nil
+}
+
+type SpanRefType int64
+
+const (
+ SpanRefType_CHILD_OF SpanRefType = 0
+ SpanRefType_FOLLOWS_FROM SpanRefType = 1
+)
+
+func (p SpanRefType) String() string {
+ switch p {
+ case SpanRefType_CHILD_OF:
+ return "CHILD_OF"
+ case SpanRefType_FOLLOWS_FROM:
+ return "FOLLOWS_FROM"
+ }
+ return "<UNSET>"
+}
+
+func SpanRefTypeFromString(s string) (SpanRefType, error) {
+ switch s {
+ case "CHILD_OF":
+ return SpanRefType_CHILD_OF, nil
+ case "FOLLOWS_FROM":
+ return SpanRefType_FOLLOWS_FROM, nil
+ }
+ return SpanRefType(0), fmt.Errorf("not a valid SpanRefType string")
+}
+
+func SpanRefTypePtr(v SpanRefType) *SpanRefType { return &v }
+
+func (p SpanRefType) MarshalText() ([]byte, error) {
+ return []byte(p.String()), nil
+}
+
+func (p *SpanRefType) UnmarshalText(text []byte) error {
+ q, err := SpanRefTypeFromString(string(text))
+ if err != nil {
+ return err
+ }
+ *p = q
+ return nil
+}
+
+// Attributes:
+// - Key
+// - VType
+// - VStr
+// - VDouble
+// - VBool
+// - VLong
+// - VBinary
+type Tag struct {
+ Key string `thrift:"key,1,required" json:"key"`
+ VType TagType `thrift:"vType,2,required" json:"vType"`
+ VStr *string `thrift:"vStr,3" json:"vStr,omitempty"`
+ VDouble *float64 `thrift:"vDouble,4" json:"vDouble,omitempty"`
+ VBool *bool `thrift:"vBool,5" json:"vBool,omitempty"`
+ VLong *int64 `thrift:"vLong,6" json:"vLong,omitempty"`
+ VBinary []byte `thrift:"vBinary,7" json:"vBinary,omitempty"`
+}
+
+func NewTag() *Tag {
+ return &Tag{}
+}
+
+func (p *Tag) GetKey() string {
+ return p.Key
+}
+
+func (p *Tag) GetVType() TagType {
+ return p.VType
+}
+
+var Tag_VStr_DEFAULT string
+
+func (p *Tag) GetVStr() string {
+ if !p.IsSetVStr() {
+ return Tag_VStr_DEFAULT
+ }
+ return *p.VStr
+}
+
+var Tag_VDouble_DEFAULT float64
+
+func (p *Tag) GetVDouble() float64 {
+ if !p.IsSetVDouble() {
+ return Tag_VDouble_DEFAULT
+ }
+ return *p.VDouble
+}
+
+var Tag_VBool_DEFAULT bool
+
+func (p *Tag) GetVBool() bool {
+ if !p.IsSetVBool() {
+ return Tag_VBool_DEFAULT
+ }
+ return *p.VBool
+}
+
+var Tag_VLong_DEFAULT int64
+
+func (p *Tag) GetVLong() int64 {
+ if !p.IsSetVLong() {
+ return Tag_VLong_DEFAULT
+ }
+ return *p.VLong
+}
+
+var Tag_VBinary_DEFAULT []byte
+
+func (p *Tag) GetVBinary() []byte {
+ return p.VBinary
+}
+func (p *Tag) IsSetVStr() bool {
+ return p.VStr != nil
+}
+
+func (p *Tag) IsSetVDouble() bool {
+ return p.VDouble != nil
+}
+
+func (p *Tag) IsSetVBool() bool {
+ return p.VBool != nil
+}
+
+func (p *Tag) IsSetVLong() bool {
+ return p.VLong != nil
+}
+
+func (p *Tag) IsSetVBinary() bool {
+ return p.VBinary != nil
+}
+
+func (p *Tag) Read(iprot thrift.TProtocol) error {
+ if _, err := iprot.ReadStructBegin(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read error: ", p), err)
+ }
+
+ var issetKey bool = false
+ var issetVType bool = false
+
+ for {
+ _, fieldTypeId, fieldId, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T field %d read error: ", p, fieldId), err)
+ }
+ if fieldTypeId == thrift.STOP {
+ break
+ }
+ switch fieldId {
+ case 1:
+ if err := p.readField1(iprot); err != nil {
+ return err
+ }
+ issetKey = true
+ case 2:
+ if err := p.readField2(iprot); err != nil {
+ return err
+ }
+ issetVType = true
+ case 3:
+ if err := p.readField3(iprot); err != nil {
+ return err
+ }
+ case 4:
+ if err := p.readField4(iprot); err != nil {
+ return err
+ }
+ case 5:
+ if err := p.readField5(iprot); err != nil {
+ return err
+ }
+ case 6:
+ if err := p.readField6(iprot); err != nil {
+ return err
+ }
+ case 7:
+ if err := p.readField7(iprot); err != nil {
+ return err
+ }
+ default:
+ if err := iprot.Skip(fieldTypeId); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadFieldEnd(); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadStructEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read struct end error: ", p), err)
+ }
+ if !issetKey {
+ return thrift.NewTProtocolExceptionWithType(thrift.INVALID_DATA, fmt.Errorf("Required field Key is not set"))
+ }
+ if !issetVType {
+ return thrift.NewTProtocolExceptionWithType(thrift.INVALID_DATA, fmt.Errorf("Required field VType is not set"))
+ }
+ return nil
+}
+
+func (p *Tag) readField1(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadString(); err != nil {
+ return thrift.PrependError("error reading field 1: ", err)
+ } else {
+ p.Key = v
+ }
+ return nil
+}
+
+func (p *Tag) readField2(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadI32(); err != nil {
+ return thrift.PrependError("error reading field 2: ", err)
+ } else {
+ temp := TagType(v)
+ p.VType = temp
+ }
+ return nil
+}
+
+func (p *Tag) readField3(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadString(); err != nil {
+ return thrift.PrependError("error reading field 3: ", err)
+ } else {
+ p.VStr = &v
+ }
+ return nil
+}
+
+func (p *Tag) readField4(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadDouble(); err != nil {
+ return thrift.PrependError("error reading field 4: ", err)
+ } else {
+ p.VDouble = &v
+ }
+ return nil
+}
+
+func (p *Tag) readField5(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadBool(); err != nil {
+ return thrift.PrependError("error reading field 5: ", err)
+ } else {
+ p.VBool = &v
+ }
+ return nil
+}
+
+func (p *Tag) readField6(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadI64(); err != nil {
+ return thrift.PrependError("error reading field 6: ", err)
+ } else {
+ p.VLong = &v
+ }
+ return nil
+}
+
+func (p *Tag) readField7(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadBinary(); err != nil {
+ return thrift.PrependError("error reading field 7: ", err)
+ } else {
+ p.VBinary = v
+ }
+ return nil
+}
+
+func (p *Tag) Write(oprot thrift.TProtocol) error {
+ if err := oprot.WriteStructBegin("Tag"); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write struct begin error: ", p), err)
+ }
+ if err := p.writeField1(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField2(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField3(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField4(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField5(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField6(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField7(oprot); err != nil {
+ return err
+ }
+ if err := oprot.WriteFieldStop(); err != nil {
+ return thrift.PrependError("write field stop error: ", err)
+ }
+ if err := oprot.WriteStructEnd(); err != nil {
+ return thrift.PrependError("write struct stop error: ", err)
+ }
+ return nil
+}
+
+func (p *Tag) writeField1(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("key", thrift.STRING, 1); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 1:key: ", p), err)
+ }
+ if err := oprot.WriteString(string(p.Key)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.key (1) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 1:key: ", p), err)
+ }
+ return err
+}
+
+func (p *Tag) writeField2(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("vType", thrift.I32, 2); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 2:vType: ", p), err)
+ }
+ if err := oprot.WriteI32(int32(p.VType)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.vType (2) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 2:vType: ", p), err)
+ }
+ return err
+}
+
+func (p *Tag) writeField3(oprot thrift.TProtocol) (err error) {
+ if p.IsSetVStr() {
+ if err := oprot.WriteFieldBegin("vStr", thrift.STRING, 3); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 3:vStr: ", p), err)
+ }
+ if err := oprot.WriteString(string(*p.VStr)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.vStr (3) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 3:vStr: ", p), err)
+ }
+ }
+ return err
+}
+
+func (p *Tag) writeField4(oprot thrift.TProtocol) (err error) {
+ if p.IsSetVDouble() {
+ if err := oprot.WriteFieldBegin("vDouble", thrift.DOUBLE, 4); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 4:vDouble: ", p), err)
+ }
+ if err := oprot.WriteDouble(float64(*p.VDouble)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.vDouble (4) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 4:vDouble: ", p), err)
+ }
+ }
+ return err
+}
+
+func (p *Tag) writeField5(oprot thrift.TProtocol) (err error) {
+ if p.IsSetVBool() {
+ if err := oprot.WriteFieldBegin("vBool", thrift.BOOL, 5); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 5:vBool: ", p), err)
+ }
+ if err := oprot.WriteBool(bool(*p.VBool)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.vBool (5) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 5:vBool: ", p), err)
+ }
+ }
+ return err
+}
+
+func (p *Tag) writeField6(oprot thrift.TProtocol) (err error) {
+ if p.IsSetVLong() {
+ if err := oprot.WriteFieldBegin("vLong", thrift.I64, 6); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 6:vLong: ", p), err)
+ }
+ if err := oprot.WriteI64(int64(*p.VLong)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.vLong (6) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 6:vLong: ", p), err)
+ }
+ }
+ return err
+}
+
+func (p *Tag) writeField7(oprot thrift.TProtocol) (err error) {
+ if p.IsSetVBinary() {
+ if err := oprot.WriteFieldBegin("vBinary", thrift.STRING, 7); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 7:vBinary: ", p), err)
+ }
+ if err := oprot.WriteBinary(p.VBinary); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.vBinary (7) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 7:vBinary: ", p), err)
+ }
+ }
+ return err
+}
+
+func (p *Tag) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return fmt.Sprintf("Tag(%+v)", *p)
+}
+
+// Attributes:
+// - Timestamp
+// - Fields
+type Log struct {
+ Timestamp int64 `thrift:"timestamp,1,required" json:"timestamp"`
+ Fields []*Tag `thrift:"fields,2,required" json:"fields"`
+}
+
+func NewLog() *Log {
+ return &Log{}
+}
+
+func (p *Log) GetTimestamp() int64 {
+ return p.Timestamp
+}
+
+func (p *Log) GetFields() []*Tag {
+ return p.Fields
+}
+func (p *Log) Read(iprot thrift.TProtocol) error {
+ if _, err := iprot.ReadStructBegin(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read error: ", p), err)
+ }
+
+ var issetTimestamp bool = false
+ var issetFields bool = false
+
+ for {
+ _, fieldTypeId, fieldId, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T field %d read error: ", p, fieldId), err)
+ }
+ if fieldTypeId == thrift.STOP {
+ break
+ }
+ switch fieldId {
+ case 1:
+ if err := p.readField1(iprot); err != nil {
+ return err
+ }
+ issetTimestamp = true
+ case 2:
+ if err := p.readField2(iprot); err != nil {
+ return err
+ }
+ issetFields = true
+ default:
+ if err := iprot.Skip(fieldTypeId); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadFieldEnd(); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadStructEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read struct end error: ", p), err)
+ }
+ if !issetTimestamp {
+ return thrift.NewTProtocolExceptionWithType(thrift.INVALID_DATA, fmt.Errorf("Required field Timestamp is not set"))
+ }
+ if !issetFields {
+ return thrift.NewTProtocolExceptionWithType(thrift.INVALID_DATA, fmt.Errorf("Required field Fields is not set"))
+ }
+ return nil
+}
+
+func (p *Log) readField1(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadI64(); err != nil {
+ return thrift.PrependError("error reading field 1: ", err)
+ } else {
+ p.Timestamp = v
+ }
+ return nil
+}
+
+func (p *Log) readField2(iprot thrift.TProtocol) error {
+ _, size, err := iprot.ReadListBegin()
+ if err != nil {
+ return thrift.PrependError("error reading list begin: ", err)
+ }
+ tSlice := make([]*Tag, 0, size)
+ p.Fields = tSlice
+ for i := 0; i < size; i++ {
+ _elem0 := &Tag{}
+ if err := _elem0.Read(iprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error reading struct: ", _elem0), err)
+ }
+ p.Fields = append(p.Fields, _elem0)
+ }
+ if err := iprot.ReadListEnd(); err != nil {
+ return thrift.PrependError("error reading list end: ", err)
+ }
+ return nil
+}
+
+func (p *Log) Write(oprot thrift.TProtocol) error {
+ if err := oprot.WriteStructBegin("Log"); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write struct begin error: ", p), err)
+ }
+ if err := p.writeField1(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField2(oprot); err != nil {
+ return err
+ }
+ if err := oprot.WriteFieldStop(); err != nil {
+ return thrift.PrependError("write field stop error: ", err)
+ }
+ if err := oprot.WriteStructEnd(); err != nil {
+ return thrift.PrependError("write struct stop error: ", err)
+ }
+ return nil
+}
+
+func (p *Log) writeField1(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("timestamp", thrift.I64, 1); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 1:timestamp: ", p), err)
+ }
+ if err := oprot.WriteI64(int64(p.Timestamp)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.timestamp (1) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 1:timestamp: ", p), err)
+ }
+ return err
+}
+
+func (p *Log) writeField2(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("fields", thrift.LIST, 2); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 2:fields: ", p), err)
+ }
+ if err := oprot.WriteListBegin(thrift.STRUCT, len(p.Fields)); err != nil {
+ return thrift.PrependError("error writing list begin: ", err)
+ }
+ for _, v := range p.Fields {
+ if err := v.Write(oprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error writing struct: ", v), err)
+ }
+ }
+ if err := oprot.WriteListEnd(); err != nil {
+ return thrift.PrependError("error writing list end: ", err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 2:fields: ", p), err)
+ }
+ return err
+}
+
+func (p *Log) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return fmt.Sprintf("Log(%+v)", *p)
+}
+
+// Attributes:
+// - RefType
+// - TraceIdLow
+// - TraceIdHigh
+// - SpanId
+type SpanRef struct {
+ RefType SpanRefType `thrift:"refType,1,required" json:"refType"`
+ TraceIdLow int64 `thrift:"traceIdLow,2,required" json:"traceIdLow"`
+ TraceIdHigh int64 `thrift:"traceIdHigh,3,required" json:"traceIdHigh"`
+ SpanId int64 `thrift:"spanId,4,required" json:"spanId"`
+}
+
+func NewSpanRef() *SpanRef {
+ return &SpanRef{}
+}
+
+func (p *SpanRef) GetRefType() SpanRefType {
+ return p.RefType
+}
+
+func (p *SpanRef) GetTraceIdLow() int64 {
+ return p.TraceIdLow
+}
+
+func (p *SpanRef) GetTraceIdHigh() int64 {
+ return p.TraceIdHigh
+}
+
+func (p *SpanRef) GetSpanId() int64 {
+ return p.SpanId
+}
+func (p *SpanRef) Read(iprot thrift.TProtocol) error {
+ if _, err := iprot.ReadStructBegin(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read error: ", p), err)
+ }
+
+ var issetRefType bool = false
+ var issetTraceIdLow bool = false
+ var issetTraceIdHigh bool = false
+ var issetSpanId bool = false
+
+ for {
+ _, fieldTypeId, fieldId, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T field %d read error: ", p, fieldId), err)
+ }
+ if fieldTypeId == thrift.STOP {
+ break
+ }
+ switch fieldId {
+ case 1:
+ if err := p.readField1(iprot); err != nil {
+ return err
+ }
+ issetRefType = true
+ case 2:
+ if err := p.readField2(iprot); err != nil {
+ return err
+ }
+ issetTraceIdLow = true
+ case 3:
+ if err := p.readField3(iprot); err != nil {
+ return err
+ }
+ issetTraceIdHigh = true
+ case 4:
+ if err := p.readField4(iprot); err != nil {
+ return err
+ }
+ issetSpanId = true
+ default:
+ if err := iprot.Skip(fieldTypeId); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadFieldEnd(); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadStructEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read struct end error: ", p), err)
+ }
+ if !issetRefType {
+ return thrift.NewTProtocolExceptionWithType(thrift.INVALID_DATA, fmt.Errorf("Required field RefType is not set"))
+ }
+ if !issetTraceIdLow {
+ return thrift.NewTProtocolExceptionWithType(thrift.INVALID_DATA, fmt.Errorf("Required field TraceIdLow is not set"))
+ }
+ if !issetTraceIdHigh {
+ return thrift.NewTProtocolExceptionWithType(thrift.INVALID_DATA, fmt.Errorf("Required field TraceIdHigh is not set"))
+ }
+ if !issetSpanId {
+ return thrift.NewTProtocolExceptionWithType(thrift.INVALID_DATA, fmt.Errorf("Required field SpanId is not set"))
+ }
+ return nil
+}
+
+func (p *SpanRef) readField1(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadI32(); err != nil {
+ return thrift.PrependError("error reading field 1: ", err)
+ } else {
+ temp := SpanRefType(v)
+ p.RefType = temp
+ }
+ return nil
+}
+
+func (p *SpanRef) readField2(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadI64(); err != nil {
+ return thrift.PrependError("error reading field 2: ", err)
+ } else {
+ p.TraceIdLow = v
+ }
+ return nil
+}
+
+func (p *SpanRef) readField3(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadI64(); err != nil {
+ return thrift.PrependError("error reading field 3: ", err)
+ } else {
+ p.TraceIdHigh = v
+ }
+ return nil
+}
+
+func (p *SpanRef) readField4(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadI64(); err != nil {
+ return thrift.PrependError("error reading field 4: ", err)
+ } else {
+ p.SpanId = v
+ }
+ return nil
+}
+
+func (p *SpanRef) Write(oprot thrift.TProtocol) error {
+ if err := oprot.WriteStructBegin("SpanRef"); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write struct begin error: ", p), err)
+ }
+ if err := p.writeField1(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField2(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField3(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField4(oprot); err != nil {
+ return err
+ }
+ if err := oprot.WriteFieldStop(); err != nil {
+ return thrift.PrependError("write field stop error: ", err)
+ }
+ if err := oprot.WriteStructEnd(); err != nil {
+ return thrift.PrependError("write struct stop error: ", err)
+ }
+ return nil
+}
+
+func (p *SpanRef) writeField1(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("refType", thrift.I32, 1); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 1:refType: ", p), err)
+ }
+ if err := oprot.WriteI32(int32(p.RefType)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.refType (1) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 1:refType: ", p), err)
+ }
+ return err
+}
+
+func (p *SpanRef) writeField2(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("traceIdLow", thrift.I64, 2); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 2:traceIdLow: ", p), err)
+ }
+ if err := oprot.WriteI64(int64(p.TraceIdLow)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.traceIdLow (2) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 2:traceIdLow: ", p), err)
+ }
+ return err
+}
+
+func (p *SpanRef) writeField3(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("traceIdHigh", thrift.I64, 3); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 3:traceIdHigh: ", p), err)
+ }
+ if err := oprot.WriteI64(int64(p.TraceIdHigh)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.traceIdHigh (3) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 3:traceIdHigh: ", p), err)
+ }
+ return err
+}
+
+func (p *SpanRef) writeField4(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("spanId", thrift.I64, 4); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 4:spanId: ", p), err)
+ }
+ if err := oprot.WriteI64(int64(p.SpanId)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.spanId (4) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 4:spanId: ", p), err)
+ }
+ return err
+}
+
+func (p *SpanRef) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return fmt.Sprintf("SpanRef(%+v)", *p)
+}
+
+// Attributes:
+// - TraceIdLow
+// - TraceIdHigh
+// - SpanId
+// - ParentSpanId
+// - OperationName
+// - References
+// - Flags
+// - StartTime
+// - Duration
+// - Tags
+// - Logs
+type Span struct {
+ TraceIdLow int64 `thrift:"traceIdLow,1,required" json:"traceIdLow"`
+ TraceIdHigh int64 `thrift:"traceIdHigh,2,required" json:"traceIdHigh"`
+ SpanId int64 `thrift:"spanId,3,required" json:"spanId"`
+ ParentSpanId int64 `thrift:"parentSpanId,4,required" json:"parentSpanId"`
+ OperationName string `thrift:"operationName,5,required" json:"operationName"`
+ References []*SpanRef `thrift:"references,6" json:"references,omitempty"`
+ Flags int32 `thrift:"flags,7,required" json:"flags"`
+ StartTime int64 `thrift:"startTime,8,required" json:"startTime"`
+ Duration int64 `thrift:"duration,9,required" json:"duration"`
+ Tags []*Tag `thrift:"tags,10" json:"tags,omitempty"`
+ Logs []*Log `thrift:"logs,11" json:"logs,omitempty"`
+}
+
+func NewSpan() *Span {
+ return &Span{}
+}
+
+func (p *Span) GetTraceIdLow() int64 {
+ return p.TraceIdLow
+}
+
+func (p *Span) GetTraceIdHigh() int64 {
+ return p.TraceIdHigh
+}
+
+func (p *Span) GetSpanId() int64 {
+ return p.SpanId
+}
+
+func (p *Span) GetParentSpanId() int64 {
+ return p.ParentSpanId
+}
+
+func (p *Span) GetOperationName() string {
+ return p.OperationName
+}
+
+var Span_References_DEFAULT []*SpanRef
+
+func (p *Span) GetReferences() []*SpanRef {
+ return p.References
+}
+
+func (p *Span) GetFlags() int32 {
+ return p.Flags
+}
+
+func (p *Span) GetStartTime() int64 {
+ return p.StartTime
+}
+
+func (p *Span) GetDuration() int64 {
+ return p.Duration
+}
+
+var Span_Tags_DEFAULT []*Tag
+
+func (p *Span) GetTags() []*Tag {
+ return p.Tags
+}
+
+var Span_Logs_DEFAULT []*Log
+
+func (p *Span) GetLogs() []*Log {
+ return p.Logs
+}
+func (p *Span) IsSetReferences() bool {
+ return p.References != nil
+}
+
+func (p *Span) IsSetTags() bool {
+ return p.Tags != nil
+}
+
+func (p *Span) IsSetLogs() bool {
+ return p.Logs != nil
+}
+
+func (p *Span) Read(iprot thrift.TProtocol) error {
+ if _, err := iprot.ReadStructBegin(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read error: ", p), err)
+ }
+
+ var issetTraceIdLow bool = false
+ var issetTraceIdHigh bool = false
+ var issetSpanId bool = false
+ var issetParentSpanId bool = false
+ var issetOperationName bool = false
+ var issetFlags bool = false
+ var issetStartTime bool = false
+ var issetDuration bool = false
+
+ for {
+ _, fieldTypeId, fieldId, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T field %d read error: ", p, fieldId), err)
+ }
+ if fieldTypeId == thrift.STOP {
+ break
+ }
+ switch fieldId {
+ case 1:
+ if err := p.readField1(iprot); err != nil {
+ return err
+ }
+ issetTraceIdLow = true
+ case 2:
+ if err := p.readField2(iprot); err != nil {
+ return err
+ }
+ issetTraceIdHigh = true
+ case 3:
+ if err := p.readField3(iprot); err != nil {
+ return err
+ }
+ issetSpanId = true
+ case 4:
+ if err := p.readField4(iprot); err != nil {
+ return err
+ }
+ issetParentSpanId = true
+ case 5:
+ if err := p.readField5(iprot); err != nil {
+ return err
+ }
+ issetOperationName = true
+ case 6:
+ if err := p.readField6(iprot); err != nil {
+ return err
+ }
+ case 7:
+ if err := p.readField7(iprot); err != nil {
+ return err
+ }
+ issetFlags = true
+ case 8:
+ if err := p.readField8(iprot); err != nil {
+ return err
+ }
+ issetStartTime = true
+ case 9:
+ if err := p.readField9(iprot); err != nil {
+ return err
+ }
+ issetDuration = true
+ case 10:
+ if err := p.readField10(iprot); err != nil {
+ return err
+ }
+ case 11:
+ if err := p.readField11(iprot); err != nil {
+ return err
+ }
+ default:
+ if err := iprot.Skip(fieldTypeId); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadFieldEnd(); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadStructEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read struct end error: ", p), err)
+ }
+ if !issetTraceIdLow {
+ return thrift.NewTProtocolExceptionWithType(thrift.INVALID_DATA, fmt.Errorf("Required field TraceIdLow is not set"))
+ }
+ if !issetTraceIdHigh {
+ return thrift.NewTProtocolExceptionWithType(thrift.INVALID_DATA, fmt.Errorf("Required field TraceIdHigh is not set"))
+ }
+ if !issetSpanId {
+ return thrift.NewTProtocolExceptionWithType(thrift.INVALID_DATA, fmt.Errorf("Required field SpanId is not set"))
+ }
+ if !issetParentSpanId {
+ return thrift.NewTProtocolExceptionWithType(thrift.INVALID_DATA, fmt.Errorf("Required field ParentSpanId is not set"))
+ }
+ if !issetOperationName {
+ return thrift.NewTProtocolExceptionWithType(thrift.INVALID_DATA, fmt.Errorf("Required field OperationName is not set"))
+ }
+ if !issetFlags {
+ return thrift.NewTProtocolExceptionWithType(thrift.INVALID_DATA, fmt.Errorf("Required field Flags is not set"))
+ }
+ if !issetStartTime {
+ return thrift.NewTProtocolExceptionWithType(thrift.INVALID_DATA, fmt.Errorf("Required field StartTime is not set"))
+ }
+ if !issetDuration {
+ return thrift.NewTProtocolExceptionWithType(thrift.INVALID_DATA, fmt.Errorf("Required field Duration is not set"))
+ }
+ return nil
+}
+
+func (p *Span) readField1(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadI64(); err != nil {
+ return thrift.PrependError("error reading field 1: ", err)
+ } else {
+ p.TraceIdLow = v
+ }
+ return nil
+}
+
+func (p *Span) readField2(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadI64(); err != nil {
+ return thrift.PrependError("error reading field 2: ", err)
+ } else {
+ p.TraceIdHigh = v
+ }
+ return nil
+}
+
+func (p *Span) readField3(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadI64(); err != nil {
+ return thrift.PrependError("error reading field 3: ", err)
+ } else {
+ p.SpanId = v
+ }
+ return nil
+}
+
+func (p *Span) readField4(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadI64(); err != nil {
+ return thrift.PrependError("error reading field 4: ", err)
+ } else {
+ p.ParentSpanId = v
+ }
+ return nil
+}
+
+func (p *Span) readField5(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadString(); err != nil {
+ return thrift.PrependError("error reading field 5: ", err)
+ } else {
+ p.OperationName = v
+ }
+ return nil
+}
+
+func (p *Span) readField6(iprot thrift.TProtocol) error {
+ _, size, err := iprot.ReadListBegin()
+ if err != nil {
+ return thrift.PrependError("error reading list begin: ", err)
+ }
+ tSlice := make([]*SpanRef, 0, size)
+ p.References = tSlice
+ for i := 0; i < size; i++ {
+ _elem1 := &SpanRef{}
+ if err := _elem1.Read(iprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error reading struct: ", _elem1), err)
+ }
+ p.References = append(p.References, _elem1)
+ }
+ if err := iprot.ReadListEnd(); err != nil {
+ return thrift.PrependError("error reading list end: ", err)
+ }
+ return nil
+}
+
+func (p *Span) readField7(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadI32(); err != nil {
+ return thrift.PrependError("error reading field 7: ", err)
+ } else {
+ p.Flags = v
+ }
+ return nil
+}
+
+func (p *Span) readField8(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadI64(); err != nil {
+ return thrift.PrependError("error reading field 8: ", err)
+ } else {
+ p.StartTime = v
+ }
+ return nil
+}
+
+func (p *Span) readField9(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadI64(); err != nil {
+ return thrift.PrependError("error reading field 9: ", err)
+ } else {
+ p.Duration = v
+ }
+ return nil
+}
+
+func (p *Span) readField10(iprot thrift.TProtocol) error {
+ _, size, err := iprot.ReadListBegin()
+ if err != nil {
+ return thrift.PrependError("error reading list begin: ", err)
+ }
+ tSlice := make([]*Tag, 0, size)
+ p.Tags = tSlice
+ for i := 0; i < size; i++ {
+ _elem2 := &Tag{}
+ if err := _elem2.Read(iprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error reading struct: ", _elem2), err)
+ }
+ p.Tags = append(p.Tags, _elem2)
+ }
+ if err := iprot.ReadListEnd(); err != nil {
+ return thrift.PrependError("error reading list end: ", err)
+ }
+ return nil
+}
+
+func (p *Span) readField11(iprot thrift.TProtocol) error {
+ _, size, err := iprot.ReadListBegin()
+ if err != nil {
+ return thrift.PrependError("error reading list begin: ", err)
+ }
+ tSlice := make([]*Log, 0, size)
+ p.Logs = tSlice
+ for i := 0; i < size; i++ {
+ _elem3 := &Log{}
+ if err := _elem3.Read(iprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error reading struct: ", _elem3), err)
+ }
+ p.Logs = append(p.Logs, _elem3)
+ }
+ if err := iprot.ReadListEnd(); err != nil {
+ return thrift.PrependError("error reading list end: ", err)
+ }
+ return nil
+}
+
+func (p *Span) Write(oprot thrift.TProtocol) error {
+ if err := oprot.WriteStructBegin("Span"); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write struct begin error: ", p), err)
+ }
+ if err := p.writeField1(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField2(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField3(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField4(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField5(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField6(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField7(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField8(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField9(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField10(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField11(oprot); err != nil {
+ return err
+ }
+ if err := oprot.WriteFieldStop(); err != nil {
+ return thrift.PrependError("write field stop error: ", err)
+ }
+ if err := oprot.WriteStructEnd(); err != nil {
+ return thrift.PrependError("write struct stop error: ", err)
+ }
+ return nil
+}
+
+func (p *Span) writeField1(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("traceIdLow", thrift.I64, 1); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 1:traceIdLow: ", p), err)
+ }
+ if err := oprot.WriteI64(int64(p.TraceIdLow)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.traceIdLow (1) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 1:traceIdLow: ", p), err)
+ }
+ return err
+}
+
+func (p *Span) writeField2(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("traceIdHigh", thrift.I64, 2); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 2:traceIdHigh: ", p), err)
+ }
+ if err := oprot.WriteI64(int64(p.TraceIdHigh)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.traceIdHigh (2) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 2:traceIdHigh: ", p), err)
+ }
+ return err
+}
+
+func (p *Span) writeField3(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("spanId", thrift.I64, 3); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 3:spanId: ", p), err)
+ }
+ if err := oprot.WriteI64(int64(p.SpanId)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.spanId (3) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 3:spanId: ", p), err)
+ }
+ return err
+}
+
+func (p *Span) writeField4(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("parentSpanId", thrift.I64, 4); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 4:parentSpanId: ", p), err)
+ }
+ if err := oprot.WriteI64(int64(p.ParentSpanId)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.parentSpanId (4) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 4:parentSpanId: ", p), err)
+ }
+ return err
+}
+
+func (p *Span) writeField5(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("operationName", thrift.STRING, 5); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 5:operationName: ", p), err)
+ }
+ if err := oprot.WriteString(string(p.OperationName)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.operationName (5) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 5:operationName: ", p), err)
+ }
+ return err
+}
+
+func (p *Span) writeField6(oprot thrift.TProtocol) (err error) {
+ if p.IsSetReferences() {
+ if err := oprot.WriteFieldBegin("references", thrift.LIST, 6); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 6:references: ", p), err)
+ }
+ if err := oprot.WriteListBegin(thrift.STRUCT, len(p.References)); err != nil {
+ return thrift.PrependError("error writing list begin: ", err)
+ }
+ for _, v := range p.References {
+ if err := v.Write(oprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error writing struct: ", v), err)
+ }
+ }
+ if err := oprot.WriteListEnd(); err != nil {
+ return thrift.PrependError("error writing list end: ", err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 6:references: ", p), err)
+ }
+ }
+ return err
+}
+
+func (p *Span) writeField7(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("flags", thrift.I32, 7); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 7:flags: ", p), err)
+ }
+ if err := oprot.WriteI32(int32(p.Flags)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.flags (7) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 7:flags: ", p), err)
+ }
+ return err
+}
+
+func (p *Span) writeField8(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("startTime", thrift.I64, 8); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 8:startTime: ", p), err)
+ }
+ if err := oprot.WriteI64(int64(p.StartTime)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.startTime (8) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 8:startTime: ", p), err)
+ }
+ return err
+}
+
+func (p *Span) writeField9(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("duration", thrift.I64, 9); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 9:duration: ", p), err)
+ }
+ if err := oprot.WriteI64(int64(p.Duration)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.duration (9) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 9:duration: ", p), err)
+ }
+ return err
+}
+
+func (p *Span) writeField10(oprot thrift.TProtocol) (err error) {
+ if p.IsSetTags() {
+ if err := oprot.WriteFieldBegin("tags", thrift.LIST, 10); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 10:tags: ", p), err)
+ }
+ if err := oprot.WriteListBegin(thrift.STRUCT, len(p.Tags)); err != nil {
+ return thrift.PrependError("error writing list begin: ", err)
+ }
+ for _, v := range p.Tags {
+ if err := v.Write(oprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error writing struct: ", v), err)
+ }
+ }
+ if err := oprot.WriteListEnd(); err != nil {
+ return thrift.PrependError("error writing list end: ", err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 10:tags: ", p), err)
+ }
+ }
+ return err
+}
+
+func (p *Span) writeField11(oprot thrift.TProtocol) (err error) {
+ if p.IsSetLogs() {
+ if err := oprot.WriteFieldBegin("logs", thrift.LIST, 11); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 11:logs: ", p), err)
+ }
+ if err := oprot.WriteListBegin(thrift.STRUCT, len(p.Logs)); err != nil {
+ return thrift.PrependError("error writing list begin: ", err)
+ }
+ for _, v := range p.Logs {
+ if err := v.Write(oprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error writing struct: ", v), err)
+ }
+ }
+ if err := oprot.WriteListEnd(); err != nil {
+ return thrift.PrependError("error writing list end: ", err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 11:logs: ", p), err)
+ }
+ }
+ return err
+}
+
+func (p *Span) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return fmt.Sprintf("Span(%+v)", *p)
+}
+
+// Attributes:
+// - ServiceName
+// - Tags
+type Process struct {
+ ServiceName string `thrift:"serviceName,1,required" json:"serviceName"`
+ Tags []*Tag `thrift:"tags,2" json:"tags,omitempty"`
+}
+
+func NewProcess() *Process {
+ return &Process{}
+}
+
+func (p *Process) GetServiceName() string {
+ return p.ServiceName
+}
+
+var Process_Tags_DEFAULT []*Tag
+
+func (p *Process) GetTags() []*Tag {
+ return p.Tags
+}
+func (p *Process) IsSetTags() bool {
+ return p.Tags != nil
+}
+
+func (p *Process) Read(iprot thrift.TProtocol) error {
+ if _, err := iprot.ReadStructBegin(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read error: ", p), err)
+ }
+
+ var issetServiceName bool = false
+
+ for {
+ _, fieldTypeId, fieldId, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T field %d read error: ", p, fieldId), err)
+ }
+ if fieldTypeId == thrift.STOP {
+ break
+ }
+ switch fieldId {
+ case 1:
+ if err := p.readField1(iprot); err != nil {
+ return err
+ }
+ issetServiceName = true
+ case 2:
+ if err := p.readField2(iprot); err != nil {
+ return err
+ }
+ default:
+ if err := iprot.Skip(fieldTypeId); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadFieldEnd(); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadStructEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read struct end error: ", p), err)
+ }
+ if !issetServiceName {
+ return thrift.NewTProtocolExceptionWithType(thrift.INVALID_DATA, fmt.Errorf("Required field ServiceName is not set"))
+ }
+ return nil
+}
+
+func (p *Process) readField1(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadString(); err != nil {
+ return thrift.PrependError("error reading field 1: ", err)
+ } else {
+ p.ServiceName = v
+ }
+ return nil
+}
+
+func (p *Process) readField2(iprot thrift.TProtocol) error {
+ _, size, err := iprot.ReadListBegin()
+ if err != nil {
+ return thrift.PrependError("error reading list begin: ", err)
+ }
+ tSlice := make([]*Tag, 0, size)
+ p.Tags = tSlice
+ for i := 0; i < size; i++ {
+ _elem4 := &Tag{}
+ if err := _elem4.Read(iprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error reading struct: ", _elem4), err)
+ }
+ p.Tags = append(p.Tags, _elem4)
+ }
+ if err := iprot.ReadListEnd(); err != nil {
+ return thrift.PrependError("error reading list end: ", err)
+ }
+ return nil
+}
+
+func (p *Process) Write(oprot thrift.TProtocol) error {
+ if err := oprot.WriteStructBegin("Process"); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write struct begin error: ", p), err)
+ }
+ if err := p.writeField1(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField2(oprot); err != nil {
+ return err
+ }
+ if err := oprot.WriteFieldStop(); err != nil {
+ return thrift.PrependError("write field stop error: ", err)
+ }
+ if err := oprot.WriteStructEnd(); err != nil {
+ return thrift.PrependError("write struct stop error: ", err)
+ }
+ return nil
+}
+
+func (p *Process) writeField1(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("serviceName", thrift.STRING, 1); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 1:serviceName: ", p), err)
+ }
+ if err := oprot.WriteString(string(p.ServiceName)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.serviceName (1) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 1:serviceName: ", p), err)
+ }
+ return err
+}
+
+func (p *Process) writeField2(oprot thrift.TProtocol) (err error) {
+ if p.IsSetTags() {
+ if err := oprot.WriteFieldBegin("tags", thrift.LIST, 2); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 2:tags: ", p), err)
+ }
+ if err := oprot.WriteListBegin(thrift.STRUCT, len(p.Tags)); err != nil {
+ return thrift.PrependError("error writing list begin: ", err)
+ }
+ for _, v := range p.Tags {
+ if err := v.Write(oprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error writing struct: ", v), err)
+ }
+ }
+ if err := oprot.WriteListEnd(); err != nil {
+ return thrift.PrependError("error writing list end: ", err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 2:tags: ", p), err)
+ }
+ }
+ return err
+}
+
+func (p *Process) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return fmt.Sprintf("Process(%+v)", *p)
+}
+
+// Attributes:
+// - Process
+// - Spans
+type Batch struct {
+ Process *Process `thrift:"process,1,required" json:"process"`
+ Spans []*Span `thrift:"spans,2,required" json:"spans"`
+}
+
+func NewBatch() *Batch {
+ return &Batch{}
+}
+
+var Batch_Process_DEFAULT *Process
+
+func (p *Batch) GetProcess() *Process {
+ if !p.IsSetProcess() {
+ return Batch_Process_DEFAULT
+ }
+ return p.Process
+}
+
+func (p *Batch) GetSpans() []*Span {
+ return p.Spans
+}
+func (p *Batch) IsSetProcess() bool {
+ return p.Process != nil
+}
+
+func (p *Batch) Read(iprot thrift.TProtocol) error {
+ if _, err := iprot.ReadStructBegin(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read error: ", p), err)
+ }
+
+ var issetProcess bool = false
+ var issetSpans bool = false
+
+ for {
+ _, fieldTypeId, fieldId, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T field %d read error: ", p, fieldId), err)
+ }
+ if fieldTypeId == thrift.STOP {
+ break
+ }
+ switch fieldId {
+ case 1:
+ if err := p.readField1(iprot); err != nil {
+ return err
+ }
+ issetProcess = true
+ case 2:
+ if err := p.readField2(iprot); err != nil {
+ return err
+ }
+ issetSpans = true
+ default:
+ if err := iprot.Skip(fieldTypeId); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadFieldEnd(); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadStructEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read struct end error: ", p), err)
+ }
+ if !issetProcess {
+ return thrift.NewTProtocolExceptionWithType(thrift.INVALID_DATA, fmt.Errorf("Required field Process is not set"))
+ }
+ if !issetSpans {
+ return thrift.NewTProtocolExceptionWithType(thrift.INVALID_DATA, fmt.Errorf("Required field Spans is not set"))
+ }
+ return nil
+}
+
+func (p *Batch) readField1(iprot thrift.TProtocol) error {
+ p.Process = &Process{}
+ if err := p.Process.Read(iprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error reading struct: ", p.Process), err)
+ }
+ return nil
+}
+
+func (p *Batch) readField2(iprot thrift.TProtocol) error {
+ _, size, err := iprot.ReadListBegin()
+ if err != nil {
+ return thrift.PrependError("error reading list begin: ", err)
+ }
+ tSlice := make([]*Span, 0, size)
+ p.Spans = tSlice
+ for i := 0; i < size; i++ {
+ _elem5 := &Span{}
+ if err := _elem5.Read(iprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error reading struct: ", _elem5), err)
+ }
+ p.Spans = append(p.Spans, _elem5)
+ }
+ if err := iprot.ReadListEnd(); err != nil {
+ return thrift.PrependError("error reading list end: ", err)
+ }
+ return nil
+}
+
+func (p *Batch) Write(oprot thrift.TProtocol) error {
+ if err := oprot.WriteStructBegin("Batch"); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write struct begin error: ", p), err)
+ }
+ if err := p.writeField1(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField2(oprot); err != nil {
+ return err
+ }
+ if err := oprot.WriteFieldStop(); err != nil {
+ return thrift.PrependError("write field stop error: ", err)
+ }
+ if err := oprot.WriteStructEnd(); err != nil {
+ return thrift.PrependError("write struct stop error: ", err)
+ }
+ return nil
+}
+
+func (p *Batch) writeField1(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("process", thrift.STRUCT, 1); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 1:process: ", p), err)
+ }
+ if err := p.Process.Write(oprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error writing struct: ", p.Process), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 1:process: ", p), err)
+ }
+ return err
+}
+
+func (p *Batch) writeField2(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("spans", thrift.LIST, 2); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 2:spans: ", p), err)
+ }
+ if err := oprot.WriteListBegin(thrift.STRUCT, len(p.Spans)); err != nil {
+ return thrift.PrependError("error writing list begin: ", err)
+ }
+ for _, v := range p.Spans {
+ if err := v.Write(oprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error writing struct: ", v), err)
+ }
+ }
+ if err := oprot.WriteListEnd(); err != nil {
+ return thrift.PrependError("error writing list end: ", err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 2:spans: ", p), err)
+ }
+ return err
+}
+
+func (p *Batch) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return fmt.Sprintf("Batch(%+v)", *p)
+}
+
+// Attributes:
+// - Ok
+type BatchSubmitResponse struct {
+ Ok bool `thrift:"ok,1,required" json:"ok"`
+}
+
+func NewBatchSubmitResponse() *BatchSubmitResponse {
+ return &BatchSubmitResponse{}
+}
+
+func (p *BatchSubmitResponse) GetOk() bool {
+ return p.Ok
+}
+func (p *BatchSubmitResponse) Read(iprot thrift.TProtocol) error {
+ if _, err := iprot.ReadStructBegin(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read error: ", p), err)
+ }
+
+ var issetOk bool = false
+
+ for {
+ _, fieldTypeId, fieldId, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T field %d read error: ", p, fieldId), err)
+ }
+ if fieldTypeId == thrift.STOP {
+ break
+ }
+ switch fieldId {
+ case 1:
+ if err := p.readField1(iprot); err != nil {
+ return err
+ }
+ issetOk = true
+ default:
+ if err := iprot.Skip(fieldTypeId); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadFieldEnd(); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadStructEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read struct end error: ", p), err)
+ }
+ if !issetOk {
+ return thrift.NewTProtocolExceptionWithType(thrift.INVALID_DATA, fmt.Errorf("Required field Ok is not set"))
+ }
+ return nil
+}
+
+func (p *BatchSubmitResponse) readField1(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadBool(); err != nil {
+ return thrift.PrependError("error reading field 1: ", err)
+ } else {
+ p.Ok = v
+ }
+ return nil
+}
+
+func (p *BatchSubmitResponse) Write(oprot thrift.TProtocol) error {
+ if err := oprot.WriteStructBegin("BatchSubmitResponse"); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write struct begin error: ", p), err)
+ }
+ if err := p.writeField1(oprot); err != nil {
+ return err
+ }
+ if err := oprot.WriteFieldStop(); err != nil {
+ return thrift.PrependError("write field stop error: ", err)
+ }
+ if err := oprot.WriteStructEnd(); err != nil {
+ return thrift.PrependError("write struct stop error: ", err)
+ }
+ return nil
+}
+
+func (p *BatchSubmitResponse) writeField1(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("ok", thrift.BOOL, 1); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 1:ok: ", p), err)
+ }
+ if err := oprot.WriteBool(bool(p.Ok)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.ok (1) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 1:ok: ", p), err)
+ }
+ return err
+}
+
+func (p *BatchSubmitResponse) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return fmt.Sprintf("BatchSubmitResponse(%+v)", *p)
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/thrift-gen/sampling/constants.go b/vendor/github.com/uber/jaeger-client-go/thrift-gen/sampling/constants.go
new file mode 100644
index 000000000..0f6e3a884
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/thrift-gen/sampling/constants.go
@@ -0,0 +1,18 @@
+// Autogenerated by Thrift Compiler (0.9.3)
+// DO NOT EDIT UNLESS YOU ARE SURE THAT YOU KNOW WHAT YOU ARE DOING
+
+package sampling
+
+import (
+ "bytes"
+ "fmt"
+ "github.com/uber/jaeger-client-go/thrift"
+)
+
+// (needed to ensure safety because of naive import list construction.)
+var _ = thrift.ZERO
+var _ = fmt.Printf
+var _ = bytes.Equal
+
+func init() {
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/thrift-gen/sampling/samplingmanager.go b/vendor/github.com/uber/jaeger-client-go/thrift-gen/sampling/samplingmanager.go
new file mode 100644
index 000000000..33179cfeb
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/thrift-gen/sampling/samplingmanager.go
@@ -0,0 +1,410 @@
+// Autogenerated by Thrift Compiler (0.9.3)
+// DO NOT EDIT UNLESS YOU ARE SURE THAT YOU KNOW WHAT YOU ARE DOING
+
+package sampling
+
+import (
+ "bytes"
+ "fmt"
+ "github.com/uber/jaeger-client-go/thrift"
+)
+
+// (needed to ensure safety because of naive import list construction.)
+var _ = thrift.ZERO
+var _ = fmt.Printf
+var _ = bytes.Equal
+
+type SamplingManager interface {
+ // Parameters:
+ // - ServiceName
+ GetSamplingStrategy(serviceName string) (r *SamplingStrategyResponse, err error)
+}
+
+type SamplingManagerClient struct {
+ Transport thrift.TTransport
+ ProtocolFactory thrift.TProtocolFactory
+ InputProtocol thrift.TProtocol
+ OutputProtocol thrift.TProtocol
+ SeqId int32
+}
+
+func NewSamplingManagerClientFactory(t thrift.TTransport, f thrift.TProtocolFactory) *SamplingManagerClient {
+ return &SamplingManagerClient{Transport: t,
+ ProtocolFactory: f,
+ InputProtocol: f.GetProtocol(t),
+ OutputProtocol: f.GetProtocol(t),
+ SeqId: 0,
+ }
+}
+
+func NewSamplingManagerClientProtocol(t thrift.TTransport, iprot thrift.TProtocol, oprot thrift.TProtocol) *SamplingManagerClient {
+ return &SamplingManagerClient{Transport: t,
+ ProtocolFactory: nil,
+ InputProtocol: iprot,
+ OutputProtocol: oprot,
+ SeqId: 0,
+ }
+}
+
+// Parameters:
+// - ServiceName
+func (p *SamplingManagerClient) GetSamplingStrategy(serviceName string) (r *SamplingStrategyResponse, err error) {
+ if err = p.sendGetSamplingStrategy(serviceName); err != nil {
+ return
+ }
+ return p.recvGetSamplingStrategy()
+}
+
+func (p *SamplingManagerClient) sendGetSamplingStrategy(serviceName string) (err error) {
+ oprot := p.OutputProtocol
+ if oprot == nil {
+ oprot = p.ProtocolFactory.GetProtocol(p.Transport)
+ p.OutputProtocol = oprot
+ }
+ p.SeqId++
+ if err = oprot.WriteMessageBegin("getSamplingStrategy", thrift.CALL, p.SeqId); err != nil {
+ return
+ }
+ args := SamplingManagerGetSamplingStrategyArgs{
+ ServiceName: serviceName,
+ }
+ if err = args.Write(oprot); err != nil {
+ return
+ }
+ if err = oprot.WriteMessageEnd(); err != nil {
+ return
+ }
+ return oprot.Flush()
+}
+
+func (p *SamplingManagerClient) recvGetSamplingStrategy() (value *SamplingStrategyResponse, err error) {
+ iprot := p.InputProtocol
+ if iprot == nil {
+ iprot = p.ProtocolFactory.GetProtocol(p.Transport)
+ p.InputProtocol = iprot
+ }
+ method, mTypeId, seqId, err := iprot.ReadMessageBegin()
+ if err != nil {
+ return
+ }
+ if method != "getSamplingStrategy" {
+ err = thrift.NewTApplicationException(thrift.WRONG_METHOD_NAME, "getSamplingStrategy failed: wrong method name")
+ return
+ }
+ if p.SeqId != seqId {
+ err = thrift.NewTApplicationException(thrift.BAD_SEQUENCE_ID, "getSamplingStrategy failed: out of sequence response")
+ return
+ }
+ if mTypeId == thrift.EXCEPTION {
+ error1 := thrift.NewTApplicationException(thrift.UNKNOWN_APPLICATION_EXCEPTION, "Unknown Exception")
+ var error2 error
+ error2, err = error1.Read(iprot)
+ if err != nil {
+ return
+ }
+ if err = iprot.ReadMessageEnd(); err != nil {
+ return
+ }
+ err = error2
+ return
+ }
+ if mTypeId != thrift.REPLY {
+ err = thrift.NewTApplicationException(thrift.INVALID_MESSAGE_TYPE_EXCEPTION, "getSamplingStrategy failed: invalid message type")
+ return
+ }
+ result := SamplingManagerGetSamplingStrategyResult{}
+ if err = result.Read(iprot); err != nil {
+ return
+ }
+ if err = iprot.ReadMessageEnd(); err != nil {
+ return
+ }
+ value = result.GetSuccess()
+ return
+}
+
+type SamplingManagerProcessor struct {
+ processorMap map[string]thrift.TProcessorFunction
+ handler SamplingManager
+}
+
+func (p *SamplingManagerProcessor) AddToProcessorMap(key string, processor thrift.TProcessorFunction) {
+ p.processorMap[key] = processor
+}
+
+func (p *SamplingManagerProcessor) GetProcessorFunction(key string) (processor thrift.TProcessorFunction, ok bool) {
+ processor, ok = p.processorMap[key]
+ return processor, ok
+}
+
+func (p *SamplingManagerProcessor) ProcessorMap() map[string]thrift.TProcessorFunction {
+ return p.processorMap
+}
+
+func NewSamplingManagerProcessor(handler SamplingManager) *SamplingManagerProcessor {
+
+ self3 := &SamplingManagerProcessor{handler: handler, processorMap: make(map[string]thrift.TProcessorFunction)}
+ self3.processorMap["getSamplingStrategy"] = &samplingManagerProcessorGetSamplingStrategy{handler: handler}
+ return self3
+}
+
+func (p *SamplingManagerProcessor) Process(iprot, oprot thrift.TProtocol) (success bool, err thrift.TException) {
+ name, _, seqId, err := iprot.ReadMessageBegin()
+ if err != nil {
+ return false, err
+ }
+ if processor, ok := p.GetProcessorFunction(name); ok {
+ return processor.Process(seqId, iprot, oprot)
+ }
+ iprot.Skip(thrift.STRUCT)
+ iprot.ReadMessageEnd()
+ x4 := thrift.NewTApplicationException(thrift.UNKNOWN_METHOD, "Unknown function "+name)
+ oprot.WriteMessageBegin(name, thrift.EXCEPTION, seqId)
+ x4.Write(oprot)
+ oprot.WriteMessageEnd()
+ oprot.Flush()
+ return false, x4
+
+}
+
+type samplingManagerProcessorGetSamplingStrategy struct {
+ handler SamplingManager
+}
+
+func (p *samplingManagerProcessorGetSamplingStrategy) Process(seqId int32, iprot, oprot thrift.TProtocol) (success bool, err thrift.TException) {
+ args := SamplingManagerGetSamplingStrategyArgs{}
+ if err = args.Read(iprot); err != nil {
+ iprot.ReadMessageEnd()
+ x := thrift.NewTApplicationException(thrift.PROTOCOL_ERROR, err.Error())
+ oprot.WriteMessageBegin("getSamplingStrategy", thrift.EXCEPTION, seqId)
+ x.Write(oprot)
+ oprot.WriteMessageEnd()
+ oprot.Flush()
+ return false, err
+ }
+
+ iprot.ReadMessageEnd()
+ result := SamplingManagerGetSamplingStrategyResult{}
+ var retval *SamplingStrategyResponse
+ var err2 error
+ if retval, err2 = p.handler.GetSamplingStrategy(args.ServiceName); err2 != nil {
+ x := thrift.NewTApplicationException(thrift.INTERNAL_ERROR, "Internal error processing getSamplingStrategy: "+err2.Error())
+ oprot.WriteMessageBegin("getSamplingStrategy", thrift.EXCEPTION, seqId)
+ x.Write(oprot)
+ oprot.WriteMessageEnd()
+ oprot.Flush()
+ return true, err2
+ } else {
+ result.Success = retval
+ }
+ if err2 = oprot.WriteMessageBegin("getSamplingStrategy", thrift.REPLY, seqId); err2 != nil {
+ err = err2
+ }
+ if err2 = result.Write(oprot); err == nil && err2 != nil {
+ err = err2
+ }
+ if err2 = oprot.WriteMessageEnd(); err == nil && err2 != nil {
+ err = err2
+ }
+ if err2 = oprot.Flush(); err == nil && err2 != nil {
+ err = err2
+ }
+ if err != nil {
+ return
+ }
+ return true, err
+}
+
+// HELPER FUNCTIONS AND STRUCTURES
+
+// Attributes:
+// - ServiceName
+type SamplingManagerGetSamplingStrategyArgs struct {
+ ServiceName string `thrift:"serviceName,1" json:"serviceName"`
+}
+
+func NewSamplingManagerGetSamplingStrategyArgs() *SamplingManagerGetSamplingStrategyArgs {
+ return &SamplingManagerGetSamplingStrategyArgs{}
+}
+
+func (p *SamplingManagerGetSamplingStrategyArgs) GetServiceName() string {
+ return p.ServiceName
+}
+func (p *SamplingManagerGetSamplingStrategyArgs) Read(iprot thrift.TProtocol) error {
+ if _, err := iprot.ReadStructBegin(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read error: ", p), err)
+ }
+
+ for {
+ _, fieldTypeId, fieldId, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T field %d read error: ", p, fieldId), err)
+ }
+ if fieldTypeId == thrift.STOP {
+ break
+ }
+ switch fieldId {
+ case 1:
+ if err := p.readField1(iprot); err != nil {
+ return err
+ }
+ default:
+ if err := iprot.Skip(fieldTypeId); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadFieldEnd(); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadStructEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read struct end error: ", p), err)
+ }
+ return nil
+}
+
+func (p *SamplingManagerGetSamplingStrategyArgs) readField1(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadString(); err != nil {
+ return thrift.PrependError("error reading field 1: ", err)
+ } else {
+ p.ServiceName = v
+ }
+ return nil
+}
+
+func (p *SamplingManagerGetSamplingStrategyArgs) Write(oprot thrift.TProtocol) error {
+ if err := oprot.WriteStructBegin("getSamplingStrategy_args"); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write struct begin error: ", p), err)
+ }
+ if err := p.writeField1(oprot); err != nil {
+ return err
+ }
+ if err := oprot.WriteFieldStop(); err != nil {
+ return thrift.PrependError("write field stop error: ", err)
+ }
+ if err := oprot.WriteStructEnd(); err != nil {
+ return thrift.PrependError("write struct stop error: ", err)
+ }
+ return nil
+}
+
+func (p *SamplingManagerGetSamplingStrategyArgs) writeField1(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("serviceName", thrift.STRING, 1); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 1:serviceName: ", p), err)
+ }
+ if err := oprot.WriteString(string(p.ServiceName)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.serviceName (1) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 1:serviceName: ", p), err)
+ }
+ return err
+}
+
+func (p *SamplingManagerGetSamplingStrategyArgs) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return fmt.Sprintf("SamplingManagerGetSamplingStrategyArgs(%+v)", *p)
+}
+
+// Attributes:
+// - Success
+type SamplingManagerGetSamplingStrategyResult struct {
+ Success *SamplingStrategyResponse `thrift:"success,0" json:"success,omitempty"`
+}
+
+func NewSamplingManagerGetSamplingStrategyResult() *SamplingManagerGetSamplingStrategyResult {
+ return &SamplingManagerGetSamplingStrategyResult{}
+}
+
+var SamplingManagerGetSamplingStrategyResult_Success_DEFAULT *SamplingStrategyResponse
+
+func (p *SamplingManagerGetSamplingStrategyResult) GetSuccess() *SamplingStrategyResponse {
+ if !p.IsSetSuccess() {
+ return SamplingManagerGetSamplingStrategyResult_Success_DEFAULT
+ }
+ return p.Success
+}
+func (p *SamplingManagerGetSamplingStrategyResult) IsSetSuccess() bool {
+ return p.Success != nil
+}
+
+func (p *SamplingManagerGetSamplingStrategyResult) Read(iprot thrift.TProtocol) error {
+ if _, err := iprot.ReadStructBegin(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read error: ", p), err)
+ }
+
+ for {
+ _, fieldTypeId, fieldId, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T field %d read error: ", p, fieldId), err)
+ }
+ if fieldTypeId == thrift.STOP {
+ break
+ }
+ switch fieldId {
+ case 0:
+ if err := p.readField0(iprot); err != nil {
+ return err
+ }
+ default:
+ if err := iprot.Skip(fieldTypeId); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadFieldEnd(); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadStructEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read struct end error: ", p), err)
+ }
+ return nil
+}
+
+func (p *SamplingManagerGetSamplingStrategyResult) readField0(iprot thrift.TProtocol) error {
+ p.Success = &SamplingStrategyResponse{}
+ if err := p.Success.Read(iprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error reading struct: ", p.Success), err)
+ }
+ return nil
+}
+
+func (p *SamplingManagerGetSamplingStrategyResult) Write(oprot thrift.TProtocol) error {
+ if err := oprot.WriteStructBegin("getSamplingStrategy_result"); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write struct begin error: ", p), err)
+ }
+ if err := p.writeField0(oprot); err != nil {
+ return err
+ }
+ if err := oprot.WriteFieldStop(); err != nil {
+ return thrift.PrependError("write field stop error: ", err)
+ }
+ if err := oprot.WriteStructEnd(); err != nil {
+ return thrift.PrependError("write struct stop error: ", err)
+ }
+ return nil
+}
+
+func (p *SamplingManagerGetSamplingStrategyResult) writeField0(oprot thrift.TProtocol) (err error) {
+ if p.IsSetSuccess() {
+ if err := oprot.WriteFieldBegin("success", thrift.STRUCT, 0); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 0:success: ", p), err)
+ }
+ if err := p.Success.Write(oprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error writing struct: ", p.Success), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 0:success: ", p), err)
+ }
+ }
+ return err
+}
+
+func (p *SamplingManagerGetSamplingStrategyResult) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return fmt.Sprintf("SamplingManagerGetSamplingStrategyResult(%+v)", *p)
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/thrift-gen/sampling/ttypes.go b/vendor/github.com/uber/jaeger-client-go/thrift-gen/sampling/ttypes.go
new file mode 100644
index 000000000..9abaf0542
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/thrift-gen/sampling/ttypes.go
@@ -0,0 +1,873 @@
+// Autogenerated by Thrift Compiler (0.9.3)
+// DO NOT EDIT UNLESS YOU ARE SURE THAT YOU KNOW WHAT YOU ARE DOING
+
+package sampling
+
+import (
+ "bytes"
+ "fmt"
+ "github.com/uber/jaeger-client-go/thrift"
+)
+
+// (needed to ensure safety because of naive import list construction.)
+var _ = thrift.ZERO
+var _ = fmt.Printf
+var _ = bytes.Equal
+
+var GoUnusedProtection__ int
+
+type SamplingStrategyType int64
+
+const (
+ SamplingStrategyType_PROBABILISTIC SamplingStrategyType = 0
+ SamplingStrategyType_RATE_LIMITING SamplingStrategyType = 1
+)
+
+func (p SamplingStrategyType) String() string {
+ switch p {
+ case SamplingStrategyType_PROBABILISTIC:
+ return "PROBABILISTIC"
+ case SamplingStrategyType_RATE_LIMITING:
+ return "RATE_LIMITING"
+ }
+ return "<UNSET>"
+}
+
+func SamplingStrategyTypeFromString(s string) (SamplingStrategyType, error) {
+ switch s {
+ case "PROBABILISTIC":
+ return SamplingStrategyType_PROBABILISTIC, nil
+ case "RATE_LIMITING":
+ return SamplingStrategyType_RATE_LIMITING, nil
+ }
+ return SamplingStrategyType(0), fmt.Errorf("not a valid SamplingStrategyType string")
+}
+
+func SamplingStrategyTypePtr(v SamplingStrategyType) *SamplingStrategyType { return &v }
+
+func (p SamplingStrategyType) MarshalText() ([]byte, error) {
+ return []byte(p.String()), nil
+}
+
+func (p *SamplingStrategyType) UnmarshalText(text []byte) error {
+ q, err := SamplingStrategyTypeFromString(string(text))
+ if err != nil {
+ return err
+ }
+ *p = q
+ return nil
+}
+
+// Attributes:
+// - SamplingRate
+type ProbabilisticSamplingStrategy struct {
+ SamplingRate float64 `thrift:"samplingRate,1,required" json:"samplingRate"`
+}
+
+func NewProbabilisticSamplingStrategy() *ProbabilisticSamplingStrategy {
+ return &ProbabilisticSamplingStrategy{}
+}
+
+func (p *ProbabilisticSamplingStrategy) GetSamplingRate() float64 {
+ return p.SamplingRate
+}
+func (p *ProbabilisticSamplingStrategy) Read(iprot thrift.TProtocol) error {
+ if _, err := iprot.ReadStructBegin(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read error: ", p), err)
+ }
+
+ var issetSamplingRate bool = false
+
+ for {
+ _, fieldTypeId, fieldId, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T field %d read error: ", p, fieldId), err)
+ }
+ if fieldTypeId == thrift.STOP {
+ break
+ }
+ switch fieldId {
+ case 1:
+ if err := p.readField1(iprot); err != nil {
+ return err
+ }
+ issetSamplingRate = true
+ default:
+ if err := iprot.Skip(fieldTypeId); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadFieldEnd(); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadStructEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read struct end error: ", p), err)
+ }
+ if !issetSamplingRate {
+ return thrift.NewTProtocolExceptionWithType(thrift.INVALID_DATA, fmt.Errorf("Required field SamplingRate is not set"))
+ }
+ return nil
+}
+
+func (p *ProbabilisticSamplingStrategy) readField1(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadDouble(); err != nil {
+ return thrift.PrependError("error reading field 1: ", err)
+ } else {
+ p.SamplingRate = v
+ }
+ return nil
+}
+
+func (p *ProbabilisticSamplingStrategy) Write(oprot thrift.TProtocol) error {
+ if err := oprot.WriteStructBegin("ProbabilisticSamplingStrategy"); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write struct begin error: ", p), err)
+ }
+ if err := p.writeField1(oprot); err != nil {
+ return err
+ }
+ if err := oprot.WriteFieldStop(); err != nil {
+ return thrift.PrependError("write field stop error: ", err)
+ }
+ if err := oprot.WriteStructEnd(); err != nil {
+ return thrift.PrependError("write struct stop error: ", err)
+ }
+ return nil
+}
+
+func (p *ProbabilisticSamplingStrategy) writeField1(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("samplingRate", thrift.DOUBLE, 1); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 1:samplingRate: ", p), err)
+ }
+ if err := oprot.WriteDouble(float64(p.SamplingRate)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.samplingRate (1) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 1:samplingRate: ", p), err)
+ }
+ return err
+}
+
+func (p *ProbabilisticSamplingStrategy) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return fmt.Sprintf("ProbabilisticSamplingStrategy(%+v)", *p)
+}
+
+// Attributes:
+// - MaxTracesPerSecond
+type RateLimitingSamplingStrategy struct {
+ MaxTracesPerSecond int16 `thrift:"maxTracesPerSecond,1,required" json:"maxTracesPerSecond"`
+}
+
+func NewRateLimitingSamplingStrategy() *RateLimitingSamplingStrategy {
+ return &RateLimitingSamplingStrategy{}
+}
+
+func (p *RateLimitingSamplingStrategy) GetMaxTracesPerSecond() int16 {
+ return p.MaxTracesPerSecond
+}
+func (p *RateLimitingSamplingStrategy) Read(iprot thrift.TProtocol) error {
+ if _, err := iprot.ReadStructBegin(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read error: ", p), err)
+ }
+
+ var issetMaxTracesPerSecond bool = false
+
+ for {
+ _, fieldTypeId, fieldId, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T field %d read error: ", p, fieldId), err)
+ }
+ if fieldTypeId == thrift.STOP {
+ break
+ }
+ switch fieldId {
+ case 1:
+ if err := p.readField1(iprot); err != nil {
+ return err
+ }
+ issetMaxTracesPerSecond = true
+ default:
+ if err := iprot.Skip(fieldTypeId); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadFieldEnd(); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadStructEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read struct end error: ", p), err)
+ }
+ if !issetMaxTracesPerSecond {
+ return thrift.NewTProtocolExceptionWithType(thrift.INVALID_DATA, fmt.Errorf("Required field MaxTracesPerSecond is not set"))
+ }
+ return nil
+}
+
+func (p *RateLimitingSamplingStrategy) readField1(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadI16(); err != nil {
+ return thrift.PrependError("error reading field 1: ", err)
+ } else {
+ p.MaxTracesPerSecond = v
+ }
+ return nil
+}
+
+func (p *RateLimitingSamplingStrategy) Write(oprot thrift.TProtocol) error {
+ if err := oprot.WriteStructBegin("RateLimitingSamplingStrategy"); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write struct begin error: ", p), err)
+ }
+ if err := p.writeField1(oprot); err != nil {
+ return err
+ }
+ if err := oprot.WriteFieldStop(); err != nil {
+ return thrift.PrependError("write field stop error: ", err)
+ }
+ if err := oprot.WriteStructEnd(); err != nil {
+ return thrift.PrependError("write struct stop error: ", err)
+ }
+ return nil
+}
+
+func (p *RateLimitingSamplingStrategy) writeField1(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("maxTracesPerSecond", thrift.I16, 1); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 1:maxTracesPerSecond: ", p), err)
+ }
+ if err := oprot.WriteI16(int16(p.MaxTracesPerSecond)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.maxTracesPerSecond (1) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 1:maxTracesPerSecond: ", p), err)
+ }
+ return err
+}
+
+func (p *RateLimitingSamplingStrategy) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return fmt.Sprintf("RateLimitingSamplingStrategy(%+v)", *p)
+}
+
+// Attributes:
+// - Operation
+// - ProbabilisticSampling
+type OperationSamplingStrategy struct {
+ Operation string `thrift:"operation,1,required" json:"operation"`
+ ProbabilisticSampling *ProbabilisticSamplingStrategy `thrift:"probabilisticSampling,2,required" json:"probabilisticSampling"`
+}
+
+func NewOperationSamplingStrategy() *OperationSamplingStrategy {
+ return &OperationSamplingStrategy{}
+}
+
+func (p *OperationSamplingStrategy) GetOperation() string {
+ return p.Operation
+}
+
+var OperationSamplingStrategy_ProbabilisticSampling_DEFAULT *ProbabilisticSamplingStrategy
+
+func (p *OperationSamplingStrategy) GetProbabilisticSampling() *ProbabilisticSamplingStrategy {
+ if !p.IsSetProbabilisticSampling() {
+ return OperationSamplingStrategy_ProbabilisticSampling_DEFAULT
+ }
+ return p.ProbabilisticSampling
+}
+func (p *OperationSamplingStrategy) IsSetProbabilisticSampling() bool {
+ return p.ProbabilisticSampling != nil
+}
+
+func (p *OperationSamplingStrategy) Read(iprot thrift.TProtocol) error {
+ if _, err := iprot.ReadStructBegin(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read error: ", p), err)
+ }
+
+ var issetOperation bool = false
+ var issetProbabilisticSampling bool = false
+
+ for {
+ _, fieldTypeId, fieldId, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T field %d read error: ", p, fieldId), err)
+ }
+ if fieldTypeId == thrift.STOP {
+ break
+ }
+ switch fieldId {
+ case 1:
+ if err := p.readField1(iprot); err != nil {
+ return err
+ }
+ issetOperation = true
+ case 2:
+ if err := p.readField2(iprot); err != nil {
+ return err
+ }
+ issetProbabilisticSampling = true
+ default:
+ if err := iprot.Skip(fieldTypeId); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadFieldEnd(); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadStructEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read struct end error: ", p), err)
+ }
+ if !issetOperation {
+ return thrift.NewTProtocolExceptionWithType(thrift.INVALID_DATA, fmt.Errorf("Required field Operation is not set"))
+ }
+ if !issetProbabilisticSampling {
+ return thrift.NewTProtocolExceptionWithType(thrift.INVALID_DATA, fmt.Errorf("Required field ProbabilisticSampling is not set"))
+ }
+ return nil
+}
+
+func (p *OperationSamplingStrategy) readField1(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadString(); err != nil {
+ return thrift.PrependError("error reading field 1: ", err)
+ } else {
+ p.Operation = v
+ }
+ return nil
+}
+
+func (p *OperationSamplingStrategy) readField2(iprot thrift.TProtocol) error {
+ p.ProbabilisticSampling = &ProbabilisticSamplingStrategy{}
+ if err := p.ProbabilisticSampling.Read(iprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error reading struct: ", p.ProbabilisticSampling), err)
+ }
+ return nil
+}
+
+func (p *OperationSamplingStrategy) Write(oprot thrift.TProtocol) error {
+ if err := oprot.WriteStructBegin("OperationSamplingStrategy"); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write struct begin error: ", p), err)
+ }
+ if err := p.writeField1(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField2(oprot); err != nil {
+ return err
+ }
+ if err := oprot.WriteFieldStop(); err != nil {
+ return thrift.PrependError("write field stop error: ", err)
+ }
+ if err := oprot.WriteStructEnd(); err != nil {
+ return thrift.PrependError("write struct stop error: ", err)
+ }
+ return nil
+}
+
+func (p *OperationSamplingStrategy) writeField1(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("operation", thrift.STRING, 1); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 1:operation: ", p), err)
+ }
+ if err := oprot.WriteString(string(p.Operation)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.operation (1) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 1:operation: ", p), err)
+ }
+ return err
+}
+
+func (p *OperationSamplingStrategy) writeField2(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("probabilisticSampling", thrift.STRUCT, 2); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 2:probabilisticSampling: ", p), err)
+ }
+ if err := p.ProbabilisticSampling.Write(oprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error writing struct: ", p.ProbabilisticSampling), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 2:probabilisticSampling: ", p), err)
+ }
+ return err
+}
+
+func (p *OperationSamplingStrategy) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return fmt.Sprintf("OperationSamplingStrategy(%+v)", *p)
+}
+
+// Attributes:
+// - DefaultSamplingProbability
+// - DefaultLowerBoundTracesPerSecond
+// - PerOperationStrategies
+// - DefaultUpperBoundTracesPerSecond
+type PerOperationSamplingStrategies struct {
+ DefaultSamplingProbability float64 `thrift:"defaultSamplingProbability,1,required" json:"defaultSamplingProbability"`
+ DefaultLowerBoundTracesPerSecond float64 `thrift:"defaultLowerBoundTracesPerSecond,2,required" json:"defaultLowerBoundTracesPerSecond"`
+ PerOperationStrategies []*OperationSamplingStrategy `thrift:"perOperationStrategies,3,required" json:"perOperationStrategies"`
+ DefaultUpperBoundTracesPerSecond *float64 `thrift:"defaultUpperBoundTracesPerSecond,4" json:"defaultUpperBoundTracesPerSecond,omitempty"`
+}
+
+func NewPerOperationSamplingStrategies() *PerOperationSamplingStrategies {
+ return &PerOperationSamplingStrategies{}
+}
+
+func (p *PerOperationSamplingStrategies) GetDefaultSamplingProbability() float64 {
+ return p.DefaultSamplingProbability
+}
+
+func (p *PerOperationSamplingStrategies) GetDefaultLowerBoundTracesPerSecond() float64 {
+ return p.DefaultLowerBoundTracesPerSecond
+}
+
+func (p *PerOperationSamplingStrategies) GetPerOperationStrategies() []*OperationSamplingStrategy {
+ return p.PerOperationStrategies
+}
+
+var PerOperationSamplingStrategies_DefaultUpperBoundTracesPerSecond_DEFAULT float64
+
+func (p *PerOperationSamplingStrategies) GetDefaultUpperBoundTracesPerSecond() float64 {
+ if !p.IsSetDefaultUpperBoundTracesPerSecond() {
+ return PerOperationSamplingStrategies_DefaultUpperBoundTracesPerSecond_DEFAULT
+ }
+ return *p.DefaultUpperBoundTracesPerSecond
+}
+func (p *PerOperationSamplingStrategies) IsSetDefaultUpperBoundTracesPerSecond() bool {
+ return p.DefaultUpperBoundTracesPerSecond != nil
+}
+
+func (p *PerOperationSamplingStrategies) Read(iprot thrift.TProtocol) error {
+ if _, err := iprot.ReadStructBegin(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read error: ", p), err)
+ }
+
+ var issetDefaultSamplingProbability bool = false
+ var issetDefaultLowerBoundTracesPerSecond bool = false
+ var issetPerOperationStrategies bool = false
+
+ for {
+ _, fieldTypeId, fieldId, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T field %d read error: ", p, fieldId), err)
+ }
+ if fieldTypeId == thrift.STOP {
+ break
+ }
+ switch fieldId {
+ case 1:
+ if err := p.readField1(iprot); err != nil {
+ return err
+ }
+ issetDefaultSamplingProbability = true
+ case 2:
+ if err := p.readField2(iprot); err != nil {
+ return err
+ }
+ issetDefaultLowerBoundTracesPerSecond = true
+ case 3:
+ if err := p.readField3(iprot); err != nil {
+ return err
+ }
+ issetPerOperationStrategies = true
+ case 4:
+ if err := p.readField4(iprot); err != nil {
+ return err
+ }
+ default:
+ if err := iprot.Skip(fieldTypeId); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadFieldEnd(); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadStructEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read struct end error: ", p), err)
+ }
+ if !issetDefaultSamplingProbability {
+ return thrift.NewTProtocolExceptionWithType(thrift.INVALID_DATA, fmt.Errorf("Required field DefaultSamplingProbability is not set"))
+ }
+ if !issetDefaultLowerBoundTracesPerSecond {
+ return thrift.NewTProtocolExceptionWithType(thrift.INVALID_DATA, fmt.Errorf("Required field DefaultLowerBoundTracesPerSecond is not set"))
+ }
+ if !issetPerOperationStrategies {
+ return thrift.NewTProtocolExceptionWithType(thrift.INVALID_DATA, fmt.Errorf("Required field PerOperationStrategies is not set"))
+ }
+ return nil
+}
+
+func (p *PerOperationSamplingStrategies) readField1(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadDouble(); err != nil {
+ return thrift.PrependError("error reading field 1: ", err)
+ } else {
+ p.DefaultSamplingProbability = v
+ }
+ return nil
+}
+
+func (p *PerOperationSamplingStrategies) readField2(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadDouble(); err != nil {
+ return thrift.PrependError("error reading field 2: ", err)
+ } else {
+ p.DefaultLowerBoundTracesPerSecond = v
+ }
+ return nil
+}
+
+func (p *PerOperationSamplingStrategies) readField3(iprot thrift.TProtocol) error {
+ _, size, err := iprot.ReadListBegin()
+ if err != nil {
+ return thrift.PrependError("error reading list begin: ", err)
+ }
+ tSlice := make([]*OperationSamplingStrategy, 0, size)
+ p.PerOperationStrategies = tSlice
+ for i := 0; i < size; i++ {
+ _elem0 := &OperationSamplingStrategy{}
+ if err := _elem0.Read(iprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error reading struct: ", _elem0), err)
+ }
+ p.PerOperationStrategies = append(p.PerOperationStrategies, _elem0)
+ }
+ if err := iprot.ReadListEnd(); err != nil {
+ return thrift.PrependError("error reading list end: ", err)
+ }
+ return nil
+}
+
+func (p *PerOperationSamplingStrategies) readField4(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadDouble(); err != nil {
+ return thrift.PrependError("error reading field 4: ", err)
+ } else {
+ p.DefaultUpperBoundTracesPerSecond = &v
+ }
+ return nil
+}
+
+func (p *PerOperationSamplingStrategies) Write(oprot thrift.TProtocol) error {
+ if err := oprot.WriteStructBegin("PerOperationSamplingStrategies"); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write struct begin error: ", p), err)
+ }
+ if err := p.writeField1(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField2(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField3(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField4(oprot); err != nil {
+ return err
+ }
+ if err := oprot.WriteFieldStop(); err != nil {
+ return thrift.PrependError("write field stop error: ", err)
+ }
+ if err := oprot.WriteStructEnd(); err != nil {
+ return thrift.PrependError("write struct stop error: ", err)
+ }
+ return nil
+}
+
+func (p *PerOperationSamplingStrategies) writeField1(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("defaultSamplingProbability", thrift.DOUBLE, 1); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 1:defaultSamplingProbability: ", p), err)
+ }
+ if err := oprot.WriteDouble(float64(p.DefaultSamplingProbability)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.defaultSamplingProbability (1) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 1:defaultSamplingProbability: ", p), err)
+ }
+ return err
+}
+
+func (p *PerOperationSamplingStrategies) writeField2(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("defaultLowerBoundTracesPerSecond", thrift.DOUBLE, 2); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 2:defaultLowerBoundTracesPerSecond: ", p), err)
+ }
+ if err := oprot.WriteDouble(float64(p.DefaultLowerBoundTracesPerSecond)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.defaultLowerBoundTracesPerSecond (2) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 2:defaultLowerBoundTracesPerSecond: ", p), err)
+ }
+ return err
+}
+
+func (p *PerOperationSamplingStrategies) writeField3(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("perOperationStrategies", thrift.LIST, 3); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 3:perOperationStrategies: ", p), err)
+ }
+ if err := oprot.WriteListBegin(thrift.STRUCT, len(p.PerOperationStrategies)); err != nil {
+ return thrift.PrependError("error writing list begin: ", err)
+ }
+ for _, v := range p.PerOperationStrategies {
+ if err := v.Write(oprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error writing struct: ", v), err)
+ }
+ }
+ if err := oprot.WriteListEnd(); err != nil {
+ return thrift.PrependError("error writing list end: ", err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 3:perOperationStrategies: ", p), err)
+ }
+ return err
+}
+
+func (p *PerOperationSamplingStrategies) writeField4(oprot thrift.TProtocol) (err error) {
+ if p.IsSetDefaultUpperBoundTracesPerSecond() {
+ if err := oprot.WriteFieldBegin("defaultUpperBoundTracesPerSecond", thrift.DOUBLE, 4); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 4:defaultUpperBoundTracesPerSecond: ", p), err)
+ }
+ if err := oprot.WriteDouble(float64(*p.DefaultUpperBoundTracesPerSecond)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.defaultUpperBoundTracesPerSecond (4) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 4:defaultUpperBoundTracesPerSecond: ", p), err)
+ }
+ }
+ return err
+}
+
+func (p *PerOperationSamplingStrategies) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return fmt.Sprintf("PerOperationSamplingStrategies(%+v)", *p)
+}
+
+// Attributes:
+// - StrategyType
+// - ProbabilisticSampling
+// - RateLimitingSampling
+// - OperationSampling
+type SamplingStrategyResponse struct {
+ StrategyType SamplingStrategyType `thrift:"strategyType,1,required" json:"strategyType"`
+ ProbabilisticSampling *ProbabilisticSamplingStrategy `thrift:"probabilisticSampling,2" json:"probabilisticSampling,omitempty"`
+ RateLimitingSampling *RateLimitingSamplingStrategy `thrift:"rateLimitingSampling,3" json:"rateLimitingSampling,omitempty"`
+ OperationSampling *PerOperationSamplingStrategies `thrift:"operationSampling,4" json:"operationSampling,omitempty"`
+}
+
+func NewSamplingStrategyResponse() *SamplingStrategyResponse {
+ return &SamplingStrategyResponse{}
+}
+
+func (p *SamplingStrategyResponse) GetStrategyType() SamplingStrategyType {
+ return p.StrategyType
+}
+
+var SamplingStrategyResponse_ProbabilisticSampling_DEFAULT *ProbabilisticSamplingStrategy
+
+func (p *SamplingStrategyResponse) GetProbabilisticSampling() *ProbabilisticSamplingStrategy {
+ if !p.IsSetProbabilisticSampling() {
+ return SamplingStrategyResponse_ProbabilisticSampling_DEFAULT
+ }
+ return p.ProbabilisticSampling
+}
+
+var SamplingStrategyResponse_RateLimitingSampling_DEFAULT *RateLimitingSamplingStrategy
+
+func (p *SamplingStrategyResponse) GetRateLimitingSampling() *RateLimitingSamplingStrategy {
+ if !p.IsSetRateLimitingSampling() {
+ return SamplingStrategyResponse_RateLimitingSampling_DEFAULT
+ }
+ return p.RateLimitingSampling
+}
+
+var SamplingStrategyResponse_OperationSampling_DEFAULT *PerOperationSamplingStrategies
+
+func (p *SamplingStrategyResponse) GetOperationSampling() *PerOperationSamplingStrategies {
+ if !p.IsSetOperationSampling() {
+ return SamplingStrategyResponse_OperationSampling_DEFAULT
+ }
+ return p.OperationSampling
+}
+func (p *SamplingStrategyResponse) IsSetProbabilisticSampling() bool {
+ return p.ProbabilisticSampling != nil
+}
+
+func (p *SamplingStrategyResponse) IsSetRateLimitingSampling() bool {
+ return p.RateLimitingSampling != nil
+}
+
+func (p *SamplingStrategyResponse) IsSetOperationSampling() bool {
+ return p.OperationSampling != nil
+}
+
+func (p *SamplingStrategyResponse) Read(iprot thrift.TProtocol) error {
+ if _, err := iprot.ReadStructBegin(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read error: ", p), err)
+ }
+
+ var issetStrategyType bool = false
+
+ for {
+ _, fieldTypeId, fieldId, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T field %d read error: ", p, fieldId), err)
+ }
+ if fieldTypeId == thrift.STOP {
+ break
+ }
+ switch fieldId {
+ case 1:
+ if err := p.readField1(iprot); err != nil {
+ return err
+ }
+ issetStrategyType = true
+ case 2:
+ if err := p.readField2(iprot); err != nil {
+ return err
+ }
+ case 3:
+ if err := p.readField3(iprot); err != nil {
+ return err
+ }
+ case 4:
+ if err := p.readField4(iprot); err != nil {
+ return err
+ }
+ default:
+ if err := iprot.Skip(fieldTypeId); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadFieldEnd(); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadStructEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read struct end error: ", p), err)
+ }
+ if !issetStrategyType {
+ return thrift.NewTProtocolExceptionWithType(thrift.INVALID_DATA, fmt.Errorf("Required field StrategyType is not set"))
+ }
+ return nil
+}
+
+func (p *SamplingStrategyResponse) readField1(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadI32(); err != nil {
+ return thrift.PrependError("error reading field 1: ", err)
+ } else {
+ temp := SamplingStrategyType(v)
+ p.StrategyType = temp
+ }
+ return nil
+}
+
+func (p *SamplingStrategyResponse) readField2(iprot thrift.TProtocol) error {
+ p.ProbabilisticSampling = &ProbabilisticSamplingStrategy{}
+ if err := p.ProbabilisticSampling.Read(iprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error reading struct: ", p.ProbabilisticSampling), err)
+ }
+ return nil
+}
+
+func (p *SamplingStrategyResponse) readField3(iprot thrift.TProtocol) error {
+ p.RateLimitingSampling = &RateLimitingSamplingStrategy{}
+ if err := p.RateLimitingSampling.Read(iprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error reading struct: ", p.RateLimitingSampling), err)
+ }
+ return nil
+}
+
+func (p *SamplingStrategyResponse) readField4(iprot thrift.TProtocol) error {
+ p.OperationSampling = &PerOperationSamplingStrategies{}
+ if err := p.OperationSampling.Read(iprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error reading struct: ", p.OperationSampling), err)
+ }
+ return nil
+}
+
+func (p *SamplingStrategyResponse) Write(oprot thrift.TProtocol) error {
+ if err := oprot.WriteStructBegin("SamplingStrategyResponse"); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write struct begin error: ", p), err)
+ }
+ if err := p.writeField1(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField2(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField3(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField4(oprot); err != nil {
+ return err
+ }
+ if err := oprot.WriteFieldStop(); err != nil {
+ return thrift.PrependError("write field stop error: ", err)
+ }
+ if err := oprot.WriteStructEnd(); err != nil {
+ return thrift.PrependError("write struct stop error: ", err)
+ }
+ return nil
+}
+
+func (p *SamplingStrategyResponse) writeField1(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("strategyType", thrift.I32, 1); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 1:strategyType: ", p), err)
+ }
+ if err := oprot.WriteI32(int32(p.StrategyType)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.strategyType (1) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 1:strategyType: ", p), err)
+ }
+ return err
+}
+
+func (p *SamplingStrategyResponse) writeField2(oprot thrift.TProtocol) (err error) {
+ if p.IsSetProbabilisticSampling() {
+ if err := oprot.WriteFieldBegin("probabilisticSampling", thrift.STRUCT, 2); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 2:probabilisticSampling: ", p), err)
+ }
+ if err := p.ProbabilisticSampling.Write(oprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error writing struct: ", p.ProbabilisticSampling), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 2:probabilisticSampling: ", p), err)
+ }
+ }
+ return err
+}
+
+func (p *SamplingStrategyResponse) writeField3(oprot thrift.TProtocol) (err error) {
+ if p.IsSetRateLimitingSampling() {
+ if err := oprot.WriteFieldBegin("rateLimitingSampling", thrift.STRUCT, 3); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 3:rateLimitingSampling: ", p), err)
+ }
+ if err := p.RateLimitingSampling.Write(oprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error writing struct: ", p.RateLimitingSampling), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 3:rateLimitingSampling: ", p), err)
+ }
+ }
+ return err
+}
+
+func (p *SamplingStrategyResponse) writeField4(oprot thrift.TProtocol) (err error) {
+ if p.IsSetOperationSampling() {
+ if err := oprot.WriteFieldBegin("operationSampling", thrift.STRUCT, 4); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 4:operationSampling: ", p), err)
+ }
+ if err := p.OperationSampling.Write(oprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error writing struct: ", p.OperationSampling), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 4:operationSampling: ", p), err)
+ }
+ }
+ return err
+}
+
+func (p *SamplingStrategyResponse) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return fmt.Sprintf("SamplingStrategyResponse(%+v)", *p)
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/thrift-gen/zipkincore/constants.go b/vendor/github.com/uber/jaeger-client-go/thrift-gen/zipkincore/constants.go
new file mode 100644
index 000000000..f05144bfc
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/thrift-gen/zipkincore/constants.go
@@ -0,0 +1,32 @@
+// Autogenerated by Thrift Compiler (0.9.3)
+// DO NOT EDIT UNLESS YOU ARE SURE THAT YOU KNOW WHAT YOU ARE DOING
+
+package zipkincore
+
+import (
+ "bytes"
+ "fmt"
+ "github.com/uber/jaeger-client-go/thrift"
+)
+
+// (needed to ensure safety because of naive import list construction.)
+var _ = thrift.ZERO
+var _ = fmt.Printf
+var _ = bytes.Equal
+
+const CLIENT_SEND = "cs"
+const CLIENT_RECV = "cr"
+const SERVER_SEND = "ss"
+const SERVER_RECV = "sr"
+const WIRE_SEND = "ws"
+const WIRE_RECV = "wr"
+const CLIENT_SEND_FRAGMENT = "csf"
+const CLIENT_RECV_FRAGMENT = "crf"
+const SERVER_SEND_FRAGMENT = "ssf"
+const SERVER_RECV_FRAGMENT = "srf"
+const LOCAL_COMPONENT = "lc"
+const CLIENT_ADDR = "ca"
+const SERVER_ADDR = "sa"
+
+func init() {
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/thrift-gen/zipkincore/ttypes.go b/vendor/github.com/uber/jaeger-client-go/thrift-gen/zipkincore/ttypes.go
new file mode 100644
index 000000000..34b2b267e
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/thrift-gen/zipkincore/ttypes.go
@@ -0,0 +1,1247 @@
+// Autogenerated by Thrift Compiler (0.9.3)
+// DO NOT EDIT UNLESS YOU ARE SURE THAT YOU KNOW WHAT YOU ARE DOING
+
+package zipkincore
+
+import (
+ "bytes"
+ "fmt"
+ "github.com/uber/jaeger-client-go/thrift"
+)
+
+// (needed to ensure safety because of naive import list construction.)
+var _ = thrift.ZERO
+var _ = fmt.Printf
+var _ = bytes.Equal
+
+var GoUnusedProtection__ int
+
+type AnnotationType int64
+
+const (
+ AnnotationType_BOOL AnnotationType = 0
+ AnnotationType_BYTES AnnotationType = 1
+ AnnotationType_I16 AnnotationType = 2
+ AnnotationType_I32 AnnotationType = 3
+ AnnotationType_I64 AnnotationType = 4
+ AnnotationType_DOUBLE AnnotationType = 5
+ AnnotationType_STRING AnnotationType = 6
+)
+
+func (p AnnotationType) String() string {
+ switch p {
+ case AnnotationType_BOOL:
+ return "BOOL"
+ case AnnotationType_BYTES:
+ return "BYTES"
+ case AnnotationType_I16:
+ return "I16"
+ case AnnotationType_I32:
+ return "I32"
+ case AnnotationType_I64:
+ return "I64"
+ case AnnotationType_DOUBLE:
+ return "DOUBLE"
+ case AnnotationType_STRING:
+ return "STRING"
+ }
+ return "<UNSET>"
+}
+
+func AnnotationTypeFromString(s string) (AnnotationType, error) {
+ switch s {
+ case "BOOL":
+ return AnnotationType_BOOL, nil
+ case "BYTES":
+ return AnnotationType_BYTES, nil
+ case "I16":
+ return AnnotationType_I16, nil
+ case "I32":
+ return AnnotationType_I32, nil
+ case "I64":
+ return AnnotationType_I64, nil
+ case "DOUBLE":
+ return AnnotationType_DOUBLE, nil
+ case "STRING":
+ return AnnotationType_STRING, nil
+ }
+ return AnnotationType(0), fmt.Errorf("not a valid AnnotationType string")
+}
+
+func AnnotationTypePtr(v AnnotationType) *AnnotationType { return &v }
+
+func (p AnnotationType) MarshalText() ([]byte, error) {
+ return []byte(p.String()), nil
+}
+
+func (p *AnnotationType) UnmarshalText(text []byte) error {
+ q, err := AnnotationTypeFromString(string(text))
+ if err != nil {
+ return err
+ }
+ *p = q
+ return nil
+}
+
+// Indicates the network context of a service recording an annotation with two
+// exceptions.
+//
+// When a BinaryAnnotation, and key is CLIENT_ADDR or SERVER_ADDR,
+// the endpoint indicates the source or destination of an RPC. This exception
+// allows zipkin to display network context of uninstrumented services, or
+// clients such as web browsers.
+//
+// Attributes:
+// - Ipv4: IPv4 host address packed into 4 bytes.
+//
+// Ex for the ip 1.2.3.4, it would be (1 << 24) | (2 << 16) | (3 << 8) | 4
+// - Port: IPv4 port
+//
+// Note: this is to be treated as an unsigned integer, so watch for negatives.
+//
+// Conventionally, when the port isn't known, port = 0.
+// - ServiceName: Service name in lowercase, such as "memcache" or "zipkin-web"
+//
+// Conventionally, when the service name isn't known, service_name = "unknown".
+type Endpoint struct {
+ Ipv4 int32 `thrift:"ipv4,1" json:"ipv4"`
+ Port int16 `thrift:"port,2" json:"port"`
+ ServiceName string `thrift:"service_name,3" json:"service_name"`
+}
+
+func NewEndpoint() *Endpoint {
+ return &Endpoint{}
+}
+
+func (p *Endpoint) GetIpv4() int32 {
+ return p.Ipv4
+}
+
+func (p *Endpoint) GetPort() int16 {
+ return p.Port
+}
+
+func (p *Endpoint) GetServiceName() string {
+ return p.ServiceName
+}
+func (p *Endpoint) Read(iprot thrift.TProtocol) error {
+ if _, err := iprot.ReadStructBegin(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read error: ", p), err)
+ }
+
+ for {
+ _, fieldTypeId, fieldId, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T field %d read error: ", p, fieldId), err)
+ }
+ if fieldTypeId == thrift.STOP {
+ break
+ }
+ switch fieldId {
+ case 1:
+ if err := p.readField1(iprot); err != nil {
+ return err
+ }
+ case 2:
+ if err := p.readField2(iprot); err != nil {
+ return err
+ }
+ case 3:
+ if err := p.readField3(iprot); err != nil {
+ return err
+ }
+ default:
+ if err := iprot.Skip(fieldTypeId); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadFieldEnd(); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadStructEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read struct end error: ", p), err)
+ }
+ return nil
+}
+
+func (p *Endpoint) readField1(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadI32(); err != nil {
+ return thrift.PrependError("error reading field 1: ", err)
+ } else {
+ p.Ipv4 = v
+ }
+ return nil
+}
+
+func (p *Endpoint) readField2(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadI16(); err != nil {
+ return thrift.PrependError("error reading field 2: ", err)
+ } else {
+ p.Port = v
+ }
+ return nil
+}
+
+func (p *Endpoint) readField3(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadString(); err != nil {
+ return thrift.PrependError("error reading field 3: ", err)
+ } else {
+ p.ServiceName = v
+ }
+ return nil
+}
+
+func (p *Endpoint) Write(oprot thrift.TProtocol) error {
+ if err := oprot.WriteStructBegin("Endpoint"); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write struct begin error: ", p), err)
+ }
+ if err := p.writeField1(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField2(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField3(oprot); err != nil {
+ return err
+ }
+ if err := oprot.WriteFieldStop(); err != nil {
+ return thrift.PrependError("write field stop error: ", err)
+ }
+ if err := oprot.WriteStructEnd(); err != nil {
+ return thrift.PrependError("write struct stop error: ", err)
+ }
+ return nil
+}
+
+func (p *Endpoint) writeField1(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("ipv4", thrift.I32, 1); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 1:ipv4: ", p), err)
+ }
+ if err := oprot.WriteI32(int32(p.Ipv4)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.ipv4 (1) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 1:ipv4: ", p), err)
+ }
+ return err
+}
+
+func (p *Endpoint) writeField2(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("port", thrift.I16, 2); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 2:port: ", p), err)
+ }
+ if err := oprot.WriteI16(int16(p.Port)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.port (2) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 2:port: ", p), err)
+ }
+ return err
+}
+
+func (p *Endpoint) writeField3(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("service_name", thrift.STRING, 3); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 3:service_name: ", p), err)
+ }
+ if err := oprot.WriteString(string(p.ServiceName)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.service_name (3) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 3:service_name: ", p), err)
+ }
+ return err
+}
+
+func (p *Endpoint) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return fmt.Sprintf("Endpoint(%+v)", *p)
+}
+
+// An annotation is similar to a log statement. It includes a host field which
+// allows these events to be attributed properly, and also aggregatable.
+//
+// Attributes:
+// - Timestamp: Microseconds from epoch.
+//
+// This value should use the most precise value possible. For example,
+// gettimeofday or syncing nanoTime against a tick of currentTimeMillis.
+// - Value
+// - Host: Always the host that recorded the event. By specifying the host you allow
+// rollup of all events (such as client requests to a service) by IP address.
+type Annotation struct {
+ Timestamp int64 `thrift:"timestamp,1" json:"timestamp"`
+ Value string `thrift:"value,2" json:"value"`
+ Host *Endpoint `thrift:"host,3" json:"host,omitempty"`
+}
+
+func NewAnnotation() *Annotation {
+ return &Annotation{}
+}
+
+func (p *Annotation) GetTimestamp() int64 {
+ return p.Timestamp
+}
+
+func (p *Annotation) GetValue() string {
+ return p.Value
+}
+
+var Annotation_Host_DEFAULT *Endpoint
+
+func (p *Annotation) GetHost() *Endpoint {
+ if !p.IsSetHost() {
+ return Annotation_Host_DEFAULT
+ }
+ return p.Host
+}
+func (p *Annotation) IsSetHost() bool {
+ return p.Host != nil
+}
+
+func (p *Annotation) Read(iprot thrift.TProtocol) error {
+ if _, err := iprot.ReadStructBegin(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read error: ", p), err)
+ }
+
+ for {
+ _, fieldTypeId, fieldId, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T field %d read error: ", p, fieldId), err)
+ }
+ if fieldTypeId == thrift.STOP {
+ break
+ }
+ switch fieldId {
+ case 1:
+ if err := p.readField1(iprot); err != nil {
+ return err
+ }
+ case 2:
+ if err := p.readField2(iprot); err != nil {
+ return err
+ }
+ case 3:
+ if err := p.readField3(iprot); err != nil {
+ return err
+ }
+ default:
+ if err := iprot.Skip(fieldTypeId); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadFieldEnd(); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadStructEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read struct end error: ", p), err)
+ }
+ return nil
+}
+
+func (p *Annotation) readField1(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadI64(); err != nil {
+ return thrift.PrependError("error reading field 1: ", err)
+ } else {
+ p.Timestamp = v
+ }
+ return nil
+}
+
+func (p *Annotation) readField2(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadString(); err != nil {
+ return thrift.PrependError("error reading field 2: ", err)
+ } else {
+ p.Value = v
+ }
+ return nil
+}
+
+func (p *Annotation) readField3(iprot thrift.TProtocol) error {
+ p.Host = &Endpoint{}
+ if err := p.Host.Read(iprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error reading struct: ", p.Host), err)
+ }
+ return nil
+}
+
+func (p *Annotation) Write(oprot thrift.TProtocol) error {
+ if err := oprot.WriteStructBegin("Annotation"); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write struct begin error: ", p), err)
+ }
+ if err := p.writeField1(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField2(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField3(oprot); err != nil {
+ return err
+ }
+ if err := oprot.WriteFieldStop(); err != nil {
+ return thrift.PrependError("write field stop error: ", err)
+ }
+ if err := oprot.WriteStructEnd(); err != nil {
+ return thrift.PrependError("write struct stop error: ", err)
+ }
+ return nil
+}
+
+func (p *Annotation) writeField1(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("timestamp", thrift.I64, 1); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 1:timestamp: ", p), err)
+ }
+ if err := oprot.WriteI64(int64(p.Timestamp)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.timestamp (1) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 1:timestamp: ", p), err)
+ }
+ return err
+}
+
+func (p *Annotation) writeField2(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("value", thrift.STRING, 2); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 2:value: ", p), err)
+ }
+ if err := oprot.WriteString(string(p.Value)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.value (2) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 2:value: ", p), err)
+ }
+ return err
+}
+
+func (p *Annotation) writeField3(oprot thrift.TProtocol) (err error) {
+ if p.IsSetHost() {
+ if err := oprot.WriteFieldBegin("host", thrift.STRUCT, 3); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 3:host: ", p), err)
+ }
+ if err := p.Host.Write(oprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error writing struct: ", p.Host), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 3:host: ", p), err)
+ }
+ }
+ return err
+}
+
+func (p *Annotation) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return fmt.Sprintf("Annotation(%+v)", *p)
+}
+
+// Binary annotations are tags applied to a Span to give it context. For
+// example, a binary annotation of "http.uri" could the path to a resource in a
+// RPC call.
+//
+// Binary annotations of type STRING are always queryable, though more a
+// historical implementation detail than a structural concern.
+//
+// Binary annotations can repeat, and vary on the host. Similar to Annotation,
+// the host indicates who logged the event. This allows you to tell the
+// difference between the client and server side of the same key. For example,
+// the key "http.uri" might be different on the client and server side due to
+// rewriting, like "/api/v1/myresource" vs "/myresource. Via the host field,
+// you can see the different points of view, which often help in debugging.
+//
+// Attributes:
+// - Key
+// - Value
+// - AnnotationType
+// - Host: The host that recorded tag, which allows you to differentiate between
+// multiple tags with the same key. There are two exceptions to this.
+//
+// When the key is CLIENT_ADDR or SERVER_ADDR, host indicates the source or
+// destination of an RPC. This exception allows zipkin to display network
+// context of uninstrumented services, or clients such as web browsers.
+type BinaryAnnotation struct {
+ Key string `thrift:"key,1" json:"key"`
+ Value []byte `thrift:"value,2" json:"value"`
+ AnnotationType AnnotationType `thrift:"annotation_type,3" json:"annotation_type"`
+ Host *Endpoint `thrift:"host,4" json:"host,omitempty"`
+}
+
+func NewBinaryAnnotation() *BinaryAnnotation {
+ return &BinaryAnnotation{}
+}
+
+func (p *BinaryAnnotation) GetKey() string {
+ return p.Key
+}
+
+func (p *BinaryAnnotation) GetValue() []byte {
+ return p.Value
+}
+
+func (p *BinaryAnnotation) GetAnnotationType() AnnotationType {
+ return p.AnnotationType
+}
+
+var BinaryAnnotation_Host_DEFAULT *Endpoint
+
+func (p *BinaryAnnotation) GetHost() *Endpoint {
+ if !p.IsSetHost() {
+ return BinaryAnnotation_Host_DEFAULT
+ }
+ return p.Host
+}
+func (p *BinaryAnnotation) IsSetHost() bool {
+ return p.Host != nil
+}
+
+func (p *BinaryAnnotation) Read(iprot thrift.TProtocol) error {
+ if _, err := iprot.ReadStructBegin(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read error: ", p), err)
+ }
+
+ for {
+ _, fieldTypeId, fieldId, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T field %d read error: ", p, fieldId), err)
+ }
+ if fieldTypeId == thrift.STOP {
+ break
+ }
+ switch fieldId {
+ case 1:
+ if err := p.readField1(iprot); err != nil {
+ return err
+ }
+ case 2:
+ if err := p.readField2(iprot); err != nil {
+ return err
+ }
+ case 3:
+ if err := p.readField3(iprot); err != nil {
+ return err
+ }
+ case 4:
+ if err := p.readField4(iprot); err != nil {
+ return err
+ }
+ default:
+ if err := iprot.Skip(fieldTypeId); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadFieldEnd(); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadStructEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read struct end error: ", p), err)
+ }
+ return nil
+}
+
+func (p *BinaryAnnotation) readField1(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadString(); err != nil {
+ return thrift.PrependError("error reading field 1: ", err)
+ } else {
+ p.Key = v
+ }
+ return nil
+}
+
+func (p *BinaryAnnotation) readField2(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadBinary(); err != nil {
+ return thrift.PrependError("error reading field 2: ", err)
+ } else {
+ p.Value = v
+ }
+ return nil
+}
+
+func (p *BinaryAnnotation) readField3(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadI32(); err != nil {
+ return thrift.PrependError("error reading field 3: ", err)
+ } else {
+ temp := AnnotationType(v)
+ p.AnnotationType = temp
+ }
+ return nil
+}
+
+func (p *BinaryAnnotation) readField4(iprot thrift.TProtocol) error {
+ p.Host = &Endpoint{}
+ if err := p.Host.Read(iprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error reading struct: ", p.Host), err)
+ }
+ return nil
+}
+
+func (p *BinaryAnnotation) Write(oprot thrift.TProtocol) error {
+ if err := oprot.WriteStructBegin("BinaryAnnotation"); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write struct begin error: ", p), err)
+ }
+ if err := p.writeField1(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField2(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField3(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField4(oprot); err != nil {
+ return err
+ }
+ if err := oprot.WriteFieldStop(); err != nil {
+ return thrift.PrependError("write field stop error: ", err)
+ }
+ if err := oprot.WriteStructEnd(); err != nil {
+ return thrift.PrependError("write struct stop error: ", err)
+ }
+ return nil
+}
+
+func (p *BinaryAnnotation) writeField1(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("key", thrift.STRING, 1); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 1:key: ", p), err)
+ }
+ if err := oprot.WriteString(string(p.Key)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.key (1) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 1:key: ", p), err)
+ }
+ return err
+}
+
+func (p *BinaryAnnotation) writeField2(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("value", thrift.STRING, 2); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 2:value: ", p), err)
+ }
+ if err := oprot.WriteBinary(p.Value); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.value (2) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 2:value: ", p), err)
+ }
+ return err
+}
+
+func (p *BinaryAnnotation) writeField3(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("annotation_type", thrift.I32, 3); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 3:annotation_type: ", p), err)
+ }
+ if err := oprot.WriteI32(int32(p.AnnotationType)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.annotation_type (3) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 3:annotation_type: ", p), err)
+ }
+ return err
+}
+
+func (p *BinaryAnnotation) writeField4(oprot thrift.TProtocol) (err error) {
+ if p.IsSetHost() {
+ if err := oprot.WriteFieldBegin("host", thrift.STRUCT, 4); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 4:host: ", p), err)
+ }
+ if err := p.Host.Write(oprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error writing struct: ", p.Host), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 4:host: ", p), err)
+ }
+ }
+ return err
+}
+
+func (p *BinaryAnnotation) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return fmt.Sprintf("BinaryAnnotation(%+v)", *p)
+}
+
+// A trace is a series of spans (often RPC calls) which form a latency tree.
+//
+// The root span is where trace_id = id and parent_id = Nil. The root span is
+// usually the longest interval in the trace, starting with a SERVER_RECV
+// annotation and ending with a SERVER_SEND.
+//
+// Attributes:
+// - TraceID
+// - Name: Span name in lowercase, rpc method for example
+//
+// Conventionally, when the span name isn't known, name = "unknown".
+// - ID
+// - ParentID
+// - Annotations
+// - BinaryAnnotations
+// - Debug
+// - Timestamp: Microseconds from epoch of the creation of this span.
+//
+// This value should be set directly by instrumentation, using the most
+// precise value possible. For example, gettimeofday or syncing nanoTime
+// against a tick of currentTimeMillis.
+//
+// For compatibilty with instrumentation that precede this field, collectors
+// or span stores can derive this via Annotation.timestamp.
+// For example, SERVER_RECV.timestamp or CLIENT_SEND.timestamp.
+//
+// This field is optional for compatibility with old data: first-party span
+// stores are expected to support this at time of introduction.
+// - Duration: Measurement of duration in microseconds, used to support queries.
+//
+// This value should be set directly, where possible. Doing so encourages
+// precise measurement decoupled from problems of clocks, such as skew or NTP
+// updates causing time to move backwards.
+//
+// For compatibilty with instrumentation that precede this field, collectors
+// or span stores can derive this by subtracting Annotation.timestamp.
+// For example, SERVER_SEND.timestamp - SERVER_RECV.timestamp.
+//
+// If this field is persisted as unset, zipkin will continue to work, except
+// duration query support will be implementation-specific. Similarly, setting
+// this field non-atomically is implementation-specific.
+//
+// This field is i64 vs i32 to support spans longer than 35 minutes.
+type Span struct {
+ TraceID int64 `thrift:"trace_id,1" json:"trace_id"`
+ // unused field # 2
+ Name string `thrift:"name,3" json:"name"`
+ ID int64 `thrift:"id,4" json:"id"`
+ ParentID *int64 `thrift:"parent_id,5" json:"parent_id,omitempty"`
+ Annotations []*Annotation `thrift:"annotations,6" json:"annotations"`
+ // unused field # 7
+ BinaryAnnotations []*BinaryAnnotation `thrift:"binary_annotations,8" json:"binary_annotations"`
+ Debug bool `thrift:"debug,9" json:"debug,omitempty"`
+ Timestamp *int64 `thrift:"timestamp,10" json:"timestamp,omitempty"`
+ Duration *int64 `thrift:"duration,11" json:"duration,omitempty"`
+}
+
+func NewSpan() *Span {
+ return &Span{}
+}
+
+func (p *Span) GetTraceID() int64 {
+ return p.TraceID
+}
+
+func (p *Span) GetName() string {
+ return p.Name
+}
+
+func (p *Span) GetID() int64 {
+ return p.ID
+}
+
+var Span_ParentID_DEFAULT int64
+
+func (p *Span) GetParentID() int64 {
+ if !p.IsSetParentID() {
+ return Span_ParentID_DEFAULT
+ }
+ return *p.ParentID
+}
+
+func (p *Span) GetAnnotations() []*Annotation {
+ return p.Annotations
+}
+
+func (p *Span) GetBinaryAnnotations() []*BinaryAnnotation {
+ return p.BinaryAnnotations
+}
+
+var Span_Debug_DEFAULT bool = false
+
+func (p *Span) GetDebug() bool {
+ return p.Debug
+}
+
+var Span_Timestamp_DEFAULT int64
+
+func (p *Span) GetTimestamp() int64 {
+ if !p.IsSetTimestamp() {
+ return Span_Timestamp_DEFAULT
+ }
+ return *p.Timestamp
+}
+
+var Span_Duration_DEFAULT int64
+
+func (p *Span) GetDuration() int64 {
+ if !p.IsSetDuration() {
+ return Span_Duration_DEFAULT
+ }
+ return *p.Duration
+}
+func (p *Span) IsSetParentID() bool {
+ return p.ParentID != nil
+}
+
+func (p *Span) IsSetDebug() bool {
+ return p.Debug != Span_Debug_DEFAULT
+}
+
+func (p *Span) IsSetTimestamp() bool {
+ return p.Timestamp != nil
+}
+
+func (p *Span) IsSetDuration() bool {
+ return p.Duration != nil
+}
+
+func (p *Span) Read(iprot thrift.TProtocol) error {
+ if _, err := iprot.ReadStructBegin(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read error: ", p), err)
+ }
+
+ for {
+ _, fieldTypeId, fieldId, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T field %d read error: ", p, fieldId), err)
+ }
+ if fieldTypeId == thrift.STOP {
+ break
+ }
+ switch fieldId {
+ case 1:
+ if err := p.readField1(iprot); err != nil {
+ return err
+ }
+ case 3:
+ if err := p.readField3(iprot); err != nil {
+ return err
+ }
+ case 4:
+ if err := p.readField4(iprot); err != nil {
+ return err
+ }
+ case 5:
+ if err := p.readField5(iprot); err != nil {
+ return err
+ }
+ case 6:
+ if err := p.readField6(iprot); err != nil {
+ return err
+ }
+ case 8:
+ if err := p.readField8(iprot); err != nil {
+ return err
+ }
+ case 9:
+ if err := p.readField9(iprot); err != nil {
+ return err
+ }
+ case 10:
+ if err := p.readField10(iprot); err != nil {
+ return err
+ }
+ case 11:
+ if err := p.readField11(iprot); err != nil {
+ return err
+ }
+ default:
+ if err := iprot.Skip(fieldTypeId); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadFieldEnd(); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadStructEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read struct end error: ", p), err)
+ }
+ return nil
+}
+
+func (p *Span) readField1(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadI64(); err != nil {
+ return thrift.PrependError("error reading field 1: ", err)
+ } else {
+ p.TraceID = v
+ }
+ return nil
+}
+
+func (p *Span) readField3(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadString(); err != nil {
+ return thrift.PrependError("error reading field 3: ", err)
+ } else {
+ p.Name = v
+ }
+ return nil
+}
+
+func (p *Span) readField4(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadI64(); err != nil {
+ return thrift.PrependError("error reading field 4: ", err)
+ } else {
+ p.ID = v
+ }
+ return nil
+}
+
+func (p *Span) readField5(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadI64(); err != nil {
+ return thrift.PrependError("error reading field 5: ", err)
+ } else {
+ p.ParentID = &v
+ }
+ return nil
+}
+
+func (p *Span) readField6(iprot thrift.TProtocol) error {
+ _, size, err := iprot.ReadListBegin()
+ if err != nil {
+ return thrift.PrependError("error reading list begin: ", err)
+ }
+ tSlice := make([]*Annotation, 0, size)
+ p.Annotations = tSlice
+ for i := 0; i < size; i++ {
+ _elem0 := &Annotation{}
+ if err := _elem0.Read(iprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error reading struct: ", _elem0), err)
+ }
+ p.Annotations = append(p.Annotations, _elem0)
+ }
+ if err := iprot.ReadListEnd(); err != nil {
+ return thrift.PrependError("error reading list end: ", err)
+ }
+ return nil
+}
+
+func (p *Span) readField8(iprot thrift.TProtocol) error {
+ _, size, err := iprot.ReadListBegin()
+ if err != nil {
+ return thrift.PrependError("error reading list begin: ", err)
+ }
+ tSlice := make([]*BinaryAnnotation, 0, size)
+ p.BinaryAnnotations = tSlice
+ for i := 0; i < size; i++ {
+ _elem1 := &BinaryAnnotation{}
+ if err := _elem1.Read(iprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error reading struct: ", _elem1), err)
+ }
+ p.BinaryAnnotations = append(p.BinaryAnnotations, _elem1)
+ }
+ if err := iprot.ReadListEnd(); err != nil {
+ return thrift.PrependError("error reading list end: ", err)
+ }
+ return nil
+}
+
+func (p *Span) readField9(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadBool(); err != nil {
+ return thrift.PrependError("error reading field 9: ", err)
+ } else {
+ p.Debug = v
+ }
+ return nil
+}
+
+func (p *Span) readField10(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadI64(); err != nil {
+ return thrift.PrependError("error reading field 10: ", err)
+ } else {
+ p.Timestamp = &v
+ }
+ return nil
+}
+
+func (p *Span) readField11(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadI64(); err != nil {
+ return thrift.PrependError("error reading field 11: ", err)
+ } else {
+ p.Duration = &v
+ }
+ return nil
+}
+
+func (p *Span) Write(oprot thrift.TProtocol) error {
+ if err := oprot.WriteStructBegin("Span"); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write struct begin error: ", p), err)
+ }
+ if err := p.writeField1(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField3(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField4(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField5(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField6(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField8(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField9(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField10(oprot); err != nil {
+ return err
+ }
+ if err := p.writeField11(oprot); err != nil {
+ return err
+ }
+ if err := oprot.WriteFieldStop(); err != nil {
+ return thrift.PrependError("write field stop error: ", err)
+ }
+ if err := oprot.WriteStructEnd(); err != nil {
+ return thrift.PrependError("write struct stop error: ", err)
+ }
+ return nil
+}
+
+func (p *Span) writeField1(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("trace_id", thrift.I64, 1); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 1:trace_id: ", p), err)
+ }
+ if err := oprot.WriteI64(int64(p.TraceID)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.trace_id (1) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 1:trace_id: ", p), err)
+ }
+ return err
+}
+
+func (p *Span) writeField3(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("name", thrift.STRING, 3); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 3:name: ", p), err)
+ }
+ if err := oprot.WriteString(string(p.Name)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.name (3) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 3:name: ", p), err)
+ }
+ return err
+}
+
+func (p *Span) writeField4(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("id", thrift.I64, 4); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 4:id: ", p), err)
+ }
+ if err := oprot.WriteI64(int64(p.ID)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.id (4) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 4:id: ", p), err)
+ }
+ return err
+}
+
+func (p *Span) writeField5(oprot thrift.TProtocol) (err error) {
+ if p.IsSetParentID() {
+ if err := oprot.WriteFieldBegin("parent_id", thrift.I64, 5); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 5:parent_id: ", p), err)
+ }
+ if err := oprot.WriteI64(int64(*p.ParentID)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.parent_id (5) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 5:parent_id: ", p), err)
+ }
+ }
+ return err
+}
+
+func (p *Span) writeField6(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("annotations", thrift.LIST, 6); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 6:annotations: ", p), err)
+ }
+ if err := oprot.WriteListBegin(thrift.STRUCT, len(p.Annotations)); err != nil {
+ return thrift.PrependError("error writing list begin: ", err)
+ }
+ for _, v := range p.Annotations {
+ if err := v.Write(oprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error writing struct: ", v), err)
+ }
+ }
+ if err := oprot.WriteListEnd(); err != nil {
+ return thrift.PrependError("error writing list end: ", err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 6:annotations: ", p), err)
+ }
+ return err
+}
+
+func (p *Span) writeField8(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("binary_annotations", thrift.LIST, 8); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 8:binary_annotations: ", p), err)
+ }
+ if err := oprot.WriteListBegin(thrift.STRUCT, len(p.BinaryAnnotations)); err != nil {
+ return thrift.PrependError("error writing list begin: ", err)
+ }
+ for _, v := range p.BinaryAnnotations {
+ if err := v.Write(oprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error writing struct: ", v), err)
+ }
+ }
+ if err := oprot.WriteListEnd(); err != nil {
+ return thrift.PrependError("error writing list end: ", err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 8:binary_annotations: ", p), err)
+ }
+ return err
+}
+
+func (p *Span) writeField9(oprot thrift.TProtocol) (err error) {
+ if p.IsSetDebug() {
+ if err := oprot.WriteFieldBegin("debug", thrift.BOOL, 9); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 9:debug: ", p), err)
+ }
+ if err := oprot.WriteBool(bool(p.Debug)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.debug (9) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 9:debug: ", p), err)
+ }
+ }
+ return err
+}
+
+func (p *Span) writeField10(oprot thrift.TProtocol) (err error) {
+ if p.IsSetTimestamp() {
+ if err := oprot.WriteFieldBegin("timestamp", thrift.I64, 10); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 10:timestamp: ", p), err)
+ }
+ if err := oprot.WriteI64(int64(*p.Timestamp)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.timestamp (10) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 10:timestamp: ", p), err)
+ }
+ }
+ return err
+}
+
+func (p *Span) writeField11(oprot thrift.TProtocol) (err error) {
+ if p.IsSetDuration() {
+ if err := oprot.WriteFieldBegin("duration", thrift.I64, 11); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 11:duration: ", p), err)
+ }
+ if err := oprot.WriteI64(int64(*p.Duration)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.duration (11) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 11:duration: ", p), err)
+ }
+ }
+ return err
+}
+
+func (p *Span) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return fmt.Sprintf("Span(%+v)", *p)
+}
+
+// Attributes:
+// - Ok
+type Response struct {
+ Ok bool `thrift:"ok,1,required" json:"ok"`
+}
+
+func NewResponse() *Response {
+ return &Response{}
+}
+
+func (p *Response) GetOk() bool {
+ return p.Ok
+}
+func (p *Response) Read(iprot thrift.TProtocol) error {
+ if _, err := iprot.ReadStructBegin(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read error: ", p), err)
+ }
+
+ var issetOk bool = false
+
+ for {
+ _, fieldTypeId, fieldId, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T field %d read error: ", p, fieldId), err)
+ }
+ if fieldTypeId == thrift.STOP {
+ break
+ }
+ switch fieldId {
+ case 1:
+ if err := p.readField1(iprot); err != nil {
+ return err
+ }
+ issetOk = true
+ default:
+ if err := iprot.Skip(fieldTypeId); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadFieldEnd(); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadStructEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read struct end error: ", p), err)
+ }
+ if !issetOk {
+ return thrift.NewTProtocolExceptionWithType(thrift.INVALID_DATA, fmt.Errorf("Required field Ok is not set"))
+ }
+ return nil
+}
+
+func (p *Response) readField1(iprot thrift.TProtocol) error {
+ if v, err := iprot.ReadBool(); err != nil {
+ return thrift.PrependError("error reading field 1: ", err)
+ } else {
+ p.Ok = v
+ }
+ return nil
+}
+
+func (p *Response) Write(oprot thrift.TProtocol) error {
+ if err := oprot.WriteStructBegin("Response"); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write struct begin error: ", p), err)
+ }
+ if err := p.writeField1(oprot); err != nil {
+ return err
+ }
+ if err := oprot.WriteFieldStop(); err != nil {
+ return thrift.PrependError("write field stop error: ", err)
+ }
+ if err := oprot.WriteStructEnd(); err != nil {
+ return thrift.PrependError("write struct stop error: ", err)
+ }
+ return nil
+}
+
+func (p *Response) writeField1(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("ok", thrift.BOOL, 1); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 1:ok: ", p), err)
+ }
+ if err := oprot.WriteBool(bool(p.Ok)); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T.ok (1) field write error: ", p), err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 1:ok: ", p), err)
+ }
+ return err
+}
+
+func (p *Response) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return fmt.Sprintf("Response(%+v)", *p)
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/thrift-gen/zipkincore/zipkincollector.go b/vendor/github.com/uber/jaeger-client-go/thrift-gen/zipkincore/zipkincollector.go
new file mode 100644
index 000000000..417e883d0
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/thrift-gen/zipkincore/zipkincollector.go
@@ -0,0 +1,446 @@
+// Autogenerated by Thrift Compiler (0.9.3)
+// DO NOT EDIT UNLESS YOU ARE SURE THAT YOU KNOW WHAT YOU ARE DOING
+
+package zipkincore
+
+import (
+ "bytes"
+ "fmt"
+ "github.com/uber/jaeger-client-go/thrift"
+)
+
+// (needed to ensure safety because of naive import list construction.)
+var _ = thrift.ZERO
+var _ = fmt.Printf
+var _ = bytes.Equal
+
+type ZipkinCollector interface {
+ // Parameters:
+ // - Spans
+ SubmitZipkinBatch(spans []*Span) (r []*Response, err error)
+}
+
+type ZipkinCollectorClient struct {
+ Transport thrift.TTransport
+ ProtocolFactory thrift.TProtocolFactory
+ InputProtocol thrift.TProtocol
+ OutputProtocol thrift.TProtocol
+ SeqId int32
+}
+
+func NewZipkinCollectorClientFactory(t thrift.TTransport, f thrift.TProtocolFactory) *ZipkinCollectorClient {
+ return &ZipkinCollectorClient{Transport: t,
+ ProtocolFactory: f,
+ InputProtocol: f.GetProtocol(t),
+ OutputProtocol: f.GetProtocol(t),
+ SeqId: 0,
+ }
+}
+
+func NewZipkinCollectorClientProtocol(t thrift.TTransport, iprot thrift.TProtocol, oprot thrift.TProtocol) *ZipkinCollectorClient {
+ return &ZipkinCollectorClient{Transport: t,
+ ProtocolFactory: nil,
+ InputProtocol: iprot,
+ OutputProtocol: oprot,
+ SeqId: 0,
+ }
+}
+
+// Parameters:
+// - Spans
+func (p *ZipkinCollectorClient) SubmitZipkinBatch(spans []*Span) (r []*Response, err error) {
+ if err = p.sendSubmitZipkinBatch(spans); err != nil {
+ return
+ }
+ return p.recvSubmitZipkinBatch()
+}
+
+func (p *ZipkinCollectorClient) sendSubmitZipkinBatch(spans []*Span) (err error) {
+ oprot := p.OutputProtocol
+ if oprot == nil {
+ oprot = p.ProtocolFactory.GetProtocol(p.Transport)
+ p.OutputProtocol = oprot
+ }
+ p.SeqId++
+ if err = oprot.WriteMessageBegin("submitZipkinBatch", thrift.CALL, p.SeqId); err != nil {
+ return
+ }
+ args := ZipkinCollectorSubmitZipkinBatchArgs{
+ Spans: spans,
+ }
+ if err = args.Write(oprot); err != nil {
+ return
+ }
+ if err = oprot.WriteMessageEnd(); err != nil {
+ return
+ }
+ return oprot.Flush()
+}
+
+func (p *ZipkinCollectorClient) recvSubmitZipkinBatch() (value []*Response, err error) {
+ iprot := p.InputProtocol
+ if iprot == nil {
+ iprot = p.ProtocolFactory.GetProtocol(p.Transport)
+ p.InputProtocol = iprot
+ }
+ method, mTypeId, seqId, err := iprot.ReadMessageBegin()
+ if err != nil {
+ return
+ }
+ if method != "submitZipkinBatch" {
+ err = thrift.NewTApplicationException(thrift.WRONG_METHOD_NAME, "submitZipkinBatch failed: wrong method name")
+ return
+ }
+ if p.SeqId != seqId {
+ err = thrift.NewTApplicationException(thrift.BAD_SEQUENCE_ID, "submitZipkinBatch failed: out of sequence response")
+ return
+ }
+ if mTypeId == thrift.EXCEPTION {
+ error2 := thrift.NewTApplicationException(thrift.UNKNOWN_APPLICATION_EXCEPTION, "Unknown Exception")
+ var error3 error
+ error3, err = error2.Read(iprot)
+ if err != nil {
+ return
+ }
+ if err = iprot.ReadMessageEnd(); err != nil {
+ return
+ }
+ err = error3
+ return
+ }
+ if mTypeId != thrift.REPLY {
+ err = thrift.NewTApplicationException(thrift.INVALID_MESSAGE_TYPE_EXCEPTION, "submitZipkinBatch failed: invalid message type")
+ return
+ }
+ result := ZipkinCollectorSubmitZipkinBatchResult{}
+ if err = result.Read(iprot); err != nil {
+ return
+ }
+ if err = iprot.ReadMessageEnd(); err != nil {
+ return
+ }
+ value = result.GetSuccess()
+ return
+}
+
+type ZipkinCollectorProcessor struct {
+ processorMap map[string]thrift.TProcessorFunction
+ handler ZipkinCollector
+}
+
+func (p *ZipkinCollectorProcessor) AddToProcessorMap(key string, processor thrift.TProcessorFunction) {
+ p.processorMap[key] = processor
+}
+
+func (p *ZipkinCollectorProcessor) GetProcessorFunction(key string) (processor thrift.TProcessorFunction, ok bool) {
+ processor, ok = p.processorMap[key]
+ return processor, ok
+}
+
+func (p *ZipkinCollectorProcessor) ProcessorMap() map[string]thrift.TProcessorFunction {
+ return p.processorMap
+}
+
+func NewZipkinCollectorProcessor(handler ZipkinCollector) *ZipkinCollectorProcessor {
+
+ self4 := &ZipkinCollectorProcessor{handler: handler, processorMap: make(map[string]thrift.TProcessorFunction)}
+ self4.processorMap["submitZipkinBatch"] = &zipkinCollectorProcessorSubmitZipkinBatch{handler: handler}
+ return self4
+}
+
+func (p *ZipkinCollectorProcessor) Process(iprot, oprot thrift.TProtocol) (success bool, err thrift.TException) {
+ name, _, seqId, err := iprot.ReadMessageBegin()
+ if err != nil {
+ return false, err
+ }
+ if processor, ok := p.GetProcessorFunction(name); ok {
+ return processor.Process(seqId, iprot, oprot)
+ }
+ iprot.Skip(thrift.STRUCT)
+ iprot.ReadMessageEnd()
+ x5 := thrift.NewTApplicationException(thrift.UNKNOWN_METHOD, "Unknown function "+name)
+ oprot.WriteMessageBegin(name, thrift.EXCEPTION, seqId)
+ x5.Write(oprot)
+ oprot.WriteMessageEnd()
+ oprot.Flush()
+ return false, x5
+
+}
+
+type zipkinCollectorProcessorSubmitZipkinBatch struct {
+ handler ZipkinCollector
+}
+
+func (p *zipkinCollectorProcessorSubmitZipkinBatch) Process(seqId int32, iprot, oprot thrift.TProtocol) (success bool, err thrift.TException) {
+ args := ZipkinCollectorSubmitZipkinBatchArgs{}
+ if err = args.Read(iprot); err != nil {
+ iprot.ReadMessageEnd()
+ x := thrift.NewTApplicationException(thrift.PROTOCOL_ERROR, err.Error())
+ oprot.WriteMessageBegin("submitZipkinBatch", thrift.EXCEPTION, seqId)
+ x.Write(oprot)
+ oprot.WriteMessageEnd()
+ oprot.Flush()
+ return false, err
+ }
+
+ iprot.ReadMessageEnd()
+ result := ZipkinCollectorSubmitZipkinBatchResult{}
+ var retval []*Response
+ var err2 error
+ if retval, err2 = p.handler.SubmitZipkinBatch(args.Spans); err2 != nil {
+ x := thrift.NewTApplicationException(thrift.INTERNAL_ERROR, "Internal error processing submitZipkinBatch: "+err2.Error())
+ oprot.WriteMessageBegin("submitZipkinBatch", thrift.EXCEPTION, seqId)
+ x.Write(oprot)
+ oprot.WriteMessageEnd()
+ oprot.Flush()
+ return true, err2
+ } else {
+ result.Success = retval
+ }
+ if err2 = oprot.WriteMessageBegin("submitZipkinBatch", thrift.REPLY, seqId); err2 != nil {
+ err = err2
+ }
+ if err2 = result.Write(oprot); err == nil && err2 != nil {
+ err = err2
+ }
+ if err2 = oprot.WriteMessageEnd(); err == nil && err2 != nil {
+ err = err2
+ }
+ if err2 = oprot.Flush(); err == nil && err2 != nil {
+ err = err2
+ }
+ if err != nil {
+ return
+ }
+ return true, err
+}
+
+// HELPER FUNCTIONS AND STRUCTURES
+
+// Attributes:
+// - Spans
+type ZipkinCollectorSubmitZipkinBatchArgs struct {
+ Spans []*Span `thrift:"spans,1" json:"spans"`
+}
+
+func NewZipkinCollectorSubmitZipkinBatchArgs() *ZipkinCollectorSubmitZipkinBatchArgs {
+ return &ZipkinCollectorSubmitZipkinBatchArgs{}
+}
+
+func (p *ZipkinCollectorSubmitZipkinBatchArgs) GetSpans() []*Span {
+ return p.Spans
+}
+func (p *ZipkinCollectorSubmitZipkinBatchArgs) Read(iprot thrift.TProtocol) error {
+ if _, err := iprot.ReadStructBegin(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read error: ", p), err)
+ }
+
+ for {
+ _, fieldTypeId, fieldId, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T field %d read error: ", p, fieldId), err)
+ }
+ if fieldTypeId == thrift.STOP {
+ break
+ }
+ switch fieldId {
+ case 1:
+ if err := p.readField1(iprot); err != nil {
+ return err
+ }
+ default:
+ if err := iprot.Skip(fieldTypeId); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadFieldEnd(); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadStructEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read struct end error: ", p), err)
+ }
+ return nil
+}
+
+func (p *ZipkinCollectorSubmitZipkinBatchArgs) readField1(iprot thrift.TProtocol) error {
+ _, size, err := iprot.ReadListBegin()
+ if err != nil {
+ return thrift.PrependError("error reading list begin: ", err)
+ }
+ tSlice := make([]*Span, 0, size)
+ p.Spans = tSlice
+ for i := 0; i < size; i++ {
+ _elem6 := &Span{}
+ if err := _elem6.Read(iprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error reading struct: ", _elem6), err)
+ }
+ p.Spans = append(p.Spans, _elem6)
+ }
+ if err := iprot.ReadListEnd(); err != nil {
+ return thrift.PrependError("error reading list end: ", err)
+ }
+ return nil
+}
+
+func (p *ZipkinCollectorSubmitZipkinBatchArgs) Write(oprot thrift.TProtocol) error {
+ if err := oprot.WriteStructBegin("submitZipkinBatch_args"); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write struct begin error: ", p), err)
+ }
+ if err := p.writeField1(oprot); err != nil {
+ return err
+ }
+ if err := oprot.WriteFieldStop(); err != nil {
+ return thrift.PrependError("write field stop error: ", err)
+ }
+ if err := oprot.WriteStructEnd(); err != nil {
+ return thrift.PrependError("write struct stop error: ", err)
+ }
+ return nil
+}
+
+func (p *ZipkinCollectorSubmitZipkinBatchArgs) writeField1(oprot thrift.TProtocol) (err error) {
+ if err := oprot.WriteFieldBegin("spans", thrift.LIST, 1); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 1:spans: ", p), err)
+ }
+ if err := oprot.WriteListBegin(thrift.STRUCT, len(p.Spans)); err != nil {
+ return thrift.PrependError("error writing list begin: ", err)
+ }
+ for _, v := range p.Spans {
+ if err := v.Write(oprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error writing struct: ", v), err)
+ }
+ }
+ if err := oprot.WriteListEnd(); err != nil {
+ return thrift.PrependError("error writing list end: ", err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 1:spans: ", p), err)
+ }
+ return err
+}
+
+func (p *ZipkinCollectorSubmitZipkinBatchArgs) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return fmt.Sprintf("ZipkinCollectorSubmitZipkinBatchArgs(%+v)", *p)
+}
+
+// Attributes:
+// - Success
+type ZipkinCollectorSubmitZipkinBatchResult struct {
+ Success []*Response `thrift:"success,0" json:"success,omitempty"`
+}
+
+func NewZipkinCollectorSubmitZipkinBatchResult() *ZipkinCollectorSubmitZipkinBatchResult {
+ return &ZipkinCollectorSubmitZipkinBatchResult{}
+}
+
+var ZipkinCollectorSubmitZipkinBatchResult_Success_DEFAULT []*Response
+
+func (p *ZipkinCollectorSubmitZipkinBatchResult) GetSuccess() []*Response {
+ return p.Success
+}
+func (p *ZipkinCollectorSubmitZipkinBatchResult) IsSetSuccess() bool {
+ return p.Success != nil
+}
+
+func (p *ZipkinCollectorSubmitZipkinBatchResult) Read(iprot thrift.TProtocol) error {
+ if _, err := iprot.ReadStructBegin(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read error: ", p), err)
+ }
+
+ for {
+ _, fieldTypeId, fieldId, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T field %d read error: ", p, fieldId), err)
+ }
+ if fieldTypeId == thrift.STOP {
+ break
+ }
+ switch fieldId {
+ case 0:
+ if err := p.readField0(iprot); err != nil {
+ return err
+ }
+ default:
+ if err := iprot.Skip(fieldTypeId); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadFieldEnd(); err != nil {
+ return err
+ }
+ }
+ if err := iprot.ReadStructEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T read struct end error: ", p), err)
+ }
+ return nil
+}
+
+func (p *ZipkinCollectorSubmitZipkinBatchResult) readField0(iprot thrift.TProtocol) error {
+ _, size, err := iprot.ReadListBegin()
+ if err != nil {
+ return thrift.PrependError("error reading list begin: ", err)
+ }
+ tSlice := make([]*Response, 0, size)
+ p.Success = tSlice
+ for i := 0; i < size; i++ {
+ _elem7 := &Response{}
+ if err := _elem7.Read(iprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error reading struct: ", _elem7), err)
+ }
+ p.Success = append(p.Success, _elem7)
+ }
+ if err := iprot.ReadListEnd(); err != nil {
+ return thrift.PrependError("error reading list end: ", err)
+ }
+ return nil
+}
+
+func (p *ZipkinCollectorSubmitZipkinBatchResult) Write(oprot thrift.TProtocol) error {
+ if err := oprot.WriteStructBegin("submitZipkinBatch_result"); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write struct begin error: ", p), err)
+ }
+ if err := p.writeField0(oprot); err != nil {
+ return err
+ }
+ if err := oprot.WriteFieldStop(); err != nil {
+ return thrift.PrependError("write field stop error: ", err)
+ }
+ if err := oprot.WriteStructEnd(); err != nil {
+ return thrift.PrependError("write struct stop error: ", err)
+ }
+ return nil
+}
+
+func (p *ZipkinCollectorSubmitZipkinBatchResult) writeField0(oprot thrift.TProtocol) (err error) {
+ if p.IsSetSuccess() {
+ if err := oprot.WriteFieldBegin("success", thrift.LIST, 0); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field begin error 0:success: ", p), err)
+ }
+ if err := oprot.WriteListBegin(thrift.STRUCT, len(p.Success)); err != nil {
+ return thrift.PrependError("error writing list begin: ", err)
+ }
+ for _, v := range p.Success {
+ if err := v.Write(oprot); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T error writing struct: ", v), err)
+ }
+ }
+ if err := oprot.WriteListEnd(); err != nil {
+ return thrift.PrependError("error writing list end: ", err)
+ }
+ if err := oprot.WriteFieldEnd(); err != nil {
+ return thrift.PrependError(fmt.Sprintf("%T write field end error 0:success: ", p), err)
+ }
+ }
+ return err
+}
+
+func (p *ZipkinCollectorSubmitZipkinBatchResult) String() string {
+ if p == nil {
+ return "<nil>"
+ }
+ return fmt.Sprintf("ZipkinCollectorSubmitZipkinBatchResult(%+v)", *p)
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/thrift/README.md b/vendor/github.com/uber/jaeger-client-go/thrift/README.md
new file mode 100644
index 000000000..1d8e642e0
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/thrift/README.md
@@ -0,0 +1,7 @@
+# Apache Thrift
+
+This is a partial copy of Apache Thrift v0.10 (https://github.com/apache/thrift/commit/b2a4d4ae21c789b689dd162deb819665567f481c).
+
+It is vendored code to avoid compatibility issues introduced in Thrift v0.11.
+
+See https://github.com/jaegertracing/jaeger-client-go/pull/303.
diff --git a/vendor/github.com/uber/jaeger-client-go/thrift/application_exception.go b/vendor/github.com/uber/jaeger-client-go/thrift/application_exception.go
new file mode 100644
index 000000000..6655cc5a9
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/thrift/application_exception.go
@@ -0,0 +1,142 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+const (
+ UNKNOWN_APPLICATION_EXCEPTION = 0
+ UNKNOWN_METHOD = 1
+ INVALID_MESSAGE_TYPE_EXCEPTION = 2
+ WRONG_METHOD_NAME = 3
+ BAD_SEQUENCE_ID = 4
+ MISSING_RESULT = 5
+ INTERNAL_ERROR = 6
+ PROTOCOL_ERROR = 7
+)
+
+// Application level Thrift exception
+type TApplicationException interface {
+ TException
+ TypeId() int32
+ Read(iprot TProtocol) (TApplicationException, error)
+ Write(oprot TProtocol) error
+}
+
+type tApplicationException struct {
+ message string
+ type_ int32
+}
+
+func (e tApplicationException) Error() string {
+ return e.message
+}
+
+func NewTApplicationException(type_ int32, message string) TApplicationException {
+ return &tApplicationException{message, type_}
+}
+
+func (p *tApplicationException) TypeId() int32 {
+ return p.type_
+}
+
+func (p *tApplicationException) Read(iprot TProtocol) (TApplicationException, error) {
+ _, err := iprot.ReadStructBegin()
+ if err != nil {
+ return nil, err
+ }
+
+ message := ""
+ type_ := int32(UNKNOWN_APPLICATION_EXCEPTION)
+
+ for {
+ _, ttype, id, err := iprot.ReadFieldBegin()
+ if err != nil {
+ return nil, err
+ }
+ if ttype == STOP {
+ break
+ }
+ switch id {
+ case 1:
+ if ttype == STRING {
+ if message, err = iprot.ReadString(); err != nil {
+ return nil, err
+ }
+ } else {
+ if err = SkipDefaultDepth(iprot, ttype); err != nil {
+ return nil, err
+ }
+ }
+ case 2:
+ if ttype == I32 {
+ if type_, err = iprot.ReadI32(); err != nil {
+ return nil, err
+ }
+ } else {
+ if err = SkipDefaultDepth(iprot, ttype); err != nil {
+ return nil, err
+ }
+ }
+ default:
+ if err = SkipDefaultDepth(iprot, ttype); err != nil {
+ return nil, err
+ }
+ }
+ if err = iprot.ReadFieldEnd(); err != nil {
+ return nil, err
+ }
+ }
+ return NewTApplicationException(type_, message), iprot.ReadStructEnd()
+}
+
+func (p *tApplicationException) Write(oprot TProtocol) (err error) {
+ err = oprot.WriteStructBegin("TApplicationException")
+ if len(p.Error()) > 0 {
+ err = oprot.WriteFieldBegin("message", STRING, 1)
+ if err != nil {
+ return
+ }
+ err = oprot.WriteString(p.Error())
+ if err != nil {
+ return
+ }
+ err = oprot.WriteFieldEnd()
+ if err != nil {
+ return
+ }
+ }
+ err = oprot.WriteFieldBegin("type", I32, 2)
+ if err != nil {
+ return
+ }
+ err = oprot.WriteI32(p.type_)
+ if err != nil {
+ return
+ }
+ err = oprot.WriteFieldEnd()
+ if err != nil {
+ return
+ }
+ err = oprot.WriteFieldStop()
+ if err != nil {
+ return
+ }
+ err = oprot.WriteStructEnd()
+ return
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/thrift/binary_protocol.go b/vendor/github.com/uber/jaeger-client-go/thrift/binary_protocol.go
new file mode 100644
index 000000000..690d34111
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/thrift/binary_protocol.go
@@ -0,0 +1,514 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+import (
+ "bytes"
+ "encoding/binary"
+ "errors"
+ "fmt"
+ "io"
+ "math"
+)
+
+type TBinaryProtocol struct {
+ trans TRichTransport
+ origTransport TTransport
+ reader io.Reader
+ writer io.Writer
+ strictRead bool
+ strictWrite bool
+ buffer [64]byte
+}
+
+type TBinaryProtocolFactory struct {
+ strictRead bool
+ strictWrite bool
+}
+
+func NewTBinaryProtocolTransport(t TTransport) *TBinaryProtocol {
+ return NewTBinaryProtocol(t, false, true)
+}
+
+func NewTBinaryProtocol(t TTransport, strictRead, strictWrite bool) *TBinaryProtocol {
+ p := &TBinaryProtocol{origTransport: t, strictRead: strictRead, strictWrite: strictWrite}
+ if et, ok := t.(TRichTransport); ok {
+ p.trans = et
+ } else {
+ p.trans = NewTRichTransport(t)
+ }
+ p.reader = p.trans
+ p.writer = p.trans
+ return p
+}
+
+func NewTBinaryProtocolFactoryDefault() *TBinaryProtocolFactory {
+ return NewTBinaryProtocolFactory(false, true)
+}
+
+func NewTBinaryProtocolFactory(strictRead, strictWrite bool) *TBinaryProtocolFactory {
+ return &TBinaryProtocolFactory{strictRead: strictRead, strictWrite: strictWrite}
+}
+
+func (p *TBinaryProtocolFactory) GetProtocol(t TTransport) TProtocol {
+ return NewTBinaryProtocol(t, p.strictRead, p.strictWrite)
+}
+
+/**
+ * Writing Methods
+ */
+
+func (p *TBinaryProtocol) WriteMessageBegin(name string, typeId TMessageType, seqId int32) error {
+ if p.strictWrite {
+ version := uint32(VERSION_1) | uint32(typeId)
+ e := p.WriteI32(int32(version))
+ if e != nil {
+ return e
+ }
+ e = p.WriteString(name)
+ if e != nil {
+ return e
+ }
+ e = p.WriteI32(seqId)
+ return e
+ } else {
+ e := p.WriteString(name)
+ if e != nil {
+ return e
+ }
+ e = p.WriteByte(int8(typeId))
+ if e != nil {
+ return e
+ }
+ e = p.WriteI32(seqId)
+ return e
+ }
+ return nil
+}
+
+func (p *TBinaryProtocol) WriteMessageEnd() error {
+ return nil
+}
+
+func (p *TBinaryProtocol) WriteStructBegin(name string) error {
+ return nil
+}
+
+func (p *TBinaryProtocol) WriteStructEnd() error {
+ return nil
+}
+
+func (p *TBinaryProtocol) WriteFieldBegin(name string, typeId TType, id int16) error {
+ e := p.WriteByte(int8(typeId))
+ if e != nil {
+ return e
+ }
+ e = p.WriteI16(id)
+ return e
+}
+
+func (p *TBinaryProtocol) WriteFieldEnd() error {
+ return nil
+}
+
+func (p *TBinaryProtocol) WriteFieldStop() error {
+ e := p.WriteByte(STOP)
+ return e
+}
+
+func (p *TBinaryProtocol) WriteMapBegin(keyType TType, valueType TType, size int) error {
+ e := p.WriteByte(int8(keyType))
+ if e != nil {
+ return e
+ }
+ e = p.WriteByte(int8(valueType))
+ if e != nil {
+ return e
+ }
+ e = p.WriteI32(int32(size))
+ return e
+}
+
+func (p *TBinaryProtocol) WriteMapEnd() error {
+ return nil
+}
+
+func (p *TBinaryProtocol) WriteListBegin(elemType TType, size int) error {
+ e := p.WriteByte(int8(elemType))
+ if e != nil {
+ return e
+ }
+ e = p.WriteI32(int32(size))
+ return e
+}
+
+func (p *TBinaryProtocol) WriteListEnd() error {
+ return nil
+}
+
+func (p *TBinaryProtocol) WriteSetBegin(elemType TType, size int) error {
+ e := p.WriteByte(int8(elemType))
+ if e != nil {
+ return e
+ }
+ e = p.WriteI32(int32(size))
+ return e
+}
+
+func (p *TBinaryProtocol) WriteSetEnd() error {
+ return nil
+}
+
+func (p *TBinaryProtocol) WriteBool(value bool) error {
+ if value {
+ return p.WriteByte(1)
+ }
+ return p.WriteByte(0)
+}
+
+func (p *TBinaryProtocol) WriteByte(value int8) error {
+ e := p.trans.WriteByte(byte(value))
+ return NewTProtocolException(e)
+}
+
+func (p *TBinaryProtocol) WriteI16(value int16) error {
+ v := p.buffer[0:2]
+ binary.BigEndian.PutUint16(v, uint16(value))
+ _, e := p.writer.Write(v)
+ return NewTProtocolException(e)
+}
+
+func (p *TBinaryProtocol) WriteI32(value int32) error {
+ v := p.buffer[0:4]
+ binary.BigEndian.PutUint32(v, uint32(value))
+ _, e := p.writer.Write(v)
+ return NewTProtocolException(e)
+}
+
+func (p *TBinaryProtocol) WriteI64(value int64) error {
+ v := p.buffer[0:8]
+ binary.BigEndian.PutUint64(v, uint64(value))
+ _, err := p.writer.Write(v)
+ return NewTProtocolException(err)
+}
+
+func (p *TBinaryProtocol) WriteDouble(value float64) error {
+ return p.WriteI64(int64(math.Float64bits(value)))
+}
+
+func (p *TBinaryProtocol) WriteString(value string) error {
+ e := p.WriteI32(int32(len(value)))
+ if e != nil {
+ return e
+ }
+ _, err := p.trans.WriteString(value)
+ return NewTProtocolException(err)
+}
+
+func (p *TBinaryProtocol) WriteBinary(value []byte) error {
+ e := p.WriteI32(int32(len(value)))
+ if e != nil {
+ return e
+ }
+ _, err := p.writer.Write(value)
+ return NewTProtocolException(err)
+}
+
+/**
+ * Reading methods
+ */
+
+func (p *TBinaryProtocol) ReadMessageBegin() (name string, typeId TMessageType, seqId int32, err error) {
+ size, e := p.ReadI32()
+ if e != nil {
+ return "", typeId, 0, NewTProtocolException(e)
+ }
+ if size < 0 {
+ typeId = TMessageType(size & 0x0ff)
+ version := int64(int64(size) & VERSION_MASK)
+ if version != VERSION_1 {
+ return name, typeId, seqId, NewTProtocolExceptionWithType(BAD_VERSION, fmt.Errorf("Bad version in ReadMessageBegin"))
+ }
+ name, e = p.ReadString()
+ if e != nil {
+ return name, typeId, seqId, NewTProtocolException(e)
+ }
+ seqId, e = p.ReadI32()
+ if e != nil {
+ return name, typeId, seqId, NewTProtocolException(e)
+ }
+ return name, typeId, seqId, nil
+ }
+ if p.strictRead {
+ return name, typeId, seqId, NewTProtocolExceptionWithType(BAD_VERSION, fmt.Errorf("Missing version in ReadMessageBegin"))
+ }
+ name, e2 := p.readStringBody(size)
+ if e2 != nil {
+ return name, typeId, seqId, e2
+ }
+ b, e3 := p.ReadByte()
+ if e3 != nil {
+ return name, typeId, seqId, e3
+ }
+ typeId = TMessageType(b)
+ seqId, e4 := p.ReadI32()
+ if e4 != nil {
+ return name, typeId, seqId, e4
+ }
+ return name, typeId, seqId, nil
+}
+
+func (p *TBinaryProtocol) ReadMessageEnd() error {
+ return nil
+}
+
+func (p *TBinaryProtocol) ReadStructBegin() (name string, err error) {
+ return
+}
+
+func (p *TBinaryProtocol) ReadStructEnd() error {
+ return nil
+}
+
+func (p *TBinaryProtocol) ReadFieldBegin() (name string, typeId TType, seqId int16, err error) {
+ t, err := p.ReadByte()
+ typeId = TType(t)
+ if err != nil {
+ return name, typeId, seqId, err
+ }
+ if t != STOP {
+ seqId, err = p.ReadI16()
+ }
+ return name, typeId, seqId, err
+}
+
+func (p *TBinaryProtocol) ReadFieldEnd() error {
+ return nil
+}
+
+var invalidDataLength = NewTProtocolExceptionWithType(INVALID_DATA, errors.New("Invalid data length"))
+
+func (p *TBinaryProtocol) ReadMapBegin() (kType, vType TType, size int, err error) {
+ k, e := p.ReadByte()
+ if e != nil {
+ err = NewTProtocolException(e)
+ return
+ }
+ kType = TType(k)
+ v, e := p.ReadByte()
+ if e != nil {
+ err = NewTProtocolException(e)
+ return
+ }
+ vType = TType(v)
+ size32, e := p.ReadI32()
+ if e != nil {
+ err = NewTProtocolException(e)
+ return
+ }
+ if size32 < 0 {
+ err = invalidDataLength
+ return
+ }
+ size = int(size32)
+ return kType, vType, size, nil
+}
+
+func (p *TBinaryProtocol) ReadMapEnd() error {
+ return nil
+}
+
+func (p *TBinaryProtocol) ReadListBegin() (elemType TType, size int, err error) {
+ b, e := p.ReadByte()
+ if e != nil {
+ err = NewTProtocolException(e)
+ return
+ }
+ elemType = TType(b)
+ size32, e := p.ReadI32()
+ if e != nil {
+ err = NewTProtocolException(e)
+ return
+ }
+ if size32 < 0 {
+ err = invalidDataLength
+ return
+ }
+ size = int(size32)
+
+ return
+}
+
+func (p *TBinaryProtocol) ReadListEnd() error {
+ return nil
+}
+
+func (p *TBinaryProtocol) ReadSetBegin() (elemType TType, size int, err error) {
+ b, e := p.ReadByte()
+ if e != nil {
+ err = NewTProtocolException(e)
+ return
+ }
+ elemType = TType(b)
+ size32, e := p.ReadI32()
+ if e != nil {
+ err = NewTProtocolException(e)
+ return
+ }
+ if size32 < 0 {
+ err = invalidDataLength
+ return
+ }
+ size = int(size32)
+ return elemType, size, nil
+}
+
+func (p *TBinaryProtocol) ReadSetEnd() error {
+ return nil
+}
+
+func (p *TBinaryProtocol) ReadBool() (bool, error) {
+ b, e := p.ReadByte()
+ v := true
+ if b != 1 {
+ v = false
+ }
+ return v, e
+}
+
+func (p *TBinaryProtocol) ReadByte() (int8, error) {
+ v, err := p.trans.ReadByte()
+ return int8(v), err
+}
+
+func (p *TBinaryProtocol) ReadI16() (value int16, err error) {
+ buf := p.buffer[0:2]
+ err = p.readAll(buf)
+ value = int16(binary.BigEndian.Uint16(buf))
+ return value, err
+}
+
+func (p *TBinaryProtocol) ReadI32() (value int32, err error) {
+ buf := p.buffer[0:4]
+ err = p.readAll(buf)
+ value = int32(binary.BigEndian.Uint32(buf))
+ return value, err
+}
+
+func (p *TBinaryProtocol) ReadI64() (value int64, err error) {
+ buf := p.buffer[0:8]
+ err = p.readAll(buf)
+ value = int64(binary.BigEndian.Uint64(buf))
+ return value, err
+}
+
+func (p *TBinaryProtocol) ReadDouble() (value float64, err error) {
+ buf := p.buffer[0:8]
+ err = p.readAll(buf)
+ value = math.Float64frombits(binary.BigEndian.Uint64(buf))
+ return value, err
+}
+
+func (p *TBinaryProtocol) ReadString() (value string, err error) {
+ size, e := p.ReadI32()
+ if e != nil {
+ return "", e
+ }
+ if size < 0 {
+ err = invalidDataLength
+ return
+ }
+
+ return p.readStringBody(size)
+}
+
+func (p *TBinaryProtocol) ReadBinary() ([]byte, error) {
+ size, e := p.ReadI32()
+ if e != nil {
+ return nil, e
+ }
+ if size < 0 {
+ return nil, invalidDataLength
+ }
+ if uint64(size) > p.trans.RemainingBytes() {
+ return nil, invalidDataLength
+ }
+
+ isize := int(size)
+ buf := make([]byte, isize)
+ _, err := io.ReadFull(p.trans, buf)
+ return buf, NewTProtocolException(err)
+}
+
+func (p *TBinaryProtocol) Flush() (err error) {
+ return NewTProtocolException(p.trans.Flush())
+}
+
+func (p *TBinaryProtocol) Skip(fieldType TType) (err error) {
+ return SkipDefaultDepth(p, fieldType)
+}
+
+func (p *TBinaryProtocol) Transport() TTransport {
+ return p.origTransport
+}
+
+func (p *TBinaryProtocol) readAll(buf []byte) error {
+ _, err := io.ReadFull(p.reader, buf)
+ return NewTProtocolException(err)
+}
+
+const readLimit = 32768
+
+func (p *TBinaryProtocol) readStringBody(size int32) (value string, err error) {
+ if size < 0 {
+ return "", nil
+ }
+ if uint64(size) > p.trans.RemainingBytes() {
+ return "", invalidDataLength
+ }
+
+ var (
+ buf bytes.Buffer
+ e error
+ b []byte
+ )
+
+ switch {
+ case int(size) <= len(p.buffer):
+ b = p.buffer[:size] // avoids allocation for small reads
+ case int(size) < readLimit:
+ b = make([]byte, size)
+ default:
+ b = make([]byte, readLimit)
+ }
+
+ for size > 0 {
+ _, e = io.ReadFull(p.trans, b)
+ buf.Write(b)
+ if e != nil {
+ break
+ }
+ size -= readLimit
+ if size < readLimit && size > 0 {
+ b = b[:size]
+ }
+ }
+ return buf.String(), NewTProtocolException(e)
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/thrift/compact_protocol.go b/vendor/github.com/uber/jaeger-client-go/thrift/compact_protocol.go
new file mode 100644
index 000000000..b9299f2fa
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/thrift/compact_protocol.go
@@ -0,0 +1,815 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+import (
+ "encoding/binary"
+ "fmt"
+ "io"
+ "math"
+)
+
+const (
+ COMPACT_PROTOCOL_ID = 0x082
+ COMPACT_VERSION = 1
+ COMPACT_VERSION_MASK = 0x1f
+ COMPACT_TYPE_MASK = 0x0E0
+ COMPACT_TYPE_BITS = 0x07
+ COMPACT_TYPE_SHIFT_AMOUNT = 5
+)
+
+type tCompactType byte
+
+const (
+ COMPACT_BOOLEAN_TRUE = 0x01
+ COMPACT_BOOLEAN_FALSE = 0x02
+ COMPACT_BYTE = 0x03
+ COMPACT_I16 = 0x04
+ COMPACT_I32 = 0x05
+ COMPACT_I64 = 0x06
+ COMPACT_DOUBLE = 0x07
+ COMPACT_BINARY = 0x08
+ COMPACT_LIST = 0x09
+ COMPACT_SET = 0x0A
+ COMPACT_MAP = 0x0B
+ COMPACT_STRUCT = 0x0C
+)
+
+var (
+ ttypeToCompactType map[TType]tCompactType
+)
+
+func init() {
+ ttypeToCompactType = map[TType]tCompactType{
+ STOP: STOP,
+ BOOL: COMPACT_BOOLEAN_TRUE,
+ BYTE: COMPACT_BYTE,
+ I16: COMPACT_I16,
+ I32: COMPACT_I32,
+ I64: COMPACT_I64,
+ DOUBLE: COMPACT_DOUBLE,
+ STRING: COMPACT_BINARY,
+ LIST: COMPACT_LIST,
+ SET: COMPACT_SET,
+ MAP: COMPACT_MAP,
+ STRUCT: COMPACT_STRUCT,
+ }
+}
+
+type TCompactProtocolFactory struct{}
+
+func NewTCompactProtocolFactory() *TCompactProtocolFactory {
+ return &TCompactProtocolFactory{}
+}
+
+func (p *TCompactProtocolFactory) GetProtocol(trans TTransport) TProtocol {
+ return NewTCompactProtocol(trans)
+}
+
+type TCompactProtocol struct {
+ trans TRichTransport
+ origTransport TTransport
+
+ // Used to keep track of the last field for the current and previous structs,
+ // so we can do the delta stuff.
+ lastField []int
+ lastFieldId int
+
+ // If we encounter a boolean field begin, save the TField here so it can
+ // have the value incorporated.
+ booleanFieldName string
+ booleanFieldId int16
+ booleanFieldPending bool
+
+ // If we read a field header, and it's a boolean field, save the boolean
+ // value here so that readBool can use it.
+ boolValue bool
+ boolValueIsNotNull bool
+ buffer [64]byte
+}
+
+// Create a TCompactProtocol given a TTransport
+func NewTCompactProtocol(trans TTransport) *TCompactProtocol {
+ p := &TCompactProtocol{origTransport: trans, lastField: []int{}}
+ if et, ok := trans.(TRichTransport); ok {
+ p.trans = et
+ } else {
+ p.trans = NewTRichTransport(trans)
+ }
+
+ return p
+
+}
+
+//
+// Public Writing methods.
+//
+
+// Write a message header to the wire. Compact Protocol messages contain the
+// protocol version so we can migrate forwards in the future if need be.
+func (p *TCompactProtocol) WriteMessageBegin(name string, typeId TMessageType, seqid int32) error {
+ err := p.writeByteDirect(COMPACT_PROTOCOL_ID)
+ if err != nil {
+ return NewTProtocolException(err)
+ }
+ err = p.writeByteDirect((COMPACT_VERSION & COMPACT_VERSION_MASK) | ((byte(typeId) << COMPACT_TYPE_SHIFT_AMOUNT) & COMPACT_TYPE_MASK))
+ if err != nil {
+ return NewTProtocolException(err)
+ }
+ _, err = p.writeVarint32(seqid)
+ if err != nil {
+ return NewTProtocolException(err)
+ }
+ e := p.WriteString(name)
+ return e
+
+}
+
+func (p *TCompactProtocol) WriteMessageEnd() error { return nil }
+
+// Write a struct begin. This doesn't actually put anything on the wire. We
+// use it as an opportunity to put special placeholder markers on the field
+// stack so we can get the field id deltas correct.
+func (p *TCompactProtocol) WriteStructBegin(name string) error {
+ p.lastField = append(p.lastField, p.lastFieldId)
+ p.lastFieldId = 0
+ return nil
+}
+
+// Write a struct end. This doesn't actually put anything on the wire. We use
+// this as an opportunity to pop the last field from the current struct off
+// of the field stack.
+func (p *TCompactProtocol) WriteStructEnd() error {
+ p.lastFieldId = p.lastField[len(p.lastField)-1]
+ p.lastField = p.lastField[:len(p.lastField)-1]
+ return nil
+}
+
+func (p *TCompactProtocol) WriteFieldBegin(name string, typeId TType, id int16) error {
+ if typeId == BOOL {
+ // we want to possibly include the value, so we'll wait.
+ p.booleanFieldName, p.booleanFieldId, p.booleanFieldPending = name, id, true
+ return nil
+ }
+ _, err := p.writeFieldBeginInternal(name, typeId, id, 0xFF)
+ return NewTProtocolException(err)
+}
+
+// The workhorse of writeFieldBegin. It has the option of doing a
+// 'type override' of the type header. This is used specifically in the
+// boolean field case.
+func (p *TCompactProtocol) writeFieldBeginInternal(name string, typeId TType, id int16, typeOverride byte) (int, error) {
+ // short lastField = lastField_.pop();
+
+ // if there's a type override, use that.
+ var typeToWrite byte
+ if typeOverride == 0xFF {
+ typeToWrite = byte(p.getCompactType(typeId))
+ } else {
+ typeToWrite = typeOverride
+ }
+ // check if we can use delta encoding for the field id
+ fieldId := int(id)
+ written := 0
+ if fieldId > p.lastFieldId && fieldId-p.lastFieldId <= 15 {
+ // write them together
+ err := p.writeByteDirect(byte((fieldId-p.lastFieldId)<<4) | typeToWrite)
+ if err != nil {
+ return 0, err
+ }
+ } else {
+ // write them separate
+ err := p.writeByteDirect(typeToWrite)
+ if err != nil {
+ return 0, err
+ }
+ err = p.WriteI16(id)
+ written = 1 + 2
+ if err != nil {
+ return 0, err
+ }
+ }
+
+ p.lastFieldId = fieldId
+ // p.lastField.Push(field.id);
+ return written, nil
+}
+
+func (p *TCompactProtocol) WriteFieldEnd() error { return nil }
+
+func (p *TCompactProtocol) WriteFieldStop() error {
+ err := p.writeByteDirect(STOP)
+ return NewTProtocolException(err)
+}
+
+func (p *TCompactProtocol) WriteMapBegin(keyType TType, valueType TType, size int) error {
+ if size == 0 {
+ err := p.writeByteDirect(0)
+ return NewTProtocolException(err)
+ }
+ _, err := p.writeVarint32(int32(size))
+ if err != nil {
+ return NewTProtocolException(err)
+ }
+ err = p.writeByteDirect(byte(p.getCompactType(keyType))<<4 | byte(p.getCompactType(valueType)))
+ return NewTProtocolException(err)
+}
+
+func (p *TCompactProtocol) WriteMapEnd() error { return nil }
+
+// Write a list header.
+func (p *TCompactProtocol) WriteListBegin(elemType TType, size int) error {
+ _, err := p.writeCollectionBegin(elemType, size)
+ return NewTProtocolException(err)
+}
+
+func (p *TCompactProtocol) WriteListEnd() error { return nil }
+
+// Write a set header.
+func (p *TCompactProtocol) WriteSetBegin(elemType TType, size int) error {
+ _, err := p.writeCollectionBegin(elemType, size)
+ return NewTProtocolException(err)
+}
+
+func (p *TCompactProtocol) WriteSetEnd() error { return nil }
+
+func (p *TCompactProtocol) WriteBool(value bool) error {
+ v := byte(COMPACT_BOOLEAN_FALSE)
+ if value {
+ v = byte(COMPACT_BOOLEAN_TRUE)
+ }
+ if p.booleanFieldPending {
+ // we haven't written the field header yet
+ _, err := p.writeFieldBeginInternal(p.booleanFieldName, BOOL, p.booleanFieldId, v)
+ p.booleanFieldPending = false
+ return NewTProtocolException(err)
+ }
+ // we're not part of a field, so just write the value.
+ err := p.writeByteDirect(v)
+ return NewTProtocolException(err)
+}
+
+// Write a byte. Nothing to see here!
+func (p *TCompactProtocol) WriteByte(value int8) error {
+ err := p.writeByteDirect(byte(value))
+ return NewTProtocolException(err)
+}
+
+// Write an I16 as a zigzag varint.
+func (p *TCompactProtocol) WriteI16(value int16) error {
+ _, err := p.writeVarint32(p.int32ToZigzag(int32(value)))
+ return NewTProtocolException(err)
+}
+
+// Write an i32 as a zigzag varint.
+func (p *TCompactProtocol) WriteI32(value int32) error {
+ _, err := p.writeVarint32(p.int32ToZigzag(value))
+ return NewTProtocolException(err)
+}
+
+// Write an i64 as a zigzag varint.
+func (p *TCompactProtocol) WriteI64(value int64) error {
+ _, err := p.writeVarint64(p.int64ToZigzag(value))
+ return NewTProtocolException(err)
+}
+
+// Write a double to the wire as 8 bytes.
+func (p *TCompactProtocol) WriteDouble(value float64) error {
+ buf := p.buffer[0:8]
+ binary.LittleEndian.PutUint64(buf, math.Float64bits(value))
+ _, err := p.trans.Write(buf)
+ return NewTProtocolException(err)
+}
+
+// Write a string to the wire with a varint size preceding.
+func (p *TCompactProtocol) WriteString(value string) error {
+ _, e := p.writeVarint32(int32(len(value)))
+ if e != nil {
+ return NewTProtocolException(e)
+ }
+ if len(value) > 0 {
+ }
+ _, e = p.trans.WriteString(value)
+ return e
+}
+
+// Write a byte array, using a varint for the size.
+func (p *TCompactProtocol) WriteBinary(bin []byte) error {
+ _, e := p.writeVarint32(int32(len(bin)))
+ if e != nil {
+ return NewTProtocolException(e)
+ }
+ if len(bin) > 0 {
+ _, e = p.trans.Write(bin)
+ return NewTProtocolException(e)
+ }
+ return nil
+}
+
+//
+// Reading methods.
+//
+
+// Read a message header.
+func (p *TCompactProtocol) ReadMessageBegin() (name string, typeId TMessageType, seqId int32, err error) {
+
+ protocolId, err := p.readByteDirect()
+ if err != nil {
+ return
+ }
+
+ if protocolId != COMPACT_PROTOCOL_ID {
+ e := fmt.Errorf("Expected protocol id %02x but got %02x", COMPACT_PROTOCOL_ID, protocolId)
+ return "", typeId, seqId, NewTProtocolExceptionWithType(BAD_VERSION, e)
+ }
+
+ versionAndType, err := p.readByteDirect()
+ if err != nil {
+ return
+ }
+
+ version := versionAndType & COMPACT_VERSION_MASK
+ typeId = TMessageType((versionAndType >> COMPACT_TYPE_SHIFT_AMOUNT) & COMPACT_TYPE_BITS)
+ if version != COMPACT_VERSION {
+ e := fmt.Errorf("Expected version %02x but got %02x", COMPACT_VERSION, version)
+ err = NewTProtocolExceptionWithType(BAD_VERSION, e)
+ return
+ }
+ seqId, e := p.readVarint32()
+ if e != nil {
+ err = NewTProtocolException(e)
+ return
+ }
+ name, err = p.ReadString()
+ return
+}
+
+func (p *TCompactProtocol) ReadMessageEnd() error { return nil }
+
+// Read a struct begin. There's nothing on the wire for this, but it is our
+// opportunity to push a new struct begin marker onto the field stack.
+func (p *TCompactProtocol) ReadStructBegin() (name string, err error) {
+ p.lastField = append(p.lastField, p.lastFieldId)
+ p.lastFieldId = 0
+ return
+}
+
+// Doesn't actually consume any wire data, just removes the last field for
+// this struct from the field stack.
+func (p *TCompactProtocol) ReadStructEnd() error {
+ // consume the last field we read off the wire.
+ p.lastFieldId = p.lastField[len(p.lastField)-1]
+ p.lastField = p.lastField[:len(p.lastField)-1]
+ return nil
+}
+
+// Read a field header off the wire.
+func (p *TCompactProtocol) ReadFieldBegin() (name string, typeId TType, id int16, err error) {
+ t, err := p.readByteDirect()
+ if err != nil {
+ return
+ }
+
+ // if it's a stop, then we can return immediately, as the struct is over.
+ if (t & 0x0f) == STOP {
+ return "", STOP, 0, nil
+ }
+
+ // mask off the 4 MSB of the type header. it could contain a field id delta.
+ modifier := int16((t & 0xf0) >> 4)
+ if modifier == 0 {
+ // not a delta. look ahead for the zigzag varint field id.
+ id, err = p.ReadI16()
+ if err != nil {
+ return
+ }
+ } else {
+ // has a delta. add the delta to the last read field id.
+ id = int16(p.lastFieldId) + modifier
+ }
+ typeId, e := p.getTType(tCompactType(t & 0x0f))
+ if e != nil {
+ err = NewTProtocolException(e)
+ return
+ }
+
+ // if this happens to be a boolean field, the value is encoded in the type
+ if p.isBoolType(t) {
+ // save the boolean value in a special instance variable.
+ p.boolValue = (byte(t)&0x0f == COMPACT_BOOLEAN_TRUE)
+ p.boolValueIsNotNull = true
+ }
+
+ // push the new field onto the field stack so we can keep the deltas going.
+ p.lastFieldId = int(id)
+ return
+}
+
+func (p *TCompactProtocol) ReadFieldEnd() error { return nil }
+
+// Read a map header off the wire. If the size is zero, skip reading the key
+// and value type. This means that 0-length maps will yield TMaps without the
+// "correct" types.
+func (p *TCompactProtocol) ReadMapBegin() (keyType TType, valueType TType, size int, err error) {
+ size32, e := p.readVarint32()
+ if e != nil {
+ err = NewTProtocolException(e)
+ return
+ }
+ if size32 < 0 {
+ err = invalidDataLength
+ return
+ }
+ size = int(size32)
+
+ keyAndValueType := byte(STOP)
+ if size != 0 {
+ keyAndValueType, err = p.readByteDirect()
+ if err != nil {
+ return
+ }
+ }
+ keyType, _ = p.getTType(tCompactType(keyAndValueType >> 4))
+ valueType, _ = p.getTType(tCompactType(keyAndValueType & 0xf))
+ return
+}
+
+func (p *TCompactProtocol) ReadMapEnd() error { return nil }
+
+// Read a list header off the wire. If the list size is 0-14, the size will
+// be packed into the element type header. If it's a longer list, the 4 MSB
+// of the element type header will be 0xF, and a varint will follow with the
+// true size.
+func (p *TCompactProtocol) ReadListBegin() (elemType TType, size int, err error) {
+ size_and_type, err := p.readByteDirect()
+ if err != nil {
+ return
+ }
+ size = int((size_and_type >> 4) & 0x0f)
+ if size == 15 {
+ size2, e := p.readVarint32()
+ if e != nil {
+ err = NewTProtocolException(e)
+ return
+ }
+ if size2 < 0 {
+ err = invalidDataLength
+ return
+ }
+ size = int(size2)
+ }
+ elemType, e := p.getTType(tCompactType(size_and_type))
+ if e != nil {
+ err = NewTProtocolException(e)
+ return
+ }
+ return
+}
+
+func (p *TCompactProtocol) ReadListEnd() error { return nil }
+
+// Read a set header off the wire. If the set size is 0-14, the size will
+// be packed into the element type header. If it's a longer set, the 4 MSB
+// of the element type header will be 0xF, and a varint will follow with the
+// true size.
+func (p *TCompactProtocol) ReadSetBegin() (elemType TType, size int, err error) {
+ return p.ReadListBegin()
+}
+
+func (p *TCompactProtocol) ReadSetEnd() error { return nil }
+
+// Read a boolean off the wire. If this is a boolean field, the value should
+// already have been read during readFieldBegin, so we'll just consume the
+// pre-stored value. Otherwise, read a byte.
+func (p *TCompactProtocol) ReadBool() (value bool, err error) {
+ if p.boolValueIsNotNull {
+ p.boolValueIsNotNull = false
+ return p.boolValue, nil
+ }
+ v, err := p.readByteDirect()
+ return v == COMPACT_BOOLEAN_TRUE, err
+}
+
+// Read a single byte off the wire. Nothing interesting here.
+func (p *TCompactProtocol) ReadByte() (int8, error) {
+ v, err := p.readByteDirect()
+ if err != nil {
+ return 0, NewTProtocolException(err)
+ }
+ return int8(v), err
+}
+
+// Read an i16 from the wire as a zigzag varint.
+func (p *TCompactProtocol) ReadI16() (value int16, err error) {
+ v, err := p.ReadI32()
+ return int16(v), err
+}
+
+// Read an i32 from the wire as a zigzag varint.
+func (p *TCompactProtocol) ReadI32() (value int32, err error) {
+ v, e := p.readVarint32()
+ if e != nil {
+ return 0, NewTProtocolException(e)
+ }
+ value = p.zigzagToInt32(v)
+ return value, nil
+}
+
+// Read an i64 from the wire as a zigzag varint.
+func (p *TCompactProtocol) ReadI64() (value int64, err error) {
+ v, e := p.readVarint64()
+ if e != nil {
+ return 0, NewTProtocolException(e)
+ }
+ value = p.zigzagToInt64(v)
+ return value, nil
+}
+
+// No magic here - just read a double off the wire.
+func (p *TCompactProtocol) ReadDouble() (value float64, err error) {
+ longBits := p.buffer[0:8]
+ _, e := io.ReadFull(p.trans, longBits)
+ if e != nil {
+ return 0.0, NewTProtocolException(e)
+ }
+ return math.Float64frombits(p.bytesToUint64(longBits)), nil
+}
+
+// Reads a []byte (via readBinary), and then UTF-8 decodes it.
+func (p *TCompactProtocol) ReadString() (value string, err error) {
+ length, e := p.readVarint32()
+ if e != nil {
+ return "", NewTProtocolException(e)
+ }
+ if length < 0 {
+ return "", invalidDataLength
+ }
+ if uint64(length) > p.trans.RemainingBytes() {
+ return "", invalidDataLength
+ }
+
+ if length == 0 {
+ return "", nil
+ }
+ var buf []byte
+ if length <= int32(len(p.buffer)) {
+ buf = p.buffer[0:length]
+ } else {
+ buf = make([]byte, length)
+ }
+ _, e = io.ReadFull(p.trans, buf)
+ return string(buf), NewTProtocolException(e)
+}
+
+// Read a []byte from the wire.
+func (p *TCompactProtocol) ReadBinary() (value []byte, err error) {
+ length, e := p.readVarint32()
+ if e != nil {
+ return nil, NewTProtocolException(e)
+ }
+ if length == 0 {
+ return []byte{}, nil
+ }
+ if length < 0 {
+ return nil, invalidDataLength
+ }
+ if uint64(length) > p.trans.RemainingBytes() {
+ return nil, invalidDataLength
+ }
+
+ buf := make([]byte, length)
+ _, e = io.ReadFull(p.trans, buf)
+ return buf, NewTProtocolException(e)
+}
+
+func (p *TCompactProtocol) Flush() (err error) {
+ return NewTProtocolException(p.trans.Flush())
+}
+
+func (p *TCompactProtocol) Skip(fieldType TType) (err error) {
+ return SkipDefaultDepth(p, fieldType)
+}
+
+func (p *TCompactProtocol) Transport() TTransport {
+ return p.origTransport
+}
+
+//
+// Internal writing methods
+//
+
+// Abstract method for writing the start of lists and sets. List and sets on
+// the wire differ only by the type indicator.
+func (p *TCompactProtocol) writeCollectionBegin(elemType TType, size int) (int, error) {
+ if size <= 14 {
+ return 1, p.writeByteDirect(byte(int32(size<<4) | int32(p.getCompactType(elemType))))
+ }
+ err := p.writeByteDirect(0xf0 | byte(p.getCompactType(elemType)))
+ if err != nil {
+ return 0, err
+ }
+ m, err := p.writeVarint32(int32(size))
+ return 1 + m, err
+}
+
+// Write an i32 as a varint. Results in 1-5 bytes on the wire.
+// TODO(pomack): make a permanent buffer like writeVarint64?
+func (p *TCompactProtocol) writeVarint32(n int32) (int, error) {
+ i32buf := p.buffer[0:5]
+ idx := 0
+ for {
+ if (n & ^0x7F) == 0 {
+ i32buf[idx] = byte(n)
+ idx++
+ // p.writeByteDirect(byte(n));
+ break
+ // return;
+ } else {
+ i32buf[idx] = byte((n & 0x7F) | 0x80)
+ idx++
+ // p.writeByteDirect(byte(((n & 0x7F) | 0x80)));
+ u := uint32(n)
+ n = int32(u >> 7)
+ }
+ }
+ return p.trans.Write(i32buf[0:idx])
+}
+
+// Write an i64 as a varint. Results in 1-10 bytes on the wire.
+func (p *TCompactProtocol) writeVarint64(n int64) (int, error) {
+ varint64out := p.buffer[0:10]
+ idx := 0
+ for {
+ if (n & ^0x7F) == 0 {
+ varint64out[idx] = byte(n)
+ idx++
+ break
+ } else {
+ varint64out[idx] = byte((n & 0x7F) | 0x80)
+ idx++
+ u := uint64(n)
+ n = int64(u >> 7)
+ }
+ }
+ return p.trans.Write(varint64out[0:idx])
+}
+
+// Convert l into a zigzag long. This allows negative numbers to be
+// represented compactly as a varint.
+func (p *TCompactProtocol) int64ToZigzag(l int64) int64 {
+ return (l << 1) ^ (l >> 63)
+}
+
+// Convert l into a zigzag long. This allows negative numbers to be
+// represented compactly as a varint.
+func (p *TCompactProtocol) int32ToZigzag(n int32) int32 {
+ return (n << 1) ^ (n >> 31)
+}
+
+func (p *TCompactProtocol) fixedUint64ToBytes(n uint64, buf []byte) {
+ binary.LittleEndian.PutUint64(buf, n)
+}
+
+func (p *TCompactProtocol) fixedInt64ToBytes(n int64, buf []byte) {
+ binary.LittleEndian.PutUint64(buf, uint64(n))
+}
+
+// Writes a byte without any possibility of all that field header nonsense.
+// Used internally by other writing methods that know they need to write a byte.
+func (p *TCompactProtocol) writeByteDirect(b byte) error {
+ return p.trans.WriteByte(b)
+}
+
+// Writes a byte without any possibility of all that field header nonsense.
+func (p *TCompactProtocol) writeIntAsByteDirect(n int) (int, error) {
+ return 1, p.writeByteDirect(byte(n))
+}
+
+//
+// Internal reading methods
+//
+
+// Read an i32 from the wire as a varint. The MSB of each byte is set
+// if there is another byte to follow. This can read up to 5 bytes.
+func (p *TCompactProtocol) readVarint32() (int32, error) {
+ // if the wire contains the right stuff, this will just truncate the i64 we
+ // read and get us the right sign.
+ v, err := p.readVarint64()
+ return int32(v), err
+}
+
+// Read an i64 from the wire as a proper varint. The MSB of each byte is set
+// if there is another byte to follow. This can read up to 10 bytes.
+func (p *TCompactProtocol) readVarint64() (int64, error) {
+ shift := uint(0)
+ result := int64(0)
+ for {
+ b, err := p.readByteDirect()
+ if err != nil {
+ return 0, err
+ }
+ result |= int64(b&0x7f) << shift
+ if (b & 0x80) != 0x80 {
+ break
+ }
+ shift += 7
+ }
+ return result, nil
+}
+
+// Read a byte, unlike ReadByte that reads Thrift-byte that is i8.
+func (p *TCompactProtocol) readByteDirect() (byte, error) {
+ return p.trans.ReadByte()
+}
+
+//
+// encoding helpers
+//
+
+// Convert from zigzag int to int.
+func (p *TCompactProtocol) zigzagToInt32(n int32) int32 {
+ u := uint32(n)
+ return int32(u>>1) ^ -(n & 1)
+}
+
+// Convert from zigzag long to long.
+func (p *TCompactProtocol) zigzagToInt64(n int64) int64 {
+ u := uint64(n)
+ return int64(u>>1) ^ -(n & 1)
+}
+
+// Note that it's important that the mask bytes are long literals,
+// otherwise they'll default to ints, and when you shift an int left 56 bits,
+// you just get a messed up int.
+func (p *TCompactProtocol) bytesToInt64(b []byte) int64 {
+ return int64(binary.LittleEndian.Uint64(b))
+}
+
+// Note that it's important that the mask bytes are long literals,
+// otherwise they'll default to ints, and when you shift an int left 56 bits,
+// you just get a messed up int.
+func (p *TCompactProtocol) bytesToUint64(b []byte) uint64 {
+ return binary.LittleEndian.Uint64(b)
+}
+
+//
+// type testing and converting
+//
+
+func (p *TCompactProtocol) isBoolType(b byte) bool {
+ return (b&0x0f) == COMPACT_BOOLEAN_TRUE || (b&0x0f) == COMPACT_BOOLEAN_FALSE
+}
+
+// Given a tCompactType constant, convert it to its corresponding
+// TType value.
+func (p *TCompactProtocol) getTType(t tCompactType) (TType, error) {
+ switch byte(t) & 0x0f {
+ case STOP:
+ return STOP, nil
+ case COMPACT_BOOLEAN_FALSE, COMPACT_BOOLEAN_TRUE:
+ return BOOL, nil
+ case COMPACT_BYTE:
+ return BYTE, nil
+ case COMPACT_I16:
+ return I16, nil
+ case COMPACT_I32:
+ return I32, nil
+ case COMPACT_I64:
+ return I64, nil
+ case COMPACT_DOUBLE:
+ return DOUBLE, nil
+ case COMPACT_BINARY:
+ return STRING, nil
+ case COMPACT_LIST:
+ return LIST, nil
+ case COMPACT_SET:
+ return SET, nil
+ case COMPACT_MAP:
+ return MAP, nil
+ case COMPACT_STRUCT:
+ return STRUCT, nil
+ }
+ return STOP, TException(fmt.Errorf("don't know what type: %d", t&0x0f))
+}
+
+// Given a TType value, find the appropriate TCompactProtocol.Types constant.
+func (p *TCompactProtocol) getCompactType(t TType) tCompactType {
+ return ttypeToCompactType[t]
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/thrift/exception.go b/vendor/github.com/uber/jaeger-client-go/thrift/exception.go
new file mode 100644
index 000000000..ea8d6f661
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/thrift/exception.go
@@ -0,0 +1,44 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+import (
+ "errors"
+)
+
+// Generic Thrift exception
+type TException interface {
+ error
+}
+
+// Prepends additional information to an error without losing the Thrift exception interface
+func PrependError(prepend string, err error) error {
+ if t, ok := err.(TTransportException); ok {
+ return NewTTransportException(t.TypeId(), prepend+t.Error())
+ }
+ if t, ok := err.(TProtocolException); ok {
+ return NewTProtocolExceptionWithType(t.TypeId(), errors.New(prepend+err.Error()))
+ }
+ if t, ok := err.(TApplicationException); ok {
+ return NewTApplicationException(t.TypeId(), prepend+t.Error())
+ }
+
+ return errors.New(prepend + err.Error())
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/thrift/memory_buffer.go b/vendor/github.com/uber/jaeger-client-go/thrift/memory_buffer.go
new file mode 100644
index 000000000..b62fd56f0
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/thrift/memory_buffer.go
@@ -0,0 +1,79 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+import (
+ "bytes"
+)
+
+// Memory buffer-based implementation of the TTransport interface.
+type TMemoryBuffer struct {
+ *bytes.Buffer
+ size int
+}
+
+type TMemoryBufferTransportFactory struct {
+ size int
+}
+
+func (p *TMemoryBufferTransportFactory) GetTransport(trans TTransport) TTransport {
+ if trans != nil {
+ t, ok := trans.(*TMemoryBuffer)
+ if ok && t.size > 0 {
+ return NewTMemoryBufferLen(t.size)
+ }
+ }
+ return NewTMemoryBufferLen(p.size)
+}
+
+func NewTMemoryBufferTransportFactory(size int) *TMemoryBufferTransportFactory {
+ return &TMemoryBufferTransportFactory{size: size}
+}
+
+func NewTMemoryBuffer() *TMemoryBuffer {
+ return &TMemoryBuffer{Buffer: &bytes.Buffer{}, size: 0}
+}
+
+func NewTMemoryBufferLen(size int) *TMemoryBuffer {
+ buf := make([]byte, 0, size)
+ return &TMemoryBuffer{Buffer: bytes.NewBuffer(buf), size: size}
+}
+
+func (p *TMemoryBuffer) IsOpen() bool {
+ return true
+}
+
+func (p *TMemoryBuffer) Open() error {
+ return nil
+}
+
+func (p *TMemoryBuffer) Close() error {
+ p.Buffer.Reset()
+ return nil
+}
+
+// Flushing a memory buffer is a no-op
+func (p *TMemoryBuffer) Flush() error {
+ return nil
+}
+
+func (p *TMemoryBuffer) RemainingBytes() (num_bytes uint64) {
+ return uint64(p.Buffer.Len())
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/thrift/messagetype.go b/vendor/github.com/uber/jaeger-client-go/thrift/messagetype.go
new file mode 100644
index 000000000..25ab2e98a
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/thrift/messagetype.go
@@ -0,0 +1,31 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+// Message type constants in the Thrift protocol.
+type TMessageType int32
+
+const (
+ INVALID_TMESSAGE_TYPE TMessageType = 0
+ CALL TMessageType = 1
+ REPLY TMessageType = 2
+ EXCEPTION TMessageType = 3
+ ONEWAY TMessageType = 4
+)
diff --git a/vendor/github.com/uber/jaeger-client-go/thrift/numeric.go b/vendor/github.com/uber/jaeger-client-go/thrift/numeric.go
new file mode 100644
index 000000000..aa8daa9b5
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/thrift/numeric.go
@@ -0,0 +1,164 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+import (
+ "math"
+ "strconv"
+)
+
+type Numeric interface {
+ Int64() int64
+ Int32() int32
+ Int16() int16
+ Byte() byte
+ Int() int
+ Float64() float64
+ Float32() float32
+ String() string
+ isNull() bool
+}
+
+type numeric struct {
+ iValue int64
+ dValue float64
+ sValue string
+ isNil bool
+}
+
+var (
+ INFINITY Numeric
+ NEGATIVE_INFINITY Numeric
+ NAN Numeric
+ ZERO Numeric
+ NUMERIC_NULL Numeric
+)
+
+func NewNumericFromDouble(dValue float64) Numeric {
+ if math.IsInf(dValue, 1) {
+ return INFINITY
+ }
+ if math.IsInf(dValue, -1) {
+ return NEGATIVE_INFINITY
+ }
+ if math.IsNaN(dValue) {
+ return NAN
+ }
+ iValue := int64(dValue)
+ sValue := strconv.FormatFloat(dValue, 'g', 10, 64)
+ isNil := false
+ return &numeric{iValue: iValue, dValue: dValue, sValue: sValue, isNil: isNil}
+}
+
+func NewNumericFromI64(iValue int64) Numeric {
+ dValue := float64(iValue)
+ sValue := string(iValue)
+ isNil := false
+ return &numeric{iValue: iValue, dValue: dValue, sValue: sValue, isNil: isNil}
+}
+
+func NewNumericFromI32(iValue int32) Numeric {
+ dValue := float64(iValue)
+ sValue := string(iValue)
+ isNil := false
+ return &numeric{iValue: int64(iValue), dValue: dValue, sValue: sValue, isNil: isNil}
+}
+
+func NewNumericFromString(sValue string) Numeric {
+ if sValue == INFINITY.String() {
+ return INFINITY
+ }
+ if sValue == NEGATIVE_INFINITY.String() {
+ return NEGATIVE_INFINITY
+ }
+ if sValue == NAN.String() {
+ return NAN
+ }
+ iValue, _ := strconv.ParseInt(sValue, 10, 64)
+ dValue, _ := strconv.ParseFloat(sValue, 64)
+ isNil := len(sValue) == 0
+ return &numeric{iValue: iValue, dValue: dValue, sValue: sValue, isNil: isNil}
+}
+
+func NewNumericFromJSONString(sValue string, isNull bool) Numeric {
+ if isNull {
+ return NewNullNumeric()
+ }
+ if sValue == JSON_INFINITY {
+ return INFINITY
+ }
+ if sValue == JSON_NEGATIVE_INFINITY {
+ return NEGATIVE_INFINITY
+ }
+ if sValue == JSON_NAN {
+ return NAN
+ }
+ iValue, _ := strconv.ParseInt(sValue, 10, 64)
+ dValue, _ := strconv.ParseFloat(sValue, 64)
+ return &numeric{iValue: iValue, dValue: dValue, sValue: sValue, isNil: isNull}
+}
+
+func NewNullNumeric() Numeric {
+ return &numeric{iValue: 0, dValue: 0.0, sValue: "", isNil: true}
+}
+
+func (p *numeric) Int64() int64 {
+ return p.iValue
+}
+
+func (p *numeric) Int32() int32 {
+ return int32(p.iValue)
+}
+
+func (p *numeric) Int16() int16 {
+ return int16(p.iValue)
+}
+
+func (p *numeric) Byte() byte {
+ return byte(p.iValue)
+}
+
+func (p *numeric) Int() int {
+ return int(p.iValue)
+}
+
+func (p *numeric) Float64() float64 {
+ return p.dValue
+}
+
+func (p *numeric) Float32() float32 {
+ return float32(p.dValue)
+}
+
+func (p *numeric) String() string {
+ return p.sValue
+}
+
+func (p *numeric) isNull() bool {
+ return p.isNil
+}
+
+func init() {
+ INFINITY = &numeric{iValue: 0, dValue: math.Inf(1), sValue: "Infinity", isNil: false}
+ NEGATIVE_INFINITY = &numeric{iValue: 0, dValue: math.Inf(-1), sValue: "-Infinity", isNil: false}
+ NAN = &numeric{iValue: 0, dValue: math.NaN(), sValue: "NaN", isNil: false}
+ ZERO = &numeric{iValue: 0, dValue: 0, sValue: "0", isNil: false}
+ NUMERIC_NULL = &numeric{iValue: 0, dValue: 0, sValue: "0", isNil: true}
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/thrift/processor.go b/vendor/github.com/uber/jaeger-client-go/thrift/processor.go
new file mode 100644
index 000000000..ca0d3faf2
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/thrift/processor.go
@@ -0,0 +1,30 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+// A processor is a generic object which operates upon an input stream and
+// writes to some output stream.
+type TProcessor interface {
+ Process(in, out TProtocol) (bool, TException)
+}
+
+type TProcessorFunction interface {
+ Process(seqId int32, in, out TProtocol) (bool, TException)
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/thrift/protocol.go b/vendor/github.com/uber/jaeger-client-go/thrift/protocol.go
new file mode 100644
index 000000000..45fa202e7
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/thrift/protocol.go
@@ -0,0 +1,175 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+import (
+ "errors"
+)
+
+const (
+ VERSION_MASK = 0xffff0000
+ VERSION_1 = 0x80010000
+)
+
+type TProtocol interface {
+ WriteMessageBegin(name string, typeId TMessageType, seqid int32) error
+ WriteMessageEnd() error
+ WriteStructBegin(name string) error
+ WriteStructEnd() error
+ WriteFieldBegin(name string, typeId TType, id int16) error
+ WriteFieldEnd() error
+ WriteFieldStop() error
+ WriteMapBegin(keyType TType, valueType TType, size int) error
+ WriteMapEnd() error
+ WriteListBegin(elemType TType, size int) error
+ WriteListEnd() error
+ WriteSetBegin(elemType TType, size int) error
+ WriteSetEnd() error
+ WriteBool(value bool) error
+ WriteByte(value int8) error
+ WriteI16(value int16) error
+ WriteI32(value int32) error
+ WriteI64(value int64) error
+ WriteDouble(value float64) error
+ WriteString(value string) error
+ WriteBinary(value []byte) error
+
+ ReadMessageBegin() (name string, typeId TMessageType, seqid int32, err error)
+ ReadMessageEnd() error
+ ReadStructBegin() (name string, err error)
+ ReadStructEnd() error
+ ReadFieldBegin() (name string, typeId TType, id int16, err error)
+ ReadFieldEnd() error
+ ReadMapBegin() (keyType TType, valueType TType, size int, err error)
+ ReadMapEnd() error
+ ReadListBegin() (elemType TType, size int, err error)
+ ReadListEnd() error
+ ReadSetBegin() (elemType TType, size int, err error)
+ ReadSetEnd() error
+ ReadBool() (value bool, err error)
+ ReadByte() (value int8, err error)
+ ReadI16() (value int16, err error)
+ ReadI32() (value int32, err error)
+ ReadI64() (value int64, err error)
+ ReadDouble() (value float64, err error)
+ ReadString() (value string, err error)
+ ReadBinary() (value []byte, err error)
+
+ Skip(fieldType TType) (err error)
+ Flush() (err error)
+
+ Transport() TTransport
+}
+
+// The maximum recursive depth the skip() function will traverse
+const DEFAULT_RECURSION_DEPTH = 64
+
+// Skips over the next data element from the provided input TProtocol object.
+func SkipDefaultDepth(prot TProtocol, typeId TType) (err error) {
+ return Skip(prot, typeId, DEFAULT_RECURSION_DEPTH)
+}
+
+// Skips over the next data element from the provided input TProtocol object.
+func Skip(self TProtocol, fieldType TType, maxDepth int) (err error) {
+
+ if maxDepth <= 0 {
+ return NewTProtocolExceptionWithType( DEPTH_LIMIT, errors.New("Depth limit exceeded"))
+ }
+
+ switch fieldType {
+ case STOP:
+ return
+ case BOOL:
+ _, err = self.ReadBool()
+ return
+ case BYTE:
+ _, err = self.ReadByte()
+ return
+ case I16:
+ _, err = self.ReadI16()
+ return
+ case I32:
+ _, err = self.ReadI32()
+ return
+ case I64:
+ _, err = self.ReadI64()
+ return
+ case DOUBLE:
+ _, err = self.ReadDouble()
+ return
+ case STRING:
+ _, err = self.ReadString()
+ return
+ case STRUCT:
+ if _, err = self.ReadStructBegin(); err != nil {
+ return err
+ }
+ for {
+ _, typeId, _, _ := self.ReadFieldBegin()
+ if typeId == STOP {
+ break
+ }
+ err := Skip(self, typeId, maxDepth-1)
+ if err != nil {
+ return err
+ }
+ self.ReadFieldEnd()
+ }
+ return self.ReadStructEnd()
+ case MAP:
+ keyType, valueType, size, err := self.ReadMapBegin()
+ if err != nil {
+ return err
+ }
+ for i := 0; i < size; i++ {
+ err := Skip(self, keyType, maxDepth-1)
+ if err != nil {
+ return err
+ }
+ self.Skip(valueType)
+ }
+ return self.ReadMapEnd()
+ case SET:
+ elemType, size, err := self.ReadSetBegin()
+ if err != nil {
+ return err
+ }
+ for i := 0; i < size; i++ {
+ err := Skip(self, elemType, maxDepth-1)
+ if err != nil {
+ return err
+ }
+ }
+ return self.ReadSetEnd()
+ case LIST:
+ elemType, size, err := self.ReadListBegin()
+ if err != nil {
+ return err
+ }
+ for i := 0; i < size; i++ {
+ err := Skip(self, elemType, maxDepth-1)
+ if err != nil {
+ return err
+ }
+ }
+ return self.ReadListEnd()
+ }
+ return nil
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/thrift/protocol_exception.go b/vendor/github.com/uber/jaeger-client-go/thrift/protocol_exception.go
new file mode 100644
index 000000000..6e357ee89
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/thrift/protocol_exception.go
@@ -0,0 +1,78 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+import (
+ "encoding/base64"
+)
+
+// Thrift Protocol exception
+type TProtocolException interface {
+ TException
+ TypeId() int
+}
+
+const (
+ UNKNOWN_PROTOCOL_EXCEPTION = 0
+ INVALID_DATA = 1
+ NEGATIVE_SIZE = 2
+ SIZE_LIMIT = 3
+ BAD_VERSION = 4
+ NOT_IMPLEMENTED = 5
+ DEPTH_LIMIT = 6
+)
+
+type tProtocolException struct {
+ typeId int
+ message string
+}
+
+func (p *tProtocolException) TypeId() int {
+ return p.typeId
+}
+
+func (p *tProtocolException) String() string {
+ return p.message
+}
+
+func (p *tProtocolException) Error() string {
+ return p.message
+}
+
+func NewTProtocolException(err error) TProtocolException {
+ if err == nil {
+ return nil
+ }
+ if e,ok := err.(TProtocolException); ok {
+ return e
+ }
+ if _, ok := err.(base64.CorruptInputError); ok {
+ return &tProtocolException{INVALID_DATA, err.Error()}
+ }
+ return &tProtocolException{UNKNOWN_PROTOCOL_EXCEPTION, err.Error()}
+}
+
+func NewTProtocolExceptionWithType(errType int, err error) TProtocolException {
+ if err == nil {
+ return nil
+ }
+ return &tProtocolException{errType, err.Error()}
+}
+
diff --git a/vendor/github.com/uber/jaeger-client-go/thrift/protocol_factory.go b/vendor/github.com/uber/jaeger-client-go/thrift/protocol_factory.go
new file mode 100644
index 000000000..c40f796d8
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/thrift/protocol_factory.go
@@ -0,0 +1,25 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+// Factory interface for constructing protocol instances.
+type TProtocolFactory interface {
+ GetProtocol(trans TTransport) TProtocol
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/thrift/rich_transport.go b/vendor/github.com/uber/jaeger-client-go/thrift/rich_transport.go
new file mode 100644
index 000000000..8e296a99b
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/thrift/rich_transport.go
@@ -0,0 +1,69 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+import "io"
+
+type RichTransport struct {
+ TTransport
+}
+
+// Wraps Transport to provide TRichTransport interface
+func NewTRichTransport(trans TTransport) *RichTransport {
+ return &RichTransport{trans}
+}
+
+func (r *RichTransport) ReadByte() (c byte, err error) {
+ return readByte(r.TTransport)
+}
+
+func (r *RichTransport) WriteByte(c byte) error {
+ return writeByte(r.TTransport, c)
+}
+
+func (r *RichTransport) WriteString(s string) (n int, err error) {
+ return r.Write([]byte(s))
+}
+
+func (r *RichTransport) RemainingBytes() (num_bytes uint64) {
+ return r.TTransport.RemainingBytes()
+}
+
+func readByte(r io.Reader) (c byte, err error) {
+ v := [1]byte{0}
+ n, err := r.Read(v[0:1])
+ if n > 0 && (err == nil || err == io.EOF) {
+ return v[0], nil
+ }
+ if n > 0 && err != nil {
+ return v[0], err
+ }
+ if err != nil {
+ return 0, err
+ }
+ return v[0], nil
+}
+
+func writeByte(w io.Writer, c byte) error {
+ v := [1]byte{c}
+ _, err := w.Write(v[0:1])
+ return err
+}
+
diff --git a/vendor/github.com/uber/jaeger-client-go/thrift/serializer.go b/vendor/github.com/uber/jaeger-client-go/thrift/serializer.go
new file mode 100644
index 000000000..771222999
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/thrift/serializer.go
@@ -0,0 +1,75 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+type TSerializer struct {
+ Transport *TMemoryBuffer
+ Protocol TProtocol
+}
+
+type TStruct interface {
+ Write(p TProtocol) error
+ Read(p TProtocol) error
+}
+
+func NewTSerializer() *TSerializer {
+ transport := NewTMemoryBufferLen(1024)
+ protocol := NewTBinaryProtocolFactoryDefault().GetProtocol(transport)
+
+ return &TSerializer{
+ transport,
+ protocol}
+}
+
+func (t *TSerializer) WriteString(msg TStruct) (s string, err error) {
+ t.Transport.Reset()
+
+ if err = msg.Write(t.Protocol); err != nil {
+ return
+ }
+
+ if err = t.Protocol.Flush(); err != nil {
+ return
+ }
+ if err = t.Transport.Flush(); err != nil {
+ return
+ }
+
+ return t.Transport.String(), nil
+}
+
+func (t *TSerializer) Write(msg TStruct) (b []byte, err error) {
+ t.Transport.Reset()
+
+ if err = msg.Write(t.Protocol); err != nil {
+ return
+ }
+
+ if err = t.Protocol.Flush(); err != nil {
+ return
+ }
+
+ if err = t.Transport.Flush(); err != nil {
+ return
+ }
+
+ b = append(b, t.Transport.Bytes()...)
+ return
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/thrift/simple_json_protocol.go b/vendor/github.com/uber/jaeger-client-go/thrift/simple_json_protocol.go
new file mode 100644
index 000000000..412a482d0
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/thrift/simple_json_protocol.go
@@ -0,0 +1,1337 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+import (
+ "bufio"
+ "bytes"
+ "encoding/base64"
+ "encoding/json"
+ "fmt"
+ "io"
+ "math"
+ "strconv"
+)
+
+type _ParseContext int
+
+const (
+ _CONTEXT_IN_TOPLEVEL _ParseContext = 1
+ _CONTEXT_IN_LIST_FIRST _ParseContext = 2
+ _CONTEXT_IN_LIST _ParseContext = 3
+ _CONTEXT_IN_OBJECT_FIRST _ParseContext = 4
+ _CONTEXT_IN_OBJECT_NEXT_KEY _ParseContext = 5
+ _CONTEXT_IN_OBJECT_NEXT_VALUE _ParseContext = 6
+)
+
+func (p _ParseContext) String() string {
+ switch p {
+ case _CONTEXT_IN_TOPLEVEL:
+ return "TOPLEVEL"
+ case _CONTEXT_IN_LIST_FIRST:
+ return "LIST-FIRST"
+ case _CONTEXT_IN_LIST:
+ return "LIST"
+ case _CONTEXT_IN_OBJECT_FIRST:
+ return "OBJECT-FIRST"
+ case _CONTEXT_IN_OBJECT_NEXT_KEY:
+ return "OBJECT-NEXT-KEY"
+ case _CONTEXT_IN_OBJECT_NEXT_VALUE:
+ return "OBJECT-NEXT-VALUE"
+ }
+ return "UNKNOWN-PARSE-CONTEXT"
+}
+
+// JSON protocol implementation for thrift.
+//
+// This protocol produces/consumes a simple output format
+// suitable for parsing by scripting languages. It should not be
+// confused with the full-featured TJSONProtocol.
+//
+type TSimpleJSONProtocol struct {
+ trans TTransport
+
+ parseContextStack []int
+ dumpContext []int
+
+ writer *bufio.Writer
+ reader *bufio.Reader
+}
+
+// Constructor
+func NewTSimpleJSONProtocol(t TTransport) *TSimpleJSONProtocol {
+ v := &TSimpleJSONProtocol{trans: t,
+ writer: bufio.NewWriter(t),
+ reader: bufio.NewReader(t),
+ }
+ v.parseContextStack = append(v.parseContextStack, int(_CONTEXT_IN_TOPLEVEL))
+ v.dumpContext = append(v.dumpContext, int(_CONTEXT_IN_TOPLEVEL))
+ return v
+}
+
+// Factory
+type TSimpleJSONProtocolFactory struct{}
+
+func (p *TSimpleJSONProtocolFactory) GetProtocol(trans TTransport) TProtocol {
+ return NewTSimpleJSONProtocol(trans)
+}
+
+func NewTSimpleJSONProtocolFactory() *TSimpleJSONProtocolFactory {
+ return &TSimpleJSONProtocolFactory{}
+}
+
+var (
+ JSON_COMMA []byte
+ JSON_COLON []byte
+ JSON_LBRACE []byte
+ JSON_RBRACE []byte
+ JSON_LBRACKET []byte
+ JSON_RBRACKET []byte
+ JSON_QUOTE byte
+ JSON_QUOTE_BYTES []byte
+ JSON_NULL []byte
+ JSON_TRUE []byte
+ JSON_FALSE []byte
+ JSON_INFINITY string
+ JSON_NEGATIVE_INFINITY string
+ JSON_NAN string
+ JSON_INFINITY_BYTES []byte
+ JSON_NEGATIVE_INFINITY_BYTES []byte
+ JSON_NAN_BYTES []byte
+ json_nonbase_map_elem_bytes []byte
+)
+
+func init() {
+ JSON_COMMA = []byte{','}
+ JSON_COLON = []byte{':'}
+ JSON_LBRACE = []byte{'{'}
+ JSON_RBRACE = []byte{'}'}
+ JSON_LBRACKET = []byte{'['}
+ JSON_RBRACKET = []byte{']'}
+ JSON_QUOTE = '"'
+ JSON_QUOTE_BYTES = []byte{'"'}
+ JSON_NULL = []byte{'n', 'u', 'l', 'l'}
+ JSON_TRUE = []byte{'t', 'r', 'u', 'e'}
+ JSON_FALSE = []byte{'f', 'a', 'l', 's', 'e'}
+ JSON_INFINITY = "Infinity"
+ JSON_NEGATIVE_INFINITY = "-Infinity"
+ JSON_NAN = "NaN"
+ JSON_INFINITY_BYTES = []byte{'I', 'n', 'f', 'i', 'n', 'i', 't', 'y'}
+ JSON_NEGATIVE_INFINITY_BYTES = []byte{'-', 'I', 'n', 'f', 'i', 'n', 'i', 't', 'y'}
+ JSON_NAN_BYTES = []byte{'N', 'a', 'N'}
+ json_nonbase_map_elem_bytes = []byte{']', ',', '['}
+}
+
+func jsonQuote(s string) string {
+ b, _ := json.Marshal(s)
+ s1 := string(b)
+ return s1
+}
+
+func jsonUnquote(s string) (string, bool) {
+ s1 := new(string)
+ err := json.Unmarshal([]byte(s), s1)
+ return *s1, err == nil
+}
+
+func mismatch(expected, actual string) error {
+ return fmt.Errorf("Expected '%s' but found '%s' while parsing JSON.", expected, actual)
+}
+
+func (p *TSimpleJSONProtocol) WriteMessageBegin(name string, typeId TMessageType, seqId int32) error {
+ p.resetContextStack() // THRIFT-3735
+ if e := p.OutputListBegin(); e != nil {
+ return e
+ }
+ if e := p.WriteString(name); e != nil {
+ return e
+ }
+ if e := p.WriteByte(int8(typeId)); e != nil {
+ return e
+ }
+ if e := p.WriteI32(seqId); e != nil {
+ return e
+ }
+ return nil
+}
+
+func (p *TSimpleJSONProtocol) WriteMessageEnd() error {
+ return p.OutputListEnd()
+}
+
+func (p *TSimpleJSONProtocol) WriteStructBegin(name string) error {
+ if e := p.OutputObjectBegin(); e != nil {
+ return e
+ }
+ return nil
+}
+
+func (p *TSimpleJSONProtocol) WriteStructEnd() error {
+ return p.OutputObjectEnd()
+}
+
+func (p *TSimpleJSONProtocol) WriteFieldBegin(name string, typeId TType, id int16) error {
+ if e := p.WriteString(name); e != nil {
+ return e
+ }
+ return nil
+}
+
+func (p *TSimpleJSONProtocol) WriteFieldEnd() error {
+ //return p.OutputListEnd()
+ return nil
+}
+
+func (p *TSimpleJSONProtocol) WriteFieldStop() error { return nil }
+
+func (p *TSimpleJSONProtocol) WriteMapBegin(keyType TType, valueType TType, size int) error {
+ if e := p.OutputListBegin(); e != nil {
+ return e
+ }
+ if e := p.WriteByte(int8(keyType)); e != nil {
+ return e
+ }
+ if e := p.WriteByte(int8(valueType)); e != nil {
+ return e
+ }
+ return p.WriteI32(int32(size))
+}
+
+func (p *TSimpleJSONProtocol) WriteMapEnd() error {
+ return p.OutputListEnd()
+}
+
+func (p *TSimpleJSONProtocol) WriteListBegin(elemType TType, size int) error {
+ return p.OutputElemListBegin(elemType, size)
+}
+
+func (p *TSimpleJSONProtocol) WriteListEnd() error {
+ return p.OutputListEnd()
+}
+
+func (p *TSimpleJSONProtocol) WriteSetBegin(elemType TType, size int) error {
+ return p.OutputElemListBegin(elemType, size)
+}
+
+func (p *TSimpleJSONProtocol) WriteSetEnd() error {
+ return p.OutputListEnd()
+}
+
+func (p *TSimpleJSONProtocol) WriteBool(b bool) error {
+ return p.OutputBool(b)
+}
+
+func (p *TSimpleJSONProtocol) WriteByte(b int8) error {
+ return p.WriteI32(int32(b))
+}
+
+func (p *TSimpleJSONProtocol) WriteI16(v int16) error {
+ return p.WriteI32(int32(v))
+}
+
+func (p *TSimpleJSONProtocol) WriteI32(v int32) error {
+ return p.OutputI64(int64(v))
+}
+
+func (p *TSimpleJSONProtocol) WriteI64(v int64) error {
+ return p.OutputI64(int64(v))
+}
+
+func (p *TSimpleJSONProtocol) WriteDouble(v float64) error {
+ return p.OutputF64(v)
+}
+
+func (p *TSimpleJSONProtocol) WriteString(v string) error {
+ return p.OutputString(v)
+}
+
+func (p *TSimpleJSONProtocol) WriteBinary(v []byte) error {
+ // JSON library only takes in a string,
+ // not an arbitrary byte array, to ensure bytes are transmitted
+ // efficiently we must convert this into a valid JSON string
+ // therefore we use base64 encoding to avoid excessive escaping/quoting
+ if e := p.OutputPreValue(); e != nil {
+ return e
+ }
+ if _, e := p.write(JSON_QUOTE_BYTES); e != nil {
+ return NewTProtocolException(e)
+ }
+ writer := base64.NewEncoder(base64.StdEncoding, p.writer)
+ if _, e := writer.Write(v); e != nil {
+ p.writer.Reset(p.trans) // THRIFT-3735
+ return NewTProtocolException(e)
+ }
+ if e := writer.Close(); e != nil {
+ return NewTProtocolException(e)
+ }
+ if _, e := p.write(JSON_QUOTE_BYTES); e != nil {
+ return NewTProtocolException(e)
+ }
+ return p.OutputPostValue()
+}
+
+// Reading methods.
+func (p *TSimpleJSONProtocol) ReadMessageBegin() (name string, typeId TMessageType, seqId int32, err error) {
+ p.resetContextStack() // THRIFT-3735
+ if isNull, err := p.ParseListBegin(); isNull || err != nil {
+ return name, typeId, seqId, err
+ }
+ if name, err = p.ReadString(); err != nil {
+ return name, typeId, seqId, err
+ }
+ bTypeId, err := p.ReadByte()
+ typeId = TMessageType(bTypeId)
+ if err != nil {
+ return name, typeId, seqId, err
+ }
+ if seqId, err = p.ReadI32(); err != nil {
+ return name, typeId, seqId, err
+ }
+ return name, typeId, seqId, nil
+}
+
+func (p *TSimpleJSONProtocol) ReadMessageEnd() error {
+ return p.ParseListEnd()
+}
+
+func (p *TSimpleJSONProtocol) ReadStructBegin() (name string, err error) {
+ _, err = p.ParseObjectStart()
+ return "", err
+}
+
+func (p *TSimpleJSONProtocol) ReadStructEnd() error {
+ return p.ParseObjectEnd()
+}
+
+func (p *TSimpleJSONProtocol) ReadFieldBegin() (string, TType, int16, error) {
+ if err := p.ParsePreValue(); err != nil {
+ return "", STOP, 0, err
+ }
+ b, _ := p.reader.Peek(1)
+ if len(b) > 0 {
+ switch b[0] {
+ case JSON_RBRACE[0]:
+ return "", STOP, 0, nil
+ case JSON_QUOTE:
+ p.reader.ReadByte()
+ name, err := p.ParseStringBody()
+ // simplejson is not meant to be read back into thrift
+ // - see http://wiki.apache.org/thrift/ThriftUsageJava
+ // - use JSON instead
+ if err != nil {
+ return name, STOP, 0, err
+ }
+ return name, STOP, -1, p.ParsePostValue()
+ /*
+ if err = p.ParsePostValue(); err != nil {
+ return name, STOP, 0, err
+ }
+ if isNull, err := p.ParseListBegin(); isNull || err != nil {
+ return name, STOP, 0, err
+ }
+ bType, err := p.ReadByte()
+ thetype := TType(bType)
+ if err != nil {
+ return name, thetype, 0, err
+ }
+ id, err := p.ReadI16()
+ return name, thetype, id, err
+ */
+ }
+ e := fmt.Errorf("Expected \"}\" or '\"', but found: '%s'", string(b))
+ return "", STOP, 0, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ return "", STOP, 0, NewTProtocolException(io.EOF)
+}
+
+func (p *TSimpleJSONProtocol) ReadFieldEnd() error {
+ return nil
+ //return p.ParseListEnd()
+}
+
+func (p *TSimpleJSONProtocol) ReadMapBegin() (keyType TType, valueType TType, size int, e error) {
+ if isNull, e := p.ParseListBegin(); isNull || e != nil {
+ return VOID, VOID, 0, e
+ }
+
+ // read keyType
+ bKeyType, e := p.ReadByte()
+ keyType = TType(bKeyType)
+ if e != nil {
+ return keyType, valueType, size, e
+ }
+
+ // read valueType
+ bValueType, e := p.ReadByte()
+ valueType = TType(bValueType)
+ if e != nil {
+ return keyType, valueType, size, e
+ }
+
+ // read size
+ iSize, err := p.ReadI64()
+ size = int(iSize)
+ return keyType, valueType, size, err
+}
+
+func (p *TSimpleJSONProtocol) ReadMapEnd() error {
+ return p.ParseListEnd()
+}
+
+func (p *TSimpleJSONProtocol) ReadListBegin() (elemType TType, size int, e error) {
+ return p.ParseElemListBegin()
+}
+
+func (p *TSimpleJSONProtocol) ReadListEnd() error {
+ return p.ParseListEnd()
+}
+
+func (p *TSimpleJSONProtocol) ReadSetBegin() (elemType TType, size int, e error) {
+ return p.ParseElemListBegin()
+}
+
+func (p *TSimpleJSONProtocol) ReadSetEnd() error {
+ return p.ParseListEnd()
+}
+
+func (p *TSimpleJSONProtocol) ReadBool() (bool, error) {
+ var value bool
+
+ if err := p.ParsePreValue(); err != nil {
+ return value, err
+ }
+ f, _ := p.reader.Peek(1)
+ if len(f) > 0 {
+ switch f[0] {
+ case JSON_TRUE[0]:
+ b := make([]byte, len(JSON_TRUE))
+ _, err := p.reader.Read(b)
+ if err != nil {
+ return false, NewTProtocolException(err)
+ }
+ if string(b) == string(JSON_TRUE) {
+ value = true
+ } else {
+ e := fmt.Errorf("Expected \"true\" but found: %s", string(b))
+ return value, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ break
+ case JSON_FALSE[0]:
+ b := make([]byte, len(JSON_FALSE))
+ _, err := p.reader.Read(b)
+ if err != nil {
+ return false, NewTProtocolException(err)
+ }
+ if string(b) == string(JSON_FALSE) {
+ value = false
+ } else {
+ e := fmt.Errorf("Expected \"false\" but found: %s", string(b))
+ return value, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ break
+ case JSON_NULL[0]:
+ b := make([]byte, len(JSON_NULL))
+ _, err := p.reader.Read(b)
+ if err != nil {
+ return false, NewTProtocolException(err)
+ }
+ if string(b) == string(JSON_NULL) {
+ value = false
+ } else {
+ e := fmt.Errorf("Expected \"null\" but found: %s", string(b))
+ return value, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ default:
+ e := fmt.Errorf("Expected \"true\", \"false\", or \"null\" but found: %s", string(f))
+ return value, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ }
+ return value, p.ParsePostValue()
+}
+
+func (p *TSimpleJSONProtocol) ReadByte() (int8, error) {
+ v, err := p.ReadI64()
+ return int8(v), err
+}
+
+func (p *TSimpleJSONProtocol) ReadI16() (int16, error) {
+ v, err := p.ReadI64()
+ return int16(v), err
+}
+
+func (p *TSimpleJSONProtocol) ReadI32() (int32, error) {
+ v, err := p.ReadI64()
+ return int32(v), err
+}
+
+func (p *TSimpleJSONProtocol) ReadI64() (int64, error) {
+ v, _, err := p.ParseI64()
+ return v, err
+}
+
+func (p *TSimpleJSONProtocol) ReadDouble() (float64, error) {
+ v, _, err := p.ParseF64()
+ return v, err
+}
+
+func (p *TSimpleJSONProtocol) ReadString() (string, error) {
+ var v string
+ if err := p.ParsePreValue(); err != nil {
+ return v, err
+ }
+ f, _ := p.reader.Peek(1)
+ if len(f) > 0 && f[0] == JSON_QUOTE {
+ p.reader.ReadByte()
+ value, err := p.ParseStringBody()
+ v = value
+ if err != nil {
+ return v, err
+ }
+ } else if len(f) > 0 && f[0] == JSON_NULL[0] {
+ b := make([]byte, len(JSON_NULL))
+ _, err := p.reader.Read(b)
+ if err != nil {
+ return v, NewTProtocolException(err)
+ }
+ if string(b) != string(JSON_NULL) {
+ e := fmt.Errorf("Expected a JSON string, found unquoted data started with %s", string(b))
+ return v, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ } else {
+ e := fmt.Errorf("Expected a JSON string, found unquoted data started with %s", string(f))
+ return v, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ return v, p.ParsePostValue()
+}
+
+func (p *TSimpleJSONProtocol) ReadBinary() ([]byte, error) {
+ var v []byte
+ if err := p.ParsePreValue(); err != nil {
+ return nil, err
+ }
+ f, _ := p.reader.Peek(1)
+ if len(f) > 0 && f[0] == JSON_QUOTE {
+ p.reader.ReadByte()
+ value, err := p.ParseBase64EncodedBody()
+ v = value
+ if err != nil {
+ return v, err
+ }
+ } else if len(f) > 0 && f[0] == JSON_NULL[0] {
+ b := make([]byte, len(JSON_NULL))
+ _, err := p.reader.Read(b)
+ if err != nil {
+ return v, NewTProtocolException(err)
+ }
+ if string(b) != string(JSON_NULL) {
+ e := fmt.Errorf("Expected a JSON string, found unquoted data started with %s", string(b))
+ return v, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ } else {
+ e := fmt.Errorf("Expected a JSON string, found unquoted data started with %s", string(f))
+ return v, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+
+ return v, p.ParsePostValue()
+}
+
+func (p *TSimpleJSONProtocol) Flush() (err error) {
+ return NewTProtocolException(p.writer.Flush())
+}
+
+func (p *TSimpleJSONProtocol) Skip(fieldType TType) (err error) {
+ return SkipDefaultDepth(p, fieldType)
+}
+
+func (p *TSimpleJSONProtocol) Transport() TTransport {
+ return p.trans
+}
+
+func (p *TSimpleJSONProtocol) OutputPreValue() error {
+ cxt := _ParseContext(p.dumpContext[len(p.dumpContext)-1])
+ switch cxt {
+ case _CONTEXT_IN_LIST, _CONTEXT_IN_OBJECT_NEXT_KEY:
+ if _, e := p.write(JSON_COMMA); e != nil {
+ return NewTProtocolException(e)
+ }
+ break
+ case _CONTEXT_IN_OBJECT_NEXT_VALUE:
+ if _, e := p.write(JSON_COLON); e != nil {
+ return NewTProtocolException(e)
+ }
+ break
+ }
+ return nil
+}
+
+func (p *TSimpleJSONProtocol) OutputPostValue() error {
+ cxt := _ParseContext(p.dumpContext[len(p.dumpContext)-1])
+ switch cxt {
+ case _CONTEXT_IN_LIST_FIRST:
+ p.dumpContext = p.dumpContext[:len(p.dumpContext)-1]
+ p.dumpContext = append(p.dumpContext, int(_CONTEXT_IN_LIST))
+ break
+ case _CONTEXT_IN_OBJECT_FIRST:
+ p.dumpContext = p.dumpContext[:len(p.dumpContext)-1]
+ p.dumpContext = append(p.dumpContext, int(_CONTEXT_IN_OBJECT_NEXT_VALUE))
+ break
+ case _CONTEXT_IN_OBJECT_NEXT_KEY:
+ p.dumpContext = p.dumpContext[:len(p.dumpContext)-1]
+ p.dumpContext = append(p.dumpContext, int(_CONTEXT_IN_OBJECT_NEXT_VALUE))
+ break
+ case _CONTEXT_IN_OBJECT_NEXT_VALUE:
+ p.dumpContext = p.dumpContext[:len(p.dumpContext)-1]
+ p.dumpContext = append(p.dumpContext, int(_CONTEXT_IN_OBJECT_NEXT_KEY))
+ break
+ }
+ return nil
+}
+
+func (p *TSimpleJSONProtocol) OutputBool(value bool) error {
+ if e := p.OutputPreValue(); e != nil {
+ return e
+ }
+ var v string
+ if value {
+ v = string(JSON_TRUE)
+ } else {
+ v = string(JSON_FALSE)
+ }
+ switch _ParseContext(p.dumpContext[len(p.dumpContext)-1]) {
+ case _CONTEXT_IN_OBJECT_FIRST, _CONTEXT_IN_OBJECT_NEXT_KEY:
+ v = jsonQuote(v)
+ default:
+ }
+ if e := p.OutputStringData(v); e != nil {
+ return e
+ }
+ return p.OutputPostValue()
+}
+
+func (p *TSimpleJSONProtocol) OutputNull() error {
+ if e := p.OutputPreValue(); e != nil {
+ return e
+ }
+ if _, e := p.write(JSON_NULL); e != nil {
+ return NewTProtocolException(e)
+ }
+ return p.OutputPostValue()
+}
+
+func (p *TSimpleJSONProtocol) OutputF64(value float64) error {
+ if e := p.OutputPreValue(); e != nil {
+ return e
+ }
+ var v string
+ if math.IsNaN(value) {
+ v = string(JSON_QUOTE) + JSON_NAN + string(JSON_QUOTE)
+ } else if math.IsInf(value, 1) {
+ v = string(JSON_QUOTE) + JSON_INFINITY + string(JSON_QUOTE)
+ } else if math.IsInf(value, -1) {
+ v = string(JSON_QUOTE) + JSON_NEGATIVE_INFINITY + string(JSON_QUOTE)
+ } else {
+ v = strconv.FormatFloat(value, 'g', -1, 64)
+ switch _ParseContext(p.dumpContext[len(p.dumpContext)-1]) {
+ case _CONTEXT_IN_OBJECT_FIRST, _CONTEXT_IN_OBJECT_NEXT_KEY:
+ v = string(JSON_QUOTE) + v + string(JSON_QUOTE)
+ default:
+ }
+ }
+ if e := p.OutputStringData(v); e != nil {
+ return e
+ }
+ return p.OutputPostValue()
+}
+
+func (p *TSimpleJSONProtocol) OutputI64(value int64) error {
+ if e := p.OutputPreValue(); e != nil {
+ return e
+ }
+ v := strconv.FormatInt(value, 10)
+ switch _ParseContext(p.dumpContext[len(p.dumpContext)-1]) {
+ case _CONTEXT_IN_OBJECT_FIRST, _CONTEXT_IN_OBJECT_NEXT_KEY:
+ v = jsonQuote(v)
+ default:
+ }
+ if e := p.OutputStringData(v); e != nil {
+ return e
+ }
+ return p.OutputPostValue()
+}
+
+func (p *TSimpleJSONProtocol) OutputString(s string) error {
+ if e := p.OutputPreValue(); e != nil {
+ return e
+ }
+ if e := p.OutputStringData(jsonQuote(s)); e != nil {
+ return e
+ }
+ return p.OutputPostValue()
+}
+
+func (p *TSimpleJSONProtocol) OutputStringData(s string) error {
+ _, e := p.write([]byte(s))
+ return NewTProtocolException(e)
+}
+
+func (p *TSimpleJSONProtocol) OutputObjectBegin() error {
+ if e := p.OutputPreValue(); e != nil {
+ return e
+ }
+ if _, e := p.write(JSON_LBRACE); e != nil {
+ return NewTProtocolException(e)
+ }
+ p.dumpContext = append(p.dumpContext, int(_CONTEXT_IN_OBJECT_FIRST))
+ return nil
+}
+
+func (p *TSimpleJSONProtocol) OutputObjectEnd() error {
+ if _, e := p.write(JSON_RBRACE); e != nil {
+ return NewTProtocolException(e)
+ }
+ p.dumpContext = p.dumpContext[:len(p.dumpContext)-1]
+ if e := p.OutputPostValue(); e != nil {
+ return e
+ }
+ return nil
+}
+
+func (p *TSimpleJSONProtocol) OutputListBegin() error {
+ if e := p.OutputPreValue(); e != nil {
+ return e
+ }
+ if _, e := p.write(JSON_LBRACKET); e != nil {
+ return NewTProtocolException(e)
+ }
+ p.dumpContext = append(p.dumpContext, int(_CONTEXT_IN_LIST_FIRST))
+ return nil
+}
+
+func (p *TSimpleJSONProtocol) OutputListEnd() error {
+ if _, e := p.write(JSON_RBRACKET); e != nil {
+ return NewTProtocolException(e)
+ }
+ p.dumpContext = p.dumpContext[:len(p.dumpContext)-1]
+ if e := p.OutputPostValue(); e != nil {
+ return e
+ }
+ return nil
+}
+
+func (p *TSimpleJSONProtocol) OutputElemListBegin(elemType TType, size int) error {
+ if e := p.OutputListBegin(); e != nil {
+ return e
+ }
+ if e := p.WriteByte(int8(elemType)); e != nil {
+ return e
+ }
+ if e := p.WriteI64(int64(size)); e != nil {
+ return e
+ }
+ return nil
+}
+
+func (p *TSimpleJSONProtocol) ParsePreValue() error {
+ if e := p.readNonSignificantWhitespace(); e != nil {
+ return NewTProtocolException(e)
+ }
+ cxt := _ParseContext(p.parseContextStack[len(p.parseContextStack)-1])
+ b, _ := p.reader.Peek(1)
+ switch cxt {
+ case _CONTEXT_IN_LIST:
+ if len(b) > 0 {
+ switch b[0] {
+ case JSON_RBRACKET[0]:
+ return nil
+ case JSON_COMMA[0]:
+ p.reader.ReadByte()
+ if e := p.readNonSignificantWhitespace(); e != nil {
+ return NewTProtocolException(e)
+ }
+ return nil
+ default:
+ e := fmt.Errorf("Expected \"]\" or \",\" in list context, but found \"%s\"", string(b))
+ return NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ }
+ break
+ case _CONTEXT_IN_OBJECT_NEXT_KEY:
+ if len(b) > 0 {
+ switch b[0] {
+ case JSON_RBRACE[0]:
+ return nil
+ case JSON_COMMA[0]:
+ p.reader.ReadByte()
+ if e := p.readNonSignificantWhitespace(); e != nil {
+ return NewTProtocolException(e)
+ }
+ return nil
+ default:
+ e := fmt.Errorf("Expected \"}\" or \",\" in object context, but found \"%s\"", string(b))
+ return NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ }
+ break
+ case _CONTEXT_IN_OBJECT_NEXT_VALUE:
+ if len(b) > 0 {
+ switch b[0] {
+ case JSON_COLON[0]:
+ p.reader.ReadByte()
+ if e := p.readNonSignificantWhitespace(); e != nil {
+ return NewTProtocolException(e)
+ }
+ return nil
+ default:
+ e := fmt.Errorf("Expected \":\" in object context, but found \"%s\"", string(b))
+ return NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ }
+ break
+ }
+ return nil
+}
+
+func (p *TSimpleJSONProtocol) ParsePostValue() error {
+ if e := p.readNonSignificantWhitespace(); e != nil {
+ return NewTProtocolException(e)
+ }
+ cxt := _ParseContext(p.parseContextStack[len(p.parseContextStack)-1])
+ switch cxt {
+ case _CONTEXT_IN_LIST_FIRST:
+ p.parseContextStack = p.parseContextStack[:len(p.parseContextStack)-1]
+ p.parseContextStack = append(p.parseContextStack, int(_CONTEXT_IN_LIST))
+ break
+ case _CONTEXT_IN_OBJECT_FIRST, _CONTEXT_IN_OBJECT_NEXT_KEY:
+ p.parseContextStack = p.parseContextStack[:len(p.parseContextStack)-1]
+ p.parseContextStack = append(p.parseContextStack, int(_CONTEXT_IN_OBJECT_NEXT_VALUE))
+ break
+ case _CONTEXT_IN_OBJECT_NEXT_VALUE:
+ p.parseContextStack = p.parseContextStack[:len(p.parseContextStack)-1]
+ p.parseContextStack = append(p.parseContextStack, int(_CONTEXT_IN_OBJECT_NEXT_KEY))
+ break
+ }
+ return nil
+}
+
+func (p *TSimpleJSONProtocol) readNonSignificantWhitespace() error {
+ for {
+ b, _ := p.reader.Peek(1)
+ if len(b) < 1 {
+ return nil
+ }
+ switch b[0] {
+ case ' ', '\r', '\n', '\t':
+ p.reader.ReadByte()
+ continue
+ default:
+ break
+ }
+ break
+ }
+ return nil
+}
+
+func (p *TSimpleJSONProtocol) ParseStringBody() (string, error) {
+ line, err := p.reader.ReadString(JSON_QUOTE)
+ if err != nil {
+ return "", NewTProtocolException(err)
+ }
+ l := len(line)
+ // count number of escapes to see if we need to keep going
+ i := 1
+ for ; i < l; i++ {
+ if line[l-i-1] != '\\' {
+ break
+ }
+ }
+ if i&0x01 == 1 {
+ v, ok := jsonUnquote(string(JSON_QUOTE) + line)
+ if !ok {
+ return "", NewTProtocolException(err)
+ }
+ return v, nil
+ }
+ s, err := p.ParseQuotedStringBody()
+ if err != nil {
+ return "", NewTProtocolException(err)
+ }
+ str := string(JSON_QUOTE) + line + s
+ v, ok := jsonUnquote(str)
+ if !ok {
+ e := fmt.Errorf("Unable to parse as JSON string %s", str)
+ return "", NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ return v, nil
+}
+
+func (p *TSimpleJSONProtocol) ParseQuotedStringBody() (string, error) {
+ line, err := p.reader.ReadString(JSON_QUOTE)
+ if err != nil {
+ return "", NewTProtocolException(err)
+ }
+ l := len(line)
+ // count number of escapes to see if we need to keep going
+ i := 1
+ for ; i < l; i++ {
+ if line[l-i-1] != '\\' {
+ break
+ }
+ }
+ if i&0x01 == 1 {
+ return line, nil
+ }
+ s, err := p.ParseQuotedStringBody()
+ if err != nil {
+ return "", NewTProtocolException(err)
+ }
+ v := line + s
+ return v, nil
+}
+
+func (p *TSimpleJSONProtocol) ParseBase64EncodedBody() ([]byte, error) {
+ line, err := p.reader.ReadBytes(JSON_QUOTE)
+ if err != nil {
+ return line, NewTProtocolException(err)
+ }
+ line2 := line[0 : len(line)-1]
+ l := len(line2)
+ if (l % 4) != 0 {
+ pad := 4 - (l % 4)
+ fill := [...]byte{'=', '=', '='}
+ line2 = append(line2, fill[:pad]...)
+ l = len(line2)
+ }
+ output := make([]byte, base64.StdEncoding.DecodedLen(l))
+ n, err := base64.StdEncoding.Decode(output, line2)
+ return output[0:n], NewTProtocolException(err)
+}
+
+func (p *TSimpleJSONProtocol) ParseI64() (int64, bool, error) {
+ if err := p.ParsePreValue(); err != nil {
+ return 0, false, err
+ }
+ var value int64
+ var isnull bool
+ if p.safePeekContains(JSON_NULL) {
+ p.reader.Read(make([]byte, len(JSON_NULL)))
+ isnull = true
+ } else {
+ num, err := p.readNumeric()
+ isnull = (num == nil)
+ if !isnull {
+ value = num.Int64()
+ }
+ if err != nil {
+ return value, isnull, err
+ }
+ }
+ return value, isnull, p.ParsePostValue()
+}
+
+func (p *TSimpleJSONProtocol) ParseF64() (float64, bool, error) {
+ if err := p.ParsePreValue(); err != nil {
+ return 0, false, err
+ }
+ var value float64
+ var isnull bool
+ if p.safePeekContains(JSON_NULL) {
+ p.reader.Read(make([]byte, len(JSON_NULL)))
+ isnull = true
+ } else {
+ num, err := p.readNumeric()
+ isnull = (num == nil)
+ if !isnull {
+ value = num.Float64()
+ }
+ if err != nil {
+ return value, isnull, err
+ }
+ }
+ return value, isnull, p.ParsePostValue()
+}
+
+func (p *TSimpleJSONProtocol) ParseObjectStart() (bool, error) {
+ if err := p.ParsePreValue(); err != nil {
+ return false, err
+ }
+ var b []byte
+ b, err := p.reader.Peek(1)
+ if err != nil {
+ return false, err
+ }
+ if len(b) > 0 && b[0] == JSON_LBRACE[0] {
+ p.reader.ReadByte()
+ p.parseContextStack = append(p.parseContextStack, int(_CONTEXT_IN_OBJECT_FIRST))
+ return false, nil
+ } else if p.safePeekContains(JSON_NULL) {
+ return true, nil
+ }
+ e := fmt.Errorf("Expected '{' or null, but found '%s'", string(b))
+ return false, NewTProtocolExceptionWithType(INVALID_DATA, e)
+}
+
+func (p *TSimpleJSONProtocol) ParseObjectEnd() error {
+ if isNull, err := p.readIfNull(); isNull || err != nil {
+ return err
+ }
+ cxt := _ParseContext(p.parseContextStack[len(p.parseContextStack)-1])
+ if (cxt != _CONTEXT_IN_OBJECT_FIRST) && (cxt != _CONTEXT_IN_OBJECT_NEXT_KEY) {
+ e := fmt.Errorf("Expected to be in the Object Context, but not in Object Context (%d)", cxt)
+ return NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ line, err := p.reader.ReadString(JSON_RBRACE[0])
+ if err != nil {
+ return NewTProtocolException(err)
+ }
+ for _, char := range line {
+ switch char {
+ default:
+ e := fmt.Errorf("Expecting end of object \"}\", but found: \"%s\"", line)
+ return NewTProtocolExceptionWithType(INVALID_DATA, e)
+ case ' ', '\n', '\r', '\t', '}':
+ break
+ }
+ }
+ p.parseContextStack = p.parseContextStack[:len(p.parseContextStack)-1]
+ return p.ParsePostValue()
+}
+
+func (p *TSimpleJSONProtocol) ParseListBegin() (isNull bool, err error) {
+ if e := p.ParsePreValue(); e != nil {
+ return false, e
+ }
+ var b []byte
+ b, err = p.reader.Peek(1)
+ if err != nil {
+ return false, err
+ }
+ if len(b) >= 1 && b[0] == JSON_LBRACKET[0] {
+ p.parseContextStack = append(p.parseContextStack, int(_CONTEXT_IN_LIST_FIRST))
+ p.reader.ReadByte()
+ isNull = false
+ } else if p.safePeekContains(JSON_NULL) {
+ isNull = true
+ } else {
+ err = fmt.Errorf("Expected \"null\" or \"[\", received %q", b)
+ }
+ return isNull, NewTProtocolExceptionWithType(INVALID_DATA, err)
+}
+
+func (p *TSimpleJSONProtocol) ParseElemListBegin() (elemType TType, size int, e error) {
+ if isNull, e := p.ParseListBegin(); isNull || e != nil {
+ return VOID, 0, e
+ }
+ bElemType, err := p.ReadByte()
+ elemType = TType(bElemType)
+ if err != nil {
+ return elemType, size, err
+ }
+ nSize, err2 := p.ReadI64()
+ size = int(nSize)
+ return elemType, size, err2
+}
+
+func (p *TSimpleJSONProtocol) ParseListEnd() error {
+ if isNull, err := p.readIfNull(); isNull || err != nil {
+ return err
+ }
+ cxt := _ParseContext(p.parseContextStack[len(p.parseContextStack)-1])
+ if cxt != _CONTEXT_IN_LIST {
+ e := fmt.Errorf("Expected to be in the List Context, but not in List Context (%d)", cxt)
+ return NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ line, err := p.reader.ReadString(JSON_RBRACKET[0])
+ if err != nil {
+ return NewTProtocolException(err)
+ }
+ for _, char := range line {
+ switch char {
+ default:
+ e := fmt.Errorf("Expecting end of list \"]\", but found: \"%s\"", line)
+ return NewTProtocolExceptionWithType(INVALID_DATA, e)
+ case ' ', '\n', '\r', '\t', rune(JSON_RBRACKET[0]):
+ break
+ }
+ }
+ p.parseContextStack = p.parseContextStack[:len(p.parseContextStack)-1]
+ if _ParseContext(p.parseContextStack[len(p.parseContextStack)-1]) == _CONTEXT_IN_TOPLEVEL {
+ return nil
+ }
+ return p.ParsePostValue()
+}
+
+func (p *TSimpleJSONProtocol) readSingleValue() (interface{}, TType, error) {
+ e := p.readNonSignificantWhitespace()
+ if e != nil {
+ return nil, VOID, NewTProtocolException(e)
+ }
+ b, e := p.reader.Peek(1)
+ if len(b) > 0 {
+ c := b[0]
+ switch c {
+ case JSON_NULL[0]:
+ buf := make([]byte, len(JSON_NULL))
+ _, e := p.reader.Read(buf)
+ if e != nil {
+ return nil, VOID, NewTProtocolException(e)
+ }
+ if string(JSON_NULL) != string(buf) {
+ e = mismatch(string(JSON_NULL), string(buf))
+ return nil, VOID, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ return nil, VOID, nil
+ case JSON_QUOTE:
+ p.reader.ReadByte()
+ v, e := p.ParseStringBody()
+ if e != nil {
+ return v, UTF8, NewTProtocolException(e)
+ }
+ if v == JSON_INFINITY {
+ return INFINITY, DOUBLE, nil
+ } else if v == JSON_NEGATIVE_INFINITY {
+ return NEGATIVE_INFINITY, DOUBLE, nil
+ } else if v == JSON_NAN {
+ return NAN, DOUBLE, nil
+ }
+ return v, UTF8, nil
+ case JSON_TRUE[0]:
+ buf := make([]byte, len(JSON_TRUE))
+ _, e := p.reader.Read(buf)
+ if e != nil {
+ return true, BOOL, NewTProtocolException(e)
+ }
+ if string(JSON_TRUE) != string(buf) {
+ e := mismatch(string(JSON_TRUE), string(buf))
+ return true, BOOL, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ return true, BOOL, nil
+ case JSON_FALSE[0]:
+ buf := make([]byte, len(JSON_FALSE))
+ _, e := p.reader.Read(buf)
+ if e != nil {
+ return false, BOOL, NewTProtocolException(e)
+ }
+ if string(JSON_FALSE) != string(buf) {
+ e := mismatch(string(JSON_FALSE), string(buf))
+ return false, BOOL, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ return false, BOOL, nil
+ case JSON_LBRACKET[0]:
+ _, e := p.reader.ReadByte()
+ return make([]interface{}, 0), LIST, NewTProtocolException(e)
+ case JSON_LBRACE[0]:
+ _, e := p.reader.ReadByte()
+ return make(map[string]interface{}), STRUCT, NewTProtocolException(e)
+ case '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'e', 'E', '.', '+', '-', JSON_INFINITY[0], JSON_NAN[0]:
+ // assume numeric
+ v, e := p.readNumeric()
+ return v, DOUBLE, e
+ default:
+ e := fmt.Errorf("Expected element in list but found '%s' while parsing JSON.", string(c))
+ return nil, VOID, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ }
+ e = fmt.Errorf("Cannot read a single element while parsing JSON.")
+ return nil, VOID, NewTProtocolExceptionWithType(INVALID_DATA, e)
+
+}
+
+func (p *TSimpleJSONProtocol) readIfNull() (bool, error) {
+ cont := true
+ for cont {
+ b, _ := p.reader.Peek(1)
+ if len(b) < 1 {
+ return false, nil
+ }
+ switch b[0] {
+ default:
+ return false, nil
+ case JSON_NULL[0]:
+ cont = false
+ break
+ case ' ', '\n', '\r', '\t':
+ p.reader.ReadByte()
+ break
+ }
+ }
+ if p.safePeekContains(JSON_NULL) {
+ p.reader.Read(make([]byte, len(JSON_NULL)))
+ return true, nil
+ }
+ return false, nil
+}
+
+func (p *TSimpleJSONProtocol) readQuoteIfNext() {
+ b, _ := p.reader.Peek(1)
+ if len(b) > 0 && b[0] == JSON_QUOTE {
+ p.reader.ReadByte()
+ }
+}
+
+func (p *TSimpleJSONProtocol) readNumeric() (Numeric, error) {
+ isNull, err := p.readIfNull()
+ if isNull || err != nil {
+ return NUMERIC_NULL, err
+ }
+ hasDecimalPoint := false
+ nextCanBeSign := true
+ hasE := false
+ MAX_LEN := 40
+ buf := bytes.NewBuffer(make([]byte, 0, MAX_LEN))
+ continueFor := true
+ inQuotes := false
+ for continueFor {
+ c, err := p.reader.ReadByte()
+ if err != nil {
+ if err == io.EOF {
+ break
+ }
+ return NUMERIC_NULL, NewTProtocolException(err)
+ }
+ switch c {
+ case '0', '1', '2', '3', '4', '5', '6', '7', '8', '9':
+ buf.WriteByte(c)
+ nextCanBeSign = false
+ case '.':
+ if hasDecimalPoint {
+ e := fmt.Errorf("Unable to parse number with multiple decimal points '%s.'", buf.String())
+ return NUMERIC_NULL, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ if hasE {
+ e := fmt.Errorf("Unable to parse number with decimal points in the exponent '%s.'", buf.String())
+ return NUMERIC_NULL, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ buf.WriteByte(c)
+ hasDecimalPoint, nextCanBeSign = true, false
+ case 'e', 'E':
+ if hasE {
+ e := fmt.Errorf("Unable to parse number with multiple exponents '%s%c'", buf.String(), c)
+ return NUMERIC_NULL, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ buf.WriteByte(c)
+ hasE, nextCanBeSign = true, true
+ case '-', '+':
+ if !nextCanBeSign {
+ e := fmt.Errorf("Negative sign within number")
+ return NUMERIC_NULL, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ buf.WriteByte(c)
+ nextCanBeSign = false
+ case ' ', 0, '\t', '\n', '\r', JSON_RBRACE[0], JSON_RBRACKET[0], JSON_COMMA[0], JSON_COLON[0]:
+ p.reader.UnreadByte()
+ continueFor = false
+ case JSON_NAN[0]:
+ if buf.Len() == 0 {
+ buffer := make([]byte, len(JSON_NAN))
+ buffer[0] = c
+ _, e := p.reader.Read(buffer[1:])
+ if e != nil {
+ return NUMERIC_NULL, NewTProtocolException(e)
+ }
+ if JSON_NAN != string(buffer) {
+ e := mismatch(JSON_NAN, string(buffer))
+ return NUMERIC_NULL, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ if inQuotes {
+ p.readQuoteIfNext()
+ }
+ return NAN, nil
+ } else {
+ e := fmt.Errorf("Unable to parse number starting with character '%c'", c)
+ return NUMERIC_NULL, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ case JSON_INFINITY[0]:
+ if buf.Len() == 0 || (buf.Len() == 1 && buf.Bytes()[0] == '+') {
+ buffer := make([]byte, len(JSON_INFINITY))
+ buffer[0] = c
+ _, e := p.reader.Read(buffer[1:])
+ if e != nil {
+ return NUMERIC_NULL, NewTProtocolException(e)
+ }
+ if JSON_INFINITY != string(buffer) {
+ e := mismatch(JSON_INFINITY, string(buffer))
+ return NUMERIC_NULL, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ if inQuotes {
+ p.readQuoteIfNext()
+ }
+ return INFINITY, nil
+ } else if buf.Len() == 1 && buf.Bytes()[0] == JSON_NEGATIVE_INFINITY[0] {
+ buffer := make([]byte, len(JSON_NEGATIVE_INFINITY))
+ buffer[0] = JSON_NEGATIVE_INFINITY[0]
+ buffer[1] = c
+ _, e := p.reader.Read(buffer[2:])
+ if e != nil {
+ return NUMERIC_NULL, NewTProtocolException(e)
+ }
+ if JSON_NEGATIVE_INFINITY != string(buffer) {
+ e := mismatch(JSON_NEGATIVE_INFINITY, string(buffer))
+ return NUMERIC_NULL, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ if inQuotes {
+ p.readQuoteIfNext()
+ }
+ return NEGATIVE_INFINITY, nil
+ } else {
+ e := fmt.Errorf("Unable to parse number starting with character '%c' due to existing buffer %s", c, buf.String())
+ return NUMERIC_NULL, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ case JSON_QUOTE:
+ if !inQuotes {
+ inQuotes = true
+ } else {
+ break
+ }
+ default:
+ e := fmt.Errorf("Unable to parse number starting with character '%c'", c)
+ return NUMERIC_NULL, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ }
+ if buf.Len() == 0 {
+ e := fmt.Errorf("Unable to parse number from empty string ''")
+ return NUMERIC_NULL, NewTProtocolExceptionWithType(INVALID_DATA, e)
+ }
+ return NewNumericFromJSONString(buf.String(), false), nil
+}
+
+// Safely peeks into the buffer, reading only what is necessary
+func (p *TSimpleJSONProtocol) safePeekContains(b []byte) bool {
+ for i := 0; i < len(b); i++ {
+ a, _ := p.reader.Peek(i + 1)
+ if len(a) == 0 || a[i] != b[i] {
+ return false
+ }
+ }
+ return true
+}
+
+// Reset the context stack to its initial state.
+func (p *TSimpleJSONProtocol) resetContextStack() {
+ p.parseContextStack = []int{int(_CONTEXT_IN_TOPLEVEL)}
+ p.dumpContext = []int{int(_CONTEXT_IN_TOPLEVEL)}
+}
+
+func (p *TSimpleJSONProtocol) write(b []byte) (int, error) {
+ n, err := p.writer.Write(b)
+ if err != nil {
+ p.writer.Reset(p.trans) // THRIFT-3735
+ }
+ return n, err
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/thrift/transport.go b/vendor/github.com/uber/jaeger-client-go/thrift/transport.go
new file mode 100644
index 000000000..453899651
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/thrift/transport.go
@@ -0,0 +1,68 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+import (
+ "errors"
+ "io"
+)
+
+var errTransportInterrupted = errors.New("Transport Interrupted")
+
+type Flusher interface {
+ Flush() (err error)
+}
+
+type ReadSizeProvider interface {
+ RemainingBytes() (num_bytes uint64)
+}
+
+
+// Encapsulates the I/O layer
+type TTransport interface {
+ io.ReadWriteCloser
+ Flusher
+ ReadSizeProvider
+
+ // Opens the transport for communication
+ Open() error
+
+ // Returns true if the transport is open
+ IsOpen() bool
+}
+
+type stringWriter interface {
+ WriteString(s string) (n int, err error)
+}
+
+
+// This is "enchanced" transport with extra capabilities. You need to use one of these
+// to construct protocol.
+// Notably, TSocket does not implement this interface, and it is always a mistake to use
+// TSocket directly in protocol.
+type TRichTransport interface {
+ io.ReadWriter
+ io.ByteReader
+ io.ByteWriter
+ stringWriter
+ Flusher
+ ReadSizeProvider
+}
+
diff --git a/vendor/github.com/uber/jaeger-client-go/thrift/transport_exception.go b/vendor/github.com/uber/jaeger-client-go/thrift/transport_exception.go
new file mode 100644
index 000000000..9505b4461
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/thrift/transport_exception.go
@@ -0,0 +1,90 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+import (
+ "errors"
+ "io"
+)
+
+type timeoutable interface {
+ Timeout() bool
+}
+
+// Thrift Transport exception
+type TTransportException interface {
+ TException
+ TypeId() int
+ Err() error
+}
+
+const (
+ UNKNOWN_TRANSPORT_EXCEPTION = 0
+ NOT_OPEN = 1
+ ALREADY_OPEN = 2
+ TIMED_OUT = 3
+ END_OF_FILE = 4
+)
+
+type tTransportException struct {
+ typeId int
+ err error
+}
+
+func (p *tTransportException) TypeId() int {
+ return p.typeId
+}
+
+func (p *tTransportException) Error() string {
+ return p.err.Error()
+}
+
+func (p *tTransportException) Err() error {
+ return p.err
+}
+
+func NewTTransportException(t int, e string) TTransportException {
+ return &tTransportException{typeId: t, err: errors.New(e)}
+}
+
+func NewTTransportExceptionFromError(e error) TTransportException {
+ if e == nil {
+ return nil
+ }
+
+ if t, ok := e.(TTransportException); ok {
+ return t
+ }
+
+ switch v := e.(type) {
+ case TTransportException:
+ return v
+ case timeoutable:
+ if v.Timeout() {
+ return &tTransportException{typeId: TIMED_OUT, err: e}
+ }
+ }
+
+ if e == io.EOF {
+ return &tTransportException{typeId: END_OF_FILE, err: e}
+ }
+
+ return &tTransportException{typeId: UNKNOWN_TRANSPORT_EXCEPTION, err: e}
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/thrift/transport_factory.go b/vendor/github.com/uber/jaeger-client-go/thrift/transport_factory.go
new file mode 100644
index 000000000..533d1b437
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/thrift/transport_factory.go
@@ -0,0 +1,39 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+// Factory class used to create wrapped instance of Transports.
+// This is used primarily in servers, which get Transports from
+// a ServerTransport and then may want to mutate them (i.e. create
+// a BufferedTransport from the underlying base transport)
+type TTransportFactory interface {
+ GetTransport(trans TTransport) TTransport
+}
+
+type tTransportFactory struct{}
+
+// Return a wrapped instance of the base Transport.
+func (p *tTransportFactory) GetTransport(trans TTransport) TTransport {
+ return trans
+}
+
+func NewTTransportFactory() TTransportFactory {
+ return &tTransportFactory{}
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/thrift/type.go b/vendor/github.com/uber/jaeger-client-go/thrift/type.go
new file mode 100644
index 000000000..4292ffcad
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/thrift/type.go
@@ -0,0 +1,69 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.
+ */
+
+package thrift
+
+// Type constants in the Thrift protocol
+type TType byte
+
+const (
+ STOP = 0
+ VOID = 1
+ BOOL = 2
+ BYTE = 3
+ I08 = 3
+ DOUBLE = 4
+ I16 = 6
+ I32 = 8
+ I64 = 10
+ STRING = 11
+ UTF7 = 11
+ STRUCT = 12
+ MAP = 13
+ SET = 14
+ LIST = 15
+ UTF8 = 16
+ UTF16 = 17
+ //BINARY = 18 wrong and unusued
+)
+
+var typeNames = map[int]string{
+ STOP: "STOP",
+ VOID: "VOID",
+ BOOL: "BOOL",
+ BYTE: "BYTE",
+ DOUBLE: "DOUBLE",
+ I16: "I16",
+ I32: "I32",
+ I64: "I64",
+ STRING: "STRING",
+ STRUCT: "STRUCT",
+ MAP: "MAP",
+ SET: "SET",
+ LIST: "LIST",
+ UTF8: "UTF8",
+ UTF16: "UTF16",
+}
+
+func (p TType) String() string {
+ if s, ok := typeNames[int(p)]; ok {
+ return s
+ }
+ return "Unknown"
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/tracer.go b/vendor/github.com/uber/jaeger-client-go/tracer.go
new file mode 100644
index 000000000..198c32eb4
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/tracer.go
@@ -0,0 +1,431 @@
+// Copyright (c) 2017-2018 Uber Technologies, Inc.
+//
+// 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.
+
+package jaeger
+
+import (
+ "fmt"
+ "io"
+ "os"
+ "reflect"
+ "strconv"
+ "sync"
+ "time"
+
+ "github.com/opentracing/opentracing-go"
+ "github.com/opentracing/opentracing-go/ext"
+
+ "github.com/uber/jaeger-client-go/internal/baggage"
+ "github.com/uber/jaeger-client-go/internal/throttler"
+ "github.com/uber/jaeger-client-go/log"
+ "github.com/uber/jaeger-client-go/utils"
+)
+
+// Tracer implements opentracing.Tracer.
+type Tracer struct {
+ serviceName string
+ hostIPv4 uint32 // this is for zipkin endpoint conversion
+
+ sampler Sampler
+ reporter Reporter
+ metrics Metrics
+ logger log.Logger
+
+ timeNow func() time.Time
+ randomNumber func() uint64
+
+ options struct {
+ poolSpans bool
+ gen128Bit bool // whether to generate 128bit trace IDs
+ zipkinSharedRPCSpan bool
+ highTraceIDGenerator func() uint64 // custom high trace ID generator
+ maxTagValueLength int
+ // more options to come
+ }
+ // pool for Span objects
+ spanPool sync.Pool
+
+ injectors map[interface{}]Injector
+ extractors map[interface{}]Extractor
+
+ observer compositeObserver
+
+ tags []Tag
+ process Process
+
+ baggageRestrictionManager baggage.RestrictionManager
+ baggageSetter *baggageSetter
+
+ debugThrottler throttler.Throttler
+}
+
+// NewTracer creates Tracer implementation that reports tracing to Jaeger.
+// The returned io.Closer can be used in shutdown hooks to ensure that the internal
+// queue of the Reporter is drained and all buffered spans are submitted to collectors.
+func NewTracer(
+ serviceName string,
+ sampler Sampler,
+ reporter Reporter,
+ options ...TracerOption,
+) (opentracing.Tracer, io.Closer) {
+ t := &Tracer{
+ serviceName: serviceName,
+ sampler: sampler,
+ reporter: reporter,
+ injectors: make(map[interface{}]Injector),
+ extractors: make(map[interface{}]Extractor),
+ metrics: *NewNullMetrics(),
+ spanPool: sync.Pool{New: func() interface{} {
+ return &Span{}
+ }},
+ }
+
+ for _, option := range options {
+ option(t)
+ }
+
+ // register default injectors/extractors unless they are already provided via options
+ textPropagator := newTextMapPropagator(getDefaultHeadersConfig(), t.metrics)
+ t.addCodec(opentracing.TextMap, textPropagator, textPropagator)
+
+ httpHeaderPropagator := newHTTPHeaderPropagator(getDefaultHeadersConfig(), t.metrics)
+ t.addCodec(opentracing.HTTPHeaders, httpHeaderPropagator, httpHeaderPropagator)
+
+ binaryPropagator := newBinaryPropagator(t)
+ t.addCodec(opentracing.Binary, binaryPropagator, binaryPropagator)
+
+ // TODO remove after TChannel supports OpenTracing
+ interopPropagator := &jaegerTraceContextPropagator{tracer: t}
+ t.addCodec(SpanContextFormat, interopPropagator, interopPropagator)
+
+ zipkinPropagator := &zipkinPropagator{tracer: t}
+ t.addCodec(ZipkinSpanFormat, zipkinPropagator, zipkinPropagator)
+
+ if t.baggageRestrictionManager != nil {
+ t.baggageSetter = newBaggageSetter(t.baggageRestrictionManager, &t.metrics)
+ } else {
+ t.baggageSetter = newBaggageSetter(baggage.NewDefaultRestrictionManager(0), &t.metrics)
+ }
+ if t.debugThrottler == nil {
+ t.debugThrottler = throttler.DefaultThrottler{}
+ }
+
+ if t.randomNumber == nil {
+ rng := utils.NewRand(time.Now().UnixNano())
+ t.randomNumber = func() uint64 {
+ return uint64(rng.Int63())
+ }
+ }
+ if t.timeNow == nil {
+ t.timeNow = time.Now
+ }
+ if t.logger == nil {
+ t.logger = log.NullLogger
+ }
+ // Set tracer-level tags
+ t.tags = append(t.tags, Tag{key: JaegerClientVersionTagKey, value: JaegerClientVersion})
+ if hostname, err := os.Hostname(); err == nil {
+ t.tags = append(t.tags, Tag{key: TracerHostnameTagKey, value: hostname})
+ }
+ if ip, err := utils.HostIP(); err == nil {
+ t.tags = append(t.tags, Tag{key: TracerIPTagKey, value: ip.String()})
+ t.hostIPv4 = utils.PackIPAsUint32(ip)
+ } else {
+ t.logger.Error("Unable to determine this host's IP address: " + err.Error())
+ }
+
+ if t.options.gen128Bit {
+ if t.options.highTraceIDGenerator == nil {
+ t.options.highTraceIDGenerator = t.randomNumber
+ }
+ } else if t.options.highTraceIDGenerator != nil {
+ t.logger.Error("Overriding high trace ID generator but not generating " +
+ "128 bit trace IDs, consider enabling the \"Gen128Bit\" option")
+ }
+ if t.options.maxTagValueLength == 0 {
+ t.options.maxTagValueLength = DefaultMaxTagValueLength
+ }
+ t.process = Process{
+ Service: serviceName,
+ UUID: strconv.FormatUint(t.randomNumber(), 16),
+ Tags: t.tags,
+ }
+ if throttler, ok := t.debugThrottler.(ProcessSetter); ok {
+ throttler.SetProcess(t.process)
+ }
+
+ return t, t
+}
+
+// addCodec adds registers injector and extractor for given propagation format if not already defined.
+func (t *Tracer) addCodec(format interface{}, injector Injector, extractor Extractor) {
+ if _, ok := t.injectors[format]; !ok {
+ t.injectors[format] = injector
+ }
+ if _, ok := t.extractors[format]; !ok {
+ t.extractors[format] = extractor
+ }
+}
+
+// StartSpan implements StartSpan() method of opentracing.Tracer.
+func (t *Tracer) StartSpan(
+ operationName string,
+ options ...opentracing.StartSpanOption,
+) opentracing.Span {
+ sso := opentracing.StartSpanOptions{}
+ for _, o := range options {
+ o.Apply(&sso)
+ }
+ return t.startSpanWithOptions(operationName, sso)
+}
+
+func (t *Tracer) startSpanWithOptions(
+ operationName string,
+ options opentracing.StartSpanOptions,
+) opentracing.Span {
+ if options.StartTime.IsZero() {
+ options.StartTime = t.timeNow()
+ }
+
+ // Predicate whether the given span context is a valid reference
+ // which may be used as parent / debug ID / baggage items source
+ isValidReference := func(ctx SpanContext) bool {
+ return ctx.IsValid() || ctx.isDebugIDContainerOnly() || len(ctx.baggage) != 0
+ }
+
+ var references []Reference
+ var parent SpanContext
+ var hasParent bool // need this because `parent` is a value, not reference
+ for _, ref := range options.References {
+ ctx, ok := ref.ReferencedContext.(SpanContext)
+ if !ok {
+ t.logger.Error(fmt.Sprintf(
+ "Reference contains invalid type of SpanReference: %s",
+ reflect.ValueOf(ref.ReferencedContext)))
+ continue
+ }
+ if !isValidReference(ctx) {
+ continue
+ }
+ references = append(references, Reference{Type: ref.Type, Context: ctx})
+ if !hasParent {
+ parent = ctx
+ hasParent = ref.Type == opentracing.ChildOfRef
+ }
+ }
+ if !hasParent && isValidReference(parent) {
+ // If ChildOfRef wasn't found but a FollowFromRef exists, use the context from
+ // the FollowFromRef as the parent
+ hasParent = true
+ }
+
+ rpcServer := false
+ if v, ok := options.Tags[ext.SpanKindRPCServer.Key]; ok {
+ rpcServer = (v == ext.SpanKindRPCServerEnum || v == string(ext.SpanKindRPCServerEnum))
+ }
+
+ var samplerTags []Tag
+ var ctx SpanContext
+ newTrace := false
+ if !hasParent || !parent.IsValid() {
+ newTrace = true
+ ctx.traceID.Low = t.randomID()
+ if t.options.gen128Bit {
+ ctx.traceID.High = t.options.highTraceIDGenerator()
+ }
+ ctx.spanID = SpanID(ctx.traceID.Low)
+ ctx.parentID = 0
+ ctx.flags = byte(0)
+ if hasParent && parent.isDebugIDContainerOnly() && t.isDebugAllowed(operationName) {
+ ctx.flags |= (flagSampled | flagDebug)
+ samplerTags = []Tag{{key: JaegerDebugHeader, value: parent.debugID}}
+ } else if sampled, tags := t.sampler.IsSampled(ctx.traceID, operationName); sampled {
+ ctx.flags |= flagSampled
+ samplerTags = tags
+ }
+ } else {
+ ctx.traceID = parent.traceID
+ if rpcServer && t.options.zipkinSharedRPCSpan {
+ // Support Zipkin's one-span-per-RPC model
+ ctx.spanID = parent.spanID
+ ctx.parentID = parent.parentID
+ } else {
+ ctx.spanID = SpanID(t.randomID())
+ ctx.parentID = parent.spanID
+ }
+ ctx.flags = parent.flags
+ }
+ if hasParent {
+ // copy baggage items
+ if l := len(parent.baggage); l > 0 {
+ ctx.baggage = make(map[string]string, len(parent.baggage))
+ for k, v := range parent.baggage {
+ ctx.baggage[k] = v
+ }
+ }
+ }
+
+ sp := t.newSpan()
+ sp.context = ctx
+ sp.observer = t.observer.OnStartSpan(sp, operationName, options)
+ return t.startSpanInternal(
+ sp,
+ operationName,
+ options.StartTime,
+ samplerTags,
+ options.Tags,
+ newTrace,
+ rpcServer,
+ references,
+ )
+}
+
+// Inject implements Inject() method of opentracing.Tracer
+func (t *Tracer) Inject(ctx opentracing.SpanContext, format interface{}, carrier interface{}) error {
+ c, ok := ctx.(SpanContext)
+ if !ok {
+ return opentracing.ErrInvalidSpanContext
+ }
+ if injector, ok := t.injectors[format]; ok {
+ return injector.Inject(c, carrier)
+ }
+ return opentracing.ErrUnsupportedFormat
+}
+
+// Extract implements Extract() method of opentracing.Tracer
+func (t *Tracer) Extract(
+ format interface{},
+ carrier interface{},
+) (opentracing.SpanContext, error) {
+ if extractor, ok := t.extractors[format]; ok {
+ return extractor.Extract(carrier)
+ }
+ return nil, opentracing.ErrUnsupportedFormat
+}
+
+// Close releases all resources used by the Tracer and flushes any remaining buffered spans.
+func (t *Tracer) Close() error {
+ t.reporter.Close()
+ t.sampler.Close()
+ if mgr, ok := t.baggageRestrictionManager.(io.Closer); ok {
+ mgr.Close()
+ }
+ if throttler, ok := t.debugThrottler.(io.Closer); ok {
+ throttler.Close()
+ }
+ return nil
+}
+
+// Tags returns a slice of tracer-level tags.
+func (t *Tracer) Tags() []opentracing.Tag {
+ tags := make([]opentracing.Tag, len(t.tags))
+ for i, tag := range t.tags {
+ tags[i] = opentracing.Tag{Key: tag.key, Value: tag.value}
+ }
+ return tags
+}
+
+// newSpan returns an instance of a clean Span object.
+// If options.PoolSpans is true, the spans are retrieved from an object pool.
+func (t *Tracer) newSpan() *Span {
+ if !t.options.poolSpans {
+ return &Span{}
+ }
+ sp := t.spanPool.Get().(*Span)
+ sp.context = emptyContext
+ sp.tracer = nil
+ sp.tags = nil
+ sp.logs = nil
+ return sp
+}
+
+func (t *Tracer) startSpanInternal(
+ sp *Span,
+ operationName string,
+ startTime time.Time,
+ internalTags []Tag,
+ tags opentracing.Tags,
+ newTrace bool,
+ rpcServer bool,
+ references []Reference,
+) *Span {
+ sp.tracer = t
+ sp.operationName = operationName
+ sp.startTime = startTime
+ sp.duration = 0
+ sp.references = references
+ sp.firstInProcess = rpcServer || sp.context.parentID == 0
+ if len(tags) > 0 || len(internalTags) > 0 {
+ sp.tags = make([]Tag, len(internalTags), len(tags)+len(internalTags))
+ copy(sp.tags, internalTags)
+ for k, v := range tags {
+ sp.observer.OnSetTag(k, v)
+ if k == string(ext.SamplingPriority) && !setSamplingPriority(sp, v) {
+ continue
+ }
+ sp.setTagNoLocking(k, v)
+ }
+ }
+ // emit metrics
+ if sp.context.IsSampled() {
+ t.metrics.SpansStartedSampled.Inc(1)
+ if newTrace {
+ // We cannot simply check for parentID==0 because in Zipkin model the
+ // server-side RPC span has the exact same trace/span/parent IDs as the
+ // calling client-side span, but obviously the server side span is
+ // no longer a root span of the trace.
+ t.metrics.TracesStartedSampled.Inc(1)
+ } else if sp.firstInProcess {
+ t.metrics.TracesJoinedSampled.Inc(1)
+ }
+ } else {
+ t.metrics.SpansStartedNotSampled.Inc(1)
+ if newTrace {
+ t.metrics.TracesStartedNotSampled.Inc(1)
+ } else if sp.firstInProcess {
+ t.metrics.TracesJoinedNotSampled.Inc(1)
+ }
+ }
+ return sp
+}
+
+func (t *Tracer) reportSpan(sp *Span) {
+ t.metrics.SpansFinished.Inc(1)
+ if sp.context.IsSampled() {
+ t.reporter.Report(sp)
+ }
+ if t.options.poolSpans {
+ t.spanPool.Put(sp)
+ }
+}
+
+// randomID generates a random trace/span ID, using tracer.random() generator.
+// It never returns 0.
+func (t *Tracer) randomID() uint64 {
+ val := t.randomNumber()
+ for val == 0 {
+ val = t.randomNumber()
+ }
+ return val
+}
+
+// (NB) span must hold the lock before making this call
+func (t *Tracer) setBaggage(sp *Span, key, value string) {
+ t.baggageSetter.setBaggage(sp, key, value)
+}
+
+// (NB) span must hold the lock before making this call
+func (t *Tracer) isDebugAllowed(operation string) bool {
+ return t.debugThrottler.IsAllowed(operation)
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/tracer_options.go b/vendor/github.com/uber/jaeger-client-go/tracer_options.go
new file mode 100644
index 000000000..a90265f03
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/tracer_options.go
@@ -0,0 +1,159 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package jaeger
+
+import (
+ "time"
+
+ "github.com/opentracing/opentracing-go"
+
+ "github.com/uber/jaeger-client-go/internal/baggage"
+ "github.com/uber/jaeger-client-go/internal/throttler"
+)
+
+// TracerOption is a function that sets some option on the tracer
+type TracerOption func(tracer *Tracer)
+
+// TracerOptions is a factory for all available TracerOption's
+var TracerOptions tracerOptions
+
+type tracerOptions struct{}
+
+// Metrics creates a TracerOption that initializes Metrics on the tracer,
+// which is used to emit statistics.
+func (tracerOptions) Metrics(m *Metrics) TracerOption {
+ return func(tracer *Tracer) {
+ tracer.metrics = *m
+ }
+}
+
+// Logger creates a TracerOption that gives the tracer a Logger.
+func (tracerOptions) Logger(logger Logger) TracerOption {
+ return func(tracer *Tracer) {
+ tracer.logger = logger
+ }
+}
+
+func (tracerOptions) CustomHeaderKeys(headerKeys *HeadersConfig) TracerOption {
+ return func(tracer *Tracer) {
+ if headerKeys == nil {
+ return
+ }
+ textPropagator := newTextMapPropagator(headerKeys.applyDefaults(), tracer.metrics)
+ tracer.addCodec(opentracing.TextMap, textPropagator, textPropagator)
+
+ httpHeaderPropagator := newHTTPHeaderPropagator(headerKeys.applyDefaults(), tracer.metrics)
+ tracer.addCodec(opentracing.HTTPHeaders, httpHeaderPropagator, httpHeaderPropagator)
+ }
+}
+
+// TimeNow creates a TracerOption that gives the tracer a function
+// used to generate timestamps for spans.
+func (tracerOptions) TimeNow(timeNow func() time.Time) TracerOption {
+ return func(tracer *Tracer) {
+ tracer.timeNow = timeNow
+ }
+}
+
+// RandomNumber creates a TracerOption that gives the tracer
+// a thread-safe random number generator function for generating trace IDs.
+func (tracerOptions) RandomNumber(randomNumber func() uint64) TracerOption {
+ return func(tracer *Tracer) {
+ tracer.randomNumber = randomNumber
+ }
+}
+
+// PoolSpans creates a TracerOption that tells the tracer whether it should use
+// an object pool to minimize span allocations.
+// This should be used with care, only if the service is not running any async tasks
+// that can access parent spans after those spans have been finished.
+func (tracerOptions) PoolSpans(poolSpans bool) TracerOption {
+ return func(tracer *Tracer) {
+ tracer.options.poolSpans = poolSpans
+ }
+}
+
+// Deprecated: HostIPv4 creates a TracerOption that identifies the current service/process.
+// If not set, the factory method will obtain the current IP address.
+// The TracerOption is deprecated; the tracer will attempt to automatically detect the IP.
+func (tracerOptions) HostIPv4(hostIPv4 uint32) TracerOption {
+ return func(tracer *Tracer) {
+ tracer.hostIPv4 = hostIPv4
+ }
+}
+
+func (tracerOptions) Injector(format interface{}, injector Injector) TracerOption {
+ return func(tracer *Tracer) {
+ tracer.injectors[format] = injector
+ }
+}
+
+func (tracerOptions) Extractor(format interface{}, extractor Extractor) TracerOption {
+ return func(tracer *Tracer) {
+ tracer.extractors[format] = extractor
+ }
+}
+
+func (t tracerOptions) Observer(observer Observer) TracerOption {
+ return t.ContribObserver(&oldObserver{obs: observer})
+}
+
+func (tracerOptions) ContribObserver(observer ContribObserver) TracerOption {
+ return func(tracer *Tracer) {
+ tracer.observer.append(observer)
+ }
+}
+
+func (tracerOptions) Gen128Bit(gen128Bit bool) TracerOption {
+ return func(tracer *Tracer) {
+ tracer.options.gen128Bit = gen128Bit
+ }
+}
+
+func (tracerOptions) HighTraceIDGenerator(highTraceIDGenerator func() uint64) TracerOption {
+ return func(tracer *Tracer) {
+ tracer.options.highTraceIDGenerator = highTraceIDGenerator
+ }
+}
+
+func (tracerOptions) MaxTagValueLength(maxTagValueLength int) TracerOption {
+ return func(tracer *Tracer) {
+ tracer.options.maxTagValueLength = maxTagValueLength
+ }
+}
+
+func (tracerOptions) ZipkinSharedRPCSpan(zipkinSharedRPCSpan bool) TracerOption {
+ return func(tracer *Tracer) {
+ tracer.options.zipkinSharedRPCSpan = zipkinSharedRPCSpan
+ }
+}
+
+func (tracerOptions) Tag(key string, value interface{}) TracerOption {
+ return func(tracer *Tracer) {
+ tracer.tags = append(tracer.tags, Tag{key: key, value: value})
+ }
+}
+
+func (tracerOptions) BaggageRestrictionManager(mgr baggage.RestrictionManager) TracerOption {
+ return func(tracer *Tracer) {
+ tracer.baggageRestrictionManager = mgr
+ }
+}
+
+func (tracerOptions) DebugThrottler(throttler throttler.Throttler) TracerOption {
+ return func(tracer *Tracer) {
+ tracer.debugThrottler = throttler
+ }
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/transport.go b/vendor/github.com/uber/jaeger-client-go/transport.go
new file mode 100644
index 000000000..c5f5b1955
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/transport.go
@@ -0,0 +1,38 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package jaeger
+
+import (
+ "io"
+)
+
+// Transport abstracts the method of sending spans out of process.
+// Implementations are NOT required to be thread-safe; the RemoteReporter
+// is expected to only call methods on the Transport from the same go-routine.
+type Transport interface {
+ // Append converts the span to the wire representation and adds it
+ // to sender's internal buffer. If the buffer exceeds its designated
+ // size, the transport should call Flush() and return the number of spans
+ // flushed, otherwise return 0. If error is returned, the returned number
+ // of spans is treated as failed span, and reported to metrics accordingly.
+ Append(span *Span) (int, error)
+
+ // Flush submits the internal buffer to the remote server. It returns the
+ // number of spans flushed. If error is returned, the returned number of
+ // spans is treated as failed span, and reported to metrics accordingly.
+ Flush() (int, error)
+
+ io.Closer
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/transport/doc.go b/vendor/github.com/uber/jaeger-client-go/transport/doc.go
new file mode 100644
index 000000000..6b961fb63
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/transport/doc.go
@@ -0,0 +1,23 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+// Package transport defines various transports that can be used with
+// RemoteReporter to send spans out of process. Transport is responsible
+// for serializing the spans into a specific format suitable for sending
+// to the tracing backend. Examples may include Thrift over UDP, Thrift
+// or JSON over HTTP, Thrift over Kafka, etc.
+//
+// Implementations are NOT required to be thread-safe; the RemoteReporter
+// is expected to only call methods on the Transport from the same go-routine.
+package transport
diff --git a/vendor/github.com/uber/jaeger-client-go/transport/http.go b/vendor/github.com/uber/jaeger-client-go/transport/http.go
new file mode 100644
index 000000000..bc1b3e6b0
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/transport/http.go
@@ -0,0 +1,163 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package transport
+
+import (
+ "bytes"
+ "fmt"
+ "io"
+ "io/ioutil"
+ "net/http"
+ "time"
+
+ "github.com/uber/jaeger-client-go/thrift"
+
+ "github.com/uber/jaeger-client-go"
+ j "github.com/uber/jaeger-client-go/thrift-gen/jaeger"
+)
+
+// Default timeout for http request in seconds
+const defaultHTTPTimeout = time.Second * 5
+
+// HTTPTransport implements Transport by forwarding spans to a http server.
+type HTTPTransport struct {
+ url string
+ client *http.Client
+ batchSize int
+ spans []*j.Span
+ process *j.Process
+ httpCredentials *HTTPBasicAuthCredentials
+}
+
+// HTTPBasicAuthCredentials stores credentials for HTTP basic auth.
+type HTTPBasicAuthCredentials struct {
+ username string
+ password string
+}
+
+// HTTPOption sets a parameter for the HttpCollector
+type HTTPOption func(c *HTTPTransport)
+
+// HTTPTimeout sets maximum timeout for http request.
+func HTTPTimeout(duration time.Duration) HTTPOption {
+ return func(c *HTTPTransport) { c.client.Timeout = duration }
+}
+
+// HTTPBatchSize sets the maximum batch size, after which a collect will be
+// triggered. The default batch size is 100 spans.
+func HTTPBatchSize(n int) HTTPOption {
+ return func(c *HTTPTransport) { c.batchSize = n }
+}
+
+// HTTPBasicAuth sets the credentials required to perform HTTP basic auth
+func HTTPBasicAuth(username string, password string) HTTPOption {
+ return func(c *HTTPTransport) {
+ c.httpCredentials = &HTTPBasicAuthCredentials{username: username, password: password}
+ }
+}
+
+// HTTPRoundTripper configures the underlying Transport on the *http.Client
+// that is used
+func HTTPRoundTripper(transport http.RoundTripper) HTTPOption {
+ return func(c *HTTPTransport) {
+ c.client.Transport = transport
+ }
+}
+
+// NewHTTPTransport returns a new HTTP-backend transport. url should be an http
+// url of the collector to handle POST request, typically something like:
+// http://hostname:14268/api/traces?format=jaeger.thrift
+func NewHTTPTransport(url string, options ...HTTPOption) *HTTPTransport {
+ c := &HTTPTransport{
+ url: url,
+ client: &http.Client{Timeout: defaultHTTPTimeout},
+ batchSize: 100,
+ spans: []*j.Span{},
+ }
+
+ for _, option := range options {
+ option(c)
+ }
+ return c
+}
+
+// Append implements Transport.
+func (c *HTTPTransport) Append(span *jaeger.Span) (int, error) {
+ if c.process == nil {
+ c.process = jaeger.BuildJaegerProcessThrift(span)
+ }
+ jSpan := jaeger.BuildJaegerThrift(span)
+ c.spans = append(c.spans, jSpan)
+ if len(c.spans) >= c.batchSize {
+ return c.Flush()
+ }
+ return 0, nil
+}
+
+// Flush implements Transport.
+func (c *HTTPTransport) Flush() (int, error) {
+ count := len(c.spans)
+ if count == 0 {
+ return 0, nil
+ }
+ err := c.send(c.spans)
+ c.spans = c.spans[:0]
+ return count, err
+}
+
+// Close implements Transport.
+func (c *HTTPTransport) Close() error {
+ return nil
+}
+
+func (c *HTTPTransport) send(spans []*j.Span) error {
+ batch := &j.Batch{
+ Spans: spans,
+ Process: c.process,
+ }
+ body, err := serializeThrift(batch)
+ if err != nil {
+ return err
+ }
+ req, err := http.NewRequest("POST", c.url, body)
+ if err != nil {
+ return err
+ }
+ req.Header.Set("Content-Type", "application/x-thrift")
+
+ if c.httpCredentials != nil {
+ req.SetBasicAuth(c.httpCredentials.username, c.httpCredentials.password)
+ }
+
+ resp, err := c.client.Do(req)
+ if err != nil {
+ return err
+ }
+ io.Copy(ioutil.Discard, resp.Body)
+ resp.Body.Close()
+ if resp.StatusCode >= http.StatusBadRequest {
+ return fmt.Errorf("error from collector: %d", resp.StatusCode)
+ }
+ return nil
+}
+
+func serializeThrift(obj thrift.TStruct) (*bytes.Buffer, error) {
+ t := thrift.NewTMemoryBuffer()
+ p := thrift.NewTBinaryProtocolTransport(t)
+ if err := obj.Write(p); err != nil {
+ return nil, err
+ }
+ return t.Buffer, nil
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/transport_udp.go b/vendor/github.com/uber/jaeger-client-go/transport_udp.go
new file mode 100644
index 000000000..7b9ccf937
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/transport_udp.go
@@ -0,0 +1,131 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package jaeger
+
+import (
+ "errors"
+ "fmt"
+
+ "github.com/uber/jaeger-client-go/thrift"
+
+ j "github.com/uber/jaeger-client-go/thrift-gen/jaeger"
+ "github.com/uber/jaeger-client-go/utils"
+)
+
+// Empirically obtained constant for how many bytes in the message are used for envelope.
+// The total datagram size is:
+// sizeof(Span) * numSpans + processByteSize + emitBatchOverhead <= maxPacketSize
+// There is a unit test `TestEmitBatchOverhead` that validates this number.
+// Note that due to the use of Compact Thrift protocol, overhead grows with the number of spans
+// in the batch, because the length of the list is encoded as varint32, as well as SeqId.
+const emitBatchOverhead = 30
+
+var errSpanTooLarge = errors.New("Span is too large")
+
+type udpSender struct {
+ client *utils.AgentClientUDP
+ maxPacketSize int // max size of datagram in bytes
+ maxSpanBytes int // max number of bytes to record spans (excluding envelope) in the datagram
+ byteBufferSize int // current number of span bytes accumulated in the buffer
+ spanBuffer []*j.Span // spans buffered before a flush
+ thriftBuffer *thrift.TMemoryBuffer // buffer used to calculate byte size of a span
+ thriftProtocol thrift.TProtocol
+ process *j.Process
+ processByteSize int
+}
+
+// NewUDPTransport creates a reporter that submits spans to jaeger-agent
+func NewUDPTransport(hostPort string, maxPacketSize int) (Transport, error) {
+ if len(hostPort) == 0 {
+ hostPort = fmt.Sprintf("%s:%d", DefaultUDPSpanServerHost, DefaultUDPSpanServerPort)
+ }
+ if maxPacketSize == 0 {
+ maxPacketSize = utils.UDPPacketMaxLength
+ }
+
+ protocolFactory := thrift.NewTCompactProtocolFactory()
+
+ // Each span is first written to thriftBuffer to determine its size in bytes.
+ thriftBuffer := thrift.NewTMemoryBufferLen(maxPacketSize)
+ thriftProtocol := protocolFactory.GetProtocol(thriftBuffer)
+
+ client, err := utils.NewAgentClientUDP(hostPort, maxPacketSize)
+ if err != nil {
+ return nil, err
+ }
+
+ sender := &udpSender{
+ client: client,
+ maxSpanBytes: maxPacketSize - emitBatchOverhead,
+ thriftBuffer: thriftBuffer,
+ thriftProtocol: thriftProtocol}
+ return sender, nil
+}
+
+func (s *udpSender) calcSizeOfSerializedThrift(thriftStruct thrift.TStruct) int {
+ s.thriftBuffer.Reset()
+ thriftStruct.Write(s.thriftProtocol)
+ return s.thriftBuffer.Len()
+}
+
+func (s *udpSender) Append(span *Span) (int, error) {
+ if s.process == nil {
+ s.process = BuildJaegerProcessThrift(span)
+ s.processByteSize = s.calcSizeOfSerializedThrift(s.process)
+ s.byteBufferSize += s.processByteSize
+ }
+ jSpan := BuildJaegerThrift(span)
+ spanSize := s.calcSizeOfSerializedThrift(jSpan)
+ if spanSize > s.maxSpanBytes {
+ return 1, errSpanTooLarge
+ }
+
+ s.byteBufferSize += spanSize
+ if s.byteBufferSize <= s.maxSpanBytes {
+ s.spanBuffer = append(s.spanBuffer, jSpan)
+ if s.byteBufferSize < s.maxSpanBytes {
+ return 0, nil
+ }
+ return s.Flush()
+ }
+ // the latest span did not fit in the buffer
+ n, err := s.Flush()
+ s.spanBuffer = append(s.spanBuffer, jSpan)
+ s.byteBufferSize = spanSize + s.processByteSize
+ return n, err
+}
+
+func (s *udpSender) Flush() (int, error) {
+ n := len(s.spanBuffer)
+ if n == 0 {
+ return 0, nil
+ }
+ err := s.client.EmitBatch(&j.Batch{Process: s.process, Spans: s.spanBuffer})
+ s.resetBuffers()
+
+ return n, err
+}
+
+func (s *udpSender) Close() error {
+ return s.client.Close()
+}
+
+func (s *udpSender) resetBuffers() {
+ for i := range s.spanBuffer {
+ s.spanBuffer[i] = nil
+ }
+ s.spanBuffer = s.spanBuffer[:0]
+ s.byteBufferSize = s.processByteSize
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/utils/http_json.go b/vendor/github.com/uber/jaeger-client-go/utils/http_json.go
new file mode 100644
index 000000000..237211f82
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/utils/http_json.go
@@ -0,0 +1,54 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package utils
+
+import (
+ "encoding/json"
+ "fmt"
+ "io"
+ "io/ioutil"
+ "net/http"
+)
+
+// GetJSON makes an HTTP call to the specified URL and parses the returned JSON into `out`.
+func GetJSON(url string, out interface{}) error {
+ resp, err := http.Get(url)
+ if err != nil {
+ return err
+ }
+ return ReadJSON(resp, out)
+}
+
+// ReadJSON reads JSON from http.Response and parses it into `out`
+func ReadJSON(resp *http.Response, out interface{}) error {
+ defer resp.Body.Close()
+
+ if resp.StatusCode >= 400 {
+ body, err := ioutil.ReadAll(resp.Body)
+ if err != nil {
+ return err
+ }
+
+ return fmt.Errorf("StatusCode: %d, Body: %s", resp.StatusCode, body)
+ }
+
+ if out == nil {
+ io.Copy(ioutil.Discard, resp.Body)
+ return nil
+ }
+
+ decoder := json.NewDecoder(resp.Body)
+ return decoder.Decode(out)
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/utils/localip.go b/vendor/github.com/uber/jaeger-client-go/utils/localip.go
new file mode 100644
index 000000000..b51af7713
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/utils/localip.go
@@ -0,0 +1,84 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package utils
+
+import (
+ "errors"
+ "net"
+)
+
+// This code is borrowed from https://github.com/uber/tchannel-go/blob/dev/localip.go
+
+// scoreAddr scores how likely the given addr is to be a remote address and returns the
+// IP to use when listening. Any address which receives a negative score should not be used.
+// Scores are calculated as:
+// -1 for any unknown IP addresses.
+// +300 for IPv4 addresses
+// +100 for non-local addresses, extra +100 for "up" interaces.
+func scoreAddr(iface net.Interface, addr net.Addr) (int, net.IP) {
+ var ip net.IP
+ if netAddr, ok := addr.(*net.IPNet); ok {
+ ip = netAddr.IP
+ } else if netIP, ok := addr.(*net.IPAddr); ok {
+ ip = netIP.IP
+ } else {
+ return -1, nil
+ }
+
+ var score int
+ if ip.To4() != nil {
+ score += 300
+ }
+ if iface.Flags&net.FlagLoopback == 0 && !ip.IsLoopback() {
+ score += 100
+ if iface.Flags&net.FlagUp != 0 {
+ score += 100
+ }
+ }
+ return score, ip
+}
+
+// HostIP tries to find an IP that can be used by other machines to reach this machine.
+func HostIP() (net.IP, error) {
+ interfaces, err := net.Interfaces()
+ if err != nil {
+ return nil, err
+ }
+
+ bestScore := -1
+ var bestIP net.IP
+ // Select the highest scoring IP as the best IP.
+ for _, iface := range interfaces {
+ addrs, err := iface.Addrs()
+ if err != nil {
+ // Skip this interface if there is an error.
+ continue
+ }
+
+ for _, addr := range addrs {
+ score, ip := scoreAddr(iface, addr)
+ if score > bestScore {
+ bestScore = score
+ bestIP = ip
+ }
+ }
+ }
+
+ if bestScore == -1 {
+ return nil, errors.New("no addresses to listen on")
+ }
+
+ return bestIP, nil
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/utils/rand.go b/vendor/github.com/uber/jaeger-client-go/utils/rand.go
new file mode 100644
index 000000000..9875f7f55
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/utils/rand.go
@@ -0,0 +1,46 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package utils
+
+import (
+ "math/rand"
+ "sync"
+)
+
+// lockedSource allows a random number generator to be used by multiple goroutines concurrently.
+// The code is very similar to math/rand.lockedSource, which is unfortunately not exposed.
+type lockedSource struct {
+ mut sync.Mutex
+ src rand.Source
+}
+
+// NewRand returns a rand.Rand that is threadsafe.
+func NewRand(seed int64) *rand.Rand {
+ return rand.New(&lockedSource{src: rand.NewSource(seed)})
+}
+
+func (r *lockedSource) Int63() (n int64) {
+ r.mut.Lock()
+ n = r.src.Int63()
+ r.mut.Unlock()
+ return
+}
+
+// Seed implements Seed() of Source
+func (r *lockedSource) Seed(seed int64) {
+ r.mut.Lock()
+ r.src.Seed(seed)
+ r.mut.Unlock()
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/utils/rate_limiter.go b/vendor/github.com/uber/jaeger-client-go/utils/rate_limiter.go
new file mode 100644
index 000000000..1b8db9758
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/utils/rate_limiter.go
@@ -0,0 +1,77 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package utils
+
+import (
+ "sync"
+ "time"
+)
+
+// RateLimiter is a filter used to check if a message that is worth itemCost units is within the rate limits.
+type RateLimiter interface {
+ CheckCredit(itemCost float64) bool
+}
+
+type rateLimiter struct {
+ sync.Mutex
+
+ creditsPerSecond float64
+ balance float64
+ maxBalance float64
+ lastTick time.Time
+
+ timeNow func() time.Time
+}
+
+// NewRateLimiter creates a new rate limiter based on leaky bucket algorithm, formulated in terms of a
+// credits balance that is replenished every time CheckCredit() method is called (tick) by the amount proportional
+// to the time elapsed since the last tick, up to max of creditsPerSecond. A call to CheckCredit() takes a cost
+// of an item we want to pay with the balance. If the balance exceeds the cost of the item, the item is "purchased"
+// and the balance reduced, indicated by returned value of true. Otherwise the balance is unchanged and return false.
+//
+// This can be used to limit a rate of messages emitted by a service by instantiating the Rate Limiter with the
+// max number of messages a service is allowed to emit per second, and calling CheckCredit(1.0) for each message
+// to determine if the message is within the rate limit.
+//
+// It can also be used to limit the rate of traffic in bytes, by setting creditsPerSecond to desired throughput
+// as bytes/second, and calling CheckCredit() with the actual message size.
+func NewRateLimiter(creditsPerSecond, maxBalance float64) RateLimiter {
+ return &rateLimiter{
+ creditsPerSecond: creditsPerSecond,
+ balance: maxBalance,
+ maxBalance: maxBalance,
+ lastTick: time.Now(),
+ timeNow: time.Now}
+}
+
+func (b *rateLimiter) CheckCredit(itemCost float64) bool {
+ b.Lock()
+ defer b.Unlock()
+ // calculate how much time passed since the last tick, and update current tick
+ currentTime := b.timeNow()
+ elapsedTime := currentTime.Sub(b.lastTick)
+ b.lastTick = currentTime
+ // calculate how much credit have we accumulated since the last tick
+ b.balance += elapsedTime.Seconds() * b.creditsPerSecond
+ if b.balance > b.maxBalance {
+ b.balance = b.maxBalance
+ }
+ // if we have enough credits to pay for current item, then reduce balance and allow
+ if b.balance >= itemCost {
+ b.balance -= itemCost
+ return true
+ }
+ return false
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/utils/udp_client.go b/vendor/github.com/uber/jaeger-client-go/utils/udp_client.go
new file mode 100644
index 000000000..6f042073d
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/utils/udp_client.go
@@ -0,0 +1,98 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package utils
+
+import (
+ "errors"
+ "fmt"
+ "io"
+ "net"
+
+ "github.com/uber/jaeger-client-go/thrift"
+
+ "github.com/uber/jaeger-client-go/thrift-gen/agent"
+ "github.com/uber/jaeger-client-go/thrift-gen/jaeger"
+ "github.com/uber/jaeger-client-go/thrift-gen/zipkincore"
+)
+
+// UDPPacketMaxLength is the max size of UDP packet we want to send, synced with jaeger-agent
+const UDPPacketMaxLength = 65000
+
+// AgentClientUDP is a UDP client to Jaeger agent that implements agent.Agent interface.
+type AgentClientUDP struct {
+ agent.Agent
+ io.Closer
+
+ connUDP *net.UDPConn
+ client *agent.AgentClient
+ maxPacketSize int // max size of datagram in bytes
+ thriftBuffer *thrift.TMemoryBuffer // buffer used to calculate byte size of a span
+}
+
+// NewAgentClientUDP creates a client that sends spans to Jaeger Agent over UDP.
+func NewAgentClientUDP(hostPort string, maxPacketSize int) (*AgentClientUDP, error) {
+ if maxPacketSize == 0 {
+ maxPacketSize = UDPPacketMaxLength
+ }
+
+ thriftBuffer := thrift.NewTMemoryBufferLen(maxPacketSize)
+ protocolFactory := thrift.NewTCompactProtocolFactory()
+ client := agent.NewAgentClientFactory(thriftBuffer, protocolFactory)
+
+ destAddr, err := net.ResolveUDPAddr("udp", hostPort)
+ if err != nil {
+ return nil, err
+ }
+
+ connUDP, err := net.DialUDP(destAddr.Network(), nil, destAddr)
+ if err != nil {
+ return nil, err
+ }
+ if err := connUDP.SetWriteBuffer(maxPacketSize); err != nil {
+ return nil, err
+ }
+
+ clientUDP := &AgentClientUDP{
+ connUDP: connUDP,
+ client: client,
+ maxPacketSize: maxPacketSize,
+ thriftBuffer: thriftBuffer}
+ return clientUDP, nil
+}
+
+// EmitZipkinBatch implements EmitZipkinBatch() of Agent interface
+func (a *AgentClientUDP) EmitZipkinBatch(spans []*zipkincore.Span) error {
+ return errors.New("Not implemented")
+}
+
+// EmitBatch implements EmitBatch() of Agent interface
+func (a *AgentClientUDP) EmitBatch(batch *jaeger.Batch) error {
+ a.thriftBuffer.Reset()
+ a.client.SeqId = 0 // we have no need for distinct SeqIds for our one-way UDP messages
+ if err := a.client.EmitBatch(batch); err != nil {
+ return err
+ }
+ if a.thriftBuffer.Len() > a.maxPacketSize {
+ return fmt.Errorf("Data does not fit within one UDP packet; size %d, max %d, spans %d",
+ a.thriftBuffer.Len(), a.maxPacketSize, len(batch.Spans))
+ }
+ _, err := a.connUDP.Write(a.thriftBuffer.Bytes())
+ return err
+}
+
+// Close implements Close() of io.Closer and closes the underlying UDP connection.
+func (a *AgentClientUDP) Close() error {
+ return a.connUDP.Close()
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/utils/utils.go b/vendor/github.com/uber/jaeger-client-go/utils/utils.go
new file mode 100644
index 000000000..ac3c325d1
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/utils/utils.go
@@ -0,0 +1,87 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package utils
+
+import (
+ "encoding/binary"
+ "errors"
+ "net"
+ "strconv"
+ "strings"
+ "time"
+)
+
+var (
+ // ErrEmptyIP an error for empty ip strings
+ ErrEmptyIP = errors.New("empty string given for ip")
+
+ // ErrNotHostColonPort an error for invalid host port string
+ ErrNotHostColonPort = errors.New("expecting host:port")
+
+ // ErrNotFourOctets an error for the wrong number of octets after splitting a string
+ ErrNotFourOctets = errors.New("Wrong number of octets")
+)
+
+// ParseIPToUint32 converts a string ip (e.g. "x.y.z.w") to an uint32
+func ParseIPToUint32(ip string) (uint32, error) {
+ if ip == "" {
+ return 0, ErrEmptyIP
+ }
+
+ if ip == "localhost" {
+ return 127<<24 | 1, nil
+ }
+
+ octets := strings.Split(ip, ".")
+ if len(octets) != 4 {
+ return 0, ErrNotFourOctets
+ }
+
+ var intIP uint32
+ for i := 0; i < 4; i++ {
+ octet, err := strconv.Atoi(octets[i])
+ if err != nil {
+ return 0, err
+ }
+ intIP = (intIP << 8) | uint32(octet)
+ }
+
+ return intIP, nil
+}
+
+// ParsePort converts port number from string to uin16
+func ParsePort(portString string) (uint16, error) {
+ port, err := strconv.ParseUint(portString, 10, 16)
+ return uint16(port), err
+}
+
+// PackIPAsUint32 packs an IPv4 as uint32
+func PackIPAsUint32(ip net.IP) uint32 {
+ if ipv4 := ip.To4(); ipv4 != nil {
+ return binary.BigEndian.Uint32(ipv4)
+ }
+ return 0
+}
+
+// TimeToMicrosecondsSinceEpochInt64 converts Go time.Time to a long
+// representing time since epoch in microseconds, which is used expected
+// in the Jaeger spans encoded as Thrift.
+func TimeToMicrosecondsSinceEpochInt64(t time.Time) int64 {
+ // ^^^ Passing time.Time by value is faster than passing a pointer!
+ // BenchmarkTimeByValue-8 2000000000 1.37 ns/op
+ // BenchmarkTimeByPtr-8 2000000000 1.98 ns/op
+
+ return t.UnixNano() / 1000
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/zipkin.go b/vendor/github.com/uber/jaeger-client-go/zipkin.go
new file mode 100644
index 000000000..636952b7f
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/zipkin.go
@@ -0,0 +1,76 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package jaeger
+
+import (
+ "github.com/opentracing/opentracing-go"
+)
+
+// ZipkinSpanFormat is an OpenTracing carrier format constant
+const ZipkinSpanFormat = "zipkin-span-format"
+
+// ExtractableZipkinSpan is a type of Carrier used for integration with Zipkin-aware
+// RPC frameworks (like TChannel). It does not support baggage, only trace IDs.
+type ExtractableZipkinSpan interface {
+ TraceID() uint64
+ SpanID() uint64
+ ParentID() uint64
+ Flags() byte
+}
+
+// InjectableZipkinSpan is a type of Carrier used for integration with Zipkin-aware
+// RPC frameworks (like TChannel). It does not support baggage, only trace IDs.
+type InjectableZipkinSpan interface {
+ SetTraceID(traceID uint64)
+ SetSpanID(spanID uint64)
+ SetParentID(parentID uint64)
+ SetFlags(flags byte)
+}
+
+type zipkinPropagator struct {
+ tracer *Tracer
+}
+
+func (p *zipkinPropagator) Inject(
+ ctx SpanContext,
+ abstractCarrier interface{},
+) error {
+ carrier, ok := abstractCarrier.(InjectableZipkinSpan)
+ if !ok {
+ return opentracing.ErrInvalidCarrier
+ }
+
+ carrier.SetTraceID(ctx.TraceID().Low) // TODO this cannot work with 128bit IDs
+ carrier.SetSpanID(uint64(ctx.SpanID()))
+ carrier.SetParentID(uint64(ctx.ParentID()))
+ carrier.SetFlags(ctx.flags)
+ return nil
+}
+
+func (p *zipkinPropagator) Extract(abstractCarrier interface{}) (SpanContext, error) {
+ carrier, ok := abstractCarrier.(ExtractableZipkinSpan)
+ if !ok {
+ return emptyContext, opentracing.ErrInvalidCarrier
+ }
+ if carrier.TraceID() == 0 {
+ return emptyContext, opentracing.ErrSpanContextNotFound
+ }
+ var ctx SpanContext
+ ctx.traceID.Low = carrier.TraceID()
+ ctx.spanID = SpanID(carrier.SpanID())
+ ctx.parentID = SpanID(carrier.ParentID())
+ ctx.flags = carrier.Flags()
+ return ctx, nil
+}
diff --git a/vendor/github.com/uber/jaeger-client-go/zipkin_thrift_span.go b/vendor/github.com/uber/jaeger-client-go/zipkin_thrift_span.go
new file mode 100644
index 000000000..dce58b433
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-client-go/zipkin_thrift_span.go
@@ -0,0 +1,322 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package jaeger
+
+import (
+ "encoding/binary"
+ "fmt"
+ "time"
+
+ "github.com/opentracing/opentracing-go/ext"
+
+ "github.com/uber/jaeger-client-go/internal/spanlog"
+ z "github.com/uber/jaeger-client-go/thrift-gen/zipkincore"
+ "github.com/uber/jaeger-client-go/utils"
+)
+
+const (
+ // Zipkin UI does not work well with non-string tag values
+ allowPackedNumbers = false
+)
+
+var specialTagHandlers = map[string]func(*zipkinSpan, interface{}){
+ string(ext.SpanKind): setSpanKind,
+ string(ext.PeerHostIPv4): setPeerIPv4,
+ string(ext.PeerPort): setPeerPort,
+ string(ext.PeerService): setPeerService,
+ TracerIPTagKey: removeTag,
+}
+
+// BuildZipkinThrift builds thrift span based on internal span.
+func BuildZipkinThrift(s *Span) *z.Span {
+ span := &zipkinSpan{Span: s}
+ span.handleSpecialTags()
+ parentID := int64(span.context.parentID)
+ var ptrParentID *int64
+ if parentID != 0 {
+ ptrParentID = &parentID
+ }
+ timestamp := utils.TimeToMicrosecondsSinceEpochInt64(span.startTime)
+ duration := span.duration.Nanoseconds() / int64(time.Microsecond)
+ endpoint := &z.Endpoint{
+ ServiceName: span.tracer.serviceName,
+ Ipv4: int32(span.tracer.hostIPv4)}
+ thriftSpan := &z.Span{
+ TraceID: int64(span.context.traceID.Low), // TODO upgrade zipkin thrift and use TraceIdHigh
+ ID: int64(span.context.spanID),
+ ParentID: ptrParentID,
+ Name: span.operationName,
+ Timestamp: &timestamp,
+ Duration: &duration,
+ Debug: span.context.IsDebug(),
+ Annotations: buildAnnotations(span, endpoint),
+ BinaryAnnotations: buildBinaryAnnotations(span, endpoint)}
+ return thriftSpan
+}
+
+func buildAnnotations(span *zipkinSpan, endpoint *z.Endpoint) []*z.Annotation {
+ // automatically adding 2 Zipkin CoreAnnotations
+ annotations := make([]*z.Annotation, 0, 2+len(span.logs))
+ var startLabel, endLabel string
+ if span.spanKind == string(ext.SpanKindRPCClientEnum) {
+ startLabel, endLabel = z.CLIENT_SEND, z.CLIENT_RECV
+ } else if span.spanKind == string(ext.SpanKindRPCServerEnum) {
+ startLabel, endLabel = z.SERVER_RECV, z.SERVER_SEND
+ }
+ if !span.startTime.IsZero() && startLabel != "" {
+ start := &z.Annotation{
+ Timestamp: utils.TimeToMicrosecondsSinceEpochInt64(span.startTime),
+ Value: startLabel,
+ Host: endpoint}
+ annotations = append(annotations, start)
+ if span.duration != 0 {
+ endTs := span.startTime.Add(span.duration)
+ end := &z.Annotation{
+ Timestamp: utils.TimeToMicrosecondsSinceEpochInt64(endTs),
+ Value: endLabel,
+ Host: endpoint}
+ annotations = append(annotations, end)
+ }
+ }
+ for _, log := range span.logs {
+ anno := &z.Annotation{
+ Timestamp: utils.TimeToMicrosecondsSinceEpochInt64(log.Timestamp),
+ Host: endpoint}
+ if content, err := spanlog.MaterializeWithJSON(log.Fields); err == nil {
+ anno.Value = truncateString(string(content), span.tracer.options.maxTagValueLength)
+ } else {
+ anno.Value = err.Error()
+ }
+ annotations = append(annotations, anno)
+ }
+ return annotations
+}
+
+func buildBinaryAnnotations(span *zipkinSpan, endpoint *z.Endpoint) []*z.BinaryAnnotation {
+ // automatically adding local component or server/client address tag, and client version
+ annotations := make([]*z.BinaryAnnotation, 0, 2+len(span.tags))
+
+ if span.peerDefined() && span.isRPC() {
+ peer := z.Endpoint{
+ Ipv4: span.peer.Ipv4,
+ Port: span.peer.Port,
+ ServiceName: span.peer.ServiceName}
+ label := z.CLIENT_ADDR
+ if span.isRPCClient() {
+ label = z.SERVER_ADDR
+ }
+ anno := &z.BinaryAnnotation{
+ Key: label,
+ Value: []byte{1},
+ AnnotationType: z.AnnotationType_BOOL,
+ Host: &peer}
+ annotations = append(annotations, anno)
+ }
+ if !span.isRPC() {
+ componentName := endpoint.ServiceName
+ for _, tag := range span.tags {
+ if tag.key == string(ext.Component) {
+ componentName = stringify(tag.value)
+ break
+ }
+ }
+ local := &z.BinaryAnnotation{
+ Key: z.LOCAL_COMPONENT,
+ Value: []byte(componentName),
+ AnnotationType: z.AnnotationType_STRING,
+ Host: endpoint}
+ annotations = append(annotations, local)
+ }
+ for _, tag := range span.tags {
+ // "Special tags" are already handled by this point, we'd be double reporting the
+ // tags if we don't skip here
+ if _, ok := specialTagHandlers[tag.key]; ok {
+ continue
+ }
+ if anno := buildBinaryAnnotation(tag.key, tag.value, span.tracer.options.maxTagValueLength, nil); anno != nil {
+ annotations = append(annotations, anno)
+ }
+ }
+ return annotations
+}
+
+func buildBinaryAnnotation(key string, val interface{}, maxTagValueLength int, endpoint *z.Endpoint) *z.BinaryAnnotation {
+ bann := &z.BinaryAnnotation{Key: key, Host: endpoint}
+ if value, ok := val.(string); ok {
+ bann.Value = []byte(truncateString(value, maxTagValueLength))
+ bann.AnnotationType = z.AnnotationType_STRING
+ } else if value, ok := val.([]byte); ok {
+ if len(value) > maxTagValueLength {
+ value = value[:maxTagValueLength]
+ }
+ bann.Value = value
+ bann.AnnotationType = z.AnnotationType_BYTES
+ } else if value, ok := val.(int32); ok && allowPackedNumbers {
+ bann.Value = int32ToBytes(value)
+ bann.AnnotationType = z.AnnotationType_I32
+ } else if value, ok := val.(int64); ok && allowPackedNumbers {
+ bann.Value = int64ToBytes(value)
+ bann.AnnotationType = z.AnnotationType_I64
+ } else if value, ok := val.(int); ok && allowPackedNumbers {
+ bann.Value = int64ToBytes(int64(value))
+ bann.AnnotationType = z.AnnotationType_I64
+ } else if value, ok := val.(bool); ok {
+ bann.Value = []byte{boolToByte(value)}
+ bann.AnnotationType = z.AnnotationType_BOOL
+ } else {
+ value := stringify(val)
+ bann.Value = []byte(truncateString(value, maxTagValueLength))
+ bann.AnnotationType = z.AnnotationType_STRING
+ }
+ return bann
+}
+
+func stringify(value interface{}) string {
+ if s, ok := value.(string); ok {
+ return s
+ }
+ return fmt.Sprintf("%+v", value)
+}
+
+func truncateString(value string, maxLength int) string {
+ // we ignore the problem of utf8 runes possibly being sliced in the middle,
+ // as it is rather expensive to iterate through each tag just to find rune
+ // boundaries.
+ if len(value) > maxLength {
+ return value[:maxLength]
+ }
+ return value
+}
+
+func boolToByte(b bool) byte {
+ if b {
+ return 1
+ }
+ return 0
+}
+
+// int32ToBytes converts int32 to bytes.
+func int32ToBytes(i int32) []byte {
+ buf := make([]byte, 4)
+ binary.BigEndian.PutUint32(buf, uint32(i))
+ return buf
+}
+
+// int64ToBytes converts int64 to bytes.
+func int64ToBytes(i int64) []byte {
+ buf := make([]byte, 8)
+ binary.BigEndian.PutUint64(buf, uint64(i))
+ return buf
+}
+
+type zipkinSpan struct {
+ *Span
+
+ // peer points to the peer service participating in this span,
+ // e.g. the Client if this span is a server span,
+ // or Server if this span is a client span
+ peer struct {
+ Ipv4 int32
+ Port int16
+ ServiceName string
+ }
+
+ // used to distinguish local vs. RPC Server vs. RPC Client spans
+ spanKind string
+}
+
+func (s *zipkinSpan) handleSpecialTags() {
+ s.Lock()
+ defer s.Unlock()
+ if s.firstInProcess {
+ // append the process tags
+ s.tags = append(s.tags, s.tracer.tags...)
+ }
+ filteredTags := make([]Tag, 0, len(s.tags))
+ for _, tag := range s.tags {
+ if handler, ok := specialTagHandlers[tag.key]; ok {
+ handler(s, tag.value)
+ } else {
+ filteredTags = append(filteredTags, tag)
+ }
+ }
+ s.tags = filteredTags
+}
+
+func setSpanKind(s *zipkinSpan, value interface{}) {
+ if val, ok := value.(string); ok {
+ s.spanKind = val
+ return
+ }
+ if val, ok := value.(ext.SpanKindEnum); ok {
+ s.spanKind = string(val)
+ }
+}
+
+func setPeerIPv4(s *zipkinSpan, value interface{}) {
+ if val, ok := value.(string); ok {
+ if ip, err := utils.ParseIPToUint32(val); err == nil {
+ s.peer.Ipv4 = int32(ip)
+ return
+ }
+ }
+ if val, ok := value.(uint32); ok {
+ s.peer.Ipv4 = int32(val)
+ return
+ }
+ if val, ok := value.(int32); ok {
+ s.peer.Ipv4 = val
+ }
+}
+
+func setPeerPort(s *zipkinSpan, value interface{}) {
+ if val, ok := value.(string); ok {
+ if port, err := utils.ParsePort(val); err == nil {
+ s.peer.Port = int16(port)
+ return
+ }
+ }
+ if val, ok := value.(uint16); ok {
+ s.peer.Port = int16(val)
+ return
+ }
+ if val, ok := value.(int); ok {
+ s.peer.Port = int16(val)
+ }
+}
+
+func setPeerService(s *zipkinSpan, value interface{}) {
+ if val, ok := value.(string); ok {
+ s.peer.ServiceName = val
+ }
+}
+
+func removeTag(s *zipkinSpan, value interface{}) {}
+
+func (s *zipkinSpan) peerDefined() bool {
+ return s.peer.ServiceName != "" || s.peer.Ipv4 != 0 || s.peer.Port != 0
+}
+
+func (s *zipkinSpan) isRPC() bool {
+ s.RLock()
+ defer s.RUnlock()
+ return s.spanKind == string(ext.SpanKindRPCClientEnum) || s.spanKind == string(ext.SpanKindRPCServerEnum)
+}
+
+func (s *zipkinSpan) isRPCClient() bool {
+ s.RLock()
+ defer s.RUnlock()
+ return s.spanKind == string(ext.SpanKindRPCClientEnum)
+}
diff --git a/vendor/github.com/uber/jaeger-lib/LICENSE b/vendor/github.com/uber/jaeger-lib/LICENSE
new file mode 100644
index 000000000..261eeb9e9
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-lib/LICENSE
@@ -0,0 +1,201 @@
+ Apache License
+ Version 2.0, January 2004
+ http://www.apache.org/licenses/
+
+ TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
+
+ 1. Definitions.
+
+ "License" shall mean the terms and conditions for use, reproduction,
+ and distribution as defined by Sections 1 through 9 of this document.
+
+ "Licensor" shall mean the copyright owner or entity authorized by
+ the copyright owner that is granting the License.
+
+ "Legal Entity" shall mean the union of the acting entity and all
+ other entities that control, are controlled by, or are under common
+ control with that entity. For the purposes of this definition,
+ "control" means (i) the power, direct or indirect, to cause the
+ direction or management of such entity, whether by contract or
+ otherwise, or (ii) ownership of fifty percent (50%) or more of the
+ outstanding shares, or (iii) beneficial ownership of such entity.
+
+ "You" (or "Your") shall mean an individual or Legal Entity
+ exercising permissions granted by this License.
+
+ "Source" form shall mean the preferred form for making modifications,
+ including but not limited to software source code, documentation
+ source, and configuration files.
+
+ "Object" form shall mean any form resulting from mechanical
+ transformation or translation of a Source form, including but
+ not limited to compiled object code, generated documentation,
+ and conversions to other media types.
+
+ "Work" shall mean the work of authorship, whether in Source or
+ Object form, made available under the License, as indicated by a
+ copyright notice that is included in or attached to the work
+ (an example is provided in the Appendix below).
+
+ "Derivative Works" shall mean any work, whether in Source or Object
+ form, that is based on (or derived from) the Work and for which the
+ editorial revisions, annotations, elaborations, or other modifications
+ represent, as a whole, an original work of authorship. For the purposes
+ of this License, Derivative Works shall not include works that remain
+ separable from, or merely link (or bind by name) to the interfaces of,
+ the Work and Derivative Works thereof.
+
+ "Contribution" shall mean any work of authorship, including
+ the original version of the Work and any modifications or additions
+ to that Work or Derivative Works thereof, that is intentionally
+ submitted to Licensor for inclusion in the Work by the copyright owner
+ or by an individual or Legal Entity authorized to submit on behalf of
+ the copyright owner. For the purposes of this definition, "submitted"
+ means any form of electronic, verbal, or written communication sent
+ to the Licensor or its representatives, including but not limited to
+ communication on electronic mailing lists, source code control systems,
+ and issue tracking systems that are managed by, or on behalf of, the
+ Licensor for the purpose of discussing and improving the Work, but
+ excluding communication that is conspicuously marked or otherwise
+ designated in writing by the copyright owner as "Not a Contribution."
+
+ "Contributor" shall mean Licensor and any individual or Legal Entity
+ on behalf of whom a Contribution has been received by Licensor and
+ subsequently incorporated within the Work.
+
+ 2. Grant of Copyright License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ copyright license to reproduce, prepare Derivative Works of,
+ publicly display, publicly perform, sublicense, and distribute the
+ Work and such Derivative Works in Source or Object form.
+
+ 3. Grant of Patent License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ (except as stated in this section) patent license to make, have made,
+ use, offer to sell, sell, import, and otherwise transfer the Work,
+ where such license applies only to those patent claims licensable
+ by such Contributor that are necessarily infringed by their
+ Contribution(s) alone or by combination of their Contribution(s)
+ with the Work to which such Contribution(s) was submitted. If You
+ institute patent litigation against any entity (including a
+ cross-claim or counterclaim in a lawsuit) alleging that the Work
+ or a Contribution incorporated within the Work constitutes direct
+ or contributory patent infringement, then any patent licenses
+ granted to You under this License for that Work shall terminate
+ as of the date such litigation is filed.
+
+ 4. Redistribution. You may reproduce and distribute copies of the
+ Work or Derivative Works thereof in any medium, with or without
+ modifications, and in Source or Object form, provided that You
+ meet the following conditions:
+
+ (a) You must give any other recipients of the Work or
+ Derivative Works a copy of this License; and
+
+ (b) You must cause any modified files to carry prominent notices
+ stating that You changed the files; and
+
+ (c) You must retain, in the Source form of any Derivative Works
+ that You distribute, all copyright, patent, trademark, and
+ attribution notices from the Source form of the Work,
+ excluding those notices that do not pertain to any part of
+ the Derivative Works; and
+
+ (d) If the Work includes a "NOTICE" text file as part of its
+ distribution, then any Derivative Works that You distribute must
+ include a readable copy of the attribution notices contained
+ within such NOTICE file, excluding those notices that do not
+ pertain to any part of the Derivative Works, in at least one
+ of the following places: within a NOTICE text file distributed
+ as part of the Derivative Works; within the Source form or
+ documentation, if provided along with the Derivative Works; or,
+ within a display generated by the Derivative Works, if and
+ wherever such third-party notices normally appear. The contents
+ of the NOTICE file are for informational purposes only and
+ do not modify the License. You may add Your own attribution
+ notices within Derivative Works that You distribute, alongside
+ or as an addendum to the NOTICE text from the Work, provided
+ that such additional attribution notices cannot be construed
+ as modifying the License.
+
+ You may add Your own copyright statement to Your modifications and
+ may provide additional or different license terms and conditions
+ for use, reproduction, or distribution of Your modifications, or
+ for any such Derivative Works as a whole, provided Your use,
+ reproduction, and distribution of the Work otherwise complies with
+ the conditions stated in this License.
+
+ 5. Submission of Contributions. Unless You explicitly state otherwise,
+ any Contribution intentionally submitted for inclusion in the Work
+ by You to the Licensor shall be under the terms and conditions of
+ this License, without any additional terms or conditions.
+ Notwithstanding the above, nothing herein shall supersede or modify
+ the terms of any separate license agreement you may have executed
+ with Licensor regarding such Contributions.
+
+ 6. Trademarks. This License does not grant permission to use the trade
+ names, trademarks, service marks, or product names of the Licensor,
+ except as required for reasonable and customary use in describing the
+ origin of the Work and reproducing the content of the NOTICE file.
+
+ 7. Disclaimer of Warranty. Unless required by applicable law or
+ agreed to in writing, Licensor provides the Work (and each
+ Contributor provides its Contributions) on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
+ implied, including, without limitation, any warranties or conditions
+ of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
+ PARTICULAR PURPOSE. You are solely responsible for determining the
+ appropriateness of using or redistributing the Work and assume any
+ risks associated with Your exercise of permissions under this License.
+
+ 8. Limitation of Liability. In no event and under no legal theory,
+ whether in tort (including negligence), contract, or otherwise,
+ unless required by applicable law (such as deliberate and grossly
+ negligent acts) or agreed to in writing, shall any Contributor be
+ liable to You for damages, including any direct, indirect, special,
+ incidental, or consequential damages of any character arising as a
+ result of this License or out of the use or inability to use the
+ Work (including but not limited to damages for loss of goodwill,
+ work stoppage, computer failure or malfunction, or any and all
+ other commercial damages or losses), even if such Contributor
+ has been advised of the possibility of such damages.
+
+ 9. Accepting Warranty or Additional Liability. While redistributing
+ the Work or Derivative Works thereof, You may choose to offer,
+ and charge a fee for, acceptance of support, warranty, indemnity,
+ or other liability obligations and/or rights consistent with this
+ License. However, in accepting such obligations, You may act only
+ on Your own behalf and on Your sole responsibility, not on behalf
+ of any other Contributor, and only if You agree to indemnify,
+ defend, and hold each Contributor harmless for any liability
+ incurred by, or claims asserted against, such Contributor by reason
+ of your accepting any such warranty or additional liability.
+
+ END OF TERMS AND CONDITIONS
+
+ APPENDIX: How to apply the Apache License to your work.
+
+ To apply the Apache License to your work, attach the following
+ boilerplate notice, with the fields enclosed by brackets "[]"
+ replaced with your own identifying information. (Don't include
+ the brackets!) The text should be enclosed in the appropriate
+ comment syntax for the file format. We also recommend that a
+ file or class name and description of purpose be included on the
+ same "printed page" as the copyright notice for easier
+ identification within third-party archives.
+
+ Copyright [yyyy] [name of copyright owner]
+
+ 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.
diff --git a/vendor/github.com/uber/jaeger-lib/metrics/counter.go b/vendor/github.com/uber/jaeger-lib/metrics/counter.go
new file mode 100644
index 000000000..2a6a43efd
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-lib/metrics/counter.go
@@ -0,0 +1,28 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package metrics
+
+// Counter tracks the number of times an event has occurred
+type Counter interface {
+ // Inc adds the given value to the counter.
+ Inc(int64)
+}
+
+// NullCounter counter that does nothing
+var NullCounter Counter = nullCounter{}
+
+type nullCounter struct{}
+
+func (nullCounter) Inc(int64) {}
diff --git a/vendor/github.com/uber/jaeger-lib/metrics/factory.go b/vendor/github.com/uber/jaeger-lib/metrics/factory.go
new file mode 100644
index 000000000..a744a890d
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-lib/metrics/factory.go
@@ -0,0 +1,35 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package metrics
+
+// Factory creates new metrics
+type Factory interface {
+ Counter(name string, tags map[string]string) Counter
+ Timer(name string, tags map[string]string) Timer
+ Gauge(name string, tags map[string]string) Gauge
+
+ // Namespace returns a nested metrics factory.
+ Namespace(name string, tags map[string]string) Factory
+}
+
+// NullFactory is a metrics factory that returns NullCounter, NullTimer, and NullGauge.
+var NullFactory Factory = nullFactory{}
+
+type nullFactory struct{}
+
+func (nullFactory) Counter(name string, tags map[string]string) Counter { return NullCounter }
+func (nullFactory) Timer(name string, tags map[string]string) Timer { return NullTimer }
+func (nullFactory) Gauge(name string, tags map[string]string) Gauge { return NullGauge }
+func (nullFactory) Namespace(name string, tags map[string]string) Factory { return NullFactory }
diff --git a/vendor/github.com/uber/jaeger-lib/metrics/gauge.go b/vendor/github.com/uber/jaeger-lib/metrics/gauge.go
new file mode 100644
index 000000000..3c606391a
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-lib/metrics/gauge.go
@@ -0,0 +1,28 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package metrics
+
+// Gauge returns instantaneous measurements of something as an int64 value
+type Gauge interface {
+ // Update the gauge to the value passed in.
+ Update(int64)
+}
+
+// NullGauge gauge that does nothing
+var NullGauge Gauge = nullGauge{}
+
+type nullGauge struct{}
+
+func (nullGauge) Update(int64) {}
diff --git a/vendor/github.com/uber/jaeger-lib/metrics/keys.go b/vendor/github.com/uber/jaeger-lib/metrics/keys.go
new file mode 100644
index 000000000..c24445a10
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-lib/metrics/keys.go
@@ -0,0 +1,35 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package metrics
+
+import (
+ "sort"
+)
+
+// GetKey converts name+tags into a single string of the form
+// "name|tag1=value1|...|tagN=valueN", where tag names are
+// sorted alphabetically.
+func GetKey(name string, tags map[string]string, tagsSep string, tagKVSep string) string {
+ keys := make([]string, 0, len(tags))
+ for k := range tags {
+ keys = append(keys, k)
+ }
+ sort.Strings(keys)
+ key := name
+ for _, k := range keys {
+ key = key + tagsSep + k + tagKVSep + tags[k]
+ }
+ return key
+}
diff --git a/vendor/github.com/uber/jaeger-lib/metrics/metrics.go b/vendor/github.com/uber/jaeger-lib/metrics/metrics.go
new file mode 100644
index 000000000..4c36b7505
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-lib/metrics/metrics.go
@@ -0,0 +1,90 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package metrics
+
+import (
+ "fmt"
+ "reflect"
+ "strings"
+)
+
+// Init initializes the passed in metrics and initializes its fields using the passed in factory.
+//
+// It uses reflection to initialize a struct containing metrics fields
+// by assigning new Counter/Gauge/Timer values with the metric name retrieved
+// from the `metric` tag and stats tags retrieved from the `tags` tag.
+//
+// Note: all fields of the struct must be exported, have a `metric` tag, and be
+// of type Counter or Gauge or Timer.
+//
+// Errors during Init lead to a panic.
+func Init(metrics interface{}, factory Factory, globalTags map[string]string) {
+ if err := InitOrError(metrics, factory, globalTags); err != nil {
+ panic(err.Error())
+ }
+}
+
+// InitOrError does the same as Init, but returns an error instead of
+// panicking.
+func InitOrError(m interface{}, factory Factory, globalTags map[string]string) error {
+ // Allow user to opt out of reporting metrics by passing in nil.
+ if factory == nil {
+ factory = NullFactory
+ }
+
+ counterPtrType := reflect.TypeOf((*Counter)(nil)).Elem()
+ gaugePtrType := reflect.TypeOf((*Gauge)(nil)).Elem()
+ timerPtrType := reflect.TypeOf((*Timer)(nil)).Elem()
+
+ v := reflect.ValueOf(m).Elem()
+ t := v.Type()
+ for i := 0; i < t.NumField(); i++ {
+ tags := make(map[string]string)
+ for k, v := range globalTags {
+ tags[k] = v
+ }
+ field := t.Field(i)
+ metric := field.Tag.Get("metric")
+ if metric == "" {
+ return fmt.Errorf("Field %s is missing a tag 'metric'", field.Name)
+ }
+ if tagString := field.Tag.Get("tags"); tagString != "" {
+ tagPairs := strings.Split(tagString, ",")
+ for _, tagPair := range tagPairs {
+ tag := strings.Split(tagPair, "=")
+ if len(tag) != 2 {
+ return fmt.Errorf(
+ "Field [%s]: Tag [%s] is not of the form key=value in 'tags' string [%s]",
+ field.Name, tagPair, tagString)
+ }
+ tags[tag[0]] = tag[1]
+ }
+ }
+ var obj interface{}
+ if field.Type.AssignableTo(counterPtrType) {
+ obj = factory.Counter(metric, tags)
+ } else if field.Type.AssignableTo(gaugePtrType) {
+ obj = factory.Gauge(metric, tags)
+ } else if field.Type.AssignableTo(timerPtrType) {
+ obj = factory.Timer(metric, tags)
+ } else {
+ return fmt.Errorf(
+ "Field %s is not a pointer to timer, gauge, or counter",
+ field.Name)
+ }
+ v.Field(i).Set(reflect.ValueOf(obj))
+ }
+ return nil
+}
diff --git a/vendor/github.com/uber/jaeger-lib/metrics/stopwatch.go b/vendor/github.com/uber/jaeger-lib/metrics/stopwatch.go
new file mode 100644
index 000000000..4a8abdb53
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-lib/metrics/stopwatch.go
@@ -0,0 +1,43 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package metrics
+
+import (
+ "time"
+)
+
+// StartStopwatch begins recording the executing time of an event, returning
+// a Stopwatch that should be used to stop the recording the time for
+// that event. Multiple events can be occurring simultaneously each
+// represented by different active Stopwatches
+func StartStopwatch(timer Timer) Stopwatch {
+ return Stopwatch{t: timer, start: time.Now()}
+}
+
+// A Stopwatch tracks the execution time of a specific event
+type Stopwatch struct {
+ t Timer
+ start time.Time
+}
+
+// Stop stops executing of the stopwatch and records the amount of elapsed time
+func (s Stopwatch) Stop() {
+ s.t.Record(s.ElapsedTime())
+}
+
+// ElapsedTime returns the amount of elapsed time (in time.Duration)
+func (s Stopwatch) ElapsedTime() time.Duration {
+ return time.Since(s.start)
+}
diff --git a/vendor/github.com/uber/jaeger-lib/metrics/timer.go b/vendor/github.com/uber/jaeger-lib/metrics/timer.go
new file mode 100644
index 000000000..e18d222ab
--- /dev/null
+++ b/vendor/github.com/uber/jaeger-lib/metrics/timer.go
@@ -0,0 +1,33 @@
+// Copyright (c) 2017 Uber Technologies, Inc.
+//
+// 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.
+
+package metrics
+
+import (
+ "time"
+)
+
+// Timer accumulates observations about how long some operation took,
+// and also maintains a historgam of percentiles.
+type Timer interface {
+ // Records the time passed in.
+ Record(time.Duration)
+}
+
+// NullTimer timer that does nothing
+var NullTimer Timer = nullTimer{}
+
+type nullTimer struct{}
+
+func (nullTimer) Record(time.Duration) {}
diff --git a/vendor/gitlab.com/gitlab-org/labkit/correlation/context.go b/vendor/gitlab.com/gitlab-org/labkit/correlation/context.go
index 911c82d81..951fcb5e6 100644
--- a/vendor/gitlab.com/gitlab-org/labkit/correlation/context.go
+++ b/vendor/gitlab.com/gitlab-org/labkit/correlation/context.go
@@ -26,7 +26,8 @@ func ExtractFromContext(ctx context.Context) string {
return str
}
-// ContextWithCorrelation will create a new context containing the Correlation-ID value
+// ContextWithCorrelation will create a new context containing the provided Correlation-ID value
+// This can be extracted using ExtractFromContext
func ContextWithCorrelation(ctx context.Context, correlationID string) context.Context {
return context.WithValue(ctx, keyCorrelationID, correlationID)
}
diff --git a/vendor/gitlab.com/gitlab-org/labkit/correlation/doc.go b/vendor/gitlab.com/gitlab-org/labkit/correlation/doc.go
new file mode 100644
index 000000000..eb8b581a4
--- /dev/null
+++ b/vendor/gitlab.com/gitlab-org/labkit/correlation/doc.go
@@ -0,0 +1,18 @@
+/*
+Package correlation is the primary entrypoint into LabKit's correlation utilities.
+
+Provided Functionality
+
+Provides http middlewares for general purpose use cases:
+
+Generating a correlation-id for an incoming HTTP request using .
+
+Obtaining the correlation-id from the context.
+
+Injecting the correlation-id from the context into an outgoing request.
+
+Still to be implemented
+
+Extracting a correlation-id from an incoming HTTP request into the context.
+*/
+package correlation
diff --git a/vendor/gitlab.com/gitlab-org/labkit/correlation/inbound_http.go b/vendor/gitlab.com/gitlab-org/labkit/correlation/inbound_http.go
index 1ff43a211..b7a297c3d 100644
--- a/vendor/gitlab.com/gitlab-org/labkit/correlation/inbound_http.go
+++ b/vendor/gitlab.com/gitlab-org/labkit/correlation/inbound_http.go
@@ -4,17 +4,33 @@ import (
"net/http"
)
-// InjectCorrelationID middleware will propagate or create a Correlation-ID for the incoming request
+// InjectCorrelationID is an HTTP middleware to generate an Correlation-ID for the incoming request,
+// or extract the existing Correlation-ID from the incoming request. By default, any upstream Correlation-ID,
+// passed in via the `X-Request-ID` header will be ignored. To enable this behaviour, the `WithPropagation`
+// option should be passed into the options.
+// Whether the Correlation-ID is generated or propagated, once inside this handler the request context
+// will have a Correlation-ID associated with it.
func InjectCorrelationID(h http.Handler, opts ...InboundHandlerOption) http.Handler {
// Currently we don't use any of the options available
- applyInboundHandlerOptions(opts)
+ config := applyInboundHandlerOptions(opts)
return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
parent := r.Context()
- var correlationID = generateRandomCorrelationIDWithFallback(r)
+ correlationID := ""
+ if config.propagation {
+ correlationID = extractFromRequest(r)
+ }
+
+ if correlationID == "" {
+ correlationID = generateRandomCorrelationIDWithFallback(r)
+ }
ctx := ContextWithCorrelation(parent, correlationID)
h.ServeHTTP(w, r.WithContext(ctx))
})
}
+
+func extractFromRequest(r *http.Request) string {
+ return r.Header.Get(propagationHeader)
+}
diff --git a/vendor/gitlab.com/gitlab-org/labkit/correlation/inbound_http_options.go b/vendor/gitlab.com/gitlab-org/labkit/correlation/inbound_http_options.go
index c68ee8e36..2bad8e46c 100644
--- a/vendor/gitlab.com/gitlab-org/labkit/correlation/inbound_http_options.go
+++ b/vendor/gitlab.com/gitlab-org/labkit/correlation/inbound_http_options.go
@@ -2,6 +2,7 @@ package correlation
// The configuration for InjectCorrelationID
type inboundHandlerConfig struct {
+ propagation bool
}
// InboundHandlerOption will configure a correlation handler
@@ -10,10 +11,21 @@ type inboundHandlerConfig struct {
type InboundHandlerOption func(*inboundHandlerConfig)
func applyInboundHandlerOptions(opts []InboundHandlerOption) inboundHandlerConfig {
- config := inboundHandlerConfig{}
+ config := inboundHandlerConfig{
+ propagation: false,
+ }
for _, v := range opts {
v(&config)
}
return config
}
+
+// WithPropagation will configure the handler to propagate existing correlation_ids
+// passed in from upstream services.
+// This is not the default behaviour.
+func WithPropagation() InboundHandlerOption {
+ return func(config *inboundHandlerConfig) {
+ config.propagation = true
+ }
+}
diff --git a/vendor/gitlab.com/gitlab-org/labkit/correlation/outbound_http.go b/vendor/gitlab.com/gitlab-org/labkit/correlation/outbound_http.go
index f8922a7d3..0345a37be 100644
--- a/vendor/gitlab.com/gitlab-org/labkit/correlation/outbound_http.go
+++ b/vendor/gitlab.com/gitlab-org/labkit/correlation/outbound_http.go
@@ -26,7 +26,10 @@ func (c instrumentedRoundTripper) RoundTrip(req *http.Request) (res *http.Respon
// NewInstrumentedRoundTripper acts as a "client-middleware" for outbound http requests
// adding instrumentation to the outbound request and then delegating to the underlying
-// transport
+// transport.
+//
+// If will extract the current Correlation-ID from the request context and pass this via
+// the X-Request-ID request header to downstream services.
func NewInstrumentedRoundTripper(delegate http.RoundTripper, opts ...InstrumentedRoundTripperOption) http.RoundTripper {
// Currently we don't use any of the options available
applyInstrumentedRoundTripperOptions(opts)
diff --git a/vendor/gitlab.com/gitlab-org/labkit/tracing/connstr/connection_string_parser.go b/vendor/gitlab.com/gitlab-org/labkit/tracing/connstr/connection_string_parser.go
new file mode 100644
index 000000000..97128de63
--- /dev/null
+++ b/vendor/gitlab.com/gitlab-org/labkit/tracing/connstr/connection_string_parser.go
@@ -0,0 +1,55 @@
+package connstr
+
+import (
+ "fmt"
+ "net/url"
+ "regexp"
+)
+
+// Connection strings:
+// * opentracing://jaeger
+// * opentracing://datadog
+// * opentracing://lightstep?access_key=12345
+
+var errInvalidConnection = fmt.Errorf("invalid connection string")
+
+// Parse parses a opentracing connection string into a driverName and options map.
+func Parse(connectionString string) (driverName string, options map[string]string, err error) {
+ if connectionString == "" {
+ return "", nil, errInvalidConnection
+ }
+
+ URL, err := url.Parse(connectionString)
+ if err != nil {
+ return "", nil, errInvalidConnection
+ }
+
+ if URL.Scheme != "opentracing" {
+ return "", nil, errInvalidConnection
+ }
+
+ driverName = URL.Host
+ if driverName == "" {
+ return "", nil, errInvalidConnection
+ }
+
+ // Connection strings should not have a path
+ if URL.Path != "" {
+ return "", nil, errInvalidConnection
+ }
+
+ matched, err := regexp.MatchString("^[a-z0-9_]+$", driverName)
+ if err != nil || !matched {
+ return "", nil, errInvalidConnection
+ }
+
+ query := URL.Query()
+ driverName = URL.Host
+ options = make(map[string]string, len(query))
+
+ for k := range query {
+ options[k] = query.Get(k)
+ }
+
+ return driverName, options, nil
+}
diff --git a/vendor/gitlab.com/gitlab-org/labkit/tracing/errors.go b/vendor/gitlab.com/gitlab-org/labkit/tracing/errors.go
new file mode 100644
index 000000000..d63b41e3a
--- /dev/null
+++ b/vendor/gitlab.com/gitlab-org/labkit/tracing/errors.go
@@ -0,0 +1,8 @@
+package tracing
+
+import (
+ "fmt"
+)
+
+// ErrConfiguration is returned when the tracer is not properly configured.
+var ErrConfiguration = fmt.Errorf("Tracing is not properly configured")
diff --git a/vendor/gitlab.com/gitlab-org/labkit/tracing/grpc/client_interceptors.go b/vendor/gitlab.com/gitlab-org/labkit/tracing/grpc/client_interceptors.go
new file mode 100644
index 000000000..78b9694ab
--- /dev/null
+++ b/vendor/gitlab.com/gitlab-org/labkit/tracing/grpc/client_interceptors.go
@@ -0,0 +1,16 @@
+package grpccorrelation
+
+import (
+ "github.com/grpc-ecosystem/go-grpc-middleware/tracing/opentracing"
+ "google.golang.org/grpc"
+)
+
+// UnaryClientTracingInterceptor will create a unary client tracing interceptor
+func UnaryClientTracingInterceptor() grpc.UnaryClientInterceptor {
+ return grpc_opentracing.UnaryClientInterceptor()
+}
+
+// StreamClientTracingInterceptor will create a streaming client tracing interceptor
+func StreamClientTracingInterceptor() grpc.StreamClientInterceptor {
+ return grpc_opentracing.StreamClientInterceptor()
+}
diff --git a/vendor/gitlab.com/gitlab-org/labkit/tracing/grpc/server_interceptors.go b/vendor/gitlab.com/gitlab-org/labkit/tracing/grpc/server_interceptors.go
new file mode 100644
index 000000000..fdd3a884d
--- /dev/null
+++ b/vendor/gitlab.com/gitlab-org/labkit/tracing/grpc/server_interceptors.go
@@ -0,0 +1,16 @@
+package grpccorrelation
+
+import (
+ "github.com/grpc-ecosystem/go-grpc-middleware/tracing/opentracing"
+ "google.golang.org/grpc"
+)
+
+// UnaryServerTracingInterceptor will create a unary server tracing interceptor
+func UnaryServerTracingInterceptor() grpc.UnaryServerInterceptor {
+ return grpc_opentracing.UnaryServerInterceptor()
+}
+
+// StreamServerTracingInterceptor will create a streaming server tracing interceptor
+func StreamServerTracingInterceptor() grpc.StreamServerInterceptor {
+ return grpc_opentracing.StreamServerInterceptor()
+}
diff --git a/vendor/gitlab.com/gitlab-org/labkit/tracing/impl/constants.go b/vendor/gitlab.com/gitlab-org/labkit/tracing/impl/constants.go
new file mode 100644
index 000000000..083eaa4fd
--- /dev/null
+++ b/vendor/gitlab.com/gitlab-org/labkit/tracing/impl/constants.go
@@ -0,0 +1,3 @@
+package impl
+
+const keyStrictConnectionParsing = "strict_parsing"
diff --git a/vendor/gitlab.com/gitlab-org/labkit/tracing/impl/datadog_tracer.go b/vendor/gitlab.com/gitlab-org/labkit/tracing/impl/datadog_tracer.go
new file mode 100644
index 000000000..cff2f56a1
--- /dev/null
+++ b/vendor/gitlab.com/gitlab-org/labkit/tracing/impl/datadog_tracer.go
@@ -0,0 +1,24 @@
+// +build tracer_static,tracer_static_datadog
+
+package impl
+
+import (
+ "io"
+
+ opentracing "github.com/opentracing/opentracing-go"
+ "gopkg.in/DataDog/dd-trace-go.v1/ddtrace/opentracer"
+ "gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer"
+)
+
+func tracerFactory(config map[string]string) (opentracing.Tracer, io.Closer, error) {
+ opts := []tracer.StartOption{}
+ if config["ServiceName"] != "" {
+ opts = append(opts, tracer.WithServiceName(config["ServiceName"]))
+ }
+
+ return opentracer.New(opts...), nil, nil
+}
+
+func init() {
+ registerTracer("datadog", tracerFactory)
+}
diff --git a/vendor/gitlab.com/gitlab-org/labkit/tracing/impl/jaeger_tracer.go b/vendor/gitlab.com/gitlab-org/labkit/tracing/impl/jaeger_tracer.go
new file mode 100644
index 000000000..dc962d765
--- /dev/null
+++ b/vendor/gitlab.com/gitlab-org/labkit/tracing/impl/jaeger_tracer.go
@@ -0,0 +1,96 @@
+// +build tracer_static,tracer_static_jaeger
+
+package impl
+
+import (
+ "fmt"
+ "io"
+ "log"
+ "strconv"
+
+ opentracing "github.com/opentracing/opentracing-go"
+ jaegercfg "github.com/uber/jaeger-client-go/config"
+ jaegerlog "github.com/uber/jaeger-client-go/log"
+)
+
+type traceConfigMapper func(traceCfg *jaegercfg.Configuration, value string) ([]jaegercfg.Option, error)
+
+var configMapper = map[string]traceConfigMapper{
+ "ServiceName": func(traceCfg *jaegercfg.Configuration, value string) ([]jaegercfg.Option, error) {
+ traceCfg.ServiceName = value
+ return nil, nil
+ },
+ "debug": func(traceCfg *jaegercfg.Configuration, value string) ([]jaegercfg.Option, error) {
+ return []jaegercfg.Option{jaegercfg.Logger(jaegerlog.StdLogger)}, nil
+ },
+ "sampler": func(traceCfg *jaegercfg.Configuration, value string) ([]jaegercfg.Option, error) {
+ if traceCfg.Sampler == nil {
+ traceCfg.Sampler = &jaegercfg.SamplerConfig{}
+ }
+
+ traceCfg.Sampler.Type = value
+ return nil, nil
+ },
+ "sampler_param": func(traceCfg *jaegercfg.Configuration, value string) ([]jaegercfg.Option, error) {
+ if traceCfg.Sampler == nil {
+ traceCfg.Sampler = &jaegercfg.SamplerConfig{}
+ }
+ valuef, err := strconv.ParseFloat(value, 64)
+ if err != nil {
+ return nil, fmt.Errorf("jaeger tracer: sampler_param must be a float")
+ }
+
+ traceCfg.Sampler.Param = valuef
+ return nil, nil
+ },
+ "http_endpoint": func(traceCfg *jaegercfg.Configuration, value string) ([]jaegercfg.Option, error) {
+ if traceCfg.Reporter == nil {
+ traceCfg.Reporter = &jaegercfg.ReporterConfig{}
+ }
+ traceCfg.Reporter.CollectorEndpoint = value
+ return nil, nil
+ },
+ "udp_endpoint": func(traceCfg *jaegercfg.Configuration, value string) ([]jaegercfg.Option, error) {
+ if traceCfg.Reporter == nil {
+ traceCfg.Reporter = &jaegercfg.ReporterConfig{}
+ }
+ traceCfg.Reporter.LocalAgentHostPort = value
+ return nil, nil
+ },
+}
+
+func jaegerTracerFactory(config map[string]string) (opentracing.Tracer, io.Closer, error) {
+ traceCfg, err := jaegercfg.FromEnv()
+ if err != nil {
+ return nil, nil, err
+ }
+ options := []jaegercfg.Option{}
+
+ // Convert the configuration map into a jaeger configuration
+ for k, v := range config {
+ mapper := configMapper[k]
+ if k == keyStrictConnectionParsing {
+ continue
+ }
+
+ if mapper != nil {
+ o, err := mapper(traceCfg, v)
+ if err != nil {
+ return nil, nil, err
+ }
+ options = append(options, o...)
+ } else {
+ if config[keyStrictConnectionParsing] != "" {
+ return nil, nil, fmt.Errorf("jaeger tracer: invalid option: %s", k)
+ }
+
+ log.Printf("jaeger tracer: warning: ignoring unknown configuration option: %s", k)
+ }
+ }
+
+ return traceCfg.NewTracer(options...)
+}
+
+func init() {
+ registerTracer("jaeger", jaegerTracerFactory)
+}
diff --git a/vendor/gitlab.com/gitlab-org/labkit/tracing/impl/lightstep_tracer.go b/vendor/gitlab.com/gitlab-org/labkit/tracing/impl/lightstep_tracer.go
new file mode 100644
index 000000000..9654f01f7
--- /dev/null
+++ b/vendor/gitlab.com/gitlab-org/labkit/tracing/impl/lightstep_tracer.go
@@ -0,0 +1,71 @@
+// +build tracer_static,tracer_static_lightstep
+
+package impl
+
+import (
+ "context"
+ "fmt"
+ "io"
+ "log"
+
+ lightstep "github.com/lightstep/lightstep-tracer-go"
+ opentracing "github.com/opentracing/opentracing-go"
+)
+
+type lightstepCloser struct {
+ tracer lightstep.Tracer
+}
+
+func (c *lightstepCloser) Close() error {
+ lightstep.Close(context.Background(), c.tracer)
+ return nil
+}
+
+var lightstepConfigMapper = map[string]func(traceCfg *lightstep.Options, value string) error{
+ "ServiceName": func(options *lightstep.Options, value string) error {
+ options.Tags[lightstep.ComponentNameKey] = value
+ return nil
+ },
+ "access_token": func(options *lightstep.Options, value string) error {
+ options.AccessToken = value
+ return nil
+ },
+}
+
+func lightstepTracerFactory(config map[string]string) (opentracing.Tracer, io.Closer, error) {
+ options := lightstep.Options{
+ Tags: map[string]interface{}{},
+ }
+
+ // Convert the configuration map into a jaeger configuration
+ for k, v := range config {
+ mapper := lightstepConfigMapper[k]
+ if k == keyStrictConnectionParsing {
+ continue
+ }
+
+ if mapper != nil {
+ err := mapper(&options, v)
+ if err != nil {
+ return nil, nil, err
+ }
+ } else {
+ if config[keyStrictConnectionParsing] != "" {
+ return nil, nil, fmt.Errorf("lightstep tracer: invalid option: %s", k)
+ }
+
+ log.Printf("lightstep tracer: warning: ignoring unknown configuration option: %s", k)
+ }
+ }
+
+ tracer := lightstep.NewTracer(options)
+ if tracer == nil {
+ return nil, nil, fmt.Errorf("lightstep tracer: unable to create tracer, review log messages")
+ }
+
+ return tracer, &lightstepCloser{tracer}, nil
+}
+
+func init() {
+ registerTracer("lightstep", lightstepTracerFactory)
+}
diff --git a/vendor/gitlab.com/gitlab-org/labkit/tracing/impl/null_tracer.go b/vendor/gitlab.com/gitlab-org/labkit/tracing/impl/null_tracer.go
new file mode 100644
index 000000000..ddfe40602
--- /dev/null
+++ b/vendor/gitlab.com/gitlab-org/labkit/tracing/impl/null_tracer.go
@@ -0,0 +1,15 @@
+// +build !tracer_static
+
+package impl
+
+import (
+ "fmt"
+ "io"
+
+ opentracing "github.com/opentracing/opentracing-go"
+)
+
+// New will instantiate a new instance of the tracer, given the driver and configuration
+func New(driverName string, config map[string]string) (opentracing.Tracer, io.Closer, error) {
+ return nil, nil, fmt.Errorf("tracer: binary compiled without tracer support: cannot load driver %s", driverName)
+}
diff --git a/vendor/gitlab.com/gitlab-org/labkit/tracing/impl/static_tracer.go b/vendor/gitlab.com/gitlab-org/labkit/tracing/impl/static_tracer.go
new file mode 100644
index 000000000..2b482738c
--- /dev/null
+++ b/vendor/gitlab.com/gitlab-org/labkit/tracing/impl/static_tracer.go
@@ -0,0 +1,20 @@
+// +build tracer_static
+
+package impl
+
+import (
+ "fmt"
+ "io"
+
+ opentracing "github.com/opentracing/opentracing-go"
+)
+
+// New will instantiate a new instance of the tracer, given the driver and configuration
+func New(driverName string, config map[string]string) (opentracing.Tracer, io.Closer, error) {
+ factory := registry[driverName]
+ if factory == nil {
+ return nil, nil, fmt.Errorf("tracer: unable to load driver %s", driverName)
+ }
+
+ return factory(config)
+}
diff --git a/vendor/gitlab.com/gitlab-org/labkit/tracing/impl/tracer_registry.go b/vendor/gitlab.com/gitlab-org/labkit/tracing/impl/tracer_registry.go
new file mode 100644
index 000000000..2506469c8
--- /dev/null
+++ b/vendor/gitlab.com/gitlab-org/labkit/tracing/impl/tracer_registry.go
@@ -0,0 +1,15 @@
+package impl
+
+import (
+ "io"
+
+ opentracing "github.com/opentracing/opentracing-go"
+)
+
+type tracerFactoryFunc func(config map[string]string) (opentracing.Tracer, io.Closer, error)
+
+var registry = map[string]tracerFactoryFunc{}
+
+func registerTracer(name string, factory tracerFactoryFunc) {
+ registry[name] = factory
+}
diff --git a/vendor/gitlab.com/gitlab-org/labkit/tracing/inbound_http.go b/vendor/gitlab.com/gitlab-org/labkit/tracing/inbound_http.go
new file mode 100644
index 000000000..c0145652a
--- /dev/null
+++ b/vendor/gitlab.com/gitlab-org/labkit/tracing/inbound_http.go
@@ -0,0 +1,48 @@
+package tracing
+
+import (
+ "net/http"
+
+ opentracing "github.com/opentracing/opentracing-go"
+ "github.com/opentracing/opentracing-go/ext"
+ "gitlab.com/gitlab-org/labkit/correlation"
+)
+
+// Handler will extract tracing from inbound request
+func Handler(h http.Handler, opts ...HandlerOption) http.Handler {
+ config := applyHandlerOptions(opts)
+
+ return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
+ tracer := opentracing.GlobalTracer()
+ if tracer == nil {
+ h.ServeHTTP(w, r)
+ return
+ }
+
+ wireContext, _ := tracer.Extract(
+ opentracing.HTTPHeaders,
+ opentracing.HTTPHeadersCarrier(r.Header))
+
+ // Create the span referring to the RPC client if available.
+ // If wireContext == nil, a root span will be created.
+ additionalStartSpanOpts := []opentracing.StartSpanOption{
+ ext.RPCServerOption(wireContext),
+ }
+
+ correlationID := correlation.ExtractFromContext(r.Context())
+ if correlationID != "" {
+ additionalStartSpanOpts = append(additionalStartSpanOpts, opentracing.Tag{Key: "correlation_id", Value: correlationID})
+ }
+
+ serverSpan := opentracing.StartSpan(
+ config.getOperationName(r),
+ additionalStartSpanOpts...,
+ )
+ defer serverSpan.Finish()
+
+ ctx := opentracing.ContextWithSpan(r.Context(), serverSpan)
+
+ h.ServeHTTP(w, r.WithContext(ctx))
+ })
+
+}
diff --git a/vendor/gitlab.com/gitlab-org/labkit/tracing/inbound_http_options.go b/vendor/gitlab.com/gitlab-org/labkit/tracing/inbound_http_options.go
new file mode 100644
index 000000000..0a0aff607
--- /dev/null
+++ b/vendor/gitlab.com/gitlab-org/labkit/tracing/inbound_http_options.go
@@ -0,0 +1,42 @@
+package tracing
+
+import (
+ "fmt"
+ "net/http"
+)
+
+// OperationNamer will return an operation name given an HTTP request
+type OperationNamer func(*http.Request) string
+
+// The configuration for InjectCorrelationID
+type handlerConfig struct {
+ getOperationName OperationNamer
+}
+
+// HandlerOption will configure a correlation handler
+type HandlerOption func(*handlerConfig)
+
+func applyHandlerOptions(opts []HandlerOption) handlerConfig {
+ config := handlerConfig{
+ getOperationName: func(req *http.Request) string {
+ // By default use `GET /x/y/z` for operation names
+ return fmt.Sprintf("%s %s", req.Method, req.URL.Path)
+ },
+ }
+ for _, v := range opts {
+ v(&config)
+ }
+
+ return config
+}
+
+// WithRouteIdentifier allows a RouteIdentifier attribute to be set in the handler.
+// This value will appear in the traces
+func WithRouteIdentifier(routeIdentifier string) HandlerOption {
+ return func(config *handlerConfig) {
+ config.getOperationName = func(req *http.Request) string {
+ // Use `GET routeIdentifier` for operation names
+ return fmt.Sprintf("%s %s", req.Method, routeIdentifier)
+ }
+ }
+}
diff --git a/vendor/gitlab.com/gitlab-org/labkit/tracing/initialization.go b/vendor/gitlab.com/gitlab-org/labkit/tracing/initialization.go
new file mode 100644
index 000000000..d0ec3ba0f
--- /dev/null
+++ b/vendor/gitlab.com/gitlab-org/labkit/tracing/initialization.go
@@ -0,0 +1,53 @@
+package tracing
+
+import (
+ "io"
+ "log"
+
+ opentracing "github.com/opentracing/opentracing-go"
+ "gitlab.com/gitlab-org/labkit/tracing/connstr"
+ "gitlab.com/gitlab-org/labkit/tracing/impl"
+)
+
+type nopCloser struct {
+}
+
+func (nopCloser) Close() error { return nil }
+
+// Initialize will initialize distributed tracing
+func Initialize(opts ...InitializationOption) io.Closer {
+ config := applyInitializationOptions(opts)
+
+ if config.connectionString == "" {
+ // No opentracing connection has been set
+ return &nopCloser{}
+ }
+
+ driverName, options, err := connstr.Parse(config.connectionString)
+ if err != nil {
+ log.Printf("unable to parse connection: %v", err)
+ return &nopCloser{}
+ }
+
+ if config.serviceName != "" {
+ options["ServiceName"] = config.serviceName
+ }
+
+ tracer, closer, err := impl.New(driverName, options)
+ if err != nil {
+ log.Printf("skipping tracing configuration step: %v", err)
+ return &nopCloser{}
+ }
+
+ if tracer == nil {
+ log.Printf("no tracer provided, tracing will be disabled")
+ } else {
+ log.Printf("Tracing enabled")
+ opentracing.SetGlobalTracer(tracer)
+ }
+
+ if closer == nil {
+ return &nopCloser{}
+ }
+ return closer
+}
diff --git a/vendor/gitlab.com/gitlab-org/labkit/tracing/initialization_options.go b/vendor/gitlab.com/gitlab-org/labkit/tracing/initialization_options.go
new file mode 100644
index 000000000..206e815aa
--- /dev/null
+++ b/vendor/gitlab.com/gitlab-org/labkit/tracing/initialization_options.go
@@ -0,0 +1,43 @@
+package tracing
+
+import (
+ "os"
+ "path"
+)
+
+// The configuration for InjectCorrelationID
+type initializationConfig struct {
+ serviceName string
+ connectionString string
+}
+
+// InitializationOption will configure a correlation handler
+type InitializationOption func(*initializationConfig)
+
+func applyInitializationOptions(opts []InitializationOption) initializationConfig {
+ config := initializationConfig{
+ serviceName: path.Base(os.Args[0]),
+ connectionString: os.Getenv("GITLAB_TRACING"),
+ }
+ for _, v := range opts {
+ v(&config)
+ }
+
+ return config
+}
+
+// WithServiceName allows the service name to be configured for the tracer
+// this will appear in traces.
+func WithServiceName(serviceName string) InitializationOption {
+ return func(config *initializationConfig) {
+ config.serviceName = serviceName
+ }
+}
+
+// WithConnectionString allows the opentracing connection string to be overridden. By default
+// this will be retrieved from the GITLAB_TRACING environment variable.
+func WithConnectionString(connectionString string) InitializationOption {
+ return func(config *initializationConfig) {
+ config.connectionString = connectionString
+ }
+}
diff --git a/vendor/gitlab.com/gitlab-org/labkit/tracing/outbound_http.go b/vendor/gitlab.com/gitlab-org/labkit/tracing/outbound_http.go
new file mode 100644
index 000000000..74935e6e3
--- /dev/null
+++ b/vendor/gitlab.com/gitlab-org/labkit/tracing/outbound_http.go
@@ -0,0 +1,143 @@
+package tracing
+
+import (
+ "crypto/tls"
+ "log"
+ "net/http"
+ "net/http/httptrace"
+
+ opentracing "github.com/opentracing/opentracing-go"
+ "github.com/opentracing/opentracing-go/ext"
+ otlog "github.com/opentracing/opentracing-go/log"
+)
+
+type tracingRoundTripper struct {
+ delegate http.RoundTripper
+ config roundTripperConfig
+}
+
+func (c tracingRoundTripper) RoundTrip(req *http.Request) (res *http.Response, e error) {
+ tracer := opentracing.GlobalTracer()
+ if tracer == nil {
+ return c.delegate.RoundTrip(req)
+ }
+
+ ctx := req.Context()
+
+ var parentCtx opentracing.SpanContext
+ parentSpan := opentracing.SpanFromContext(ctx)
+ if parentSpan != nil {
+ parentCtx = parentSpan.Context()
+ }
+
+ // start a new Span to wrap HTTP request
+ span := opentracing.StartSpan(
+ c.config.getOperationName(req),
+ opentracing.ChildOf(parentCtx),
+ )
+ defer span.Finish()
+
+ ctx = opentracing.ContextWithSpan(ctx, span)
+
+ // attach ClientTrace to the Context, and Context to request
+ trace := newClientTrace(span)
+ ctx = httptrace.WithClientTrace(ctx, trace)
+ req = req.WithContext(ctx)
+
+ ext.SpanKindRPCClient.Set(span)
+ ext.HTTPUrl.Set(span, req.URL.String())
+ ext.HTTPMethod.Set(span, req.Method)
+
+ carrier := opentracing.HTTPHeadersCarrier(req.Header)
+ err := span.Tracer().Inject(span.Context(), opentracing.HTTPHeaders, carrier)
+
+ if err != nil {
+ log.Printf("tracing span injection failed: %v", err)
+ }
+
+ response, err := c.delegate.RoundTrip(req)
+
+ if err != nil {
+ span.LogFields(
+ otlog.String("event", "roundtrip error"),
+ otlog.Object("error", err),
+ )
+ } else {
+ span.LogFields(
+ otlog.String("event", "roundtrip complete"),
+ otlog.Int("status", response.StatusCode),
+ )
+ }
+
+ return response, err
+}
+
+func newClientTrace(span opentracing.Span) *httptrace.ClientTrace {
+ trace := &clientTrace{span: span}
+ return &httptrace.ClientTrace{
+ GotFirstResponseByte: trace.gotFirstResponseByte,
+ ConnectStart: trace.connectStart,
+ ConnectDone: trace.connectDone,
+ TLSHandshakeStart: trace.tlsHandshakeStart,
+ TLSHandshakeDone: trace.tlsHandshakeDone,
+ WroteHeaders: trace.wroteHeaders,
+ WroteRequest: trace.wroteRequest,
+ }
+}
+
+// clientTrace holds a reference to the Span and
+// provides methods used as ClientTrace callbacks
+type clientTrace struct {
+ span opentracing.Span
+}
+
+func (h *clientTrace) gotFirstResponseByte() {
+ h.span.LogFields(otlog.String("event", "got first response byte"))
+}
+
+func (h *clientTrace) connectStart(network, addr string) {
+ h.span.LogFields(
+ otlog.String("event", "connect started"),
+ otlog.String("network", network),
+ otlog.String("addr", addr),
+ )
+}
+
+func (h *clientTrace) connectDone(network, addr string, err error) {
+ h.span.LogFields(
+ otlog.String("event", "connect done"),
+ otlog.String("network", network),
+ otlog.String("addr", addr),
+ otlog.Object("error", err),
+ )
+}
+
+func (h *clientTrace) tlsHandshakeStart() {
+ h.span.LogFields(otlog.String("event", "tls handshake started"))
+}
+
+func (h *clientTrace) tlsHandshakeDone(state tls.ConnectionState, err error) {
+ h.span.LogFields(
+ otlog.String("event", "tls handshake done"),
+ otlog.Object("error", err),
+ )
+}
+
+func (h *clientTrace) wroteHeaders() {
+ h.span.LogFields(otlog.String("event", "headers written"))
+}
+
+func (h *clientTrace) wroteRequest(info httptrace.WroteRequestInfo) {
+ h.span.LogFields(
+ otlog.String("event", "request written"),
+ otlog.Object("error", info.Err),
+ )
+}
+
+// NewRoundTripper acts as a "client-middleware" for outbound http requests
+// adding instrumentation to the outbound request and then delegating to the underlying
+// transport
+func NewRoundTripper(delegate http.RoundTripper, opts ...RoundTripperOption) http.RoundTripper {
+ config := applyRoundTripperOptions(opts)
+ return &tracingRoundTripper{delegate: delegate, config: config}
+}
diff --git a/vendor/gitlab.com/gitlab-org/labkit/tracing/outbound_http_options.go b/vendor/gitlab.com/gitlab-org/labkit/tracing/outbound_http_options.go
new file mode 100644
index 000000000..2777b1d33
--- /dev/null
+++ b/vendor/gitlab.com/gitlab-org/labkit/tracing/outbound_http_options.go
@@ -0,0 +1,28 @@
+package tracing
+
+import (
+ "fmt"
+ "net/http"
+)
+
+// The configuration for InjectCorrelationID
+type roundTripperConfig struct {
+ getOperationName OperationNamer
+}
+
+// RoundTripperOption will configure a correlation handler
+type RoundTripperOption func(*roundTripperConfig)
+
+func applyRoundTripperOptions(opts []RoundTripperOption) roundTripperConfig {
+ config := roundTripperConfig{
+ getOperationName: func(req *http.Request) string {
+ // By default use `GET https://localhost` for operation names
+ return fmt.Sprintf("%s %s://%s", req.Method, req.URL.Scheme, req.URL.Host)
+ },
+ }
+ for _, v := range opts {
+ v(&config)
+ }
+
+ return config
+}
diff --git a/vendor/google.golang.org/genproto/googleapis/api/annotations/annotations.pb.go b/vendor/google.golang.org/genproto/googleapis/api/annotations/annotations.pb.go
new file mode 100644
index 000000000..9521b50e9
--- /dev/null
+++ b/vendor/google.golang.org/genproto/googleapis/api/annotations/annotations.pb.go
@@ -0,0 +1,54 @@
+// Code generated by protoc-gen-go. DO NOT EDIT.
+// source: google/api/annotations.proto
+
+package annotations // import "google.golang.org/genproto/googleapis/api/annotations"
+
+import proto "github.com/golang/protobuf/proto"
+import fmt "fmt"
+import math "math"
+import descriptor "github.com/golang/protobuf/protoc-gen-go/descriptor"
+
+// Reference imports to suppress errors if they are not otherwise used.
+var _ = proto.Marshal
+var _ = fmt.Errorf
+var _ = math.Inf
+
+// This is a compile-time assertion to ensure that this generated file
+// is compatible with the proto package it is being compiled against.
+// A compilation error at this line likely means your copy of the
+// proto package needs to be updated.
+const _ = proto.ProtoPackageIsVersion2 // please upgrade the proto package
+
+var E_Http = &proto.ExtensionDesc{
+ ExtendedType: (*descriptor.MethodOptions)(nil),
+ ExtensionType: (*HttpRule)(nil),
+ Field: 72295728,
+ Name: "google.api.http",
+ Tag: "bytes,72295728,opt,name=http",
+ Filename: "google/api/annotations.proto",
+}
+
+func init() {
+ proto.RegisterExtension(E_Http)
+}
+
+func init() {
+ proto.RegisterFile("google/api/annotations.proto", fileDescriptor_annotations_55609bb51d80951d)
+}
+
+var fileDescriptor_annotations_55609bb51d80951d = []byte{
+ // 208 bytes of a gzipped FileDescriptorProto
+ 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xe2, 0x92, 0x49, 0xcf, 0xcf, 0x4f,
+ 0xcf, 0x49, 0xd5, 0x4f, 0x2c, 0xc8, 0xd4, 0x4f, 0xcc, 0xcb, 0xcb, 0x2f, 0x49, 0x2c, 0xc9, 0xcc,
+ 0xcf, 0x2b, 0xd6, 0x2b, 0x28, 0xca, 0x2f, 0xc9, 0x17, 0xe2, 0x82, 0xc8, 0xea, 0x25, 0x16, 0x64,
+ 0x4a, 0x89, 0x22, 0xa9, 0xcc, 0x28, 0x29, 0x29, 0x80, 0x28, 0x91, 0x52, 0x80, 0x0a, 0x83, 0x79,
+ 0x49, 0xa5, 0x69, 0xfa, 0x29, 0xa9, 0xc5, 0xc9, 0x45, 0x99, 0x05, 0x25, 0xf9, 0x45, 0x10, 0x15,
+ 0x56, 0xde, 0x5c, 0x2c, 0x20, 0xf5, 0x42, 0x72, 0x7a, 0x50, 0xd3, 0x60, 0x4a, 0xf5, 0x7c, 0x53,
+ 0x4b, 0x32, 0xf2, 0x53, 0xfc, 0x0b, 0xc0, 0x56, 0x4a, 0x6c, 0x38, 0xb5, 0x47, 0x49, 0x81, 0x51,
+ 0x83, 0xdb, 0x48, 0x44, 0x0f, 0x61, 0xad, 0x9e, 0x47, 0x49, 0x49, 0x41, 0x50, 0x69, 0x4e, 0x6a,
+ 0x10, 0xd8, 0x10, 0xa7, 0x3c, 0x2e, 0xbe, 0xe4, 0xfc, 0x5c, 0x24, 0x05, 0x4e, 0x02, 0x8e, 0x08,
+ 0x67, 0x07, 0x80, 0x4c, 0x0e, 0x60, 0x8c, 0x72, 0x84, 0xca, 0xa7, 0xe7, 0xe7, 0x24, 0xe6, 0xa5,
+ 0xeb, 0xe5, 0x17, 0xa5, 0xeb, 0xa7, 0xa7, 0xe6, 0x81, 0xed, 0xd5, 0x87, 0x48, 0x25, 0x16, 0x64,
+ 0x16, 0xa3, 0x7b, 0xda, 0x1a, 0x89, 0xbd, 0x88, 0x89, 0xc5, 0xdd, 0x31, 0xc0, 0x33, 0x89, 0x0d,
+ 0xac, 0xc9, 0x18, 0x10, 0x00, 0x00, 0xff, 0xff, 0xe3, 0x29, 0x19, 0x62, 0x28, 0x01, 0x00, 0x00,
+}
diff --git a/vendor/google.golang.org/genproto/googleapis/api/annotations/http.pb.go b/vendor/google.golang.org/genproto/googleapis/api/annotations/http.pb.go
new file mode 100644
index 000000000..1a8a27b65
--- /dev/null
+++ b/vendor/google.golang.org/genproto/googleapis/api/annotations/http.pb.go
@@ -0,0 +1,688 @@
+// Code generated by protoc-gen-go. DO NOT EDIT.
+// source: google/api/http.proto
+
+package annotations // import "google.golang.org/genproto/googleapis/api/annotations"
+
+import proto "github.com/golang/protobuf/proto"
+import fmt "fmt"
+import math "math"
+
+// Reference imports to suppress errors if they are not otherwise used.
+var _ = proto.Marshal
+var _ = fmt.Errorf
+var _ = math.Inf
+
+// This is a compile-time assertion to ensure that this generated file
+// is compatible with the proto package it is being compiled against.
+// A compilation error at this line likely means your copy of the
+// proto package needs to be updated.
+const _ = proto.ProtoPackageIsVersion2 // please upgrade the proto package
+
+// Defines the HTTP configuration for an API service. It contains a list of
+// [HttpRule][google.api.HttpRule], each specifying the mapping of an RPC method
+// to one or more HTTP REST API methods.
+type Http struct {
+ // A list of HTTP configuration rules that apply to individual API methods.
+ //
+ // **NOTE:** All service configuration rules follow "last one wins" order.
+ Rules []*HttpRule `protobuf:"bytes,1,rep,name=rules,proto3" json:"rules,omitempty"`
+ // When set to true, URL path parmeters will be fully URI-decoded except in
+ // cases of single segment matches in reserved expansion, where "%2F" will be
+ // left encoded.
+ //
+ // The default behavior is to not decode RFC 6570 reserved characters in multi
+ // segment matches.
+ FullyDecodeReservedExpansion bool `protobuf:"varint,2,opt,name=fully_decode_reserved_expansion,json=fullyDecodeReservedExpansion,proto3" json:"fully_decode_reserved_expansion,omitempty"`
+ XXX_NoUnkeyedLiteral struct{} `json:"-"`
+ XXX_unrecognized []byte `json:"-"`
+ XXX_sizecache int32 `json:"-"`
+}
+
+func (m *Http) Reset() { *m = Http{} }
+func (m *Http) String() string { return proto.CompactTextString(m) }
+func (*Http) ProtoMessage() {}
+func (*Http) Descriptor() ([]byte, []int) {
+ return fileDescriptor_http_e457621dddd7365b, []int{0}
+}
+func (m *Http) XXX_Unmarshal(b []byte) error {
+ return xxx_messageInfo_Http.Unmarshal(m, b)
+}
+func (m *Http) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) {
+ return xxx_messageInfo_Http.Marshal(b, m, deterministic)
+}
+func (dst *Http) XXX_Merge(src proto.Message) {
+ xxx_messageInfo_Http.Merge(dst, src)
+}
+func (m *Http) XXX_Size() int {
+ return xxx_messageInfo_Http.Size(m)
+}
+func (m *Http) XXX_DiscardUnknown() {
+ xxx_messageInfo_Http.DiscardUnknown(m)
+}
+
+var xxx_messageInfo_Http proto.InternalMessageInfo
+
+func (m *Http) GetRules() []*HttpRule {
+ if m != nil {
+ return m.Rules
+ }
+ return nil
+}
+
+func (m *Http) GetFullyDecodeReservedExpansion() bool {
+ if m != nil {
+ return m.FullyDecodeReservedExpansion
+ }
+ return false
+}
+
+// `HttpRule` defines the mapping of an RPC method to one or more HTTP
+// REST API methods. The mapping specifies how different portions of the RPC
+// request message are mapped to URL path, URL query parameters, and
+// HTTP request body. The mapping is typically specified as an
+// `google.api.http` annotation on the RPC method,
+// see "google/api/annotations.proto" for details.
+//
+// The mapping consists of a field specifying the path template and
+// method kind. The path template can refer to fields in the request
+// message, as in the example below which describes a REST GET
+// operation on a resource collection of messages:
+//
+//
+// service Messaging {
+// rpc GetMessage(GetMessageRequest) returns (Message) {
+// option (google.api.http).get = "/v1/messages/{message_id}/{sub.subfield}";
+// }
+// }
+// message GetMessageRequest {
+// message SubMessage {
+// string subfield = 1;
+// }
+// string message_id = 1; // mapped to the URL
+// SubMessage sub = 2; // `sub.subfield` is url-mapped
+// }
+// message Message {
+// string text = 1; // content of the resource
+// }
+//
+// The same http annotation can alternatively be expressed inside the
+// `GRPC API Configuration` YAML file.
+//
+// http:
+// rules:
+// - selector: <proto_package_name>.Messaging.GetMessage
+// get: /v1/messages/{message_id}/{sub.subfield}
+//
+// This definition enables an automatic, bidrectional mapping of HTTP
+// JSON to RPC. Example:
+//
+// HTTP | RPC
+// -----|-----
+// `GET /v1/messages/123456/foo` | `GetMessage(message_id: "123456" sub: SubMessage(subfield: "foo"))`
+//
+// In general, not only fields but also field paths can be referenced
+// from a path pattern. Fields mapped to the path pattern cannot be
+// repeated and must have a primitive (non-message) type.
+//
+// Any fields in the request message which are not bound by the path
+// pattern automatically become (optional) HTTP query
+// parameters. Assume the following definition of the request message:
+//
+//
+// service Messaging {
+// rpc GetMessage(GetMessageRequest) returns (Message) {
+// option (google.api.http).get = "/v1/messages/{message_id}";
+// }
+// }
+// message GetMessageRequest {
+// message SubMessage {
+// string subfield = 1;
+// }
+// string message_id = 1; // mapped to the URL
+// int64 revision = 2; // becomes a parameter
+// SubMessage sub = 3; // `sub.subfield` becomes a parameter
+// }
+//
+//
+// This enables a HTTP JSON to RPC mapping as below:
+//
+// HTTP | RPC
+// -----|-----
+// `GET /v1/messages/123456?revision=2&sub.subfield=foo` | `GetMessage(message_id: "123456" revision: 2 sub: SubMessage(subfield: "foo"))`
+//
+// Note that fields which are mapped to HTTP parameters must have a
+// primitive type or a repeated primitive type. Message types are not
+// allowed. In the case of a repeated type, the parameter can be
+// repeated in the URL, as in `...?param=A&param=B`.
+//
+// For HTTP method kinds which allow a request body, the `body` field
+// specifies the mapping. Consider a REST update method on the
+// message resource collection:
+//
+//
+// service Messaging {
+// rpc UpdateMessage(UpdateMessageRequest) returns (Message) {
+// option (google.api.http) = {
+// put: "/v1/messages/{message_id}"
+// body: "message"
+// };
+// }
+// }
+// message UpdateMessageRequest {
+// string message_id = 1; // mapped to the URL
+// Message message = 2; // mapped to the body
+// }
+//
+//
+// The following HTTP JSON to RPC mapping is enabled, where the
+// representation of the JSON in the request body is determined by
+// protos JSON encoding:
+//
+// HTTP | RPC
+// -----|-----
+// `PUT /v1/messages/123456 { "text": "Hi!" }` | `UpdateMessage(message_id: "123456" message { text: "Hi!" })`
+//
+// The special name `*` can be used in the body mapping to define that
+// every field not bound by the path template should be mapped to the
+// request body. This enables the following alternative definition of
+// the update method:
+//
+// service Messaging {
+// rpc UpdateMessage(Message) returns (Message) {
+// option (google.api.http) = {
+// put: "/v1/messages/{message_id}"
+// body: "*"
+// };
+// }
+// }
+// message Message {
+// string message_id = 1;
+// string text = 2;
+// }
+//
+//
+// The following HTTP JSON to RPC mapping is enabled:
+//
+// HTTP | RPC
+// -----|-----
+// `PUT /v1/messages/123456 { "text": "Hi!" }` | `UpdateMessage(message_id: "123456" text: "Hi!")`
+//
+// Note that when using `*` in the body mapping, it is not possible to
+// have HTTP parameters, as all fields not bound by the path end in
+// the body. This makes this option more rarely used in practice of
+// defining REST APIs. The common usage of `*` is in custom methods
+// which don't use the URL at all for transferring data.
+//
+// It is possible to define multiple HTTP methods for one RPC by using
+// the `additional_bindings` option. Example:
+//
+// service Messaging {
+// rpc GetMessage(GetMessageRequest) returns (Message) {
+// option (google.api.http) = {
+// get: "/v1/messages/{message_id}"
+// additional_bindings {
+// get: "/v1/users/{user_id}/messages/{message_id}"
+// }
+// };
+// }
+// }
+// message GetMessageRequest {
+// string message_id = 1;
+// string user_id = 2;
+// }
+//
+//
+// This enables the following two alternative HTTP JSON to RPC
+// mappings:
+//
+// HTTP | RPC
+// -----|-----
+// `GET /v1/messages/123456` | `GetMessage(message_id: "123456")`
+// `GET /v1/users/me/messages/123456` | `GetMessage(user_id: "me" message_id: "123456")`
+//
+// # Rules for HTTP mapping
+//
+// The rules for mapping HTTP path, query parameters, and body fields
+// to the request message are as follows:
+//
+// 1. The `body` field specifies either `*` or a field path, or is
+// omitted. If omitted, it indicates there is no HTTP request body.
+// 2. Leaf fields (recursive expansion of nested messages in the
+// request) can be classified into three types:
+// (a) Matched in the URL template.
+// (b) Covered by body (if body is `*`, everything except (a) fields;
+// else everything under the body field)
+// (c) All other fields.
+// 3. URL query parameters found in the HTTP request are mapped to (c) fields.
+// 4. Any body sent with an HTTP request can contain only (b) fields.
+//
+// The syntax of the path template is as follows:
+//
+// Template = "/" Segments [ Verb ] ;
+// Segments = Segment { "/" Segment } ;
+// Segment = "*" | "**" | LITERAL | Variable ;
+// Variable = "{" FieldPath [ "=" Segments ] "}" ;
+// FieldPath = IDENT { "." IDENT } ;
+// Verb = ":" LITERAL ;
+//
+// The syntax `*` matches a single path segment. The syntax `**` matches zero
+// or more path segments, which must be the last part of the path except the
+// `Verb`. The syntax `LITERAL` matches literal text in the path.
+//
+// The syntax `Variable` matches part of the URL path as specified by its
+// template. A variable template must not contain other variables. If a variable
+// matches a single path segment, its template may be omitted, e.g. `{var}`
+// is equivalent to `{var=*}`.
+//
+// If a variable contains exactly one path segment, such as `"{var}"` or
+// `"{var=*}"`, when such a variable is expanded into a URL path, all characters
+// except `[-_.~0-9a-zA-Z]` are percent-encoded. Such variables show up in the
+// Discovery Document as `{var}`.
+//
+// If a variable contains one or more path segments, such as `"{var=foo/*}"`
+// or `"{var=**}"`, when such a variable is expanded into a URL path, all
+// characters except `[-_.~/0-9a-zA-Z]` are percent-encoded. Such variables
+// show up in the Discovery Document as `{+var}`.
+//
+// NOTE: While the single segment variable matches the semantics of
+// [RFC 6570](https://tools.ietf.org/html/rfc6570) Section 3.2.2
+// Simple String Expansion, the multi segment variable **does not** match
+// RFC 6570 Reserved Expansion. The reason is that the Reserved Expansion
+// does not expand special characters like `?` and `#`, which would lead
+// to invalid URLs.
+//
+// NOTE: the field paths in variables and in the `body` must not refer to
+// repeated fields or map fields.
+type HttpRule struct {
+ // Selects methods to which this rule applies.
+ //
+ // Refer to [selector][google.api.DocumentationRule.selector] for syntax details.
+ Selector string `protobuf:"bytes,1,opt,name=selector,proto3" json:"selector,omitempty"`
+ // Determines the URL pattern is matched by this rules. This pattern can be
+ // used with any of the {get|put|post|delete|patch} methods. A custom method
+ // can be defined using the 'custom' field.
+ //
+ // Types that are valid to be assigned to Pattern:
+ // *HttpRule_Get
+ // *HttpRule_Put
+ // *HttpRule_Post
+ // *HttpRule_Delete
+ // *HttpRule_Patch
+ // *HttpRule_Custom
+ Pattern isHttpRule_Pattern `protobuf_oneof:"pattern"`
+ // The name of the request field whose value is mapped to the HTTP body, or
+ // `*` for mapping all fields not captured by the path pattern to the HTTP
+ // body. NOTE: the referred field must not be a repeated field and must be
+ // present at the top-level of request message type.
+ Body string `protobuf:"bytes,7,opt,name=body,proto3" json:"body,omitempty"`
+ // Optional. The name of the response field whose value is mapped to the HTTP
+ // body of response. Other response fields are ignored. When
+ // not set, the response message will be used as HTTP body of response.
+ ResponseBody string `protobuf:"bytes,12,opt,name=response_body,json=responseBody,proto3" json:"response_body,omitempty"`
+ // Additional HTTP bindings for the selector. Nested bindings must
+ // not contain an `additional_bindings` field themselves (that is,
+ // the nesting may only be one level deep).
+ AdditionalBindings []*HttpRule `protobuf:"bytes,11,rep,name=additional_bindings,json=additionalBindings,proto3" json:"additional_bindings,omitempty"`
+ XXX_NoUnkeyedLiteral struct{} `json:"-"`
+ XXX_unrecognized []byte `json:"-"`
+ XXX_sizecache int32 `json:"-"`
+}
+
+func (m *HttpRule) Reset() { *m = HttpRule{} }
+func (m *HttpRule) String() string { return proto.CompactTextString(m) }
+func (*HttpRule) ProtoMessage() {}
+func (*HttpRule) Descriptor() ([]byte, []int) {
+ return fileDescriptor_http_e457621dddd7365b, []int{1}
+}
+func (m *HttpRule) XXX_Unmarshal(b []byte) error {
+ return xxx_messageInfo_HttpRule.Unmarshal(m, b)
+}
+func (m *HttpRule) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) {
+ return xxx_messageInfo_HttpRule.Marshal(b, m, deterministic)
+}
+func (dst *HttpRule) XXX_Merge(src proto.Message) {
+ xxx_messageInfo_HttpRule.Merge(dst, src)
+}
+func (m *HttpRule) XXX_Size() int {
+ return xxx_messageInfo_HttpRule.Size(m)
+}
+func (m *HttpRule) XXX_DiscardUnknown() {
+ xxx_messageInfo_HttpRule.DiscardUnknown(m)
+}
+
+var xxx_messageInfo_HttpRule proto.InternalMessageInfo
+
+func (m *HttpRule) GetSelector() string {
+ if m != nil {
+ return m.Selector
+ }
+ return ""
+}
+
+type isHttpRule_Pattern interface {
+ isHttpRule_Pattern()
+}
+
+type HttpRule_Get struct {
+ Get string `protobuf:"bytes,2,opt,name=get,proto3,oneof"`
+}
+
+type HttpRule_Put struct {
+ Put string `protobuf:"bytes,3,opt,name=put,proto3,oneof"`
+}
+
+type HttpRule_Post struct {
+ Post string `protobuf:"bytes,4,opt,name=post,proto3,oneof"`
+}
+
+type HttpRule_Delete struct {
+ Delete string `protobuf:"bytes,5,opt,name=delete,proto3,oneof"`
+}
+
+type HttpRule_Patch struct {
+ Patch string `protobuf:"bytes,6,opt,name=patch,proto3,oneof"`
+}
+
+type HttpRule_Custom struct {
+ Custom *CustomHttpPattern `protobuf:"bytes,8,opt,name=custom,proto3,oneof"`
+}
+
+func (*HttpRule_Get) isHttpRule_Pattern() {}
+
+func (*HttpRule_Put) isHttpRule_Pattern() {}
+
+func (*HttpRule_Post) isHttpRule_Pattern() {}
+
+func (*HttpRule_Delete) isHttpRule_Pattern() {}
+
+func (*HttpRule_Patch) isHttpRule_Pattern() {}
+
+func (*HttpRule_Custom) isHttpRule_Pattern() {}
+
+func (m *HttpRule) GetPattern() isHttpRule_Pattern {
+ if m != nil {
+ return m.Pattern
+ }
+ return nil
+}
+
+func (m *HttpRule) GetGet() string {
+ if x, ok := m.GetPattern().(*HttpRule_Get); ok {
+ return x.Get
+ }
+ return ""
+}
+
+func (m *HttpRule) GetPut() string {
+ if x, ok := m.GetPattern().(*HttpRule_Put); ok {
+ return x.Put
+ }
+ return ""
+}
+
+func (m *HttpRule) GetPost() string {
+ if x, ok := m.GetPattern().(*HttpRule_Post); ok {
+ return x.Post
+ }
+ return ""
+}
+
+func (m *HttpRule) GetDelete() string {
+ if x, ok := m.GetPattern().(*HttpRule_Delete); ok {
+ return x.Delete
+ }
+ return ""
+}
+
+func (m *HttpRule) GetPatch() string {
+ if x, ok := m.GetPattern().(*HttpRule_Patch); ok {
+ return x.Patch
+ }
+ return ""
+}
+
+func (m *HttpRule) GetCustom() *CustomHttpPattern {
+ if x, ok := m.GetPattern().(*HttpRule_Custom); ok {
+ return x.Custom
+ }
+ return nil
+}
+
+func (m *HttpRule) GetBody() string {
+ if m != nil {
+ return m.Body
+ }
+ return ""
+}
+
+func (m *HttpRule) GetResponseBody() string {
+ if m != nil {
+ return m.ResponseBody
+ }
+ return ""
+}
+
+func (m *HttpRule) GetAdditionalBindings() []*HttpRule {
+ if m != nil {
+ return m.AdditionalBindings
+ }
+ return nil
+}
+
+// XXX_OneofFuncs is for the internal use of the proto package.
+func (*HttpRule) XXX_OneofFuncs() (func(msg proto.Message, b *proto.Buffer) error, func(msg proto.Message, tag, wire int, b *proto.Buffer) (bool, error), func(msg proto.Message) (n int), []interface{}) {
+ return _HttpRule_OneofMarshaler, _HttpRule_OneofUnmarshaler, _HttpRule_OneofSizer, []interface{}{
+ (*HttpRule_Get)(nil),
+ (*HttpRule_Put)(nil),
+ (*HttpRule_Post)(nil),
+ (*HttpRule_Delete)(nil),
+ (*HttpRule_Patch)(nil),
+ (*HttpRule_Custom)(nil),
+ }
+}
+
+func _HttpRule_OneofMarshaler(msg proto.Message, b *proto.Buffer) error {
+ m := msg.(*HttpRule)
+ // pattern
+ switch x := m.Pattern.(type) {
+ case *HttpRule_Get:
+ b.EncodeVarint(2<<3 | proto.WireBytes)
+ b.EncodeStringBytes(x.Get)
+ case *HttpRule_Put:
+ b.EncodeVarint(3<<3 | proto.WireBytes)
+ b.EncodeStringBytes(x.Put)
+ case *HttpRule_Post:
+ b.EncodeVarint(4<<3 | proto.WireBytes)
+ b.EncodeStringBytes(x.Post)
+ case *HttpRule_Delete:
+ b.EncodeVarint(5<<3 | proto.WireBytes)
+ b.EncodeStringBytes(x.Delete)
+ case *HttpRule_Patch:
+ b.EncodeVarint(6<<3 | proto.WireBytes)
+ b.EncodeStringBytes(x.Patch)
+ case *HttpRule_Custom:
+ b.EncodeVarint(8<<3 | proto.WireBytes)
+ if err := b.EncodeMessage(x.Custom); err != nil {
+ return err
+ }
+ case nil:
+ default:
+ return fmt.Errorf("HttpRule.Pattern has unexpected type %T", x)
+ }
+ return nil
+}
+
+func _HttpRule_OneofUnmarshaler(msg proto.Message, tag, wire int, b *proto.Buffer) (bool, error) {
+ m := msg.(*HttpRule)
+ switch tag {
+ case 2: // pattern.get
+ if wire != proto.WireBytes {
+ return true, proto.ErrInternalBadWireType
+ }
+ x, err := b.DecodeStringBytes()
+ m.Pattern = &HttpRule_Get{x}
+ return true, err
+ case 3: // pattern.put
+ if wire != proto.WireBytes {
+ return true, proto.ErrInternalBadWireType
+ }
+ x, err := b.DecodeStringBytes()
+ m.Pattern = &HttpRule_Put{x}
+ return true, err
+ case 4: // pattern.post
+ if wire != proto.WireBytes {
+ return true, proto.ErrInternalBadWireType
+ }
+ x, err := b.DecodeStringBytes()
+ m.Pattern = &HttpRule_Post{x}
+ return true, err
+ case 5: // pattern.delete
+ if wire != proto.WireBytes {
+ return true, proto.ErrInternalBadWireType
+ }
+ x, err := b.DecodeStringBytes()
+ m.Pattern = &HttpRule_Delete{x}
+ return true, err
+ case 6: // pattern.patch
+ if wire != proto.WireBytes {
+ return true, proto.ErrInternalBadWireType
+ }
+ x, err := b.DecodeStringBytes()
+ m.Pattern = &HttpRule_Patch{x}
+ return true, err
+ case 8: // pattern.custom
+ if wire != proto.WireBytes {
+ return true, proto.ErrInternalBadWireType
+ }
+ msg := new(CustomHttpPattern)
+ err := b.DecodeMessage(msg)
+ m.Pattern = &HttpRule_Custom{msg}
+ return true, err
+ default:
+ return false, nil
+ }
+}
+
+func _HttpRule_OneofSizer(msg proto.Message) (n int) {
+ m := msg.(*HttpRule)
+ // pattern
+ switch x := m.Pattern.(type) {
+ case *HttpRule_Get:
+ n += 1 // tag and wire
+ n += proto.SizeVarint(uint64(len(x.Get)))
+ n += len(x.Get)
+ case *HttpRule_Put:
+ n += 1 // tag and wire
+ n += proto.SizeVarint(uint64(len(x.Put)))
+ n += len(x.Put)
+ case *HttpRule_Post:
+ n += 1 // tag and wire
+ n += proto.SizeVarint(uint64(len(x.Post)))
+ n += len(x.Post)
+ case *HttpRule_Delete:
+ n += 1 // tag and wire
+ n += proto.SizeVarint(uint64(len(x.Delete)))
+ n += len(x.Delete)
+ case *HttpRule_Patch:
+ n += 1 // tag and wire
+ n += proto.SizeVarint(uint64(len(x.Patch)))
+ n += len(x.Patch)
+ case *HttpRule_Custom:
+ s := proto.Size(x.Custom)
+ n += 1 // tag and wire
+ n += proto.SizeVarint(uint64(s))
+ n += s
+ case nil:
+ default:
+ panic(fmt.Sprintf("proto: unexpected type %T in oneof", x))
+ }
+ return n
+}
+
+// A custom pattern is used for defining custom HTTP verb.
+type CustomHttpPattern struct {
+ // The name of this custom HTTP verb.
+ Kind string `protobuf:"bytes,1,opt,name=kind,proto3" json:"kind,omitempty"`
+ // The path matched by this custom verb.
+ Path string `protobuf:"bytes,2,opt,name=path,proto3" json:"path,omitempty"`
+ XXX_NoUnkeyedLiteral struct{} `json:"-"`
+ XXX_unrecognized []byte `json:"-"`
+ XXX_sizecache int32 `json:"-"`
+}
+
+func (m *CustomHttpPattern) Reset() { *m = CustomHttpPattern{} }
+func (m *CustomHttpPattern) String() string { return proto.CompactTextString(m) }
+func (*CustomHttpPattern) ProtoMessage() {}
+func (*CustomHttpPattern) Descriptor() ([]byte, []int) {
+ return fileDescriptor_http_e457621dddd7365b, []int{2}
+}
+func (m *CustomHttpPattern) XXX_Unmarshal(b []byte) error {
+ return xxx_messageInfo_CustomHttpPattern.Unmarshal(m, b)
+}
+func (m *CustomHttpPattern) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) {
+ return xxx_messageInfo_CustomHttpPattern.Marshal(b, m, deterministic)
+}
+func (dst *CustomHttpPattern) XXX_Merge(src proto.Message) {
+ xxx_messageInfo_CustomHttpPattern.Merge(dst, src)
+}
+func (m *CustomHttpPattern) XXX_Size() int {
+ return xxx_messageInfo_CustomHttpPattern.Size(m)
+}
+func (m *CustomHttpPattern) XXX_DiscardUnknown() {
+ xxx_messageInfo_CustomHttpPattern.DiscardUnknown(m)
+}
+
+var xxx_messageInfo_CustomHttpPattern proto.InternalMessageInfo
+
+func (m *CustomHttpPattern) GetKind() string {
+ if m != nil {
+ return m.Kind
+ }
+ return ""
+}
+
+func (m *CustomHttpPattern) GetPath() string {
+ if m != nil {
+ return m.Path
+ }
+ return ""
+}
+
+func init() {
+ proto.RegisterType((*Http)(nil), "google.api.Http")
+ proto.RegisterType((*HttpRule)(nil), "google.api.HttpRule")
+ proto.RegisterType((*CustomHttpPattern)(nil), "google.api.CustomHttpPattern")
+}
+
+func init() { proto.RegisterFile("google/api/http.proto", fileDescriptor_http_e457621dddd7365b) }
+
+var fileDescriptor_http_e457621dddd7365b = []byte{
+ // 419 bytes of a gzipped FileDescriptorProto
+ 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0x7c, 0x92, 0xc1, 0x8e, 0xd3, 0x30,
+ 0x10, 0x86, 0x49, 0x9b, 0x76, 0xdb, 0xe9, 0x82, 0x84, 0x59, 0x90, 0x85, 0x40, 0x54, 0xe5, 0x52,
+ 0x71, 0x48, 0xa5, 0xe5, 0xc0, 0x61, 0x4f, 0x1b, 0xa8, 0x58, 0x6e, 0x55, 0x8e, 0x5c, 0x22, 0x37,
+ 0x1e, 0x52, 0x83, 0xd7, 0xb6, 0xe2, 0x09, 0xa2, 0xaf, 0xc3, 0x63, 0xf1, 0x24, 0x1c, 0x91, 0x9d,
+ 0x84, 0x56, 0x42, 0xe2, 0x36, 0xf3, 0xff, 0x9f, 0xa7, 0x7f, 0x27, 0x03, 0x4f, 0x6b, 0x6b, 0x6b,
+ 0x8d, 0x1b, 0xe1, 0xd4, 0xe6, 0x40, 0xe4, 0x32, 0xd7, 0x58, 0xb2, 0x0c, 0x3a, 0x39, 0x13, 0x4e,
+ 0xad, 0x8e, 0x90, 0xde, 0x11, 0x39, 0xf6, 0x06, 0x26, 0x4d, 0xab, 0xd1, 0xf3, 0x64, 0x39, 0x5e,
+ 0x2f, 0xae, 0xaf, 0xb2, 0x13, 0x93, 0x05, 0xa0, 0x68, 0x35, 0x16, 0x1d, 0xc2, 0xb6, 0xf0, 0xea,
+ 0x4b, 0xab, 0xf5, 0xb1, 0x94, 0x58, 0x59, 0x89, 0x65, 0x83, 0x1e, 0x9b, 0xef, 0x28, 0x4b, 0xfc,
+ 0xe1, 0x84, 0xf1, 0xca, 0x1a, 0x3e, 0x5a, 0x26, 0xeb, 0x59, 0xf1, 0x22, 0x62, 0x1f, 0x22, 0x55,
+ 0xf4, 0xd0, 0x76, 0x60, 0x56, 0xbf, 0x46, 0x30, 0x1b, 0x46, 0xb3, 0xe7, 0x30, 0xf3, 0xa8, 0xb1,
+ 0x22, 0xdb, 0xf0, 0x64, 0x99, 0xac, 0xe7, 0xc5, 0xdf, 0x9e, 0x31, 0x18, 0xd7, 0x48, 0x71, 0xe6,
+ 0xfc, 0xee, 0x41, 0x11, 0x9a, 0xa0, 0xb9, 0x96, 0xf8, 0x78, 0xd0, 0x5c, 0x4b, 0xec, 0x0a, 0x52,
+ 0x67, 0x3d, 0xf1, 0xb4, 0x17, 0x63, 0xc7, 0x38, 0x4c, 0x25, 0x6a, 0x24, 0xe4, 0x93, 0x5e, 0xef,
+ 0x7b, 0xf6, 0x0c, 0x26, 0x4e, 0x50, 0x75, 0xe0, 0xd3, 0xde, 0xe8, 0x5a, 0xf6, 0x0e, 0xa6, 0x55,
+ 0xeb, 0xc9, 0xde, 0xf3, 0xd9, 0x32, 0x59, 0x2f, 0xae, 0x5f, 0x9e, 0x2f, 0xe3, 0x7d, 0x74, 0x42,
+ 0xee, 0x9d, 0x20, 0xc2, 0xc6, 0x84, 0x81, 0x1d, 0xce, 0x18, 0xa4, 0x7b, 0x2b, 0x8f, 0xfc, 0x22,
+ 0xfe, 0x81, 0x58, 0xb3, 0xd7, 0xf0, 0xb0, 0x41, 0xef, 0xac, 0xf1, 0x58, 0x46, 0xf3, 0x32, 0x9a,
+ 0x97, 0x83, 0x98, 0x07, 0x68, 0x0b, 0x4f, 0x84, 0x94, 0x8a, 0x94, 0x35, 0x42, 0x97, 0x7b, 0x65,
+ 0xa4, 0x32, 0xb5, 0xe7, 0x8b, 0xff, 0x7c, 0x0b, 0x76, 0x7a, 0x90, 0xf7, 0x7c, 0x3e, 0x87, 0x0b,
+ 0xd7, 0x85, 0x5a, 0xdd, 0xc0, 0xe3, 0x7f, 0x92, 0x86, 0x7c, 0xdf, 0x94, 0x91, 0xfd, 0x82, 0x63,
+ 0x1d, 0x34, 0x27, 0xe8, 0xd0, 0x6d, 0xb7, 0x88, 0x75, 0xfe, 0x15, 0x1e, 0x55, 0xf6, 0xfe, 0xec,
+ 0x67, 0xf3, 0x79, 0x1c, 0x13, 0xae, 0x67, 0x97, 0x7c, 0xbe, 0xed, 0x8d, 0xda, 0x6a, 0x61, 0xea,
+ 0xcc, 0x36, 0xf5, 0xa6, 0x46, 0x13, 0x6f, 0x6b, 0xd3, 0x59, 0xc2, 0x29, 0x1f, 0xaf, 0x4e, 0x18,
+ 0x63, 0x49, 0x84, 0x98, 0xfe, 0xe6, 0xac, 0xfe, 0x9d, 0x24, 0x3f, 0x47, 0xe9, 0xc7, 0xdb, 0xdd,
+ 0xa7, 0xfd, 0x34, 0xbe, 0x7b, 0xfb, 0x27, 0x00, 0x00, 0xff, 0xff, 0xae, 0xde, 0xa1, 0xd0, 0xac,
+ 0x02, 0x00, 0x00,
+}
diff --git a/vendor/gopkg.in/DataDog/dd-trace-go.v1/LICENSE b/vendor/gopkg.in/DataDog/dd-trace-go.v1/LICENSE
new file mode 100644
index 000000000..23351821f
--- /dev/null
+++ b/vendor/gopkg.in/DataDog/dd-trace-go.v1/LICENSE
@@ -0,0 +1,24 @@
+Copyright (c) 2016, Datadog <info@datadoghq.com>
+All rights reserved.
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions are met:
+ * Redistributions of source code must retain the above copyright
+ notice, this list of conditions and the following disclaimer.
+ * Redistributions in binary form must reproduce the above copyright
+ notice, this list of conditions and the following disclaimer in the
+ documentation and/or other materials provided with the distribution.
+ * Neither the name of Datadog nor the
+ names of its contributors may be used to endorse or promote products
+ derived from this software without specific prior written permission.
+
+THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
+ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+DISCLAIMED. IN NO EVENT SHALL <COPYRIGHT HOLDER> BE LIABLE FOR ANY
+DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
diff --git a/vendor/gopkg.in/DataDog/dd-trace-go.v1/LICENSE-3rdparty.csv b/vendor/gopkg.in/DataDog/dd-trace-go.v1/LICENSE-3rdparty.csv
new file mode 100644
index 000000000..582ea7910
--- /dev/null
+++ b/vendor/gopkg.in/DataDog/dd-trace-go.v1/LICENSE-3rdparty.csv
@@ -0,0 +1,2 @@
+Component,Origin,License,Copyright
+import,io.opentracing,Apache-2.0,Copyright 2016-2017 The OpenTracing Authors \ No newline at end of file
diff --git a/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/Gopkg.toml b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/Gopkg.toml
new file mode 100644
index 000000000..1fb732af8
--- /dev/null
+++ b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/Gopkg.toml
@@ -0,0 +1,9 @@
+ignored = [
+ # From these libraries we should always ensure compatibility with the latest:
+ "github.com/opentracing/*",
+ "golang.org/x/*",
+]
+
+[[constraint]]
+ name = "github.com/tinylib/msgp"
+ revision = "3b5c87ab5fb00c660bf85b888445d9a01db64db4" # Feb 15, 2018
diff --git a/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/ddtrace.go b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/ddtrace.go
new file mode 100644
index 000000000..bfd40561e
--- /dev/null
+++ b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/ddtrace.go
@@ -0,0 +1,111 @@
+// Package ddtrace contains the interfaces that specify the implementations of Datadog's
+// tracing library, as well as a set of sub-packages containing various implementations:
+// our native implementation ("tracer"), a wrapper that can be used with Opentracing
+// ("opentracer") and a mock tracer to be used for testing ("mocktracer"). Additionally,
+// package "ext" provides a set of tag names and values specific to Datadog's APM product.
+//
+// To get started, visit the documentation for any of the packages you'd like to begin
+// with by accessing the subdirectories of this package: https://godoc.org/gopkg.in/DataDog/dd-trace-go.v1/ddtrace#pkg-subdirectories.
+package ddtrace // import "gopkg.in/DataDog/dd-trace-go.v1/ddtrace"
+
+import "time"
+
+// Tracer specifies an implementation of the Datadog tracer which allows starting
+// and propagating spans. The official implementation if exposed as functions
+// within the "tracer" package.
+type Tracer interface {
+ // StartSpan starts a span with the given operation name and options.
+ StartSpan(operationName string, opts ...StartSpanOption) Span
+
+ // Extract extracts a span context from a given carrier. Note that baggage item
+ // keys will always be lower-cased to maintain consistency. It is impossible to
+ // maintain the original casing due to MIME header canonicalization standards.
+ Extract(carrier interface{}) (SpanContext, error)
+
+ // Inject injects a span context into the given carrier.
+ Inject(context SpanContext, carrier interface{}) error
+
+ // Stop stops the active tracer and sets the global tracer to a no-op. Calls to
+ // Stop should be idempotent.
+ Stop()
+}
+
+// Span represents a chunk of computation time. Spans have names, durations,
+// timestamps and other metadata. A Tracer is used to create hierarchies of
+// spans in a request, buffer and submit them to the server.
+type Span interface {
+ // SetTag sets a key/value pair as metadata on the span.
+ SetTag(key string, value interface{})
+
+ // SetOperationName sets the operation name for this span. An operation name should be
+ // a representative name for a group of spans (e.g. "grpc.server" or "http.request").
+ SetOperationName(operationName string)
+
+ // BaggageItem returns the baggage item held by the given key.
+ BaggageItem(key string) string
+
+ // SetBaggageItem sets a new baggage item at the given key. The baggage
+ // item should propagate to all descendant spans, both in- and cross-process.
+ SetBaggageItem(key, val string)
+
+ // Finish finishes the current span with the given options. Finish calls should be idempotent.
+ Finish(opts ...FinishOption)
+
+ // Context returns the SpanContext of this Span.
+ Context() SpanContext
+}
+
+// SpanContext represents a span state that can propagate to descendant spans
+// and across process boundaries. It contains all the information needed to
+// spawn a direct descendant of the span that it belongs to. It can be used
+// to create distributed tracing by propagating it using the provided interfaces.
+type SpanContext interface {
+ // SpanID returns the span ID that this context is carrying.
+ SpanID() uint64
+
+ // TraceID returns the trace ID that this context is carrying.
+ TraceID() uint64
+
+ // ForeachBaggageItem provides an iterator over the key/value pairs set as
+ // baggage within this context. Iteration stops when the handler returns
+ // false.
+ ForeachBaggageItem(handler func(k, v string) bool)
+}
+
+// StartSpanOption is a configuration option that can be used with a Tracer's StartSpan method.
+type StartSpanOption func(cfg *StartSpanConfig)
+
+// FinishOption is a configuration option that can be used with a Span's Finish method.
+type FinishOption func(cfg *FinishConfig)
+
+// FinishConfig holds the configuration for finishing a span. It is usually passed around by
+// reference to one or more FinishOption functions which shape it into its final form.
+type FinishConfig struct {
+ // FinishTime represents the time that should be set as finishing time for the
+ // span. Implementations should use the current time when FinishTime.IsZero().
+ FinishTime time.Time
+
+ // Error holds an optional error that should be set on the span before
+ // finishing.
+ Error error
+
+ // NoDebugStack will prevent any set errors from generating an attached stack trace tag.
+ NoDebugStack bool
+}
+
+// StartSpanConfig holds the configuration for starting a new span. It is usually passed
+// around by reference to one or more StartSpanOption functions which shape it into its
+// final form.
+type StartSpanConfig struct {
+ // Parent holds the SpanContext that should be used as a parent for the
+ // new span. If nil, implementations should return a root span.
+ Parent SpanContext
+
+ // StartTime holds the time that should be used as the start time of the span.
+ // Implementations should use the current time when StartTime.IsZero().
+ StartTime time.Time
+
+ // Tags holds a set of key/value pairs that should be set as metadata on the
+ // new span.
+ Tags map[string]interface{}
+}
diff --git a/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/ext/app_types.go b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/ext/app_types.go
new file mode 100644
index 000000000..77a26fbfc
--- /dev/null
+++ b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/ext/app_types.go
@@ -0,0 +1,70 @@
+package ext // import "gopkg.in/DataDog/dd-trace-go.v1/ddtrace/ext"
+
+// App types determine how to categorize a trace in the Datadog application.
+// For more fine-grained behaviour, use the SpanType* constants.
+const (
+ // DEPRECATED: Use SpanTypeWeb
+ // AppTypeWeb specifies the Web span type and can be used as a tag value
+ // for a span's SpanType tag.
+ AppTypeWeb = "web"
+
+ // AppTypeDB specifies the DB span type and can be used as a tag value
+ // for a span's SpanType tag. If possible, use one of the SpanType*
+ // constants for a more accurate indication.
+ AppTypeDB = "db"
+
+ // AppTypeCache specifies the Cache span type and can be used as a tag value
+ // for a span's SpanType tag. If possible, consider using SpanTypeRedis or
+ // SpanTypeMemcached.
+ AppTypeCache = "cache"
+
+ // AppTypeRPC specifies the RPC span type and can be used as a tag value
+ // for a span's SpanType tag.
+ AppTypeRPC = "rpc"
+)
+
+// Span types have similar behaviour to "app types" and help categorize
+// traces in the Datadog application. They can also help fine grain agent
+// level bahviours such as obfuscation and quantization, when these are
+// enabled in the agent's configuration.
+const (
+ // SpanTypeWeb marks a span as an HTTP server request.
+ SpanTypeWeb = "web"
+
+ // SpanTypeHTTP marks a span as an HTTP client request.
+ SpanTypeHTTP = "http"
+
+ // SpanTypeSQL marks a span as an SQL operation. These spans may
+ // have an "sql.command" tag.
+ SpanTypeSQL = "sql"
+
+ // SpanTypeCassandra marks a span as a Cassandra operation. These
+ // spans may have an "sql.command" tag.
+ SpanTypeCassandra = "cassandra"
+
+ // SpanTypeRedis marks a span as a Redis operation. These spans may
+ // also have a "redis.raw_command" tag.
+ SpanTypeRedis = "redis"
+
+ // SpanTypeMemcached marks a span as a memcached operation.
+ SpanTypeMemcached = "memcached"
+
+ // SpanTypeMongoDB marks a span as a MongoDB operation.
+ SpanTypeMongoDB = "mongodb"
+
+ // SpanTypeElasticSearch marks a span as an ElasticSearch operation.
+ // These spans may also have an "elasticsearch.body" tag.
+ SpanTypeElasticSearch = "elasticsearch"
+
+ // SpanTypeLevelDB marks a span as a leveldb operation
+ SpanTypeLevelDB = "leveldb"
+
+ // SpanTypeDNS marks a span as a DNS operation.
+ SpanTypeDNS = "dns"
+
+ // SpanTypeMessageConsumer marks a span as a queue operation
+ SpanTypeMessageConsumer = "queue"
+
+ // SpanTypeMessageProducer marks a span as a queue operation.
+ SpanTypeMessageProducer = "queue"
+)
diff --git a/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/ext/cassandra.go b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/ext/cassandra.go
new file mode 100644
index 000000000..c3569cda3
--- /dev/null
+++ b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/ext/cassandra.go
@@ -0,0 +1,21 @@
+package ext
+
+const (
+ // CassandraQuery is the tag name used for cassandra queries.
+ CassandraQuery = "cassandra.query"
+
+ // CassandraConsistencyLevel is the tag name to set for consitency level.
+ CassandraConsistencyLevel = "cassandra.consistency_level"
+
+ // CassandraCluster specifies the tag name that is used to set the cluster.
+ CassandraCluster = "cassandra.cluster"
+
+ // CassandraRowCount specifies the tag name to use when settings the row count.
+ CassandraRowCount = "cassandra.row_count"
+
+ // CassandraKeyspace is used as tag name for setting the key space.
+ CassandraKeyspace = "cassandra.keyspace"
+
+ // CassandraPaginated specifies the tag name for paginated queries.
+ CassandraPaginated = "cassandra.paginated"
+)
diff --git a/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/ext/db.go b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/ext/db.go
new file mode 100644
index 000000000..d30741216
--- /dev/null
+++ b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/ext/db.go
@@ -0,0 +1,16 @@
+package ext
+
+const (
+ // DBApplication indicates the application using the database.
+ DBApplication = "db.application"
+ // DBName indicates the database name.
+ DBName = "db.name"
+ // DBType indicates the type of Database.
+ DBType = "db.type"
+ // DBInstance indicates the instance name of Database.
+ DBInstance = "db.instance"
+ // DBUser indicates the user name of Database, e.g. "readonly_user" or "reporting_user".
+ DBUser = "db.user"
+ // DBStatement records a database statement for the given database type.
+ DBStatement = "db.statement"
+)
diff --git a/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/ext/peer.go b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/ext/peer.go
new file mode 100644
index 000000000..3b32cef46
--- /dev/null
+++ b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/ext/peer.go
@@ -0,0 +1,14 @@
+package ext
+
+const (
+ // PeerHostIPV4 records IPv4 host address of the peer.
+ PeerHostIPV4 = "peer.ipv4"
+ // PeerHostIPV6 records the IPv6 host address of the peer.
+ PeerHostIPV6 = "peer.ipv6"
+ // PeerService records the service name of the peer service.
+ PeerService = "peer.service"
+ // PeerHostname records the host name of the peer.
+ PeerHostname = "peer.hostname"
+ // PeerPort records the port number of the peer.
+ PeerPort = "peer.port"
+)
diff --git a/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/ext/priority.go b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/ext/priority.go
new file mode 100644
index 000000000..cbda42042
--- /dev/null
+++ b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/ext/priority.go
@@ -0,0 +1,22 @@
+package ext
+
+// Priority is a hint given to the backend so that it knows which traces to reject or kept.
+// In a distributed context, it should be set before any context propagation (fork, RPC calls) to be effective.
+
+const (
+ // PriorityUserReject informs the backend that a trace should be rejected and not stored.
+ // This should be used by user code overriding default priority.
+ PriorityUserReject = -1
+
+ // PriorityAutoReject informs the backend that a trace should be rejected and not stored.
+ // This is used by the builtin sampler.
+ PriorityAutoReject = 0
+
+ // PriorityAutoKeep informs the backend that a trace should be kept and not stored.
+ // This is used by the builtin sampler.
+ PriorityAutoKeep = 1
+
+ // PriorityUserKeep informs the backend that a trace should be kept and not stored.
+ // This should be used by user code overriding default priority.
+ PriorityUserKeep = 2
+)
diff --git a/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/ext/system.go b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/ext/system.go
new file mode 100644
index 000000000..9256aa5b2
--- /dev/null
+++ b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/ext/system.go
@@ -0,0 +1,7 @@
+package ext
+
+// Standard system metadata names
+const (
+ // The pid of the traced process
+ Pid = "system.pid"
+)
diff --git a/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/ext/tags.go b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/ext/tags.go
new file mode 100644
index 000000000..6775e2aac
--- /dev/null
+++ b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/ext/tags.go
@@ -0,0 +1,57 @@
+// Package ext contains a set of Datadog-specific constants. Most of them are used
+// for setting span metadata.
+package ext
+
+const (
+ // TargetHost sets the target host address.
+ TargetHost = "out.host"
+
+ // TargetPort sets the target host port.
+ TargetPort = "out.port"
+
+ // SamplingPriority is the tag that marks the sampling priority of a span.
+ SamplingPriority = "sampling.priority"
+
+ // SQLType sets the sql type tag.
+ SQLType = "sql"
+
+ // SQLQuery sets the sql query tag on a span.
+ SQLQuery = "sql.query"
+
+ // HTTPMethod specifies the HTTP method used in a span.
+ HTTPMethod = "http.method"
+
+ // HTTPCode sets the HTTP status code as a tag.
+ HTTPCode = "http.status_code"
+
+ // HTTPURL sets the HTTP URL for a span.
+ HTTPURL = "http.url"
+
+ // TODO: In the next major version, suffix these constants (SpanType, etc)
+ // with "*Key" (SpanTypeKey, etc) to more easily differentiate between
+ // constants representing tag values and constants representing keys.
+
+ // SpanType defines the Span type (web, db, cache).
+ SpanType = "span.type"
+
+ // ServiceName defines the Service name for this Span.
+ ServiceName = "service.name"
+
+ // ResourceName defines the Resource name for the Span.
+ ResourceName = "resource.name"
+
+ // Error specifies the error tag. It's value is usually of type "error".
+ Error = "error"
+
+ // ErrorMsg specifies the error message.
+ ErrorMsg = "error.msg"
+
+ // ErrorType specifies the error type.
+ ErrorType = "error.type"
+
+ // ErrorStack specifies the stack dump.
+ ErrorStack = "error.stack"
+
+ // Environment specifies the environment to use with a trace.
+ Environment = "env"
+)
diff --git a/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/internal/globaltracer.go b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/internal/globaltracer.go
new file mode 100644
index 000000000..008f5f033
--- /dev/null
+++ b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/internal/globaltracer.go
@@ -0,0 +1,98 @@
+package internal // import "gopkg.in/DataDog/dd-trace-go.v1/ddtrace/internal"
+
+import (
+ "sync"
+
+ "gopkg.in/DataDog/dd-trace-go.v1/ddtrace"
+)
+
+var (
+ mu sync.RWMutex // guards globalTracer
+ globalTracer ddtrace.Tracer = &NoopTracer{}
+)
+
+// SetGlobalTracer sets the global tracer to t.
+func SetGlobalTracer(t ddtrace.Tracer) {
+ mu.Lock()
+ defer mu.Unlock()
+ if !Testing {
+ // avoid infinite loop when calling (*mocktracer.Tracer).Stop
+ globalTracer.Stop()
+ }
+ globalTracer = t
+}
+
+// GetGlobalTracer returns the currently active tracer.
+func GetGlobalTracer() ddtrace.Tracer {
+ mu.RLock()
+ defer mu.RUnlock()
+ return globalTracer
+}
+
+// Testing is set to true when the mock tracer is active. It usually signifies that we are in a test
+// environment. This value is used by tracer.Start to prevent overriding the GlobalTracer in tests.
+var Testing = false
+
+var _ ddtrace.Tracer = (*NoopTracer)(nil)
+
+// NoopTracer is an implementation of ddtrace.Tracer that is a no-op.
+type NoopTracer struct{}
+
+// StartSpan implements ddtrace.Tracer.
+func (NoopTracer) StartSpan(operationName string, opts ...ddtrace.StartSpanOption) ddtrace.Span {
+ return NoopSpan{}
+}
+
+// SetServiceInfo implements ddtrace.Tracer.
+func (NoopTracer) SetServiceInfo(name, app, appType string) {}
+
+// Extract implements ddtrace.Tracer.
+func (NoopTracer) Extract(carrier interface{}) (ddtrace.SpanContext, error) {
+ return NoopSpanContext{}, nil
+}
+
+// Inject implements ddtrace.Tracer.
+func (NoopTracer) Inject(context ddtrace.SpanContext, carrier interface{}) error { return nil }
+
+// Stop implements ddtrace.Tracer.
+func (NoopTracer) Stop() {}
+
+var _ ddtrace.Span = (*NoopSpan)(nil)
+
+// NoopSpan is an implementation of ddtrace.Span that is a no-op.
+type NoopSpan struct{}
+
+// SetTag implements ddtrace.Span.
+func (NoopSpan) SetTag(key string, value interface{}) {}
+
+// SetOperationName implements ddtrace.Span.
+func (NoopSpan) SetOperationName(operationName string) {}
+
+// BaggageItem implements ddtrace.Span.
+func (NoopSpan) BaggageItem(key string) string { return "" }
+
+// SetBaggageItem implements ddtrace.Span.
+func (NoopSpan) SetBaggageItem(key, val string) {}
+
+// Finish implements ddtrace.Span.
+func (NoopSpan) Finish(opts ...ddtrace.FinishOption) {}
+
+// Tracer implements ddtrace.Span.
+func (NoopSpan) Tracer() ddtrace.Tracer { return NoopTracer{} }
+
+// Context implements ddtrace.Span.
+func (NoopSpan) Context() ddtrace.SpanContext { return NoopSpanContext{} }
+
+var _ ddtrace.SpanContext = (*NoopSpanContext)(nil)
+
+// NoopSpanContext is an implementation of ddtrace.SpanContext that is a no-op.
+type NoopSpanContext struct{}
+
+// SpanID implements ddtrace.SpanContext.
+func (NoopSpanContext) SpanID() uint64 { return 0 }
+
+// TraceID implements ddtrace.SpanContext.
+func (NoopSpanContext) TraceID() uint64 { return 0 }
+
+// ForeachBaggageItem implements ddtrace.SpanContext.
+func (NoopSpanContext) ForeachBaggageItem(handler func(k, v string) bool) {}
diff --git a/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/opentracer/option.go b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/opentracer/option.go
new file mode 100644
index 000000000..cbae45184
--- /dev/null
+++ b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/opentracer/option.go
@@ -0,0 +1,24 @@
+package opentracer // import "gopkg.in/DataDog/dd-trace-go.v1/ddtrace/opentracer"
+
+import (
+ "gopkg.in/DataDog/dd-trace-go.v1/ddtrace/ext"
+
+ opentracing "github.com/opentracing/opentracing-go"
+)
+
+// ServiceName can be used with opentracing.StartSpan to set the
+// service name of a span.
+func ServiceName(name string) opentracing.StartSpanOption {
+ return opentracing.Tag{Key: ext.ServiceName, Value: name}
+}
+
+// ResourceName can be used with opentracing.StartSpan to set the
+// resource name of a span.
+func ResourceName(name string) opentracing.StartSpanOption {
+ return opentracing.Tag{Key: ext.ResourceName, Value: name}
+}
+
+// SpanType can be used with opentracing.StartSpan to set the type of a span.
+func SpanType(name string) opentracing.StartSpanOption {
+ return opentracing.Tag{Key: ext.SpanType, Value: name}
+}
diff --git a/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/opentracer/span.go b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/opentracer/span.go
new file mode 100644
index 000000000..1e02764e4
--- /dev/null
+++ b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/opentracer/span.go
@@ -0,0 +1,83 @@
+package opentracer
+
+import (
+ "fmt"
+
+ "gopkg.in/DataDog/dd-trace-go.v1/ddtrace"
+ "gopkg.in/DataDog/dd-trace-go.v1/ddtrace/ext"
+ "gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer"
+
+ opentracing "github.com/opentracing/opentracing-go"
+ "github.com/opentracing/opentracing-go/log"
+)
+
+var _ opentracing.Span = (*span)(nil)
+
+// span implements opentracing.Span on top of ddtrace.Span.
+type span struct {
+ ddtrace.Span
+ *opentracer
+}
+
+func (s *span) Context() opentracing.SpanContext { return s.Span.Context() }
+func (s *span) Finish() { s.Span.Finish() }
+func (s *span) Tracer() opentracing.Tracer { return s.opentracer }
+func (s *span) LogEvent(event string) { /* deprecated */ }
+func (s *span) LogEventWithPayload(event string, payload interface{}) { /* deprecated */ }
+func (s *span) Log(data opentracing.LogData) { /* deprecated */ }
+
+func (s *span) FinishWithOptions(opts opentracing.FinishOptions) {
+ for _, lr := range opts.LogRecords {
+ if len(lr.Fields) > 0 {
+ s.LogFields(lr.Fields...)
+ }
+ }
+ s.Span.Finish(tracer.FinishTime(opts.FinishTime))
+}
+
+func (s *span) LogFields(fields ...log.Field) {
+ // catch standard opentracing keys and adjust to internal ones as per spec:
+ // https://github.com/opentracing/specification/blob/master/semantic_conventions.md#log-fields-table
+ for _, f := range fields {
+ switch f.Key() {
+ case "event":
+ if v, ok := f.Value().(string); ok && v == "error" {
+ s.SetTag("error", true)
+ }
+ case "error", "error.object":
+ if err, ok := f.Value().(error); ok {
+ s.SetTag("error", err)
+ }
+ case "message":
+ s.SetTag(ext.ErrorMsg, fmt.Sprint(f.Value()))
+ case "stack":
+ s.SetTag(ext.ErrorStack, fmt.Sprint(f.Value()))
+ default:
+ // not implemented
+ }
+ }
+}
+
+func (s *span) LogKV(keyVals ...interface{}) {
+ fields, err := log.InterleavedKVToFields(keyVals...)
+ if err != nil {
+ // TODO(gbbr): create a log package
+ return
+ }
+ s.LogFields(fields...)
+}
+
+func (s *span) SetBaggageItem(key, val string) opentracing.Span {
+ s.Span.SetBaggageItem(key, val)
+ return s
+}
+
+func (s *span) SetOperationName(operationName string) opentracing.Span {
+ s.Span.SetOperationName(operationName)
+ return s
+}
+
+func (s *span) SetTag(key string, value interface{}) opentracing.Span {
+ s.Span.SetTag(key, value)
+ return s
+}
diff --git a/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/opentracer/tracer.go b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/opentracer/tracer.go
new file mode 100644
index 000000000..df7302803
--- /dev/null
+++ b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/opentracer/tracer.go
@@ -0,0 +1,81 @@
+// Package opentracer provides a wrapper on top of the Datadog tracer that can be used with Opentracing.
+// It also provides a set of opentracing.StartSpanOption that are specific to Datadog's APM product.
+// To use it, simply call "New".
+//
+// Note that there are currently some small incompatibilities between the Opentracing spec and the Datadog
+// APM product, which we are in the process of addressing on the long term. When using Datadog, the
+// Opentracing operation name is what is called resource in Datadog's terms and the Opentracing "component"
+// tag is Datadog's operation name. Meaning that in order to define (in Opentracing terms) a span that
+// has the operation name "/user/profile" and the component "http.request", one would do:
+// opentracing.StartSpan("http.request", opentracer.ResourceName("/user/profile"))
+//
+// Some libraries and frameworks are supported out-of-the-box by using our integrations. You can see a list
+// of supported integrations here: https://godoc.org/gopkg.in/DataDog/dd-trace-go.v1/contrib. They are fully
+// compatible with the Opentracing implementation.
+package opentracer
+
+import (
+ "gopkg.in/DataDog/dd-trace-go.v1/ddtrace"
+ "gopkg.in/DataDog/dd-trace-go.v1/ddtrace/internal"
+ "gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer"
+
+ opentracing "github.com/opentracing/opentracing-go"
+)
+
+// New creates, instantiates and returns an Opentracing compatible version of the
+// Datadog tracer using the provided set of options.
+func New(opts ...tracer.StartOption) opentracing.Tracer {
+ tracer.Start(opts...)
+ return &opentracer{internal.GetGlobalTracer()}
+}
+
+var _ opentracing.Tracer = (*opentracer)(nil)
+
+// opentracer implements opentracing.Tracer on top of ddtrace.Tracer.
+type opentracer struct{ ddtrace.Tracer }
+
+// StartSpan implements opentracing.Tracer.
+func (t *opentracer) StartSpan(operationName string, options ...opentracing.StartSpanOption) opentracing.Span {
+ var sso opentracing.StartSpanOptions
+ for _, o := range options {
+ o.Apply(&sso)
+ }
+ opts := []ddtrace.StartSpanOption{tracer.StartTime(sso.StartTime)}
+ for _, ref := range sso.References {
+ if v, ok := ref.ReferencedContext.(ddtrace.SpanContext); ok && ref.Type == opentracing.ChildOfRef {
+ opts = append(opts, tracer.ChildOf(v))
+ break // can only have one parent
+ }
+ }
+ for k, v := range sso.Tags {
+ opts = append(opts, tracer.Tag(k, v))
+ }
+ return &span{
+ Span: t.Tracer.StartSpan(operationName, opts...),
+ opentracer: t,
+ }
+}
+
+// Inject implements opentracing.Tracer.
+func (t *opentracer) Inject(ctx opentracing.SpanContext, format interface{}, carrier interface{}) error {
+ sctx, ok := ctx.(ddtrace.SpanContext)
+ if !ok {
+ return opentracing.ErrUnsupportedFormat
+ }
+ switch format {
+ case opentracing.TextMap, opentracing.HTTPHeaders:
+ return t.Tracer.Inject(sctx, carrier)
+ default:
+ return opentracing.ErrUnsupportedFormat
+ }
+}
+
+// Extract implements opentracing.Tracer.
+func (t *opentracer) Extract(format interface{}, carrier interface{}) (opentracing.SpanContext, error) {
+ switch format {
+ case opentracing.TextMap, opentracing.HTTPHeaders:
+ return t.Tracer.Extract(carrier)
+ default:
+ return nil, opentracing.ErrUnsupportedFormat
+ }
+}
diff --git a/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/context.go b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/context.go
new file mode 100644
index 000000000..b95b14831
--- /dev/null
+++ b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/context.go
@@ -0,0 +1,42 @@
+package tracer
+
+import (
+ "context"
+
+ "gopkg.in/DataDog/dd-trace-go.v1/ddtrace"
+ "gopkg.in/DataDog/dd-trace-go.v1/ddtrace/internal"
+)
+
+type contextKey struct{}
+
+var activeSpanKey = contextKey{}
+
+// ContextWithSpan returns a copy of the given context which includes the span s.
+func ContextWithSpan(ctx context.Context, s Span) context.Context {
+ return context.WithValue(ctx, activeSpanKey, s)
+}
+
+// SpanFromContext returns the span contained in the given context. A second return
+// value indicates if a span was found in the context. If no span is found, a no-op
+// span is returned.
+func SpanFromContext(ctx context.Context) (Span, bool) {
+ if ctx == nil {
+ return &internal.NoopSpan{}, false
+ }
+ v := ctx.Value(activeSpanKey)
+ if s, ok := v.(ddtrace.Span); ok {
+ return s, true
+ }
+ return &internal.NoopSpan{}, false
+}
+
+// StartSpanFromContext returns a new span with the given operation name and options. If a span
+// is found in the context, it will be used as the parent of the resulting span. If the ChildOf
+// option is passed, the span from context will take precedence over it as the parent span.
+func StartSpanFromContext(ctx context.Context, operationName string, opts ...StartSpanOption) (Span, context.Context) {
+ if s, ok := SpanFromContext(ctx); ok {
+ opts = append(opts, ChildOf(s.Context()))
+ }
+ s := StartSpan(operationName, opts...)
+ return s, ContextWithSpan(ctx, s)
+}
diff --git a/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/doc.go b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/doc.go
new file mode 100644
index 000000000..2abd319a6
--- /dev/null
+++ b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/doc.go
@@ -0,0 +1,50 @@
+// Package tracer contains Datadog's core tracing client. It is used to trace
+// requests as they flow across web servers, databases and microservices, giving
+// developers visibility into bottlenecks and troublesome requests. To start the
+// tracer, simply call the start method along with an optional set of options.
+// By default, the trace agent is considered to be found at "localhost:8126". In a
+// setup where this would be different (let's say 127.0.0.1:1234), we could do:
+// tracer.Start(tracer.WithAgentAddr("127.0.0.1:1234"))
+// defer tracer.Stop()
+//
+// The tracing client can perform trace sampling. While the trace agent
+// already samples traces to reduce bandwidth usage, client sampling reduces
+// performance overhead. To make use of it, the package comes with a ready-to-use
+// rate sampler that can be passed to the tracer. To use it and keep only 30% of the
+// requests, one would do:
+// s := tracer.NewRateSampler(0.3)
+// tracer.Start(tracer.WithSampler(s))
+//
+// All spans created by the tracer contain a context hereby referred to as the span
+// context. Note that this is different from Go's context. The span context is used
+// to package essential information from a span, which is needed when creating child
+// spans that inherit from it. Thus, a child span is created from a span's span context.
+// The span context can originate from within the same process, but also a
+// different process or even a different machine in the case of distributed tracing.
+//
+// To make use of distributed tracing, a span's context may be injected via a carrier
+// into a transport (HTTP, RPC, etc.) to be extracted on the other end and used to
+// create spans that are direct descendants of it. A couple of carrier interfaces
+// which should cover most of the use-case scenarios are readily provided, such as
+// HTTPCarrier and TextMapCarrier. Users are free to create their own, which will work
+// with our propagation algorithm as long as they implement the TextMapReader and TextMapWriter
+// interfaces. An example alternate implementation is the MDCarrier in our gRPC integration.
+//
+// As an example, injecting a span's context into an HTTP request would look like this:
+// req, err := http.NewRequest("GET", "http://example.com", nil)
+// // ...
+// err := tracer.Inject(span.Context(), tracer.HTTPHeadersCarrier(req.Header))
+// // ...
+// http.DefaultClient.Do(req)
+// Then, on the server side, to continue the trace one would do:
+// sctx, err := tracer.Extract(tracer.HTTPHeadersCarrier(req.Header))
+// // ...
+// span := tracer.StartSpan("child.span", tracer.ChildOf(sctx))
+// In the same manner, any means can be used as a carrier to inject a context into a transport. Go's
+// context can also be used as a means to transport spans within the same process. The methods
+// StartSpanFromContext, ContextWithSpan and SpanFromContext exist for this reason.
+//
+// Some libraries and frameworks are supported out-of-the-box by using one
+// of our integrations. You can see a list of supported integrations here:
+// https://godoc.org/gopkg.in/DataDog/dd-trace-go.v1/contrib
+package tracer // import "gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer"
diff --git a/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/errors.go b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/errors.go
new file mode 100644
index 000000000..35c14c60a
--- /dev/null
+++ b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/errors.go
@@ -0,0 +1,69 @@
+package tracer
+
+import (
+ "fmt"
+ "log"
+ "strconv"
+)
+
+var errorPrefix = fmt.Sprintf("Datadog Tracer Error (%s): ", tracerVersion)
+
+type traceEncodingError struct{ context error }
+
+func (e *traceEncodingError) Error() string {
+ return fmt.Sprintf("error encoding trace: %s", e.context)
+}
+
+type spanBufferFullError struct{}
+
+func (e *spanBufferFullError) Error() string {
+ return fmt.Sprintf("trace span cap (%d) reached, dropping trace", traceMaxSize)
+}
+
+type dataLossError struct {
+ count int // number of items lost
+ context error // any context error, if available
+}
+
+func (e *dataLossError) Error() string {
+ return fmt.Sprintf("lost traces (count: %d), error: %v", e.count, e.context)
+}
+
+type errorSummary struct {
+ Count int
+ Example string
+}
+
+func aggregateErrors(errChan <-chan error) map[string]errorSummary {
+ errs := make(map[string]errorSummary, len(errChan))
+ for {
+ select {
+ case err := <-errChan:
+ if err == nil {
+ break
+ }
+ key := fmt.Sprintf("%T", err)
+ summary := errs[key]
+ summary.Count++
+ summary.Example = err.Error()
+ errs[key] = summary
+ default: // stop when there's no more data
+ return errs
+ }
+ }
+}
+
+// logErrors logs the errors, preventing log file flooding, when there
+// are many messages, it caps them and shows a quick summary.
+// As of today it only logs using standard golang log package, but
+// later we could send those stats to agent // TODO(ufoot).
+func logErrors(errChan <-chan error) {
+ errs := aggregateErrors(errChan)
+ for _, v := range errs {
+ var repeat string
+ if v.Count > 1 {
+ repeat = " (repeated " + strconv.Itoa(v.Count) + " times)"
+ }
+ log.Println(errorPrefix + v.Example + repeat)
+ }
+}
diff --git a/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/option.go b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/option.go
new file mode 100644
index 000000000..9fa82c78f
--- /dev/null
+++ b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/option.go
@@ -0,0 +1,198 @@
+package tracer
+
+import (
+ "net/http"
+ "os"
+ "path/filepath"
+ "time"
+
+ "gopkg.in/DataDog/dd-trace-go.v1/ddtrace"
+ "gopkg.in/DataDog/dd-trace-go.v1/ddtrace/ext"
+)
+
+// config holds the tracer configuration.
+type config struct {
+ // debug, when true, writes details to logs.
+ debug bool
+
+ // serviceName specifies the name of this application.
+ serviceName string
+
+ // sampler specifies the sampler that will be used for sampling traces.
+ sampler Sampler
+
+ // prioritySampling will be non-nil when priority sampling is enabled.
+ prioritySampling *prioritySampler
+
+ // agentAddr specifies the hostname and of the agent where the traces
+ // are sent to.
+ agentAddr string
+
+ // globalTags holds a set of tags that will be automatically applied to
+ // all spans.
+ globalTags map[string]interface{}
+
+ // transport specifies the Transport interface which will be used to send data to the agent.
+ transport transport
+
+ // propagator propagates span context cross-process
+ propagator Propagator
+
+ // httpRoundTripper defines the http.RoundTripper used by the agent transport.
+ httpRoundTripper http.RoundTripper
+}
+
+// StartOption represents a function that can be provided as a parameter to Start.
+type StartOption func(*config)
+
+// defaults sets the default values for a config.
+func defaults(c *config) {
+ c.serviceName = filepath.Base(os.Args[0])
+ c.sampler = NewAllSampler()
+ c.agentAddr = defaultAddress
+}
+
+// WithPrioritySampling enables priority sampling on the active tracer instance. When using
+// distributed tracing, this option must be enabled in order to get all the parts of a distributed
+// trace sampled. To learn more about priority sampling, please visit:
+// https://docs.datadoghq.com/tracing/getting_further/trace_sampling_and_storage/#priority-sampling-for-distributed-tracing
+func WithPrioritySampling() StartOption {
+ return func(c *config) {
+ c.prioritySampling = newPrioritySampler()
+ }
+}
+
+// WithDebugMode enables debug mode on the tracer, resulting in more verbose logging.
+func WithDebugMode(enabled bool) StartOption {
+ return func(c *config) {
+ c.debug = enabled
+ }
+}
+
+// WithPropagator sets an alternative propagator to be used by the tracer.
+func WithPropagator(p Propagator) StartOption {
+ return func(c *config) {
+ c.propagator = p
+ }
+}
+
+// WithServiceName sets the default service name to be used with the tracer.
+func WithServiceName(name string) StartOption {
+ return func(c *config) {
+ c.serviceName = name
+ }
+}
+
+// WithAgentAddr sets the address where the agent is located. The default is
+// localhost:8126. It should contain both host and port.
+func WithAgentAddr(addr string) StartOption {
+ return func(c *config) {
+ c.agentAddr = addr
+ }
+}
+
+// WithGlobalTag sets a key/value pair which will be set as a tag on all spans
+// created by tracer. This option may be used multiple times.
+func WithGlobalTag(k string, v interface{}) StartOption {
+ return func(c *config) {
+ if c.globalTags == nil {
+ c.globalTags = make(map[string]interface{})
+ }
+ c.globalTags[k] = v
+ }
+}
+
+// WithSampler sets the given sampler to be used with the tracer. By default
+// an all-permissive sampler is used.
+func WithSampler(s Sampler) StartOption {
+ return func(c *config) {
+ c.sampler = s
+ }
+}
+
+// WithHTTPRoundTripper allows customizing the underlying HTTP transport for
+// emitting spans. This is useful for advanced customization such as emitting
+// spans to a unix domain socket. The default should be used in most cases.
+func WithHTTPRoundTripper(r http.RoundTripper) StartOption {
+ return func(c *config) {
+ c.httpRoundTripper = r
+ }
+}
+
+// StartSpanOption is a configuration option for StartSpan. It is aliased in order
+// to help godoc group all the functions returning it together. It is considered
+// more correct to refer to it as the type as the origin, ddtrace.StartSpanOption.
+type StartSpanOption = ddtrace.StartSpanOption
+
+// Tag sets the given key/value pair as a tag on the started Span.
+func Tag(k string, v interface{}) StartSpanOption {
+ return func(cfg *ddtrace.StartSpanConfig) {
+ if cfg.Tags == nil {
+ cfg.Tags = map[string]interface{}{}
+ }
+ cfg.Tags[k] = v
+ }
+}
+
+// ServiceName sets the given service name on the started span. For example "http.server".
+func ServiceName(name string) StartSpanOption {
+ return Tag(ext.ServiceName, name)
+}
+
+// ResourceName sets the given resource name on the started span. A resource could
+// be an SQL query, a URL, an RPC method or something else.
+func ResourceName(name string) StartSpanOption {
+ return Tag(ext.ResourceName, name)
+}
+
+// SpanType sets the given span type on the started span. Some examples in the case of
+// the Datadog APM product could be "web", "db" or "cache".
+func SpanType(name string) StartSpanOption {
+ return Tag(ext.SpanType, name)
+}
+
+// ChildOf tells StartSpan to use the given span context as a parent for the
+// created span.
+func ChildOf(ctx ddtrace.SpanContext) StartSpanOption {
+ return func(cfg *ddtrace.StartSpanConfig) {
+ cfg.Parent = ctx
+ }
+}
+
+// StartTime sets a custom time as the start time for the created span. By
+// default a span is started using the creation time.
+func StartTime(t time.Time) StartSpanOption {
+ return func(cfg *ddtrace.StartSpanConfig) {
+ cfg.StartTime = t
+ }
+}
+
+// FinishOption is a configuration option for FinishSpan. It is aliased in order
+// to help godoc group all the functions returning it together. It is considered
+// more correct to refer to it as the type as the origin, ddtrace.FinishOption.
+type FinishOption = ddtrace.FinishOption
+
+// FinishTime sets the given time as the finishing time for the span. By default,
+// the current time is used.
+func FinishTime(t time.Time) FinishOption {
+ return func(cfg *ddtrace.FinishConfig) {
+ cfg.FinishTime = t
+ }
+}
+
+// WithError marks the span as having had an error. It uses the information from
+// err to set tags such as the error message, error type and stack trace.
+func WithError(err error) FinishOption {
+ return func(cfg *ddtrace.FinishConfig) {
+ cfg.Error = err
+ }
+}
+
+// NoDebugStack prevents any error presented using the WithError finishing option
+// from generating a stack trace. This is useful in situations where errors are frequent
+// and performance is critical.
+func NoDebugStack() FinishOption {
+ return func(cfg *ddtrace.FinishConfig) {
+ cfg.NoDebugStack = true
+ }
+}
diff --git a/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/payload.go b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/payload.go
new file mode 100644
index 000000000..65ce37fec
--- /dev/null
+++ b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/payload.go
@@ -0,0 +1,116 @@
+package tracer
+
+import (
+ "bytes"
+ "encoding/binary"
+ "io"
+
+ "github.com/tinylib/msgp/msgp"
+)
+
+// payload is a wrapper on top of the msgpack encoder which allows constructing an
+// encoded array by pushing its entries sequentially, one at a time. It basically
+// allows us to encode as we would with a stream, except that the contents of the stream
+// can be read as a slice by the msgpack decoder at any time. It follows the guidelines
+// from the msgpack array spec:
+// https://github.com/msgpack/msgpack/blob/master/spec.md#array-format-family
+//
+// payload implements io.Reader and can be used with the decoder directly. To create
+// a new payload use the newPayload method.
+//
+// payload is not safe for concurrent use.
+//
+// This structure basically allows us to push traces into the payload one at a time
+// in order to always have knowledge of the payload size, but also making it possible
+// for the agent to decode it as an array.
+type payload struct {
+ // header specifies the first few bytes in the msgpack stream
+ // indicating the type of array (fixarray, array16 or array32)
+ // and the number of items contained in the stream.
+ header []byte
+
+ // off specifies the current read position on the header.
+ off int
+
+ // count specifies the number of items in the stream.
+ count uint64
+
+ // buf holds the sequence of msgpack-encoded items.
+ buf bytes.Buffer
+}
+
+var _ io.Reader = (*payload)(nil)
+
+// newPayload returns a ready to use payload.
+func newPayload() *payload {
+ p := &payload{
+ header: make([]byte, 8),
+ off: 8,
+ }
+ return p
+}
+
+// push pushes a new item into the stream.
+func (p *payload) push(t spanList) error {
+ if err := msgp.Encode(&p.buf, t); err != nil {
+ return err
+ }
+ p.count++
+ p.updateHeader()
+ return nil
+}
+
+// itemCount returns the number of items available in the srteam.
+func (p *payload) itemCount() int {
+ return int(p.count)
+}
+
+// size returns the payload size in bytes. After the first read the value becomes
+// inaccurate by up to 8 bytes.
+func (p *payload) size() int {
+ return p.buf.Len() + len(p.header) - p.off
+}
+
+// reset resets the internal buffer, counter and read offset.
+func (p *payload) reset() {
+ p.off = 8
+ p.count = 0
+ p.buf.Reset()
+}
+
+// https://github.com/msgpack/msgpack/blob/master/spec.md#array-format-family
+const (
+ msgpackArrayFix byte = 144 // up to 15 items
+ msgpackArray16 = 0xdc // up to 2^16-1 items, followed by size in 2 bytes
+ msgpackArray32 = 0xdd // up to 2^32-1 items, followed by size in 4 bytes
+)
+
+// updateHeader updates the payload header based on the number of items currently
+// present in the stream.
+func (p *payload) updateHeader() {
+ n := p.count
+ switch {
+ case n <= 15:
+ p.header[7] = msgpackArrayFix + byte(n)
+ p.off = 7
+ case n <= 1<<16-1:
+ binary.BigEndian.PutUint64(p.header, n) // writes 2 bytes
+ p.header[5] = msgpackArray16
+ p.off = 5
+ default: // n <= 1<<32-1
+ binary.BigEndian.PutUint64(p.header, n) // writes 4 bytes
+ p.header[3] = msgpackArray32
+ p.off = 3
+ }
+}
+
+// Read implements io.Reader. It reads from the msgpack-encoded stream.
+func (p *payload) Read(b []byte) (n int, err error) {
+ if p.off < len(p.header) {
+ // reading header
+ n = copy(b, p.header[p.off:])
+ p.off += n
+ return n, nil
+ }
+ return p.buf.Read(b)
+}
diff --git a/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/propagator.go b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/propagator.go
new file mode 100644
index 000000000..3c7822d4a
--- /dev/null
+++ b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/propagator.go
@@ -0,0 +1,52 @@
+package tracer
+
+import (
+ "errors"
+
+ "gopkg.in/DataDog/dd-trace-go.v1/ddtrace"
+)
+
+// Propagator implementations should be able to inject and extract
+// SpanContexts into an implementation specific carrier.
+type Propagator interface {
+ // Inject takes the SpanContext and injects it into the carrier.
+ Inject(context ddtrace.SpanContext, carrier interface{}) error
+
+ // Extract returns the SpanContext from the given carrier.
+ Extract(carrier interface{}) (ddtrace.SpanContext, error)
+}
+
+// TextMapWriter allows setting key/value pairs of strings on the underlying
+// data structure. Carriers implementing TextMapWriter are compatible to be
+// used with Datadog's TextMapPropagator.
+type TextMapWriter interface {
+ // Set sets the given key/value pair.
+ Set(key, val string)
+}
+
+// TextMapReader allows iterating over sets of key/value pairs. Carriers implementing
+// TextMapReader are compatible to be used with Datadog's TextMapPropagator.
+type TextMapReader interface {
+ // ForeachKey iterates over all keys that exist in the underlying
+ // carrier. It takes a callback function which will be called
+ // using all key/value pairs as arguments. ForeachKey will return
+ // the first error returned by the handler.
+ ForeachKey(handler func(key, val string) error) error
+}
+
+var (
+ // ErrInvalidCarrier is returned when the carrier provided to the propagator
+ // does not implemented the correct interfaces.
+ ErrInvalidCarrier = errors.New("invalid carrier")
+
+ // ErrInvalidSpanContext is returned when the span context found in the
+ // carrier is not of the expected type.
+ ErrInvalidSpanContext = errors.New("invalid span context")
+
+ // ErrSpanContextCorrupted is returned when there was a problem parsing
+ // the information found in the carrier.
+ ErrSpanContextCorrupted = errors.New("span context corrupted")
+
+ // ErrSpanContextNotFound represents missing information in the given carrier.
+ ErrSpanContextNotFound = errors.New("span context not found")
+)
diff --git a/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/rand.go b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/rand.go
new file mode 100644
index 000000000..356ae5497
--- /dev/null
+++ b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/rand.go
@@ -0,0 +1,50 @@
+package tracer
+
+import (
+ cryptorand "crypto/rand"
+ "log"
+ "math"
+ "math/big"
+ "math/rand"
+ "sync"
+ "time"
+)
+
+// random holds a thread-safe source of random numbers.
+var random *rand.Rand
+
+func init() {
+ var seed int64
+ n, err := cryptorand.Int(cryptorand.Reader, big.NewInt(math.MaxInt64))
+ if err == nil {
+ seed = n.Int64()
+ } else {
+ log.Printf("%scannot generate random seed: %v; using current time\n", errorPrefix, err)
+ seed = time.Now().UnixNano()
+ }
+ random = rand.New(&safeSource{
+ source: rand.NewSource(seed),
+ })
+}
+
+// safeSource holds a thread-safe implementation of rand.Source64.
+type safeSource struct {
+ source rand.Source
+ sync.Mutex
+}
+
+func (rs *safeSource) Int63() int64 {
+ rs.Lock()
+ n := rs.source.Int63()
+ rs.Unlock()
+
+ return n
+}
+
+func (rs *safeSource) Uint64() uint64 { return uint64(rs.Int63()) }
+
+func (rs *safeSource) Seed(seed int64) {
+ rs.Lock()
+ rs.Seed(seed)
+ rs.Unlock()
+}
diff --git a/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/sampler.go b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/sampler.go
new file mode 100644
index 000000000..1c3d87a7a
--- /dev/null
+++ b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/sampler.go
@@ -0,0 +1,140 @@
+package tracer
+
+import (
+ "encoding/json"
+ "io"
+ "math"
+ "sync"
+
+ "gopkg.in/DataDog/dd-trace-go.v1/ddtrace"
+ "gopkg.in/DataDog/dd-trace-go.v1/ddtrace/ext"
+)
+
+// Sampler is the generic interface of any sampler. It must be safe for concurrent use.
+type Sampler interface {
+ // Sample returns true if the given span should be sampled.
+ Sample(span Span) bool
+}
+
+// RateSampler is a sampler implementation which randomly selects spans using a
+// provided rate. For example, a rate of 0.75 will permit 75% of the spans.
+// RateSampler implementations should be safe for concurrent use.
+type RateSampler interface {
+ Sampler
+
+ // Rate returns the current sample rate.
+ Rate() float64
+
+ // SetRate sets a new sample rate.
+ SetRate(rate float64)
+}
+
+// rateSampler samples from a sample rate.
+type rateSampler struct {
+ sync.RWMutex
+ rate float64
+}
+
+// NewAllSampler is a short-hand for NewRateSampler(1). It is all-permissive.
+func NewAllSampler() RateSampler { return NewRateSampler(1) }
+
+// NewRateSampler returns an initialized RateSampler with a given sample rate.
+func NewRateSampler(rate float64) RateSampler {
+ return &rateSampler{rate: rate}
+}
+
+// Rate returns the current rate of the sampler.
+func (r *rateSampler) Rate() float64 {
+ r.RLock()
+ defer r.RUnlock()
+ return r.rate
+}
+
+// SetRate sets a new sampling rate.
+func (r *rateSampler) SetRate(rate float64) {
+ r.Lock()
+ r.rate = rate
+ r.Unlock()
+}
+
+// constants used for the Knuth hashing, same as agent.
+const knuthFactor = uint64(1111111111111111111)
+
+// Sample returns true if the given span should be sampled.
+func (r *rateSampler) Sample(spn ddtrace.Span) bool {
+ s, ok := spn.(*span)
+ if !ok {
+ return false
+ }
+ r.RLock()
+ defer r.RUnlock()
+ return sampledByRate(s.TraceID, r.rate)
+}
+
+// sampledByRate verifies if the number n should be sampled at the specified
+// rate.
+func sampledByRate(n uint64, rate float64) bool {
+ if rate < 1 {
+ return n*knuthFactor < uint64(rate*math.MaxUint64)
+ }
+ return true
+}
+
+// prioritySampler holds a set of per-service sampling rates and applies
+// them to spans.
+type prioritySampler struct {
+ mu sync.RWMutex
+ rates map[string]float64
+ defaultRate float64
+}
+
+func newPrioritySampler() *prioritySampler {
+ return &prioritySampler{
+ rates: make(map[string]float64),
+ defaultRate: 1.,
+ }
+}
+
+// readRatesJSON will try to read the rates as JSON from the given io.ReadCloser.
+func (ps *prioritySampler) readRatesJSON(rc io.ReadCloser) error {
+ var payload struct {
+ Rates map[string]float64 `json:"rate_by_service"`
+ }
+ if err := json.NewDecoder(rc).Decode(&payload); err != nil {
+ return err
+ }
+ rc.Close()
+ const defaultRateKey = "service:,env:"
+ ps.mu.Lock()
+ defer ps.mu.Unlock()
+ ps.rates = payload.Rates
+ if v, ok := ps.rates[defaultRateKey]; ok {
+ ps.defaultRate = v
+ delete(ps.rates, defaultRateKey)
+ }
+ return nil
+}
+
+// getRate returns the sampling rate to be used for the given span. Callers must
+// guard the span.
+func (ps *prioritySampler) getRate(spn *span) float64 {
+ key := "service:" + spn.Service + ",env:" + spn.Meta[ext.Environment]
+ ps.mu.RLock()
+ defer ps.mu.RUnlock()
+ if rate, ok := ps.rates[key]; ok {
+ return rate
+ }
+ return ps.defaultRate
+}
+
+// apply applies sampling priority to the given span. Caller must ensure it is safe
+// to modify the span.
+func (ps *prioritySampler) apply(spn *span) {
+ rate := ps.getRate(spn)
+ if sampledByRate(spn.TraceID, rate) {
+ spn.SetTag(ext.SamplingPriority, ext.PriorityAutoKeep)
+ } else {
+ spn.SetTag(ext.SamplingPriority, ext.PriorityAutoReject)
+ }
+ spn.SetTag(samplingPriorityRateKey, rate)
+}
diff --git a/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/span.go b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/span.go
new file mode 100644
index 000000000..1e3e469e8
--- /dev/null
+++ b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/span.go
@@ -0,0 +1,241 @@
+//go:generate msgp -unexported -marshal=false -o=span_msgp.go -tests=false
+
+package tracer
+
+import (
+ "fmt"
+ "reflect"
+ "runtime/debug"
+ "strings"
+ "sync"
+ "time"
+
+ "github.com/tinylib/msgp/msgp"
+ "gopkg.in/DataDog/dd-trace-go.v1/ddtrace"
+ "gopkg.in/DataDog/dd-trace-go.v1/ddtrace/ext"
+)
+
+type (
+ // spanList implements msgp.Encodable on top of a slice of spans.
+ spanList []*span
+
+ // spanLists implements msgp.Decodable on top of a slice of spanList.
+ // This type is only used in tests.
+ spanLists []spanList
+)
+
+var (
+ _ ddtrace.Span = (*span)(nil)
+ _ msgp.Encodable = (*spanList)(nil)
+ _ msgp.Decodable = (*spanLists)(nil)
+)
+
+// span represents a computation. Callers must call Finish when a span is
+// complete to ensure it's submitted.
+type span struct {
+ sync.RWMutex `msg:"-"`
+
+ Name string `msg:"name"` // operation name
+ Service string `msg:"service"` // service name (i.e. "grpc.server", "http.request")
+ Resource string `msg:"resource"` // resource name (i.e. "/user?id=123", "SELECT * FROM users")
+ Type string `msg:"type"` // protocol associated with the span (i.e. "web", "db", "cache")
+ Start int64 `msg:"start"` // span start time expressed in nanoseconds since epoch
+ Duration int64 `msg:"duration"` // duration of the span expressed in nanoseconds
+ Meta map[string]string `msg:"meta,omitempty"` // arbitrary map of metadata
+ Metrics map[string]float64 `msg:"metrics,omitempty"` // arbitrary map of numeric metrics
+ SpanID uint64 `msg:"span_id"` // identifier of this span
+ TraceID uint64 `msg:"trace_id"` // identifier of the root span
+ ParentID uint64 `msg:"parent_id"` // identifier of the span's direct parent
+ Error int32 `msg:"error"` // error status of the span; 0 means no errors
+
+ finished bool `msg:"-"` // true if the span has been submitted to a tracer.
+ context *spanContext `msg:"-"` // span propagation context
+}
+
+// Context yields the SpanContext for this Span. Note that the return
+// value of Context() is still valid after a call to Finish(). This is
+// called the span context and it is different from Go's context.
+func (s *span) Context() ddtrace.SpanContext { return s.context }
+
+// SetBaggageItem sets a key/value pair as baggage on the span. Baggage items
+// are propagated down to descendant spans and injected cross-process. Use with
+// care as it adds extra load onto your tracing layer.
+func (s *span) SetBaggageItem(key, val string) {
+ s.context.setBaggageItem(key, val)
+}
+
+// BaggageItem gets the value for a baggage item given its key. Returns the
+// empty string if the value isn't found in this Span.
+func (s *span) BaggageItem(key string) string {
+ return s.context.baggageItem(key)
+}
+
+// SetTag adds a set of key/value metadata to the span.
+func (s *span) SetTag(key string, value interface{}) {
+ s.Lock()
+ defer s.Unlock()
+ // We don't lock spans when flushing, so we could have a data race when
+ // modifying a span as it's being flushed. This protects us against that
+ // race, since spans are marked `finished` before we flush them.
+ if s.finished {
+ return
+ }
+ if key == ext.Error {
+ s.setTagError(value, true)
+ return
+ }
+ if v, ok := value.(string); ok {
+ s.setTagString(key, v)
+ return
+ }
+ if v, ok := toFloat64(value); ok {
+ s.setTagNumeric(key, v)
+ return
+ }
+ // not numeric, not a string and not an error, the likelihood of this
+ // happening is close to zero, but we should nevertheless account for it.
+ s.Meta[key] = fmt.Sprint(value)
+}
+
+// setTagError sets the error tag. It accounts for various valid scenarios.
+// This method is not safe for concurrent use.
+func (s *span) setTagError(value interface{}, debugStack bool) {
+ if s.finished {
+ return
+ }
+ switch v := value.(type) {
+ case bool:
+ // bool value as per Opentracing spec.
+ if !v {
+ s.Error = 0
+ } else {
+ s.Error = 1
+ }
+ case error:
+ // if anyone sets an error value as the tag, be nice here
+ // and provide all the benefits.
+ s.Error = 1
+ s.Meta[ext.ErrorMsg] = v.Error()
+ s.Meta[ext.ErrorType] = reflect.TypeOf(v).String()
+ if debugStack {
+ s.Meta[ext.ErrorStack] = string(debug.Stack())
+ }
+ case nil:
+ // no error
+ s.Error = 0
+ default:
+ // in all other cases, let's assume that setting this tag
+ // is the result of an error.
+ s.Error = 1
+ }
+}
+
+// setTagString sets a string tag. This method is not safe for concurrent use.
+func (s *span) setTagString(key, v string) {
+ switch key {
+ case ext.ServiceName:
+ s.Service = v
+ case ext.ResourceName:
+ s.Resource = v
+ case ext.SpanType:
+ s.Type = v
+ default:
+ s.Meta[key] = v
+ }
+}
+
+// setTagNumeric sets a numeric tag, in our case called a metric. This method
+// is not safe for concurrent use.
+func (s *span) setTagNumeric(key string, v float64) {
+ switch key {
+ case ext.SamplingPriority:
+ // setting sampling priority per spec
+ s.Metrics[samplingPriorityKey] = v
+ s.context.setSamplingPriority(int(v))
+ default:
+ s.Metrics[key] = v
+ }
+}
+
+// Finish closes this Span (but not its children) providing the duration
+// of its part of the tracing session.
+func (s *span) Finish(opts ...ddtrace.FinishOption) {
+ var cfg ddtrace.FinishConfig
+ for _, fn := range opts {
+ fn(&cfg)
+ }
+ var t int64
+ if cfg.FinishTime.IsZero() {
+ t = now()
+ } else {
+ t = cfg.FinishTime.UnixNano()
+ }
+ if cfg.Error != nil {
+ s.Lock()
+ s.setTagError(cfg.Error, !cfg.NoDebugStack)
+ s.Unlock()
+ }
+ s.finish(t)
+}
+
+// SetOperationName sets or changes the operation name.
+func (s *span) SetOperationName(operationName string) {
+ s.Lock()
+ defer s.Unlock()
+
+ s.Name = operationName
+}
+
+func (s *span) finish(finishTime int64) {
+ s.Lock()
+ defer s.Unlock()
+ // We don't lock spans when flushing, so we could have a data race when
+ // modifying a span as it's being flushed. This protects us against that
+ // race, since spans are marked `finished` before we flush them.
+ if s.finished {
+ // already finished
+ return
+ }
+ if s.Duration == 0 {
+ s.Duration = finishTime - s.Start
+ }
+ s.finished = true
+
+ if !s.context.sampled {
+ // not sampled
+ return
+ }
+ s.context.finish()
+}
+
+// String returns a human readable representation of the span. Not for
+// production, just debugging.
+func (s *span) String() string {
+ lines := []string{
+ fmt.Sprintf("Name: %s", s.Name),
+ fmt.Sprintf("Service: %s", s.Service),
+ fmt.Sprintf("Resource: %s", s.Resource),
+ fmt.Sprintf("TraceID: %d", s.TraceID),
+ fmt.Sprintf("SpanID: %d", s.SpanID),
+ fmt.Sprintf("ParentID: %d", s.ParentID),
+ fmt.Sprintf("Start: %s", time.Unix(0, s.Start)),
+ fmt.Sprintf("Duration: %s", time.Duration(s.Duration)),
+ fmt.Sprintf("Error: %d", s.Error),
+ fmt.Sprintf("Type: %s", s.Type),
+ "Tags:",
+ }
+ s.RLock()
+ for key, val := range s.Meta {
+ lines = append(lines, fmt.Sprintf("\t%s:%s", key, val))
+ }
+ for key, val := range s.Metrics {
+ lines = append(lines, fmt.Sprintf("\t%s:%f", key, val))
+ }
+ s.RUnlock()
+ return strings.Join(lines, "\n")
+}
+
+const (
+ samplingPriorityKey = "_sampling_priority_v1"
+ samplingPriorityRateKey = "_sampling_priority_rate_v1"
+)
diff --git a/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/span_msgp.go b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/span_msgp.go
new file mode 100644
index 000000000..39cac84a0
--- /dev/null
+++ b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/span_msgp.go
@@ -0,0 +1,448 @@
+package tracer
+
+// NOTE: THIS FILE WAS PRODUCED BY THE
+// MSGP CODE GENERATION TOOL (github.com/tinylib/msgp)
+// DO NOT EDIT
+
+import (
+ "github.com/tinylib/msgp/msgp"
+)
+
+// DecodeMsg implements msgp.Decodable
+func (z *span) DecodeMsg(dc *msgp.Reader) (err error) {
+ var field []byte
+ _ = field
+ var zb0001 uint32
+ zb0001, err = dc.ReadMapHeader()
+ if err != nil {
+ return
+ }
+ for zb0001 > 0 {
+ zb0001--
+ field, err = dc.ReadMapKeyPtr()
+ if err != nil {
+ return
+ }
+ switch msgp.UnsafeString(field) {
+ case "name":
+ z.Name, err = dc.ReadString()
+ if err != nil {
+ return
+ }
+ case "service":
+ z.Service, err = dc.ReadString()
+ if err != nil {
+ return
+ }
+ case "resource":
+ z.Resource, err = dc.ReadString()
+ if err != nil {
+ return
+ }
+ case "type":
+ z.Type, err = dc.ReadString()
+ if err != nil {
+ return
+ }
+ case "start":
+ z.Start, err = dc.ReadInt64()
+ if err != nil {
+ return
+ }
+ case "duration":
+ z.Duration, err = dc.ReadInt64()
+ if err != nil {
+ return
+ }
+ case "meta":
+ var zb0002 uint32
+ zb0002, err = dc.ReadMapHeader()
+ if err != nil {
+ return
+ }
+ if z.Meta == nil && zb0002 > 0 {
+ z.Meta = make(map[string]string, zb0002)
+ } else if len(z.Meta) > 0 {
+ for key := range z.Meta {
+ delete(z.Meta, key)
+ }
+ }
+ for zb0002 > 0 {
+ zb0002--
+ var za0001 string
+ var za0002 string
+ za0001, err = dc.ReadString()
+ if err != nil {
+ return
+ }
+ za0002, err = dc.ReadString()
+ if err != nil {
+ return
+ }
+ z.Meta[za0001] = za0002
+ }
+ case "metrics":
+ var zb0003 uint32
+ zb0003, err = dc.ReadMapHeader()
+ if err != nil {
+ return
+ }
+ if z.Metrics == nil && zb0003 > 0 {
+ z.Metrics = make(map[string]float64, zb0003)
+ } else if len(z.Metrics) > 0 {
+ for key := range z.Metrics {
+ delete(z.Metrics, key)
+ }
+ }
+ for zb0003 > 0 {
+ zb0003--
+ var za0003 string
+ var za0004 float64
+ za0003, err = dc.ReadString()
+ if err != nil {
+ return
+ }
+ za0004, err = dc.ReadFloat64()
+ if err != nil {
+ return
+ }
+ z.Metrics[za0003] = za0004
+ }
+ case "span_id":
+ z.SpanID, err = dc.ReadUint64()
+ if err != nil {
+ return
+ }
+ case "trace_id":
+ z.TraceID, err = dc.ReadUint64()
+ if err != nil {
+ return
+ }
+ case "parent_id":
+ z.ParentID, err = dc.ReadUint64()
+ if err != nil {
+ return
+ }
+ case "error":
+ z.Error, err = dc.ReadInt32()
+ if err != nil {
+ return
+ }
+ default:
+ err = dc.Skip()
+ if err != nil {
+ return
+ }
+ }
+ }
+ return
+}
+
+// EncodeMsg implements msgp.Encodable
+func (z *span) EncodeMsg(en *msgp.Writer) (err error) {
+ // map header, size 12
+ // write "name"
+ err = en.Append(0x8c, 0xa4, 0x6e, 0x61, 0x6d, 0x65)
+ if err != nil {
+ return
+ }
+ err = en.WriteString(z.Name)
+ if err != nil {
+ return
+ }
+ // write "service"
+ err = en.Append(0xa7, 0x73, 0x65, 0x72, 0x76, 0x69, 0x63, 0x65)
+ if err != nil {
+ return
+ }
+ err = en.WriteString(z.Service)
+ if err != nil {
+ return
+ }
+ // write "resource"
+ err = en.Append(0xa8, 0x72, 0x65, 0x73, 0x6f, 0x75, 0x72, 0x63, 0x65)
+ if err != nil {
+ return
+ }
+ err = en.WriteString(z.Resource)
+ if err != nil {
+ return
+ }
+ // write "type"
+ err = en.Append(0xa4, 0x74, 0x79, 0x70, 0x65)
+ if err != nil {
+ return
+ }
+ err = en.WriteString(z.Type)
+ if err != nil {
+ return
+ }
+ // write "start"
+ err = en.Append(0xa5, 0x73, 0x74, 0x61, 0x72, 0x74)
+ if err != nil {
+ return
+ }
+ err = en.WriteInt64(z.Start)
+ if err != nil {
+ return
+ }
+ // write "duration"
+ err = en.Append(0xa8, 0x64, 0x75, 0x72, 0x61, 0x74, 0x69, 0x6f, 0x6e)
+ if err != nil {
+ return
+ }
+ err = en.WriteInt64(z.Duration)
+ if err != nil {
+ return
+ }
+ // write "meta"
+ err = en.Append(0xa4, 0x6d, 0x65, 0x74, 0x61)
+ if err != nil {
+ return
+ }
+ err = en.WriteMapHeader(uint32(len(z.Meta)))
+ if err != nil {
+ return
+ }
+ for za0001, za0002 := range z.Meta {
+ err = en.WriteString(za0001)
+ if err != nil {
+ return
+ }
+ err = en.WriteString(za0002)
+ if err != nil {
+ return
+ }
+ }
+ // write "metrics"
+ err = en.Append(0xa7, 0x6d, 0x65, 0x74, 0x72, 0x69, 0x63, 0x73)
+ if err != nil {
+ return
+ }
+ err = en.WriteMapHeader(uint32(len(z.Metrics)))
+ if err != nil {
+ return
+ }
+ for za0003, za0004 := range z.Metrics {
+ err = en.WriteString(za0003)
+ if err != nil {
+ return
+ }
+ err = en.WriteFloat64(za0004)
+ if err != nil {
+ return
+ }
+ }
+ // write "span_id"
+ err = en.Append(0xa7, 0x73, 0x70, 0x61, 0x6e, 0x5f, 0x69, 0x64)
+ if err != nil {
+ return
+ }
+ err = en.WriteUint64(z.SpanID)
+ if err != nil {
+ return
+ }
+ // write "trace_id"
+ err = en.Append(0xa8, 0x74, 0x72, 0x61, 0x63, 0x65, 0x5f, 0x69, 0x64)
+ if err != nil {
+ return
+ }
+ err = en.WriteUint64(z.TraceID)
+ if err != nil {
+ return
+ }
+ // write "parent_id"
+ err = en.Append(0xa9, 0x70, 0x61, 0x72, 0x65, 0x6e, 0x74, 0x5f, 0x69, 0x64)
+ if err != nil {
+ return
+ }
+ err = en.WriteUint64(z.ParentID)
+ if err != nil {
+ return
+ }
+ // write "error"
+ err = en.Append(0xa5, 0x65, 0x72, 0x72, 0x6f, 0x72)
+ if err != nil {
+ return
+ }
+ err = en.WriteInt32(z.Error)
+ if err != nil {
+ return
+ }
+ return
+}
+
+// Msgsize returns an upper bound estimate of the number of bytes occupied by the serialized message
+func (z *span) Msgsize() (s int) {
+ s = 1 + 5 + msgp.StringPrefixSize + len(z.Name) + 8 + msgp.StringPrefixSize + len(z.Service) + 9 + msgp.StringPrefixSize + len(z.Resource) + 5 + msgp.StringPrefixSize + len(z.Type) + 6 + msgp.Int64Size + 9 + msgp.Int64Size + 5 + msgp.MapHeaderSize
+ if z.Meta != nil {
+ for za0001, za0002 := range z.Meta {
+ _ = za0002
+ s += msgp.StringPrefixSize + len(za0001) + msgp.StringPrefixSize + len(za0002)
+ }
+ }
+ s += 8 + msgp.MapHeaderSize
+ if z.Metrics != nil {
+ for za0003, za0004 := range z.Metrics {
+ _ = za0004
+ s += msgp.StringPrefixSize + len(za0003) + msgp.Float64Size
+ }
+ }
+ s += 8 + msgp.Uint64Size + 9 + msgp.Uint64Size + 10 + msgp.Uint64Size + 6 + msgp.Int32Size
+ return
+}
+
+// DecodeMsg implements msgp.Decodable
+func (z *spanList) DecodeMsg(dc *msgp.Reader) (err error) {
+ var zb0002 uint32
+ zb0002, err = dc.ReadArrayHeader()
+ if err != nil {
+ return
+ }
+ if cap((*z)) >= int(zb0002) {
+ (*z) = (*z)[:zb0002]
+ } else {
+ (*z) = make(spanList, zb0002)
+ }
+ for zb0001 := range *z {
+ if dc.IsNil() {
+ err = dc.ReadNil()
+ if err != nil {
+ return
+ }
+ (*z)[zb0001] = nil
+ } else {
+ if (*z)[zb0001] == nil {
+ (*z)[zb0001] = new(span)
+ }
+ err = (*z)[zb0001].DecodeMsg(dc)
+ if err != nil {
+ return
+ }
+ }
+ }
+ return
+}
+
+// EncodeMsg implements msgp.Encodable
+func (z spanList) EncodeMsg(en *msgp.Writer) (err error) {
+ err = en.WriteArrayHeader(uint32(len(z)))
+ if err != nil {
+ return
+ }
+ for zb0003 := range z {
+ if z[zb0003] == nil {
+ err = en.WriteNil()
+ if err != nil {
+ return
+ }
+ } else {
+ err = z[zb0003].EncodeMsg(en)
+ if err != nil {
+ return
+ }
+ }
+ }
+ return
+}
+
+// Msgsize returns an upper bound estimate of the number of bytes occupied by the serialized message
+func (z spanList) Msgsize() (s int) {
+ s = msgp.ArrayHeaderSize
+ for zb0003 := range z {
+ if z[zb0003] == nil {
+ s += msgp.NilSize
+ } else {
+ s += z[zb0003].Msgsize()
+ }
+ }
+ return
+}
+
+// DecodeMsg implements msgp.Decodable
+func (z *spanLists) DecodeMsg(dc *msgp.Reader) (err error) {
+ var zb0003 uint32
+ zb0003, err = dc.ReadArrayHeader()
+ if err != nil {
+ return
+ }
+ if cap((*z)) >= int(zb0003) {
+ (*z) = (*z)[:zb0003]
+ } else {
+ (*z) = make(spanLists, zb0003)
+ }
+ for zb0001 := range *z {
+ var zb0004 uint32
+ zb0004, err = dc.ReadArrayHeader()
+ if err != nil {
+ return
+ }
+ if cap((*z)[zb0001]) >= int(zb0004) {
+ (*z)[zb0001] = ((*z)[zb0001])[:zb0004]
+ } else {
+ (*z)[zb0001] = make(spanList, zb0004)
+ }
+ for zb0002 := range (*z)[zb0001] {
+ if dc.IsNil() {
+ err = dc.ReadNil()
+ if err != nil {
+ return
+ }
+ (*z)[zb0001][zb0002] = nil
+ } else {
+ if (*z)[zb0001][zb0002] == nil {
+ (*z)[zb0001][zb0002] = new(span)
+ }
+ err = (*z)[zb0001][zb0002].DecodeMsg(dc)
+ if err != nil {
+ return
+ }
+ }
+ }
+ }
+ return
+}
+
+// EncodeMsg implements msgp.Encodable
+func (z spanLists) EncodeMsg(en *msgp.Writer) (err error) {
+ err = en.WriteArrayHeader(uint32(len(z)))
+ if err != nil {
+ return
+ }
+ for zb0005 := range z {
+ err = en.WriteArrayHeader(uint32(len(z[zb0005])))
+ if err != nil {
+ return
+ }
+ for zb0006 := range z[zb0005] {
+ if z[zb0005][zb0006] == nil {
+ err = en.WriteNil()
+ if err != nil {
+ return
+ }
+ } else {
+ err = z[zb0005][zb0006].EncodeMsg(en)
+ if err != nil {
+ return
+ }
+ }
+ }
+ }
+ return
+}
+
+// Msgsize returns an upper bound estimate of the number of bytes occupied by the serialized message
+func (z spanLists) Msgsize() (s int) {
+ s = msgp.ArrayHeaderSize
+ for zb0005 := range z {
+ s += msgp.ArrayHeaderSize
+ for zb0006 := range z[zb0005] {
+ if z[zb0005][zb0006] == nil {
+ s += msgp.NilSize
+ } else {
+ s += z[zb0005][zb0006].Msgsize()
+ }
+ }
+ }
+ return
+}
diff --git a/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/spancontext.go b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/spancontext.go
new file mode 100644
index 000000000..6758f3ba0
--- /dev/null
+++ b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/spancontext.go
@@ -0,0 +1,193 @@
+package tracer
+
+import (
+ "sync"
+
+ "gopkg.in/DataDog/dd-trace-go.v1/ddtrace"
+ "gopkg.in/DataDog/dd-trace-go.v1/ddtrace/internal"
+)
+
+var _ ddtrace.SpanContext = (*spanContext)(nil)
+
+// SpanContext represents a span state that can propagate to descendant spans
+// and across process boundaries. It contains all the information needed to
+// spawn a direct descendant of the span that it belongs to. It can be used
+// to create distributed tracing by propagating it using the provided interfaces.
+type spanContext struct {
+ // the below group should propagate only locally
+
+ trace *trace // reference to the trace that this span belongs too
+ span *span // reference to the span that hosts this context
+ sampled bool // whether this span will be sampled or not
+
+ // the below group should propagate cross-process
+
+ traceID uint64
+ spanID uint64
+
+ mu sync.RWMutex // guards below fields
+ baggage map[string]string
+ priority int
+ hasPriority bool
+}
+
+// newSpanContext creates a new SpanContext to serve as context for the given
+// span. If the provided parent is not nil, the context will inherit the trace,
+// baggage and other values from it. This method also pushes the span into the
+// new context's trace and as a result, it should not be called multiple times
+// for the same span.
+func newSpanContext(span *span, parent *spanContext) *spanContext {
+ context := &spanContext{
+ traceID: span.TraceID,
+ spanID: span.SpanID,
+ sampled: true,
+ span: span,
+ }
+ if v, ok := span.Metrics[samplingPriorityKey]; ok {
+ context.hasPriority = true
+ context.priority = int(v)
+ }
+ if parent != nil {
+ context.trace = parent.trace
+ context.sampled = parent.sampled
+ context.hasPriority = parent.hasSamplingPriority()
+ context.priority = parent.samplingPriority()
+ parent.ForeachBaggageItem(func(k, v string) bool {
+ context.setBaggageItem(k, v)
+ return true
+ })
+ }
+ if context.trace == nil {
+ context.trace = newTrace()
+ }
+ // put span in context's trace
+ context.trace.push(span)
+ return context
+}
+
+// SpanID implements ddtrace.SpanContext.
+func (c *spanContext) SpanID() uint64 { return c.spanID }
+
+// TraceID implements ddtrace.SpanContext.
+func (c *spanContext) TraceID() uint64 { return c.traceID }
+
+// ForeachBaggageItem implements ddtrace.SpanContext.
+func (c *spanContext) ForeachBaggageItem(handler func(k, v string) bool) {
+ c.mu.RLock()
+ defer c.mu.RUnlock()
+ for k, v := range c.baggage {
+ if !handler(k, v) {
+ break
+ }
+ }
+}
+
+func (c *spanContext) setSamplingPriority(p int) {
+ c.mu.Lock()
+ defer c.mu.Unlock()
+ c.priority = p
+ c.hasPriority = true
+}
+
+func (c *spanContext) samplingPriority() int {
+ c.mu.RLock()
+ defer c.mu.RUnlock()
+ return c.priority
+}
+
+func (c *spanContext) hasSamplingPriority() bool {
+ c.mu.RLock()
+ defer c.mu.RUnlock()
+ return c.hasPriority
+}
+
+func (c *spanContext) setBaggageItem(key, val string) {
+ c.mu.Lock()
+ defer c.mu.Unlock()
+ if c.baggage == nil {
+ c.baggage = make(map[string]string, 1)
+ }
+ c.baggage[key] = val
+}
+
+func (c *spanContext) baggageItem(key string) string {
+ c.mu.RLock()
+ defer c.mu.RUnlock()
+ return c.baggage[key]
+}
+
+// finish marks this span as finished in the trace.
+func (c *spanContext) finish() { c.trace.ackFinish() }
+
+// trace holds information about a specific trace. This structure is shared
+// between all spans in a trace.
+type trace struct {
+ mu sync.RWMutex // guards below fields
+ spans []*span // all the spans that are part of this trace
+ finished int // the number of finished spans
+ full bool // signifies that the span buffer is full
+}
+
+var (
+ // traceStartSize is the initial size of our trace buffer,
+ // by default we allocate for a handful of spans within the trace,
+ // reasonable as span is actually way bigger, and avoids re-allocating
+ // over and over. Could be fine-tuned at runtime.
+ traceStartSize = 10
+ // traceMaxSize is the maximum number of spans we keep in memory.
+ // This is to avoid memory leaks, if above that value, spans are randomly
+ // dropped and ignore, resulting in corrupted tracing data, but ensuring
+ // original program continues to work as expected.
+ traceMaxSize = int(1e5)
+)
+
+// newTrace creates a new trace using the given callback which will be called
+// upon completion of the trace.
+func newTrace() *trace {
+ return &trace{spans: make([]*span, 0, traceStartSize)}
+}
+
+// push pushes a new span into the trace. If the buffer is full, it returns
+// a errBufferFull error.
+func (t *trace) push(sp *span) {
+ t.mu.Lock()
+ defer t.mu.Unlock()
+ if t.full {
+ return
+ }
+ if len(t.spans) >= traceMaxSize {
+ // capacity is reached, we will not be able to complete this trace.
+ t.full = true
+ t.spans = nil // GC
+ if tr, ok := internal.GetGlobalTracer().(*tracer); ok {
+ // we have a tracer we can submit errors too.
+ tr.pushError(&spanBufferFullError{})
+ }
+ return
+ }
+ t.spans = append(t.spans, sp)
+}
+
+// ackFinish aknowledges that another span in the trace has finished, and checks
+// if the trace is complete, in which case it calls the onFinish function.
+func (t *trace) ackFinish() {
+ t.mu.Lock()
+ defer t.mu.Unlock()
+ if t.full {
+ // capacity has been reached, the buffer is no longer tracking
+ // all the spans in the trace, so the below conditions will not
+ // be accurate and would trigger a pre-mature flush, exposing us
+ // to a race condition where spans can be modified while flushing.
+ return
+ }
+ t.finished++
+ if len(t.spans) != t.finished {
+ return
+ }
+ if tr, ok := internal.GetGlobalTracer().(*tracer); ok {
+ // we have a tracer that can receive completed traces.
+ tr.pushTrace(t.spans)
+ }
+ t.spans = nil
+ t.finished = 0 // important, because a buffer can be used for several flushes
+}
diff --git a/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/textmap.go b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/textmap.go
new file mode 100644
index 000000000..30c4c78e6
--- /dev/null
+++ b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/textmap.go
@@ -0,0 +1,197 @@
+package tracer
+
+import (
+ "net/http"
+ "strconv"
+ "strings"
+
+ "gopkg.in/DataDog/dd-trace-go.v1/ddtrace"
+)
+
+// HTTPHeadersCarrier wraps an http.Header as a TextMapWriter and TextMapReader, allowing
+// it to be used using the provided Propagator implementation.
+type HTTPHeadersCarrier http.Header
+
+var _ TextMapWriter = (*HTTPHeadersCarrier)(nil)
+var _ TextMapReader = (*HTTPHeadersCarrier)(nil)
+
+// Set implements TextMapWriter.
+func (c HTTPHeadersCarrier) Set(key, val string) {
+ http.Header(c).Set(key, val)
+}
+
+// ForeachKey implements TextMapReader.
+func (c HTTPHeadersCarrier) ForeachKey(handler func(key, val string) error) error {
+ for k, vals := range c {
+ for _, v := range vals {
+ if err := handler(k, v); err != nil {
+ return err
+ }
+ }
+ }
+ return nil
+}
+
+// TextMapCarrier allows the use of a regular map[string]string as both TextMapWriter
+// and TextMapReader, making it compatible with the provided Propagator.
+type TextMapCarrier map[string]string
+
+var _ TextMapWriter = (*TextMapCarrier)(nil)
+var _ TextMapReader = (*TextMapCarrier)(nil)
+
+// Set implements TextMapWriter.
+func (c TextMapCarrier) Set(key, val string) {
+ c[key] = val
+}
+
+// ForeachKey conforms to the TextMapReader interface.
+func (c TextMapCarrier) ForeachKey(handler func(key, val string) error) error {
+ for k, v := range c {
+ if err := handler(k, v); err != nil {
+ return err
+ }
+ }
+ return nil
+}
+
+const (
+ // DefaultBaggageHeaderPrefix specifies the prefix that will be used in
+ // HTTP headers or text maps to prefix baggage keys.
+ DefaultBaggageHeaderPrefix = "ot-baggage-"
+
+ // DefaultTraceIDHeader specifies the key that will be used in HTTP headers
+ // or text maps to store the trace ID.
+ DefaultTraceIDHeader = "x-datadog-trace-id"
+
+ // DefaultParentIDHeader specifies the key that will be used in HTTP headers
+ // or text maps to store the parent ID.
+ DefaultParentIDHeader = "x-datadog-parent-id"
+
+ // DefaultPriorityHeader specifies the key that will be used in HTTP headers
+ // or text maps to store the sampling priority value.
+ DefaultPriorityHeader = "x-datadog-sampling-priority"
+)
+
+// PropagatorConfig defines the configuration for initializing a propagator.
+type PropagatorConfig struct {
+ // BaggagePrefix specifies the prefix that will be used to store baggage
+ // items in a map. It defaults to DefaultBaggageHeaderPrefix.
+ BaggagePrefix string
+
+ // TraceHeader specifies the map key that will be used to store the trace ID.
+ // It defaults to DefaultTraceIDHeader.
+ TraceHeader string
+
+ // ParentHeader specifies the map key that will be used to store the parent ID.
+ // It defaults to DefaultParentIDHeader.
+ ParentHeader string
+
+ // PriorityHeader specifies the map key that will be used to store the sampling priority.
+ // It deafults to DefaultPriorityHeader.
+ PriorityHeader string
+}
+
+// NewPropagator returns a new propagator which uses TextMap to inject
+// and extract values. It propagates trace and span IDs and baggage.
+// To use the defaults, nil may be provided in place of the config.
+func NewPropagator(cfg *PropagatorConfig) Propagator {
+ if cfg == nil {
+ cfg = new(PropagatorConfig)
+ }
+ if cfg.BaggagePrefix == "" {
+ cfg.BaggagePrefix = DefaultBaggageHeaderPrefix
+ }
+ if cfg.TraceHeader == "" {
+ cfg.TraceHeader = DefaultTraceIDHeader
+ }
+ if cfg.ParentHeader == "" {
+ cfg.ParentHeader = DefaultParentIDHeader
+ }
+ if cfg.PriorityHeader == "" {
+ cfg.PriorityHeader = DefaultPriorityHeader
+ }
+ return &propagator{cfg}
+}
+
+// propagator implements a propagator which uses TextMap internally.
+// It propagates the trace and span IDs, as well as the baggage from the
+// context.
+type propagator struct{ cfg *PropagatorConfig }
+
+// Inject defines the Propagator to propagate SpanContext data
+// out of the current process. The implementation propagates the
+// TraceID and the current active SpanID, as well as the Span baggage.
+func (p *propagator) Inject(spanCtx ddtrace.SpanContext, carrier interface{}) error {
+ switch v := carrier.(type) {
+ case TextMapWriter:
+ return p.injectTextMap(spanCtx, v)
+ default:
+ return ErrInvalidCarrier
+ }
+}
+
+func (p *propagator) injectTextMap(spanCtx ddtrace.SpanContext, writer TextMapWriter) error {
+ ctx, ok := spanCtx.(*spanContext)
+ if !ok || ctx.traceID == 0 || ctx.spanID == 0 {
+ return ErrInvalidSpanContext
+ }
+ // propagate the TraceID and the current active SpanID
+ writer.Set(p.cfg.TraceHeader, strconv.FormatUint(ctx.traceID, 10))
+ writer.Set(p.cfg.ParentHeader, strconv.FormatUint(ctx.spanID, 10))
+ if ctx.hasSamplingPriority() {
+ writer.Set(p.cfg.PriorityHeader, strconv.Itoa(ctx.samplingPriority()))
+ }
+ // propagate OpenTracing baggage
+ for k, v := range ctx.baggage {
+ writer.Set(p.cfg.BaggagePrefix+k, v)
+ }
+ return nil
+}
+
+// Extract implements Propagator.
+func (p *propagator) Extract(carrier interface{}) (ddtrace.SpanContext, error) {
+ switch v := carrier.(type) {
+ case TextMapReader:
+ return p.extractTextMap(v)
+ default:
+ return nil, ErrInvalidCarrier
+ }
+}
+
+func (p *propagator) extractTextMap(reader TextMapReader) (ddtrace.SpanContext, error) {
+ var ctx spanContext
+ err := reader.ForeachKey(func(k, v string) error {
+ var err error
+ key := strings.ToLower(k)
+ switch key {
+ case p.cfg.TraceHeader:
+ ctx.traceID, err = parseUint64(v)
+ if err != nil {
+ return ErrSpanContextCorrupted
+ }
+ case p.cfg.ParentHeader:
+ ctx.spanID, err = parseUint64(v)
+ if err != nil {
+ return ErrSpanContextCorrupted
+ }
+ case p.cfg.PriorityHeader:
+ ctx.priority, err = strconv.Atoi(v)
+ if err != nil {
+ return ErrSpanContextCorrupted
+ }
+ ctx.hasPriority = true
+ default:
+ if strings.HasPrefix(key, p.cfg.BaggagePrefix) {
+ ctx.setBaggageItem(strings.TrimPrefix(key, p.cfg.BaggagePrefix), v)
+ }
+ }
+ return nil
+ })
+ if err != nil {
+ return nil, err
+ }
+ if ctx.traceID == 0 || ctx.spanID == 0 {
+ return nil, ErrSpanContextNotFound
+ }
+ return &ctx, nil
+}
diff --git a/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/time.go b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/time.go
new file mode 100644
index 000000000..459161c71
--- /dev/null
+++ b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/time.go
@@ -0,0 +1,10 @@
+// +build !windows
+
+package tracer
+
+import "time"
+
+// now returns current UTC time in nanos.
+func now() int64 {
+ return time.Now().UTC().UnixNano()
+}
diff --git a/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/time_windows.go b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/time_windows.go
new file mode 100644
index 000000000..f9c56aeb7
--- /dev/null
+++ b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/time_windows.go
@@ -0,0 +1,35 @@
+package tracer
+
+import (
+ "log"
+ "time"
+
+ "golang.org/x/sys/windows"
+)
+
+// This method is more precise than the go1.8 time.Now on Windows
+// See https://msdn.microsoft.com/en-us/library/windows/desktop/hh706895(v=vs.85).aspx
+// It is however ~10x slower and requires Windows 8+.
+func highPrecisionNow() int64 {
+ var ft windows.Filetime
+ windows.GetSystemTimePreciseAsFileTime(&ft)
+ return ft.Nanoseconds()
+}
+
+func lowPrecisionNow() int64 {
+ return time.Now().UTC().UnixNano()
+}
+
+var now func() int64
+
+// If GetSystemTimePreciseAsFileTime is not available we default to the less
+// precise implementation based on time.Now()
+func init() {
+ if err := windows.LoadGetSystemTimePreciseAsFileTime(); err != nil {
+ log.Printf("Unable to load high precison timer, defaulting to time.Now()")
+ now = lowPrecisionNow
+ } else {
+ log.Printf("Using high precision timer")
+ now = highPrecisionNow
+ }
+}
diff --git a/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/tracer.go b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/tracer.go
new file mode 100644
index 000000000..d5f16f0bd
--- /dev/null
+++ b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/tracer.go
@@ -0,0 +1,380 @@
+package tracer
+
+import (
+ "errors"
+ "log"
+ "os"
+ "strconv"
+ "time"
+
+ "gopkg.in/DataDog/dd-trace-go.v1/ddtrace"
+ "gopkg.in/DataDog/dd-trace-go.v1/ddtrace/ext"
+ "gopkg.in/DataDog/dd-trace-go.v1/ddtrace/internal"
+)
+
+var _ ddtrace.Tracer = (*tracer)(nil)
+
+// tracer creates, buffers and submits Spans which are used to time blocks of
+// computation. They are accumulated and streamed into an internal payload,
+// which is flushed to the agent whenever its size exceeds a specific threshold
+// or when a certain interval of time has passed, whichever happens first.
+//
+// tracer operates based on a worker loop which responds to various request
+// channels. It additionally holds two buffers which accumulates error and trace
+// queues to be processed by the payload encoder.
+type tracer struct {
+ *config
+ *payload
+
+ flushAllReq chan chan<- struct{}
+ flushTracesReq chan struct{}
+ flushErrorsReq chan struct{}
+ exitReq chan struct{}
+
+ payloadQueue chan []*span
+ errorBuffer chan error
+
+ // stopped is a channel that will be closed when the worker has exited.
+ stopped chan struct{}
+
+ // syncPush is used for testing. When non-nil, it causes pushTrace to become
+ // a synchronous (blocking) operation, meaning that it will only return after
+ // the trace has been fully processed and added onto the payload.
+ syncPush chan struct{}
+}
+
+const (
+ // flushInterval is the interval at which the payload contents will be flushed
+ // to the transport.
+ flushInterval = 2 * time.Second
+
+ // payloadMaxLimit is the maximum payload size allowed and should indicate the
+ // maximum size of the package that the agent can receive.
+ payloadMaxLimit = 9.5 * 1024 * 1024 // 9.5 MB
+
+ // payloadSizeLimit specifies the maximum allowed size of the payload before
+ // it will trigger a flush to the transport.
+ payloadSizeLimit = payloadMaxLimit / 2
+)
+
+// Start starts the tracer with the given set of options. It will stop and replace
+// any running tracer, meaning that calling it several times will result in a restart
+// of the tracer by replacing the current instance with a new one.
+func Start(opts ...StartOption) {
+ if internal.Testing {
+ return // mock tracer active
+ }
+ internal.SetGlobalTracer(newTracer(opts...))
+}
+
+// Stop stops the started tracer. Subsequent calls are valid but become no-op.
+func Stop() {
+ internal.SetGlobalTracer(&internal.NoopTracer{})
+}
+
+// Span is an alias for ddtrace.Span. It is here to allow godoc to group methods returning
+// ddtrace.Span. It is recommended and is considered more correct to refer to this type as
+// ddtrace.Span instead.
+type Span = ddtrace.Span
+
+// StartSpan starts a new span with the given operation name and set of options.
+// If the tracer is not started, calling this function is a no-op.
+func StartSpan(operationName string, opts ...StartSpanOption) Span {
+ return internal.GetGlobalTracer().StartSpan(operationName, opts...)
+}
+
+// Extract extracts a SpanContext from the carrier. The carrier is expected
+// to implement TextMapReader, otherwise an error is returned.
+// If the tracer is not started, calling this function is a no-op.
+func Extract(carrier interface{}) (ddtrace.SpanContext, error) {
+ return internal.GetGlobalTracer().Extract(carrier)
+}
+
+// Inject injects the given SpanContext into the carrier. The carrier is
+// expected to implement TextMapWriter, otherwise an error is returned.
+// If the tracer is not started, calling this function is a no-op.
+func Inject(ctx ddtrace.SpanContext, carrier interface{}) error {
+ return internal.GetGlobalTracer().Inject(ctx, carrier)
+}
+
+const (
+ // payloadQueueSize is the buffer size of the trace channel.
+ payloadQueueSize = 1000
+
+ // errorBufferSize is the buffer size of the error channel.
+ errorBufferSize = 200
+)
+
+func newTracer(opts ...StartOption) *tracer {
+ c := new(config)
+ defaults(c)
+ for _, fn := range opts {
+ fn(c)
+ }
+ if c.transport == nil {
+ c.transport = newTransport(c.agentAddr, c.httpRoundTripper)
+ }
+ if c.propagator == nil {
+ c.propagator = NewPropagator(nil)
+ }
+ t := &tracer{
+ config: c,
+ payload: newPayload(),
+ flushAllReq: make(chan chan<- struct{}),
+ flushTracesReq: make(chan struct{}, 1),
+ flushErrorsReq: make(chan struct{}, 1),
+ exitReq: make(chan struct{}),
+ payloadQueue: make(chan []*span, payloadQueueSize),
+ errorBuffer: make(chan error, errorBufferSize),
+ stopped: make(chan struct{}),
+ }
+
+ go t.worker()
+
+ return t
+}
+
+// worker receives finished traces to be added into the payload, as well
+// as periodically flushes traces to the transport.
+func (t *tracer) worker() {
+ defer close(t.stopped)
+ ticker := time.NewTicker(flushInterval)
+ defer ticker.Stop()
+
+ for {
+ select {
+ case trace := <-t.payloadQueue:
+ t.pushPayload(trace)
+
+ case <-ticker.C:
+ t.flush()
+
+ case done := <-t.flushAllReq:
+ t.flush()
+ done <- struct{}{}
+
+ case <-t.flushTracesReq:
+ t.flushTraces()
+
+ case <-t.flushErrorsReq:
+ t.flushErrors()
+
+ case <-t.exitReq:
+ t.flush()
+ return
+ }
+ }
+}
+
+func (t *tracer) pushTrace(trace []*span) {
+ select {
+ case <-t.stopped:
+ return
+ default:
+ }
+ select {
+ case t.payloadQueue <- trace:
+ default:
+ t.pushError(&dataLossError{
+ context: errors.New("payload queue full, dropping trace"),
+ count: len(trace),
+ })
+ }
+ if t.syncPush != nil {
+ // only in tests
+ <-t.syncPush
+ }
+}
+
+func (t *tracer) pushError(err error) {
+ select {
+ case <-t.stopped:
+ return
+ default:
+ }
+ if len(t.errorBuffer) >= cap(t.errorBuffer)/2 { // starts being full, anticipate, try and flush soon
+ select {
+ case t.flushErrorsReq <- struct{}{}:
+ default: // a flush was already requested, skip
+ }
+ }
+ select {
+ case t.errorBuffer <- err:
+ default:
+ // OK, if we get this, our error error buffer is full,
+ // we can assume it is filled with meaningful messages which
+ // are going to be logged and hopefully read, nothing better
+ // we can do, blocking would make things worse.
+ }
+}
+
+// StartSpan creates, starts, and returns a new Span with the given `operationName`.
+func (t *tracer) StartSpan(operationName string, options ...ddtrace.StartSpanOption) ddtrace.Span {
+ var opts ddtrace.StartSpanConfig
+ for _, fn := range options {
+ fn(&opts)
+ }
+ var startTime int64
+ if opts.StartTime.IsZero() {
+ startTime = now()
+ } else {
+ startTime = opts.StartTime.UnixNano()
+ }
+ var context *spanContext
+ if opts.Parent != nil {
+ if ctx, ok := opts.Parent.(*spanContext); ok {
+ context = ctx
+ }
+ }
+ id := random.Uint64()
+ // span defaults
+ span := &span{
+ Name: operationName,
+ Service: t.config.serviceName,
+ Resource: operationName,
+ Meta: map[string]string{},
+ Metrics: map[string]float64{},
+ SpanID: id,
+ TraceID: id,
+ ParentID: 0,
+ Start: startTime,
+ }
+ if context != nil {
+ // this is a child span
+ span.TraceID = context.traceID
+ span.ParentID = context.spanID
+ if context.hasSamplingPriority() {
+ span.Metrics[samplingPriorityKey] = float64(context.samplingPriority())
+ }
+ if context.span != nil {
+ // it has a local parent, inherit the service
+ context.span.RLock()
+ span.Service = context.span.Service
+ context.span.RUnlock()
+ }
+ }
+ span.context = newSpanContext(span, context)
+ if context == nil || context.span == nil {
+ // this is either a root span or it has a remote parent, we should add the PID.
+ span.SetTag(ext.Pid, strconv.Itoa(os.Getpid()))
+ }
+ // add tags from options
+ for k, v := range opts.Tags {
+ span.SetTag(k, v)
+ }
+ // add global tags
+ for k, v := range t.config.globalTags {
+ span.SetTag(k, v)
+ }
+ if context == nil {
+ // this is a brand new trace, sample it
+ t.sample(span)
+ }
+ return span
+}
+
+// Stop stops the tracer.
+func (t *tracer) Stop() {
+ select {
+ case <-t.stopped:
+ return
+ default:
+ t.exitReq <- struct{}{}
+ <-t.stopped
+ }
+}
+
+// Inject uses the configured or default TextMap Propagator.
+func (t *tracer) Inject(ctx ddtrace.SpanContext, carrier interface{}) error {
+ return t.config.propagator.Inject(ctx, carrier)
+}
+
+// Extract uses the configured or default TextMap Propagator.
+func (t *tracer) Extract(carrier interface{}) (ddtrace.SpanContext, error) {
+ return t.config.propagator.Extract(carrier)
+}
+
+// flushTraces will push any currently buffered traces to the server.
+func (t *tracer) flushTraces() {
+ if t.payload.itemCount() == 0 {
+ return
+ }
+ size, count := t.payload.size(), t.payload.itemCount()
+ if t.config.debug {
+ log.Printf("Sending payload: size: %d traces: %d\n", size, count)
+ }
+ rc, err := t.config.transport.send(t.payload)
+ if err != nil {
+ t.pushError(&dataLossError{context: err, count: count})
+ }
+ if err == nil && t.config.prioritySampling != nil {
+ t.config.prioritySampling.readRatesJSON(rc) // TODO: handle error?
+ }
+ t.payload.reset()
+}
+
+// flushErrors will process log messages that were queued
+func (t *tracer) flushErrors() {
+ logErrors(t.errorBuffer)
+}
+
+func (t *tracer) flush() {
+ t.flushTraces()
+ t.flushErrors()
+}
+
+// forceFlush forces a flush of data (traces and services) to the agent.
+// Flushes are done by a background task on a regular basis, so you never
+// need to call this manually, mostly useful for testing and debugging.
+func (t *tracer) forceFlush() {
+ done := make(chan struct{})
+ t.flushAllReq <- done
+ <-done
+}
+
+// pushPayload pushes the trace onto the payload. If the payload becomes
+// larger than the threshold as a result, it sends a flush request.
+func (t *tracer) pushPayload(trace []*span) {
+ if err := t.payload.push(trace); err != nil {
+ t.pushError(&traceEncodingError{context: err})
+ }
+ if t.payload.size() > payloadSizeLimit {
+ // getting large
+ select {
+ case t.flushTracesReq <- struct{}{}:
+ default:
+ // flush already queued
+ }
+ }
+ if t.syncPush != nil {
+ // only in tests
+ t.syncPush <- struct{}{}
+ }
+}
+
+// sampleRateMetricKey is the metric key holding the applied sample rate. Has to be the same as the Agent.
+const sampleRateMetricKey = "_sample_rate"
+
+// Sample samples a span with the internal sampler.
+func (t *tracer) sample(span *span) {
+ sampler := t.config.sampler
+ sampled := sampler.Sample(span)
+ span.context.sampled = sampled
+ if !sampled {
+ return
+ }
+ if rs, ok := sampler.(RateSampler); ok && rs.Rate() < 1 {
+ // the span was sampled using a rate sampler which wasn't all permissive,
+ // so we make note of the sampling rate.
+ span.Lock()
+ defer span.Unlock()
+ if span.finished {
+ // we don't touch finished span as they might be flushing
+ return
+ }
+ span.Metrics[sampleRateMetricKey] = rs.Rate()
+ }
+ if t.config.prioritySampling != nil {
+ t.config.prioritySampling.apply(span)
+ }
+}
diff --git a/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/transport.go b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/transport.go
new file mode 100644
index 000000000..9a8e70cfd
--- /dev/null
+++ b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/transport.go
@@ -0,0 +1,152 @@
+package tracer
+
+import (
+ "fmt"
+ "io"
+ "net"
+ "net/http"
+ "os"
+ "runtime"
+ "strconv"
+ "strings"
+ "time"
+)
+
+var (
+ // TODO(gbbr): find a more effective way to keep this up to date,
+ // e.g. via `go generate`
+ tracerVersion = "v1.7.0"
+
+ // We copy the transport to avoid using the default one, as it might be
+ // augmented with tracing and we don't want these calls to be recorded.
+ // See https://golang.org/pkg/net/http/#DefaultTransport .
+ defaultRoundTripper = &http.Transport{
+ Proxy: http.ProxyFromEnvironment,
+ DialContext: (&net.Dialer{
+ Timeout: 30 * time.Second,
+ KeepAlive: 30 * time.Second,
+ DualStack: true,
+ }).DialContext,
+ MaxIdleConns: 100,
+ IdleConnTimeout: 90 * time.Second,
+ TLSHandshakeTimeout: 10 * time.Second,
+ ExpectContinueTimeout: 1 * time.Second,
+ }
+)
+
+const (
+ defaultHostname = "localhost"
+ defaultPort = "8126"
+ defaultAddress = defaultHostname + ":" + defaultPort
+ defaultHTTPTimeout = time.Second // defines the current timeout before giving up with the send process
+ traceCountHeader = "X-Datadog-Trace-Count" // header containing the number of traces in the payload
+)
+
+// transport is an interface for span submission to the agent.
+type transport interface {
+ // send sends the payload p to the agent using the transport set up.
+ // It returns a non-nil response body when no error occurred.
+ send(p *payload) (body io.ReadCloser, err error)
+}
+
+// newTransport returns a new Transport implementation that sends traces to a
+// trace agent running on the given hostname and port, using a given
+// http.RoundTripper. If the zero values for hostname and port are provided,
+// the default values will be used ("localhost" for hostname, and "8126" for
+// port). If roundTripper is nil, a default is used.
+//
+// In general, using this method is only necessary if you have a trace agent
+// running on a non-default port, if it's located on another machine, or when
+// otherwise needing to customize the transport layer, for instance when using
+// a unix domain socket.
+func newTransport(addr string, roundTripper http.RoundTripper) transport {
+ if roundTripper == nil {
+ roundTripper = defaultRoundTripper
+ }
+ return newHTTPTransport(addr, roundTripper)
+}
+
+// newDefaultTransport return a default transport for this tracing client
+func newDefaultTransport() transport {
+ return newHTTPTransport(defaultAddress, defaultRoundTripper)
+}
+
+type httpTransport struct {
+ traceURL string // the delivery URL for traces
+ client *http.Client // the HTTP client used in the POST
+ headers map[string]string // the Transport headers
+}
+
+// newHTTPTransport returns an httpTransport for the given endpoint
+func newHTTPTransport(addr string, roundTripper http.RoundTripper) *httpTransport {
+ // initialize the default EncoderPool with Encoder headers
+ defaultHeaders := map[string]string{
+ "Datadog-Meta-Lang": "go",
+ "Datadog-Meta-Lang-Version": strings.TrimPrefix(runtime.Version(), "go"),
+ "Datadog-Meta-Lang-Interpreter": runtime.Compiler + "-" + runtime.GOARCH + "-" + runtime.GOOS,
+ "Datadog-Meta-Tracer-Version": tracerVersion,
+ "Content-Type": "application/msgpack",
+ }
+ return &httpTransport{
+ traceURL: fmt.Sprintf("http://%s/v0.4/traces", resolveAddr(addr)),
+ client: &http.Client{
+ Transport: roundTripper,
+ Timeout: defaultHTTPTimeout,
+ },
+ headers: defaultHeaders,
+ }
+}
+
+func (t *httpTransport) send(p *payload) (body io.ReadCloser, err error) {
+ // prepare the client and send the payload
+ req, err := http.NewRequest("POST", t.traceURL, p)
+ if err != nil {
+ return nil, fmt.Errorf("cannot create http request: %v", err)
+ }
+ for header, value := range t.headers {
+ req.Header.Set(header, value)
+ }
+ req.Header.Set(traceCountHeader, strconv.Itoa(p.itemCount()))
+ req.Header.Set("Content-Length", strconv.Itoa(p.size()))
+ response, err := t.client.Do(req)
+ if err != nil {
+ return nil, err
+ }
+ if code := response.StatusCode; code >= 400 {
+ // error, check the body for context information and
+ // return a nice error.
+ msg := make([]byte, 1000)
+ n, _ := response.Body.Read(msg)
+ response.Body.Close()
+ txt := http.StatusText(code)
+ if n > 0 {
+ return nil, fmt.Errorf("%s (Status: %s)", msg[:n], txt)
+ }
+ return nil, fmt.Errorf("%s", txt)
+ }
+ return response.Body, nil
+}
+
+// resolveAddr resolves the given agent address and fills in any missing host
+// and port using the defaults. Some environment variable settings will
+// take precedence over configuration.
+func resolveAddr(addr string) string {
+ host, port, err := net.SplitHostPort(addr)
+ if err != nil {
+ // no port in addr
+ host = addr
+ }
+ if host == "" {
+ host = defaultHostname
+ }
+ if port == "" {
+ port = defaultPort
+ }
+ if v := os.Getenv("DD_AGENT_HOST"); v != "" {
+ host = v
+ }
+ if v := os.Getenv("DD_TRACE_AGENT_PORT"); v != "" {
+ port = v
+ }
+ return fmt.Sprintf("%s:%s", host, port)
+}
diff --git a/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/util.go b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/util.go
new file mode 100644
index 000000000..c21297783
--- /dev/null
+++ b/vendor/gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer/util.go
@@ -0,0 +1,50 @@
+package tracer
+
+import (
+ "strconv"
+ "strings"
+)
+
+// toFloat64 attempts to convert value into a float64. If it succeeds it returns
+// the value and true, otherwise 0 and false.
+func toFloat64(value interface{}) (f float64, ok bool) {
+ switch i := value.(type) {
+ case byte:
+ return float64(i), true
+ case float32:
+ return float64(i), true
+ case float64:
+ return i, true
+ case int:
+ return float64(i), true
+ case int16:
+ return float64(i), true
+ case int32:
+ return float64(i), true
+ case int64:
+ return float64(i), true
+ case uint:
+ return float64(i), true
+ case uint16:
+ return float64(i), true
+ case uint32:
+ return float64(i), true
+ case uint64:
+ return float64(i), true
+ default:
+ return 0, false
+ }
+}
+
+// parseUint64 parses a uint64 from either an unsigned 64 bit base-10 string
+// or a signed 64 bit base-10 string representing an unsigned integer
+func parseUint64(str string) (uint64, error) {
+ if strings.HasPrefix(str, "-") {
+ id, err := strconv.ParseInt(str, 10, 64)
+ if err != nil {
+ return 0, err
+ }
+ return uint64(id), nil
+ }
+ return strconv.ParseUint(str, 10, 64)
+}
diff --git a/vendor/vendor.json b/vendor/vendor.json
index 7f09cf4f2..32c8376a3 100644
--- a/vendor/vendor.json
+++ b/vendor/vendor.json
@@ -149,6 +149,12 @@
"revisionTime": "2018-11-12T10:25:10Z"
},
{
+ "checksumSHA1": "40Idbv0LvYI4eMdoV3UCFH0zvjA=",
+ "path": "github.com/grpc-ecosystem/go-grpc-middleware/tracing/opentracing",
+ "revision": "3304cc8863525cd0b328fbfd5bf745bbd38e7106",
+ "revisionTime": "2018-11-12T10:25:10Z"
+ },
+ {
"checksumSHA1": "L5z1C445GhhQmDKSisTFv754LdU=",
"path": "github.com/grpc-ecosystem/go-grpc-middleware/util/metautils",
"revision": "3304cc8863525cd0b328fbfd5bf745bbd38e7106",
@@ -179,6 +185,42 @@
"versionExact": "v1.0.1"
},
{
+ "checksumSHA1": "++h3LjgqASQ5dGLM2WOZmwYp+mU=",
+ "path": "github.com/lightstep/lightstep-tracer-go",
+ "revision": "c9cafc033badd91d4e27900874429fc30a5ffdc2",
+ "revisionTime": "2018-11-01T20:03:43Z"
+ },
+ {
+ "checksumSHA1": "+yBmXMLtl+DTjHc7TnPCLAgJVog=",
+ "path": "github.com/lightstep/lightstep-tracer-go/collectorpb",
+ "revision": "c9cafc033badd91d4e27900874429fc30a5ffdc2",
+ "revisionTime": "2018-11-01T20:03:43Z"
+ },
+ {
+ "checksumSHA1": "RQ3kvBKcSz0kxmQ1p/0taghnjIU=",
+ "path": "github.com/lightstep/lightstep-tracer-go/lightstep/rand",
+ "revision": "c9cafc033badd91d4e27900874429fc30a5ffdc2",
+ "revisionTime": "2018-11-01T20:03:43Z"
+ },
+ {
+ "checksumSHA1": "BOLaaHQ9edFbBXKKJebv2kZHCNQ=",
+ "path": "github.com/lightstep/lightstep-tracer-go/lightstep_thrift",
+ "revision": "c9cafc033badd91d4e27900874429fc30a5ffdc2",
+ "revisionTime": "2018-11-01T20:03:43Z"
+ },
+ {
+ "checksumSHA1": "h8z4oTPYik6oM5Cr0GcnovYVmzA=",
+ "path": "github.com/lightstep/lightstep-tracer-go/lightsteppb",
+ "revision": "c9cafc033badd91d4e27900874429fc30a5ffdc2",
+ "revisionTime": "2018-11-01T20:03:43Z"
+ },
+ {
+ "checksumSHA1": "rUIl0W2zua6pRZvMwOom7EzJCE4=",
+ "path": "github.com/lightstep/thrift/lib/go/thrift",
+ "revision": "de6c3c01b88c1fc8ae76cec4a30f0441ef55a4a4",
+ "revisionTime": "2018-10-23T18:28:18Z"
+ },
+ {
"checksumSHA1": "bKMZjd2wPw13VwoE7mBeSv5djFA=",
"path": "github.com/matttproud/golang_protobuf_extensions/pbutil",
"revision": "c12348ce28de40eed0136aa2b644d0ee0650e56c",
@@ -187,6 +229,30 @@
"versionExact": "v1.0.1"
},
{
+ "checksumSHA1": "jqEjDv//suCrQUg8iOGI7oxwfRU=",
+ "path": "github.com/opentracing/opentracing-go",
+ "revision": "be550b025b433cdfa2f11efb962afa2ea3c4d967",
+ "revisionTime": "2018-10-12T22:12:31Z"
+ },
+ {
+ "checksumSHA1": "uhDxBvLEqRAMZKgpTZ8MFuLIIM8=",
+ "path": "github.com/opentracing/opentracing-go/ext",
+ "revision": "be550b025b433cdfa2f11efb962afa2ea3c4d967",
+ "revisionTime": "2018-10-12T22:12:31Z"
+ },
+ {
+ "checksumSHA1": "tnkdNJbJxNKuPZMWapP1xhKIIGw=",
+ "path": "github.com/opentracing/opentracing-go/log",
+ "revision": "be550b025b433cdfa2f11efb962afa2ea3c4d967",
+ "revisionTime": "2018-10-12T22:12:31Z"
+ },
+ {
+ "checksumSHA1": "8U5pEHFpXd1/Klgp+C/a6TqWoh8=",
+ "path": "github.com/philhofer/fwd",
+ "revision": "bb6d471dc95d4fe11e432687f8b70ff496cf3136",
+ "revisionTime": "2017-09-05T21:21:22Z"
+ },
+ {
"checksumSHA1": "DTy0iJ2w5C+FDsN9EnzfhNmvS+o=",
"path": "github.com/pkg/errors",
"revision": "059132a15dd08d6704c67711dae0cf35ab991756",
@@ -315,6 +381,120 @@
"versionExact": "v1.2.2"
},
{
+ "checksumSHA1": "DAZUaXNahejywdwKXvMohfyHKNc=",
+ "path": "github.com/tinylib/msgp/msgp",
+ "revision": "af6442a0fcf6e2a1b824f70dd0c734f01e817751",
+ "revisionTime": "2018-11-28T01:18:08Z"
+ },
+ {
+ "checksumSHA1": "9JF0HfwNlRf1MVAqpAUGrLukpZw=",
+ "path": "github.com/uber/jaeger-client-go",
+ "revision": "c58709fe19d793cdd40ad8bfa6e645a40a2eccf8",
+ "revisionTime": "2018-11-07T14:24:01Z"
+ },
+ {
+ "checksumSHA1": "n0IcgkLEOYuFPP+S8+VQuGZY6I0=",
+ "path": "github.com/uber/jaeger-client-go/config",
+ "revision": "c58709fe19d793cdd40ad8bfa6e645a40a2eccf8",
+ "revisionTime": "2018-11-07T14:24:01Z"
+ },
+ {
+ "checksumSHA1": "KM5UXTWkHULmw0dDRNuk8ogWyGs=",
+ "path": "github.com/uber/jaeger-client-go/internal/baggage",
+ "revision": "c58709fe19d793cdd40ad8bfa6e645a40a2eccf8",
+ "revisionTime": "2018-11-07T14:24:01Z"
+ },
+ {
+ "checksumSHA1": "tZqlcHV1XoLdZp9jfnydzsZAvYo=",
+ "path": "github.com/uber/jaeger-client-go/internal/baggage/remote",
+ "revision": "c58709fe19d793cdd40ad8bfa6e645a40a2eccf8",
+ "revisionTime": "2018-11-07T14:24:01Z"
+ },
+ {
+ "checksumSHA1": "QB0L0GrzyMGQp6ivkkxp7a1DPsE=",
+ "path": "github.com/uber/jaeger-client-go/internal/spanlog",
+ "revision": "c58709fe19d793cdd40ad8bfa6e645a40a2eccf8",
+ "revisionTime": "2018-11-07T14:24:01Z"
+ },
+ {
+ "checksumSHA1": "79HRO/+ekkpwqDB/OMiW+AHJtlE=",
+ "path": "github.com/uber/jaeger-client-go/internal/throttler",
+ "revision": "c58709fe19d793cdd40ad8bfa6e645a40a2eccf8",
+ "revisionTime": "2018-11-07T14:24:01Z"
+ },
+ {
+ "checksumSHA1": "OVQDWFtFMs+NODe0F/S5kYViQco=",
+ "path": "github.com/uber/jaeger-client-go/internal/throttler/remote",
+ "revision": "c58709fe19d793cdd40ad8bfa6e645a40a2eccf8",
+ "revisionTime": "2018-11-07T14:24:01Z"
+ },
+ {
+ "checksumSHA1": "tMP/vxbHwNAbOEaUhic5/meKfac=",
+ "path": "github.com/uber/jaeger-client-go/log",
+ "revision": "c58709fe19d793cdd40ad8bfa6e645a40a2eccf8",
+ "revisionTime": "2018-11-07T14:24:01Z"
+ },
+ {
+ "checksumSHA1": "j4WrA/B2SJCqHxttCQ+TYbmtQqE=",
+ "path": "github.com/uber/jaeger-client-go/rpcmetrics",
+ "revision": "c58709fe19d793cdd40ad8bfa6e645a40a2eccf8",
+ "revisionTime": "2018-11-07T14:24:01Z"
+ },
+ {
+ "checksumSHA1": "+ffspyTBQLql2UiU6muvfWR/m1o=",
+ "path": "github.com/uber/jaeger-client-go/thrift",
+ "revision": "c58709fe19d793cdd40ad8bfa6e645a40a2eccf8",
+ "revisionTime": "2018-11-07T14:24:01Z"
+ },
+ {
+ "checksumSHA1": "fMIQ4sJFCkqFYhXvvLKIlofqxvY=",
+ "path": "github.com/uber/jaeger-client-go/thrift-gen/agent",
+ "revision": "c58709fe19d793cdd40ad8bfa6e645a40a2eccf8",
+ "revisionTime": "2018-11-07T14:24:01Z"
+ },
+ {
+ "checksumSHA1": "fRR2p+JAp7paApf32YuQuWU7yzY=",
+ "path": "github.com/uber/jaeger-client-go/thrift-gen/baggage",
+ "revision": "c58709fe19d793cdd40ad8bfa6e645a40a2eccf8",
+ "revisionTime": "2018-11-07T14:24:01Z"
+ },
+ {
+ "checksumSHA1": "JZkMEOmiOFFEuGCsDOVLK5RzvMM=",
+ "path": "github.com/uber/jaeger-client-go/thrift-gen/jaeger",
+ "revision": "c58709fe19d793cdd40ad8bfa6e645a40a2eccf8",
+ "revisionTime": "2018-11-07T14:24:01Z"
+ },
+ {
+ "checksumSHA1": "0teQUhTqTE1fLs+vbnTTzWOqdEQ=",
+ "path": "github.com/uber/jaeger-client-go/thrift-gen/sampling",
+ "revision": "c58709fe19d793cdd40ad8bfa6e645a40a2eccf8",
+ "revisionTime": "2018-11-07T14:24:01Z"
+ },
+ {
+ "checksumSHA1": "Nx5witfz05BSO2YlFzh2Gno6bA0=",
+ "path": "github.com/uber/jaeger-client-go/thrift-gen/zipkincore",
+ "revision": "c58709fe19d793cdd40ad8bfa6e645a40a2eccf8",
+ "revisionTime": "2018-11-07T14:24:01Z"
+ },
+ {
+ "checksumSHA1": "UlW+AcyeItWM0x1W4vT9hbUiOJs=",
+ "path": "github.com/uber/jaeger-client-go/transport",
+ "revision": "c58709fe19d793cdd40ad8bfa6e645a40a2eccf8",
+ "revisionTime": "2018-11-07T14:24:01Z"
+ },
+ {
+ "checksumSHA1": "DKwwIk9vq53IKO7RKccat9cnqeo=",
+ "path": "github.com/uber/jaeger-client-go/utils",
+ "revision": "c58709fe19d793cdd40ad8bfa6e645a40a2eccf8",
+ "revisionTime": "2018-11-07T14:24:01Z"
+ },
+ {
+ "checksumSHA1": "gVpUsKwkIZNZfdZXoldq8WPWA3c=",
+ "path": "github.com/uber/jaeger-lib/metrics",
+ "revision": "1fc5c315e03c871d98a3df762234414d185115d7",
+ "revisionTime": "2018-11-02T16:30:54Z"
+ },
+ {
"checksumSHA1": "VpLdojyLYx9d/bwnqFkEy12sNd8=",
"path": "gitlab.com/gitlab-org/gitaly-proto/go/gitalypb",
"revision": "20e398e887e239ba4ddaa44cf075e99841e43f8a",
@@ -323,18 +503,66 @@
"versionExact": "v1.5.0"
},
{
- "checksumSHA1": "S9x46Eq79I1EkoXI8woeIU6w/wY=",
+ "checksumSHA1": "R6fNN36q3UydLODupK0vdx9h/CY=",
+ "path": "gitlab.com/gitlab-org/labkit/correlation",
+ "revision": "2a3e1f5415a890402696dcbb2c31b5a79c17b579",
+ "revisionTime": "2019-01-08T10:46:58Z",
+ "version": "master",
+ "versionExact": "master"
+ },
+ {
+ "checksumSHA1": "R6fNN36q3UydLODupK0vdx9h/CY=",
"path": "gitlab.com/gitlab-org/labkit/correlation",
- "revision": "fb2eeb11fc358f8f538692d1c0f6e57d7f268691",
- "revisionTime": "2018-11-21T15:01:09Z",
+ "revision": "9c613f6d8258a1b55701079bf9b358147aea139e",
+ "revisionTime": "2018-12-20T16:08:28Z",
+ "version": "=d-tracing",
+ "versionExact": "d-tracing"
+ },
+ {
+ "checksumSHA1": "UFBFulprWZHuL9GHhjCKoHXm+Ww=",
+ "path": "gitlab.com/gitlab-org/labkit/correlation/grpc",
+ "revision": "2a3e1f5415a890402696dcbb2c31b5a79c17b579",
+ "revisionTime": "2019-01-08T10:46:58Z",
"version": "master",
"versionExact": "master"
},
{
"checksumSHA1": "UFBFulprWZHuL9GHhjCKoHXm+Ww=",
"path": "gitlab.com/gitlab-org/labkit/correlation/grpc",
- "revision": "fb2eeb11fc358f8f538692d1c0f6e57d7f268691",
- "revisionTime": "2018-11-21T15:01:09Z",
+ "revision": "3a481e4f5d6cdd19bf9fbbc48a2fe50387b7ae5f",
+ "revisionTime": "2018-12-13T12:30:12Z",
+ "version": "=d-tracing",
+ "versionExact": "d-tracing"
+ },
+ {
+ "checksumSHA1": "JAe9JIwWcJvTUxCbdOPAZxaXIz8=",
+ "path": "gitlab.com/gitlab-org/labkit/tracing",
+ "revision": "2a3e1f5415a890402696dcbb2c31b5a79c17b579",
+ "revisionTime": "2019-01-08T10:46:58Z",
+ "version": "master",
+ "versionExact": "master"
+ },
+ {
+ "checksumSHA1": "uIvjqXAsMQK/Y5FgWRaGydYGbYs=",
+ "path": "gitlab.com/gitlab-org/labkit/tracing/connstr",
+ "revision": "2a3e1f5415a890402696dcbb2c31b5a79c17b579",
+ "revisionTime": "2019-01-08T10:46:58Z",
+ "version": "master",
+ "versionExact": "master"
+ },
+ {
+ "checksumSHA1": "IE38In/zPKpmKqvWAAThyaufQak=",
+ "path": "gitlab.com/gitlab-org/labkit/tracing/grpc",
+ "revision": "2a3e1f5415a890402696dcbb2c31b5a79c17b579",
+ "revisionTime": "2019-01-08T10:46:58Z",
+ "version": "master",
+ "versionExact": "master"
+ },
+ {
+ "checksumSHA1": "hB59Es/WTWfBPLSAheQaRyHGSXA=",
+ "path": "gitlab.com/gitlab-org/labkit/tracing/impl",
+ "revision": "2a3e1f5415a890402696dcbb2c31b5a79c17b579",
+ "revisionTime": "2019-01-08T10:46:58Z",
"version": "master",
"versionExact": "master"
},
@@ -429,6 +657,12 @@
"revisionTime": "2018-10-29T18:00:05Z"
},
{
+ "checksumSHA1": "YNqziavfZHurG6wrwR5Uf9SnI4s=",
+ "path": "google.golang.org/genproto/googleapis/api/annotations",
+ "revision": "bd91e49a0898e27abb88c339b432fa53d7497ac0",
+ "revisionTime": "2018-12-02T18:38:23Z"
+ },
+ {
"checksumSHA1": "MgYFT27I9gfAtSVBpGVqkCYOj3U=",
"path": "google.golang.org/genproto/googleapis/rpc/status",
"revision": "b69ba1387ce2108ac9bc8e8e5e5a46e7d5c72313",
@@ -707,6 +941,36 @@
"revisionTime": "2018-10-23T17:37:47Z",
"version": "v1.16.0",
"versionExact": "v1.16.0"
+ },
+ {
+ "checksumSHA1": "GE96+o57Lj5bo7eUP/rPHAJvhOY=",
+ "path": "gopkg.in/DataDog/dd-trace-go.v1/ddtrace",
+ "revision": "5a8139286014811d2bccd5ef67ec4844ea0998a7",
+ "revisionTime": "2018-12-07T15:03:43Z"
+ },
+ {
+ "checksumSHA1": "o/e29hKUQ2p/+0gAvCBk6Fri2og=",
+ "path": "gopkg.in/DataDog/dd-trace-go.v1/ddtrace/ext",
+ "revision": "5a8139286014811d2bccd5ef67ec4844ea0998a7",
+ "revisionTime": "2018-12-07T15:03:43Z"
+ },
+ {
+ "checksumSHA1": "Y+OLwoHr6B/kbFMbI8IRui26wZ0=",
+ "path": "gopkg.in/DataDog/dd-trace-go.v1/ddtrace/internal",
+ "revision": "5a8139286014811d2bccd5ef67ec4844ea0998a7",
+ "revisionTime": "2018-12-07T15:03:43Z"
+ },
+ {
+ "checksumSHA1": "5eLUeoF0F5+BYLgztcwUCg/T3dc=",
+ "path": "gopkg.in/DataDog/dd-trace-go.v1/ddtrace/opentracer",
+ "revision": "5a8139286014811d2bccd5ef67ec4844ea0998a7",
+ "revisionTime": "2018-12-07T15:03:43Z"
+ },
+ {
+ "checksumSHA1": "IUL2h4UqM7KmRzHSWPmn/AIit+o=",
+ "path": "gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer",
+ "revision": "5a8139286014811d2bccd5ef67ec4844ea0998a7",
+ "revisionTime": "2018-12-07T15:03:43Z"
}
],
"rootPath": "gitlab.com/gitlab-org/gitaly"