-
Notifications
You must be signed in to change notification settings - Fork 40
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
Add Builder
of Attributes
. Documentation improvements
#382
Conversation
Builder
of Attributes
. Documentation improvements.Builder
of Attributes
. Documentation improvements
wasn't the purpose of the builder to be mutable? while this is perhaps a little more efficient than before, there's still a decent bit of copying |
3af9641
to
bbbf748
Compare
You are right, we should use a mutable builder instead. |
I've added a mutable builder. |
7f23bec
to
6814e88
Compare
what if we made |
interesting idea. Then we can drop the custom |
6814e88
to
b821ea7
Compare
@NthPortal thanks for the idea! I like the outcome |
|
||
def iterator: Iterator[Attribute[_]] = m.values.iterator | ||
|
||
override def toList: List[Attribute[_]] = m.values.toList |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The compilation fails without this override in Scala 3:
[error] 177 | private final class MapAttributes(
[error] | ^
[error] |class MapAttributes needs to be abstract, since def toList: List[org.typelevel.otel4s.Attribute[?]] in trait Attributes in package org.typelevel.otel4s.sdk is not defined
[error] one error found
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
... what?? that makes no sense.
the only thing I can think of is that Iterable
already defines toList
, but that doesn't really explain things
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
... what?? that makes no sense.
the only thing I can think of is that
Iterable
already definestoList
, but that doesn't really explain things
I didn't find a meaningful answer either. ¯\_(ツ)_/¯
I assume Scala 3 compiler handles some inheritance cases differently.
sdk/common/src/main/scala/org/typelevel/otel4s/sdk/Attributes.scala
Outdated
Show resolved
Hide resolved
sdk/common/src/main/scala/org/typelevel/otel4s/sdk/Attributes.scala
Outdated
Show resolved
Hide resolved
|
||
/** Returns the `Map` representation of the attributes collection. | ||
*/ | ||
def toMap: Map[AttributeKey[_], Attribute[_]] |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'm torn between this being toMap
vs asMap
. asMap
has the implication that Attributes
is already either like a map (and can be easily wrapped as one) or backed by a map. is that something that we should commit to publicly as its design?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Good question. Collections use to{X}
. Technically, Attributes
is a collection now.
Across the code base, we only use asMap
in TraceState
.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Collections use
to{X}
except for conversions (i.e. wrappers) between Java and Scala collections, which use as{Java,Scala}
@iRevive I wrote up my own implementation of |
0277171
to
051fbc9
Compare
I've backported some changes from #384. And a few benchmarks:
Some overhead is expected because we use Benchmarks with GC
|
13ns?! is it just identity hash code in the Java implementation? |
The implementation is this one: https://github.com/open-telemetry/opentelemetry-java/blob/main/api/all/src/main/java/io/opentelemetry/api/common/ArrayBackedAttributes.java. And the hash function is defined here https://github.com/open-telemetry/opentelemetry-java/blob/main/api/all/src/main/java/io/opentelemetry/api/internal/ImmutableKeyValuePairs.java#L250 |
oh, it caches it in a field. that'll do it. is that worth doing for us? I'm guessing not |
We can keep everything as is, I believe. And implement caching only if the current version will affect performance so badly (I doubt that's the case). |
private val values = List.tabulate(10)(i => s"value$i") | ||
|
||
private val jKeys = List.tabulate(10)(i => JAttributeKey.stringKey(s"key$i")) | ||
private val jAttributes = List.tabulate(10) { i => | ||
val size = i + 1 | ||
val pairs = jKeys.take(size).zip(values.take(size)) | ||
|
||
pairs | ||
.foldLeft(JAttributes.builder()) { case (builder, (key, value)) => | ||
builder.put(key, value) | ||
} | ||
.build() | ||
} | ||
|
||
private val keys = List.tabulate(10)(i => AttributeKey.string(s"key$i")) | ||
private val attributes = List.tabulate(10) { i => | ||
val size = i + 1 | ||
val pairs = keys.take(size).zip(values.take(size)) | ||
|
||
pairs | ||
.foldLeft(Attributes.newBuilder) { case (builder, (key, value)) => | ||
builder.addOne(key, value) | ||
} | ||
.result() | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
it's been so long since I've done any benchmarking, but I think we want these defined in the benchmark instance rather than the companion, and I think there's also a setup method where you're supposed to construct them to prevent some compiler optimisations that wouldn't happen in regular code
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I took the idea of the benchmark from https://github.com/open-telemetry/opentelemetry-java/blob/main/api/all/src/jmh/java/io/opentelemetry/api/common/AttributesBenchmark.java#L25-L40.
Here, they are defined as static variables.
Closes #371.