استفاده از WebTransport، استفاده از WebTransport

WebTransport یک API است که پیام‌رسانی مشتری-سرور را با تاخیر کم، دو جهته ارائه می‌دهد. درباره موارد استفاده آن و نحوه ارائه بازخورد در مورد آینده اجرای آن بیشتر بیاموزید.

WebTransport یک API وب است که از پروتکل HTTP/3 به عنوان یک انتقال دوطرفه استفاده می کند. این برای ارتباطات دو طرفه بین یک سرویس گیرنده وب و یک سرور HTTP/3 در نظر گرفته شده است. از ارسال داده ها به صورت غیرقابل اعتماد از طریق API های دیتاگرام خود و به طور قابل اعتماد از طریق API های جریانی خود پشتیبانی می کند.

دیتاگرام ها برای ارسال و دریافت داده هایی که نیاز به ضمانت تحویل قوی ندارند ایده آل هستند. بسته های منفرد داده از نظر اندازه توسط حداکثر واحد انتقال (MTU) اتصال زیربنایی محدود می شوند و ممکن است با موفقیت ارسال شوند یا نشوند و اگر منتقل شوند، ممکن است به ترتیب دلخواه برسند. این ویژگی ها API های دیتاگرام را برای انتقال داده با تاخیر کم و بهترین تلاش ایده آل می کند. می‌توانید دیتاگرام‌ها را به‌عنوان پیام‌های پروتکل داده‌گرام کاربر (UDP) در نظر بگیرید، اما رمزگذاری شده و تحت کنترل تراکم هستند.

در مقابل، APIهای استریم، انتقال داده قابل اعتماد و منظم را ارائه می دهند. آنها برای سناریوهایی که شما نیاز به ارسال یا دریافت یک یا چند جریان داده سفارش داده شده دارید، مناسب هستند. استفاده از چندین جریان WebTransport مشابه برقراری چندین اتصال TCP است، اما از آنجایی که HTTP/3 از پروتکل QUIC با وزن سبک‌تر در زیر هود استفاده می‌کند، می‌توان آنها را بدون سربار باز و بسته کرد.

موارد استفاده کنید

این فهرست کوچکی از راه‌های ممکن است که توسعه‌دهندگان ممکن است از WebTransport استفاده کنند.

  • ارسال وضعیت بازی در یک بازه زمانی منظم با کمترین تأخیر به سرور از طریق پیام‌های کوچک، غیرقابل اعتماد و خارج از نظم.
  • دریافت جریان‌های رسانه ارسال‌شده از سرور با حداقل تأخیر، مستقل از سایر جریان‌های داده.
  • دریافت اعلان های ارسال شده از سرور در حالی که یک صفحه وب باز است.

ما علاقه مندیم درباره نحوه استفاده از WebTransport بیشتر بدانیم .

پشتیبانی از مرورگر

پشتیبانی مرورگر

  • کروم: 97.
  • لبه: 97.
  • فایرفاکس: 114.
  • سافاری: پشتیبانی نمی شود.

منبع

مانند همه ویژگی‌هایی که از مرورگر جهانی پشتیبانی نمی‌کنند، کدنویسی دفاعی از طریق تشخیص ویژگی بهترین روش است.

وضعیت فعلی

مرحله وضعیت
1. توضیح دهنده ایجاد کنید کامل
2. پیش نویس اولیه مشخصات را ایجاد کنید کامل
3. بازخورد جمع آوری کنید و طراحی را تکرار کنید کامل
4. آزمایش مبدا کامل
5. راه اندازی کنید کروم 97

ارتباط WebTransport با سایر فناوری ها

آیا WebTransport جایگزینی برای WebSockets است؟

شاید. مواردی وجود دارد که WebSockets یا WebTransport ممکن است پروتکل های ارتباطی معتبری برای استفاده باشند.

ارتباطات WebSockets حول یک جریان منفرد، قابل اعتماد و مرتب از پیام ها مدل می شوند که برای برخی از انواع نیازهای ارتباطی مناسب است. اگر به این ویژگی ها نیاز دارید، API های جریان WebTransport نیز می توانند آنها را ارائه دهند. در مقایسه، APIهای دیتاگرام WebTransport، تحویل با تأخیر کم را بدون ضمانت در مورد قابلیت اطمینان یا سفارش ارائه می‌کنند، بنابراین آنها جایگزین مستقیمی برای WebSockets نیستند.

استفاده از WebTransport، از طریق APIهای دیتاگرام یا از طریق چندین نمونه API Streams همزمان، به این معنی است که شما نیازی به نگرانی در مورد مسدود کردن سرفصل‌ها ندارید، که می‌تواند مشکلی برای WebSockets باشد. علاوه بر این، هنگام ایجاد اتصالات جدید، مزایای عملکردی نیز وجود دارد، زیرا دست دادن QUIC اساسی سریعتر از راه اندازی TCP از طریق TLS است.

WebTransport بخشی از یک پیش نویس مشخصات جدید است و به همین دلیل اکوسیستم WebSocket در اطراف کتابخانه های مشتری و سرور در حال حاضر بسیار قوی تر است. اگر به چیزی نیاز دارید که با تنظیمات سرور رایج و با پشتیبانی گسترده مشتری وب کار کند، WebSockets امروز انتخاب بهتری است.

آیا WebTransport همان UDP Socket API است؟

خیر. WebTransport یک API سوکت UDP نیست. در حالی که WebTransport از HTTP/3 استفاده می کند، که به نوبه خود از UDP "زیر سرپوش" استفاده می کند، WebTransport دارای الزاماتی در مورد رمزگذاری و کنترل تراکم است که آن را فراتر از یک UDP Socket API اساسی می کند.

آیا WebTransport جایگزینی برای کانال های داده WebRTC است؟

بله، برای اتصالات مشتری-سرور. WebTransport بسیاری از ویژگی های مشابه کانال های داده WebRTC را به اشتراک می گذارد، اگرچه پروتکل های اساسی متفاوت هستند.

به طور کلی، اجرای یک سرور سازگار با HTTP/3 به تنظیمات و پیکربندی کمتری نسبت به نگهداری یک سرور WebRTC نیاز دارد، که شامل درک پروتکل های متعدد ( ICE ، DTLS و SCTP ) برای به دست آوردن یک حمل و نقل کارآمد است. WebRTC شامل قطعات متحرک بسیاری است که می تواند منجر به شکست مذاکرات مشتری/سرور شود.

WebTransport API با در نظر گرفتن موارد استفاده توسعه دهندگان وب طراحی شده است و باید بیشتر شبیه نوشتن کد پلت فرم وب مدرن باشد تا استفاده از رابط های کانال داده WebRTC. برخلاف WebRTC ، WebTransport در داخل Web Workers پشتیبانی می‌شود، که به شما امکان می‌دهد ارتباطات مشتری-سرور را مستقل از یک صفحه HTML معین انجام دهید. از آنجایی که WebTransport یک رابط سازگار با Streams را نشان می‌دهد، از بهینه‌سازی‌های مربوط به فشار برگشتی پشتیبانی می‌کند.

با این حال، اگر قبلاً یک راه‌اندازی سرویس گیرنده/سرور WebRTC دارید که از آن راضی هستید، تغییر به WebTransport ممکن است مزایای زیادی نداشته باشد.

آن را امتحان کنید

بهترین راه برای آزمایش WebTransport راه اندازی یک سرور HTTP/3 سازگار است. سپس می توانید از این صفحه با یک کلاینت اصلی جاوا اسکریپت برای آزمایش ارتباطات مشتری/سرور استفاده کنید.

علاوه بر این، یک سرور اکو نگهداری شده توسط جامعه در webtransport.day موجود است.

با استفاده از API

WebTransport بر روی پلتفرم های وب مدرن اولیه مانند Streams API طراحی شده است. به شدت به وعده ها متکی است و با async و await به خوبی کار می کند.

پیاده‌سازی WebTransport کنونی در Chromium از سه نوع مجزای ترافیک پشتیبانی می‌کند: دیتاگرام‌ها، و همچنین جریان‌های یک طرفه و دو طرفه.

اتصال به سرور

می توانید با ایجاد یک نمونه WebTransport به سرور HTTP/3 متصل شوید. طرح URL باید https باشد. باید به صراحت شماره پورت را مشخص کنید.

باید از وعده ready برای صبر کردن برای برقراری ارتباط استفاده کنید. این وعده تا زمانی که راه‌اندازی کامل نشود محقق نمی‌شود و اگر اتصال در مرحله QUIC/TLS شکست بخورد، رد می‌شود.

وعده closed زمانی محقق می شود که اتصال به طور معمول بسته شود، و اگر بسته شدن غیرمنتظره باشد، رد می شود.

اگر سرور اتصال را به دلیل خطای نشانگر مشتری رد کند (مثلاً مسیر URL نامعتبر است)، آنگاه باعث می‌شود closed به رد شود، در حالی که ready حل نشده باقی می‌ماند.

const url = 'https://example.com:4999/foo/bar';
const transport = new WebTransport(url);

// Optionally, set up functions to respond to
// the connection closing:
transport.closed.then(() => {
  console.log(`The HTTP/3 connection to ${url} closed gracefully.`);
}).catch((error) => {
  console.error(`The HTTP/3 connection to ${url} closed due to ${error}.`);
});

// Once .ready fulfills, the connection can be used.
await transport.ready;

API های دیتاگرام

هنگامی که یک نمونه WebTransport دارید که به یک سرور متصل است، می‌توانید از آن برای ارسال و دریافت بیت‌های گسسته داده، به نام دیتاگرام استفاده کنید.

گیرنده writeable یک WritableStream را برمی‌گرداند که یک سرویس گیرنده وب می‌تواند از آن برای ارسال داده به سرور استفاده کند. دریافت‌کننده readable یک ReadableStream را برمی‌گرداند و به شما امکان می‌دهد به داده‌های سرور گوش دهید. هر دو جریان ذاتا غیر قابل اعتماد هستند، بنابراین ممکن است داده هایی که می نویسید توسط سرور دریافت نشود و بالعکس.

هر دو نوع جریان از نمونه های Uint8Array برای انتقال داده استفاده می کنند.

// Send two datagrams to the server.
const writer = transport.datagrams.writable.getWriter();
const data1 = new Uint8Array([65, 66, 67]);
const data2 = new Uint8Array([68, 69, 70]);
writer.write(data1);
writer.write(data2);

// Read datagrams from the server.
const reader = transport.datagrams.readable.getReader();
while (true) {
  const {value, done} = await reader.read();
  if (done) {
    break;
  }
  // value is a Uint8Array.
  console.log(value);
}

APIهای جریانی

پس از اتصال به سرور، می‌توانید از WebTransport برای ارسال و دریافت داده‌ها از طریق Streams API آن نیز استفاده کنید.

هر تکه از تمام جریان ها یک Uint8Array است. برخلاف API های Datagram، این جریان ها قابل اعتماد هستند. اما هر جریان مستقل است، بنابراین ترتیب داده ها در سراسر جریان ها تضمین نمی شود.

WebTransportSendStream

یک WebTransportSendStream توسط سرویس گیرنده وب با استفاده از متد createUnidirectionalStream() یک نمونه WebTransport ایجاد می شود که یک وعده برای WebTransportSendStream برمی گرداند.

از متد close() WritableStreamDefaultWriter برای بستن اتصال HTTP/3 مرتبط استفاده کنید. مرورگر سعی می کند قبل از بستن اتصال مرتبط، تمام داده های معلق را ارسال کند.

// Send two Uint8Arrays to the server.
const stream = await transport.createUnidirectionalStream();
const writer = stream.writable.getWriter();
const data1 = new Uint8Array([65, 66, 67]);
const data2 = new Uint8Array([68, 69, 70]);
writer.write(data1);
writer.write(data2);
try {
  await writer.close();
  console.log('All data has been sent.');
} catch (error) {
  console.error(`An error occurred: ${error}`);
}

به طور مشابه، از متد abort() WritableStreamDefaultWriter برای ارسال RESET\_STREAM به سرور استفاده کنید. هنگام استفاده از abort() ، مرورگر ممکن است داده‌های معلقی را که هنوز ارسال نشده است دور بیندازد.

const ws = await transport.createUnidirectionalStream();
const writer = ws.getWriter();
writer.write(...);
writer.write(...);
await writer.abort();
// Not all the data may have been written.

WebTransportReceiveStream

یک WebTransportReceiveStream توسط سرور آغاز می شود. دریافت WebTransportReceiveStream یک فرآیند دو مرحله ای برای یک سرویس گیرنده وب است. ابتدا، ویژگی incomingUnidirectionalStreams یک نمونه WebTransport را فراخوانی می کند که یک ReadableStream برمی گرداند. هر تکه از آن ReadableStream به نوبه خود یک WebTransportReceiveStream است که می تواند برای خواندن نمونه های Uint8Array ارسال شده توسط سرور استفاده شود.

async function readFrom(receiveStream) {
  const reader = receiveStream.readable.getReader();
  while (true) {
    const {done, value} = await reader.read();
    if (done) {
      break;
    }
    // value is a Uint8Array
    console.log(value);
  }
}

const rs = transport.incomingUnidirectionalStreams;
const reader = rs.getReader();
while (true) {
  const {done, value} = await reader.read();
  if (done) {
    break;
  }
  // value is an instance of WebTransportReceiveStream
  await readFrom(value);
}

شما می توانید بسته شدن جریان را با استفاده از قول closed ReadableStreamDefaultReader تشخیص دهید. هنگامی که اتصال HTTP/3 زیربنایی با بیت FIN بسته می شود، پس از خواندن همه داده ها، وعده closed محقق می شود. هنگامی که اتصال HTTP/3 به طور ناگهانی بسته می شود (به عنوان مثال، توسط RESET\_STREAM )، سپس قول closed رد می شود.

// Assume an active receiveStream
const reader = receiveStream.readable.getReader();
reader.closed.then(() => {
  console.log('The receiveStream closed gracefully.');
}).catch(() => {
  console.error('The receiveStream closed abruptly.');
});

WebTransportBidirectionalStream

یک WebTransportBidirectionalStream ممکن است توسط سرور یا مشتری ایجاد شود.

کلاینت های وب می توانند با استفاده از متد createBidirectionalStream() یک نمونه WebTransport یکی ایجاد کنند که یک وعده WebTransportBidirectionalStream را برمی گرداند.

const stream = await transport.createBidirectionalStream();
// stream is a WebTransportBidirectionalStream
// stream.readable is a ReadableStream
// stream.writable is a WritableStream

می توانید به یک WebTransportBidirectionalStream که توسط سرور با ویژگی incomingBidirectionalStreams یک نمونه WebTransport ایجاد شده است گوش دهید، که ReadableStream برمی گرداند. هر تکه از آن ReadableStream به نوبه خود یک WebTransportBidirectionalStream است.

const rs = transport.incomingBidirectionalStreams;
const reader = rs.getReader();
while (true) {
  const {done, value} = await reader.read();
  if (done) {
    break;
  }
  // value is a WebTransportBidirectionalStream
  // value.readable is a ReadableStream
  // value.writable is a WritableStream
}

یک WebTransportBidirectionalStream فقط ترکیبی از WebTransportSendStream و WebTransportReceiveStream است. مثال های دو بخش قبل نحوه استفاده از هر یک از آنها را توضیح می دهد.

نمونه های بیشتر

مشخصات پیش نویس WebTransport شامل تعدادی مثال درون خطی اضافی، همراه با مستندات کامل برای همه روش ها و ویژگی ها است.

WebTransport در DevTools کروم

متأسفانه DevTools Chrome در حال حاضر از WebTransport پشتیبانی نمی کند. می‌توانید این مشکل Chrome را ستاره‌دار کنید تا از به‌روزرسانی‌های رابط DevTools مطلع شوید.

پلی پر

یک polyfill (یا بهتر است بگوییم ponyfill که عملکردی را به عنوان یک ماژول مستقل ارائه می دهد که می توانید از آن استفاده کنید) به نام webtransport-ponyfill-websocket که برخی از ویژگی های WebTransport را پیاده سازی می کند در دسترس است. محدودیت های موجود در README پروژه را با دقت بخوانید تا مشخص کنید که آیا این راه حل می تواند برای مورد استفاده شما کار کند یا خیر.

ملاحظات حفظ حریم خصوصی و امنیتی

برای راهنمایی معتبر به بخش مربوطه از مشخصات پیش نویس مراجعه کنید.

بازخورد

تیم Chrome می‌خواهد نظرات و تجربیات شما را با استفاده از این API بشنود.

بازخورد در مورد طراحی API

آیا چیزی در مورد API وجود دارد که ناخوشایند باشد یا آنطور که انتظار می رود کار نمی کند؟ یا قطعات گم شده ای هستند که برای اجرای ایده خود به آنها نیاز دارید؟

یک مشکل را در مخزن Web Transport GitHub ثبت کنید یا افکار خود را به یک مشکل موجود اضافه کنید.

مشکل در اجرا؟

آیا اشکالی در پیاده سازی کروم پیدا کردید؟

یک اشکال را در https://new.crbug.com ثبت کنید. تا جایی که می توانید جزئیات را همراه با دستورالعمل های ساده برای بازتولید قرار دهید.

آیا قصد استفاده از API را دارید؟

پشتیبانی عمومی شما به Chrome کمک می‌کند ویژگی‌ها را اولویت‌بندی کند و به سایر فروشندگان مرورگر نشان می‌دهد که چقدر حمایت از آنها ضروری است.

  • با استفاده از هشتگ #WebTransport و جزئیات مکان و نحوه استفاده از آن، یک توییت به @ChromiumDev ارسال کنید.

بحث کلی

می‌توانید از گروه Google web-transport-dev برای سؤالات عمومی یا مشکلاتی که در یکی از دسته‌های دیگر نمی‌گنجد استفاده کنید.

قدردانی ها

این مقاله حاوی اطلاعاتی از WebTransport Explainer , مشخصات پیش نویس و اسناد طراحی مرتبط است . از نویسندگان مربوطه برای ارائه این پایه تشکر می کنم.

تصویر قهرمان در این پست توسط Robin Pierre در Unsplash است.