@effect/platform 0.80.21 → 0.81.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/src/HttpClient.ts CHANGED
@@ -809,7 +809,7 @@ export const followRedirects: {
809
809
 
810
810
  /**
811
811
  * @since 1.0.0
812
- * @category fiber refs
812
+ * @category Tracing
813
813
  */
814
814
  export const currentTracerDisabledWhen: FiberRef.FiberRef<Predicate.Predicate<ClientRequest.HttpClientRequest>> =
815
815
  internal.currentTracerDisabledWhen
@@ -818,31 +818,31 @@ export const currentTracerDisabledWhen: FiberRef.FiberRef<Predicate.Predicate<Cl
818
818
  * Disables tracing for specific requests based on a provided predicate.
819
819
  *
820
820
  * @since 1.0.0
821
- * @category fiber refs
821
+ * @category Tracing
822
822
  */
823
823
  export const withTracerDisabledWhen: {
824
824
  /**
825
825
  * Disables tracing for specific requests based on a provided predicate.
826
826
  *
827
827
  * @since 1.0.0
828
- * @category fiber refs
828
+ * @category Tracing
829
829
  */
830
- (predicate: Predicate.Predicate<ClientRequest.HttpClientRequest>): <A, E, R>(effect: Effect.Effect<A, E, R>) => Effect.Effect<A, E, R>
830
+ (predicate: Predicate.Predicate<ClientRequest.HttpClientRequest>): <E, R>(self: HttpClient.With<E, R>) => HttpClient.With<E, R>
831
831
  /**
832
832
  * Disables tracing for specific requests based on a provided predicate.
833
833
  *
834
834
  * @since 1.0.0
835
- * @category fiber refs
835
+ * @category Tracing
836
836
  */
837
- <A, E, R>(
838
- effect: Effect.Effect<A, E, R>,
837
+ <E, R>(
838
+ self: HttpClient.With<E, R>,
839
839
  predicate: Predicate.Predicate<ClientRequest.HttpClientRequest>
840
- ): Effect.Effect<A, E, R>
840
+ ): HttpClient.With<E, R>
841
841
  } = internal.withTracerDisabledWhen
842
842
 
843
843
  /**
844
844
  * @since 1.0.0
845
- * @category fiber refs
845
+ * @category Tracing
846
846
  */
847
847
  export const currentTracerPropagation: FiberRef.FiberRef<boolean> = internal.currentTracerPropagation
848
848
 
@@ -850,23 +850,23 @@ export const currentTracerPropagation: FiberRef.FiberRef<boolean> = internal.cur
850
850
  * Enables or disables tracing propagation for the request.
851
851
  *
852
852
  * @since 1.0.0
853
- * @category fiber refs
853
+ * @category Tracing
854
854
  */
855
855
  export const withTracerPropagation: {
856
856
  /**
857
857
  * Enables or disables tracing propagation for the request.
858
858
  *
859
859
  * @since 1.0.0
860
- * @category fiber refs
860
+ * @category Tracing
861
861
  */
862
- (enabled: boolean): <A, E, R>(effect: Effect.Effect<A, E, R>) => Effect.Effect<A, E, R>
862
+ (enabled: boolean): <E, R>(self: HttpClient.With<E, R>) => HttpClient.With<E, R>
863
863
  /**
864
864
  * Enables or disables tracing propagation for the request.
865
865
  *
866
866
  * @since 1.0.0
867
- * @category fiber refs
867
+ * @category Tracing
868
868
  */
869
- <A, E, R>(effect: Effect.Effect<A, E, R>, enabled: boolean): Effect.Effect<A, E, R>
869
+ <E, R>(self: HttpClient.With<E, R>, enabled: boolean): HttpClient.With<E, R>
870
870
  } = internal.withTracerPropagation
871
871
 
872
872
  /**
@@ -875,3 +875,97 @@ export const withTracerPropagation: {
875
875
  export const layerMergedContext: <E, R>(
876
876
  effect: Effect.Effect<HttpClient, E, R>
877
877
  ) => Layer<HttpClient, E, R> = internal.layerMergedContext
878
+
879
+ /**
880
+ * @since 1.0.0
881
+ * @category Tracing
882
+ */
883
+ export interface SpanNameGenerator {
884
+ readonly _: unique symbol
885
+ }
886
+
887
+ /**
888
+ * @since 1.0.0
889
+ * @category Tracing
890
+ */
891
+ export const SpanNameGenerator: Context.Reference<
892
+ SpanNameGenerator,
893
+ (request: ClientRequest.HttpClientRequest) => string
894
+ > = internal.SpanNameGenerator
895
+
896
+ /**
897
+ * Customizes the span names for tracing.
898
+ *
899
+ * ```ts
900
+ * import { FetchHttpClient, HttpClient } from "@effect/platform"
901
+ * import { NodeRuntime } from "@effect/platform-node"
902
+ * import { Effect } from "effect"
903
+ *
904
+ * Effect.gen(function* () {
905
+ * const client = (yield* HttpClient.HttpClient).pipe(
906
+ * // Customize the span names for this HttpClient
907
+ * HttpClient.withSpanNameGenerator(
908
+ * (request) => `http.client ${request.method} ${request.url}`
909
+ * )
910
+ * )
911
+ *
912
+ * yield* client.get("https://jsonplaceholder.typicode.com/posts/1")
913
+ * }).pipe(Effect.provide(FetchHttpClient.layer), NodeRuntime.runMain)
914
+ * ```
915
+ *
916
+ * @since 1.0.0
917
+ * @category Tracing
918
+ */
919
+ export const withSpanNameGenerator: {
920
+ /**
921
+ * Customizes the span names for tracing.
922
+ *
923
+ * ```ts
924
+ * import { FetchHttpClient, HttpClient } from "@effect/platform"
925
+ * import { NodeRuntime } from "@effect/platform-node"
926
+ * import { Effect } from "effect"
927
+ *
928
+ * Effect.gen(function* () {
929
+ * const client = (yield* HttpClient.HttpClient).pipe(
930
+ * // Customize the span names for this HttpClient
931
+ * HttpClient.withSpanNameGenerator(
932
+ * (request) => `http.client ${request.method} ${request.url}`
933
+ * )
934
+ * )
935
+ *
936
+ * yield* client.get("https://jsonplaceholder.typicode.com/posts/1")
937
+ * }).pipe(Effect.provide(FetchHttpClient.layer), NodeRuntime.runMain)
938
+ * ```
939
+ *
940
+ * @since 1.0.0
941
+ * @category Tracing
942
+ */
943
+ (f: (request: ClientRequest.HttpClientRequest) => string): <E, R>(self: HttpClient.With<E, R>) => HttpClient.With<E, R>
944
+ /**
945
+ * Customizes the span names for tracing.
946
+ *
947
+ * ```ts
948
+ * import { FetchHttpClient, HttpClient } from "@effect/platform"
949
+ * import { NodeRuntime } from "@effect/platform-node"
950
+ * import { Effect } from "effect"
951
+ *
952
+ * Effect.gen(function* () {
953
+ * const client = (yield* HttpClient.HttpClient).pipe(
954
+ * // Customize the span names for this HttpClient
955
+ * HttpClient.withSpanNameGenerator(
956
+ * (request) => `http.client ${request.method} ${request.url}`
957
+ * )
958
+ * )
959
+ *
960
+ * yield* client.get("https://jsonplaceholder.typicode.com/posts/1")
961
+ * }).pipe(Effect.provide(FetchHttpClient.layer), NodeRuntime.runMain)
962
+ * ```
963
+ *
964
+ * @since 1.0.0
965
+ * @category Tracing
966
+ */
967
+ <E, R>(
968
+ self: HttpClient.With<E, R>,
969
+ f: (request: ClientRequest.HttpClientRequest) => string
970
+ ): HttpClient.With<E, R>
971
+ } = internal.withSpanNameGenerator
@@ -1,6 +1,7 @@
1
1
  /**
2
2
  * @since 1.0.0
3
3
  */
4
+ import type * as Context from "effect/Context"
4
5
  import type * as Effect from "effect/Effect"
5
6
  import type * as FiberRef from "effect/FiberRef"
6
7
  import type * as Layer from "effect/Layer"
@@ -149,3 +150,112 @@ export const cors: (
149
150
  readonly credentials?: boolean | undefined
150
151
  } | undefined
151
152
  ) => <E, R>(httpApp: App.Default<E, R>) => App.Default<E, R> = internal.cors
153
+
154
+ /**
155
+ * @since 1.0.0
156
+ * @category Tracing
157
+ */
158
+ export interface SpanNameGenerator {
159
+ readonly _: unique symbol
160
+ }
161
+
162
+ /**
163
+ * @since 1.0.0
164
+ * @category Tracing
165
+ */
166
+ export const SpanNameGenerator: Context.Reference<
167
+ SpanNameGenerator,
168
+ (request: ServerRequest.HttpServerRequest) => string
169
+ > = internal.SpanNameGenerator
170
+
171
+ /**
172
+ * Customizes the span name for the http app.
173
+ *
174
+ * ```ts
175
+ * import {
176
+ * HttpMiddleware,
177
+ * HttpRouter,
178
+ * HttpServer,
179
+ * HttpServerResponse
180
+ * } from "@effect/platform"
181
+ * import { NodeHttpServer, NodeRuntime } from "@effect/platform-node"
182
+ * import { Layer } from "effect"
183
+ * import { createServer } from "http"
184
+ *
185
+ * HttpRouter.empty.pipe(
186
+ * HttpRouter.get("/", HttpServerResponse.empty()),
187
+ * HttpServer.serve(),
188
+ * // Customize the span names for this HttpApp
189
+ * HttpMiddleware.withSpanNameGenerator((request) => `GET ${request.url}`),
190
+ * Layer.provide(NodeHttpServer.layer(createServer, { port: 3000 })),
191
+ * Layer.launch,
192
+ * NodeRuntime.runMain
193
+ * )
194
+ * ```
195
+ *
196
+ * @since 1.0.0
197
+ * @category Tracing
198
+ */
199
+ export const withSpanNameGenerator: {
200
+ /**
201
+ * Customizes the span name for the http app.
202
+ *
203
+ * ```ts
204
+ * import {
205
+ * HttpMiddleware,
206
+ * HttpRouter,
207
+ * HttpServer,
208
+ * HttpServerResponse
209
+ * } from "@effect/platform"
210
+ * import { NodeHttpServer, NodeRuntime } from "@effect/platform-node"
211
+ * import { Layer } from "effect"
212
+ * import { createServer } from "http"
213
+ *
214
+ * HttpRouter.empty.pipe(
215
+ * HttpRouter.get("/", HttpServerResponse.empty()),
216
+ * HttpServer.serve(),
217
+ * // Customize the span names for this HttpApp
218
+ * HttpMiddleware.withSpanNameGenerator((request) => `GET ${request.url}`),
219
+ * Layer.provide(NodeHttpServer.layer(createServer, { port: 3000 })),
220
+ * Layer.launch,
221
+ * NodeRuntime.runMain
222
+ * )
223
+ * ```
224
+ *
225
+ * @since 1.0.0
226
+ * @category Tracing
227
+ */
228
+ (f: (request: ServerRequest.HttpServerRequest) => string): <A, E, R>(layer: Layer.Layer<A, E, R>) => Layer.Layer<A, E, R>
229
+ /**
230
+ * Customizes the span name for the http app.
231
+ *
232
+ * ```ts
233
+ * import {
234
+ * HttpMiddleware,
235
+ * HttpRouter,
236
+ * HttpServer,
237
+ * HttpServerResponse
238
+ * } from "@effect/platform"
239
+ * import { NodeHttpServer, NodeRuntime } from "@effect/platform-node"
240
+ * import { Layer } from "effect"
241
+ * import { createServer } from "http"
242
+ *
243
+ * HttpRouter.empty.pipe(
244
+ * HttpRouter.get("/", HttpServerResponse.empty()),
245
+ * HttpServer.serve(),
246
+ * // Customize the span names for this HttpApp
247
+ * HttpMiddleware.withSpanNameGenerator((request) => `GET ${request.url}`),
248
+ * Layer.provide(NodeHttpServer.layer(createServer, { port: 3000 })),
249
+ * Layer.launch,
250
+ * NodeRuntime.runMain
251
+ * )
252
+ * ```
253
+ *
254
+ * @since 1.0.0
255
+ * @category Tracing
256
+ */
257
+ <A, E, R>(
258
+ layer: Layer.Layer<A, E, R>,
259
+ f: (request: ServerRequest.HttpServerRequest) => string
260
+ ): Layer.Layer<A, E, R>
261
+ } = internal.withSpanNameGenerator
@@ -44,12 +44,12 @@ export const currentTracerDisabledWhen = globalValue(
44
44
  export const withTracerDisabledWhen = dual<
45
45
  (
46
46
  predicate: Predicate.Predicate<ClientRequest.HttpClientRequest>
47
- ) => <A, E, R>(effect: Effect.Effect<A, E, R>) => Effect.Effect<A, E, R>,
48
- <A, E, R>(
49
- effect: Effect.Effect<A, E, R>,
47
+ ) => <E, R>(self: Client.HttpClient.With<E, R>) => Client.HttpClient.With<E, R>,
48
+ <E, R>(
49
+ self: Client.HttpClient.With<E, R>,
50
50
  predicate: Predicate.Predicate<ClientRequest.HttpClientRequest>
51
- ) => Effect.Effect<A, E, R>
52
- >(2, (self, pred) => Effect.locally(self, currentTracerDisabledWhen, pred))
51
+ ) => Client.HttpClient.With<E, R>
52
+ >(2, (self, pred) => transformResponse(self, Effect.locally(currentTracerDisabledWhen, pred)))
53
53
 
54
54
  /** @internal */
55
55
  export const currentTracerPropagation = globalValue(
@@ -61,12 +61,31 @@ export const currentTracerPropagation = globalValue(
61
61
  export const withTracerPropagation = dual<
62
62
  (
63
63
  enabled: boolean
64
- ) => <A, E, R>(effect: Effect.Effect<A, E, R>) => Effect.Effect<A, E, R>,
65
- <A, E, R>(
66
- effect: Effect.Effect<A, E, R>,
64
+ ) => <E, R>(self: Client.HttpClient.With<E, R>) => Client.HttpClient.With<E, R>,
65
+ <E, R>(
66
+ self: Client.HttpClient.With<E, R>,
67
67
  enabled: boolean
68
- ) => Effect.Effect<A, E, R>
69
- >(2, (self, enabled) => Effect.locally(self, currentTracerPropagation, enabled))
68
+ ) => Client.HttpClient.With<E, R>
69
+ >(2, (self, enabled) => transformResponse(self, Effect.locally(currentTracerPropagation, enabled)))
70
+
71
+ /** @internal */
72
+ export const SpanNameGenerator = Context.Reference<Client.SpanNameGenerator>()(
73
+ "@effect/platform/HttpClient/SpanNameGenerator",
74
+ {
75
+ defaultValue: () => (request: ClientRequest.HttpClientRequest) => `http.client ${request.method}`
76
+ }
77
+ )
78
+
79
+ /** @internal */
80
+ export const withSpanNameGenerator = dual<
81
+ (
82
+ f: (request: ClientRequest.HttpClientRequest) => string
83
+ ) => <E, R>(self: Client.HttpClient.With<E, R>) => Client.HttpClient.With<E, R>,
84
+ <E, R>(
85
+ self: Client.HttpClient.With<E, R>,
86
+ f: (request: ClientRequest.HttpClientRequest) => string
87
+ ) => Client.HttpClient.With<E, R>
88
+ >(2, (self, f) => transformResponse(self, Effect.provideService(SpanNameGenerator, f)))
70
89
 
71
90
  const ClientProto = {
72
91
  [TypeId]: TypeId,
@@ -193,8 +212,9 @@ export const make = (
193
212
  })
194
213
  )
195
214
  }
215
+ const nameGenerator = Context.get(fiber.currentContext, SpanNameGenerator)
196
216
  return Effect.useSpan(
197
- `http.client ${request.method}`,
217
+ nameGenerator(request),
198
218
  { kind: "client", captureStackTrace: false },
199
219
  (span) => {
200
220
  span.attribute("http.request.method", request.method)
@@ -72,6 +72,25 @@ export const withTracerDisabledForUrls = dual<
72
72
  ) => Layer.Layer<A, E, R>
73
73
  >(2, (self, urls) => Layer.locally(self, currentTracerDisabledWhen, (req) => urls.includes(req.url)))
74
74
 
75
+ /** @internal */
76
+ export const SpanNameGenerator = Context.Reference<Middleware.SpanNameGenerator>()(
77
+ "@effect/platform/HttpMiddleware/SpanNameGenerator",
78
+ {
79
+ defaultValue: () => (request: ServerRequest.HttpServerRequest) => `http.server ${request.method}`
80
+ }
81
+ )
82
+
83
+ /** @internal */
84
+ export const withSpanNameGenerator = dual<
85
+ (
86
+ f: (request: ServerRequest.HttpServerRequest) => string
87
+ ) => <A, E, R>(layer: Layer.Layer<A, E, R>) => Layer.Layer<A, E, R>,
88
+ <A, E, R>(
89
+ layer: Layer.Layer<A, E, R>,
90
+ f: (request: ServerRequest.HttpServerRequest) => string
91
+ ) => Layer.Layer<A, E, R>
92
+ >(2, (self, f) => Layer.provide(self, Layer.succeed(SpanNameGenerator, f)))
93
+
75
94
  /** @internal */
76
95
  export const logger = make((httpApp) => {
77
96
  let counter = 0
@@ -121,8 +140,9 @@ export const tracer = make((httpApp) =>
121
140
  }
122
141
  const redactedHeaderNames = fiber.getFiberRef(Headers.currentRedactedNames)
123
142
  const redactedHeaders = Headers.redact(request.headers, redactedHeaderNames)
143
+ const nameGenerator = Context.get(fiber.currentContext, SpanNameGenerator)
124
144
  return Effect.useSpan(
125
- `http.server ${request.method}`,
145
+ nameGenerator(request),
126
146
  {
127
147
  parent: Option.getOrUndefined(TraceContext.fromHeaders(request.headers)),
128
148
  kind: "server",