Skrip saya dipanggil oleh server. Dari server saya akan menerima ID_OF_MESSAGE
dan TEXT_OF_MESSAGE
.
Dalam skrip saya, saya akan menangani teks yang masuk dan menghasilkan respons dengan params: ANSWER_TO_ID
dan RESPONSE_MESSAGE
.
Masalahnya adalah saya mengirim tanggapan ke incomming "ID_OF_MESSAGE"
, tetapi server yang mengirimi saya pesan untuk ditangani akan mengatur pesannya sebagai dikirim kepada saya (Artinya saya dapat mengirimnya tanggapan ke ID itu), setelah menerima tanggapan http 200.
Salah satu solusinya adalah menyimpan pesan ke database dan membuat beberapa cron yang akan berjalan setiap menit, tetapi saya perlu segera menghasilkan pesan tanggapan.
Apakah ada solusi bagaimana mengirim ke server http response 200 dan kemudian melanjutkan menjalankan script php?
Terima kasih banyak
header("Content-Encoding: none")
fastcgi_finish_request()
di bagian akhirSaya telah melihat banyak tanggapan di sini yang menyarankan penggunaan
ignore_user_abort(true);
tetapi kode ini tidak diperlukan. Semua ini dilakukan untuk memastikan skrip Anda terus berjalan sebelum respons dikirim jika pengguna membatalkan (dengan menutup browser mereka atau menekan escape untuk menghentikan permintaan). Tapi bukan itu yang Anda tanyakan. Anda meminta untuk melanjutkan eksekusi SETELAH tanggapan dikirim. Yang Anda butuhkan hanyalah sebagai berikut:Jika Anda khawatir bahwa pekerjaan latar belakang Anda akan memakan waktu lebih lama dari batas waktu eksekusi skrip default PHP, maka tetaplah
set_time_limit(0);
di bagian atas.sumber
Jika Anda menggunakan pemrosesan FastCGI atau PHP-FPM, Anda dapat:
Sumber: https://www.php.net/manual/en/function.fastcgi-finish-request.php
Masalah PHP # 68722: https://bugs.php.net/bug.php?id=68772
sumber
Saya menghabiskan beberapa jam untuk masalah ini dan saya datang dengan fungsi ini yang berfungsi pada Apache dan Nginx:
Anda dapat memanggil fungsi ini sebelum pemrosesan panjang Anda.
sumber
filter_input
fungsinya kadang-kadang mengembalikan NULL. lihat kontribusi pengguna ini untuk detailSedikit mengubah jawaban oleh @vcampitelli. Jangan berpikir Anda membutuhkan
close
header. Saya melihat header dekat duplikat di Chrome.sumber
Saya menggunakan fungsi register_shutdown_function php untuk ini.
http://php.net/manual/en/function.register-shutdown-function.php
Edit : Di atas tidak berfungsi. Sepertinya saya disesatkan oleh beberapa dokumentasi lama. Perilaku register_shutdown_function telah berubah sejak link link PHP 4.1
sumber
Saya tidak dapat menginstal pthread dan tidak ada solusi sebelumnya yang berfungsi untuk saya. Saya hanya menemukan solusi berikut untuk berfungsi (ref: https://stackoverflow.com/a/14469376/1315873 ):
sumber
dalam kasus penggunaan file_get_contents php, koneksi dekat tidak cukup. php masih menunggu eof witch dikirim oleh server.
solusi saya adalah membaca 'Panjang-Konten:'
berikut ini contohnya:
response.php:
Perhatikan "\ n" dalam menanggapi baris penutup, jika tidak fget dibaca sambil menunggu eof.
read.php:
Seperti yang Anda lihat, dosis skrip ini menunggu tentang eof jika panjang konten tercapai.
semoga membantu
sumber
Saya mengajukan pertanyaan ini kepada Rasmus Lerdorf pada bulan April 2012, mengutip artikel berikut:
Saya menyarankan pengembangan fungsi built-in PHP baru untuk memberi tahu platform bahwa tidak ada output lebih lanjut (pada stdout?) Yang akan dihasilkan (fungsi seperti itu mungkin menangani penutupan koneksi). Rasmus Lerdorf menjawab:
Saya dapat memahami maksudnya, dan mendukung pendapatnya untuk beberapa skenario aplikasi / pemuatan! Namun, dalam beberapa skenario lain, solusi dari vcampitelli et al, adalah solusi yang baik.
sumber
Saya memiliki sesuatu yang dapat dikompresi dan mengirim respons dan membiarkan kode php lain dijalankan.
sumber
Ada pendekatan lain dan pertimbangan yang berharga jika Anda tidak ingin merusak header respons. Jika Anda memulai utas pada proses lain, fungsi yang dipanggil tidak akan menunggu tanggapannya dan akan kembali ke browser dengan kode http yang telah diselesaikan. Anda perlu mengkonfigurasi pthread .
Setelah kita menjalankan $ continue_processing-> start () PHP tidak akan menunggu hasil kembalian dari utas ini dan oleh karena itu sejauh rest_endpoint dianggap. Selesai.
Beberapa tautan untuk membantu dengan pthreads
Semoga berhasil.
sumber
Saya tahu ini sudah lama, tapi mungkin berguna saat ini.
Dengan jawaban ini saya tidak mendukung pertanyaan yang sebenarnya tetapi bagaimana mengatasi masalah ini dengan benar. Semoga bisa membantu orang lain untuk memecahkan masalah seperti ini.
Saya akan menyarankan untuk menggunakan RabbitMQ atau layanan serupa dan menjalankan beban kerja latar belakang menggunakan instance pekerja . Ada sebuah paket bernama amqplib untuk php yang melakukan semua pekerjaan bagi Anda untuk menggunakan RabbitMQ.
Pro:
Neg ini:
sumber