message: minor fixes from another PR review

diff:
@@ -46,10 +46,10 @@ func SetupGlobalTraceProviderAndExporter(ctx context.Context) (sdktrace.SpanExpo
addr := fmt.Sprintf("%s:%d", defaultCollectorHost, defaultCollectorPort)
- // // Every 15 seconds we'll try to connect to opentelemetry collector at
- // // the default location of localhost:4317
- // // When running in production this is a sidecar, and when running
- // // locally this is a locally running opetelemetry-collector.
+ // Every 15 seconds we'll try to connect to opentelemetry collector at
+ // the default location of localhost:4317
+ // When running in production this is a sidecar, and when running
+ // locally this is a locally running opetelemetry-collector.
otlpClient := otlptracegrpc.NewClient(
otlptracegrpc.WithReconnectionPeriod(15*time.Second),
otlptracegrpc.WithEndpoint(addr),
@@ -84,10 +84,10 @@ func newTracerProvider(exporter sdktrace.SpanExporter, resource *resource.Resour
EventCountLimit: 100,
LinkCountLimit: 100,
}),
+
// Batcher is more efficient, switch to it after testing
sdktrace.WithSyncer(exporter),
// sdktrace.WithBatcher(exporter),
- //Have to figure out how I'm going to generate this resource first.
sdktrace.WithResource(resource),
)
otel.SetTracerProvider(tp)
@@ -160,9 +160,9 @@ func MuxServerMiddleware(serviceName string) func(http.Handler) http.Handler {
// Used for setting up tracer provider
func newResource() *resource.Resource {
var appName string
- if os.Getenv("_POD_ID") != "" {
+ if os.Getenv("_APP_NAME") != "" {
appName = os.Getenv("_APP_NAME")
- } else if os.Getenv("POD_ID") != "" {
+ } else if os.Getenv("APP_NAME") != "" {
appName = os.Getenv("APP_NAME")
}
r, _ := resource.Merge(

diff:
@@ -243,7 +243,7 @@ func doNothing(baseTransport http.RoundTripper, spanNameCtxValue interface{}, tp
func determineSampling() (samplingProbability float64, err error) {
// If we're running locally, then turn off sampling. Otherwise sample
- // 1% or whatever TRACING_SAMPLING_PROBABILITY specifies.
+ // 1%% or whatever TRACING_SAMPLING_PROBABILITY specifies.
samplingProbability = 0.01
isLocal := os.Getenv("_IS_LOCAL") == "true"
if isLocal {
@@ -252,7 +252,7 @@ func determineSampling() (samplingProbability float64, err error) {
} else if v := os.Getenv("TRACING_SAMPLING_PROBABILITY"); v != "" {
samplingProbabilityFromEnv, err := strconv.ParseFloat(v, 64)
if err != nil {
- return 0, fmt.Errorf("could not parse '%s' to float", v)
+ return 0, fmt.Errorf("could not parse '%%s' to float", v)
}
samplingProbability = samplingProbabilityFromEnv
}

original_message: minor fixes from another PR review


message: removed errant req.Done

change_type: MODIFY

diff:
@@ -731,7 +731,6 @@ func (c *WagClient) do%sRequest(ctx context.Context, req *http.Request, headers
defer cancel()
req = req.WithContext(ctx)
}
- req.Done=true
resp, err := c.requestDoer.Do(c.client, req)
retCode := 0

license: Apache License 2.0

repo: clever/wag

original_message: removed errant req.Done


message: Include baggage in propagation

diff:
@@ -10,11 +10,13 @@ import (
"time"
"github.com/Clever/kayvee-go/v7/logger"
+ "github.com/davecgh/go-spew/spew"
// "github.com/davecgh/go-spew/spew"
"go.opentelemetry.io/contrib/instrumentation/github.com/gorilla/mux/otelmux"
"go.opentelemetry.io/otel"
"go.opentelemetry.io/otel/attribute"
+ "go.opentelemetry.io/otel/baggage"
"go.opentelemetry.io/otel/exporters/otlp/otlptrace"
"go.opentelemetry.io/otel/exporters/otlp/otlptrace/otlptracegrpc"
"go.opentelemetry.io/otel/propagation"
@@ -114,22 +116,44 @@ func MuxServerMiddleware(serviceName string) func(http.Handler) http.Handler {
fmt.Println("Adding mux server middleware")
return func(h http.Handler) http.Handler {
return otlmux(http.HandlerFunc(func(rw http.ResponseWriter, r *http.Request) {
+ var rid string
// otelmux has extracted the span. now put it into the ctx-specific logger
// var carrier propagation.HeaderCarrier = propagation.HeaderCarrier{}
// otelmux has extracted the span. now put it into the ctx-specific logger
// ctx := otel.GetTextMapPropagator().Extract(r.Context(), carrier)
- // spew.Dump(r.Header)
+ spew.Dump(r.Header)
+ spew.Dump(r.Context())
// testsc := trace.SpanFromContext(ctx).SpanContext()
// spew.Dump(testsc)
s := trace.SpanFromContext(r.Context())
- rid := r.Header.Get("X-Request-ID")
- if rid != "" {
- rid = s.SpanContext().TraceID().String())
+ bag := baggage.FromContext(r.Context())
+ rid = bag.Member("X-Request-ID").Value()
+ spew.Dump(bag.Members())
+
+ fmt.Println("rid:", rid)
+
+ if rid == "" {
+ rid = r.Header.Get("X-Request-ID")
+ if rid == "" {
+ rid = s.SpanContext().TraceID().String()
+ }
}
+ if rid != "" {
s.SetAttributes(attribute.String("X-Request-ID", rid))
+ member, err := baggage.NewMember("X-Request-ID", rid)
+ if err != nil {
+ s.RecordError(err)
+ }
+ bag, err = bag.SetMember(member)
+ spew.Dump(bag.Members())
+ ctx := baggage.ContextWithBaggage(r.Context(), bag)
+ r = r.Clone(ctx)
+
rw.Header().Add("X-Request-ID", rid)
+ logger.FromContext(r.Context()).AddContext("X-Request-ID", rid)
+ }
// testctx := trace.ContextWithSpanContext(ctx, s.SpanContext())
// r2 := r.Clone(testctx)
@@ -137,9 +161,8 @@ func MuxServerMiddleware(serviceName string) func(http.Handler) http.Handler {
if sc := s.SpanContext(); sc.HasTraceID() {
spanID, traceID := sc.SpanID().String(), sc.TraceID().String()
- logger.FromContext(r.Context()).AddContext("X-Request-ID", rid)
// fmt.Println("span/trace: ", spanID, " ", traceID)
- // spew.Dump(sc)
+ spew.Dump(sc)
// datadog converts hex strings to uint64 IDs, so log those so that correlating logs and traces works
if len(traceID) == 32 && len(spanID) == 16 { // opentelemetry format: 16 byte (32-char hex), 8 byte (16-char hex) trace and span ids

diff:
@@ -18,7 +18,7 @@ import (
)
//propagator to use
-var propagator propagation.TextMapPropagator = propagation.TraceContext{} // traceparent header
+var propagator propagation.TextMapPropagator = propagation.NewCompositeTextMapPropagator(propagation.TraceContext{}, propagation.Baggage{}) // traceparent header
type Option interface {
apply(*options)
}

old_path: wag

new_path: wag

diff: Binary files a/wag and b/wag differ

original_message: Include baggage in propagation


message: cleaned up some spews and printlns

diff:
@@ -122,16 +122,11 @@ func MuxServerMiddleware(serviceName string) func(http.Handler) http.Handler {
// otelmux has extracted the span. now put it into the ctx-specific logger
// ctx := otel.GetTextMapPropagator().Extract(r.Context(), carrier)
- spew.Dump(r.Header)
- spew.Dump(r.Context())
// testsc := trace.SpanFromContext(ctx).SpanContext()
// spew.Dump(testsc)
s := trace.SpanFromContext(r.Context())
bag := baggage.FromContext(r.Context())
rid = bag.Member("X-Request-ID").Value()
- spew.Dump(bag.Members())
-
- fmt.Println("rid:", rid)
if rid == "" {
rid = r.Header.Get("X-Request-ID")
@@ -147,7 +142,6 @@ func MuxServerMiddleware(serviceName string) func(http.Handler) http.Handler {
s.RecordError(err)
}
bag, err = bag.SetMember(member)
- spew.Dump(bag.Members())
ctx := baggage.ContextWithBaggage(r.Context(), bag)
r = r.Clone(ctx)

original_message: cleaned up some spews and printlns


message: added back debug stuff

diff:
@@ -122,12 +122,16 @@ func MuxServerMiddleware(serviceName string) func(http.Handler) http.Handler {
// otelmux has extracted the span. now put it into the ctx-specific logger
// ctx := otel.GetTextMapPropagator().Extract(r.Context(), carrier)
+ spew.Dump(r.Header)
+ spew.Dump(r.Context())
// testsc := trace.SpanFromContext(ctx).SpanContext()
// spew.Dump(testsc)
s := trace.SpanFromContext(r.Context())
bag := baggage.FromContext(r.Context())
rid = bag.Member("X-Request-ID").Value()
+ fmt.Println("rid:", rid)
+
if rid == "" {
rid = r.Header.Get("X-Request-ID")
if rid == "" {
@@ -142,6 +146,7 @@ func MuxServerMiddleware(serviceName string) func(http.Handler) http.Handler {
s.RecordError(err)
}
bag, err = bag.SetMember(member)
+ spew.Dump(bag.Members())
ctx := baggage.ContextWithBaggage(r.Context(), bag)
r = r.Clone(ctx)

original_message: added back debug stuff


message: request-id propagation into logs fully functional

diff:
@@ -10,7 +10,6 @@ import (
"time"
"github.com/Clever/kayvee-go/v7/logger"
- "github.com/davecgh/go-spew/spew"
// "github.com/davecgh/go-spew/spew"
"go.opentelemetry.io/contrib/instrumentation/github.com/gorilla/mux/otelmux"
@@ -122,16 +121,12 @@ func MuxServerMiddleware(serviceName string) func(http.Handler) http.Handler {
// otelmux has extracted the span. now put it into the ctx-specific logger
// ctx := otel.GetTextMapPropagator().Extract(r.Context(), carrier)
- spew.Dump(r.Header)
- spew.Dump(r.Context())
// testsc := trace.SpanFromContext(ctx).SpanContext()
// spew.Dump(testsc)
s := trace.SpanFromContext(r.Context())
bag := baggage.FromContext(r.Context())
rid = bag.Member("X-Request-ID").Value()
- fmt.Println("rid:", rid)
-
if rid == "" {
rid = r.Header.Get("X-Request-ID")
if rid == "" {
@@ -146,7 +141,6 @@ func MuxServerMiddleware(serviceName string) func(http.Handler) http.Handler {
s.RecordError(err)
}
bag, err = bag.SetMember(member)
- spew.Dump(bag.Members())
ctx := baggage.ContextWithBaggage(r.Context(), bag)
r = r.Clone(ctx)
@@ -161,7 +155,6 @@ func MuxServerMiddleware(serviceName string) func(http.Handler) http.Handler {
if sc := s.SpanContext(); sc.HasTraceID() {
spanID, traceID := sc.SpanID().String(), sc.TraceID().String()
// fmt.Println("span/trace: ", spanID, " ", traceID)
- spew.Dump(sc)
// datadog converts hex strings to uint64 IDs, so log those so that correlating logs and traces works
if len(traceID) == 32 && len(spanID) == 16 { // opentelemetry format: 16 byte (32-char hex), 8 byte (16-char hex) trace and span ids

diff:
@@ -11,7 +11,6 @@ import (
"regexp"
"strings"
- "github.com/davecgh/go-spew/spew"
"github.com/go-openapi/loads"
"github.com/go-openapi/loads/fmts"
"github.com/go-openapi/spec"
@@ -74,7 +73,6 @@ func main() {
if err := conf.parse(); err != nil {
log.Fatalf(err.Error())
}
- spew.Dump(conf)
loads.AddLoader(fmts.YAMLMatcher, fmts.YAMLDoc)
doc, err := loads.Spec(*conf.swaggerFile)


message: first pass at moving from v8 to v9 internally

old_path: VERSION

new_path: VERSION

diff:
-v9.0.2-alpha
+v9.0.2-alpha client/models as separate modules, otel updates, other breaking changes.
v8.2.1 Sort attributes list used in v8.2.0 to reduce diffs
@@ -11,7 +11,7 @@ v8.1.7: Fix for dynamo batch deletes when using common initialisms in composite
v8.1.6: Add dynamodb codegen support for batch deleting arrays of objects
v8.1.5: Fixed dynamodb codegen error involving fields marked with x-nullable
-su
+
v8.1.4: Add dynamodb codegen support for batch writing arrays of objects
v8.1.3: Support TS methods with a single hyphenated header variable

diff:
@@ -7,6 +7,7 @@ import (
"fmt"
"net/http"
"os"
+ "strconv"
"time"
"github.com/Clever/kayvee-go/v7/logger"
@@ -29,21 +30,7 @@ import (
var defaultCollectorHost string = "localhost"
var defaultCollectorPort uint16 = 4317
-// propagator to use.
-var propagator propagation.TextMapPropagator = propagation.TraceContext{} // traceparent header
func SetupGlobalTraceProviderAndExporter(ctx context.Context) (sdktrace.SpanExporter, *sdktrace.TracerProvider, error) {
- // samplingProbability := 0.01
- // isLocal := os.Getenv("_IS_LOCAL") == "true"
- // if isLocal {
- // samplingProbability = 1.0
- // } else if v := os.Getenv("TRACING_SAMPLING_PROBABILITY"); v != "" {
- // samplingProbabilityFromEnv, err := strconv.ParseFloat(v, 64)
- // if err != nil {
- // return nil, nil, fmt.Errorf("could not parse '%s' to float", v)
- // }
- // samplingProbability = samplingProbabilityFromEnv
- // }
- // fmt.Println("isLocal:", isLocal)
addr := fmt.Sprintf("%s:%d", defaultCollectorHost, defaultCollectorPort)
@@ -73,12 +60,25 @@ func SetupGlobalTraceProviderAndExporter(ctx context.Context) (sdktrace.SpanExpo
}
func newTracerProvider(exporter sdktrace.SpanExporter, resource *resource.Resource) *sdktrace.TracerProvider {
+ samplingProbability := 0.05
+ isLocal := os.Getenv("_IS_LOCAL") == "true"
+ if isLocal {
+ samplingProbability = 1.0
+ } else if v := os.Getenv("TRACING_SAMPLING_PROBABILITY"); v != "" {
+ samplingProbabilityFromEnv, err := strconv.ParseFloat(v, 64)
+ if err != nil {
+ samplingProbabilityFromEnv = 1
+ }
+ samplingProbability = samplingProbabilityFromEnv
+ }
+ fmt.Println("samplingProbability:", samplingProbability)
+
tp := sdktrace.NewTracerProvider(
// We use the default ID generator. In order for sampling to work (at least with this sampler)
// the ID generator must generate trace IDs uniformly at random from the entire space of uint64.
// For example, the default x-ray ID generator does not do this.
- sdktrace.WithSampler(sdktrace.AlwaysSample()),
- // sdktrace.WithSampler(sdktrace.ParentBased(sdktrace.TraceIDRatioBased(samplingProbability))),
+ // sdktrace.WithSampler(sdktrace.TraceIDRatioBased()),
+ sdktrace.WithSampler(sdktrace.ParentBased(sdktrace.TraceIDRatioBased(samplingProbability))),
// These maximums are to guard against something going wrong and sending a ton of data unexpectedly
sdktrace.WithSpanLimits(sdktrace.SpanLimits{
AttributeCountLimit: 100,
@@ -87,8 +87,8 @@ func newTracerProvider(exporter sdktrace.SpanExporter, resource *resource.Resour
}),
// Batcher is more efficient, switch to it after testing
- sdktrace.WithSyncer(exporter),
- // sdktrace.WithBatcher(exporter),
+ // sdktrace.WithSyncer(exporter),
+ sdktrace.WithBatcher(exporter),
sdktrace.WithResource(resource),
)
otel.SetTracerProvider(tp)
@@ -120,9 +120,7 @@ func MuxServerMiddleware(serviceName string) func(http.Handler) http.Handler {
// var carrier propagation.HeaderCarrier = propagation.HeaderCarrier{}
// otelmux has extracted the span. now put it into the ctx-specific logger
- // ctx := otel.GetTextMapPropagator().Extract(r.Context(), carrier)
- // testsc := trace.SpanFromContext(ctx).SpanContext()
- // spew.Dump(testsc)
+
s := trace.SpanFromContext(r.Context())
bag := baggage.FromContext(r.Context())
rid = bag.Member("X-Request-ID").Value()
@@ -142,27 +140,22 @@ func MuxServerMiddleware(serviceName string) func(http.Handler) http.Handler {
}
bag, err = bag.SetMember(member)
ctx := baggage.ContextWithBaggage(r.Context(), bag)
- r = r.Clone(ctx)
+ r = r.WithContext(ctx)
rw.Header().Add("X-Request-ID", rid)
logger.FromContext(r.Context()).AddContext("X-Request-ID", rid)
}
- // testctx := trace.ContextWithSpanContext(ctx, s.SpanContext())
- // r2 := r.Clone(testctx)
- // spew.Dump(r2.Header)
-
if sc := s.SpanContext(); sc.HasTraceID() {
spanID, traceID := sc.SpanID().String(), sc.TraceID().String()
- // fmt.Println("span/trace: ", spanID, " ", traceID)
// datadog converts hex strings to uint64 IDs, so log those so that correlating logs and traces works
if len(traceID) == 32 && len(spanID) == 16 { // opentelemetry format: 16 byte (32-char hex), 8 byte (16-char hex) trace and span ids
traceIDBs, _ := hex.DecodeString(traceID)
- logger.FromContext(r.Context()).AddContext("trace_id",
+ logger.FromContext(r.Context()).AddContext("dd.trace_id",
fmt.Sprintf("%d", binary.BigEndian.Uint64(traceIDBs[8:])))
spanIDBs, _ := hex.DecodeString(spanID)
- logger.FromContext(r.Context()).AddContext("span_id",
+ logger.FromContext(r.Context()).AddContext("dd.span_id",
fmt.Sprintf("%d", binary.BigEndian.Uint64(spanIDBs)))
}
}

diff:
@@ -226,8 +226,8 @@ func newTracerProvider(exporter sdktrace.SpanExporter, samplingProbability float
LinkCountLimit: 100,
}),
//Batcher is more efficient, switch to it after testing
- sdktrace.WithSyncer(exporter),
- //sdktrace.WithBatcher(exporter),
+ // sdktrace.WithSyncer(exporter),
+ sdktrace.WithBatcher(exporter),
sdktrace.WithResource(newResource()),
)

diff:
-module github.com/Clever/wag/v8
+module github.com/Clever/wag/v9
go 1.16

diff:
@@ -16,14 +16,14 @@ import (
"github.com/go-openapi/spec"
"github.com/go-openapi/swag"
- goclient "github.com/Clever/wag/v8/clients/go"
- jsclient "github.com/Clever/wag/v8/clients/js"
- "github.com/Clever/wag/v8/hardcoded"
- "github.com/Clever/wag/v8/models"
- "github.com/Clever/wag/v8/server"
- "github.com/Clever/wag/v8/server/gendb"
- "github.com/Clever/wag/v8/swagger"
- "github.com/Clever/wag/v8/validation"
+ goclient "github.com/Clever/wag/v9/clients/go"
+ jsclient "github.com/Clever/wag/v9/clients/js"
+ "github.com/Clever/wag/v9/hardcoded"
+ "github.com/Clever/wag/v9/models"
+ "github.com/Clever/wag/v9/server"
+ "github.com/Clever/wag/v9/server/gendb"
+ "github.com/Clever/wag/v9/swagger"
+ "github.com/Clever/wag/v9/validation"
)
// config contains the configuration of command line flags and configuration derived from command line flags

diff:
@@ -18,12 +18,12 @@ func Test_config_validate(t *testing.T) {
name: "with server",
input: config{
outputPath: swag.String("output-path"),
- goPackageName: swag.String("github.com/Clever/wag/v8/output-path"),
+ goPackageName: swag.String("github.com/Clever/wag/v9/output-path"),
jsModulePath: swag.String("jsModulePath"),
},
output: config{
outputPath: swag.String("output-path"),
- goPackageName: swag.String("github.com/Clever/wag/v8/output-path"),
+ goPackageName: swag.String("github.com/Clever/wag/v9/output-path"),
jsModulePath: swag.String("jsModulePath"),
relativeDynamoPath: swag.String("server/db"),
generateDynamo: true,
@@ -45,7 +45,7 @@ func Test_config_validate(t *testing.T) {
output: config{
clientOnly: swag.Bool(true),
outputPath: swag.String("output-path"),
- goPackageName: swag.String("github.com/Clever/wag/v8/output-path"),
+ goPackageName: swag.String("github.com/Clever/wag/v9/output-path"),
jsModulePath: swag.String("jsModulePath"),
generateServer: false,
generateDynamo: false,
@@ -61,13 +61,13 @@ func Test_config_validate(t *testing.T) {
clientOnly: swag.Bool(true),
clientLanguage: swag.String("go"),
outputPath: swag.String("output-path"),
- goPackageName: swag.String("github.com/Clever/wag/v8/output-path"),
+ goPackageName: swag.String("github.com/Clever/wag/v9/output-path"),
},
output: config{
clientOnly: swag.Bool(true),
clientLanguage: swag.String("go"),
outputPath: swag.String("output-path"),
- goPackageName: swag.String("github.com/Clever/wag/v8/output-path"),
+ goPackageName: swag.String("github.com/Clever/wag/v9/output-path"),
generateServer: false,
generateDynamo: false,
generateTracing: true,
@@ -82,14 +82,14 @@ func Test_config_validate(t *testing.T) {
clientOnly: swag.Bool(true),
clientLanguage: swag.String("js"),
outputPath: swag.String("output-path"),
- goPackageName: swag.String("github.com/Clever/wag/v8/output-path"),
+ goPackageName: swag.String("github.com/Clever/wag/v9/output-path"),
jsModulePath: swag.String("jsModulePath"),
},
output: config{
clientOnly: swag.Bool(true),
clientLanguage: swag.String("js"),
outputPath: swag.String("output-path"),
- goPackageName: swag.String("github.com/Clever/wag/v8/output-path"),
+ goPackageName: swag.String("github.com/Clever/wag/v9/output-path"),
jsModulePath: swag.String("jsModulePath"),
generateServer: false,
generateDynamo: false,
@@ -104,13 +104,13 @@ func Test_config_validate(t *testing.T) {
input: config{
clientLanguage: swag.String("js"),
outputPath: swag.String("output-path"),
- goPackageName: swag.String("github.com/Clever/wag/v8/output-path"),
+ goPackageName: swag.String("github.com/Clever/wag/v9/output-path"),
jsModulePath: swag.String("jsModulePath"),
},
output: config{
clientLanguage: swag.String("js"),
outputPath: swag.String("output-path"),
- goPackageName: swag.String("github.com/Clever/wag/v8/output-path"),
+ goPackageName: swag.String("github.com/Clever/wag/v9/output-path"),
jsModulePath: swag.String("jsModulePath"),
relativeDynamoPath: swag.String("server/db"),
generateServer: true,
@@ -126,12 +126,12 @@ func Test_config_validate(t *testing.T) {
input: config{
clientLanguage: swag.String("go"),
outputPath: swag.String("output-path"),
- goPackageName: swag.String("github.com/Clever/wag/v8/output-path"),
+ goPackageName: swag.String("github.com/Clever/wag/v9/output-path"),
},
output: config{
clientLanguage: swag.String("go"),
outputPath: swag.String("output-path"),
- goPackageName: swag.String("github.com/Clever/wag/v8/output-path"),
+ goPackageName: swag.String("github.com/Clever/wag/v9/output-path"),
relativeDynamoPath: swag.String("server/db"),
generateServer: true,
generateTracing: true,
@@ -146,7 +146,7 @@ func Test_config_validate(t *testing.T) {
input: config{
clientLanguage: swag.String("js"),
outputPath: swag.String("output-path"),
- goPackageName: swag.String("github.com/Clever/wag/v8/output-path"),
+ goPackageName: swag.String("github.com/Clever/wag/v9/output-path"),
},
wantErr: true,
},
@@ -166,11 +166,11 @@ func Test_config_validate(t *testing.T) {
dynamoOnly: swag.Bool(true),
relativeDynamoPath: swag.String("gen-db/db"),
outputPath: swag.String("output-path"),
- goPackageName: swag.String("github.com/Clever/wag/v8/output-path"),
+ goPackageName: swag.String("github.com/Clever/wag/v9/output-path"),
},
output: config{
outputPath: swag.String("output-path"),
- goPackageName: swag.String("github.com/Clever/wag/v8/output-path"),
+ goPackageName: swag.String("github.com/Clever/wag/v9/output-path"),
relativeDynamoPath: swag.String("gen-db/db"),
dynamoOnly: swag.Bool(true),
generateServer: false,
@@ -186,11 +186,11 @@ func Test_config_validate(t *testing.T) {
input: config{
dynamoOnly: swag.Bool(true),
outputPath: swag.String("output-path"),
- goPackageName: swag.String("github.com/Clever/wag/v8/output-path"),
+ goPackageName: swag.String("github.com/Clever/wag/v9/output-path"),
},
output: config{
outputPath: swag.String("output-path"),
- goPackageName: swag.String("github.com/Clever/wag/v8/output-path"),
+ goPackageName: swag.String("github.com/Clever/wag/v9/output-path"),
relativeDynamoPath: swag.String("db"),
dynamoOnly: swag.Bool(true),
generateServer: false,

diff:
@@ -9,7 +9,7 @@ import (
"strings"
"text/template"
- "github.com/Clever/wag/v8/swagger"
+ "github.com/Clever/wag/v9/swagger"
"github.com/awslabs/goformation/v2/cloudformation/resources"
"github.com/go-openapi/spec"
"github.com/go-swagger/go-swagger/generator"

diff:
@@ -7,7 +7,7 @@ import (
"text/template"
"github.com/Clever/go-utils/stringset"
- "github.com/Clever/wag/v8/utils"
+ "github.com/Clever/wag/v9/utils"
"github.com/awslabs/goformation/v2/cloudformation/resources"
"github.com/go-openapi/spec"
"github.com/go-openapi/swag"

diff:
@@ -9,10 +9,10 @@ import (
"github.com/go-openapi/spec"
- clients "github.com/Clever/wag/v8/clients/go"
- "github.com/Clever/wag/v8/swagger"
- "github.com/Clever/wag/v8/templates"
- "github.com/Clever/wag/v8/utils"
+ clients "github.com/Clever/wag/v9/clients/go"
+ "github.com/Clever/wag/v9/swagger"
+ "github.com/Clever/wag/v9/templates"
+ "github.com/Clever/wag/v9/utils"
)
// Generate server package for a swagger spec.

diff:
@@ -4,8 +4,8 @@ import (
"fmt"
"strings"
- "github.com/Clever/wag/v8/templates"
- "github.com/Clever/wag/v8/utils"
+ "github.com/Clever/wag/v9/templates"
+ "github.com/Clever/wag/v9/utils"
"github.com/go-openapi/spec"
)

diff:
@@ -5,7 +5,7 @@ import (
"strconv"
"strings"
- "github.com/Clever/wag/v8/utils"
+ "github.com/Clever/wag/v9/utils"
"github.com/go-openapi/spec"
)

diff:
@@ -6,7 +6,7 @@ import (
"regexp"
"strings"
- "github.com/Clever/wag/v8/swagger"
+ "github.com/Clever/wag/v9/swagger"
swaggererrors "github.com/go-openapi/errors"
"github.com/go-openapi/loads"
"github.com/go-openapi/spec"


message: ran generate/build

diff:
@@ -12,7 +12,6 @@ import (
"crypto/sha256"
"fmt"
"io"
- "io/ioutil"
"os"
"path/filepath"
"strings"
@@ -234,11 +233,13 @@ const AssetDebug = false
// directory embedded in the file by go-bindata.
// For example if you run go-bindata on data/... and data contains the
// following hierarchy:
+//
// data/
// foo.txt
// img/
// a.png
// b.png
+//
// then AssetDir("data") would return []string{"foo.txt", "img"},
// AssetDir("data/img") would return []string{"a.png", "b.png"},
// AssetDir("foo.txt") and AssetDir("notexist") would return an error, and
@@ -294,7 +295,7 @@ func RestoreAsset(dir, name string) error {
if err != nil {
return err
}
- err = ioutil.WriteFile(_filePath(dir, name), data, info.Mode())
+ err = os.WriteFile(_filePath(dir, name), data, info.Mode())
if err != nil {
return err
}

change_type: ADD

diff:
+// Code generated by MockGen. DO NOT EDIT.
+// Source: interface.go
+
+// Package client is a generated GoMock package.
+package client
+
+import (
+ context "context"
+ reflect "reflect"
+
+ models "github.com/Clever/wag/samples/v8/gen-go-blog/models"
+ gomock "github.com/golang/mock/gomock"
+)
+
+// MockClient is a mock of Client interface.
+type MockClient struct {
+ ctrl *gomock.Controller
+ recorder *MockClientMockRecorder
+}
+
+// MockClientMockRecorder is the mock recorder for MockClient.
+type MockClientMockRecorder struct {
+ mock *MockClient
+}
+
+// NewMockClient creates a new mock instance.
+func NewMockClient(ctrl *gomock.Controller) *MockClient {git s
+ mock := &MockClient{ctrl: ctrl}
+ mock.recorder = &MockClientMockRecorder{mock}
+ return mock
+}
+
+// EXPECT returns an object that allows the caller to indicate expected use.
+func (m *MockClient) EXPECT() *MockClientMockRecorder {
+ return m.recorder
+}
+
+// GetSectionsForStudent mocks base method.
+func (m *MockClient) GetSectionsForStudent(ctx context.Context, studentID string) ([]models.Section, error) {
+ m.ctrl.T.Helper()
+ ret := m.ctrl.Call(m, "GetSectionsForStudent", ctx, studentID)
+ ret0, _ := ret[0].([]models.Section)
+ ret1, _ := ret[1].(error)
+ return ret0, ret1
+}
+
+// GetSectionsForStudent indicates an expected call of GetSectionsForStudent.
+func (mr *MockClientMockRecorder) GetSectionsForStudent(ctx, studentID interface{}) *gomock.Call {
+ mr.mock.ctrl.T.Helper()
+ return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "GetSectionsForStudent", reflect.TypeOf((*MockClient)(nil).GetSectionsForStudent), ctx, studentID)
+}
+
+// PostGradeFileForStudent mocks base method.
+func (m *MockClient) PostGradeFileForStudent(ctx context.Context, i *models.PostGradeFileForStudentInput) error {
+ m.ctrl.T.Helper()
+ ret := m.ctrl.Call(m, "PostGradeFileForStudent", ctx, i)
+ ret0, _ := ret[0].(error)
+ return ret0
+}
+
+// PostGradeFileForStudent indicates an expected call of PostGradeFileForStudent.
+func (mr *MockClientMockRecorder) PostGradeFileForStudent(ctx, i interface{}) *gomock.Call {
+ mr.mock.ctrl.T.Helper()
+ return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "PostGradeFileForStudent", reflect.TypeOf((*MockClient)(nil).PostGradeFileForStudent), ctx, i)
+}
+
+// PostSectionsForStudent mocks base method.
+func (m *MockClient) PostSectionsForStudent(ctx context.Context, i *models.PostSectionsForStudentInput) ([]models.Section, error) {
+ m.ctrl.T.Helper()
+ ret := m.ctrl.Call(m, "PostSectionsForStudent", ctx, i)
+ ret0, _ := ret[0].([]models.Section)
+ ret1, _ := ret[1].(error)
+ return ret0, ret1
+}
+
+// PostSectionsForStudent indicates an expected call of PostSectionsForStudent.
+func (mr *MockClientMockRecorder) PostSectionsForStudent(ctx, i interface{}) *gomock.Call {
+ mr.mock.ctrl.T.Helper()
+ return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "PostSectionsForStudent", reflect.TypeOf((*MockClient)(nil).PostSectionsForStudent), ctx, i)
+}

diff:
+// Code generated by MockGen. DO NOT EDIT.
+// Source: interface.go
+
+// Package server is a generated GoMock package.
+package server
+
+import (
+ context "context"
+ reflect "reflect"
+
+ models "github.com/Clever/wag/samples/v8/gen-go-blog/models"
+ gomock "github.com/golang/mock/gomock"
+)
+
+// MockController is a mock of Controller interface.
+type MockController struct {
+ ctrl *gomock.Controller
+ recorder *MockControllerMockRecorder
+}
+
+// MockControllerMockRecorder is the mock recorder for MockController.
+type MockControllerMockRecorder struct {
+ mock *MockController
+}
+
+// NewMockController creates a new mock instance.
+func NewMockController(ctrl *gomock.Controller) *MockController {
+ mock := &MockController{ctrl: ctrl}
+ mock.recorder = &MockControllerMockRecorder{mock}
+ return mock
+}
+
+// EXPECT returns an object that allows the caller to indicate expected use.
+func (m *MockController) EXPECT() *MockControllerMockRecorder {
+ return m.recorder
+}
+
+// GetSectionsForStudent mocks base method.
+func (m *MockController) GetSectionsForStudent(ctx context.Context, studentID string) ([]models.Section, error) {
+ m.ctrl.T.Helper()
+ ret := m.ctrl.Call(m, "GetSectionsForStudent", ctx, studentID)
+ ret0, _ := ret[0].([]models.Section)
+ ret1, _ := ret[1].(error)
+ return ret0, ret1
+}
+
+// GetSectionsForStudent indicates an expected call of GetSectionsForStudent.
+func (mr *MockControllerMockRecorder) GetSectionsForStudent(ctx, studentID interface{}) *gomock.Call {
+ mr.mock.ctrl.T.Helper()
+ return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "GetSectionsForStudent", reflect.TypeOf((*MockController)(nil).GetSectionsForStudent), ctx, studentID)
+}
+
+// PostGradeFileForStudent mocks base method.
+func (m *MockController) PostGradeFileForStudent(ctx context.Context, i *models.PostGradeFileForStudentInput) error {
+ m.ctrl.T.Helper()
+ ret := m.ctrl.Call(m, "PostGradeFileForStudent", ctx, i)
+ ret0, _ := ret[0].(error)
+ return ret0
+}
+
+// PostGradeFileForStudent indicates an expected call of PostGradeFileForStudent.
+func (mr *MockControllerMockRecorder) PostGradeFileForStudent(ctx, i interface{}) *gomock.Call {
+ mr.mock.ctrl.T.Helper()
+ return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "PostGradeFileForStudent", reflect.TypeOf((*MockController)(nil).PostGradeFileForStudent), ctx, i)
+}
+
+// PostSectionsForStudent mocks base method.
+func (m *MockController) PostSectionsForStudent(ctx context.Context, i *models.PostSectionsForStudentInput) ([]models.Section, error) {
+ m.ctrl.T.Helper()
+ ret := m.ctrl.Call(m, "PostSectionsForStudent", ctx, i)
+ ret0, _ := ret[0].([]models.Section)
+ ret1, _ := ret[1].(error)
+ return ret0, ret1
+}
+
+// PostSectionsForStudent indicates an expected call of PostSectionsForStudent.
+func (mr *MockControllerMockRecorder) PostSectionsForStudent(ctx, i interface{}) *gomock.Call {
+ mr.mock.ctrl.T.Helper()
+ return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "PostSectionsForStudent", reflect.TypeOf((*MockController)(nil).PostSectionsForStudent), ctx, i)
+}

diff:
@@ -247,6 +247,7 @@ github.com/kardianos/osext v0.0.0-20190222173326-2bc1f35cddc0/go.mod h1:1NbS8ALr
github.com/karrick/godirwalk v1.8.0/go.mod h1:H5KPZjojv4lE+QYImBI8xVtrBRgYrIVsaRPx4tDPEn4=
github.com/karrick/godirwalk v1.10.3/go.mod h1:RoGL9dQei4vP9ilrpETWE8CLOZ1kiN0LhBygSwrAsHA=
github.com/kevinburke/go-bindata v3.23.0+incompatible/go.mod h1:/pEEZ72flUW2p0yi30bslSp9YqD9pysLxunQDdb2CPM=
+github.com/kevinburke/go-bindata v3.24.0+incompatible/go.mod h1:/pEEZ72flUW2p0yi30bslSp9YqD9pysLxunQDdb2CPM=
github.com/kisielk/errcheck v1.1.0/go.mod h1:EZBBE59ingxPouuu3KfxchcWSUPOHkagtvWXihfKN4Q=
github.com/kisielk/errcheck v1.2.0/go.mod h1:/BMXB+zMLi60iA8Vv6Ksmxu/1UDYcXs4uQLJ+jE2L00=
github.com/kisielk/gotool v1.0.0/go.mod h1:XhKaO+MFFWcvkIS/tQcRk01m1F5IRFswLeQ+oQHNcck=

diff:
@@ -15,7 +15,6 @@ import (
"crypto/sha256"
"fmt"
"io"
- "io/ioutil"
"os"
"path/filepath"
"strings"
@@ -300,11 +299,13 @@ const AssetDebug = false
// directory embedded in the file by go-bindata.
// For example if you run go-bindata on data/... and data contains the
// following hierarchy:
+//
// data/
// foo.txt
// img/
// a.png
// b.png
+//
// then AssetDir("data") would return []string{"foo.txt", "img"},
// AssetDir("data/img") would return []string{"a.png", "b.png"},
// AssetDir("foo.txt") and AssetDir("notexist") would return an error, and
@@ -359,7 +360,7 @@ func RestoreAsset(dir, name string) error {
if err != nil {
return err
}
- err = ioutil.WriteFile(_filePath(dir, name), data, info.Mode())
+ err = os.WriteFile(_filePath(dir, name), data, info.Mode())
if err != nil {
return err
}

original_message: ran generate/build


message: tidy tracing go.mod

diff:
@@ -6,7 +6,6 @@ require (
github.com/grpc-ecosystem/grpc-gateway/v2 v2.11.2 // indirect
go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp v0.35.0
go.opentelemetry.io/otel v1.10.0
- go.opentelemetry.io/otel/exporters/jaeger v1.10.0
go.opentelemetry.io/otel/exporters/otlp/otlptrace v1.10.0
go.opentelemetry.io/otel/exporters/otlp/otlptrace/otlptracegrpc v1.10.0
go.opentelemetry.io/otel/sdk v1.10.0

diff:
@@ -202,7 +202,6 @@ github.com/rogpeppe/fastuuid v1.2.0/go.mod h1:jVj6XXZzXRy/MSR5jhDC/2q6DgLz+nrA6L
github.com/rogpeppe/go-internal v1.3.0/go.mod h1:M8bDsm7K2OlrFYOpmOWEs/qY81heoFRclV5y23lUDJ4=
github.com/spaolacci/murmur3 v0.0.0-20180118202830-f09979ecbc72/go.mod h1:JwIasOWyU6f++ZhiEuf87xNszmSA2myDM2Kzu9HwQUA=
github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME=
-github.com/stretchr/objx v0.4.0 h1:M2gUjqZET1qApGOWNSnZ49BAIMX4F/1plDv3+l31EJ4=
github.com/stretchr/objx v0.4.0/go.mod h1:YvHI0jy2hoMjB+UWwv71VJQ9isScKT/TqJzVSSt89Yw=
github.com/stretchr/testify v1.4.0/go.mod h1:j7eGeouHqKxXV5pUuKE4zz7dFj8WfuZ+81PSLYec5m4=
github.com/stretchr/testify v1.5.1/go.mod h1:5W2xD1RspED5o8YsWQXVCued0rvSQ+mT+I5cxcmMvtA=
@@ -228,8 +227,6 @@ go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp v0.35.0/go.mod h1:
go.opentelemetry.io/otel v1.8.0/go.mod h1:2pkj+iMj0o03Y+cW6/m8Y4WkRdYN3AvCXCnzRMp9yvM=
go.opentelemetry.io/otel v1.10.0 h1:Y7DTJMR6zs1xkS/upamJYk0SxxN4C9AqRd77jmZnyY4=
go.opentelemetry.io/otel v1.10.0/go.mod h1:NbvWjCthWHKBEUMpf0/v8ZRZlni86PpGFEMA9pnQSnQ=
-go.opentelemetry.io/otel/exporters/jaeger v1.10.0 h1:7W3aVVjEYayu/GOqOVF4mbTvnCuxF1wWu3eRxFGQXvw=
-go.opentelemetry.io/otel/exporters/jaeger v1.10.0/go.mod h1:n9IGyx0fgyXXZ/i0foLHNxtET9CzXHzZeKCucvRBFgA=
go.opentelemetry.io/otel/exporters/otlp/internal/retry v1.10.0 h1:TaB+1rQhddO1sF71MpZOZAuSPW1klK2M8XxfrBMfK7Y=
go.opentelemetry.io/otel/exporters/otlp/internal/retry v1.10.0/go.mod h1:78XhIg8Ht9vR4tbLNUhXsiOnE2HOuSeKAiAcoVQEpOY=
go.opentelemetry.io/otel/exporters/otlp/otlptrace v1.10.0 h1:pDDYmo0QadUPal5fwXoY1pmMpFcdyhXOmL5drCrI3vU=

original_message: tidy tracing go.mod


message: with changes suggested in PR

diff:
@@ -3,13 +3,11 @@ package tracing
import (
"context"
"fmt"
- "log"
"net/http"
"time"
"go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp"
"go.opentelemetry.io/otel"
- "go.opentelemetry.io/otel/exporters/jaeger"
"go.opentelemetry.io/otel/exporters/otlp/otlptrace"
"go.opentelemetry.io/otel/exporters/otlp/otlptrace/otlptracegrpc"
"go.opentelemetry.io/otel/propagation"
@@ -40,10 +38,10 @@ func (o addrOption) apply(opts *options) {
}
// OtlpGrpcExporter uses the otlptracegrpc modules and the otlptrace module to produce a new exporter at our default addr
-func OtlpGrpcExporter(ctx context.Context, opts ...Option) sdktrace.SpanExporter {
+func OtlpGrpcExporter(ctx context.Context, opts ...Option) (sdktrace.SpanExporter, error) {
- DefaultCollectorHost := "localhost"
- var defaultCollectorPort uint16 = 4317
+ const DefaultCollectorHost = "localhost"
+ const defaultCollectorPort uint16 = 4317
addr := fmt.Sprintf("%s:%d", DefaultCollectorHost, defaultCollectorPort)
options := options{
@@ -62,24 +60,12 @@ func OtlpGrpcExporter(ctx context.Context, opts ...Option) sdktrace.SpanExporter
spanExporter, err := otlptrace.New(ctx, otlpClient)
if err != nil {
- log.Fatal(err)
- //Is doing a fatal error here too risky? No easy way to bubble up errors from here to the app using this.
- //without making each of the WithXOption() takes an error as an arg as well.
- return nil
+ return nil, err
}
- return spanExporter
+ return spanExporter, nil
}
-func JaegerExporter() (spanExporter sdktrace.SpanExporter) {
- fmt.Println("Creating Jaeger Exporter")
- spanExporter, err := jaeger.New(jaeger.WithCollectorEndpoint(jaeger.WithEndpoint("http://localhost:14268/api/traces")))
- if err != nil {
- log.Fatal("Error creating Jaeger Exporter")
- }
- return
-}
-
// InstrumentedTransport returns the transport to use in client requests.
// It takes in a transport to wrap, e.g. http.DefaultTransport, and the request
// context value to pull the span name out from.

original_message: with changes suggested in PR


message: remove log.txt

change_type: DELETE

diff:
-go generate ./hardcoded/
-go generate ./server/gendb/
-go build -o bin/wag
-hash npm 2>/dev/null || (echo "Could not run npm, please install node" && false)
-hash jsdoc2md 2>/dev/null || npm install -g jsdoc-to-markdown@^4.0.0
-/Library/Developer/CommandLineTools/usr/bin/make -C samples generate
-github.com/Clever/wag/samples/v9/test ./gen-go-db/server/db/dynamodb
-../bin/wag -file ./swagger.yml -output-path ./gen-go-basic -js-path ./gen-js
-From main: ./gen-go-basic
-(main.config) {
- clientLanguage: (*string)(0x1400033e2b0)(""),
- clientOnly: (*bool)(0x1400034c351)(false),
- dynamoOnly: (*bool)(0x1400034c352)(false),
- outputPath: (*string)(0x1400033e290)((len=14) "./gen-go-basic"),
- versionFlag: (*bool)(0x1400034c350)(false),
- swaggerFile: (*string)(0x1400033e270)((len=13) "./swagger.yml"),
- relativeDynamoPath: (*string)(0x14000302080)((len=9) "server/db"),
- jsModulePath: (*string)(0x1400033e2a0)((len=8) "./gen-js"),
- goPackageName: (*string)(0x1400033e280)((len=45) "github.com/Clever/wag/samples/v9/gen-go-basic"),
- dynamoPath: (string) (len=93) "/Users/chris.martin/go/src/github.com/Clever/functionalWag/wag/samples/gen-go-basic/server/db",
- goAbsolutePackagePath: (string) (len=83) "/Users/chris.martin/go/src/github.com/Clever/functionalWag/wag/samples/gen-go-basic",
- jsClientPath: (string) "",
- generateDynamo: (bool) true,
- generateGoClient: (bool) true,
- generateGoModels: (bool) true,
- generateJSClient: (bool) true,
- generateServer: (bool) true,
- generateTracing: (bool) true
-}
-cd ./gen-js && jsdoc2md index.js types.js > ./README.md
-go generate -mod=mod ./gen-go-basic...
-../bin/wag -file ./deprecated.yml -output-path ./gen-go-deprecated -js-path ./gen-js-deprecated
-From main: ./gen-go-deprecated
-(main.config) {
- clientLanguage: (*string)(0x14000415050)(""),
- clientOnly: (*bool)(0x140004533e1)(false),
- dynamoOnly: (*bool)(0x140004533e2)(false),
- outputPath: (*string)(0x14000415030)((len=19) "./gen-go-deprecated"),
- versionFlag: (*bool)(0x140004533e0)(false),
- swaggerFile: (*string)(0x14000415010)((len=16) "./deprecated.yml"),
- relativeDynamoPath: (*string)(0x14000414260)((len=9) "server/db"),
- jsModulePath: (*string)(0x14000415040)((len=19) "./gen-js-deprecated"),
- goPackageName: (*string)(0x14000415020)((len=50) "github.com/Clever/wag/samples/v9/gen-go-deprecated"),
- dynamoPath: (string) (len=98) "/Users/chris.martin/go/src/github.com/Clever/functionalWag/wag/samples/gen-go-deprecated/server/db",
- goAbsolutePackagePath: (string) (len=88) "/Users/chris.martin/go/src/github.com/Clever/functionalWag/wag/samples/gen-go-deprecated",
- jsClientPath: (string) "",
- generateDynamo: (bool) true,
- generateGoClient: (bool) true,
- generateGoModels: (bool) true,
- generateJSClient: (bool) true,
- generateServer: (bool) true,
- generateTracing: (bool) true
-}
-cd ./gen-js-deprecated && jsdoc2md index.js types.js > ./README.md
-go generate -mod=mod ./gen-go-deprecated...
-../bin/wag -file ./errors.yml -output-path ./gen-go-errors -js-path ./gen-js-errors
-From main: ./gen-go-errors
-(main.config) {
- clientLanguage: (*string)(0x14000414c90)(""),
- clientOnly: (*bool)(0x140000a8d31)(false),
- dynamoOnly: (*bool)(0x140000a8d32)(false),
- outputPath: (*string)(0x14000414c70)((len=15) "./gen-go-errors"),
- versionFlag: (*bool)(0x140000a8d30)(false),
- swaggerFile: (*string)(0x14000414c50)((len=12) "./errors.yml"),
- relativeDynamoPath: (*string)(0x14000382020)((len=9) "server/db"),
- jsModulePath: (*string)(0x14000414c80)((len=15) "./gen-js-errors"),
- goPackageName: (*string)(0x14000414c60)((len=46) "github.com/Clever/wag/samples/v9/gen-go-errors"),
- dynamoPath: (string) (len=94) "/Users/chris.martin/go/src/github.com/Clever/functionalWag/wag/samples/gen-go-errors/server/db",
- goAbsolutePackagePath: (string) (len=84) "/Users/chris.martin/go/src/github.com/Clever/functionalWag/wag/samples/gen-go-errors",
- jsClientPath: (string) "",
- generateDynamo: (bool) true,
- generateGoClient: (bool) true,
- generateGoModels: (bool) true,
- generateJSClient: (bool) true,
- generateServer: (bool) true,
- generateTracing: (bool) true
-}
-cd ./gen-js-errors && jsdoc2md index.js types.js > ./README.md
-go generate -mod=mod ./gen-go-errors...
-../bin/wag -file ./nils.yml -output-path ./gen-go-nils -js-path ./gen-js-nils
-From main: ./gen-go-nils
-(main.config) {
- clientLanguage: (*string)(0x1400039cdb0)(""),
- clientOnly: (*bool)(0x140005905e1)(false),
- dynamoOnly: (*bool)(0x140005905e2)(false),
- outputPath: (*string)(0x1400039cd90)((len=13) "./gen-go-nils"),
- versionFlag: (*bool)(0x140005905e0)(false),
- swaggerFile: (*string)(0x1400039cd70)((len=10) "./nils.yml"),
- relativeDynamoPath: (*string)(0x1400039cdf0)((len=9) "server/db"),
- jsModulePath: (*string)(0x1400039cda0)((len=13) "./gen-js-nils"),
- goPackageName: (*string)(0x1400039cd80)((len=44) "github.com/Clever/wag/samples/v9/gen-go-nils"),
- dynamoPath: (string) (len=92) "/Users/chris.martin/go/src/github.com/Clever/functionalWag/wag/samples/gen-go-nils/server/db",
- goAbsolutePackagePath: (string) (len=82) "/Users/chris.martin/go/src/github.com/Clever/functionalWag/wag/samples/gen-go-nils",
- jsClientPath: (string) "",
- generateDynamo: (bool) true,
- generateGoClient: (bool) true,
- generateGoModels: (bool) true,
- generateJSClient: (bool) true,
- generateServer: (bool) true,
- generateTracing: (bool) true
-}
-cd ./gen-js-nils && jsdoc2md index.js types.js > ./README.md
-go generate -mod=mod ./gen-go-nils...
-../bin/wag -file ./blog.yml -output-path ./gen-go-blog -js-path ./gen-js-blog
-From main: ./gen-go-blog
-(main.config) {
- clientLanguage: (*string)(0x14000454190)(""),
- clientOnly: (*bool)(0x1400060e281)(false),
- dynamoOnly: (*bool)(0x1400060e282)(false),
- outputPath: (*string)(0x14000454170)((len=13) "./gen-go-blog"),
- versionFlag: (*bool)(0x1400060e280)(false),
- swaggerFile: (*string)(0x14000454150)((len=10) "./blog.yml"),
- relativeDynamoPath: (*string)(0x140003e00c0)((len=9) "server/db"),
- jsModulePath: (*string)(0x14000454180)((len=13) "./gen-js-blog"),
- goPackageName: (*string)(0x14000454160)((len=44) "github.com/Clever/wag/samples/v9/gen-go-blog"),
- dynamoPath: (string) (len=92) "/Users/chris.martin/go/src/github.com/Clever/functionalWag/wag/samples/gen-go-blog/server/db",
- goAbsolutePackagePath: (string) (len=82) "/Users/chris.martin/go/src/github.com/Clever/functionalWag/wag/samples/gen-go-blog",
- jsClientPath: (string) "",
- generateDynamo: (bool) true,
- generateGoClient: (bool) true,
- generateGoModels: (bool) true,
- generateJSClient: (bool) true,
- generateServer: (bool) true,
- generateTracing: (bool) true
-}
-cd ./gen-js-blog && jsdoc2md index.js types.js > ./README.md
-go generate -mod=mod ./gen-go-nils...
-../bin/wag -file ./db.yml -output-path ./gen-go-db -js-path ./gen-js-db
-From main: ./gen-go-db
-(main.config) {
- clientLanguage: (*string)(0x140002deff0)(""),
- clientOnly: (*bool)(0x140000eb261)(false),
- dynamoOnly: (*bool)(0x140000eb262)(false),
- outputPath: (*string)(0x140002defd0)((len=11) "./gen-go-db"),
- versionFlag: (*bool)(0x140000eb260)(false),
- swaggerFile: (*string)(0x140002defb0)((len=8) "./db.yml"),
- relativeDynamoPath: (*string)(0x140002df030)((len=9) "server/db"),
- jsModulePath: (*string)(0x140002defe0)((len=11) "./gen-js-db"),
- goPackageName: (*string)(0x140002defc0)((len=42) "github.com/Clever/wag/samples/v9/gen-go-db"),
- dynamoPath: (string) (len=90) "/Users/chris.martin/go/src/github.com/Clever/functionalWag/wag/samples/gen-go-db/server/db",
- goAbsolutePackagePath: (string) (len=80) "/Users/chris.martin/go/src/github.com/Clever/functionalWag/wag/samples/gen-go-db",
- jsClientPath: (string) "",
- generateDynamo: (bool) true,
- generateGoClient: (bool) true,
- generateGoModels: (bool) true,
- generateJSClient: (bool) true,
- generateServer: (bool) true,
- generateTracing: (bool) true
-}
-cd ./gen-js-db && jsdoc2md index.js types.js > ./README.md
-go generate -mod=mod ./gen-go-db...

original_message: remove log.txt


message: grammar fix in comment

diff:
@@ -172,7 +172,7 @@ func (se exporterOption) apply(opts *options) {
// NewLogger creates a logger for id that produces logs at and below the indicated level.
-//Level indicated the level at and below which logs are created.
+// level here indicates the level at and below which logs are created.
func NewLogger(id string, level wcl.LogLevel) PrintlnLogger {
return PrintlnLogger{id: id, level: level}
}

original_message: grammar fix in comment


message: comment modification

diff:
@@ -288,7 +288,8 @@ func New(ctx context.Context, basePath string, opts ...Option) *WagClient {
}
- samplingProbability := 1.0 // TODO: Put back logic to set this to 1 for local, 0.1 otherwise etc.
+ samplingProbability := 1.0 // TODO: Hard setting this to one for now, because right now
+ // it is essentially ignored as the sidecar is determining the sample rate it forwards on to DD.
// samplingProbability := determineSampling()
tp := newTracerProvider(options.exporter, samplingProbability)

original_message: comment modification


message: tracing fixes to play nice with envoy

diff:
@@ -110,37 +110,52 @@ func SetupGlobalTraceProviderAndExporterForTest() (*tracetest.InMemoryExporter,
// Right now we only support logging IDs in the format that Datadog expects.
func MuxServerMiddleware(serviceName string) func(http.Handler) http.Handler {
otlmux := otelmux.Middleware(serviceName, otelmux.WithPropagators(otel.GetTextMapPropagator()))
+ fmt.Println("Adding mux server middleware")
return func(h http.Handler) http.Handler {
return otlmux(http.HandlerFunc(func(rw http.ResponseWriter, r *http.Request) {
var rid string
- // otelmux has extracted the span. now put it into the ctx-specific logger
- // var carrier propagation.HeaderCarrier = propagation.HeaderCarrier{}
-
- // otelmux has extracted the span. now put it into the ctx-specific logger
+ var crid string
s := trace.SpanFromContext(r.Context())
bag := baggage.FromContext(r.Context())
+
+ // Prefer to grab values from baggage
+ crid = bag.Member("clever-request-id").Value()
rid = bag.Member("X-Request-ID").Value()
+ // If the values aren't set in baggage grab the traceid from otel, and the x-request-id
+ // from the headers (set by envoy)
+ if crid == "" {
+ crid = s.SpanContext().TraceID().String()
+ }
+
if rid == "" {
rid = r.Header.Get("X-Request-ID")
- if rid == "" {
- rid = s.SpanContext().TraceID().String()
}
+
+ s.SetAttributes(attribute.String("clever-request-id", crid))
+
+ cridMember, err := baggage.NewMember("clever-request-id", crid)
+ if err != nil {
+ s.RecordError(err)
}
+ bag, err = bag.SetMember(cridMember)
+ logger.FromContext(r.Context()).AddContext("clever-request-id", crid)
+ rw.Header().Add("clever-request-id", crid)
+
if rid != "" {
s.SetAttributes(attribute.String("X-Request-ID", rid))
- member, err := baggage.NewMember("X-Request-ID", rid)
+ ridMember, err := baggage.NewMember("X-Request-ID", rid)
if err != nil {
s.RecordError(err)
}
- bag, err = bag.SetMember(member)
- ctx := baggage.ContextWithBaggage(r.Context(), bag)
- r = r.WithContext(ctx)
+ bag, err = bag.SetMember(ridMember)
+
+ // Envoy logs store this as request_id so lets match it for easier filtering.
+ logger.FromContext(r.Context()).AddContext("request_id", rid)
rw.Header().Add("X-Request-ID", rid)
- logger.FromContext(r.Context()).AddContext("X-Request-ID", rid)
}
if sc := s.SpanContext(); sc.HasTraceID() {
@@ -156,6 +171,10 @@ func MuxServerMiddleware(serviceName string) func(http.Handler) http.Handler {
fmt.Sprintf("%d", binary.BigEndian.Uint64(spanIDBs)))
}
}
+
+ ctx := baggage.ContextWithBaggage(r.Context(), bag)
+ r = r.WithContext(ctx)
+
h.ServeHTTP(rw, r)
}))
}

original_message: tracing fixes to play nice with envoy


message: removed unnecessary print statement

diff:
@@ -110,7 +110,7 @@ func SetupGlobalTraceProviderAndExporterForTest() (*tracetest.InMemoryExporter,
// Right now we only support logging IDs in the format that Datadog expects.
func MuxServerMiddleware(serviceName string) func(http.Handler) http.Handler {
otlmux := otelmux.Middleware(serviceName, otelmux.WithPropagators(otel.GetTextMapPropagator()))
- fmt.Println("Adding mux server middleware")
+ // fmt.Println("Adding mux server middleware")
return func(h http.Handler) http.Handler {
return otlmux(http.HandlerFunc(func(rw http.ResponseWriter, r *http.Request) {
var rid string

original_message: removed unnecessary print statement


message: Thanks jake!

diff:
@@ -141,6 +141,10 @@ func MuxServerMiddleware(serviceName string) func(http.Handler) http.Handler {
}
bag, err = bag.SetMember(cridMember)
+ if err != nil {
+ s.RecordError(err)
+ }
+
logger.FromContext(r.Context()).AddContext("clever-request-id", crid)
rw.Header().Add("clever-request-id", crid)
@@ -151,6 +155,9 @@ func MuxServerMiddleware(serviceName string) func(http.Handler) http.Handler {
s.RecordError(err)
}
bag, err = bag.SetMember(ridMember)
+ if err != nil {
+ s.RecordError(err)
+ }
// Envoy logs store this as request_id so lets match it for easier filtering.
logger.FromContext(r.Context()).AddContext("request_id", rid)

original_message: Thanks jake!


message: added the check for the internal pod

diff:
+#!/usr/bin/env python
+
+'''
+ Send Cluster Infra node's pod status to Zagg
+'''
+#pylint: disable=import-error
+#pylint: disable=invalid-name
+
+from openshift_tools.monitoring.ocutil import OCUtil
+from openshift_tools.monitoring.metric_sender import MetricSender
+
+class InfraNodePodStatus(object):
+ '''
+ This is a check for making sure the internal pods like
+ router and registry running and located on different infra nodes
+ '''
+ def __init__(self):
+ '''initial for the InfraNodePodStatus'''
+ self.kubeconfig = '/tmp/admin.kubeconfig'
+ self.oc = OCUtil(namespace='default', config_file=self.kubeconfig)
+
+ def check_pods(self):
+ ''' get all the pod information '''
+ pods = self.oc.get_pods()
+ pod_report = {}
+ for pod in pods['items']:
+ pod_name = pod['metadata']['name']
+ pod_report[pod_name] = {}
+ pod_report[pod_name]['hostIP'] = pod['status']['hostIP']
+ pod_report[pod_name]['status'] = pod['status']['phase']
+ return pod_report
+
+ @staticmethod
+ def compare_ip(keyword, pod_info_dict):
+ ''' to compare the pod host ip and check the pod status '''
+ pod_hostip_status = [pod_info_dict[i] for i in pod_info_dict.keys() if keyword in i]
+# pod_status = [pod_info_dict[i] for i in pod_info_dict.keys() if keyword in i]
+ pod_run_num = 0
+ for i in pod_hostip_status:
+ if i['status'] == "Running":
+ pod_run_num += 1
+ if len(pod_hostip_status) == 2:
+ if pod_hostip_status[0]['hostIP'] != pod_hostip_status[1]['hostIP']:
+ # print "ok, you do not need do anything for {} pod".format(keyword)
+ result_code = 1
+ else:
+ # print "there are something wrong, please check the pod"
+ result_code = 0
+ else:
+ print "plese check the pod"
+ result_code = 0
+ # result_code 1 means the two pods are on different nodes
+ # pod_run_num means the running pod number
+ return result_code, pod_run_num
+
+ def run(self):
+ ''' run the command and send the code to zabbix '''
+ ms = MetricSender()
+
+ pod_report = self.check_pods()
+
+ # the check_value is the value to send to zabbix
+ router_check_value = self.compare_ip('router', pod_report)
+ registry_check_value = self.compare_ip('registry', pod_report)
+ print router_check_value, registry_check_value
+
+ ms.add_metric({'openshift.router.pod.location': router_check_value[0]})
+ ms.add_metric({'openshift.router.pod.status': router_check_value[1]})
+ ms.add_metric({'openshift.registry.pod.location': registry_check_value[0]})
+ ms.add_metric({'openshift.registry.pod.status': registry_check_value[1]})
+ ms.send_metrics()
+
+if __name__ == '__main__':
+ INPS = InfraNodePodStatus()
+ INPS.run()

repo: openshift/openshift-tools

original_message: added the check for the internal pod


message:
Add OpenShift master audit config role.
Configures the settings in auditConfig section of master-config.yaml.
Variables left unset indicates property should be removed if present, we
assume that if calling this role, you intend to manage that section of
config and have passed appropriate vars.

diff:
+openshift_master_audit
+=========
+
+Ansible role for configuring the audit capabilities on OpenShift masters.
+
+Optional parameters not defined will be removed from master-config.yaml if
+present.
+
+https://docs.openshift.org/latest/install_config/master_node_configuration.html#master-node-config-audit-config
+
+Requirements
+------------
+
+Ansible Modules:
+
+- tools_roles/lib_openshift_3.2
+- tools_roles/lib_yaml_editor
+
+
+Role Variables
+--------------
+
+### omac_enabled
+
+Enable/disable the OpenShift master audit log.
+
+Default: `False`
+
+### omac_auditConfig_auditFilePath
+
+File path where the requests should be logged to. If not set, logs will be printed to master logs.
+
+### omac_auditConfig_maximumFileRetentionDays
+
+Specifies maximum number of days to retain old audit log files based on the timestamp encoded in their filename.
+
+### omac_auditConfig_maximumRetainedFiles
+
+Specifies Maximum number of old audit log files to retain.
+
+### omac_auditConfig_maximumFileSizeMegabytes
+
+Specifies maximum size in megabytes of the log file before it gets rotated.
+
+Dependencies
+------------
+
+
+Example Playbook
+----------------
+ - role: tools_roles/openshift_master_audit
+ omac_auditConfig_enabled: False
+ omac_auditConfig_auditFilePath: "/var/log/openshift-master-audit.log"
+ omac_auditConfig_maximumFileRetentionDays: 30
+ omac_auditConfig_maximumRetainedFiles: 30
+ omac_auditConfig_maximumFileSizeMegabytes: 100
+
+License
+-------
+
+Apache 2.0
+
+Author Information
+------------------
+
+Openshift Operations

diff:
+---
+omac_auditConfig_enabled: False

diff:
+---
+- name: restart openshift master services
+ service:
+ name: "{{ item[1] }}"
+ state: restarted
+ delegate_to: "{{ item[0] }}"
+ with_nested:
+ - "{{ ansible_play_hosts }}"
+ - [ 'atomic-openshift-master-api', 'atomic-openshift-master-controllers' ]
+ run_once: true
+

diff:
+---
+galaxy_info:
+ author: OpenShift Ops
+ description: Openshift Operations Master Audit Config
+ company: Red Hat, Inc
+ license: ASL 2.0
+ min_ansible_version: 1.2
+ platforms:
+ - name: EL
+ versions:
+ - 7
+dependencies:
+- role: tools_roles/lib_openshift_3.2
+- role: tools_roles/lib_yaml_editor

diff:
+---
+- name: "auditConfig.enabled"
+ yedit:
+ src: /etc/origin/master/master-config.yaml
+ key: auditConfig.enabled
+ value: "{{ omac_auditConfig_enabled }}"
+ notify: restart openshift master services
+
+- name: "deploy master audit config options"
+ yedit:
+ src: /etc/origin/master/master-config.yaml
+ key: "{{ item.key }}"
+ value: "{{ item.value }}"
+ state: "{{ 'present' if item.value != '' else 'absent' }}"
+ notify: restart openshift master services
+ with_items:
+ - key: auditConfig.auditFilePath
+ value: "{{ omac_auditConfig_auditFilePath | default('') }}"
+ - key: auditConfig.maximumFileRetentionDays
+ value: "{{ omac_auditConfig_maximumFileRetentionDays | default('') }}"
+ - key: auditConfig.maximumRetainedFiles
+ value: "{{ omac_auditConfig_maximumRetainedFiles | default('') }}"
+ - key: auditConfig.maximumFileSizeMegabytes
+ value: "{{ omac_auditConfig_maximumFileSizeMegabytes | default('') }}"
+


message: Symlink version specific upgrade filter/lookup plugins when vendoring rpms.

diff:
- [ 'filter_plugins', 'lookup_plugins' ]
- [ 'openshift-cluster', 'openshift-master', 'openshift-node']
+ # Each OpenShift release ships with 1-2 supported upgrade paths in a
+ # version specific directory like "v3_4". Search for anything that looks like
+ # one, and create the required symlinks within it.
+ - name: Lookup versioned upgrade directories
+ find:
+ paths: "{{ vendored_dir }}/playbooks/byo/openshift-cluster/upgrades/"
+ patterns: "v3_*"
+ file_type: directory
+ register: upgrade_versions
+
+ - fail:
+ msg: "No upgrade directories found."
+ when: upgrade_versions.files | length == 0
+
+ - name: Symlink the filter and lookup plugins (no longer shipped with rpm) for byo/openshift-cluster/upgrades
+ file:
+ state: link
+ src: "../../../../../{{ item[0] }}"
+ dest: "{{ vendored_dir }}/playbooks/byo/openshift-cluster/upgrades/{{ item[1].path | basename }}/{{ item[0] }}"
+ with_nested:
+ - [ 'filter_plugins', 'lookup_plugins' ]
+ - "{{ upgrade_versions.files }}"
+
- name: Symlink the openshift version to the installer
file:
state: link


message: Add symlinks for OpenShift versioned upgrades.

diff:
+../../../../../filter_plugins
\ No newline at end of file

diff:
+../../../../../lookup_plugins
\ No newline at end of file


message: Automatic commit of package [openshift-tools-scripts] release [0.1.25-1].

diff:
Summary: OpenShift Tools Scripts
Name: openshift-tools-scripts
-Version: 0.1.24
+Version: 0.1.25
Release: 1%{?dist}
License: ASL 2.0
URL: https://github.com/openshift/openshift-tools
@@ -380,6 +380,9 @@ OpenShift Tools IAM specific scripts
%{python_sitelib}/openshift_tools/saml_aws_creds*
%changelog
+* Wed Feb 08 2017 zhiwliu <zhiwliu@redhat.com> 0.1.25-1
+- added the check for the internal pod (zhiwliu@redhat.com)
+
* Tue Jan 31 2017 Ivan Horvath <ihorvath@redhat.com> 0.1.24-1
- Adding 'unknown' build state to the count script (bmorriso@redhat.com)
- Fix docker oc version script (zgalor@redhat.com)


message: Automatic commit of package [openshift-tools-scripts] release [0.1.27-1].

diff:
Summary: OpenShift Tools Scripts
Name: openshift-tools-scripts
-Version: 0.1.26
+Version: 0.1.27
Release: 1%{?dist}
License: ASL 2.0
URL: https://github.com/openshift/openshift-tools
@@ -380,6 +380,9 @@ OpenShift Tools IAM specific scripts
%{python_sitelib}/openshift_tools/saml_aws_creds*
%changelog
+* Wed Feb 08 2017 zhiwliu <zhiwliu@redhat.com> 0.1.27-1
+-
+
* Wed Feb 08 2017 Drew Anderson <dranders@redhat.com> 0.1.26-1
- Automatic commit of package [openshift-tools-scripts] release [0.1.25-1].
(zhiwliu@redhat.com)


message: changed cron-send-elb-status just for aws cluster

diff:
@@ -192,7 +192,7 @@ host_monitoring_cron:
{# end if dnsmasq #}
{% endif %}
-{% if osohm_host_type == 'master' or osohm_host_type == 'infra' %}
+{% if osohm_host_type == 'master' or osohm_host_type == 'infra' and osohm_cloud == 'aws' %}
- name: send ELB status
minute: "*/15"
job: ops-runner -f -s 60 -n cses.openshift.aws.elbd.status /usr/bin/cron-send-elb-status


message: add the brackets for monitoring-config.yml.j2

diff:
@@ -192,7 +192,7 @@ host_monitoring_cron:
{# end if dnsmasq #}
{% endif %}
-{% if osohm_host_type == 'master' or osohm_host_type == 'infra' and osohm_cloud == 'aws' %}
+{% if ( osohm_host_type == 'master' or osohm_host_type == 'infra' ) and osohm_cloud == 'aws' %}
- name: send ELB status
minute: "*/15"
job: ops-runner -f -s 60 -n cses.openshift.aws.elbd.status /usr/bin/cron-send-elb-status


message: added cron-send-internal-pods-check.py

diff:
@@ -53,6 +53,7 @@ cp -p monitoring/cron-send-os-skydns-checks.py %{buildroot}/usr/bin/cron-send-os
cp -p monitoring/cron-send-os-dnsmasq-checks.py %{buildroot}/usr/bin/cron-send-os-dnsmasq-checks
cp -p monitoring/cron-fix-ovs-rules.py %{buildroot}/usr/bin/cron-fix-ovs-rules
cp -p monitoring/cron-send-create-app.py %{buildroot}/usr/bin/cron-send-create-app
+cp -p monitoring/cron-send-internal-pods-check.py %{buildroot}/usr/bin/cron-send-internal-pods-check
cp -p monitoring/cron-send-usage-pv.py %{buildroot}/usr/bin/cron-send-usage-pv
cp -p monitoring/cron-send-project-stats.py %{buildroot}/usr/bin/cron-send-project-stats
cp -p monitoring/cron-openshift-pruner.py %{buildroot}/usr/bin/cron-openshift-pruner
@@ -288,6 +289,7 @@ OpenShift Tools Openshift Product Scripts
/usr/bin/cron-send-etcd-status
/usr/bin/cron-send-os-master-metrics
/usr/bin/cron-send-create-app
+/usr/bin/cron-send-internal-pods-check
/usr/bin/cron-send-usage-pv
/usr/bin/cron-send-project-stats
/usr/bin/cron-send-os-dnsmasq-checks

original_message: added cron-send-internal-pods-check.py


message:
Automatic commit of package [openshift-tools-scripts] release [0.1.30-1].
Created by command:
/usr/bin/tito tag

diff:
Summary: OpenShift Tools Scripts
Name: openshift-tools-scripts
-Version: 0.1.29
+Version: 0.1.30
Release: 1%{?dist}
License: ASL 2.0
URL: https://github.com/openshift/openshift-tools
@@ -382,6 +382,13 @@ OpenShift Tools IAM specific scripts
%{python_sitelib}/openshift_tools/saml_aws_creds*
%changelog
+* Tue Feb 14 2017 zhiwliu <zhiwliu@redhat.com> 0.1.30-1
+- added cron-send-internal-pods-check.py (zhiwliu@redhat.com)
+- testing bot status check (dedgar@redhat.com)
+- adding pylint disable (dedgar@redhat.com)
+- ossh local helper (dranders@redhat.com)
+- adding stale credential entry removal option (dedgar@redhat.com)
+
* Thu Feb 09 2017 Zhiming Zhang <zhizhang@redhat.com> 0.1.29-1
- change_iam_password: Capture a few of the common expected exceptions
(joesmith@redhat.com)


message:
Automatic commit of package [python-openshift-tools] release [0.0.103-1].
Created by command:
/usr/bin/tito tag

diff:
Summary: OpenShift Tools Python Package
Name: python-openshift-tools
-Version: 0.0.102
+Version: 0.0.103
Release: 1%{?dist}
License: ASL 2.0
URL: https://github.com/openshift/openshift-tools
@@ -297,6 +297,10 @@ Adds GCP specific python modules
%{python_sitelib}/openshift_tools/cloud/gcp/*.py[co]
%changelog
+* Wed Feb 15 2017 zhiwliu <zhiwliu@redhat.com> 0.0.103-1
+- Translate metrics with key "heartbeat.ping" to Hawkular Availability Metrics
+ (zgalor@redhat.com)
+
* Thu Jan 19 2017 Ivan Horvath <ihorvath@redhat.com> 0.0.102-1
- use metric_sender.yaml as default config file for zagg_sender
(zgalor@redhat.com)

old_path: rel-eng/packages/python-openshift-tools

new_path: rel-eng/packages/python-openshift-tools

diff:
-0.0.102-1 openshift_tools/
+0.0.103-1 openshift_tools/


message: update the README.md for local ossh

diff:
@@ -10,15 +10,21 @@ A helper to make parts of ossh work locally
* git clone to your local disk
* add to bashrc:
```
-# ~/.bashrc OSSH helper
+# ~/.bashrc OSSH helper, /path/to/project means where you put git/openshift-tools/scripts/local-ops/ossh-local-helper
export OSSH_HELPER_BASEDIR=/path/to/project
+# setup your remote host(tower) user, usually it's your kerberos username
+export myUser=$kerberos_name
+
+# setup remote host, since it's for v3, so it's tower
+export bastion=tower.ops.rhcloud.com
+
# -v is optional
# --target-host is intentionally blank as it will take the very next argument as target-host
-alias ossh='${OSSH_HELPER_BASEDIR}/ossh.py3 -v --bastion-user myUser --bastion-host bastion.ops.example.com --target-user root --target-host'
+alias ossh="${OSSH_HELPER_BASEDIR}/ossh.py3 -v --bastion-user $myUser --bastion-host $bastion --target-user root --target-host'
# required for OSSH_HELPER_CACHE
source ${OSSH_HELPER_BASEDIR}/ossh.bashrc
-export OSSH_HELPER_BASTION=bastion.ops.example.com
+export OSSH_HELPER_BASTION=$bastion
export OSSH_HELPER_CACHE=${OSSH_HELPER_BASEDIR}/ossh-list.bash
```

original_message: update the README.md for local ossh


message:
Carry restart hosts fix from upstream until next vendoring.
This is commit in
openshift-ansible.
It has been merged and will therefore be picked up next time we vendor
in a new version.

diff:
ignore_errors: true
become: yes
+# WARNING: This process is riddled with weird behavior.
+
+# Workaround for https://github.com/ansible/ansible/issues/21269
+- set_fact:
+ wait_for_host: "{{ ansible_host }}"
+
+# Ansible's blog documents this *without* the port, which appears to now
+# just wait until the timeout value and then proceed without checking anything.
+# port is now required.
+#
+# However neither ansible_ssh_port or ansible_port are reliably defined, likely
+# only if overridden. Assume a default of 22.
- name: Wait for master to restart
local_action:
module: wait_for
- host="{{ ansible_host }}"
+ host="{{ wait_for_host }}"
state=started
delay=10
timeout=600
- port="{{ ansible_ssh_port }}"
+ port="{{ ansible_port | default(ansible_ssh_port | default(22,boolean=True),boolean=True) }}"
become: no
# Now that ssh is back up we can wait for API on the remote system,
state: started
delay: 10
port: "{{ openshift.master.api_port }}"
+

original_message:
Carry restart hosts fix from upstream until next vendoring.

This is commit 781d2a1dc87bdc37f02ea6f1a3e83abb666f9c49 in
openshift-ansible.

It has been merged and will therefore be picked up next time we vendor
in a new version.


message:
Add a git fetch module.
Assumes the repository is already checked out, and the remote exists,
otherwise we consider this an error.
If nothing is fetched, we return no change.

diff:
+# pylint: skip-file
+
+def main():
+ '''
+ ansible git module for cloning
+ '''
+ module = AnsibleModule(
+ argument_spec=dict(
+ # TODO: state necessary for this?
+ state=dict(default='present', type='str', choices=['present']),
+ path=dict(default=None, required=True, type='str'),
+ remote=dict(default='origin', required=False, type='str'),
+ ssh_key=dict(default=None, required=False, type='str'),
+ ),
+ supports_check_mode=False,
+ )
+ git = GitFetch(module.params['path'],
+ module.params['remote'],
+ module.params['ssh_key'])
+
+ state = module.params['state']
+
+ if state == 'present':
+ results = git.fetch()
+
+ if results['returncode'] != 0:
+ module.fail_json(msg=results)
+
+ if results['no_fetch_needed'] == True:
+ module.exit_json(changed=False, results=results, state="present")
+
+ module.exit_json(changed=True, results=results, state="present")
+
+ module.exit_json(failed=True,
+ changed=False,
+ results='Unknown state passed. %s' % state,
+ state="unknown")
+
+# pylint: disable=redefined-builtin, unused-wildcard-import, wildcard-import, locally-disabled
+# import module snippets. This are required
+if __name__ == '__main__':
+ from ansible.module_utils.basic import *
+ main()

diff:
@@ -53,6 +53,11 @@ FILES = {'git_commit.py': ['lib/ssh_agent.py',
'src/git_clone.py',
'ansible/git_clone.py',
],
+ 'git_fetch.py': ['lib/ssh_agent.py',
+ 'lib/base.py',
+ 'src/git_fetch.py',
+ 'ansible/git_fetch.py',
+ ],
}
def main():

diff:
@@ -72,6 +72,17 @@ class GitCLI(object):
return results
+ def _fetch(self, remote):
+ ''' git fetch '''
+
+ cmd = ["fetch"]
+
+ cmd += [remote]
+
+ results = self.git_cmd(cmd, output=True, output_type='raw')
+
+ return results
+
def _status(self, porcelain=False, show_untracked=True):
''' Do a git status '''
@@ -214,15 +225,14 @@ class GitCLI(object):
if err:
rval.update({"err": err,
- "stderr": stderr,
- "stdout": stdout,
"cmd": cmds
})
else:
+ rval.update({"results": {}})
+
+ # Always include stdout/stderr:
rval.update({"stderr": stderr,
- "stdout": stdout,
- "results": {},
- })
+ "stdout": stdout})
return rval

diff:
+# pylint: skip-file
+
+class GitFetch(GitCLI):
+ ''' Class to wrap the git merge line tools '''
+ # pylint: disable=too-many-arguments
+ def __init__(self,
+ path,
+ remote,
+ ssh_key=None):
+ ''' Constructor for GitFetch '''
+ super(GitFetch, self).__init__(path, remote, ssh_key=ssh_key)
+ self.remote = remote
+ self.debug = []
+
+ if not os.path.isdir(self.path):
+ print "Git checkout directory does not exist. Exiting..."
+ sys.exit(1)
+
+ def fetch(self):
+ ''' fetch from the selected remote '''
+
+ os.chdir(self.path)
+
+ fetch_results = self._fetch(self.remote)
+ no_fetch_needed = False
+
+ # TODO: Check for no results
+ if fetch_results['returncode'] != 0:
+ return {'returncode': 1,
+ 'results': fetch_results,
+ 'error_msg': 'Unable to fetch for remote: ' + self.remote,
+ 'no_fetch_needed': False
+ }
+
+ # git fetch returns output to stderr.
+ # Success but no stderr contents implies nothing was fetched.
+ no_fetch_needed = len(fetch_results['stderr']) == 0
+ return {'returncode': 0,
+ 'results': fetch_results,
+ 'no_fetch_needed': no_fetch_needed
+ }
+

diff:
@@ -209,6 +209,17 @@ class GitCLI(object):
return results
+ def _fetch(self, remote):
+ ''' git fetch '''
+
+ cmd = ["fetch"]
+
+ cmd += [remote]
+
+ results = self.git_cmd(cmd, output=True, output_type='raw')
+
+ return results
+
def _status(self, porcelain=False, show_untracked=True):
''' Do a git status '''
@@ -351,16 +362,15 @@ class GitCLI(object):
if err:
rval.update({"err": err,
- "stderr": stderr,
- "stdout": stdout,
"cmd": cmds
})
else:
+ rval.update({"results": {}})
+
+ # Always include stdout/stderr:
rval.update({"stderr": stderr,
- "stdout": stdout,
- "results": {},
- })
+ "stdout": stdout})
return rval

diff:
+#!/usr/bin/env python
+# ___ ___ _ _ ___ ___ _ _____ ___ ___
+# / __| __| \| | __| _ \ /_\_ _| __| \
+# | (_ | _|| .` | _|| / / _ \| | | _|| |) |
+# \___|___|_|\_|___|_|_\/_/_\_\_|_|___|___/_ _____
+# | \ / _ \ | \| |/ _ \_ _| | __| \_ _|_ _|
+# | |) | (_) | | .` | (_) || | | _|| |) | | | |
+# |___/ \___/ |_|\_|\___/ |_| |___|___/___| |_|
+"""Run an ssh agent and set SSH_AUTH_SOCK so that clients will use it
+
+Example:
+ with ssh_agent.SshAgent() as agent:
+ agent.add_key(private_key_string)
+ # do ssh stuff
+ # as agent loses scope, the ssh agent is killed
+"""
+
+from __future__ import with_statement
+import atexit
+import tempfile
+import os
+import sys
+import shutil
+import subprocess
+import random
+import time
+import datetime
+
+class SshAgentException(Exception):
+ """An exception thrown for problems in SshAgent
+ """
+ def __init__(self, message):
+ # Call the base class constructor with the parameters it needs
+ super(SshAgentException, self).__init__(message)
+
+class SshAgent(object):
+ """Run an ssh agent and set SSH_AUTH_SOCK so that clients will use it.
+
+ The running agent can have one or more keys added (via the SshAgent.add_key()
+ method or via any other method that can find and talk to the running agent.
+ """
+
+ class Cleanup(object):
+ """A helper functor class for SshAgent
+
+ An object of this class can be passed
+ directly to atexit, which will call __call__() when the
+ program exits
+ """
+ def __init__(self, ssh_agent, ssh_auth_sock_dir):
+ self.ssh_agent = ssh_agent
+ self.ssh_auth_sock_dir = ssh_auth_sock_dir
+ self.cleaned_up = False
+ self.original_env_var = os.environ.get('SSH_AUTH_SOCK')
+ def __call__(self):
+ if self.cleaned_up:
+ return
+ self.cleaned_up = True
+ try:
+ shutil.rmtree(self.ssh_auth_sock_dir, ignore_errors=True)
+ except OSError:
+ pass
+ try:
+ self.ssh_agent.kill()
+ except OSError:
+ pass
+ if self.original_env_var:
+ os.environ['SSH_AUTH_SOCK'] = self.original_env_var
+ else:
+ del os.environ['SSH_AUTH_SOCK']
+ def pass_(self):
+ """A function to appease pylint"""
+ pass
+ def pass__(self):
+ """Another function to appease pylint"""
+ self.pass_()
+ def __init__(self):
+ devnull = open(os.devnull, 'w')
+ # Start an ssh-agent process and register it to be killed atexit
+ self.ssh_auth_sock_dir = tempfile.mkdtemp(prefix=os.path.basename(sys.argv[0]) + '.')
+ self.ssh_auth_sock = os.path.join(self.ssh_auth_sock_dir, "ssh_agent")
+ self.ssh_agent = subprocess.Popen(["ssh-agent", "-d", "-a", self.ssh_auth_sock], stdout=devnull, stderr=devnull)
+ self.cleanup = self.Cleanup(self.ssh_agent, self.ssh_auth_sock_dir)
+ # this is here so that when python exits, we make sure that the agent is killed
+ # (in case python exits before our __del__() is called
+ atexit.register(self.cleanup)
+ os.environ["SSH_AUTH_SOCK"] = self.ssh_auth_sock
+ def __enter__(self):
+ return self
+ def __exit__(self, exc_type, exc_value, tback):
+ self.cleanup()
+ def __del__(self):
+ self.cleanup()
+
+ def kill(self):
+ '''Explicitly kill the running ssh-agent
+
+ It's not necessary to call this function as the agent
+ will be cleaned up automatically.
+ '''
+ self.cleanup()
+
+ def add_key(self, key):
+ """Add a key to the running agent.
+
+ Note:
+ This function can be called any number of times to add multiple keys.
+
+ Args:
+ key (str): A string containing the ssh private key to be added (the
+ actual key data, not the filename of a key)
+ Raises:
+ SshAgentException: when ssh-add does not immediately return (as in the
+ case of a private key with a passphrase)
+ """
+ #if self.ssh_agent.poll() is None:
+ # raise SshAgentException("Unable to add ssh key. Did agent die?")
+ named_pipe_path = os.path.join(self.ssh_auth_sock_dir, "keypipe." + str(random.getrandbits(64)))
+ try:
+ os.mkfifo(named_pipe_path, 0600)
+ except OSError, exception:
+ print "Failed to create FIFO: %s" % exception
+ devnull = open(os.devnull, 'w')
+ ssh_add = subprocess.Popen(["ssh-add", named_pipe_path], stdout=devnull, stderr=devnull)
+ fifo = open(named_pipe_path, 'w')
+ print >> fifo, key
+ fifo.close()
+ #Popen.wait() doesn't have a timeout, so we'll implement one using poll() :(
+ start_time = datetime.datetime.now()
+ while ssh_add.poll() is None:
+ if (datetime.datetime.now() - start_time).total_seconds() > 5:
+ try:
+ ssh_add.kill()
+ except OSError:
+ pass
+ raise SshAgentException("Unable to add ssh key. Timed out. Does key have a passphrase?")
+ time.sleep(0.1)
+ os.remove(named_pipe_path)
+# pylint: disable=too-many-lines
+
+# these are already imported inside of the ssh library
+#import os
+#import subprocess
+
+class GitCLIError(Exception):
+ '''Exception class for openshiftcli'''
+ pass
+
+# pylint: disable=too-few-public-methods
+class GitCLI(object):
+ ''' Class to wrap the command line tools '''
+ def __init__(self,
+ path,
+ verbose=False,
+ ssh_key=None,
+ author=None):
+ ''' Constructor for GitCLI '''
+ self.path = path
+ self.verbose = verbose
+ self.ssh_key = ssh_key
+ self.author = author
+ self.environment_vars = os.environ.copy()
+
+ if self.author:
+ author_dict = {}
+ author_list = author.split('<')
+ author_dict['GIT_COMMITTER_NAME'] = author_list[0].strip()
+ author_dict['GIT_COMMITTER_EMAIL'] = author_list[0].strip()
+
+ self.environment_vars.update(author_dict)
+
+ def _add(self, files_to_add=None):
+ ''' git add '''
+
+ cmd = ["add", "--no-ignore-removal"]
+
+ if files_to_add:
+ cmd.extend(files_to_add)
+ else:
+ cmd.append('.')
+
+ results = self.git_cmd(cmd)
+
+ return results
+
+ def _commit(self, msg, author=None):
+ ''' git commit with message '''
+
+ cmd = ["commit", "-m", msg]
+
+ if author:
+ cmd += ["--author", author]
+
+ results = self.git_cmd(cmd)
+
+ return results
+
+ def _clone(self, repo, dest, bare=False):
+ ''' git clone '''
+
+ cmd = ["clone"]
+
+ if bare:
+ cmd += ["--bare"]
+
+ cmd += [repo, dest]
+
+ results = self.git_cmd(cmd)
+
+ return results
+
+ def _fetch(self, remote):
+ ''' git fetch '''
+
+ cmd = ["fetch"]
+
+ cmd += [remote]
+
+ results = self.git_cmd(cmd, output=True, output_type='raw')
+
+ return results
+
+ def _status(self, porcelain=False, show_untracked=True):
+ ''' Do a git status '''
+
+ cmd = ["status"]
+ if porcelain:
+ cmd.append('--porcelain')
+
+ if show_untracked:
+ cmd.append('--untracked-files=normal')
+ else:
+ cmd.append('--untracked-files=no')
+
+ results = self.git_cmd(cmd, output=True, output_type='raw')
+
+ return results
+
+ def _checkout(self, branch):
+ ''' Do a git checkout to <branch> '''
+
+ cmd = ["checkout", branch]
+ results = self.git_cmd(cmd, output=True, output_type='raw')
+
+ return results
+
+ def _get_current_branch(self):
+ ''' Do a git checkout to <branch> '''
+
+ cmd = ["describe", "--contains", "--all", "HEAD"]
+ results = self.git_cmd(cmd, output=True, output_type='raw')
+ results['results'] = results['results'].rstrip()
+
+ return results
+
+ def _merge(self, merge_id):
+ ''' Do a git checkout to <branch> '''
+
+ cmd = ["merge", merge_id]
+ results = self.git_cmd(cmd, output=True, output_type='raw')
+
+ return results
+
+ def _push(self, remote, src_branch, dest_branch):
+ ''' Do a git checkout to <branch> '''
+
+ push_branches = src_branch + ":" + dest_branch
+
+ cmd = ["push", remote, push_branches]
+ results = self.git_cmd(cmd, output=True, output_type='raw')
+
+ return results
+
+ def _remote_update(self):
+ ''' Do a git remote update '''
+
+ cmd = ["remote", "update"]
+ results = self.git_cmd(cmd, output=True, output_type='raw')
+
+ return results
+
+ def _diff(self, diff_branch):
+ ''' Do a git diff diff_branch'''
+
+ cmd = ["diff", diff_branch]
+ results = self.git_cmd(cmd, output=True, output_type='raw')
+
+ return results
+
+ def _rebase(self, rebase_branch):
+ ''' Do a git rebase rebase_branch'''
+
+ cmd = ["rebase", rebase_branch]
+ results = self.git_cmd(cmd, output=True, output_type='raw')
+
+ return results
+
+ def _config(self, get_args):
+ ''' Do a git config --get <get_args> '''
+
+ cmd = ["config", '--get', get_args]
+ results = self.git_cmd(cmd, output=True, output_type='raw')
+
+ return results
+
+ def git_cmd(self, cmd, output=False, output_type='json'):
+ '''Base command for git '''
+ cmds = ['/usr/bin/git']
+
+ cmds.extend(cmd)
+
+ rval = {}
+ results = ''
+ err = None
+
+ if self.verbose:
+ print ' '.join(cmds)
+
+ if self.ssh_key:
+ with SshAgent() as agent:
+ self.environment_vars['SSH_AUTH_SOCK'] = os.environ['SSH_AUTH_SOCK']
+ agent.add_key(self.ssh_key)
+
+ proc = subprocess.Popen(cmds,
+ stdout=subprocess.PIPE,
+ stderr=subprocess.PIPE,
+ env=self.environment_vars)
+
+ stdout, stderr = proc.communicate()
+
+ rval = {"returncode": proc.returncode,
+ "results": results,
+ "cmd": ' '.join(cmds),
+ }
+ else:
+ proc = subprocess.Popen(cmds,
+ stdout=subprocess.PIPE,
+ stderr=subprocess.PIPE,
+ env=self.environment_vars)
+
+ stdout, stderr = proc.communicate()
+ rval = {"returncode": proc.returncode,
+ "results": results,
+ "cmd": ' '.join(cmds),
+ }
+
+
+ if proc.returncode == 0:
+ if output:
+ if output_type == 'json':
+ try:
+ rval['results'] = json.loads(stdout)
+ except ValueError as err:
+ if "No JSON object could be decoded" in err.message:
+ err = err.message
+ elif output_type == 'raw':
+ rval['results'] = stdout
+
+ if self.verbose:
+ print stdout
+ print stderr
+
+ if err:
+ rval.update({"err": err,
+ "cmd": cmds
+ })
+
+ else:
+ rval.update({"results": {}})
+
+ # Always include stdout/stderr:
+ rval.update({"stderr": stderr,
+ "stdout": stdout})
+
+ return rval
+
+class GitFetch(GitCLI):
+ ''' Class to wrap the git merge line tools '''
+ # pylint: disable=too-many-arguments
+ def __init__(self,
+ path,
+ remote,
+ ssh_key=None):
+ ''' Constructor for GitFetch '''
+ super(GitFetch, self).__init__(path, remote, ssh_key=ssh_key)
+ self.remote = remote
+ self.debug = []
+
+ if not os.path.isdir(self.path):
+ print "Git checkout directory does not exist. Exiting..."
+ sys.exit(1)
+
+ def fetch(self):
+ ''' fetch from the selected remote '''
+
+ os.chdir(self.path)
+
+ fetch_results = self._fetch(self.remote)
+ no_fetch_needed = False
+
+ # TODO: Check for no results
+ if fetch_results['returncode'] != 0:
+ return {'returncode': 1,
+ 'results': fetch_results,
+ 'error_msg': 'Unable to fetch for remote: ' + self.remote,
+ 'no_fetch_needed': False
+ }
+
+ # git fetch returns output to stderr.
+ # Success but no stderr contents implies nothing was fetched.
+ no_fetch_needed = len(fetch_results['stderr']) == 0
+ return {'returncode': 0,
+ 'results': fetch_results,
+ 'no_fetch_needed': no_fetch_needed
+ }
+
+
+def main():
+ '''
+ ansible git module for cloning
+ '''
+ module = AnsibleModule(
+ argument_spec=dict(
+ # TODO: state necessary for this?
+ state=dict(default='present', type='str', choices=['present']),
+ path=dict(default=None, required=True, type='str'),
+ remote=dict(default='origin', required=False, type='str'),
+ ssh_key=dict(default=None, required=False, type='str'),
+ ),
+ supports_check_mode=False,
+ )
+ git = GitFetch(module.params['path'],
+ module.params['remote'],
+ module.params['ssh_key'])
+
+ state = module.params['state']
+
+ if state == 'present':
+ results = git.fetch()
+
+ if results['returncode'] != 0:
+ module.fail_json(msg=results)
+
+ if results['no_fetch_needed'] == True:
+ module.exit_json(changed=False, results=results, state="present")
+
+ module.exit_json(changed=True, results=results, state="present")
+
+ module.exit_json(failed=True,
+ changed=False,
+ results='Unknown state passed. %s' % state,
+ state="unknown")
+
+# pylint: disable=redefined-builtin, unused-wildcard-import, wildcard-import, locally-disabled
+# import module snippets. This are required
+if __name__ == '__main__':
+ from ansible.module_utils.basic import *
+ main()


message: add key for internal pods check

diff:
@@ -106,6 +106,30 @@ g_template_openshift_master:
applications:
- Openshift Master
+ - key: openshift.router.pod.location
+ description: "check the openshift router pod location"
+ value_type: int
+ applications:
+ - Openshift Master
+
+ - key: openshift.router.pod.status
+ description: "check the openshift router pod status"
+ value_type: int
+ applications:
+ - Openshift Master
+
+ - key: openshift.registry.pod.location
+ description: "check the openshift registry pod location"
+ value_type: int
+ applications:
+ - Openshift Master
+
+ - key: openshift.registry.pod.status
+ description: "check the openshift registry pod status"
+ value_type: int
+ applications:
+ - Openshift Master
+
- key: openshift.master.pv.percent.usage
description: "check the openshift pv usage"
value_type: int
@@ -844,6 +868,26 @@ g_template_openshift_master:
description: The application create loop has failed 4 or more times in the last hour
priority: high
+ - name: "openshift router pods are in the same infra node on {HOST.NAME}"
+ expression: "{Template Openshift Master:openshift.router.pod.location.last(#1)}=0"
+ url: "https://github.com/openshift/ops-sop/blob/master/V3/Alerts/check_internal_pod.asciidoc"
+ priority: avg
+
+ - name: "openshift registry pods are in the same infra node on {HOST.NAME}"
+ expression: "{Template Openshift Master:openshift.registry.pod.location.last(#1)}=0"
+ url: "https://github.com/openshift/ops-sop/blob/master/V3/Alerts/check_internal_pod.asciidoc"
+ priority: avg
+
+ - name: "openshift router pods are in bad status on {HOST.NAME}"
+ expression: "{Template Openshift Master:openshift.router.pod.status.last(#1)}<2"
+ url: "https://github.com/openshift/ops-sop/blob/master/V3/Alerts/check_internal_pod.asciidoc"
+ priority: avg
+
+ - name: "openshift registry pods are in bad status on {HOST.NAME}"
+ expression: "{Template Openshift Master:openshift.registry.pod.status.last(#1)}<2"
+ url: "https://github.com/openshift/ops-sop/blob/master/V3/Alerts/check_internal_pod.asciidoc"
+ priority: avg
+
- name: "Openshift Master API health check is failing on {HOST.NAME}"
expression: "{Template Openshift Master:openshift.master.api.healthz.max(#3)}<1"
url: "https://github.com/openshift/ops-sop/blob/master/V3/Alerts/openshift_master.asciidoc"

original_message: add key for internal pods check


message:
Properly wait for metrics deploy to complete.
Includes some fixes for logging as well.

diff:
kind: pods
selector: logging-infra=deployer
register: podout
- until: podout.results.results[0]['items'][0].status.phase == 'Succeeded'
+ until: podout.results.results[0]['items'][0].status.phase in ['Succeeded', 'Failed']
retries: 36
delay: 5
run_once: true
-- name: get deployer pod status
- oc_obj:
- state: list
- namespace: logging
- kind: pods
- selector: logging-infra=deployer
- register: podout
- run_once: true
-
- fail:
msg: logging deployer failed to complete setup
when: podout.results.results[0]['items'][0].status.phase != 'Succeeded'
run_once: true
- debug: var=pvcout
-- name: wait until logging deployer pod has completed
+- name: wait until logging pvcs are bound completed
oc_obj:
state: list
namespace: logging

diff:
register: processout
- debug: var=processout
-- name: wait for deployment to finish
- pause:
- seconds: 240
+# wait up to 10 minutes for deployer pod to complete
+- name: wait until metrics deployer pod has completed
+ oc_obj:
+ state: list
+ namespace: openshift-infra
+ kind: pods
+ selector: metrics-infra=deployer
+ register: podout
+ until: podout.results.results[0]['items'][0].status.phase in ['Succeeded', 'Failed']
+ retries: 120
+ delay: 5
+ run_once: true
+
+- fail:
+ msg: metrics deployer failed to complete setup
+ when: podout.results.results[0]['items'][0].status.phase != 'Succeeded'
+ run_once: true
- name: Add the "view" role to system:serviceaccount:openshift-infra:hawkular
oadm_policy_user:


message: added the -t for ossh.py3 when need login monitoring container

diff:
@@ -93,6 +93,7 @@ def main():
show_verbose()
if len(args.arguments) > 0:
if "mon" in args.arguments[0]:
+ sshcmd.insert(1, '-t')
sshcmd.append('/usr/bin/bash -c "echo \"%s\"; docker exec -it oso-rhel7-host-monitoring bash"' % args.target_host)
subprocess.call(shlex.split(" ".join(sshcmd)))
else:


message: fixed the verbose output issue for ossh.py3

diff:
@@ -81,7 +81,8 @@ sshcmd = [
]
def show_verbose():
- if '-v'in args.arguments:
+ #if args.verbose:
+ if '-v'in args.arguments or args.verbose:
logger.setLevel(logging.DEBUG)
logger.debug("args:" + repr(args))
logger.debug(" ".join(shlex.split(" ".join(sshcmd))))


message: add cronjob for internal-pods-check

diff:
@@ -357,6 +357,11 @@ host_monitoring_cron:
minute: "*/10"
job: /usr/bin/delete-stuck-projects &>> /var/log/delete-stuck-projects
+- name: Do a quick check for the internal pods status and location every 1 hour
+ minute: "15"
+ hour: "*/1"
+ job: ops-runner -f -s 15 -n csipc.openshift.internal.status /usr/bin/cron-send-internal-pods-check
+
- name: "Prune builds/deployments/images"
hour: "{{ osohm_pruning.cron.hour }}"
minute: "{{ osohm_pruning.cron.minute }}"

original_message: add cronjob for internal-pods-check


message: update monitoring-config.yml.j2 without hour specification

diff:
@@ -359,7 +359,6 @@ host_monitoring_cron:
- name: Do a quick check for the internal pods status and location every 1 hour
minute: "15"
- hour: "*/1"
job: ops-runner -f -s 15 -n csipc.openshift.internal.status /usr/bin/cron-send-internal-pods-check
- name: "Prune builds/deployments/images"


message: Add view role to hawkular SA before launching metrics deployer.

diff:
- "/usr/share/ansible/openshift-ansible/roles/openshift_hosted_templates/files/v{{ kube_version }}/enterprise/metrics-deployer.yaml"
register: templateout
+- name: Add the "view" role to system:serviceaccount:openshift-infra:hawkular
+ oadm_policy_user:
+ namespace: openshift-infra
+ user: system:serviceaccount:openshift-infra:hawkular
+ resource_kind: role
+ resource_name: view
+ register: policyout
+- debug: var=policyout
+
- name: create application using metrics deployer template
oc_process:
namespace: openshift-infra
when: podout.results.results[0]['items'][0].status.phase != 'Succeeded'
run_once: true
-- name: Add the "view" role to system:serviceaccount:openshift-infra:hawkular
- oadm_policy_user:
- namespace: openshift-infra
- user: system:serviceaccount:openshift-infra:hawkular
- resource_kind: role
- resource_name: view
- register: policyout
-- debug: var=policyout
-
- name: scale down cassandra to 0
oc_scale:
name: "hawkular-cassandra-{{ item }}"


message: Start specifying v3.4 for the metrics image version.

diff:
@@ -6,3 +6,4 @@ osamet_hawkular_limits_memory: 3G
osamet_hawkular_requests_memory: 2G
osamet_heapster_limits_memory: 3.75G
osamet_heapster_requests_memory: 0.9375G
+osamet_image_version: "v3.4"

diff:
CASSANDRA_PV_SIZE: "{{ osamet_pv_size }}"
CASSANDRA_NODES: "{{ osamet_cassandra_node }}"
IMAGE_PREFIX: registry.ops.openshift.com/openshift3/
+ IMAGE_VERSION: "{{ osamet_image_version }}"
reconcile: False
register: processout
- debug: var=processout


message: Increase metrics deployer wait to 15 minutes.

diff:
register: processout
- debug: var=processout
-# wait up to 10 minutes for deployer pod to complete
+# wait up to 15 minutes for deployer pod to complete
- name: wait until metrics deployer pod has completed
oc_obj:
state: list
selector: metrics-infra=deployer
register: podout
until: podout.results.results[0]['items'][0].status.phase in ['Succeeded', 'Failed']
- retries: 120
+ retries: 180
delay: 5
run_once: true


message:
Upgrade specific rpm versions.
This is a carried openshift-ansible patch from:
It will be picked up officially on next vendoring.

diff:
---
# We verified latest rpm available is suitable, so just yum update.
-- name: Upgrade packages
- package: "name={{ openshift.common.service_type }}-{{ component }}{{ openshift_pkg_version }} state=present"
+
+# Master package upgrade ends up depending on node and sdn packages, we need to be explicit
+# with all versions to avoid yum from accidentally jumping to something newer than intended:
+- name: Upgrade master packages
+ package: name={{ item }} state=present
+ when: component == "master"
+ with_items:
+ - "{{ openshift.common.service_type }}{{ openshift_pkg_version }}"
+ - "{{ openshift.common.service_type }}-master{{ openshift_pkg_version }}"
+ - "{{ openshift.common.service_type }}-node{{ openshift_pkg_version }}"
+ - "{{ openshift.common.service_type }}-sdn-ovs{{ openshift_pkg_version }}"
+ - "{{ openshift.common.service_type }}-clients{{ openshift_pkg_version }}"
+
+- name: Upgrade node packages
+ package: name={{ item }} state=present
+ when: component == "node"
+ with_items:
+ - "{{ openshift.common.service_type }}{{ openshift_pkg_version }}"
+ - "{{ openshift.common.service_type }}-node{{ openshift_pkg_version }}"
+ - "{{ openshift.common.service_type }}-sdn-ovs{{ openshift_pkg_version }}"
+ - "{{ openshift.common.service_type }}-clients{{ openshift_pkg_version }}"
- name: Ensure python-yaml present for config upgrade
package: name=PyYAML state=present

original_message:
Upgrade specific rpm versions.

This is a carried openshift-ansible patch from:

https://github.com/openshift/openshift-ansible/pull/3737

It will be picked up officially on next vendoring.


message: added cron-send-project-operation.py and make it reading more easily

diff:
+#!/usr/bin/env python
+""" project creation and deletion check for v3 """
+
+import argparse
+import time
+
+import logging
+# We just want to see any exception that happens
+# don't want the script to die under any cicumstances
+# script must try to clean itself up
+# pylint: disable=broad-except
+
+# pylint: disable=invalid-name
+# pylint: disable=import-error
+from openshift_tools.monitoring.ocutil import OCUtil
+from openshift_tools.monitoring.metric_sender import MetricSender
+
+logging.basicConfig(
+ format='%(asctime)s - %(relativeCreated)6d - %(levelname)-8s - %(message)s',
+)
+logger = logging.getLogger()
+logger.setLevel(logging.INFO)
+
+ocutil = OCUtil()
+
+commandDelay = 10 # seconds
+
+def runOCcmd(cmd, base_cmd='oc'):
+ """ log commands through ocutil """
+ logger.info(base_cmd + " " + cmd)
+ oc_time = time.time()
+ oc_result = ocutil.run_user_cmd(cmd, base_cmd=base_cmd, )
+ logger.info("oc command took %s seconds", str(time.time() - oc_time))
+ return oc_result
+
+def parse_args():
+ """ parse the args from the cli """
+ logger.debug("parse_args()")
+
+ parser = argparse.ArgumentParser(description='OpenShift project creation and deletion test')
+ parser.add_argument('-v', '--verbose', action='store_true', default=None, help='Verbose?')
+ parser.add_argument('--namespace', default="ops-project-operation-check",
+ help='namespace (be careful of using existing namespaces)')
+ return parser.parse_args()
+
+def send_metrics(status_code_create, status_code_delete):
+ """ send data to MetricSender"""
+ logger.debug("send_metrics()")
+
+ ms_time = time.time()
+ ms = MetricSender()
+ logger.info("Send data to MetricSender")
+
+ # 1 means create and delete the project failed
+ ms.add_metric({'openshift.master.project.create': status_code_create})
+ ms.add_metric({'openshift.master.project.delete': status_code_delete})
+
+ ms.send_metrics()
+ logger.info("Data sent to Zagg in %s seconds", str(time.time() - ms_time))
+
+def check_project(config):
+ """ check create and delete project """
+ logger.info('check_project()')
+ logger.debug(config)
+
+ project = None
+
+ try:
+ project = runOCcmd("get project {}".format(config.namespace))
+ logger.debug(project)
+ except Exception:
+ pass # don't want exception if project not found
+ if project:
+ project_exist = 1 # project exists
+ else:
+ project_exist = 0 # project doest not exists
+
+ return project_exist
+
+def create_project(config):
+ " create the project "
+ try:
+ runOCcmd("new-project {}".format(config.namespace), base_cmd='oadm')
+ time.sleep(commandDelay)
+ except Exception:
+ logger.exception('error creating new project')
+
+def delete_project(config):
+ " delete the project "
+ try:
+ runOCcmd("delete project {}".format(config.namespace), base_cmd='oc')
+ time.sleep(commandDelay)
+ except Exception:
+ logger.exception('error delete project')
+
+def main():
+ """ check the project operation status """
+ logger.debug("main()")
+ args = parse_args()
+
+ if args.verbose:
+ logger.setLevel(logging.DEBUG)
+
+ ocutil.namespace = args.namespace
+ project_exists = check_project(args)
+ # project does not exists.
+ delete_project_code = 0
+
+ if project_exists == 0:
+ logger.info("project does not exists, going to create it")
+ create_project(args)
+ create_project_code = check_project(args)
+ if create_project_code == 0:
+ # 0 means project creation failed, no project was created
+ logger.info('project creation failed')
+ else:
+ # project creation succeed, then delete the project
+ delete_project(args)
+ delete_project_code = check_project(args)
+ if delete_project_code == 1:
+ # 1 means project deletion failed, the project still exists
+ logger.info('project deletion failed')
+ else:
+ delete_project_code = 0
+ else:
+ # the project already exists, so I think the project creation failed
+ create_project_code = 0
+
+ #logger.info("{} {}".format(create_project_code, delete_project_code))
+ if create_project_code == 1 and delete_project_code == 0:
+ logger.info('creation and deletion succeed, no data was sent to zagg')
+ else:
+ send_metrics(create_project_code, delete_project_code)
+
+if __name__ == "__main__":
+ main()


message: relocate the pylint position, fixed the pylint complain

diff:
#!/usr/bin/env python
""" project creation and deletion check for v3 """
-import argparse
-import time
-
-import logging
# We just want to see any exception that happens
# don't want the script to die under any cicumstances
# script must try to clean itself up
@@ -12,6 +8,10 @@ import logging
# pylint: disable=invalid-name
# pylint: disable=import-error
+import argparse
+import time
+
+import logging
from openshift_tools.monitoring.ocutil import OCUtil
from openshift_tools.monitoring.metric_sender import MetricSender


message:
Temporary fix for openshift_logging failure on es_ops_indices
This was applied in the openshift-ansible release-1.5 branch as
It will be picked up the next
time we vendor. (openshift-ansible-3.5.63-1)

diff:
with_together:
- "{{ openshift_logging_facts.elasticsearch_ops.deploymentconfigs.keys() }}"
- "{{ openshift_logging_facts.elasticsearch_ops.deploymentconfigs.values() }}"
- - "{{ es_ops_indices }}"
+ - "{{ es_ops_indices | default([]) }}"
loop_control:
loop_var: deployment
when:

original_message:
Temporary fix for openshift_logging failure on es_ops_indices

This was applied in the openshift-ansible release-1.5 branch as
c6fdd242fe6b29a680b43b7b65088746de677743. It will be picked up the next
time we vendor. (openshift-ansible-3.5.63-1)


message: add zabbix key for cron-send-project-operation.py

diff:
@@ -252,6 +252,18 @@ g_template_openshift_master:
applications:
- Openshift Cluster
+ - key: openshift.master.project.create
+ description: "check the openshift project create status"
+ value_type: int
+ applications:
+ - Openshift Master
+
+ - key: openshift.master.project.delete
+ description: "check the openshift project delete status"
+ value_type: int
+ applications:
+ - Openshift Master
+
- key: openshift.master.pv.space.total
description: Shows the total space of pv
value_type: int
@@ -917,6 +929,16 @@ g_template_openshift_master:
url: "https://github.com/openshift/ops-sop/blob/master/V3/Alerts/check_internal_pod.asciidoc"
priority: avg
+ - name: "openshift project creation failed on {HOST.NAME}"
+ expression: "{Template Openshift Master:openshift.master.project.create.last(#1)}=0"
+ url: "https://github.com/openshift/ops-sop/blob/master/V3/Alerts/check_create_app.asciidoc"
+ priority: high
+
+ - name: "openshift project deletion failed on {HOST.NAME}"
+ expression: "{Template Openshift Master:openshift.master.project.delete.last(#1)}=1"
+ url: "https://github.com/openshift/ops-sop/blob/master/V3/Alerts/check_create_app.asciidoc"
+ priority: high
+
- name: "Openshift Master API health check is failing on {HOST.NAME}"
expression: "{Template Openshift Master:openshift.master.api.healthz.max(#3)}<1"
url: "https://github.com/openshift/ops-sop/blob/master/V3/Alerts/openshift_master.asciidoc"

diff:
@@ -57,6 +57,7 @@ cp -p monitoring/cron-send-ec2-ebs-volumes-in-stuck-state.py %{buildroot}/usr/bi
cp -p monitoring/cron-send-create-app.py %{buildroot}/usr/bin/cron-send-create-app
cp -p monitoring/cron-send-internal-pods-check.py %{buildroot}/usr/bin/cron-send-internal-pods-check
cp -p monitoring/cron-send-usage-pv.py %{buildroot}/usr/bin/cron-send-usage-pv
+cp -p monitoring/cron-send-project-operation.py %{buildroot}/usr/bin/cron-send-project-operation
cp -p monitoring/cron-send-project-stats.py %{buildroot}/usr/bin/cron-send-project-stats
cp -p monitoring/cron-openshift-pruner.py %{buildroot}/usr/bin/cron-openshift-pruner
cp -p remote-heal/remote-healer.py %{buildroot}/usr/bin/remote-healer
@@ -301,6 +302,7 @@ OpenShift Tools Openshift Product Scripts
/usr/bin/cron-send-create-app
/usr/bin/cron-send-internal-pods-check
/usr/bin/cron-send-usage-pv
+/usr/bin/cron-send-project-operation
/usr/bin/cron-send-project-stats
/usr/bin/cron-send-os-dnsmasq-checks
/usr/bin/cron-send-os-skydns-checks


message: added cron job for /usr/bin/cron-send-project-operation

diff:
@@ -367,6 +367,10 @@ host_monitoring_cron:
minute: "15"
job: ops-runner -f -s 15 -n csipc.openshift.internal.status /usr/bin/cron-send-internal-pods-check
+- name: Do a quick check for the project creation and deletion
+ minute: "*/15"
+ job: ops-runner -f -s 15 -n cspo.openshift.project.status /usr/bin/cron-send-project-operation
+
{% if osohm_pruning.pruning_enabled | default(True) | bool %}
- name: "Prune builds/deployments/images"
hour: "{{ osohm_pruning.cron.hour }}"


message: give a second chance for the deletion of the project operation check

diff:
@@ -119,7 +119,11 @@ def main():
delete_project_code = check_project(args)
if delete_project_code == 1:
# 1 means project deletion failed, the project still exists
- logger.info('project deletion failed')
+ # give the deletion second chance. 10 more seconds to check the
+ # teminating status project
+ delete_project_code = check_project(args)
+ if delete_project_code == 1:
+ logger.info('project deletion failed in 20s')
else:
delete_project_code = 0
else:
@@ -129,7 +133,7 @@ def main():
#logger.info("{} {}".format(create_project_code, delete_project_code))
if create_project_code == 1 and delete_project_code == 0:
logger.info('creation and deletion succeed, no data was sent to zagg')
- else:
+
send_metrics(create_project_code, delete_project_code)
if __name__ == "__main__":