Mempertahankan nama host HTTP asli antara proksi terbalik dan aplikasi web back-end-nya

Azure API Management
Azure App Service
Azure Application Gateway
Azure Front Door
Azure Spring Apps

Kami menyarankan agar Anda mempertahankan nama host HTTP asli saat Anda menggunakan proksi terbalik di depan aplikasi web. Memiliki nama host yang berbeda di proksi terbalik daripada yang disediakan untuk server aplikasi back-end dapat menyebabkan cookie atau URL pengalihan yang tidak berfungsi dengan baik. Misalnya, status sesi bisa hilang, autentikasi dapat gagal, atau URL back-end secara tidak sengaja dapat diekspos ke pengguna akhir. Anda dapat menghindari masalah ini dengan mempertahankan nama host permintaan awal sehingga server aplikasi melihat domain yang sama dengan browser web.

Panduan ini berlaku terutama untuk aplikasi yang dihosting dalam penawaran platform as a service (PaaS) seperti Azure App Service dan Azure Spring Apps. Artikel ini menyediakan panduan implementasi khusus untuk Azure Application Gateway, Azure Front Door, dan Azure API Management, yang umumnya digunakan layanan proksi terbalik.

Catatan

API Web umumnya kurang sensitif terhadap masalah yang disebabkan oleh ketidakcocokan nama host. Mereka biasanya tidak bergantung pada cookie, kecuali Anda menggunakan cookie untuk mengamankan komunikasi antara aplikasi satu halaman dan API back-end-nya, misalnya, dalam pola yang dikenal sebagai Backend untuk Frontend. API Web sering tidak mengembalikan URL absolut kembali ke diri mereka sendiri, kecuali dalam gaya API tertentu, seperti OData dan HATEOAS. Jika implementasi API Anda bergantung pada cookie atau menghasilkan URL absolut, panduan yang diberikan dalam artikel ini berlaku.

Jika Anda memerlukan TLS/SSL end-to-end (koneksi antara proksi terbalik dan layanan back-end menggunakan HTTPS), layanan back-end juga memerlukan sertifikat TLS yang cocok untuk nama host asli. Persyaratan ini menambah kompleksitas operasional saat Anda menyebarkan dan memperbarui sertifikat, tetapi banyak layanan PaaS menawarkan sertifikat TLS gratis yang dikelola sepenuhnya.

Konteks

Host permintaan HTTP

Dalam banyak kasus, server aplikasi atau beberapa komponen dalam alur permintaan membutuhkan nama domain internet yang digunakan oleh browser untuk mengaksesnya. Ini adalah host permintaan. Ini bisa menjadi alamat IP, tetapi biasanya nama seperti contoso.com (yang kemudian diselesaikan browser ke alamat IP dengan menggunakan DNS). Nilai host biasanya ditentukan dari komponen host dari URI permintaan, yang dikirim browser ke aplikasi sebagai Host header HTTP.

Penting

Jangan pernah menggunakan nilai host dalam mekanisme keamanan. Nilai disediakan oleh browser atau beberapa agen pengguna lain dan dapat dengan mudah dimanipulasi oleh pengguna akhir.

Dalam beberapa skenario, terutama ketika ada proksi terbalik HTTP dalam rantai permintaan, header host asli dapat diubah sebelum mencapai server aplikasi. Proksi terbalik menutup sesi jaringan klien dan menyiapkan koneksi baru ke ujung belakang. Dalam sesi baru ini, dapat membawa nama host asli sesi klien atau mengatur yang baru. Dalam kasus terakhir, proksi sering kali masih mengirim nilai host asli di header HTTP lainnya, seperti Forwarded atau X-Forwarded-Host. Nilai ini memungkinkan aplikasi untuk menentukan nama host asli, tetapi hanya jika dikodekan untuk membaca header ini.

Mengapa platform web menggunakan nama host

Layanan PaaS multipenyewa sering memerlukan nama host yang terdaftar dan divalidasi untuk merutekan permintaan masuk ke server back-end penyewa yang sesuai. Ini karena biasanya ada kumpulan penyeimbang beban bersama yang menerima permintaan masuk untuk semua penyewa. Penyewa biasanya menggunakan nama host masuk untuk mencari ujung belakang yang benar untuk penyewa pelanggan.

Untuk memudahkan memulai, platform ini biasanya menyediakan domain default yang telah dikonfigurasi sebelumnya untuk merutekan lalu lintas ke instans yang Anda sebarkan. Untuk App Service, domain default ini adalah azurewebsites.net. Setiap aplikasi web yang Anda buat mendapatkan subdomainnya sendiri, misalnya, contoso.azurewebsites.net. Demikian pula, domain default adalah azuremicroservices.io untuk Spring Apps dan azure-api.net untuk API Management.

Untuk penyebaran produksi, Anda tidak menggunakan domain default ini. Sebagai gantinya, Anda menyediakan domain Anda sendiri untuk selaras dengan merek organisasi atau aplikasi Anda. Misalnya, contoso.com dapat menyelesaikan di balik layar ke contoso.azurewebsites.net aplikasi web di App Service, tetapi domain ini tidak boleh terlihat oleh pengguna akhir yang mengunjungi situs web. Nama host kustom contoso.com ini harus didaftarkan dengan layanan PaaS, sehingga platform dapat mengidentifikasi server back-end yang harus merespons permintaan.

Diagram that illustrates host-based routing in App Service.

Mengapa aplikasi menggunakan nama host

Dua alasan umum bahwa server aplikasi membutuhkan nama host adalah untuk membuat URL absolut dan mengeluarkan cookie untuk domain tertentu. Misalnya, ketika kode aplikasi perlu:

  • Mengembalikan URL absolut daripada URL relatif dalam respons HTTP-nya (meskipun umumnya situs web cenderung merender tautan relatif jika memungkinkan).
  • Buat URL yang akan digunakan di luar respons HTTP-nya di mana URL relatif tidak dapat digunakan, seperti untuk mengirim tautan melalui email ke situs web kepada pengguna.
  • Buat URL pengalihan absolut untuk layanan eksternal. Misalnya, ke layanan autentikasi seperti MICROSOFT Entra ID untuk menunjukkan di mana ia harus mengembalikan pengguna setelah autentikasi berhasil.
  • Terbitkan cookie HTTP yang dibatasi untuk host tertentu, seperti yang didefinisikan dalam atribut cookieDomain.

Anda dapat memenuhi semua persyaratan ini dengan menambahkan nama host yang diharapkan ke konfigurasi aplikasi dan menggunakan nilai yang ditentukan secara statis alih-alih nama host masuk pada permintaan. Namun, pendekatan ini mempersulit pengembangan dan penyebaran aplikasi. Selain itu, satu instalasi aplikasi dapat melayani beberapa host. Misalnya, satu aplikasi web dapat digunakan untuk beberapa penyewa aplikasi yang semuanya memiliki nama host unik mereka sendiri (seperti tenant1.contoso.com dan tenant2.contoso.com).

Dan terkadang nama host masuk digunakan oleh komponen di luar kode aplikasi atau di middleware di server aplikasi tempat Anda tidak memiliki kontrol penuh. Berikut adalah beberapa contoh:

  • Di App Service, Anda dapat menerapkan HTTPS untuk aplikasi web Anda. Melakukannya menyebabkan permintaan HTTP apa pun yang tidak aman untuk dialihkan ke HTTPS. Dalam hal ini, nama host masuk digunakan untuk menghasilkan URL absolut untuk header pengalihan Location HTTP.
  • Spring Apps menggunakan fitur serupa untuk memberlakukan HTTPS. Ini juga menggunakan host masuk untuk menghasilkan URL HTTPS.
  • App Service memiliki pengaturan afinitas ARR untuk mengaktifkan sesi lengket, sehingga permintaan dari instans browser yang sama selalu dilayani oleh server back-end yang sama. Ini dilakukan oleh ujung depan App Service, yang menambahkan cookie ke respons HTTP. Cookie Domain diatur ke host masuk.
  • App Service menyediakan kemampuan autentikasi dan otorisasi untuk dengan mudah memungkinkan pengguna masuk dan mengakses data di API.

Mengapa Anda mungkin tergoda untuk mengambil alih nama host

Katakanlah Anda membuat aplikasi web di App Service yang memiliki domain contoso.azurewebsites.netdefault . (Atau di layanan lain seperti Spring Apps.) Anda belum mengonfigurasi domain kustom di App Service. Untuk menempatkan proksi terbalik seperti Application Gateway (atau layanan serupa) di depan aplikasi ini, Anda mengatur catatan DNS untuk contoso.com diselesaikan ke alamat IP Application Gateway. Oleh karena itu menerima permintaan contoso.com dari browser dan dikonfigurasi untuk meneruskan permintaan tersebut ke alamat IP yang contoso.azurewebsites.net diselesaikan: ini adalah layanan back-end akhir untuk host yang diminta. Namun, dalam hal ini, App Service tidak mengenali contoso.com domain kustom dan menolak semua permintaan masuk untuk nama host ini. Ini tidak dapat menentukan tempat untuk merutekan permintaan.

Mungkin tampak seperti cara mudah untuk membuat konfigurasi ini berfungsi adalah dengan mengambil alih atau menulis Host ulang header permintaan HTTP di Application Gateway dan mengaturnya ke nilai contoso.azurewebsites.net. Jika Anda melakukannya, permintaan keluar dari Application Gateway membuatnya tampak seperti permintaan asli benar-benar ditujukan untuk contoso.azurewebsites.net alih-alih contoso.com:

Diagram that illustrates a configuration with the host name overridden.

Pada titik ini, App Service mengenali nama host, dan menerima permintaan tanpa mengharuskan nama domain kustom dikonfigurasi. Bahkan, Application Gateway memudahkan untuk mengambil alih header host dengan host kumpulan back-end. Azure Front Door bahkan melakukannya secara default.

Namun, masalah dengan solusi ini adalah dapat mengakibatkan berbagai masalah ketika aplikasi tidak melihat nama host asli.

Potensi masalah

URL absolut yang salah

Jika nama host asli tidak dipertahankan dan server aplikasi menggunakan nama host masuk untuk menghasilkan URL absolut, domain back-end mungkin diungkapkan kepada pengguna akhir. URL absolut ini dapat dihasilkan oleh kode aplikasi atau, seperti yang disebutkan sebelumnya, oleh fitur platform seperti dukungan untuk pengalihan HTTP-ke-HTTPS di App Service dan Spring Apps. Diagram ini mengilustrasikan masalah:

Diagram that illustrates the problem of incorrect absolute URLs.

  1. Browser mengirimkan permintaan ke contoso.com proksi terbalik.
  2. Proksi terbalik menulis ulang nama host ke contoso.azurewebsites.net dalam permintaan ke aplikasi web back-end (atau ke domain default serupa untuk layanan lain).
  3. Aplikasi ini menghasilkan URL absolut yang didasarkan pada nama host masuk contoso.azurewebsites.net , misalnya, https://contoso.azurewebsites.net/.
  4. Browser mengikuti URL ini, yang langsung masuk ke layanan back-end daripada kembali ke proksi terbalik di contoso.com.

Ini bahkan dapat menimbulkan risiko keamanan dalam kasus umum di mana proksi terbalik juga berfungsi sebagai firewall aplikasi web. Pengguna menerima URL yang langsung masuk ke aplikasi back-end dan melewati proksi terbalik.

Penting

Karena risiko keamanan ini, Anda perlu memastikan bahwa aplikasi web back-end hanya langsung menerima lalu lintas jaringan dari proksi terbalik (misalnya, dengan menggunakan pembatasan akses di App Service). Jika Anda melakukannya, bahkan jika URL absolut yang salah dihasilkan, setidaknya url tersebut tidak berfungsi dan tidak dapat digunakan oleh pengguna berbahaya untuk melewati firewall.

URL pengalihan yang salah

Kasus umum dan lebih spesifik dari skenario sebelumnya terjadi ketika URL pengalihan absolut dihasilkan. URL ini diperlukan oleh layanan identitas seperti ID Microsoft Entra saat Anda menggunakan protokol identitas berbasis browser seperti OpenID Koneksi, OAuth 2.0, atau SAML 2.0. URL pengalihan ini dapat dihasilkan oleh server aplikasi atau middleware itu sendiri, atau, seperti yang disebutkan sebelumnya, oleh fitur platform seperti kemampuan autentikasi dan otorisasi App Service. Diagram ini mengilustrasikan masalah:

Diagram that illustrates the problem of incorrect redirect URLs.

  1. Browser mengirimkan permintaan ke contoso.com proksi terbalik.
  2. Proksi terbalik menulis ulang nama host ke contoso.azurewebsites.net pada permintaan ke aplikasi web back-end (atau ke domain default serupa untuk layanan lain).
  3. Aplikasi ini menghasilkan URL pengalihan absolut yang didasarkan pada nama host masuk contoso.azurewebsites.net , misalnya, https://contoso.azurewebsites.net/.
  4. Browser masuk ke penyedia identitas untuk mengautentikasi pengguna. Permintaan mencakup URL pengalihan yang dihasilkan untuk menunjukkan tempat mengembalikan pengguna setelah autentikasi berhasil.
  5. Penyedia identitas biasanya mengharuskan URL pengalihan didaftarkan di muka, jadi pada titik ini penyedia identitas harus menolak permintaan karena URL pengalihan yang disediakan tidak terdaftar. (Seharusnya tidak digunakan.) Namun, jika karena alasan tertentu URL pengalihan terdaftar, penyedia identitas mengalihkan browser ke URL pengalihan yang ditentukan dalam permintaan autentikasi. Dalam hal ini, URL adalah https://contoso.azurewebsites.net/.
  6. Browser mengikuti URL ini, yang langsung masuk ke layanan back-end daripada kembali ke proksi terbalik.

Cookie rusak

Ketidakcocokan nama host juga dapat menyebabkan masalah ketika server aplikasi mengeluarkan cookie dan menggunakan nama host masuk untuk membangun Domain atribut cookie. Atribut Domain memastikan bahwa cookie hanya akan digunakan untuk domain tertentu. Cookie ini dapat dihasilkan oleh kode aplikasi atau, seperti yang disebutkan sebelumnya, berdasarkan fitur platform seperti pengaturan afinitas ARR App Service. Diagram ini mengilustrasikan masalah:

Diagram that illustrates an incorrect cookie domain.

  1. Browser mengirimkan permintaan ke contoso.com proksi terbalik.
  2. Proksi terbalik menulis ulang nama host untuk berada contoso.azurewebsites.net dalam permintaan ke aplikasi web back-end (atau ke domain default serupa untuk layanan lain).
  3. Aplikasi ini menghasilkan cookie yang menggunakan domain berdasarkan nama host masuk contoso.azurewebsites.net . Browser menyimpan cookie untuk domain khusus ini daripada contoso.com domain yang benar-benar digunakan pengguna.
  4. Browser tidak menyertakan cookie pada permintaan contoso.com berikutnya karena domain cookie contoso.azurewebsites.net tidak cocok dengan domain permintaan. Aplikasi tidak menerima cookie yang dikeluarkan sebelumnya. Akibatnya, pengguna mungkin kehilangan status yang seharusnya ada di cookie, atau fitur seperti afinitas ARR tidak berfungsi. Sayangnya, tidak ada masalah ini yang menghasilkan kesalahan atau langsung terlihat oleh pengguna akhir. Itu membuat mereka sulit untuk memecahkan masalah.

Panduan implementasi untuk layanan Azure umum

Untuk menghindari potensi masalah yang dibahas di sini, kami sarankan Anda mempertahankan nama host asli dalam panggilan antara proksi terbalik dan server aplikasi back-end:

Diagram that shows a configuration in which the host name is preserved.

Konfigurasi back-end

Banyak platform hosting web mengharuskan Anda secara eksplisit mengonfigurasi nama host masuk yang diizinkan. Bagian berikut menjelaskan cara menerapkan konfigurasi ini untuk layanan Azure yang paling umum. Platform lain biasanya menyediakan metode serupa untuk mengonfigurasi domain kustom.

Jika Anda menghosting aplikasi web di App Service, Anda dapat melampirkan nama domain kustom ke aplikasi web dan menghindari penggunaan nama host default azurewebsites.net di ujung belakang. Anda tidak perlu mengubah resolusi DNS saat melampirkan domain kustom ke aplikasi web: Anda bisa memverifikasi domain dengan menggunakan TXT catatan tanpa memengaruhi reguler CNAME atau A rekaman Anda. (Rekaman ini masih akan diselesaikan ke alamat IP proksi terbalik.) Jika Anda memerlukan TLS/SSL end-to-end, Anda dapat mengimpor sertifikat yang ada dari Key Vault atau menggunakan Sertifikat App Service untuk domain kustom Anda. (Perhatikan bahwa gratis Sertifikat terkelola App Service tidak dapat digunakan dalam kasus ini, karena memerlukan catatan DNS domain untuk diselesaikan langsung ke App Service, bukan proksi terbalik.)

Demikian pula, jika Anda menggunakan Spring Apps, Anda dapat menggunakan domain kustom untuk aplikasi Anda untuk menghindari penggunaan azuremicroservices.io nama host. Anda dapat mengimpor sertifikat yang sudah ada atau ditandatangani sendiri jika Anda memerlukan TLS/SSL end-to-end.

Jika Anda memiliki proksi terbalik di depan API Management (yang juga bertindak sebagai proksi terbalik), Anda dapat mengonfigurasi domain kustom pada instans API Management Anda untuk menghindari penggunaan azure-api.net nama host. Anda dapat mengimpor sertifikat terkelola yang ada atau gratis jika Anda memerlukan TLS/SSL end-to-end. Namun, seperti yang disebutkan sebelumnya, API kurang sensitif terhadap masalah yang disebabkan oleh ketidakcocokan nama host, sehingga konfigurasi ini mungkin tidak sepenting.

Jika Anda menghosting aplikasi di platform lain, seperti di Kubernetes atau langsung di komputer virtual, tidak ada fungsionalitas bawaan yang bergantung pada nama host yang masuk. Anda bertanggung jawab atas bagaimana nama host digunakan di server aplikasi itu sendiri. Rekomendasi untuk mempertahankan nama host biasanya masih berlaku untuk komponen apa pun dalam aplikasi Anda yang bergantung padanya, kecuali Anda secara khusus membuat aplikasi Anda menyadari proksi terbalik dan menghormati forwarded header atau X-Forwarded-Host , misalnya.

Konfigurasi proksi terbalik

Saat Anda menentukan ujung belakang dalam proksi terbalik, Anda masih dapat menggunakan domain default layanan back-end, misalnya, https://contoso.azurewebsites.net/. URL ini digunakan oleh proksi terbalik untuk menyelesaikan alamat IP yang benar untuk layanan back-end. Jika Anda menggunakan domain default platform, alamat IP selalu dijamin benar. Anda biasanya tidak dapat menggunakan domain yang menghadap publik, seperti contoso.com, karena harus diselesaikan ke alamat IP proksi terbalik itu sendiri. (Kecuali Anda menggunakan teknik resolusi DNS yang lebih canggih, seperti DNS split-horizon).

Penting

Jika Anda memiliki firewall generasi berikutnya seperti Azure Firewall Premium antara proksi terbalik dan back end akhir, Anda mungkin perlu menggunakan DNS split-horizon. Jenis firewall ini mungkin secara eksplisit memeriksa apakah header HTTP Host diselesaikan ke alamat IP target. Dalam kasus ini, nama host asli yang digunakan oleh browser harus diselesaikan ke alamat IP proksi terbalik ketika diakses dari internet publik. Namun, dari sudut pandang firewall, nama host tersebut harus diselesaikan ke alamat IP layanan back-end akhir. Untuk informasi selengkapnya, lihat Jaringan zero-trust untuk aplikasi web dengan Azure Firewall dan Application Gateway.

Sebagian besar proksi terbalik memungkinkan Anda mengonfigurasi nama host mana yang diteruskan ke layanan back-end. Informasi berikut menjelaskan cara memastikan, untuk layanan Azure yang paling umum, bahwa nama host asli permintaan masuk digunakan.

Catatan

Dalam semua kasus, Anda juga dapat memilih untuk mengambil alih nama host dengan domain kustom yang ditentukan secara eksplisit daripada mengambilnya dari permintaan masuk. Jika aplikasi hanya menggunakan satu domain, pendekatan tersebut mungkin berfungsi dengan baik. Jika penyebaran aplikasi yang sama menerima permintaan dari beberapa domain (misalnya, dalam skenario multipenyewa), Anda tidak dapat menentukan satu domain secara statis. Anda harus mengambil nama host dari permintaan masuk (sekali lagi, kecuali aplikasi secara eksplisit dikodekan untuk memperhitungkan header HTTP tambahan). Oleh karena itu, rekomendasi umumnya adalah Anda tidak boleh mengambil alih nama host sama sekali. Teruskan nama host masuk yang tidak dimodifikasi ke ujung belakang.

Application Gateway

Jika Anda menggunakan Application Gateway sebagai proksi terbalik, Anda dapat memastikan bahwa nama host asli dipertahankan dengan menonaktifkan Ambil alih dengan nama host baru pada pengaturan HTTP back-end. Melakukannya menonaktifkan Pilih nama host dari alamat back-end dan Ambil alih dengan nama domain tertentu. (Kedua pengaturan ini mengambil alih nama host.) Di properti Azure Resource Manager untuk Application Gateway, konfigurasi ini sesuai dengan pengaturan hostName properti ke null dan pickHostNameFromBackendAddress ke false.

Karena pemeriksaan kesehatan dikirim di luar konteks permintaan masuk, mereka tidak dapat menentukan nama host yang benar secara dinamis. Sebagai gantinya, Anda harus membuat pemeriksaan kesehatan kustom, menonaktifkan Pilih nama host dari pengaturan HTTP backend, dan secara eksplisit menentukan nama host. Untuk nama host ini, Anda juga harus menggunakan domain kustom yang sesuai, untuk konsistensi. (Namun, Anda dapat menggunakan domain default platform hosting di sini, karena pemeriksaan kesehatan mengabaikan cookie yang salah atau MENGAlihkan URL dalam respons.)

Azure Front Door

Jika Anda menggunakan Azure Front Door, Anda dapat menghindari penggantian nama host dengan membiarkan header host back-end kosong dalam definisi kumpulan back-end. Dalam definisi Resource Manager dari kumpulan back-end, konfigurasi ini sesuai dengan pengaturan backendHostHeader ke null.

Jika Anda menggunakan Azure Front Door Standard atau Premium, Anda dapat mempertahankan nama host dengan membiarkan header host asal kosong dalam definisi asal. Dalam definisi Resource Manager asal, konfigurasi ini sesuai dengan pengaturan originHostHeader ke null.

API Management

Secara default, API Management mengambil alih nama host yang dikirim ke ujung belakang dengan komponen host URL layanan web API (yang sesuai dengan serviceUrl nilai definisi Resource Manager API).

Anda dapat memaksa API Management untuk menggunakan nama host permintaan masuk dengan menambahkan inboundkebijakan Atur header HTTP, sebagai berikut:

<inbound>
  <base />
  <set-header name="Host" exists-action="override">
    <value>@(context.Request.OriginalUrl.Host)</value>
  </set-header>
</inbound>

Namun, seperti yang disebutkan sebelumnya, API kurang sensitif terhadap masalah yang disebabkan oleh ketidakcocokan nama host, sehingga konfigurasi ini mungkin tidak sepenting.

Langkah berikutnya