Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

OT API using Brave 4 #14

Merged
merged 17 commits into from
Feb 4, 2017

Conversation

devinsba
Copy link
Member

@devinsba devinsba commented Jan 16, 2017

Move to Brave 4 implementation for backing the OpenTracing API layer

  • BraveTracer
  • BraveSpan
  • BraveSpanBuilder
  • BraveSpanContext
  • JRE 7 compatibility
  • brave package space
  • brave 3 context??
  • Update README
  • More test coverage

...

@devinsba
Copy link
Member Author

@adriancole I've never used retrolambda, can you look at the config to double check?

*
* @return the SpanContext that encapsulates Span state that should propagate across process boundaries.
*/
@Override
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

if the javadoc are copied from the parent, maybe use

/**
 * {@inheritDoc}
 */

pom.xml Outdated
</dependency>
<dependency>
<groupId>io.zipkin.brave</groupId>
<artifactId>brave-http</artifactId>
<version>3.17.0</version>
<version>4.0.3</version>
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

not sure you need this dep anymore

<goal>process-main</goal>
</goals>
<configuration>
<target>${main.java.version}</target>
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

looks good

@codefromthecrypt
Copy link
Contributor

for those reading along, eventually this pull request will look like a cleaned up version of this https://github.com/openzipkin/brave/tree/master/brave/src/test/java/brave/features/opentracing

@felixbarny
Copy link

felixbarny commented Jan 21, 2017

Interesting :)
Will this eventually be included in brave core and possibly become the main API?

@codefromthecrypt
Copy link
Contributor

codefromthecrypt commented Jan 23, 2017 via email

@felixbarny
Copy link

When I originally commended, I thought I was at the /openzipkin/brave repo 😅 . Since then, I rephrased my question. Your response answered it anyway, thx :)

@devinsba
Copy link
Member Author

@adriancole Not sure if its needed or not to add this to the brave3 context / thread binder. I know you want to do a thread context API in brave4, should we use brave3's context until that is worked out?

Copy link
Contributor

@codefromthecrypt codefromthecrypt left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't think this PR should use any brave-specific propagation api, as OT does not define propagation at this level of abstraction. Rather, it would using the "global-tracer/active-span" contrib stuff.

In other words, no reason to include brave 3 apis directly, unless it is a part of supporting the OT extension apis

*/
@Override
public String getBaggageItem(String key) {
// brave does not support baggage
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

maybe move this to javadoc instead of inheritdoc.

/**
  * Returns null as neither <a href="https://github.com/openzipkin/b3-propagation">B3</a>
  * nor Brave include baggage support.
  */
// OpenTracing could one day define a way to plug-in arbitrary baggage handling similar to how
// it has feature-specific apis like active-span

public Span log(Map<String, ?> fields) {
if (fields.isEmpty()) return this;
// in real life, do like zipkin-go-opentracing: "key1=value1 key2=value2"
return log(fields.toString());
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'd go ahead and make the utility function now

ex.

static String toAnnotation(Map<String, ?> fields) {
  // special-case the "event" field which is similar to the semantics of a zipkin annotation
  Object event = fields.get("event");
  if (event != null && fields.size() == 1) return event.toString();

  return joinOnEqualsSpace(fields);
}

static String joinOnEqualsSpace(Map<String, ?> fields) {
  if (fields.isEmpty()) return "";

  StringBuilder result = new StringBuilder();
  for (Iterator<Map.Entry<String, String>> i = fields.entrySet().iterator(); i.hasNext(); ) {
    Map.Entry<String, String> next = i.next();
    result.append(next.getKey()).append('=').append(next.getValue());
    if (i.hasNext()) result.append(' ');
  }
  return result.toString();
}

static final TraceContext.Extractor<TextMapView> EXTRACTOR = Propagation.B3_STRING.extractor(TextMapView::get);

private brave.Tracer brave4;
private Brave brave3; // Not sure if I need this or not. Might want to attach to the local tracer context
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think the adapter pattern is sufficient rather than make a permanent dependency on brave-core

}

@Test
public void extractTraceContext() throws Exception {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Hey @devinsba,
great work 👍 .

I have a question. Does this PR solve extract when there is no span context in a carrier? Current impl returns NoopSpanBuilder...

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

looks like a missing test is all.

currently...

  • if the sampling flag is "0", but there's no ids, trace ids will be generated (but still have sampling false)
  • if there's nothing valid, trace ids will be generated along with a new sampling decision

If the semantics of OpenTracing say that no-op is for extract failure or unsampled, the logic could be changed.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks, this is great 👍

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I had a look at this, and it is an interesting topic.

Seems the api says to throw IllegalArgumentException when you cannot extract a context due to something corrupt https://github.com/opentracing/opentracing-java/blob/master/opentracing-api/src/main/java/io/opentracing/Tracer.java#L76

It doesn't say if null is permitted or not as a return value. I just noticed that at least in Jaeger null is returned when fields are missing etc.

sampled=0 without ids isn't corrupt, rather an unsampled context. Probably grey area whether to generate span ids here when absent (Historically in B3, ids were ignored when unsampled, but some prefer to propagate them anyway)

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I was also looking at null returned in Jaeger..

Seems the api says to throw IllegalArgumentException when you cannot extract a context due to something corrupt https://github.com/opentracing/opentracing-java/blob/master/opentracing-api/src/main/java/io/opentracing/Tracer.java#L76

I understand this like: there is X─B3─ParentSpanId but X─B3─TraceId is missing (or similar combinations).

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

PS I thought about this last night.. we can raise a separate issue about policy. This could be configuration specified when building the opentracer

Ex.

  • ExtractFailurePolicy.RESTART
    • default and what exists on most tracers
  • ExtractFailurePolicy.THROW
    • throw IllegalStateException knowing it might break apps, like assertions on
  • ExtractFailurePolicy.TAG_AND_RESTART
    • add a tag with the cause of the extraction failure, but restart normally

cc @basvanbeek who I discussed this lightly with..

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I like it..

Isn't ExtractFailurePolicy.TAG_AND_RESTART redundant? if there is a standard tag for it, it makes sense, otherwise it would by tracer specific.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Should I defer this change to a separate PR?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

yeah different PR for sure

@codefromthecrypt
Copy link
Contributor

codefromthecrypt commented Jan 25, 2017 via email

@devinsba
Copy link
Member Author

I don't think this PR should use any brave-specific propagation api, as OT does not define propagation at this level of abstraction. Rather, it would using the "global-tracer/active-span" contrib stuff.

In other words, no reason to include brave 3 apis directly, unless it is a part of supporting the OT extension apis

Ok, cool. Then this is close. Just want to look over the tests a bit more for completeness.

@devinsba devinsba changed the title [WIP] OT API using Brave 4 OT API using Brave 4 Jan 25, 2017
import java.util.Collections;
import java.util.Map;

public class BraveSpanContext implements SpanContext {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

make this final and add javadoc

/**
  * Holds the {@linkplain TraceContext} used by the underlying {@linkplain brave.Tracer}. An 
  * {@link TraceContext#sampled() unsampled} context results in a {@link opentracing...NoopSpan}.
  *
  * <p>This type also includes hooks to integrate with the underlying {@linkplain brave.Tracer}.
  * Ex you can access the underlying trace context with {@link #unwrap}
  */

Copy link
Contributor

@codefromthecrypt codefromthecrypt left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

made a lot of polish related remarks, as the code is probably fine.

If you need more help with content (Ex example tests, javadoc or README, let me know)


public class BraveSpanContext implements SpanContext {

private TraceContext traceContext;
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

final

this.traceContext = traceContext;
}

final TraceContext unwrap() {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

public (final implied when you final the type)

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

also add javadoc

/** Returns the underlying trace context for use in Brave apis */

}

/**
* {@inheritDoc}
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

change to..

/**
 * Returns empty as neither <a href="https://github.com/openzipkin/b3-propagation">B3</a>
 * nor Brave include baggage support.
 */

import java.util.List;
import java.util.Map;

public class BraveTracer implements Tracer {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

add final

add javadoc similar to what's on brave.tracer

static final TraceContext.Injector<TextMap> INJECTOR = Propagation.B3_STRING.injector(TextMap::put);
static final TraceContext.Extractor<TextMapView> EXTRACTOR = Propagation.B3_STRING.extractor(TextMapView::get);

private brave.Tracer brave4;
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

final

* {@inheritDoc}
*/
@Override
public Span start() {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

covariant override as BraveSpan

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Not sure what you mean by this?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I mean @Override BraveSpan start()


public class BraveSpan implements Span {

static BraveSpan wrap(brave.Span span) {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

make this public and javadoc

/** Converts an existing {@linkplain brave.Span} for use in OpenTracing apis */


import java.util.Map;

public class BraveSpan implements Span {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

make type final with javadoc similar to BraveSpanContext

import java.util.LinkedHashMap;
import java.util.Map;

public class BraveSpanBuilder implements Tracer.SpanBuilder {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

add javadoc similar to BraveSpanContext

@@ -30,6 +30,14 @@
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<project.build.resourceEncoding>UTF-8</project.build.resourceEncoding>

<!-- default bytecode version for src/main -->
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

add or replace the root README with one that looks like the one from openzipkin/brave/brave (particularly the section about converting in-out from brave 3, as this is similar to converting in and out of opentracing)

@codefromthecrypt
Copy link
Contributor

codefromthecrypt commented Jan 26, 2017 via email

@pavolloffay
Copy link
Contributor

It's definitely a good idea 👍 thanks.

Could you please raise it in OT/spec repo as it is your idea 👍 ? Or I can do it.

@codefromthecrypt
Copy link
Contributor

codefromthecrypt commented Jan 26, 2017 via email

return new BraveSpan(span);
}

final brave.Span unwrap() {
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Wondering if this should be public?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

yep it should

* {@inheritDoc}
*/
@Override
public Span start() {
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Not sure what you mean by this?

}

@Test
public void extractTraceContext() throws Exception {
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Should I defer this change to a separate PR?

@devinsba
Copy link
Member Author

devinsba commented Feb 3, 2017

Honestly I'm not sure what exactly to modify in the current README. The old one is still completely applicable (the magic of using the same interfaces). I guess there might be some context from the discussion in this thread missing though.

@adriancole you have edit permission if you want to take a shot

@codefromthecrypt
Copy link
Contributor

codefromthecrypt commented Feb 3, 2017 via email

@codefromthecrypt
Copy link
Contributor

codefromthecrypt commented Feb 3, 2017 via email

@codefromthecrypt codefromthecrypt merged commit f4fcd74 into openzipkin-contrib:master Feb 4, 2017
@codefromthecrypt
Copy link
Contributor

thanks @devinsba for all the work here! Thanks also @felixbarny and @pavolloffay for taking a look. will release shortly

@codefromthecrypt
Copy link
Contributor

going out now as v0.18.0

@pavolloffay
Copy link
Contributor

This is great 👍 👍 👍 thanks!

@bhs
Copy link
Contributor

bhs commented Feb 4, 2017

Agreed, thank you @devinsba and @adriancole!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

5 participants