489 Commits

Author SHA1 Message Date
David Pedersen
d4865641e7
tower: prepare to release 0.4.10 (#608)
* tower: prepare to release 0.4.10

- Fix accidental breaking change when using the
  `rustdoc::broken_intra_doc_links` lint ([#605])
- Clarity that tower's minimum supported rust version is 1.46 ([#605])

[#605]: https://github.com/tower-rs/tower/pull/605

* Update tower/CHANGELOG.md

Co-authored-by: Oliver Gould <ver@buoyant.io>

Co-authored-by: Oliver Gould <ver@buoyant.io>
tower-0.4.10
2021-10-19 21:56:23 +02:00
David Pedersen
1c9631d7b3
chore: Bump MSRV to 1.46 (#605)
* Actually check MSCV on CI

* check broken_intra_doc_links on CI

* clean up CI

* fix other crates

* bump MSRV to 1.42 because of tracing-core

* attempt to fix http not working on 1.42

* use `--workspace` instead of `--all`

`--all` is deprecated

* make tower-service build on 1.42

* force http version 0.2.4

* actually msrv is 1.46 because of tokio

* fix running `cargo fmt`

* clean up

* also run tests on 1.46

* ignore rustsec in time
2021-10-19 16:28:55 +02:00
David Pedersen
62e09024aa
tower: prepare to release 0.4.9 (#602)
- Migrate to pin-project-lite ([#595])
- **builder**: Implement `Layer` for `ServiceBuilder` ([#600])
- **builder**: Add `ServiceBuilder::and_then` analogous to
  `ServiceExt::and_then` ([#601])

[#600]: https://github.com/tower-rs/tower/pull/600
[#601]: https://github.com/tower-rs/tower/pull/601
[#595]: https://github.com/tower-rs/tower/pull/595
[pin-project-lite]: https://crates.io/crates/pin-project-lite
tower-0.4.9
2021-10-14 09:12:28 +02:00
David Pedersen
c4cb3b0788
builder: Add ServiceBuilder::and_then (#601)
This one was missing.

Was the only combinator from `ServiceExt` that wasn't on
`ServiceBuilder` so now they match.
2021-09-04 13:05:46 -07:00
David Pedersen
d91c0f5ba3
builder: Implement Layer for ServiceBuilder (#600) 2021-09-03 18:54:49 +02:00
David Pedersen
3a134ba08a
util: Refactor BoxService (#598) 2021-08-26 06:54:29 +02:00
Michael-J-Ward
ee131aaf46
Migrate to pin project lite (#595)
* REMOVE ME updates peak_wema test to pass

* adds pin_project_lite dependency

* uses pin_project_lite for load::Constant

* uses pin_project_lite for load::PencingRequestsDiscover

* uses pin_project_lite for load::PeakEwma

* uses pin_project_lite for load::Completion

* uses pin_project_lite for tests::support::IntoStream

Turns IntoStream into a regular struct because pin_project_lite does not and will support tuple structs.

416be96f77/src/lib.rs (L401-L408)

* refactors opaque_future into a regular struct

This enables migration to pin_project_lite, which does not and will not support tuple structs
416be96f77/src/lib.rs (L401-L408)

* migrates opaque_future to use pin_project_lite

* removes tuple variant from load_shed::ResponseState enum

* migrates load_shed::future to pin_project_lite

* removes tuple variant from filter::future::State

* migrates filter::future to pin_project_lite

Note: the doc comment on AsyncResponseFuture::service was also reduced to a regular comment.

This is a known limitation of pin_project_lite that the they have labeled as "help wanted".
https://github.com/taiki-e/pin-project-lite/issues/3#issuecomment-745194112

* migrates retry::Retry to pin_project_lite

* refactors retry::future::State to enable pin_project_lite

pin_project_lite has the current limitation of nto supporting doc comments
https://github.com/taiki-e/pin-project-lite/issues/3#issuecomment-745194112

pin_project_lite does not and will not support tuple variants
416be96f77/src/lib.rs (L401-L408)

* migrates retry::future to pin_project_lite

* migrates spawn_ready::make to pin_project_lite

* refactors buffer::future::ResponseState to allow pin_project_lite

* migrates buffer::future to pin_project_lite

* refactors util::AndThenFuture to allow pin_project_lite

* migrates util::AndThenFuture to pin_project_lite

* migrates hedge::Future to pin_project_lite

* migrates hedge::select::ResponseFuture to pin_project_lite

* refactors hedge::delay enum for pin_project_lite

* refactors reconnect::future enum for pin_project_lite

* refactors oneshot::State enum for pin_project_lite

* migrates util::oneshot to pin_project_lite

* migrates reconnect::future to pin_project_lite

* migrates hedge::delay to pin_project_lite

* migrates hedge::latency to pin_project_lite

* migrates discover::list to pin_project_lite

* migrates timeout::future to pin_project_lite

* migrates balance::pool to pin_project_lite

* migrates balance::p2c::make to pin_project_lite

* migrates balance::p2c::service to pin_project_lite

* migrates call_all::ordered to pin_project_lite

* migrates call_all::common to pin_project_lite

* migrates call_all::unordered to pin_project_lite

* migrates util::optional::future to pin_project_lite

* migrates limit::concurrency::future to pin_project_lite

* migrates tower-balance example to pin_project_lite

* applies cargo fmt

* migrates tower-test to pin_project_lite

* fixes cargo hack check

peak_wma and pending_requests will now properly compile without the "discover" feature enabled.

* fixes lint rename warning on nightly

broken_intra_doc_links has been renamed to rustdoc::broken_intra_doc_links

* migrates buffer::Worker to pin_project_lite

pin_project_lite does support PinnedDrop
https://github.com/taiki-e/pin-project-lite/pull/25/files

However, it does not support generic trait bounds on the PinnedDrop impl.

To workaround this, I removed the T::Error bound from the Worker struct definition,
and moved `close_semaphore` to a a new impl without that trait bound.

* fixes abort_on_drop test

This test was also failing on master.

* applies cargo fmt
2021-07-28 13:48:47 -04:00
David Pedersen
77760198f1
docs: add "Building a middleware from scratch" guide (#590)
This adds a guide that explains how to implement a middleware from scratch without taking any shortcuts. It walks through implementing `Timeout` as it exists in Tower today.

The hope is that once users have read [the previous guide](https://tokio.rs/blog/2021-05-14-inventing-the-service-trait) followed by this one they should be fully equipped to implement their own middleware.
2021-06-07 11:06:30 +02:00
kazk
31dbc90c45
Add kube to the list of libraries (#592) 2021-06-06 08:54:21 +02:00
David Pedersen
b5d2c8f1d3
tower: prepare to release 0.4.8 (#591) tower-0.4.8 2021-05-28 22:18:09 +02:00
Jerome Gravel-Niquet
74f9047f30
Allow reusable concurrency limit via GlobalConcurrencyLimit (#574)
* limit: global concurrency limit layer from a owned semaphore

* new_owned -> new_shared + docs improvements

Co-authored-by: David Pedersen <david.pdrsn@gmail.com>

* keep exposing Semaphore, but rename the API a bit and make it simpler to use

* missed a spot

* minor docs fixes

* update changelog

Co-authored-by: David Pedersen <david.pdrsn@gmail.com>
Co-authored-by: Eliza Weisman <eliza@buoyant.io>
2021-05-28 16:45:44 +02:00
Lucio Franco
71ece8ea5a
Fix warning in oneshot test (#587)
Co-authored-by: David Pedersen <david.pdrsn@gmail.com>
2021-05-18 16:31:29 -04:00
David Pedersen
ce2f031523
docs: guide moved to tokio.rs (#588) 2021-05-18 14:35:19 +02:00
David Pedersen
31d5a6652a
Fix a couple of typos in the guide (#586) 2021-05-17 19:36:04 +02:00
David Pedersen
5e0c8da260
docs: Add "Inventing the Service trait" guide (#585)
This adds the first Tower guide called "Inventing the `Service` trait". It attempts to motivate all the parts to `Service` by walking the user through how they could have invented `Service` themselves, from scratch. It goes into quite a bit of detail but hopefully it paints a somewhat complete picture in the end.

The next guide I want to write is about how to implement a proper `Timeout` middleware using `Layer`, pin-project, and all the bells and whistles.

Ref: https://github.com/tower-rs/tower/issues/33
2021-05-14 22:59:43 +02:00
David Pedersen
53ec99eb8f
builder: Add ServiceBuilder::map_result (#583)
Noticed that `ServiceBuilder` didn't have `map_result`, only `then`
which is async.
2021-05-07 09:42:31 -07:00
David Pedersen
7b1528815e
service: Clarify subtly around cloning and readiness (#548)
* service: Clarify subtly around cloning and readiness

* Fix typo
2021-05-06 09:26:50 +02:00
Eliza Weisman
58544d65d9
tower: prepare to release 0.4.7 (#582)
# 0.4.7 (April 27, 2021)

### Added

- **builder**: Add `ServiceBuilder::check_service` to check the request,
    response, and error types of the output service. ([#576])
- **builder**: Add `ServiceBuilder::check_service_clone` to check the
  output service can be cloned. ([#576])

### Fixed

- **spawn_ready**: Abort spawned background tasks when the `SpawnReady`
  service is dropped, fixing a potential task/resource leak (#[581])
- Fixed broken documentation links ([#578])

[#576]: https://github.com/tower-rs/tower/pull/576
[#578]: https://github.com/tower-rs/tower/pull/578
[#581]: https://github.com/tower-rs/tower/pull/581
tower-0.4.7
2021-04-27 12:59:57 -07:00
Oliver Gould
8ceee45fdf
spawn-ready: Abort background tasks when the service is dropped (#581)
The `SpawnReady` service spawns a background task whenever the inner
service is not ready; but when the `SpawnReady` service is dropped, this
task continues to run until it becomes ready (at which point the ready
service will be dropped). This can cause resource leaks when the inner
service never becomes ready.

This change adds a `Drop` implementation for the `SpawnReady` service
that aborts the background task when one is present.

Co-authored-by: Eliza Weisman <eliza@buoyant.io>
2021-04-27 10:26:07 -07:00
Michał Zabielski
7b4ebc6c3e
chore: add explicit feature flag for tower-balance example (#580) 2021-04-22 16:38:58 -04:00
Folyd
1467321fab
chore: convert rest doc-links to intra-doc links (#578) 2021-04-21 13:02:58 +02:00
David Pedersen
9b4261fe8a
builder: Add type check utility methods (#576) 2021-04-08 23:39:15 +02:00
Eliza Weisman
e1760d385d
tower: prepare to release v0.4.6 (#573)
Deprecated

- **util**: Deprecated `ServiceExt::ready_and` (renamed to
  `ServiceExt::ready`). ([#567])
- **util**: Deprecated `ReadyAnd` future (renamed to `Ready`). ([#567])

Added

- **builder**: Add `ServiceBuilder::layer_fn` to add a layer built from
  a function. ([#560])
- **builder**: Add `ServiceBuilder::map_future` for transforming the
  futures produced by a service. ([#559])
- **builder**: Add `ServiceBuilder::service_fn` for applying `Layer`s to
  an async function using `util::service_fn`. ([#564])
- **util**: Add example for `service_fn`. ([#563])
- **util**: Add `BoxLayer` for creating boxed `Layer` trait objects.
  ([#569])

[#567]: https://github.com/tower-rs/tower/pull/567
[#560]: https://github.com/tower-rs/tower/pull/560
[#559]: https://github.com/tower-rs/tower/pull/559
[#564]: https://github.com/tower-rs/tower/pull/564
[#563]: https://github.com/tower-rs/tower/pull/563
[#569]: https://github.com/tower-rs/tower/pull/569

Signed-off-by: Eliza Weisman <eliza@buoyant.io>
2021-03-01 09:32:29 -08:00
David Pedersen
f2505d2ade
util: Add BoxLayer (#569)
I've run into a use case where I need to return a `Layer` with a complex
type from a function. I previously used `impl Layer<S, Service = impl
Service<...>>` but that impacted compile times quite significantly.
Boxing the `Layer` fixed it. Thought it made sense to upstream.

The `Send + Sync + 'static` bounds on the inner `dyn Layer` were
necessary to get it working with hyper.

Co-authored-by: Eliza Weisman <eliza@buoyant.io>
2021-02-26 15:35:47 -08:00
David Barsky
208160e6bb
chore: add Netlify redirect to tower/` (#572)
Co-authored-by: Eliza Weisman <eliza@buoyant.io>
2021-02-25 17:28:48 -05:00
David Pedersen
7461abc6b5
builder: Add ServiceBuilder::service_fn (#564)
* builder: Add `ServiceBuilder::service_fn`

A small convenience for doing `.service(service_fn(handler_function))`.

* Docs tweaks

* Apply suggestions from code review

Co-authored-by: Eliza Weisman <eliza@buoyant.io>

* Fix

Co-authored-by: Eliza Weisman <eliza@buoyant.io>
2021-02-25 22:52:37 +01:00
David Pedersen
9948f2561d
builder: Add ServiceBuilder::layer_fn (#560)
This gem as just [sitting in Tonic][sit] waiting to be upstreamed.

[sit]: https://github.com/hyperium/tonic/blob/master/tonic/src/transport/service/layer.rs

Co-authored-by: Eliza Weisman <eliza@buoyant.io>
2021-02-25 22:33:35 +01:00
David Barsky
b538246296
chore: remove unnecessary mut and imports in tests (#570)
Co-authored-by: Eliza Weisman <eliza@buoyant.io>
2021-02-25 16:19:59 -05:00
David Barsky
db0b2c5885
chore: create doc preview website with Netlify (#571)
* chore: create doc preview website with Netlify

* Remove redirects
2021-02-25 13:10:15 -08:00
David Pedersen
a63e3cf07a
util: Add example for service_fn (#563) 2021-02-25 10:17:37 -08:00
David Barsky
a8884ae150
util: Rename ServiceExt::ready_and to ServiceExt::ready (#567)
This PR renames: 

- `ServiceExt::ready_and` to `ServiceExt::ready`
- the `ReadyAnd` future to `Ready`
- the associated documentation to refer to `ServiceExt::ready`
  and `ReadyAnd`.

This PR deprecates:

- the `ServiceExt::ready_and` method
- the `ReadyAnd` future

These can be removed in Tower 0.5.

My recollection of the original conversation surrounding the
introduction of the `ServiceExt::ready_and` combinator in
https://github.com/tower-rs/tower/pull/427 was that it was meant to be a
temporary workaround for the unchainable `ServiceExt::ready` combinator
until the next breaking release of the Tower crate. The unchainable
`ServiceExt::ready` combinator was removed, but `ServiceExt::ready_and`
was not renamed. I believe, but am not 100% sure, that this was an
oversight.
2021-02-25 09:37:45 -08:00
David Pedersen
04369f3b8f
builder: Add ServiceBuilder::map_future (#559)
* builder: Add `ServiceBuilder::map_future`

I forgot at add this one in #542. Think its nice to have for
consistency.

* Update tower/src/builder/mod.rs

Co-authored-by: Eliza Weisman <eliza@buoyant.io>

Co-authored-by: Eliza Weisman <eliza@buoyant.io>
2021-02-18 21:53:57 +01:00
David Pedersen
ba3d431c04
tower: prepare to release v0.4.5 (#558)
* tower: prepare to release v0.4.5

* Minor docs fix

* fix wordings

* Fix tense

* more wording

* move
tower-0.4.5
2021-02-11 00:12:52 +01:00
Eliza Weisman
ec547b329b
spawn_ready: propagate tracing spans (#557)
Currently, when using `SpawnReady`, the current `tracing` span is not
propagated to the spawned task when the inner service is not ready. This
means that any traces emitted by the inner service's `poll_ready` occur
in their own root span, rather than the span the `SpawnReady` service
was polled in.

This branch fixes this by propagating the current trace span to the
spawned task.

This means that "spawn-ready" now enables the "tracing" feature. In the
future, we may want to consider feature-flagging `tracing` separately
from the middleware implementation that contain tracing instrumentation,
but doing so would break traces if the feature flag isn't enabled. This
doesn't break API compatibility, but it *does* break functionality, so
we may not want to do that until the next breaking change release.

I also added tests for span propagation. I realized the same test could
easily be applied to `Buffer`, which also propagates `tracing` spans, to
guard against regressions, so I also added a test for buffer.

Signed-off-by: Eliza Weisman <eliza@buoyant.io>
2021-02-10 15:01:58 -08:00
David Pedersen
f90f518f9f
make: Add Shared (#533)
* make: Add `Shared`

Fixes https://github.com/tower-rs/tower/issues/262

`Shared` is a `MakeService` that produces services by cloning an inner
service.

* Fix build with different set of features

* Formatting

* Make `Shared` generic over any target

* Fix tests

* Move `Shared` into its own file

* Add example
2021-02-10 22:28:23 +01:00
kazk
e49700a79d
Add util::option_layer and ServiceBuilder::option_layer (#555)
* Add `util::option_layer` and `ServiceBuilder::option_layer`

Closes #553

* Apply suggestions to improve the docs

Co-authored-by: Eliza Weisman <eliza@buoyant.io>

Co-authored-by: Eliza Weisman <eliza@buoyant.io>
2021-02-10 22:17:25 +01:00
Eliza Weisman
ccfaffc1f4
buffer, limit: use tokio-util's PollSemaphore (#556)
The [`Semaphore` implementation in `tokio::sync`][1] doesn't expose a
`poll_acquire` method to acquire owned semaphore permits in a
non-async-await context. Currently, the `limit::concurrency` and
`buffer` middleware use our own pollable wrapper for
`tokio::sync::Semaphore`. This works by creating a new
`Semaphore::acquire_owned` future and boxing it every time the semaphore
starts acquiring a new permit.

Recently, the `tokio_util` crate introduced its own [`PollSemaphore`
wrapper type][2]. This provides the same functionality of a pollable
version of `tokio::sync`'s `Semaphore`, just like our semaphore wrapper.
However, `tokio_util`'s version is significantly more efficient: rather
than allocating a new `Box` for _each_ `acquire_owned` future, it uses
the [`ReusableBoxFuture` type][3] to reuse a *single* allocation every
time a new `acquire_owned` future is needed. This means that rather than
allocating *every* time a `Buffer` or `ConcurrencyLimit` service starts
acquiring a new permit, there's a single allocation for each clone of
the service. Unless services are cloned per-request, this means that the
allocation is moved out of the request path in most cases.

I had originally considered an approach similar to this, but I didn't
think the reduced allocations were worth adding a bunch of unsafe code
in `tower` (which presently contains no unsafe code). However, this type
fits in perfectly in `tokio-util`, and now that there's an upstream
implementation, we should use it.

This introduces a dependency on `tokio-util` when the "limit" or "buffer"
features are enabled.

Additionally, I've added a new test for `Buffer` asserting that once an
individual `Buffer` service has been driven to readiness but not called,
additional `poll_ready` calls won't acquire additional buffer capacity.
This reproduces a bug that existed in earlier versions of
`tower::buffer`, which could result in starvation of buffer waiters.
This bug doesn't exist in 0.4, but I wanted to ensure that changing the
buffer internals here didn't introduce any new regressions.

[1]: https://docs.rs/tokio/1.2.0/tokio/sync/struct.Semaphore.html
[2]: https://docs.rs/tokio-util/0.6.3/tokio_util/sync/struct.PollSemaphore.html
[3]: https://docs.rs/tokio-util/0.6.3/src/tokio_util/sync/poll_semaphore.rs.html#13-16

Signed-off-by: Eliza Weisman <eliza@buoyant.io>
2021-02-10 11:52:40 -08:00
David Pedersen
52fab7c446
steer: Implement Clone for Steer (#554) 2021-02-09 15:41:07 -08:00
David Pedersen
0226ef0f4c
Make combinators implement Debug in more cases (#552)
Co-authored-by: Eliza Weisman <eliza@buoyant.io>
2021-01-27 23:47:04 +01:00
David Pedersen
02b6731350
Only pull in tracing when necessary (#551)
Fixes https://github.com/tower-rs/tower/issues/549

Tested with `cargo hack check --each-feature --no-dev-deps`
2021-01-27 14:16:07 -08:00
David Pedersen
d80044f825
util: Add ServiceExt::map_future (#542)
* util: Add `ServiceExt::map_future`

I ran into a thing today where I wanted to write a middleware that wraps
all futures produced by a service in a `tracing::Span`. So something
like `self.inner.call(req).instrument(span)`.

Afaik all the combinators we have today receive the value produced by
the future and not the future itself. At that point its too late to call
`.instrument`. So I thought this made sense to add a combinator for.

* Add additional trait bounds to improve UX

* Add docs

* Update changelog

* Clean up debug impl

* Better debug impl for `MapFutureLayer`
2021-01-27 09:39:15 +01:00
David Pedersen
776f215135
tower-service: prepare to release v0.3.1 (#540)
Co-authored-by: Eliza Weisman <eliza@buoyant.io>
2021-01-23 12:31:05 +01:00
Eliza Weisman
3d9efce2d3
tower: expand on usage docs, mention compatible libraries (#529)
This branch adds to the "Usage" section in the `tower` crate's README
and lib.rs docs. In particular, I've added a discussion of the various
use-cases for Tower, and a list of crates that support Tower.

Let me know if I'm missing anything!
2021-01-21 09:29:21 -08:00
David Pedersen
886f72a53e
tower: prepare to release v0.4.4 (#539) tower-0.4.4 2021-01-20 16:21:57 +01:00
David Pedersen
2683ab6231
Add "full" feature that turns on all other features (#532)
* Add "full" feature that turns on all other features

Fixes https://github.com/tower-rs/tower/issues/530

* Don't include "log" feature in "full"

Makes it easier to disable "log" since its already included in the
default feature set.

* Fix changelog
2021-01-20 16:02:04 +01:00
Oliver Gould
f2bb123928
spawn-ready: Avoid oneshot allocations (#538)
This change modifies the `SpawnReady` service to track a
`tokio::task::JoinHandle` instead of creating a `tokio::sync::oneshot`
on each pending poll. This avoid unnecessary allocation.

The `spawn_ready` test is also fixed to avoid using `thread::sleep`,
instead using `tokio::time::pause`.
2021-01-19 10:12:16 -08:00
teor
1cd65c104c
util: Fix some doc comment typos (#537)
* Fix a comment typo in util::and_then

* Fix apostrophes in tower::util doc comments

* Add a missing word in the tower::util module comment
2021-01-19 12:03:37 +01:00
David Pedersen
f62c5b5350
service: Improve example in docs (#510)
* Fix typos in docs

* Make example in `Service` docs runnable

* Apply suggestions from code review

Co-authored-by: Eliza Weisman <eliza@buoyant.io>

* Update tower-service/src/lib.rs

Co-authored-by: Lucio Franco <luciofranco14@gmail.com>

* Update tower-service/src/lib.rs

Co-authored-by: Lucio Franco <luciofranco14@gmail.com>

* Update tower-service/src/lib.rs

Co-authored-by: Lucio Franco <luciofranco14@gmail.com>

* Update tower-service/src/lib.rs

Co-authored-by: Lucio Franco <luciofranco14@gmail.com>

* Consistent casing

* Consistent casing - take 2

* Update changelog

Co-authored-by: Eliza Weisman <eliza@buoyant.io>
Co-authored-by: Lucio Franco <luciofranco14@gmail.com>
2021-01-19 10:25:00 +01:00
David Pedersen
487e531c8b limit: Implement Clone for RateLimitLayer 2021-01-18 12:26:55 +01:00
David Pedersen
78a32743bd timeout: Implement Clone for TimeoutLayer 2021-01-18 12:26:38 +01:00