| 1 | // Copyright 2019 The Go Authors. All rights reserved. |
|---|---|
| 2 | // Use of this source code is governed by a BSD-style |
| 3 | // license that can be found in the LICENSE file. |
| 4 | |
| 5 | package ocagent_test |
| 6 | |
| 7 | import ( |
| 8 | "context" |
| 9 | "errors" |
| 10 | "testing" |
| 11 | |
| 12 | "golang.org/x/tools/internal/event" |
| 13 | ) |
| 14 | |
| 15 | func TestTrace(t *testing.T) { |
| 16 | exporter := registerExporter() |
| 17 | const prefix = testNodeStr + ` |
| 18 | "spans":[{ |
| 19 | "trace_id":"AAAAAAAAAAAAAAAAAAAAAA==", |
| 20 | "span_id":"AAAAAAAAAAA=", |
| 21 | "parent_span_id":"AAAAAAAAAAA=", |
| 22 | "name":{"value":"event span"}, |
| 23 | "start_time":"1970-01-01T00:00:30Z", |
| 24 | "end_time":"1970-01-01T00:00:50Z", |
| 25 | "time_events":{ |
| 26 | ` |
| 27 | const suffix = ` |
| 28 | }, |
| 29 | "same_process_as_parent_span":true |
| 30 | }] |
| 31 | }` |
| 32 | |
| 33 | tests := []struct { |
| 34 | name string |
| 35 | run func(ctx context.Context) |
| 36 | want string |
| 37 | }{ |
| 38 | { |
| 39 | name: "no labels", |
| 40 | run: func(ctx context.Context) { |
| 41 | event.Label(ctx) |
| 42 | }, |
| 43 | want: prefix + ` |
| 44 | "timeEvent":[{"time":"1970-01-01T00:00:40Z"}] |
| 45 | ` + suffix, |
| 46 | }, |
| 47 | { |
| 48 | name: "description no error", |
| 49 | run: func(ctx context.Context) { |
| 50 | event.Log(ctx, "cache miss", keyDB.Of("godb")) |
| 51 | }, |
| 52 | want: prefix + `"timeEvent":[{"time":"1970-01-01T00:00:40Z","annotation":{ |
| 53 | "description": { "value": "cache miss" }, |
| 54 | "attributes": { |
| 55 | "attributeMap": { |
| 56 | "db": { "stringValue": { "value": "godb" } } |
| 57 | } |
| 58 | } |
| 59 | }}]` + suffix, |
| 60 | }, |
| 61 | |
| 62 | { |
| 63 | name: "description and error", |
| 64 | run: func(ctx context.Context) { |
| 65 | event.Error(ctx, "cache miss", |
| 66 | errors.New("no network connectivity"), |
| 67 | keyDB.Of("godb"), |
| 68 | ) |
| 69 | }, |
| 70 | want: prefix + `"timeEvent":[{"time":"1970-01-01T00:00:40Z","annotation":{ |
| 71 | "description": { "value": "cache miss" }, |
| 72 | "attributes": { |
| 73 | "attributeMap": { |
| 74 | "db": { "stringValue": { "value": "godb" } }, |
| 75 | "error": { "stringValue": { "value": "no network connectivity" } } |
| 76 | } |
| 77 | } |
| 78 | }}]` + suffix, |
| 79 | }, |
| 80 | { |
| 81 | name: "no description, but error", |
| 82 | run: func(ctx context.Context) { |
| 83 | event.Error(ctx, "", |
| 84 | errors.New("no network connectivity"), |
| 85 | keyDB.Of("godb"), |
| 86 | ) |
| 87 | }, |
| 88 | want: prefix + `"timeEvent":[{"time":"1970-01-01T00:00:40Z","annotation":{ |
| 89 | "description": { "value": "no network connectivity" }, |
| 90 | "attributes": { |
| 91 | "attributeMap": { |
| 92 | "db": { "stringValue": { "value": "godb" } } |
| 93 | } |
| 94 | } |
| 95 | }}]` + suffix, |
| 96 | }, |
| 97 | { |
| 98 | name: "enumerate all attribute types", |
| 99 | run: func(ctx context.Context) { |
| 100 | event.Log(ctx, "cache miss", |
| 101 | key1DB.Of("godb"), |
| 102 | |
| 103 | key2aAge.Of(0.456), // Constant converted into "float64" |
| 104 | key2bTTL.Of(float32(5000)), |
| 105 | key2cExpiryMS.Of(float64(1e3)), |
| 106 | |
| 107 | key3aRetry.Of(false), |
| 108 | key3bStale.Of(true), |
| 109 | |
| 110 | key4aMax.Of(0x7fff), // Constant converted into "int" |
| 111 | key4bOpcode.Of(int8(0x7e)), |
| 112 | key4cBase.Of(int16(1<<9)), |
| 113 | key4eChecksum.Of(int32(0x11f7e294)), |
| 114 | key4fMode.Of(int64(0644)), |
| 115 | |
| 116 | key5aMin.Of(uint(1)), |
| 117 | key5bMix.Of(uint8(44)), |
| 118 | key5cPort.Of(uint16(55678)), |
| 119 | key5dMinHops.Of(uint32(1<<9)), |
| 120 | key5eMaxHops.Of(uint64(0xffffff)), |
| 121 | ) |
| 122 | }, |
| 123 | want: prefix + `"timeEvent":[{"time":"1970-01-01T00:00:40Z","annotation":{ |
| 124 | "description": { "value": "cache miss" }, |
| 125 | "attributes": { |
| 126 | "attributeMap": { |
| 127 | "1_db": { "stringValue": { "value": "godb" } }, |
| 128 | "2a_age": { "doubleValue": 0.456 }, |
| 129 | "2b_ttl": { "doubleValue": 5000 }, |
| 130 | "2c_expiry_ms": { "doubleValue": 1000 }, |
| 131 | "3a_retry": {}, |
| 132 | "3b_stale": { "boolValue": true }, |
| 133 | "4a_max": { "intValue": 32767 }, |
| 134 | "4b_opcode": { "intValue": 126 }, |
| 135 | "4c_base": { "intValue": 512 }, |
| 136 | "4e_checksum": { "intValue": 301458068 }, |
| 137 | "4f_mode": { "intValue": 420 }, |
| 138 | "5a_min": { "intValue": 1 }, |
| 139 | "5b_mix": { "intValue": 44 }, |
| 140 | "5c_port": { "intValue": 55678 }, |
| 141 | "5d_min_hops": { "intValue": 512 }, |
| 142 | "5e_max_hops": { "intValue": 16777215 } |
| 143 | } |
| 144 | } |
| 145 | }}]` + suffix, |
| 146 | }, |
| 147 | } |
| 148 | ctx := context.TODO() |
| 149 | for _, tt := range tests { |
| 150 | t.Run(tt.name, func(t *testing.T) { |
| 151 | ctx, done := event.Start(ctx, "event span") |
| 152 | tt.run(ctx) |
| 153 | done() |
| 154 | got := exporter.Output("/v1/trace") |
| 155 | checkJSON(t, got, []byte(tt.want)) |
| 156 | }) |
| 157 | } |
| 158 | } |
| 159 |
Members