gpt4 book ai didi

rust - 如何创建一个 tokio 专用传输来覆盖默认的 tick 实现?

转载 作者:行者123 更新时间:2023-11-29 08:33:10 25 4
gpt4 key购买 nike

我正尝试在传输中使用非默认 tick() 方法编写流式管道服务器。我认为这会做到这一点:

use std::io;

use mio::net::TcpListener;
use tokio_core::reactor::PollEvented;
use tokio_io::{AsyncRead, AsyncWrite};
use tokio_io::codec::{Framed, Encoder, Decoder};
use tokio_proto::streaming::pipeline::Transport;

use codec::PacketCodec;

type GearmanIO = PollEvented<TcpListener>;
type GearmanFramed = Framed<GearmanIO, PacketCodec>;

impl Transport for GearmanFramed {
fn tick(&mut self) {
trace!("tick!");
}

fn cancel(&mut self) -> io::Result<()> {
trace!("cancel!");
}
}

但是,尝试构建此文件会产生以下结果:

error[E0119]: conflicting implementations of trait `tokio_proto::streaming::pipeline::Transport` for type `tokio_io::codec::Framed<tokio_core::reactor::PollEvented<mio::net::TcpListener>, codec::PacketCodec>`:
--> src/transport.rs:14:1
|
14 | / impl Transport for GearmanFramed
15 | | {
16 | | fn tick(&mut self) {
17 | | trace!("tick!");
... |
22 | | }
23 | | }
| |_^
|
= note: conflicting implementation in crate `tokio_proto`

error[E0117]: only traits defined in the current crate can be implemented for arbitrary types
--> src/transport.rs:14:1
|
14 | / impl Transport for GearmanFramed
15 | | {
16 | | fn tick(&mut self) {
17 | | trace!("tick!");
... |
22 | | }
23 | | }
| |_^ impl doesn't use types inside crate
|
= note: the impl does not reference any types defined in this crate
= note: define and implement a trait or new type instead

我本来希望 GearmanFramed 的特殊性质允许我实现 Transport 特性,因为“特化”,但这仍然与默认值冲突,这是在这里:

use tokio_io as new_io;

// ...

impl<T, C> Transport for new_io::codec::Framed<T,C>
where T: new_io::AsyncRead + new_io::AsyncWrite + 'static,
C: new_io::codec::Encoder<Error=io::Error> +
new_io::codec::Decoder<Error=io::Error> + 'static,
{}

最佳答案

经过几天的努力,我想通了。答案是使用一个新类型包围Framed,从而避免默认实现。

use std::io;

use tokio_io::{AsyncRead, AsyncWrite};
use tokio_io::codec::{Framed, Encoder, Decoder};
use tokio_proto::streaming::pipeline::Transport;
use futures::{Poll, Sink, StartSend, Stream};

use codec::PacketCodec;

pub struct GearmanFramed<T>(pub Framed<T, PacketCodec>);

impl<T> Transport for GearmanFramed<T>
where T: AsyncRead + AsyncWrite + 'static
{
fn tick(&mut self) {
trace!("tick!");
}

fn cancel(&mut self) -> io::Result<()> {
trace!("cancel!");
Ok(())
}
}

impl<T> Stream for GearmanFramed<T>
where T: AsyncRead
{
type Item = <PacketCodec as Decoder>::Item;
type Error = <PacketCodec as Decoder>::Error;
fn poll(&mut self) -> Poll<Option<Self::Item>, Self::Error> {
self.0.poll()
}
}

impl<T> Sink for GearmanFramed<T>
where T: AsyncWrite
{
type SinkItem = <PacketCodec as Encoder>::Item;
type SinkError = <PacketCodec as Encoder>::Error;
fn start_send(&mut self, item: Self::SinkItem) -> StartSend<Self::SinkItem, Self::SinkError> {
self.0.start_send(item)
}
fn poll_complete(&mut self) -> Poll<(), Self::SinkError> {
self.0.poll_complete()
}
fn close(&mut self) -> Poll<(), Self::SinkError> {
self.0.close()
}
}

关于rust - 如何创建一个 tokio 专用传输来覆盖默认的 tick 实现?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/44599487/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com