Skip to content
Permalink

Comparing changes

Choose two branches to see what’s changed or to start a new pull request. If you need to, you can also or learn more about diff comparisons.

Open a pull request

Create a new pull request by comparing changes across two branches. If you need to, you can also . Learn more about diff comparisons here.
base repository: open-telemetry/opentelemetry-rust
Failed to load repositories. Confirm that selected base ref is valid, then try again.
Loading
base: opentelemetry-zipkin-0.28.0
Choose a base ref
...
head repository: open-telemetry/opentelemetry-rust
Failed to load repositories. Confirm that selected head ref is valid, then try again.
Loading
compare: opentelemetry-zipkin-0.29.0
Choose a head ref
Loading
Showing with 8,365 additions and 4,243 deletions.
  1. +1 −1 .github/ISSUE_TEMPLATE/BUG-REPORT.yml
  2. +54 −0 .github/workflows/benchmark.yml
  3. +3 −5 .github/workflows/ci.yml
  4. +20 −0 .github/workflows/fossa.yml
  5. +2 −0 .github/workflows/integration_tests.yml
  6. +15 −0 .github/workflows/pr_naming.yml
  7. +7 −2 CONTRIBUTING.md
  8. +36 −1 Cargo.toml
  9. +7 −3 README.md
  10. +173 −0 docs/adr/001_error_handling.md
  11. +5 −0 docs/adr/README.md
  12. +360 −0 docs/design/logs.md
  13. +6 −0 docs/design/metrics.md
  14. +6 −0 docs/design/traces.md
  15. +1 −2 docs/migration_0.28.md
  16. +92 −0 docs/migration_0.29.md
  17. +3 −3 examples/logs-basic/Cargo.toml
  18. +32 −3 examples/logs-basic/src/main.rs
  19. +1 −1 examples/metrics-advanced/Cargo.toml
  20. +1 −3 examples/metrics-advanced/src/main.rs
  21. +1 −1 examples/metrics-basic/Cargo.toml
  22. +1 −2 examples/metrics-basic/src/main.rs
  23. +2 −2 examples/tracing-grpc/Cargo.toml
  24. +17 −6 examples/tracing-grpc/src/client.rs
  25. +8 −2 examples/tracing-grpc/src/server.rs
  26. +1 −1 examples/tracing-http-propagator/Cargo.toml
  27. +19 −11 examples/tracing-http-propagator/src/server.rs
  28. +0 −12 examples/tracing-jaeger/Cargo.toml
  29. +0 −21 examples/tracing-jaeger/README.md
  30. BIN examples/tracing-jaeger/jaeger.png
  31. +0 −48 examples/tracing-jaeger/src/main.rs
  32. +12 −0 opentelemetry-appender-log/CHANGELOG.md
  33. +7 −4 opentelemetry-appender-log/Cargo.toml
  34. +2 −2 opentelemetry-appender-log/README.md
  35. +29 −18 opentelemetry-appender-log/src/lib.rs
  36. +63 −2 opentelemetry-appender-tracing/CHANGELOG.md
  37. +20 −9 opentelemetry-appender-tracing/Cargo.toml
  38. +2 −2 opentelemetry-appender-tracing/README.md
  39. +272 −0 opentelemetry-appender-tracing/benches/log-attributes.rs
  40. +28 −40 opentelemetry-appender-tracing/benches/logs.rs
  41. +32 −3 opentelemetry-appender-tracing/examples/basic.rs
  42. +368 −130 opentelemetry-appender-tracing/src/layer.rs
  43. +154 −0 opentelemetry-appender-tracing/src/lib.rs
  44. +6 −0 opentelemetry-http/CHANGELOG.md
  45. +8 −5 opentelemetry-http/Cargo.toml
  46. +2 −2 opentelemetry-http/README.md
  47. +6 −0 opentelemetry-jaeger-propagator/CHANGELOG.md
  48. +5 −2 opentelemetry-jaeger-propagator/Cargo.toml
  49. +2 −2 opentelemetry-jaeger-propagator/README.md
  50. +35 −3 opentelemetry-otlp/CHANGELOG.md
  51. +9 −6 opentelemetry-otlp/Cargo.toml
  52. +2 −2 opentelemetry-otlp/README.md
  53. +5 −3 opentelemetry-otlp/examples/basic-otlp-http/Cargo.toml
  54. +35 −13 opentelemetry-otlp/examples/basic-otlp-http/src/main.rs
  55. +7 −5 opentelemetry-otlp/examples/basic-otlp/Cargo.toml
  56. +37 −12 opentelemetry-otlp/examples/basic-otlp/src/main.rs
  57. +35 −41 opentelemetry-otlp/src/exporter/http/logs.rs
  58. +0 −2 opentelemetry-otlp/src/exporter/http/metrics.rs
  59. +87 −85 opentelemetry-otlp/src/exporter/http/mod.rs
  60. +20 −31 opentelemetry-otlp/src/exporter/http/trace.rs
  61. +178 −11 opentelemetry-otlp/src/exporter/mod.rs
  62. +38 −42 opentelemetry-otlp/src/exporter/tonic/logs.rs
  63. +0 −2 opentelemetry-otlp/src/exporter/tonic/metrics.rs
  64. +113 −59 opentelemetry-otlp/src/exporter/tonic/mod.rs
  65. +22 −27 opentelemetry-otlp/src/exporter/tonic/trace.rs
  66. +142 −143 opentelemetry-otlp/src/lib.rs
  67. +18 −15 opentelemetry-otlp/src/logs.rs
  68. +47 −16 opentelemetry-otlp/src/metric.rs
  69. +42 −13 opentelemetry-otlp/src/span.rs
  70. +9 −6 opentelemetry-otlp/tests/integration_test/Cargo.toml
  71. +19 −2 opentelemetry-otlp/tests/integration_test/src/logs_asserter.rs
  72. +2 −2 opentelemetry-otlp/tests/integration_test/src/metric_helpers.rs
  73. +30 −26 opentelemetry-otlp/tests/integration_test/src/test_utils.rs
  74. +6 −4 opentelemetry-otlp/tests/integration_test/tests/logs.rs
  75. +1 −1 opentelemetry-otlp/tests/integration_test/tests/logs_serialize_deserialize.rs
  76. +6 −6 opentelemetry-otlp/tests/integration_test/tests/metrics.rs
  77. +2 −3 opentelemetry-otlp/tests/integration_test/tests/traces.rs
  78. +6 −2 opentelemetry-prometheus/CHANGELOG.md
  79. +6 −6 opentelemetry-prometheus/Cargo.toml
  80. +15 −4 opentelemetry-prometheus/README.md
  81. +16 −5 opentelemetry-prometheus/src/lib.rs
  82. +33 −55 opentelemetry-prometheus/tests/integration_test.rs
  83. +7 −0 opentelemetry-proto/CHANGELOG.md
  84. +11 −8 opentelemetry-proto/Cargo.toml
  85. +1 −1 opentelemetry-proto/README.md
  86. +89 −5 opentelemetry-sdk/CHANGELOG.md
  87. +28 −16 opentelemetry-sdk/Cargo.toml
  88. +2 −2 opentelemetry-sdk/README.md
  89. +41 −13 opentelemetry-sdk/benches/context.rs
  90. +84 −0 opentelemetry-sdk/benches/log_enabled.rs
  91. +2 −4 opentelemetry-sdk/benches/log_exporter.rs
  92. +5 −3 opentelemetry-sdk/benches/metric.rs
  93. +23 −22 opentelemetry-sdk/benches/metrics_counter.rs
  94. +5 −5 opentelemetry-sdk/benches/metrics_gauge.rs
  95. +9 −9 opentelemetry-sdk/benches/metrics_histogram.rs
  96. +2 −3 opentelemetry-sdk/benches/span_builder.rs
  97. +2 −3 opentelemetry-sdk/benches/trace.rs
  98. +100 −0 opentelemetry-sdk/benches/tracer_creation.rs
  99. +22 −4 opentelemetry-sdk/src/lib.rs
  100. +999 −0 opentelemetry-sdk/src/logs/batch_log_processor.rs
  101. +64 −0 opentelemetry-sdk/src/logs/concurrent_log_processor.rs
  102. +0 −63 opentelemetry-sdk/src/logs/error.rs
  103. +3 −3 opentelemetry-sdk/src/logs/export.rs
  104. +31 −32 opentelemetry-sdk/src/logs/in_memory_exporter.rs
  105. +20 −1,352 opentelemetry-sdk/src/logs/log_processor.rs
  106. +21 −38 opentelemetry-sdk/src/logs/log_processor_with_async_runtime.rs
  107. +7 −14 opentelemetry-sdk/src/logs/logger.rs
  108. +227 −64 opentelemetry-sdk/src/logs/logger_provider.rs
  109. +91 −10 opentelemetry-sdk/src/logs/mod.rs
  110. +441 −0 opentelemetry-sdk/src/logs/simple_log_processor.rs
  111. +5 −5 opentelemetry-sdk/src/metrics/exporter.rs
  112. +7 −8 opentelemetry-sdk/src/metrics/in_memory_exporter.rs
  113. +99 −4 opentelemetry-sdk/src/metrics/meter_provider.rs
  114. +5 −5 opentelemetry-sdk/src/metrics/mod.rs
  115. +31 −33 opentelemetry-sdk/src/metrics/periodic_reader.rs
  116. +30 −23 opentelemetry-sdk/src/metrics/periodic_reader_with_async_runtime.rs
  117. +20 −17 opentelemetry-sdk/src/propagation/baggage.rs
  118. +22 −11 opentelemetry-sdk/src/resource/mod.rs
  119. +49 −105 opentelemetry-sdk/src/runtime.rs
  120. +7 −9 opentelemetry-sdk/src/testing/trace/span_exporters.rs
  121. +0 −98 opentelemetry-sdk/src/trace/config.rs
  122. +60 −0 opentelemetry-sdk/src/trace/error.rs
  123. +4 −2 opentelemetry-sdk/src/trace/export.rs
  124. +3 −3 opentelemetry-sdk/src/trace/id_generator/mod.rs
  125. +12 −14 opentelemetry-sdk/src/trace/in_memory_exporter.rs
  126. +151 −11 opentelemetry-sdk/src/trace/mod.rs
  127. +56 −23 opentelemetry-sdk/src/trace/provider.rs
  128. +2 −5 opentelemetry-sdk/src/trace/runtime_tests.rs
  129. +2 −3 opentelemetry-sdk/src/trace/sampler.rs
  130. +8 −6 opentelemetry-sdk/src/trace/sampler/jaeger_remote/sampler.rs
  131. +98 −58 opentelemetry-sdk/src/trace/span_processor.rs
  132. +35 −76 opentelemetry-sdk/src/trace/span_processor_with_async_runtime.rs
  133. +6 −0 opentelemetry-semantic-conventions/CHANGELOG.md
  134. +4 −1 opentelemetry-semantic-conventions/Cargo.toml
  135. +2 −2 opentelemetry-semantic-conventions/README.md
  136. +2 −8 opentelemetry-semantic-conventions/scripts/generate-consts-from-spec.sh
  137. +2 −2 opentelemetry-semantic-conventions/scripts/templates/registry/rust/metric.rs.j2
  138. +3 −3 opentelemetry-semantic-conventions/scripts/templates/registry/rust/resource.rs.j2
  139. +1 −1 opentelemetry-semantic-conventions/scripts/templates/registry/rust/weaver.yaml
  140. +327 −153 opentelemetry-semantic-conventions/src/attribute.rs
  141. +1 −1 opentelemetry-semantic-conventions/src/lib.rs
  142. +372 −54 opentelemetry-semantic-conventions/src/metric.rs
  143. +21 −3 opentelemetry-semantic-conventions/src/resource.rs
  144. +29 −81 opentelemetry-semantic-conventions/src/trace.rs
  145. +7 −0 opentelemetry-stdout/CHANGELOG.md
  146. +10 −11 opentelemetry-stdout/Cargo.toml
  147. +2 −2 opentelemetry-stdout/README.md
  148. +6 −6 opentelemetry-stdout/src/lib.rs
  149. +22 −28 opentelemetry-stdout/src/logs/exporter.rs
  150. +1 −3 opentelemetry-stdout/src/metrics/exporter.rs
  151. +15 −13 opentelemetry-stdout/src/trace/exporter.rs
  152. +16 −0 opentelemetry-zipkin/CHANGELOG.md
  153. +8 −5 opentelemetry-zipkin/Cargo.toml
  154. +5 −6 opentelemetry-zipkin/README.md
  155. +3 −3 opentelemetry-zipkin/examples/zipkin.rs
  156. +1 −1 opentelemetry-zipkin/src/exporter/env.rs
  157. +35 −28 opentelemetry-zipkin/src/exporter/mod.rs
  158. +12 −12 opentelemetry-zipkin/src/lib.rs
  159. +21 −0 opentelemetry/CHANGELOG.md
  160. +22 −5 opentelemetry/Cargo.toml
  161. +2 −2 opentelemetry/README.md
  162. +99 −0 opentelemetry/benches/baggage.rs
  163. +110 −0 opentelemetry/benches/context_attach.rs
  164. +197 −152 opentelemetry/src/baggage.rs
  165. +202 −4 opentelemetry/src/common.rs
  166. +516 −42 opentelemetry/src/context.rs
  167. +108 −0 opentelemetry/src/context/future_ext.rs
  168. +75 −8 opentelemetry/src/global/internal_logging.rs
  169. +1 −1 opentelemetry/src/lib.rs
  170. +2 −2 opentelemetry/src/logs/logger.rs
  171. +1 −1 opentelemetry/src/logs/noop.rs
  172. +6 −0 opentelemetry/src/logs/record.rs
  173. +0 −120 opentelemetry/src/metrics/mod.rs
  174. +1 −1 opentelemetry/src/propagation/composite.rs
  175. +4 −112 opentelemetry/src/trace/context.rs
  176. +2 −71 opentelemetry/src/trace/mod.rs
  177. +14 −18 opentelemetry/src/trace/span_context.rs
  178. +0 −1 scripts/RELEASING.md
  179. +6 −17 scripts/lint.sh
  180. +1 −0 scripts/patch_dependencies.sh
  181. +3 −0 scripts/test.sh
  182. +11 −8 stress/Cargo.toml
  183. +51 −32 stress/src/logs.rs
  184. +4 −4 stress/src/metrics_counter.rs
  185. +4 −4 stress/src/metrics_gauge.rs
  186. +24 −7 stress/src/metrics_histogram.rs
  187. +2 −2 stress/src/metrics_overflow.rs
  188. +4 −4 stress/src/random.rs
  189. +1 −1 stress/src/throughput.rs
2 changes: 1 addition & 1 deletion .github/ISSUE_TEMPLATE/BUG-REPORT.yml
Original file line number Diff line number Diff line change
@@ -28,7 +28,7 @@ body:
- type: textarea
id: sdk-version
attributes:
label: label: OpenTelemetry SDK Version (i.e version of `opentelemetry_sdk` crate)
label: OpenTelemetry SDK Version (i.e version of `opentelemetry_sdk` crate)
description: What version of the `opentelemetry_sdk` crate are you using?
placeholder: 0.x, 1.x, etc.
validations:
54 changes: 54 additions & 0 deletions .github/workflows/benchmark.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,54 @@
# This workflow runs a Criterion benchmark on a PR and compares the results against the base branch.
# It is triggered on a PR or a push to main.
#
# The workflow is gated on the presence of the "performance" label on the PR.
#
# The workflow runs on a self-hosted runner pool. We can't use the shared runners for this,
# because they are only permitted to run on the default branch to preserve resources.
#
# In the future, we might like to consider using bencher.dev or the framework used by otel-golang here.
on:
pull_request:
push:
branches:
- main
name: benchmark pull requests
jobs:
runBenchmark:
name: run benchmark
permissions:
pull-requests: write

# If we're running on a PR, use ubuntu-latest - a shared runner. We can't use the self-hosted
# runners on arbitrary PRs, and we don't want to unleash that load on the pool anyway.
# If we're running on main, use the OTEL self-hosted runner pool.
runs-on: ${{ github.event_name == 'pull_request' && 'ubuntu-latest' || 'self-hosted' }}
if: ${{ (github.event_name == 'pull_request' && contains(github.event.pull_request.labels.*.name, 'performance')) || github.event_name == 'push' }}
env:
# For PRs, compare against the base branch - e.g., 'main'.
# For pushes to main, compare against the previous commit
BRANCH_NAME: ${{ github.event_name == 'pull_request' && github.base_ref || github.event.before }}
steps:
- uses: actions/checkout@v4
with:
fetch-depth: 10 # Fetch current commit and its parent
- uses: arduino/setup-protoc@v3
with:
repo-token: ${{ secrets.GITHUB_TOKEN }}
- uses: dtolnay/rust-toolchain@master
with:
toolchain: stable
- uses: boa-dev/criterion-compare-action@v3
with:
cwd: opentelemetry
branchName: ${{ env.BRANCH_NAME }}
- uses: boa-dev/criterion-compare-action@v3
with:
cwd: opentelemetry-appender-tracing
features: spec_unstable_logs_enabled
branchName: ${{ env.BRANCH_NAME }}
- uses: boa-dev/criterion-compare-action@v3
with:
cwd: opentelemetry-sdk
features: rt-tokio,testing,metrics,logs,spec_unstable_metrics_views
branchName: ${{ env.BRANCH_NAME }}
8 changes: 3 additions & 5 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
@@ -25,7 +25,7 @@ jobs:
- rust: stable
os: macos-latest
- rust: stable
os: otel-linux-arm64
os: ubuntu-22.04-arm
runs-on: ${{ matrix.os }}
continue-on-error: ${{ matrix.rust == 'beta' }}
steps:
@@ -62,10 +62,8 @@ jobs:
- uses: arduino/setup-protoc@v3
with:
repo-token: ${{ secrets.GITHUB_TOKEN }}
- uses: actions-rs/cargo@v1
with:
command: fmt
args: --all -- --check
- name: Format
run: cargo fmt --all -- --check
- name: Lint
run: bash ./scripts/lint.sh
external-types:
20 changes: 20 additions & 0 deletions .github/workflows/fossa.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
name: FOSSA scanning

on:
push:
branches:
- main

permissions:
contents: read

jobs:
fossa:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2

- uses: fossas/fossa-action@93a52ecf7c3ac7eb40f5de77fd69b1a19524de94 # v1.5.0
with:
api-key: ${{secrets.FOSSA_API_KEY}}
team: OpenTelemetry
2 changes: 2 additions & 0 deletions .github/workflows/integration_tests.yml
Original file line number Diff line number Diff line change
@@ -23,5 +23,7 @@ jobs:
with:
components: rustfmt
- uses: arduino/setup-protoc@v3
with:
repo-token: ${{ secrets.GITHUB_TOKEN }}
- name: Run integration tests
run: ./scripts/integration_tests.sh
15 changes: 15 additions & 0 deletions .github/workflows/pr_naming.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
name: PR Conventional Commit Validation

on:
pull_request:
types: [opened, synchronize, reopened, edited]

jobs:
validate-pr-title:
runs-on: ubuntu-latest
steps:
- name: PR Conventional Commit Validation
uses: ytanikin/pr-conventional-commits@1.4.1
with:
task_types: '["build","chore","ci","docs","feat","fix","perf","refactor","revert","test"]'
add_label: 'false'
9 changes: 7 additions & 2 deletions CONTRIBUTING.md
Original file line number Diff line number Diff line change
@@ -8,7 +8,7 @@ for specific dates and for Zoom meeting links. "OTel Rust SIG" is the name of
meeting for this group.

Meeting notes are available as a public [Google
doc](https://docs.google.com/document/d/1tGKuCsSnyT2McDncVJrMgg74_z8V06riWZa0Sr79I_4/edit).
doc](https://docs.google.com/document/d/12upOzNk8c3SFTjsL6IRohCWMgzLKoknSCOOdMakbWo4/edit).
If you have trouble accessing the doc, please get in touch on
[Slack](https://cloud-native.slack.com/archives/C03GDP0H023).

@@ -78,6 +78,11 @@ Open a pull request against the main
[opentelemetry-rust](https://github.com/open-telemetry/opentelemetry-rust)
repo.

Your pull request should be named according to the
[conventional commits](https://www.conventionalcommits.org/en/v1.0.0/) standard. This ensures that
when the PR is squashed into `main`, the resulting commit message is consistent and makes it easier
for us to generate a changelog standard.

> **Note**
> It is recommended to run [pre-commit script](scripts/precommit.sh) to catch any issues locally.
@@ -167,7 +172,7 @@ It's important to regularly review and remove the `otel_unstable` flag from the

The potential features include:

- Stable and non-experimental features that compliant to specification, and have a feature flag to minimize compilation size. Example: feature flags for signals (like `logs`, `traces`, `metrics`) and runtimes (`rt-tokio`, `rt-tokio-current-thread`, `rt-async-std`).
- Stable and non-experimental features that are compliant with the specification and have a feature flag to minimize compilation size. Example: feature flags for signals (like `logs`, `traces`, `metrics`) and runtimes (`rt-tokio`, `rt-tokio-current-thread`).
- Stable and non-experimental features, although not part of the specification, are crucial for enhancing the tracing/log crate's functionality or boosting performance. These features are also subject to discussion and approval by the OpenTelemetry Rust Maintainers.

All such features should adhere to naming convention `<signal>_<feature_name>`
37 changes: 36 additions & 1 deletion Cargo.toml
Original file line number Diff line number Diff line change
@@ -36,7 +36,7 @@ pin-project-lite = "0.2"
prost = "0.13"
prost-build = "0.13"
prost-types = "0.13"
rand = { version = "0.8", default-features = false }
rand = { version = "0.9", default-features = false }
reqwest = { version = "0.12", default-features = false }
serde = { version = "1.0", default-features = false }
serde_json = "1.0"
@@ -53,9 +53,44 @@ tracing = { version = ">=0.1.40", default-features = false }
tracing-core = { version = ">=0.1.33", default-features = false }
tracing-subscriber = { version = "0.3", default-features = false }
url = { version = "2.5", default-features = false }
anyhow = "1.0.94"
base64 = "0.22.1"
chrono = { version = "0.4.34", default-features = false }
ctor = "0.2.9"
ctrlc = "3.2.5"
futures-channel = "0.3"
futures-sink = "0.3"
glob = "0.3.1"
hex = "0.4.3"
lazy_static = "1.4.0"
num-format = "0.4.4"
num_cpus = "1.15.0"
opentelemetry-appender-tracing = { path = "opentelemetry-appender-tracing", default-features = false }
opentelemetry-otlp = { path = "opentelemetry-otlp" }
opentelemetry-stdout = { path = "opentelemetry-stdout" }
percent-encoding = "2.0"
rstest = "0.23.0"
schemars = "0.8"
sysinfo = "0.32"
tempfile = "3.3.0"
testcontainers = "0.23.1"
tracing-log = "0.2"
tracing-opentelemetry = "0.29"
typed-builder = "0.20"
uuid = "1.3"

# Aviod use of crates.io version of these crates through the tracing-opentelemetry dependencies
[patch.crates-io]
opentelemetry = { path = "opentelemetry" }
opentelemetry_sdk = { path = "opentelemetry-sdk" }
opentelemetry-stdout = { path = "opentelemetry-stdout" }

[workspace.lints.rust]
rust_2024_compatibility = { level = "warn", priority = -1 }
# No need to enable those, because it either not needed or results in ugly syntax
edition_2024_expr_fragment_specifier = "allow"
if_let_rescope = "allow"
tail_expr_drop_order = "allow"

[workspace.lints.clippy]
all = { level = "warn", priority = 1 }
10 changes: 7 additions & 3 deletions README.md
Original file line number Diff line number Diff line change
@@ -30,10 +30,13 @@ documentation.

| Signal/Component | Overall Status |
| -------------------- | ------------------ |
| Context | Beta |
| Baggage | RC |
| Propagators | Beta |
| Logs-API | Stable* |
| Logs-SDK | RC |
| Logs-SDK | Stable |
| Logs-OTLP Exporter | RC |
| Logs-Appender-Tracing | RC |
| Logs-Appender-Tracing | Stable |
| Metrics-API | Stable |
| Metrics-SDK | RC |
| Metrics-OTLP Exporter | RC |
@@ -178,19 +181,20 @@ you're more than welcome to participate!

* [Cijo Thomas](https://github.com/cijothomas)
* [Harold Dost](https://github.com/hdost)
* [Julian Tescher](https://github.com/jtescher)
* [Lalit Kumar Bhasin](https://github.com/lalitb)
* [Utkarsh Umesan Pillai](https://github.com/utpilla)
* [Zhongyang Wu](https://github.com/TommyCpp)

### Approvers

* [Shaun Cox](https://github.com/shaun-cox)
* [Scott Gerring](https://github.com/scottgerring)

### Emeritus

* [Dirkjan Ochtman](https://github.com/djc)
* [Jan Kühle](https://github.com/frigus02)
* [Julian Tescher](https://github.com/jtescher)
* [Isobel Redelmeier](https://github.com/iredelmeier)
* [Mike Goldsmith](https://github.com/MikeGoldsmith)

Loading