@@ -764,19 +764,32 @@ function sysctl_parameters() {
764764
765765/**
766766 * Removes entry of the site from /etc/hosts
767+ * Optimized for Docker environments to prevent Inode/Device busy errors.
767768 *
768769 * @param string $site_url site name.
769- *
770+ * @throws Exception If /etc/hosts cannot be read or written.
770771 */
771772function remove_etc_hosts_entry ( $ site_url ) {
772- $ fs = new Filesystem ();
773773
774- $ hosts_file = file_get_contents ( '/etc/hosts ' );
774+ // 1. Read /etc/hosts file; suppress warnings and handle failure manually
775+ $ hosts_file = @file_get_contents ( '/etc/hosts ' );
776+ if ( $ hosts_file === false ) {
777+ throw new Exception ( "Failed to read /etc/hosts " );
778+ }
779+
780+ // 2. Escape special characters in domain (e.g., dots) for regex safety
781+ $ site_url_escaped = preg_quote ( $ site_url , '/ ' );
782+
783+ // 3. Remove the specific line matching the Localhost IP and the site URL
784+ $ hosts_file_new = preg_replace ( "/127\.0\.0\.1\s+ $ site_url_escaped \n/ " , '' , $ hosts_file );
775785
776- $ site_url_escaped = preg_replace ( '/\./ ' , '\. ' , $ site_url );
777- $ hosts_file_new = preg_replace ( "/127\.0\.0\.1\s+ $ site_url_escaped \n/ " , '' , $ hosts_file );
786+ // 4. Overwrite file directly to maintain the Inode (fixes Docker mount issues)
787+ // Using LOCK_EX to prevent race conditions during write
788+ $ result = file_put_contents ( '/etc/hosts ' , $ hosts_file_new , LOCK_EX );
778789
779- $ fs ->dumpFile ( '/etc/hosts ' , $ hosts_file_new );
790+ if ( $ result === false ) {
791+ throw new Exception ( "Failed to update /etc/hosts " );
792+ }
780793}
781794
782795/**
0 commit comments